Resolute Public API Reference Guide
Introduction
This reference guide is intended for customers and authorized partners interested in programmatically connecting to Resolute software applications and retrieving relevant data for use in complimentary software applications. This guide addresses security and authentication matters associated with the successful access and use of the Resolute Public API library and provides a list of currently available Resolute APIs.
Security and Authentication
Client Credentials
Upon request, Resolute will provide you with a set of client credentials that consist of a client id and a client secret. It is important that you securely store your credentials immediately upon receipt, as there is no way to recover these values. If your credentials are compromised, a new set of credentials will need to be provided.
Security Assumptions
The current implementation of the Resolute public APIs is based on the following assumptions:
- Clients (i.e., customers and partners) will keep their credentials secret.
- Clients will never invoke the Resolute APIs from a browser or mobile device, since doing so would compromise the client id and client secret. Only server-to-server invocations are supported.
- All communications with the REST server must be conducted over HTTPS. Any API invocations conducted over an insecure channel will be redirected to HTTPS.
Authentication
Before invoking public APIs exposed by Resolute, you must authenticate using your client credentials by issuing a GET request using Basic Auth to the /authorize
endpoint. Once completed, you will receive a valid JWT bearer token. This bearer token must be included with calls to all other API endpoints. Failure to do so will result in a 401 Unauthorized response. Bearer tokens expire after a certain amount of time and are no longer considered valid. When this occurs, you must re-authenticate to the /authorize
endpoint to receive a new bearer token.
/authorize endpoint
To authenticate with the /authorize
endpoint, make sure to issue a GET request over HTTPS that includes the following HTTP request header for Basic Authentication:
Authorization: Basic Base64(client_id + ':' + client_secret)
Example: Suppose that you were issued the following client credentials:
Client Id: 46d2431b-519a-44f1-9c24-0f32b6e89e7bClient Secret: e3d39585-8855-4cf8-a778-0a74c5229f44
You would first concatenate these credentials, separated by a colon, to produce the following string:
46d2431b-519a-44f1-9c24-0f32b6e89e7b:e3d39585-8855-4cf8-a778-0a74c5229f44
You would then apply the Base64 encoding algorithm to this string to generate the following value:
NDZkMjQzMWItNTE5YS00NGYxLTljMjQtMGYzMmI2ZTg5ZTdiOmUzZDM5NTg1LTg4NTUtNGNmOC1hNzc4LTBhNzRjNTIyOWY0NA==
Finally, you would invoke the /authorize
endpoint by issuing a GET request that includes the following HTTP request header:
Authorization: Basic NDZkMjQzMWItNTE5YS00NGYxLTljMjQtMGYzMmI2ZTg5ZTdiOmUzZDM5NTg1LTg4NTUtNGNmOC1hNzc4LTBhNzRjNTIyOWY0NA==
If the credentials correspond to a valid client, the /authorize
endpoint will return a response that looks like the following:
{
"access_token" : "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiaWF0IjoxNTE2MjM5MDIyfQ.SflKxwRJSMeKKF2QT4fwpMeJf36POk6yJV_adQssw5c", "token_type" : "bearer",
"expires_in" : 21600
}
After invoking the /authorize
endpoint, store the value of the access_token
in memory, since you will need to include it in subsequent calls to all other API endpoints.
The value of the expires_in
attribute represents the number of seconds before the access token will expire. When the access token expires, the client will need to repeat their invocation of the /authorize
endpoint to obtain a new access token.
Other endpoints
For all other endpoints, you must issue a request that includes the following HTTP request header:
Authorization: Bearer access_token
For instance, using the previous example in which the /authorize
endpoint returned an access token starting with the letters eyJhbGc
, your HTTP request header would look as follows:
Authorization: Bearer
eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiaWF0IjoxNTE2MjM5MDIyfQ.SflKxwRJSMeKKF2QT4fwpMeJf36POk6yJV_adQssw5c
If you fail to include a valid access token with each request, a 401 Unauthorized error will be returned. Note that the access tokens are digitally signed by Resolute and adhere to the JSON Web Tokens (JWT) standard (see https://tools.ietf.org/html/rfc7519 for more information). Expired tokens and tokens that cannot be validated based on their signature will be rejected by Resolute, resulting in a 401 Unauthorized error.
Currently Available Resolute Public APIs
All of the public API endpoints, including the /authorize
endpoint, are accessible by appending the specified endpoint path to the following base URL:
https://api.resolutebi.com
Retrieve Customers
Retrieve a list of all customers that the current client has access to.
Endpoint
GET /customers
Sample Output
1 [ 2 { 3 "id": "3526416c-22d0-4302-b733-aa782853dcbe", 4 "name": "Customer Name" 5 }, 6 { 7 "id": "6fc0f74e-684f-4b33-9962-2adbc767dbd0", 8 "name"": "Customer Name" 9 } 10]
Retrieve Buildings for a Given Customer
Retrieve a list of all buildings associated with the specified customer.
Endpoint
GET /customers/{customerId}/buildings
Sample Output
1[
2 {
3 "id": "35264a6c-22d0-4302-b733-aa782853dcbe",
4 "name": "Customer ID"
5 },
6 {
7 "id": "6fc0f74e-684f-4b33-9962-2adbc767dbd0",
8 "name": "Customer ID"
9 }
10]
Retrieve Report Definitions
Retrieve a list of all reports currently defined within the Resolute product.
Endpoint
GET /reports
Sample Output
1[
2 {
3 "id": "35264a6c-22d0-4302-b733-aa782853dcbe",
4 "name": "VAV Scorecard"
5 },
6 {
7 "id": "6fc0f74e-684f-4b33-9962-2adbc767dbd0",
8 "name": "AHU Operations"
9 }
10]
Retrieve Enabled Reports for a Given Building
Endpoint
GET /buildings/{buildingId}/reports
Sample Output
1[
2 {
3 "id": "35264a6c-22d0-4302-b733-aa782853dcbe",
4 "name": "VAV Scorecard"
5 },
6{
7"id": "6fc0f74e-684f-4b33-9962-2adbc767dbd0",
8 "name": "AHU Operations"
9 },
10]
Retrieve Equipment for a Given Building
Endpoint
GET /buildings/{buildingId}/equipment
Sample Output
1[
2 {
3“id”: “35264a6c-22d0-4302-b733-aa782853dcbe”,
4 “name”: “Building Name/subbuilding/floor/sc_VAV_51”,
5 “type”: “vav”
6 },
7 {
8 “id”: “48264a6c-22d0-4302-b733-aa782853dcbe”,
9 “name”: “Building Name/subbuilding/floor/sc_VAV_54”,
10 “type”: “vav”
11 }
12]
Note: The "type" attribute for a given piece of equipment will be absent if the piece of equipment in question has not yet been assigned to a type.
Retrieve all Generated Instances of a Given Report for a Given Building
Endpoint
GET /buildings/{buildingId}/reports/{reportId}/generatedReports
Sample Output
1[
2 {
3 "id": "35264a6c-22d0-4302-b733-aa782853dcbe",
4 "startDate": "2021-06-07",
5 "interval": "WEEKLY"
6 },
7 {
8 "id": "6fc0f74e-684f-4b33-9962-2adbc767dbd0",
9 "startDate": "2021-06-01",
10 "interval": "MONTHLY"
11 "url": "https://fusion.resolutebi.com/reports?id=67"
12 }
13]
Retrieve the Details for a Given Generated Report
Endpoint
GET /generatedReports/{generatedReportId}
Sample Output
If the Report definition supports the concept of a root cause, then each element in the "equipment" array will include a rootCause
attribute. If the report definition does not support the concept of a root cause, then the rootCause
attribute will be missing. In cases where the rootCause
element is present, it will be set to an empty string if the equipment score falls into the “good” category.
1{ 2 "equipment": [ 3 { 4 "id": "35264a6c-22d0-4302-b733-aa782853dcbe", 5 "name": "Sample Name", 6 "score": 78 7 "rootCause": " 8 }, 9 { 10 "id": "48264a6c-22d0-4302-b733-aa782853dcbe", 11 "name": "Sample Name", 12 "score": 52 13 "rootCause": "Cooling valve is overridden or poor cooling control” 14 }, 15 ... 16 ] 17}
Retrieve list of Action Center Tasks
Returns all tasks for a specific customer, or all tasks for a specific building, or a specific task.
Endpoint
POST /customers/{customerId}/actioncenter/tasks
Sample Input
Note: All request properties are optional, if a property is not specified, ALL is the default.
1{
2 "nodeId": 1,
3 "taskId": 1,
4 "viewType": "Public Actions", // ['Synergy Integrator Actions', 'Public Actions']
5 "sectionType": "Work Log", // ('Work Log' (Default), 'Blocked', 'Closed')
6 "typeIds": [1, 3, 5], // list of type ids [1=BAS, 2=Mechanical, 3=Capital, 4=ECM, 5=Maintenance, 6=Operational, 7=Observations, 8=Memo]
7 "customerTaskId": 1, // customerTaskId (a.k.a. taskId without "RES-" prefix)
8 "priorities": ["High"], // list of priorities ['Low', 'Medium', 'High']
9 "title": "te*", // wildcard-able string
10 "assignees": [328], // list of assignee ids --- use -1 for unassigned tasks
11 "statuses": ["Open Actions", "New Actions"], // list of statuses ['Open Actions', 'In Progress', 'New Actions', 'Old Actions', 'All Closed Actions', 'Closed Recently']. if sectionType = 'Closed' then Default = 'All Closed Actions'
12 "tags": [1, 4, 5], // list of tag ids
13}
Sample Output
List of Action Center Task JSON objects
1[
2 {
3 "id": 1,
4 "customerId": 4,
5 "customerTaskId": 1,
6 "taskId": "RES-1",
7 "nodeId": 41,
8 "typeId": 1,
9 "typeName": "BAS",
10 "typeColor": "#FBAA18",
11 "title": "test",
12 "description": "task id 1 customer 4",
13 "assigneeId": 328,
14 "assignedTo": "Assignee Name",
15 "creatorId": 328,
16 "createdBy": "Creator name",
17 "updatedAt": 1585022400000,
18 "createdAt": 1585022400000,
19 "effort": "Low",
20 "status": "Open",
21 "priority": "High",
22 "visibility": "Public",
23 "potentialSavingsLow": 1000,
24 "potentialSavingHigh": 3000,
25 "suggestedAction": "suggestion",
26 "tagsAsString": "C1, G1",
27 "statusUpdatedAt": "Open - 03/24/2021",
28 "tags": [],
29 "links": [],
30 "watchers": [
31 {
32 "userId": 307
33 }
34 ],
35 "comments": [
36 {
37 "userName": "John Smith",
38 "body": "Single zone unit operating as expected. Possibly import additional points to gain insight into entire unit operations, but this issue is closed."
39 }
40 ]
41 }
42]
AuthUserValidationError Output:
Client does not have access to any customers.
Client does not have access to the customer.
Client does not have access to the building.
Client does not have access to the task.
Invalid view type.
RequestValidation Output:
Invalid section type.
Invalid status(es) for section type of Work Log.
Invalid status(es) for section type of Closed.
Invalid status(es) for section type of Blocked.
Invalid effort(s).
Invalid priority(ies).
Invalid visibility(ies).
Add an Action Center Task
Endpoint
PUT /customers/{customerId}/actioncenter/task
Sample Input
1{
2 "nodeId": 41, \\required
3 "typeId": 1, \\required (1=BAS, 2=Mechanical, 3=Capital, 4=ECM, 5=Maintenance, 6=Operational, 7=Observations, 8=Memo)
4 "title": "new title", \\required
5 "status": "Open", \\required ('Open', 'In Progress', 'Blocked', 'Closed')
6 "priority": "High", \\required ('Low', 'Medium', 'High')
7 "effort": "Low", \\required ('Very Low', 'Low', 'Medium', 'High', 'Very High')
8 "visibility": "Public", \\required ('Public', 'Integrators')
9 "assigneeId": 396,
10 "description": "desc",
11 "blockedReason": "reason",
12 "blockedUntil": 1639307110000,
13 "potentialSavingsLow": 10,
14 "potentialSavingsHigh": 999,
15 "suggestedAction": "sug",
16 "implementationCost": "eye",
17 "roi": "nada",
18 "tags": [
19 {
20 "name": "G2" \\required
21 }
22 ],
23 "links": [
24 {
25 "name": "link 1",
26 "url": "url 1" \\required
27 }
28 ],
29 "watchers": [
30 {
31 "userId": 328 \\required
32 }
33 ]
34}
Sample Output
1{
2 "id": 13,
3 "customerId": 4,
4 "customerTaskId": 11,
5 "taskId": "RES-11",
6 "nodeId": 41,
7 "typeId": 1,
8 "typeName": "BAS",
9 "typeColor": "#FBAA18",
10 "title": "new title",
11 "description": "desc",
12 "assigneeId": 396,
13 "assignedTo": "John Smith",
14 "creatorId": 328,
15 "createdBy": "John Smith",
16 "updatedAt": 1613041913497,
17 "createdAt": 1613041913497,
18 "effort": "Low",
19 "status": "Open",
20 "priority": "High",
21 "visibility": "Public",
22 "blockedReason": "reason",
23 "blockedUntil": 1639307110000,
24 "potentialSavingsLow": 10,
25 "potentialSavingsHigh": 999,
26 "suggestedAction": "sug",
27 "implementationCost": "eye",
28 "roi": "nada",
29 "tags": [
30 {
31 "id": 21,
32 "taskId": 13,
33 "name": "C1"
34 }
35 ],
36 "links": [
37 {
38 "id": 13,
39 "taskId": 13,
40 "name": "link 1",
41 "url": "url 1"
42 }
43 ],
44 "watchers": [
45 {
46 "id": 13,
47 "taskId": 13,
48 "userId": 396,
49 "userName": "John Smith"
50 }
51 ],
52 "totalWatchers": 1
53}
AuthUserValidationError Output:
Client does not have access to the customer.
Client does not have access to the building.
Missing customer ID.
Assignee does not have access to the customer.
Assignee does not have access to the building.
Assignee does not have access to an Integrators Visibility task.
Watcher does not have access to an Integrators Visibility task.
RequestValidation Output:
Missing node ID.
Missing type ID.
Missing title.
Missing status.
Missing effort.
Missing priority.
Missing visibility.
Missing task tag name.
Missing task link url.
Missing task watcher user ID.
Invalid node ID.
Invalid type ID.
Invalid title.
Invalid status.
Invalid effort.
Invalid priority.
Invalid visibility.
Update an Action Center Task
Endpoint
PUT /customers/{customerId}/actioncenter/task
Sample Input
1{
2 "id": 13, \\required
3 "nodeId": 41, \\required
4 "typeId": 1, \\required (1=BAS, 2=Mechanical, 3=Capital, 4=ECM, 5=Maintenance, 6=Operational, 7=Observations, 8=Memo)
5 "title": "new title", \\required
6 "status": "Open", \\required ('Open', 'In Progress', 'Blocked', 'Closed')
7 "priority": "High", \\required ('Low', 'Medium', 'High')
8 "effort": "Low", \\required ('Very Low', 'Low', 'Medium', 'High', 'Very High')
9 "visibility": "Public", \\required ('Public', 'Integrators')
10 "assigneeId": 396,
11 "description": "desc",
12 "blockedReason": "reason",
13 "blockedUntil": 1639307110000,
14 "potentialSavingsLow": 10,
15 "potentialSavingsHigh": 999,
16 "suggestedAction": "sug",
17 "implementationCost": "eye",
18 "roi": "nada",
19 "tags": [
20 {
21 "name": "G2" \\required
22 }
23 ],
24 "links": [
25 {
26 "name": "link 1",
27 "url": "url 1" \\required
28 }
29 ],
30 "watchers": [
31 {
32 "userId": 328 \\required
33 }
34 ]
35}
Sample Output
1{ 2 "id": 13, 3 "customerId": 4, 4 "customerTaskId": 11, 5 "taskId": "RES-11", 6 "nodeId": 41, 7 "typeId": 1, 8 "typeName": "BAS", 9 "typeColor": "#FBAA18", 10 "title": "new title", 11 "description": "desc", 12 "assigneeId": 396, 13 "assignedTo": "John Smith", 14 "creatorId": 328, 15 "createdBy": "John Smith", 16 "updatedAt": 1613041913497, 17 "createdAt": 1613041913497, 18 "effort": "Low", 19 "status": "Open", 20 "priority": "High", 21 "visibility": "Public", 22 "blockedReason": "reason", 23 "blockedUntil": 1639307110000, 24 "potentialSavingsLow": 10, 25 "potentialSavingsHigh": 999, 26 "suggestedAction": "sug", 27 "implementationCost": "eye", 28 "roi": "nada", 29 "tags": [ 30 { 31 "id": 21, 32 "taskId": 13, 33 "name": "C1" 34 } 35 ], 36 "links": [ 37 { 38 "id": 13, 39 "taskId": 13, 40 "name": "link 1", 41 "url": "url 1" 42 } 43 ], 44 "watchers": [ 45 { 46 "id": 13, 47 "taskId": 13, 48 "userId": 396, 49 "userName": "John Smith" 50 } 51 ], 52 "totalWatchers": 1 53}
AuthUserValidationError Output:
Client does not have access to the customer.
Client does not have access to the building.
Missing customer ID.
Assignee does not have access to the customer.
Assignee does not have access to the building.
Assignee does not have access to an Integrators Visibility task.
Watcher does not have access to an Integrators Visibility task.
RequestValidation Output:
Missing node ID.
Missing type ID.
Missing title.
Missing status.
Missing effort.
Missing priority.
Missing visibility.
Missing task tag name.
Missing task link url.
Missing task watcher user ID.
Invalid nodeId.
Invalid typeId.
Invalid title.
Invalid status.
Invalid effort.
Invalid priority.
Invalid visibility.
Delete an Action Center Task
Endpoint
DELETE /customers/{customerId}/actioncenter/task/{taskId}
AuthUserValidation Output:
Client does not have access to the task.
Retrieve Action Center Task Summary
Return the summary of all tasks for all customer buildings, or all tasks for a specific building.
Endpoint
POST /customers/{customerId}/actioncenter/summary
Sample Input
1{
2 "nodeId": 1 //Optional
3 "viewType": "My Actions", //Optional (Default=ALL) ('Synergy Integrator Actions', 'Public Actions')
4}
Sample Output
1[ 2 { 3 "customerId": 4, 4 "nodeId": 41, 5 "buildingName": "Bay Region", 6 "totalNew": 5, 7 "open": 2, 8 "openPct": "40%", 9 "inProgress": 1, 10 "inProgressPct": "20%", 11 "closed": 1, 12 "closedPct": "20%", 13 "blocked": 1, 14 "blockedPct": "20%", 15 "totalWorklog": 4, 16 "worklogNew": 3, 17 "worklogOld": 1, 18 "worklogNewPct": "75%", 19 "worklogOldPct": "25%" 20 }, 21 { 22 "customerId": 4, 23 "nodeId": 48, 24 "buildingName": "Bay Special Care", 25 "total": 20, 26 "open": 20, 27 "openPct": "100%", 28 "inProgress": 0, 29 "inProgressPct": "0%", 30 "closed": 0, 31 "closedPct": "0%", 32 "blocked": 0, 33 "blockedPct": "0%", 34 "totalWorklog": 20, 35 "worklogNew": 10, 36 "worklogOld": 10, 37 "worklogNewPct": "50%", 38 "worklogOldPct": "50%" 39 } 40]
AuthUserValidationError Output:
Client does not have access to any customers.
Client does not have access to the customer.
Client does not have access to the building.
Invalid view type.
Add an Action Center Task Comment
Endpoint
PUT /customers/{customerId}/actioncenter/task/comment
Sample Input
1{
2 "taskId": 1 //Required
3 "body": "Sample Text" //Required
4}
Sample Output
List of Action Center Comments for task.
1[
2 {
3 "id": 1,
4 "taskId": 1,
5 "userName": "User Name",
6 "body": "task id 1 customer 1 message 1",
7 "createdAt": 1612806202817,
8 "canModify": true
9 },
10 {
11
12 "id": 2,
13 "taskId": 1,
14 "userName": "User2 Name2",
15 "body": "Sample Text",
16 "createdAt": 1612806202817,
17 "canModify": false
18 }
19]
AuthUserValidationError Output:
Client does not have access to the task.
Missing task Id.
Task does not exist.
Missing task comment body.
Modify an Action Center Task Comment
Endpoint
PUT /customers/{customerId}/actioncenter/task/comment
Sample Input
1{ 2 "id": 2 //Required id of the comment 3 "taskId": 1 //Required 4 "body": "I'm modified" //Required 5}
Sample Output
1[
2 {
3
4 "id": 1,
5
6 "taskId": 1,
7 "userName": "User Name",
8 "body": "task id 1 customer 1 message 1",
9 "createdAt": 1612806202817,
10 "canModify": true
11 },
12 {
13 "id": 2,
14 "taskId": 1,
15 "userName": "User2 Name2",
16 "body": "I'm modified",
17 "createdAt": 1612806202817,
18 "canModify": false
19 }
20]
AuthUserValidationError Output:
Client does not have access to the task.
Missing task Id.
Task does not exist.
Missing task comment body.
Task comment does not exist.
Retrieve Data Dictionary Objects
Returns a list of various lists of items representing the possible values that can be used in other Action Center APIs.
Endpoint
GET /customers/{customerId}/actioncenter/dictionarydata
Sample Output
1{
2 "viewTypes": [
3 "Synergy Integrator Actions",
4 "Public Actions"
5 ],
6 "sectionTypes": [
7 "Work Log",
8 "Blocked",
9 "Closed"
10 ],
11 "actionTypes": [
12 {
13 "id": 1,
14 "name": "BAS",
15 "color": "#FBAA18"
16 },
17 {
18 "id": 3,
19 "name": "Capital",
20 "color": "#333333"
21 },
22 {
23 "id": 4,
24 "name": "ECM",
25 "color": "#3D4A26"
26 },
27 {
28 "id": 5,
29 "name": "Maintenance",
30 "color": "#330033"
31 },
32 {
33 "id": 2,
34 "name": "Mechanical",
35 "color": "#955393"
36 },
37 {
38 "id": 8,
39 "name": "Memo",
40 "color": "#2E4A79"
41 },
42 {
43 "id": 7,
44 "name": "Observations",
45 "color": "#C66A00"
46 },
47 {
48 "id": 6,
49 "name": "Operational",
50 "color": "#EB5E74"
51 }
52 ],
53 "workLogStatuses": [
54 "Open Actions",
55 "In Progress",
56 "New Actions",
57 "Old Actions"
58 ],
59 "closedStatuses": [
60 "Closed Recently",
61 "All Closed Actions"
62 ],
63 "statuses": [
64 "Open",
65 "In Progress",
66 "Blocked",
67 "Closed"
68 ],
69 "efforts": [
70 "Very High",
71 "High",
72 "Medium",
73 "Low",
74 "Very Low"
75 ],
76 "priorities": [
77 "High",
78 "Medium",
79 "Low"
80 ],
81 "visibilities": [
82 "Public",
83 "Integrators"
84 ],
85 "sortColumns": [
86 "type_name",
87 "customer_task_id",
88 "priority",
89 "title",
90 "assigned_to",
91 "status_updated_at",
92 "updated_at",
93 "created_at"
94 ],
95 "sortDirections": [
96 "asc",
97 "desc"
98 ]
99}
AuthUserValidationError Output:
Client does not have access to any customers.
Retrieve Available Action Center Task Assignees
Returns a list of valid Action Center task assignees for a given building.
Endpoint
GET/customers/{customerId}/actioncenter/buildings/{buildingId}/assignees
Sample Output
1[
2 {
3 "id": 201,
4 "name": "First Last",
5 "email": "First.Last@email.com",
6 "distributor": false,
7 "distributorName": null
8 },
9 {
10 "id": 200,
11 "name": "First Last2",
12 "email": "First.Last@email.com",
13 "distributor": false,
14 "distributorName": null
15 },
16 {
17 "id": 104,
18 "name": "First Last",
19 "email": "First.Last@email.com",
20 "distributor": true,
21 "distributorName": "Resolute"
22 },
23 {
24 "id": 337,
25 "name": "First Last2",
26 "email": "First.Last@email.com",
27 "distributor": true,
28 "distributorName": "Resolute"
29 }
30]
AuthUserValidationError Output:
Client does not have access to the building.