From 471a029bdf82f4dabc9774850158f3d988167431 Mon Sep 17 00:00:00 2001 From: Viacheslav Klimov Date: Thu, 23 Apr 2026 11:42:48 +0100 Subject: [PATCH] Update PE OpenAPI spec (from lts-4.3) --- pe/docs/AiChatControllerApi.md | 148 + pe/docs/AiSolutionControllerApi.md | 230 + pe/docs/AiToolControllerApi.md | 30 + pe/docs/AllowedPermissionsInfo.md | 2 +- pe/docs/ApiFeature.md | 2 + ...UsageLimitNotificationRuleTriggerConfig.md | 2 +- pe/docs/AvailableEntityKeysV2.md | 1 + pe/docs/ChatType.md | 23 + pe/docs/DefaultTenantProfileConfiguration.md | 2 + pe/docs/LimitedApi.md | 2 + pe/docs/NotificationRule.md | 4 +- pe/docs/NotificationRuleInfo.md | 4 +- pe/docs/NotificationRuleTriggerConfig.md | 4 +- pe/docs/PageDataNotificationRuleInfo.md | 4 +- pe/docs/PageDataTenantProfile.md | 2 + ...RateLimitsNotificationRuleTriggerConfig.md | 2 +- pe/docs/Resource.md | 2 + pe/docs/SolutionStep.md | 23 + pe/docs/TenantProfile.md | 2 + pe/docs/TenantProfileConfiguration.md | 2 + pe/docs/TenantProfileData.md | 2 + pe/docs/UsageInfo.md | 2 + pe/spec/openapi.json | 20816 +++++++++------- .../client/api/ThingsboardApi.java | 1759 +- .../thingsboard/client/model/ApiFeature.java | 4 +- .../client/model/AvailableEntityKeysV2.java | 40 +- .../thingsboard/client/model/ChatType.java | 80 + .../DefaultTenantProfileConfiguration.java | 76 +- .../thingsboard/client/model/LimitedApi.java | 4 +- .../thingsboard/client/model/Resource.java | 2 + .../client/model/SolutionStep.java | 80 + .../thingsboard/client/model/UsageInfo.java | 78 +- 32 files changed, 14090 insertions(+), 9344 deletions(-) create mode 100644 pe/docs/AiChatControllerApi.md create mode 100644 pe/docs/AiSolutionControllerApi.md create mode 100644 pe/docs/AiToolControllerApi.md create mode 100644 pe/docs/ChatType.md create mode 100644 pe/docs/SolutionStep.md create mode 100644 pe/src/main/java/org/thingsboard/client/model/ChatType.java create mode 100644 pe/src/main/java/org/thingsboard/client/model/SolutionStep.java diff --git a/pe/docs/AiChatControllerApi.md b/pe/docs/AiChatControllerApi.md new file mode 100644 index 00000000..dda839c3 --- /dev/null +++ b/pe/docs/AiChatControllerApi.md @@ -0,0 +1,148 @@ +# AiChatControllerApi + +`ThingsboardClient` methods: + +``` +com.fasterxml.jackson.databind.JsonNode createChat(@Nonnull Object body) // createChat +void deleteChat(@Nonnull UUID chatId) // deleteChat +com.fasterxml.jackson.databind.JsonNode getChatMessages(@Nonnull UUID chatId) // getChatMessages +com.fasterxml.jackson.databind.JsonNode listChats(@Nonnull ChatType chatType) // listChats +List sendChatMessage(@Nonnull UUID chatId, @Nonnull String xAuthorization, @Nonnull String body) // sendChatMessage +void updateChat(@Nonnull UUID chatId, @Nonnull Object body) // updateChat +``` + + +## createChat + +``` +com.fasterxml.jackson.databind.JsonNode createChat(@Nonnull Object body) +``` + +**POST** `/api/ai/chats` + +createChat + + +### Parameters + +| Name | Type | Description | Notes | +|------------- | ------------- | ------------- | -------------| +| **body** | **Object** | | | + +### Return type + +**com.fasterxml.jackson.databind.JsonNode** + + +## deleteChat + +``` +void deleteChat(@Nonnull UUID chatId) +``` + +**DELETE** `/api/ai/chats/{chatId}` + +deleteChat + + +### Parameters + +| Name | Type | Description | Notes | +|------------- | ------------- | ------------- | -------------| +| **chatId** | **UUID** | | | + +### Return type + +null (empty response body) + + +## getChatMessages + +``` +com.fasterxml.jackson.databind.JsonNode getChatMessages(@Nonnull UUID chatId) +``` + +**GET** `/api/ai/chats/{chatId}/messages` + +getChatMessages + + +### Parameters + +| Name | Type | Description | Notes | +|------------- | ------------- | ------------- | -------------| +| **chatId** | **UUID** | | | + +### Return type + +**com.fasterxml.jackson.databind.JsonNode** + + +## listChats + +``` +com.fasterxml.jackson.databind.JsonNode listChats(@Nonnull ChatType chatType) +``` + +**GET** `/api/ai/chats/{chatType}` + +listChats + + +### Parameters + +| Name | Type | Description | Notes | +|------------- | ------------- | ------------- | -------------| +| **chatType** | **ChatType** | | [enum: GENERIC, SOLUTION_BUILDER] | + +### Return type + +**com.fasterxml.jackson.databind.JsonNode** + + +## sendChatMessage + +``` +List sendChatMessage(@Nonnull UUID chatId, @Nonnull String xAuthorization, @Nonnull String body) +``` + +**POST** `/api/ai/chats/{chatId}/messages` + +sendChatMessage + + +### Parameters + +| Name | Type | Description | Notes | +|------------- | ------------- | ------------- | -------------| +| **chatId** | **UUID** | | | +| **xAuthorization** | **String** | | | +| **body** | **String** | | | + +### Return type + +**List** + + +## updateChat + +``` +void updateChat(@Nonnull UUID chatId, @Nonnull Object body) +``` + +**PATCH** `/api/ai/chats/{chatId}` + +updateChat + + +### Parameters + +| Name | Type | Description | Notes | +|------------- | ------------- | ------------- | -------------| +| **chatId** | **UUID** | | | +| **body** | **Object** | | | + +### Return type + +null (empty response body) + diff --git a/pe/docs/AiSolutionControllerApi.md b/pe/docs/AiSolutionControllerApi.md new file mode 100644 index 00000000..810876f5 --- /dev/null +++ b/pe/docs/AiSolutionControllerApi.md @@ -0,0 +1,230 @@ +# AiSolutionControllerApi + +`ThingsboardClient` methods: + +``` +com.fasterxml.jackson.databind.JsonNode chat(@Nonnull UUID solutionId, @Nonnull SolutionStep step, @Nonnull String body) // chat +void clearStep(@Nonnull UUID solutionId, @Nonnull SolutionStep step) // clearStep +com.fasterxml.jackson.databind.JsonNode createSolution(@Nonnull UUID solutionId) // createSolution +void deleteSolution(@Nonnull UUID solutionId) // deleteSolution +com.fasterxml.jackson.databind.JsonNode getSolution(@Nonnull UUID solutionId) // getSolution +com.fasterxml.jackson.databind.JsonNode getSolutions() // getSolutions +com.fasterxml.jackson.databind.JsonNode installSolution(@Nonnull UUID solutionId, @Nonnull String xAuthorization) // installSolution +com.fasterxml.jackson.databind.JsonNode startNew() // startNew +com.fasterxml.jackson.databind.JsonNode uninstallSolution(@Nonnull UUID solutionId, @Nonnull String xAuthorization) // uninstallSolution +com.fasterxml.jackson.databind.JsonNode updateData(@Nonnull UUID solutionId, @Nonnull String dataKey, @Nonnull Object body) // updateData +``` + + +## chat + +``` +com.fasterxml.jackson.databind.JsonNode chat(@Nonnull UUID solutionId, @Nonnull SolutionStep step, @Nonnull String body) +``` + +**POST** `/api/ai/solution/{solutionId}/{step}/chat` + +chat + + +### Parameters + +| Name | Type | Description | Notes | +|------------- | ------------- | ------------- | -------------| +| **solutionId** | **UUID** | | | +| **step** | **SolutionStep** | | [enum: INITIAL_CONFIGURATION, DASHBOARDS_CONFIGURATION] | +| **body** | **String** | | | + +### Return type + +**com.fasterxml.jackson.databind.JsonNode** + + +## clearStep + +``` +void clearStep(@Nonnull UUID solutionId, @Nonnull SolutionStep step) +``` + +**DELETE** `/api/ai/solution/{solutionId}/{step}/clear` + +clearStep + + +### Parameters + +| Name | Type | Description | Notes | +|------------- | ------------- | ------------- | -------------| +| **solutionId** | **UUID** | | | +| **step** | **SolutionStep** | | [enum: INITIAL_CONFIGURATION, DASHBOARDS_CONFIGURATION] | + +### Return type + +null (empty response body) + + +## createSolution + +``` +com.fasterxml.jackson.databind.JsonNode createSolution(@Nonnull UUID solutionId) +``` + +**POST** `/api/ai/solution/{solutionId}/create` + +createSolution + + +### Parameters + +| Name | Type | Description | Notes | +|------------- | ------------- | ------------- | -------------| +| **solutionId** | **UUID** | | | + +### Return type + +**com.fasterxml.jackson.databind.JsonNode** + + +## deleteSolution + +``` +void deleteSolution(@Nonnull UUID solutionId) +``` + +**DELETE** `/api/ai/solution/{solutionId}` + +deleteSolution + + +### Parameters + +| Name | Type | Description | Notes | +|------------- | ------------- | ------------- | -------------| +| **solutionId** | **UUID** | | | + +### Return type + +null (empty response body) + + +## getSolution + +``` +com.fasterxml.jackson.databind.JsonNode getSolution(@Nonnull UUID solutionId) +``` + +**GET** `/api/ai/solution/{solutionId}` + +getSolution + + +### Parameters + +| Name | Type | Description | Notes | +|------------- | ------------- | ------------- | -------------| +| **solutionId** | **UUID** | | | + +### Return type + +**com.fasterxml.jackson.databind.JsonNode** + + +## getSolutions + +``` +com.fasterxml.jackson.databind.JsonNode getSolutions() +``` + +**GET** `/api/ai/solution/infos` + +getSolutions + +### Return type + +**com.fasterxml.jackson.databind.JsonNode** + + +## installSolution + +``` +com.fasterxml.jackson.databind.JsonNode installSolution(@Nonnull UUID solutionId, @Nonnull String xAuthorization) +``` + +**POST** `/api/ai/solution/{solutionId}/install` + +installSolution + + +### Parameters + +| Name | Type | Description | Notes | +|------------- | ------------- | ------------- | -------------| +| **solutionId** | **UUID** | | | +| **xAuthorization** | **String** | | | + +### Return type + +**com.fasterxml.jackson.databind.JsonNode** + + +## startNew + +``` +com.fasterxml.jackson.databind.JsonNode startNew() +``` + +**POST** `/api/ai/solution/start` + +startNew + +### Return type + +**com.fasterxml.jackson.databind.JsonNode** + + +## uninstallSolution + +``` +com.fasterxml.jackson.databind.JsonNode uninstallSolution(@Nonnull UUID solutionId, @Nonnull String xAuthorization) +``` + +**DELETE** `/api/ai/solution/{solutionId}/uninstall` + +uninstallSolution + + +### Parameters + +| Name | Type | Description | Notes | +|------------- | ------------- | ------------- | -------------| +| **solutionId** | **UUID** | | | +| **xAuthorization** | **String** | | | + +### Return type + +**com.fasterxml.jackson.databind.JsonNode** + + +## updateData + +``` +com.fasterxml.jackson.databind.JsonNode updateData(@Nonnull UUID solutionId, @Nonnull String dataKey, @Nonnull Object body) +``` + +**PUT** `/api/ai/solution/{solutionId}/{dataKey}` + +updateData + + +### Parameters + +| Name | Type | Description | Notes | +|------------- | ------------- | ------------- | -------------| +| **solutionId** | **UUID** | | | +| **dataKey** | **String** | | | +| **body** | **Object** | | | + +### Return type + +**com.fasterxml.jackson.databind.JsonNode** + diff --git a/pe/docs/AiToolControllerApi.md b/pe/docs/AiToolControllerApi.md new file mode 100644 index 00000000..8f92465a --- /dev/null +++ b/pe/docs/AiToolControllerApi.md @@ -0,0 +1,30 @@ +# AiToolControllerApi + +`ThingsboardClient` methods: + +``` +com.fasterxml.jackson.databind.JsonNode resolveToolApproval(@Nonnull Object body) // resolveToolApproval +``` + + +## resolveToolApproval + +``` +com.fasterxml.jackson.databind.JsonNode resolveToolApproval(@Nonnull Object body) +``` + +**POST** `/api/ai/tools/resolve-approval` + +resolveToolApproval + + +### Parameters + +| Name | Type | Description | Notes | +|------------- | ------------- | ------------- | -------------| +| **body** | **Object** | | | + +### Return type + +**com.fasterxml.jackson.databind.JsonNode** + diff --git a/pe/docs/AllowedPermissionsInfo.md b/pe/docs/AllowedPermissionsInfo.md index b4f26ea1..042aaa84 100644 --- a/pe/docs/AllowedPermissionsInfo.md +++ b/pe/docs/AllowedPermissionsInfo.md @@ -25,7 +25,7 @@ `ALL` | `CREATE` | `READ` | `WRITE` | `DELETE` | `RPC_CALL` | `READ_CREDENTIALS` | `WRITE_CREDENTIALS` | `READ_ATTRIBUTES` | `WRITE_ATTRIBUTES` | … (21 values total) #### Resource (enum) -`ALL` | `PROFILE` | `ADMIN_SETTINGS` | `ALARM` | `DEVICE` | `ASSET` | `CUSTOMER` | `DASHBOARD` | `ENTITY_VIEW` | `EDGE` | … (53 values total) +`ALL` | `PROFILE` | `ADMIN_SETTINGS` | `ALARM` | `DEVICE` | `ASSET` | `CUSTOMER` | `DASHBOARD` | `ENTITY_VIEW` | `EDGE` | … (54 values total) #### MergedUserPermissions | Name | Type | Description | Notes | diff --git a/pe/docs/ApiFeature.md b/pe/docs/ApiFeature.md index 48752c4c..094fbb3b 100644 --- a/pe/docs/ApiFeature.md +++ b/pe/docs/ApiFeature.md @@ -24,6 +24,8 @@ * `REPORT` (value: `"REPORT"`) +* `AI` (value: `"AI"`) + --- diff --git a/pe/docs/ApiUsageLimitNotificationRuleTriggerConfig.md b/pe/docs/ApiUsageLimitNotificationRuleTriggerConfig.md index 23073f71..155f8d1f 100644 --- a/pe/docs/ApiUsageLimitNotificationRuleTriggerConfig.md +++ b/pe/docs/ApiUsageLimitNotificationRuleTriggerConfig.md @@ -22,7 +22,7 @@ | triggerType | NotificationRuleTriggerType | | | #### ApiFeature (enum) -`TRANSPORT` | `DB` | `RE` | `JS` | `TBEL` | `EMAIL` | `SMS` | `ALARM` | `REPORT` +`TRANSPORT` | `DB` | `RE` | `JS` | `TBEL` | `EMAIL` | `SMS` | `ALARM` | `REPORT` | `AI` #### ApiUsageStateValue (enum) `ENABLED` | `WARNING` | `DISABLED` diff --git a/pe/docs/AvailableEntityKeysV2.md b/pe/docs/AvailableEntityKeysV2.md index cc058a4a..ec83e9fd 100644 --- a/pe/docs/AvailableEntityKeysV2.md +++ b/pe/docs/AvailableEntityKeysV2.md @@ -9,6 +9,7 @@ Contains unique time series and attribute key names discovered from entities mat | Name | Type | Description | Notes | |------------ | ------------- | ------------- | -------------| +| **totalEntities** | **Integer** | Total number of entities that matched the query filter. | | | **entityTypes** | **Set\** | Set of entity types found among the matched entities. | | | **timeseries** | **List\** | | [optional] | | **attributes** | **Map\\>** | Map of attribute scope to the list of unique attribute keys available on the matched entities. Only scopes supported by the matched entity types are included. Omitted when attribute keys were not requested or when none of the requested scopes apply to the matched entity types. | [optional] | diff --git a/pe/docs/ChatType.md b/pe/docs/ChatType.md new file mode 100644 index 00000000..4dd1fe97 --- /dev/null +++ b/pe/docs/ChatType.md @@ -0,0 +1,23 @@ + +# ChatType + +`org.thingsboard.client.model.ChatType` + +## Enum Values + + +* `GENERIC` (value: `"GENERIC"`) + +* `SOLUTION_BUILDER` (value: `"SOLUTION_BUILDER"`) + + + +--- + +### Conventions + +- **Package:** `org.thingsboard.client.model` +- **Getter pattern:** `get()` — e.g., `getId()`, `getName()` +- **Setter pattern:** `set(value)` — e.g., `setId(value)`, `setName(value)` +- **Null fields:** Getters return `null` for unset optional fields; they do not throw exceptions + diff --git a/pe/docs/DefaultTenantProfileConfiguration.md b/pe/docs/DefaultTenantProfileConfiguration.md index f60a0436..6fee9a73 100644 --- a/pe/docs/DefaultTenantProfileConfiguration.md +++ b/pe/docs/DefaultTenantProfileConfiguration.md @@ -55,6 +55,7 @@ | **maxSms** | **Long** | | [optional] | | **maxCreatedAlarms** | **Long** | | [optional] | | **maxGeneratedReports** | **Long** | | [optional] | +| **maxAiCredits** | **Long** | | [optional] | | **tenantServerRestLimitsConfiguration** | **String** | | [optional] | | **customerServerRestLimitsConfiguration** | **String** | | [optional] | | **maxWsSessionsPerTenant** | **Integer** | | [optional] | @@ -96,6 +97,7 @@ | **intermediateAggregationIntervalInSecForCF** | **Long** | | [optional] | | **cfReevaluationCheckInterval** | **Long** | | [optional] | | **alarmsReevaluationInterval** | **Long** | | [optional] | +| **aiChatRequestsPerTenantRateLimit** | **String** | | [optional] | diff --git a/pe/docs/LimitedApi.md b/pe/docs/LimitedApi.md index 9477ece7..828d1110 100644 --- a/pe/docs/LimitedApi.md +++ b/pe/docs/LimitedApi.md @@ -76,6 +76,8 @@ * `TRENDZ_PUBLIC_SYNC` (value: `"TRENDZ_PUBLIC_SYNC"`) +* `AI_CHAT_REQUESTS` (value: `"AI_CHAT_REQUESTS"`) + --- diff --git a/pe/docs/NotificationRule.md b/pe/docs/NotificationRule.md index 1345bac6..7cc5edbc 100644 --- a/pe/docs/NotificationRule.md +++ b/pe/docs/NotificationRule.md @@ -243,13 +243,13 @@ `ASSIGNED` | `UNASSIGNED` #### ApiFeature (enum) -`TRANSPORT` | `DB` | `RE` | `JS` | `TBEL` | `EMAIL` | `SMS` | `ALARM` | `REPORT` +`TRANSPORT` | `DB` | `RE` | `JS` | `TBEL` | `EMAIL` | `SMS` | `ALARM` | `REPORT` | `AI` #### ApiUsageStateValue (enum) `ENABLED` | `WARNING` | `DISABLED` #### LimitedApi (enum) -`ENTITY_EXPORT` | `ENTITY_IMPORT` | `NOTIFICATION_REQUESTS` | `NOTIFICATION_REQUESTS_PER_RULE` | `REST_REQUESTS_PER_TENANT` | `REST_REQUESTS_PER_CUSTOMER` | `WS_UPDATES_PER_SESSION` | `CASSANDRA_WRITE_QUERIES_CORE` | `CASSANDRA_READ_QUERIES_CORE` | `CASSANDRA_WRITE_QUERIES_RULE_ENGINE` | … (35 values total) +`ENTITY_EXPORT` | `ENTITY_IMPORT` | `NOTIFICATION_REQUESTS` | `NOTIFICATION_REQUESTS_PER_RULE` | `REST_REQUESTS_PER_TENANT` | `REST_REQUESTS_PER_CUSTOMER` | `WS_UPDATES_PER_SESSION` | `CASSANDRA_WRITE_QUERIES_CORE` | `CASSANDRA_READ_QUERIES_CORE` | `CASSANDRA_WRITE_QUERIES_RULE_ENGINE` | … (36 values total) #### EdgeConnectivityEvent (enum) `CONNECTED` | `DISCONNECTED` diff --git a/pe/docs/NotificationRuleInfo.md b/pe/docs/NotificationRuleInfo.md index 8bdfb043..d6159bd2 100644 --- a/pe/docs/NotificationRuleInfo.md +++ b/pe/docs/NotificationRuleInfo.md @@ -248,13 +248,13 @@ `ASSIGNED` | `UNASSIGNED` #### ApiFeature (enum) -`TRANSPORT` | `DB` | `RE` | `JS` | `TBEL` | `EMAIL` | `SMS` | `ALARM` | `REPORT` +`TRANSPORT` | `DB` | `RE` | `JS` | `TBEL` | `EMAIL` | `SMS` | `ALARM` | `REPORT` | `AI` #### ApiUsageStateValue (enum) `ENABLED` | `WARNING` | `DISABLED` #### LimitedApi (enum) -`ENTITY_EXPORT` | `ENTITY_IMPORT` | `NOTIFICATION_REQUESTS` | `NOTIFICATION_REQUESTS_PER_RULE` | `REST_REQUESTS_PER_TENANT` | `REST_REQUESTS_PER_CUSTOMER` | `WS_UPDATES_PER_SESSION` | `CASSANDRA_WRITE_QUERIES_CORE` | `CASSANDRA_READ_QUERIES_CORE` | `CASSANDRA_WRITE_QUERIES_RULE_ENGINE` | … (35 values total) +`ENTITY_EXPORT` | `ENTITY_IMPORT` | `NOTIFICATION_REQUESTS` | `NOTIFICATION_REQUESTS_PER_RULE` | `REST_REQUESTS_PER_TENANT` | `REST_REQUESTS_PER_CUSTOMER` | `WS_UPDATES_PER_SESSION` | `CASSANDRA_WRITE_QUERIES_CORE` | `CASSANDRA_READ_QUERIES_CORE` | `CASSANDRA_WRITE_QUERIES_RULE_ENGINE` | … (36 values total) #### EdgeConnectivityEvent (enum) `CONNECTED` | `DISCONNECTED` diff --git a/pe/docs/NotificationRuleTriggerConfig.md b/pe/docs/NotificationRuleTriggerConfig.md index ed5d7936..ee80ad37 100644 --- a/pe/docs/NotificationRuleTriggerConfig.md +++ b/pe/docs/NotificationRuleTriggerConfig.md @@ -137,7 +137,7 @@ Configuration for notification rule trigger `ASSIGNED` | `UNASSIGNED` #### ApiFeature (enum) -`TRANSPORT` | `DB` | `RE` | `JS` | `TBEL` | `EMAIL` | `SMS` | `ALARM` | `REPORT` +`TRANSPORT` | `DB` | `RE` | `JS` | `TBEL` | `EMAIL` | `SMS` | `ALARM` | `REPORT` | `AI` #### ApiUsageStateValue (enum) `ENABLED` | `WARNING` | `DISABLED` @@ -158,7 +158,7 @@ Configuration for notification rule trigger `CREATED` | `STARTED` | `ACTIVATED` | `SUSPENDED` | `UPDATED` | `STOPPED` | `DELETED` | `FAILED` | `DEACTIVATED` | `RELATION_UPDATED` | … (11 values total) #### LimitedApi (enum) -`ENTITY_EXPORT` | `ENTITY_IMPORT` | `NOTIFICATION_REQUESTS` | `NOTIFICATION_REQUESTS_PER_RULE` | `REST_REQUESTS_PER_TENANT` | `REST_REQUESTS_PER_CUSTOMER` | `WS_UPDATES_PER_SESSION` | `CASSANDRA_WRITE_QUERIES_CORE` | `CASSANDRA_READ_QUERIES_CORE` | `CASSANDRA_WRITE_QUERIES_RULE_ENGINE` | … (35 values total) +`ENTITY_EXPORT` | `ENTITY_IMPORT` | `NOTIFICATION_REQUESTS` | `NOTIFICATION_REQUESTS_PER_RULE` | `REST_REQUESTS_PER_TENANT` | `REST_REQUESTS_PER_CUSTOMER` | `WS_UPDATES_PER_SESSION` | `CASSANDRA_WRITE_QUERIES_CORE` | `CASSANDRA_READ_QUERIES_CORE` | `CASSANDRA_WRITE_QUERIES_RULE_ENGINE` | … (36 values total) --- diff --git a/pe/docs/PageDataNotificationRuleInfo.md b/pe/docs/PageDataNotificationRuleInfo.md index 518e6f08..dc835d80 100644 --- a/pe/docs/PageDataNotificationRuleInfo.md +++ b/pe/docs/PageDataNotificationRuleInfo.md @@ -256,13 +256,13 @@ `ASSIGNED` | `UNASSIGNED` #### ApiFeature (enum) -`TRANSPORT` | `DB` | `RE` | `JS` | `TBEL` | `EMAIL` | `SMS` | `ALARM` | `REPORT` +`TRANSPORT` | `DB` | `RE` | `JS` | `TBEL` | `EMAIL` | `SMS` | `ALARM` | `REPORT` | `AI` #### ApiUsageStateValue (enum) `ENABLED` | `WARNING` | `DISABLED` #### LimitedApi (enum) -`ENTITY_EXPORT` | `ENTITY_IMPORT` | `NOTIFICATION_REQUESTS` | `NOTIFICATION_REQUESTS_PER_RULE` | `REST_REQUESTS_PER_TENANT` | `REST_REQUESTS_PER_CUSTOMER` | `WS_UPDATES_PER_SESSION` | `CASSANDRA_WRITE_QUERIES_CORE` | `CASSANDRA_READ_QUERIES_CORE` | `CASSANDRA_WRITE_QUERIES_RULE_ENGINE` | … (35 values total) +`ENTITY_EXPORT` | `ENTITY_IMPORT` | `NOTIFICATION_REQUESTS` | `NOTIFICATION_REQUESTS_PER_RULE` | `REST_REQUESTS_PER_TENANT` | `REST_REQUESTS_PER_CUSTOMER` | `WS_UPDATES_PER_SESSION` | `CASSANDRA_WRITE_QUERIES_CORE` | `CASSANDRA_READ_QUERIES_CORE` | `CASSANDRA_WRITE_QUERIES_RULE_ENGINE` | … (36 values total) #### EdgeConnectivityEvent (enum) `CONNECTED` | `DISCONNECTED` diff --git a/pe/docs/PageDataTenantProfile.md b/pe/docs/PageDataTenantProfile.md index 5065c3dc..87cc24d2 100644 --- a/pe/docs/PageDataTenantProfile.md +++ b/pe/docs/PageDataTenantProfile.md @@ -89,6 +89,7 @@ | maxSms | Long | | [optional] | | maxCreatedAlarms | Long | | [optional] | | maxGeneratedReports | Long | | [optional] | +| maxAiCredits | Long | | [optional] | | tenantServerRestLimitsConfiguration | String | | [optional] | | customerServerRestLimitsConfiguration | String | | [optional] | | maxWsSessionsPerTenant | Integer | | [optional] | @@ -130,6 +131,7 @@ | intermediateAggregationIntervalInSecForCF | Long | | [optional] | | cfReevaluationCheckInterval | Long | | [optional] | | alarmsReevaluationInterval | Long | | [optional] | +| aiChatRequestsPerTenantRateLimit | String | | [optional] | #### TenantProfileQueueConfiguration | Name | Type | Description | Notes | diff --git a/pe/docs/RateLimitsNotificationRuleTriggerConfig.md b/pe/docs/RateLimitsNotificationRuleTriggerConfig.md index b5b70ed8..26c8e19a 100644 --- a/pe/docs/RateLimitsNotificationRuleTriggerConfig.md +++ b/pe/docs/RateLimitsNotificationRuleTriggerConfig.md @@ -21,7 +21,7 @@ | triggerType | NotificationRuleTriggerType | | | #### LimitedApi (enum) -`ENTITY_EXPORT` | `ENTITY_IMPORT` | `NOTIFICATION_REQUESTS` | `NOTIFICATION_REQUESTS_PER_RULE` | `REST_REQUESTS_PER_TENANT` | `REST_REQUESTS_PER_CUSTOMER` | `WS_UPDATES_PER_SESSION` | `CASSANDRA_WRITE_QUERIES_CORE` | `CASSANDRA_READ_QUERIES_CORE` | `CASSANDRA_WRITE_QUERIES_RULE_ENGINE` | … (35 values total) +`ENTITY_EXPORT` | `ENTITY_IMPORT` | `NOTIFICATION_REQUESTS` | `NOTIFICATION_REQUESTS_PER_RULE` | `REST_REQUESTS_PER_TENANT` | `REST_REQUESTS_PER_CUSTOMER` | `WS_UPDATES_PER_SESSION` | `CASSANDRA_WRITE_QUERIES_CORE` | `CASSANDRA_READ_QUERIES_CORE` | `CASSANDRA_WRITE_QUERIES_RULE_ENGINE` | … (36 values total) #### NotificationRuleTriggerType (enum) `ENTITY_ACTION` | `ALARM` | `ALARM_COMMENT` | `ALARM_ASSIGNMENT` | `DEVICE_ACTIVITY` | `RULE_ENGINE_COMPONENT_LIFECYCLE_EVENT` | `INTEGRATION_LIFECYCLE_EVENT` | `EDGE_CONNECTION` | `EDGE_COMMUNICATION_FAILURE` | `NEW_PLATFORM_VERSION` | … (15 values total) diff --git a/pe/docs/Resource.md b/pe/docs/Resource.md index 2f7bea63..b97b1220 100644 --- a/pe/docs/Resource.md +++ b/pe/docs/Resource.md @@ -110,6 +110,8 @@ * `AI_MODEL` (value: `"AI_MODEL"`) +* `AI` (value: `"AI"`) + * `API_KEY` (value: `"API_KEY"`) diff --git a/pe/docs/SolutionStep.md b/pe/docs/SolutionStep.md new file mode 100644 index 00000000..323ef8ab --- /dev/null +++ b/pe/docs/SolutionStep.md @@ -0,0 +1,23 @@ + +# SolutionStep + +`org.thingsboard.client.model.SolutionStep` + +## Enum Values + + +* `INITIAL_CONFIGURATION` (value: `"INITIAL_CONFIGURATION"`) + +* `DASHBOARDS_CONFIGURATION` (value: `"DASHBOARDS_CONFIGURATION"`) + + + +--- + +### Conventions + +- **Package:** `org.thingsboard.client.model` +- **Getter pattern:** `get()` — e.g., `getId()`, `getName()` +- **Setter pattern:** `set(value)` — e.g., `setId(value)`, `setName(value)` +- **Null fields:** Getters return `null` for unset optional fields; they do not throw exceptions + diff --git a/pe/docs/TenantProfile.md b/pe/docs/TenantProfile.md index 6b27a41f..448baf56 100644 --- a/pe/docs/TenantProfile.md +++ b/pe/docs/TenantProfile.md @@ -83,6 +83,7 @@ A JSON value representing the tenant profile. | maxSms | Long | | [optional] | | maxCreatedAlarms | Long | | [optional] | | maxGeneratedReports | Long | | [optional] | +| maxAiCredits | Long | | [optional] | | tenantServerRestLimitsConfiguration | String | | [optional] | | customerServerRestLimitsConfiguration | String | | [optional] | | maxWsSessionsPerTenant | Integer | | [optional] | @@ -124,6 +125,7 @@ A JSON value representing the tenant profile. | intermediateAggregationIntervalInSecForCF | Long | | [optional] | | cfReevaluationCheckInterval | Long | | [optional] | | alarmsReevaluationInterval | Long | | [optional] | +| aiChatRequestsPerTenantRateLimit | String | | [optional] | #### TenantProfileQueueConfiguration | Name | Type | Description | Notes | diff --git a/pe/docs/TenantProfileConfiguration.md b/pe/docs/TenantProfileConfiguration.md index 3ec5515c..3457091a 100644 --- a/pe/docs/TenantProfileConfiguration.md +++ b/pe/docs/TenantProfileConfiguration.md @@ -62,6 +62,7 @@ | maxSms | Long | | [optional] | | maxCreatedAlarms | Long | | [optional] | | maxGeneratedReports | Long | | [optional] | +| maxAiCredits | Long | | [optional] | | tenantServerRestLimitsConfiguration | String | | [optional] | | customerServerRestLimitsConfiguration | String | | [optional] | | maxWsSessionsPerTenant | Integer | | [optional] | @@ -103,6 +104,7 @@ | intermediateAggregationIntervalInSecForCF | Long | | [optional] | | cfReevaluationCheckInterval | Long | | [optional] | | alarmsReevaluationInterval | Long | | [optional] | +| aiChatRequestsPerTenantRateLimit | String | | [optional] | --- diff --git a/pe/docs/TenantProfileData.md b/pe/docs/TenantProfileData.md index bd78c0dc..56999bba 100644 --- a/pe/docs/TenantProfileData.md +++ b/pe/docs/TenantProfileData.md @@ -68,6 +68,7 @@ | maxSms | Long | | [optional] | | maxCreatedAlarms | Long | | [optional] | | maxGeneratedReports | Long | | [optional] | +| maxAiCredits | Long | | [optional] | | tenantServerRestLimitsConfiguration | String | | [optional] | | customerServerRestLimitsConfiguration | String | | [optional] | | maxWsSessionsPerTenant | Integer | | [optional] | @@ -109,6 +110,7 @@ | intermediateAggregationIntervalInSecForCF | Long | | [optional] | | cfReevaluationCheckInterval | Long | | [optional] | | alarmsReevaluationInterval | Long | | [optional] | +| aiChatRequestsPerTenantRateLimit | String | | [optional] | #### TenantProfileQueueConfiguration | Name | Type | Description | Notes | diff --git a/pe/docs/UsageInfo.md b/pe/docs/UsageInfo.md index 0a2c9a57..3e7f8c1c 100644 --- a/pe/docs/UsageInfo.md +++ b/pe/docs/UsageInfo.md @@ -34,6 +34,8 @@ | **maxAlarms** | **Long** | | [optional] | | **reports** | **Long** | | [optional] | | **maxReports** | **Long** | | [optional] | +| **aiCredits** | **Long** | | [optional] | +| **maxAiCredits** | **Long** | | [optional] | diff --git a/pe/spec/openapi.json b/pe/spec/openapi.json index dbf604fd..20bc78e4 100644 --- a/pe/spec/openapi.json +++ b/pe/spec/openapi.json @@ -25,10 +25,22 @@ "name": "admin-controller", "description": "Admin Controller" }, + { + "name": "ai-chat-controller", + "description": "Ai Chat Controller" + }, { "name": "ai-model-controller", "description": "Ai Model Controller" }, + { + "name": "ai-solution-controller", + "description": "Ai Solution Controller" + }, + { + "name": "ai-tool-controller", + "description": "Ai Tool Controller" + }, { "name": "alarm-comment-controller", "description": "Alarm Comment Controller" @@ -3790,80 +3802,30 @@ ] } }, - "/api/ai/model": { - "get": { + "/api/ai/chats": { + "post": { "tags": [ - "ai-model-controller" + "ai-chat-controller" ], - "summary": "Get AI models (getAiModels)", - "description": "Returns a page of AI models. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "getAiModels", - "parameters": [ - { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", - "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'substring' filter based on the AI model name, provider and model ID.", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, - "schema": { - "type": "string", - "enum": [ - "createdTime", - "name", - "provider", - "modelId" - ] + "summary": "createChat", + "operationId": "createChat", + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/JsonNode" + } } }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] - } - } - ], + "required": true + }, "responses": { - "200": { - "description": "OK", + "201": { + "description": "Created", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataAiModel" + "$ref": "#/components/schemas/JsonNode" } } } @@ -3880,7 +3842,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -3982,34 +3944,29 @@ "ApiKeyForm": [] } ] - }, - "post": { + } + }, + "/api/ai/chats/{chatId}": { + "delete": { "tags": [ - "ai-model-controller" + "ai-chat-controller" ], - "summary": "Create or update AI model (saveAiModel)", - "description": "Creates or updates an AI model record.\n\n• **Create:** Omit the `id` to create a new record. The platform assigns a UUID to the new record and returns it in the `id` field of the response.\n\n• **Update:** Include an existing `id` to modify that record. If no matching record exists, the API responds with **404 Not Found**.\n\nTenant ID for the AI model will be taken from the authenticated user making the request, regardless of any value provided in the request body.\n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "saveAiModel", - "requestBody": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/AiModel" - } + "summary": "deleteChat", + "operationId": "deleteChat", + "parameters": [ + { + "name": "chatId", + "in": "path", + "required": true, + "schema": { + "type": "string", + "format": "uuid" } - }, - "required": true - }, + } + ], "responses": { - "200": { - "description": "OK", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/AiModel" - } - } - } + "204": { + "description": "No Content" }, "400": { "description": "Bad Request", @@ -4023,7 +3980,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -4125,36 +4082,37 @@ "ApiKeyForm": [] } ] - } - }, - "/api/ai/model/chat": { - "post": { + }, + "patch": { "tags": [ - "ai-model-controller" + "ai-chat-controller" + ], + "summary": "updateChat", + "operationId": "updateChat", + "parameters": [ + { + "name": "chatId", + "in": "path", + "required": true, + "schema": { + "type": "string", + "format": "uuid" + } + } ], - "summary": "Send request to AI chat model (sendChatRequest)", - "description": "Submits a single prompt - made up of an optional system message and a required user message - to the specified AI chat model and returns either the generated answer or an error envelope.\n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "sendChatRequest", "requestBody": { "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/TbChatRequest" + "$ref": "#/components/schemas/JsonNode" } } }, "required": true }, "responses": { - "200": { - "description": "OK", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/TbChatResponse" - } - } - } + "204": { + "description": "No Content" }, "400": { "description": "Bad Request", @@ -4168,7 +4126,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -4272,25 +4230,22 @@ ] } }, - "/api/ai/model/{modelUuid}": { + "/api/ai/chats/{chatId}/messages": { "get": { "tags": [ - "ai-model-controller" + "ai-chat-controller" ], - "summary": "Get AI model by ID (getAiModelById)", - "description": "Fetches an AI model record by its `id`.\n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "getAiModelById", + "summary": "getChatMessages", + "operationId": "getChatMessages", "parameters": [ { - "name": "modelUuid", + "name": "chatId", "in": "path", - "description": "ID of the AI model record", "required": true, "schema": { "type": "string", "format": "uuid" - }, - "example": "de7900d4-30e2-11f0-9cd2-0242ac120002" + } } ], "responses": { @@ -4299,7 +4254,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/AiModel" + "$ref": "#/components/schemas/JsonNode" } } } @@ -4419,33 +4374,51 @@ } ] }, - "delete": { + "post": { "tags": [ - "ai-model-controller" + "ai-chat-controller" ], - "summary": "Delete AI model by ID (deleteAiModelById)", - "description": "Deletes the AI model record by its `id`. If a record with the specified `id` exists, the record is deleted and the endpoint returns `true`. If no such record exists, the endpoint returns `false`.\n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "deleteAiModelById", + "summary": "sendChatMessage", + "operationId": "sendChatMessage", "parameters": [ { - "name": "modelUuid", + "name": "chatId", "in": "path", - "description": "ID of the AI model record", "required": true, "schema": { "type": "string", "format": "uuid" - }, - "example": "de7900d4-30e2-11f0-9cd2-0242ac120002" + } + }, + { + "name": "X-Authorization", + "in": "header", + "required": true, + "schema": { + "type": "string" + } } ], + "requestBody": { + "content": { + "text/plain": { + "schema": { + "type": "string" + } + } + }, + "required": true + }, "responses": { "200": { "description": "OK", "content": { - "application/json": { + "text/event-stream": { "schema": { - "type": "boolean" + "type": "array", + "items": { + "$ref": "#/components/schemas/ServerSentEventString" + } } } } @@ -4462,7 +4435,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -4566,68 +4539,20 @@ ] } }, - "/api/alarm/{alarmId}/comment": { + "/api/ai/chats/{chatType}": { "get": { "tags": [ - "alarm-comment-controller" + "ai-chat-controller" ], - "summary": "Get Alarm comments (getAlarmComments)", - "description": "Returns a page of alarm comments for specified alarm. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", - "operationId": "getAlarmComments", + "summary": "listChats", + "operationId": "listChats", "parameters": [ { - "name": "alarmId", + "name": "chatType", "in": "path", - "description": "A string value representing the alarm id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": true, - "schema": { - "type": "string" - } - }, - { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", "required": true, "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, - "schema": { - "type": "string", - "enum": [ - "createdTime", - "id" - ] - } - }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] + "$ref": "#/components/schemas/ChatType" } } ], @@ -4637,7 +4562,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataAlarmCommentInfo" + "$ref": "#/components/schemas/JsonNode" } } } @@ -4756,43 +4681,82 @@ "ApiKeyForm": [] } ] - }, - "post": { + } + }, + "/api/ai/model": { + "get": { "tags": [ - "alarm-comment-controller" + "ai-model-controller" ], - "summary": "Create or update Alarm Comment ", - "description": "Creates or Updates the Alarm Comment. When creating comment, platform generates Alarm Comment Id as [time-based UUID](https://en.wikipedia.org/wiki/Universally_unique_identifier#Version_1_(date-time_and_MAC_address)). The newly created Alarm Comment id will be present in the response. Specify existing Alarm Comment id to update the alarm. Referencing non-existing Alarm Comment Id will cause 'Not Found' error. \n\n To create new Alarm comment entity it is enough to specify 'comment' json element with 'text' node, for example: {\"comment\": { \"text\": \"my comment\"}}. \n\n If comment type is not specified the default value 'OTHER' will be saved. If 'alarmId' or 'userId' specified in body it will be ignored.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", - "operationId": "saveAlarmComment", + "summary": "Get AI models (getAiModels)", + "description": "Returns a page of AI models. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "getAiModels", "parameters": [ { - "name": "alarmId", - "in": "path", - "description": "A string value representing the alarm id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", + "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'substring' filter based on the AI model name, provider and model ID.", + "required": false, "schema": { "type": "string" } - } - ], - "requestBody": { - "description": "A JSON value representing the comment.", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/AlarmComment" - } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string", + "enum": [ + "createdTime", + "name", + "provider", + "modelId" + ] } }, - "required": true - }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] + } + } + ], "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/AlarmComment" + "$ref": "#/components/schemas/PageDataAiModel" } } } @@ -4809,7 +4773,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -4911,39 +4875,34 @@ "ApiKeyForm": [] } ] - } - }, - "/api/alarm/{alarmId}/comment/{commentId}": { - "delete": { + }, + "post": { "tags": [ - "alarm-comment-controller" + "ai-model-controller" ], - "summary": "Delete Alarm comment (deleteAlarmComment)", - "description": "Deletes the Alarm comment. Referencing non-existing Alarm comment Id will cause an error.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", - "operationId": "deleteAlarmComment", - "parameters": [ - { - "name": "alarmId", - "in": "path", - "description": "A string value representing the alarm id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": true, - "schema": { - "type": "string" + "summary": "Create or update AI model (saveAiModel)", + "description": "Creates or updates an AI model record.\n\n• **Create:** Omit the `id` to create a new record. The platform assigns a UUID to the new record and returns it in the `id` field of the response.\n\n• **Update:** Include an existing `id` to modify that record. If no matching record exists, the API responds with **404 Not Found**.\n\nTenant ID for the AI model will be taken from the authenticated user making the request, regardless of any value provided in the request body.\n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "saveAiModel", + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/AiModel" + } } }, - { - "name": "commentId", - "in": "path", - "description": "A string value representing the alarm comment id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": true, - "schema": { - "type": "string" - } - } - ], + "required": true + }, "responses": { "200": { - "description": "OK" + "description": "OK", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/AiModel" + } + } + } }, "400": { "description": "Bad Request", @@ -4957,7 +4916,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -5061,20 +5020,19 @@ ] } }, - "/api/alarm": { + "/api/ai/model/chat": { "post": { "tags": [ - "alarm-controller" + "ai-model-controller" ], - "summary": "Create or Update Alarm (saveAlarm)", - "description": "Creates or Updates the Alarm. When creating alarm, platform generates Alarm Id as [time-based UUID](https://en.wikipedia.org/wiki/Universally_unique_identifier#Version_1_(date-time_and_MAC_address)). The newly created Alarm id will be present in the response. Specify existing Alarm id to update the alarm. Referencing non-existing Alarm Id will cause 'Not Found' error. \n\nPlatform also deduplicate the alarms based on the entity id of originator and alarm 'type'. For example, if the user or system component create the alarm with the type 'HighTemperature' for device 'Device A' the new active alarm is created. If the user tries to create 'HighTemperature' alarm for the same device again, the previous alarm will be updated (the 'end_ts' will be set to current timestamp). If the user clears the alarm (see 'Clear Alarm(clearAlarm)'), than new alarm with the same type and same device may be created. Remove 'id', 'tenantId' and optionally 'customerId' from the request body example (below) to create new Alarm entity. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'WRITE' permission for the entity (entities).", - "operationId": "saveAlarm", + "summary": "Send request to AI chat model (sendChatRequest)", + "description": "Submits a single prompt - made up of an optional system message and a required user message - to the specified AI chat model and returns either the generated answer or an error envelope.\n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "sendChatRequest", "requestBody": { - "description": "A JSON value representing the alarm.", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/Alarm" + "$ref": "#/components/schemas/TbChatRequest" } } }, @@ -5086,7 +5044,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/Alarm" + "$ref": "#/components/schemas/TbChatResponse" } } } @@ -5207,72 +5165,25 @@ ] } }, - "/api/alarm/highestSeverity/{entityType}/{entityId}": { + "/api/ai/model/{modelUuid}": { "get": { "tags": [ - "alarm-controller" + "ai-model-controller" ], - "summary": "Get Highest Alarm Severity (getHighestAlarmSeverity)", - "description": "Search the alarms by originator ('entityType' and entityId') and optional 'status' or 'searchStatus' filters and returns the highest AlarmSeverity(CRITICAL, MAJOR, MINOR, WARNING or INDETERMINATE). Specifying both parameters 'searchStatus' and 'status' at the same time will cause an error.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getHighestAlarmSeverity", + "summary": "Get AI model by ID (getAiModelById)", + "description": "Fetches an AI model record by its `id`.\n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "getAiModelById", "parameters": [ { - "name": "entityType", - "in": "path", - "description": "A string value representing the entity type. For example, 'DEVICE'", - "required": true, - "schema": { - "type": "string" - } - }, - { - "name": "entityId", + "name": "modelUuid", "in": "path", - "description": "A string value representing the entity id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "description": "ID of the AI model record", "required": true, - "schema": { - "type": "string" - } - }, - { - "name": "searchStatus", - "in": "query", - "description": "A string value representing one of the AlarmSearchStatus enumeration value", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ANY", - "ACTIVE", - "CLEARED", - "ACK", - "UNACK" - ] - } - }, - { - "name": "status", - "in": "query", - "description": "A string value representing one of the AlarmStatus enumeration value", - "required": false, "schema": { "type": "string", - "enum": [ - "ACTIVE_UNACK", - "ACTIVE_ACK", - "CLEARED_UNACK", - "CLEARED_ACK" - ] - } - }, - { - "name": "assigneeId", - "in": "query", - "description": "A string value representing the assignee user id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": false, - "schema": { - "type": "string" - } + "format": "uuid" + }, + "example": "de7900d4-30e2-11f0-9cd2-0242ac120002" } ], "responses": { @@ -5281,7 +5192,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/AlarmSeverity" + "$ref": "#/components/schemas/AiModel" } } } @@ -5400,25 +5311,25 @@ "ApiKeyForm": [] } ] - } - }, - "/api/alarm/info/{alarmId}": { - "get": { + }, + "delete": { "tags": [ - "alarm-controller" + "ai-model-controller" ], - "summary": "Get Alarm Info (getAlarmInfoById)", - "description": "Fetch the Alarm Info object based on the provided Alarm Id. Alarm Info is an extension of the default Alarm object that also contains name of the alarm originator.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getAlarmInfoById", + "summary": "Delete AI model by ID (deleteAiModelById)", + "description": "Deletes the AI model record by its `id`. If a record with the specified `id` exists, the record is deleted and the endpoint returns `true`. If no such record exists, the endpoint returns `false`.\n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "deleteAiModelById", "parameters": [ { - "name": "alarmId", + "name": "modelUuid", "in": "path", - "description": "A string value representing the alarm id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "description": "ID of the AI model record", "required": true, "schema": { - "type": "string" - } + "type": "string", + "format": "uuid" + }, + "example": "de7900d4-30e2-11f0-9cd2-0242ac120002" } ], "responses": { @@ -5427,7 +5338,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/AlarmInfo" + "type": "boolean" } } } @@ -5548,65 +5459,20 @@ ] } }, - "/api/alarm/types": { + "/api/ai/solution/infos": { "get": { "tags": [ - "alarm-controller" - ], - "summary": "Get Alarm Types (getAlarmTypes)", - "description": "Returns a set of unique alarm types based on alarms that are either owned by the tenant or assigned to the customer which user is performing the request.", - "operationId": "getAlarmTypes", - "parameters": [ - { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", - "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'substring' filter based on of next alarm fields: type, severity or status", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] - } - } + "ai-solution-controller" ], + "summary": "getSolutions", + "operationId": "getSolutions", "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataEntitySubtype" + "$ref": "#/components/schemas/JsonNode" } } } @@ -5727,32 +5593,20 @@ ] } }, - "/api/alarm/{alarmId}": { - "get": { + "/api/ai/solution/start": { + "post": { "tags": [ - "alarm-controller" - ], - "summary": "Get Alarm (getAlarmById)", - "description": "Fetch the Alarm object based on the provided Alarm Id. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getAlarmById", - "parameters": [ - { - "name": "alarmId", - "in": "path", - "description": "A string value representing the alarm id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": true, - "schema": { - "type": "string" - } - } + "ai-solution-controller" ], + "summary": "startNew", + "operationId": "startNew", "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/Alarm" + "$ref": "#/components/schemas/JsonNode" } } } @@ -5769,7 +5623,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -5871,22 +5725,23 @@ "ApiKeyForm": [] } ] - }, - "delete": { + } + }, + "/api/ai/solution/{solutionId}": { + "get": { "tags": [ - "alarm-controller" + "ai-solution-controller" ], - "summary": "Delete Alarm (deleteAlarm)", - "description": "Deletes the Alarm. Referencing non-existing Alarm Id will cause an error.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'DELETE' permission for the entity (entities).", - "operationId": "deleteAlarm", + "summary": "getSolution", + "operationId": "getSolution", "parameters": [ { - "name": "alarmId", + "name": "solutionId", "in": "path", - "description": "A string value representing the alarm id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { - "type": "string" + "type": "string", + "format": "uuid" } } ], @@ -5896,7 +5751,7 @@ "content": { "application/json": { "schema": { - "type": "boolean" + "$ref": "#/components/schemas/JsonNode" } } } @@ -6015,37 +5870,27 @@ "ApiKeyForm": [] } ] - } - }, - "/api/alarm/{alarmId}/ack": { - "post": { + }, + "delete": { "tags": [ - "alarm-controller" + "ai-solution-controller" ], - "summary": "Acknowledge Alarm (ackAlarm)", - "description": "Acknowledge the Alarm. Once acknowledged, the 'ack_ts' field will be set to current timestamp and special rule chain event 'ALARM_ACK' will be generated. Referencing non-existing Alarm Id will cause an error.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'WRITE' permission for the entity (entities).", - "operationId": "ackAlarm", + "summary": "deleteSolution", + "operationId": "deleteSolution", "parameters": [ { - "name": "alarmId", + "name": "solutionId", "in": "path", - "description": "A string value representing the alarm id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { - "type": "string" + "type": "string", + "format": "uuid" } } ], "responses": { "200": { - "description": "OK", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/AlarmInfo" - } - } - } + "description": "OK" }, "400": { "description": "Bad Request", @@ -6059,7 +5904,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -6163,22 +6008,21 @@ ] } }, - "/api/alarm/{alarmId}/assign": { - "delete": { + "/api/ai/solution/{solutionId}/create": { + "post": { "tags": [ - "alarm-controller" + "ai-solution-controller" ], - "summary": "Unassign Alarm (unassignAlarm)", - "description": "Unassign the Alarm. Once unassigned, the 'assign_ts' field will be set to current timestamp and special rule chain event 'ALARM_UNASSIGNED' will be generated. Referencing non-existing Alarm Id will cause an error.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", - "operationId": "unassignAlarm", + "summary": "createSolution", + "operationId": "createSolution", "parameters": [ { - "name": "alarmId", + "name": "solutionId", "in": "path", - "description": "A string value representing the alarm id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { - "type": "string" + "type": "string", + "format": "uuid" } } ], @@ -6188,7 +6032,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/Alarm" + "$ref": "#/components/schemas/JsonNode" } } } @@ -6205,7 +6049,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -6309,28 +6153,26 @@ ] } }, - "/api/alarm/{alarmId}/assign/{assigneeId}": { + "/api/ai/solution/{solutionId}/install": { "post": { "tags": [ - "alarm-controller" + "ai-solution-controller" ], - "summary": "Assign/Reassign Alarm (assignAlarm)", - "description": "Assign the Alarm. Once assigned, the 'assign_ts' field will be set to current timestamp and special rule chain event 'ALARM_ASSIGNED' (or ALARM_REASSIGNED in case of assigning already assigned alarm) will be generated. Referencing non-existing Alarm Id will cause an error.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", - "operationId": "assignAlarm", + "summary": "installSolution", + "operationId": "installSolution", "parameters": [ { - "name": "alarmId", + "name": "solutionId", "in": "path", - "description": "A string value representing the alarm id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { - "type": "string" + "type": "string", + "format": "uuid" } }, { - "name": "assigneeId", - "in": "path", - "description": "A string value representing the user id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "name": "X-Authorization", + "in": "header", "required": true, "schema": { "type": "string" @@ -6343,7 +6185,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/Alarm" + "$ref": "#/components/schemas/JsonNode" } } } @@ -6464,19 +6306,26 @@ ] } }, - "/api/alarm/{alarmId}/clear": { - "post": { + "/api/ai/solution/{solutionId}/uninstall": { + "delete": { "tags": [ - "alarm-controller" + "ai-solution-controller" ], - "summary": "Clear Alarm (clearAlarm)", - "description": "Clear the Alarm. Once cleared, the 'clear_ts' field will be set to current timestamp and special rule chain event 'ALARM_CLEAR' will be generated. Referencing non-existing Alarm Id will cause an error.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'WRITE' permission for the entity (entities).", - "operationId": "clearAlarm", + "summary": "uninstallSolution", + "operationId": "uninstallSolution", "parameters": [ { - "name": "alarmId", + "name": "solutionId", "in": "path", - "description": "A string value representing the alarm id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, + "schema": { + "type": "string", + "format": "uuid" + } + }, + { + "name": "X-Authorization", + "in": "header", "required": true, "schema": { "type": "string" @@ -6489,7 +6338,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/AlarmInfo" + "$ref": "#/components/schemas/JsonNode" } } } @@ -6506,7 +6355,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -6610,171 +6459,49 @@ ] } }, - "/api/alarm/{entityType}/{entityId}": { - "get": { + "/api/ai/solution/{solutionId}/{dataKey}": { + "put": { "tags": [ - "alarm-controller" + "ai-solution-controller" ], - "summary": "Get Alarms (getAlarmsByEntity)", - "description": "Returns a page of alarms for the selected entity. Specifying both parameters 'searchStatus' and 'status' at the same time will cause an error. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getAlarmsByEntity", + "summary": "updateData", + "operationId": "updateData", "parameters": [ { - "name": "entityType", + "name": "solutionId", "in": "path", - "description": "A string value representing the entity type. For example, 'DEVICE'", "required": true, - "schema": { - "type": "string" - } - }, - { - "name": "entityId", - "in": "path", - "description": "A string value representing the entity id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": true, - "schema": { - "type": "string" - } - }, - { - "name": "searchStatus", - "in": "query", - "description": "A string value representing one of the AlarmSearchStatus enumeration value", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ANY", - "ACTIVE", - "CLEARED", - "ACK", - "UNACK" - ] - } - }, - { - "name": "status", - "in": "query", - "description": "A string value representing one of the AlarmStatus enumeration value", - "required": false, "schema": { "type": "string", - "enum": [ - "ACTIVE_UNACK", - "ACTIVE_ACK", - "CLEARED_UNACK", - "CLEARED_ACK" - ] - } - }, - { - "name": "assigneeId", - "in": "query", - "description": "A string value representing the assignee user id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "integer", - "format": "int32" + "format": "uuid" } }, { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", + "name": "dataKey", + "in": "path", "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'substring' filter based on of next alarm fields: type, severity or status", - "required": false, "schema": { "type": "string" } - }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, - "schema": { - "type": "string", - "enum": [ - "createdTime", - "startTs", - "endTs", - "type", - "ackTs", - "clearTs", - "severity", - "status" - ] - } - }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] - } - }, - { - "name": "startTime", - "in": "query", - "description": "The start timestamp in milliseconds of the search time range over the Alarm class field: 'createdTime'.", - "required": false, - "schema": { - "type": "integer", - "format": "int64" - } - }, - { - "name": "endTime", - "in": "query", - "description": "The end timestamp in milliseconds of the search time range over the Alarm class field: 'createdTime'.", - "required": false, - "schema": { - "type": "integer", - "format": "int64" - } - }, - { - "name": "fetchOriginator", - "in": "query", - "description": "A boolean value to specify if the alarm originator name will be filled in the AlarmInfo object field: 'originatorName' or will returns as null.", - "required": false, - "schema": { - "type": "boolean" - } } ], + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/JsonNode" + } + } + }, + "required": true + }, "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataAlarmInfo" + "$ref": "#/components/schemas/JsonNode" } } } @@ -6895,153 +6622,49 @@ ] } }, - "/api/alarms": { - "get": { + "/api/ai/solution/{solutionId}/{step}/chat": { + "post": { "tags": [ - "alarm-controller" + "ai-solution-controller" ], - "summary": "Get All Alarms (getAllAlarms)", - "description": "Returns a page of alarms that belongs to the current user owner. If the user has the authority of 'Tenant Administrator', the server returns alarms that belongs to the tenant of current user. If the user has the authority of 'Customer User', the server returns alarms that belongs to the customer of current user. Specifying both parameters 'searchStatus' and 'status' at the same time will cause an error. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getAllAlarms", + "summary": "chat", + "operationId": "chat", "parameters": [ { - "name": "searchStatus", - "in": "query", - "description": "A string value representing one of the AlarmSearchStatus enumeration value", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ANY", - "ACTIVE", - "CLEARED", - "ACK", - "UNACK" - ] - } - }, - { - "name": "status", - "in": "query", - "description": "A string value representing one of the AlarmStatus enumeration value", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ACTIVE_UNACK", - "ACTIVE_ACK", - "CLEARED_UNACK", - "CLEARED_ACK" - ] - } - }, - { - "name": "assigneeId", - "in": "query", - "description": "A string value representing the assignee user id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", + "name": "solutionId", + "in": "path", "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'substring' filter based on of next alarm fields: type, severity or status", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, - "schema": { - "type": "string", - "enum": [ - "createdTime", - "startTs", - "endTs", - "type", - "ackTs", - "clearTs", - "severity", - "status" - ] - } - }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, "schema": { "type": "string", - "enum": [ - "ASC", - "DESC" - ] - } - }, - { - "name": "startTime", - "in": "query", - "description": "The start timestamp in milliseconds of the search time range over the Alarm class field: 'createdTime'.", - "required": false, - "schema": { - "type": "integer", - "format": "int64" - } - }, - { - "name": "endTime", - "in": "query", - "description": "The end timestamp in milliseconds of the search time range over the Alarm class field: 'createdTime'.", - "required": false, - "schema": { - "type": "integer", - "format": "int64" + "format": "uuid" } }, { - "name": "fetchOriginator", - "in": "query", - "description": "A boolean value to specify if the alarm originator name will be filled in the AlarmInfo object field: 'originatorName' or will returns as null.", - "required": false, + "name": "step", + "in": "path", + "required": true, "schema": { - "type": "boolean" + "$ref": "#/components/schemas/SolutionStep" } } ], + "requestBody": { + "content": { + "application/json": { + "schema": { + "type": "string" + } + } + }, + "required": true + }, "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataAlarmInfo" + "$ref": "#/components/schemas/JsonNode" } } } @@ -7058,7 +6681,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -7162,181 +6785,176 @@ ] } }, - "/api/v2/alarm/{entityType}/{entityId}": { - "get": { + "/api/ai/solution/{solutionId}/{step}/clear": { + "delete": { "tags": [ - "alarm-controller" + "ai-solution-controller" ], - "summary": "Get Alarms (getAlarmsV2)", - "description": "Returns a page of alarms for the selected entity. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", - "operationId": "getAlarmsV2", + "summary": "clearStep", + "operationId": "clearStep", "parameters": [ { - "name": "entityType", + "name": "solutionId", "in": "path", - "description": "A string value representing the entity type. For example, 'DEVICE'", "required": true, "schema": { - "type": "string" + "type": "string", + "format": "uuid" } }, { - "name": "entityId", + "name": "step", "in": "path", - "description": "A string value representing the entity id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { - "type": "string" + "$ref": "#/components/schemas/SolutionStep" } + } + ], + "responses": { + "200": { + "description": "OK" }, - { - "name": "statusList", - "in": "query", - "description": "A list of string values separated by comma ',' representing one of the AlarmSearchStatus enumeration value", - "required": false, - "schema": { - "type": "array", - "items": { - "type": "string", - "enum": [ - "ANY", - "ACTIVE", - "CLEARED", - "ACK", - "UNACK" - ] + "400": { + "description": "Bad Request", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-400": { + "summary": "Bad Request", + "value": { + "status": 400, + "message": "Invalid UUID string: 123", + "errorCode": 31, + "timestamp": 1609459200000 + } + } + } } } }, - { - "name": "severityList", - "in": "query", - "description": "A list of string values separated by comma ',' representing one of the AlarmSeverity enumeration value", - "required": false, - "schema": { - "type": "array", - "items": { - "type": "string", - "enum": [ - "CRITICAL", - "MAJOR", - "MINOR", - "WARNING", - "INDETERMINATE" - ] + "401": { + "description": "Unauthorized", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-401": { + "summary": "Unauthorized", + "value": { + "status": 401, + "message": "Authentication failed", + "errorCode": 10, + "timestamp": 1609459200000 + } + } + } } } }, - { - "name": "typeList", - "in": "query", - "description": "A list of string values separated by comma ',' representing alarm types", - "required": false, - "schema": { - "type": "array", - "items": { - "type": "string" + "403": { + "description": "Forbidden", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-403": { + "summary": "Forbidden", + "value": { + "status": 403, + "message": "You don't have permission to perform this operation!", + "errorCode": 20, + "timestamp": 1609459200000 + } + } + } } } }, - { - "name": "assigneeId", - "in": "query", - "description": "A string value representing the assignee user id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", - "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'substring' filter based on of next alarm fields: type, severity or status", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, - "schema": { - "type": "string", - "enum": [ - "createdTime", - "startTs", - "endTs", - "type", - "ackTs", - "clearTs", - "severity", - "status" - ] + "404": { + "description": "Not Found", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-404": { + "summary": "Not Found", + "value": { + "status": 404, + "message": "Requested item wasn't found!", + "errorCode": 32, + "timestamp": 1609459200000 + } + } + } + } } }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] + "429": { + "description": "Too Many Requests", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-429": { + "summary": "Too Many Requests", + "value": { + "status": 429, + "message": "Too many requests for current tenant!", + "errorCode": 33, + "timestamp": 1609459200000 + } + } + } + } } - }, + } + }, + "security": [ { - "name": "startTime", - "in": "query", - "description": "The start timestamp in milliseconds of the search time range over the Alarm class field: 'createdTime'.", - "required": false, - "schema": { - "type": "integer", - "format": "int64" - } + "HttpLoginForm": [] }, { - "name": "endTime", - "in": "query", - "description": "The end timestamp in milliseconds of the search time range over the Alarm class field: 'createdTime'.", - "required": false, - "schema": { - "type": "integer", - "format": "int64" - } + "ApiKeyForm": [] } + ] + } + }, + "/api/ai/tools/resolve-approval": { + "post": { + "tags": [ + "ai-tool-controller" ], + "summary": "resolveToolApproval", + "operationId": "resolveToolApproval", + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/JsonNode" + } + } + }, + "required": true + }, "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataAlarmInfo" + "$ref": "#/components/schemas/JsonNode" } } } @@ -7353,7 +6971,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -7457,70 +7075,20 @@ ] } }, - "/api/v2/alarms": { + "/api/alarm/{alarmId}/comment": { "get": { "tags": [ - "alarm-controller" + "alarm-comment-controller" ], - "summary": "Get All Alarms (getAllAlarmsV2)", - "description": "Returns a page of alarms that belongs to the current user owner. If the user has the authority of 'Tenant Administrator', the server returns alarms that belongs to the tenant of current user. If the user has the authority of 'Customer User', the server returns alarms that belongs to the customer of current user. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", - "operationId": "getAllAlarmsV2", + "summary": "Get Alarm comments (getAlarmComments)", + "description": "Returns a page of alarm comments for specified alarm. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", + "operationId": "getAlarmComments", "parameters": [ { - "name": "statusList", - "in": "query", - "description": "A list of string values separated by comma ',' representing one of the AlarmSearchStatus enumeration value", - "required": false, - "schema": { - "type": "array", - "items": { - "type": "string", - "enum": [ - "ANY", - "ACTIVE", - "CLEARED", - "ACK", - "UNACK" - ] - } - } - }, - { - "name": "severityList", - "in": "query", - "description": "A list of string values separated by comma ',' representing one of the AlarmSeverity enumeration value", - "required": false, - "schema": { - "type": "array", - "items": { - "type": "string", - "enum": [ - "CRITICAL", - "MAJOR", - "MINOR", - "WARNING", - "INDETERMINATE" - ] - } - } - }, - { - "name": "typeList", - "in": "query", - "description": "A list of string values separated by comma ',' representing alarm types", - "required": false, - "schema": { - "type": "array", - "items": { - "type": "string" - } - } - }, - { - "name": "assigneeId", - "in": "query", - "description": "A string value representing the assignee user id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": false, + "name": "alarmId", + "in": "path", + "description": "A string value representing the alarm id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, "schema": { "type": "string" } @@ -7545,15 +7113,6 @@ "format": "int32" } }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'substring' filter based on of next alarm fields: type, severity or status", - "required": false, - "schema": { - "type": "string" - } - }, { "name": "sortProperty", "in": "query", @@ -7563,13 +7122,7 @@ "type": "string", "enum": [ "createdTime", - "startTs", - "endTs", - "type", - "ackTs", - "clearTs", - "severity", - "status" + "id" ] } }, @@ -7585,26 +7138,6 @@ "DESC" ] } - }, - { - "name": "startTime", - "in": "query", - "description": "The start timestamp in milliseconds of the search time range over the Alarm class field: 'createdTime'.", - "required": false, - "schema": { - "type": "integer", - "format": "int64" - } - }, - { - "name": "endTime", - "in": "query", - "description": "The end timestamp in milliseconds of the search time range over the Alarm class field: 'createdTime'.", - "required": false, - "schema": { - "type": "integer", - "format": "int64" - } } ], "responses": { @@ -7613,7 +7146,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataAlarmInfo" + "$ref": "#/components/schemas/PageDataAlarmCommentInfo" } } } @@ -7732,22 +7265,31 @@ "ApiKeyForm": [] } ] - } - }, - "/api/alarm/rule": { + }, "post": { "tags": [ - "alarm-rule-controller" + "alarm-comment-controller" + ], + "summary": "Create or update Alarm Comment ", + "description": "Creates or Updates the Alarm Comment. When creating comment, platform generates Alarm Comment Id as [time-based UUID](https://en.wikipedia.org/wiki/Universally_unique_identifier#Version_1_(date-time_and_MAC_address)). The newly created Alarm Comment id will be present in the response. Specify existing Alarm Comment id to update the alarm. Referencing non-existing Alarm Comment Id will cause 'Not Found' error. \n\n To create new Alarm comment entity it is enough to specify 'comment' json element with 'text' node, for example: {\"comment\": { \"text\": \"my comment\"}}. \n\n If comment type is not specified the default value 'OTHER' will be saved. If 'alarmId' or 'userId' specified in body it will be ignored.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", + "operationId": "saveAlarmComment", + "parameters": [ + { + "name": "alarmId", + "in": "path", + "description": "A string value representing the alarm id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, + "schema": { + "type": "string" + } + } ], - "summary": "Create Or Update Alarm Rule (saveAlarmRule)", - "description": "Creates or Updates the Alarm Rule. When creating alarm rule, platform generates Alarm Rule Id as [time-based UUID](https://en.wikipedia.org/wiki/Universally_unique_identifier#Version_1_(date-time_and_MAC_address)). The newly created Alarm Rule Id will be present in the response. Specify existing Alarm Rule Id to update the alarm rule. Referencing non-existing Alarm Rule Id will cause 'Not Found' error. Remove 'id', 'tenantId' from the request body example (below) to create new Alarm Rule entity. \n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "saveAlarmRule", "requestBody": { - "description": "A JSON value representing the alarm rule.", + "description": "A JSON value representing the comment.", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/AlarmRuleDefinition" + "$ref": "#/components/schemas/AlarmComment" } } }, @@ -7759,7 +7301,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/AlarmRuleDefinition" + "$ref": "#/components/schemas/AlarmComment" } } } @@ -7880,35 +7422,37 @@ ] } }, - "/api/alarm/rule/testScript": { - "post": { + "/api/alarm/{alarmId}/comment/{commentId}": { + "delete": { "tags": [ - "alarm-rule-controller" + "alarm-comment-controller" ], - "summary": "Test alarm rule TBEL expression (testAlarmRuleScript)", - "description": "Execute the alarm rule TBEL condition expression and return the result. Alarm rule expressions must return a boolean value. The format of request: \n\n```json\n{\n \"expression\": \"return temperature > 50;\",\n \"arguments\": {\n \"temperature\": { \"type\": \"SINGLE_VALUE\", \"ts\": 1739776478057, \"value\": 55 }\n }\n}\n```\n\n Expected result JSON contains \"output\" and \"error\".\n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "testAlarmRuleScript", - "requestBody": { - "description": "Test alarm rule TBEL condition expression. The expression must return a boolean value.", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/JsonNode" - } + "summary": "Delete Alarm comment (deleteAlarmComment)", + "description": "Deletes the Alarm comment. Referencing non-existing Alarm comment Id will cause an error.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", + "operationId": "deleteAlarmComment", + "parameters": [ + { + "name": "alarmId", + "in": "path", + "description": "A string value representing the alarm id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, + "schema": { + "type": "string" } }, - "required": true - }, + { + "name": "commentId", + "in": "path", + "description": "A string value representing the alarm comment id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, + "schema": { + "type": "string" + } + } + ], "responses": { "200": { - "description": "OK", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/JsonNode" - } - } - } + "description": "OK" }, "400": { "description": "Bad Request", @@ -7922,7 +7466,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -8026,31 +7570,32 @@ ] } }, - "/api/alarm/rule/{alarmRuleId}": { - "get": { + "/api/alarm": { + "post": { "tags": [ - "alarm-rule-controller" + "alarm-controller" ], - "summary": "Get Alarm Rule (getAlarmRuleById)", - "description": "Fetch the Alarm Rule object based on the provided Alarm Rule Id.\n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "getAlarmRuleById", - "parameters": [ - { - "name": "alarmRuleId", - "in": "path", - "required": true, - "schema": { - "type": "string" + "summary": "Create or Update Alarm (saveAlarm)", + "description": "Creates or Updates the Alarm. When creating alarm, platform generates Alarm Id as [time-based UUID](https://en.wikipedia.org/wiki/Universally_unique_identifier#Version_1_(date-time_and_MAC_address)). The newly created Alarm id will be present in the response. Specify existing Alarm id to update the alarm. Referencing non-existing Alarm Id will cause 'Not Found' error. \n\nPlatform also deduplicate the alarms based on the entity id of originator and alarm 'type'. For example, if the user or system component create the alarm with the type 'HighTemperature' for device 'Device A' the new active alarm is created. If the user tries to create 'HighTemperature' alarm for the same device again, the previous alarm will be updated (the 'end_ts' will be set to current timestamp). If the user clears the alarm (see 'Clear Alarm(clearAlarm)'), than new alarm with the same type and same device may be created. Remove 'id', 'tenantId' and optionally 'customerId' from the request body example (below) to create new Alarm entity. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'WRITE' permission for the entity (entities).", + "operationId": "saveAlarm", + "requestBody": { + "description": "A JSON value representing the alarm.", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/Alarm" + } } - } - ], + }, + "required": true + }, "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/AlarmRuleDefinition" + "$ref": "#/components/schemas/Alarm" } } } @@ -8067,7 +7612,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -8169,27 +7714,86 @@ "ApiKeyForm": [] } ] - }, - "delete": { + } + }, + "/api/alarm/highestSeverity/{entityType}/{entityId}": { + "get": { "tags": [ - "alarm-rule-controller" + "alarm-controller" ], - "summary": "Delete Alarm Rule (deleteAlarmRule)", - "description": "Deletes the alarm rule. Referencing non-existing Alarm Rule Id will cause an error.\n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "deleteAlarmRule", + "summary": "Get Highest Alarm Severity (getHighestAlarmSeverity)", + "description": "Search the alarms by originator ('entityType' and entityId') and optional 'status' or 'searchStatus' filters and returns the highest AlarmSeverity(CRITICAL, MAJOR, MINOR, WARNING or INDETERMINATE). Specifying both parameters 'searchStatus' and 'status' at the same time will cause an error.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getHighestAlarmSeverity", "parameters": [ { - "name": "alarmRuleId", + "name": "entityType", + "in": "path", + "description": "A string value representing the entity type. For example, 'DEVICE'", + "required": true, + "schema": { + "type": "string" + } + }, + { + "name": "entityId", "in": "path", + "description": "A string value representing the entity id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { "type": "string" } + }, + { + "name": "searchStatus", + "in": "query", + "description": "A string value representing one of the AlarmSearchStatus enumeration value", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ANY", + "ACTIVE", + "CLEARED", + "ACK", + "UNACK" + ] + } + }, + { + "name": "status", + "in": "query", + "description": "A string value representing one of the AlarmStatus enumeration value", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ACTIVE_UNACK", + "ACTIVE_ACK", + "CLEARED_UNACK", + "CLEARED_ACK" + ] + } + }, + { + "name": "assigneeId", + "in": "query", + "description": "A string value representing the assignee user id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": false, + "schema": { + "type": "string" + } } ], "responses": { "200": { - "description": "OK" + "description": "OK", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/AlarmSeverity" + } + } + } }, "400": { "description": "Bad Request", @@ -8307,18 +7911,19 @@ ] } }, - "/api/alarm/rule/{alarmRuleId}/debug": { + "/api/alarm/info/{alarmId}": { "get": { "tags": [ - "alarm-rule-controller" + "alarm-controller" ], - "summary": "Get latest alarm rule debug event (getLatestAlarmRuleDebugEvent)", - "description": "Gets latest alarm rule debug event for specified alarm rule id. Referencing non-existing alarm rule id will cause an error. \n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "getLatestAlarmRuleDebugEvent", + "summary": "Get Alarm Info (getAlarmInfoById)", + "description": "Fetch the Alarm Info object based on the provided Alarm Id. Alarm Info is an extension of the default Alarm object that also contains name of the alarm originator.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getAlarmInfoById", "parameters": [ { - "name": "alarmRuleId", + "name": "alarmId", "in": "path", + "description": "A string value representing the alarm id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { "type": "string" @@ -8331,7 +7936,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/JsonNode" + "$ref": "#/components/schemas/AlarmInfo" } } } @@ -8452,14 +8057,14 @@ ] } }, - "/api/alarm/rules": { + "/api/alarm/types": { "get": { "tags": [ - "alarm-rule-controller" + "alarm-controller" ], - "summary": "Get alarm rules (getAlarmRules)", - "description": "Fetch tenant alarm rules based on the filter.\n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "getAlarmRules", + "summary": "Get Alarm Types (getAlarmTypes)", + "description": "Returns a set of unique alarm types based on alarms that are either owned by the tenant or assigned to the customer which user is performing the request.", + "operationId": "getAlarmTypes", "parameters": [ { "name": "pageSize", @@ -8481,51 +8086,15 @@ "format": "int32" } }, - { - "name": "entityType", - "in": "query", - "description": "Entity type filter. If not specified, alarm rules for all supported entity types will be returned.", - "required": false, - "schema": { - "$ref": "#/components/schemas/EntityType" - } - }, - { - "name": "entities", - "in": "query", - "description": "Entities filter. If not specified, alarm rules for entity type filter will be returned.", - "required": false, - "schema": { - "type": "array", - "items": { - "type": "string", - "format": "uuid" - }, - "uniqueItems": true - } - }, { "name": "textSearch", "in": "query", - "description": "The case insensitive 'substring' filter based on the calculated field name.", + "description": "The case insensitive 'substring' filter based on of next alarm fields: type, severity or status", "required": false, "schema": { "type": "string" } }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, - "schema": { - "type": "string", - "enum": [ - "createdTime", - "name" - ] - } - }, { "name": "sortOrder", "in": "query", @@ -8546,7 +8115,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataAlarmRuleDefinitionInfo" + "$ref": "#/components/schemas/PageDataEntitySubtype" } } } @@ -8667,56 +8236,23 @@ ] } }, - "/api/alarm/rules/names": { + "/api/alarm/{alarmId}": { "get": { "tags": [ - "alarm-rule-controller" + "alarm-controller" ], - "summary": "Get alarm rule names (getAlarmRuleNames)", - "description": "Fetch the list of alarm rule names.\n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "getAlarmRuleNames", + "summary": "Get Alarm (getAlarmById)", + "description": "Fetch the Alarm object based on the provided Alarm Id. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getAlarmById", "parameters": [ { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", + "name": "alarmId", + "in": "path", + "description": "A string value representing the alarm id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'substring' filter based on the calculated field name.", - "required": false, "schema": { "type": "string" } - }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] - } } ], "responses": { @@ -8725,7 +8261,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataString" + "$ref": "#/components/schemas/Alarm" } } } @@ -8844,89 +8380,23 @@ "ApiKeyForm": [] } ] - } - }, - "/api/alarm/rules/{entityType}/{entityId}": { - "get": { + }, + "delete": { "tags": [ - "alarm-rule-controller" + "alarm-controller" ], - "summary": "Get Alarm Rules by Entity Id (getAlarmRulesByEntityId)", - "description": "Fetch the Alarm Rules based on the provided Entity Id.\n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "getAlarmRulesByEntityId", + "summary": "Delete Alarm (deleteAlarm)", + "description": "Deletes the Alarm. Referencing non-existing Alarm Id will cause an error.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'DELETE' permission for the entity (entities).", + "operationId": "deleteAlarm", "parameters": [ { - "name": "entityType", - "in": "path", - "description": "A string value representing the entity type. For example, 'DEVICE'", - "required": true, - "schema": { - "type": "string" - } - }, - { - "name": "entityId", + "name": "alarmId", "in": "path", - "description": "A string value representing the entity id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": true, - "schema": { - "type": "string" - } - }, - { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", + "description": "A string value representing the alarm id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'substring' filter based on the calculated field name.", - "required": false, "schema": { "type": "string" } - }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, - "schema": { - "type": "string", - "enum": [ - "createdTime", - "name" - ] - } - }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] - } } ], "responses": { @@ -8935,7 +8405,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataAlarmRuleDefinition" + "type": "boolean" } } } @@ -9056,31 +8526,32 @@ ] } }, - "/api/apiKey": { + "/api/alarm/{alarmId}/ack": { "post": { "tags": [ - "api-key-controller" + "alarm-controller" ], - "summary": "Save API key for user (saveApiKey)", - "description": "Creates an API key for the given user and returns the token ONCE as 'ApiKey {value}'.\n\nAvailable for any authorized user. ", - "operationId": "saveApiKey", - "requestBody": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ApiKeyInfo" - } + "summary": "Acknowledge Alarm (ackAlarm)", + "description": "Acknowledge the Alarm. Once acknowledged, the 'ack_ts' field will be set to current timestamp and special rule chain event 'ALARM_ACK' will be generated. Referencing non-existing Alarm Id will cause an error.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'WRITE' permission for the entity (entities).", + "operationId": "ackAlarm", + "parameters": [ + { + "name": "alarmId", + "in": "path", + "description": "A string value representing the alarm id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, + "schema": { + "type": "string" } - }, - "required": true - }, + } + ], "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/ApiKey" + "$ref": "#/components/schemas/AlarmInfo" } } } @@ -9201,28 +8672,35 @@ ] } }, - "/api/apiKey/{id}": { + "/api/alarm/{alarmId}/assign": { "delete": { "tags": [ - "api-key-controller" + "alarm-controller" ], - "summary": "Delete API key by ID (deleteApiKey)", - "description": "Deletes the API key. Referencing non-existing ApiKey Id will cause an error.\n\nAvailable for any authorized user. ", - "operationId": "deleteApiKey", + "summary": "Unassign Alarm (unassignAlarm)", + "description": "Unassign the Alarm. Once unassigned, the 'assign_ts' field will be set to current timestamp and special rule chain event 'ALARM_UNASSIGNED' will be generated. Referencing non-existing Alarm Id will cause an error.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", + "operationId": "unassignAlarm", "parameters": [ { - "name": "id", + "name": "alarmId", "in": "path", + "description": "A string value representing the alarm id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { - "type": "string", - "format": "uuid" + "type": "string" } } ], "responses": { "200": { - "description": "OK" + "description": "OK", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/Alarm" + } + } + } }, "400": { "description": "Bad Request", @@ -9340,43 +8818,41 @@ ] } }, - "/api/apiKey/{id}/description": { - "put": { + "/api/alarm/{alarmId}/assign/{assigneeId}": { + "post": { "tags": [ - "api-key-controller" + "alarm-controller" ], - "summary": "Update API key Description", - "description": "Updates the description of the existing API key by apiKeyId. Only the description can be updated. Referencing a non-existing ApiKey Id will cause a 'Not Found' error.\n\nAvailable for any authorized user. ", - "operationId": "updateApiKeyDescription", + "summary": "Assign/Reassign Alarm (assignAlarm)", + "description": "Assign the Alarm. Once assigned, the 'assign_ts' field will be set to current timestamp and special rule chain event 'ALARM_ASSIGNED' (or ALARM_REASSIGNED in case of assigning already assigned alarm) will be generated. Referencing non-existing Alarm Id will cause an error.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", + "operationId": "assignAlarm", "parameters": [ { - "name": "id", + "name": "alarmId", "in": "path", - "description": "A string value representing the api key id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "description": "A string value representing the alarm id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { - "type": "string", - "format": "uuid" + "type": "string" } - } - ], - "requestBody": { - "content": { - "application/json": { - "schema": { - "type": "string", - "description": "New description for the API key" - } + }, + { + "name": "assigneeId", + "in": "path", + "description": "A string value representing the user id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, + "schema": { + "type": "string" } } - }, + ], "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/ApiKeyInfo" + "$ref": "#/components/schemas/Alarm" } } } @@ -9393,7 +8869,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -9497,32 +8973,22 @@ ] } }, - "/api/apiKey/{id}/enabled/{enabledValue}": { - "put": { + "/api/alarm/{alarmId}/clear": { + "post": { "tags": [ - "api-key-controller" + "alarm-controller" ], - "summary": "Enable or disable API key (enableApiKey)", - "description": "Updates api key with enabled = true/false. \n\nAvailable for any authorized user. ", - "operationId": "enableApiKey", + "summary": "Clear Alarm (clearAlarm)", + "description": "Clear the Alarm. Once cleared, the 'clear_ts' field will be set to current timestamp and special rule chain event 'ALARM_CLEAR' will be generated. Referencing non-existing Alarm Id will cause an error.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'WRITE' permission for the entity (entities).", + "operationId": "clearAlarm", "parameters": [ { - "name": "id", - "in": "path", - "description": "Unique identifier of the API key to enable/disable", - "required": true, - "schema": { - "type": "string", - "format": "uuid" - } - }, - { - "name": "enabledValue", + "name": "alarmId", "in": "path", - "description": "Enabled or disabled api key", + "description": "A string value representing the alarm id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { - "type": "boolean" + "type": "string" } } ], @@ -9532,7 +8998,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/ApiKeyInfo" + "$ref": "#/components/schemas/AlarmInfo" } } } @@ -9549,7 +9015,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -9653,24 +9119,73 @@ ] } }, - "/api/apiKeys/{userId}": { + "/api/alarm/{entityType}/{entityId}": { "get": { "tags": [ - "api-key-controller" + "alarm-controller" ], - "summary": "Get User Api Keys (getUserApiKeys)", - "description": "Returns a page of api keys owned by user. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for any authorized user. ", - "operationId": "getUserApiKeys", + "summary": "Get Alarms (getAlarmsByEntity)", + "description": "Returns a page of alarms for the selected entity. Specifying both parameters 'searchStatus' and 'status' at the same time will cause an error. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getAlarmsByEntity", "parameters": [ { - "name": "userId", + "name": "entityType", "in": "path", - "description": "A string value representing the user id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "description": "A string value representing the entity type. For example, 'DEVICE'", + "required": true, + "schema": { + "type": "string" + } + }, + { + "name": "entityId", + "in": "path", + "description": "A string value representing the entity id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { "type": "string" } }, + { + "name": "searchStatus", + "in": "query", + "description": "A string value representing one of the AlarmSearchStatus enumeration value", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ANY", + "ACTIVE", + "CLEARED", + "ACK", + "UNACK" + ] + } + }, + { + "name": "status", + "in": "query", + "description": "A string value representing one of the AlarmStatus enumeration value", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ACTIVE_UNACK", + "ACTIVE_ACK", + "CLEARED_UNACK", + "CLEARED_ACK" + ] + } + }, + { + "name": "assigneeId", + "in": "query", + "description": "A string value representing the assignee user id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": false, + "schema": { + "type": "string" + } + }, { "name": "pageSize", "in": "query", @@ -9694,7 +9209,7 @@ { "name": "textSearch", "in": "query", - "description": "The case insensitive 'substring' filter based on the description.", + "description": "The case insensitive 'substring' filter based on of next alarm fields: type, severity or status", "required": false, "schema": { "type": "string" @@ -9709,9 +9224,13 @@ "type": "string", "enum": [ "createdTime", - "expirationTime", - "description", - "enabled" + "startTs", + "endTs", + "type", + "ackTs", + "clearTs", + "severity", + "status" ] } }, @@ -9727,6 +9246,35 @@ "DESC" ] } + }, + { + "name": "startTime", + "in": "query", + "description": "The start timestamp in milliseconds of the search time range over the Alarm class field: 'createdTime'.", + "required": false, + "schema": { + "type": "integer", + "format": "int64" + } + }, + { + "name": "endTime", + "in": "query", + "description": "The end timestamp in milliseconds of the search time range over the Alarm class field: 'createdTime'.", + "required": false, + "schema": { + "type": "integer", + "format": "int64" + } + }, + { + "name": "fetchOriginator", + "in": "query", + "description": "A boolean value to specify if the alarm originator name will be filled in the AlarmInfo object field: 'originatorName' or will returns as null.", + "required": false, + "schema": { + "type": "boolean" + } } ], "responses": { @@ -9735,7 +9283,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataApiKeyInfo" + "$ref": "#/components/schemas/PageDataAlarmInfo" } } } @@ -9856,85 +9404,153 @@ ] } }, - "/api/asset": { - "post": { + "/api/alarms": { + "get": { "tags": [ - "asset-controller" + "alarm-controller" ], - "summary": "Create Or Update Asset (saveAsset)", - "description": "Creates or Updates the Asset. When creating asset, platform generates Asset Id as [time-based UUID](https://en.wikipedia.org/wiki/Universally_unique_identifier#Version_1_(date-time_and_MAC_address)). The newly created Asset id will be present in the response. Specify existing Asset id to update the asset. Referencing non-existing Asset Id will cause 'Not Found' error. Remove 'id', 'tenantId' and optionally 'customerId' from the request body example (below) to create new Asset entity. \n\n Security check is performed to verify that the user has 'WRITE' permission for the entity (entities).", - "operationId": "saveAsset", + "summary": "Get All Alarms (getAllAlarms)", + "description": "Returns a page of alarms that belongs to the current user owner. If the user has the authority of 'Tenant Administrator', the server returns alarms that belongs to the tenant of current user. If the user has the authority of 'Customer User', the server returns alarms that belongs to the customer of current user. Specifying both parameters 'searchStatus' and 'status' at the same time will cause an error. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getAllAlarms", "parameters": [ { - "name": "entityGroupId", + "name": "searchStatus", "in": "query", - "description": "A string value representing the Entity Group Id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'. If specified, the entity will be added to the corresponding entity group.", + "description": "A string value representing one of the AlarmSearchStatus enumeration value", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ANY", + "ACTIVE", + "CLEARED", + "ACK", + "UNACK" + ] + } + }, + { + "name": "status", + "in": "query", + "description": "A string value representing one of the AlarmStatus enumeration value", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ACTIVE_UNACK", + "ACTIVE_ACK", + "CLEARED_UNACK", + "CLEARED_ACK" + ] + } + }, + { + "name": "assigneeId", + "in": "query", + "description": "A string value representing the assignee user id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": false, "schema": { "type": "string" } }, { - "name": "entityGroupIds", + "name": "pageSize", "in": "query", - "description": "A list of string values, separated by comma ',' representing the Entity Group Ids. For example, '784f394c-42b6-435a-983c-b7beff2784f9','a84f394c-42b6-435a-083c-b7beff2784f9'. If specified, the entity will be added to the corresponding entity groups.", + "description": "Maximum amount of entities in a one page", + "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", + "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'substring' filter based on of next alarm fields: type, severity or status", "required": false, "schema": { - "type": "array", - "items": { - "type": "string" - } + "type": "string" } }, { - "name": "nameConflictPolicy", + "name": "sortProperty", "in": "query", - "description": "Optional value of name conflict policy. Possible values: FAIL or UNIQUIFY. If omitted, FAIL policy is applied. FAIL policy implies exception will be thrown if an entity with the same name already exists. UNIQUIFY policy appends a suffix to the entity name, if a name conflict occurs.", + "description": "Property of entity to sort by", "required": false, "schema": { - "$ref": "#/components/schemas/NameConflictPolicy", - "default": "FAIL" + "type": "string", + "enum": [ + "createdTime", + "startTs", + "endTs", + "type", + "ackTs", + "clearTs", + "severity", + "status" + ] } }, { - "name": "uniquifySeparator", + "name": "sortOrder", "in": "query", - "description": "Optional value of name suffix separator used by UNIQUIFY policy. By default, underscore separator is used. For example, strategy is UNIQUIFY, separator is '-'; if a name conflict occurs for entity name 'test-name', created entity will have name like 'test-name-7fsh4f'.", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", "required": false, "schema": { "type": "string", - "default": "_" + "enum": [ + "ASC", + "DESC" + ] } }, { - "name": "uniquifyStrategy", + "name": "startTime", "in": "query", - "description": "Optional value of uniquify strategy used by UNIQUIFY policy. Possible values: RANDOM or INCREMENTAL. By default, RANDOM strategy is used, which means random alphanumeric string will be added as a suffix to entity name. INCREMENTAL implies the first possible number starting from 1 will be added as a name suffix. For example, strategy is UNIQUIFY, uniquify strategy is INCREMENTAL; if a name conflict occurs for entity name 'test-name', created entity will have name like 'test-name-1.", + "description": "The start timestamp in milliseconds of the search time range over the Alarm class field: 'createdTime'.", "required": false, "schema": { - "$ref": "#/components/schemas/UniquifyStrategy", - "default": "RANDOM" + "type": "integer", + "format": "int64" } - } - ], - "requestBody": { - "description": "A JSON value representing the asset.", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/Asset" - } + }, + { + "name": "endTime", + "in": "query", + "description": "The end timestamp in milliseconds of the search time range over the Alarm class field: 'createdTime'.", + "required": false, + "schema": { + "type": "integer", + "format": "int64" } }, - "required": true - }, + { + "name": "fetchOriginator", + "in": "query", + "description": "A boolean value to specify if the alarm originator name will be filled in the AlarmInfo object field: 'originatorName' or will returns as null.", + "required": false, + "schema": { + "type": "boolean" + } + } + ], "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/Asset" + "$ref": "#/components/schemas/PageDataAlarmInfo" } } } @@ -9951,7 +9567,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -10055,31 +9671,181 @@ ] } }, - "/api/asset/bulk_import": { - "post": { + "/api/v2/alarm/{entityType}/{entityId}": { + "get": { "tags": [ - "asset-controller" + "alarm-controller" ], - "summary": "Import the bulk of assets (processAssetsBulkImport)", - "description": "There's an ability to import the bulk of assets using the only .csv file.\n\n Security check is performed to verify that the user has 'WRITE' permission for the entity (entities).", - "operationId": "processAssetBulkImport", - "requestBody": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/BulkImportRequest" + "summary": "Get Alarms (getAlarmsV2)", + "description": "Returns a page of alarms for the selected entity. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", + "operationId": "getAlarmsV2", + "parameters": [ + { + "name": "entityType", + "in": "path", + "description": "A string value representing the entity type. For example, 'DEVICE'", + "required": true, + "schema": { + "type": "string" + } + }, + { + "name": "entityId", + "in": "path", + "description": "A string value representing the entity id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, + "schema": { + "type": "string" + } + }, + { + "name": "statusList", + "in": "query", + "description": "A list of string values separated by comma ',' representing one of the AlarmSearchStatus enumeration value", + "required": false, + "schema": { + "type": "array", + "items": { + "type": "string", + "enum": [ + "ANY", + "ACTIVE", + "CLEARED", + "ACK", + "UNACK" + ] } } }, - "required": true - }, + { + "name": "severityList", + "in": "query", + "description": "A list of string values separated by comma ',' representing one of the AlarmSeverity enumeration value", + "required": false, + "schema": { + "type": "array", + "items": { + "type": "string", + "enum": [ + "CRITICAL", + "MAJOR", + "MINOR", + "WARNING", + "INDETERMINATE" + ] + } + } + }, + { + "name": "typeList", + "in": "query", + "description": "A list of string values separated by comma ',' representing alarm types", + "required": false, + "schema": { + "type": "array", + "items": { + "type": "string" + } + } + }, + { + "name": "assigneeId", + "in": "query", + "description": "A string value representing the assignee user id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", + "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", + "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'substring' filter based on of next alarm fields: type, severity or status", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string", + "enum": [ + "createdTime", + "startTs", + "endTs", + "type", + "ackTs", + "clearTs", + "severity", + "status" + ] + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] + } + }, + { + "name": "startTime", + "in": "query", + "description": "The start timestamp in milliseconds of the search time range over the Alarm class field: 'createdTime'.", + "required": false, + "schema": { + "type": "integer", + "format": "int64" + } + }, + { + "name": "endTime", + "in": "query", + "description": "The end timestamp in milliseconds of the search time range over the Alarm class field: 'createdTime'.", + "required": false, + "schema": { + "type": "integer", + "format": "int64" + } + } + ], "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/BulkImportResultAsset" + "$ref": "#/components/schemas/PageDataAlarmInfo" } } } @@ -10096,7 +9862,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -10200,23 +9966,154 @@ ] } }, - "/api/asset/info/{assetId}": { + "/api/v2/alarms": { "get": { "tags": [ - "asset-controller" + "alarm-controller" ], - "summary": "Get Asset Info (getAssetInfoById)", - "description": "Fetch the Asset Info object based on the provided Asset Id. If the user has the authority of 'Tenant Administrator', the server checks that the asset is owned by the same tenant. If the user has the authority of 'Customer User', the server checks that the asset is assigned to the same customer.Asset Info is an extension of the default Asset object that contains information about the owner name. \n\n Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getAssetInfoById", + "summary": "Get All Alarms (getAllAlarmsV2)", + "description": "Returns a page of alarms that belongs to the current user owner. If the user has the authority of 'Tenant Administrator', the server returns alarms that belongs to the tenant of current user. If the user has the authority of 'Customer User', the server returns alarms that belongs to the customer of current user. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", + "operationId": "getAllAlarmsV2", "parameters": [ { - "name": "assetId", - "in": "path", - "description": "A string value representing the asset id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "name": "statusList", + "in": "query", + "description": "A list of string values separated by comma ',' representing one of the AlarmSearchStatus enumeration value", + "required": false, + "schema": { + "type": "array", + "items": { + "type": "string", + "enum": [ + "ANY", + "ACTIVE", + "CLEARED", + "ACK", + "UNACK" + ] + } + } + }, + { + "name": "severityList", + "in": "query", + "description": "A list of string values separated by comma ',' representing one of the AlarmSeverity enumeration value", + "required": false, + "schema": { + "type": "array", + "items": { + "type": "string", + "enum": [ + "CRITICAL", + "MAJOR", + "MINOR", + "WARNING", + "INDETERMINATE" + ] + } + } + }, + { + "name": "typeList", + "in": "query", + "description": "A list of string values separated by comma ',' representing alarm types", + "required": false, + "schema": { + "type": "array", + "items": { + "type": "string" + } + } + }, + { + "name": "assigneeId", + "in": "query", + "description": "A string value representing the assignee user id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", + "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'substring' filter based on of next alarm fields: type, severity or status", + "required": false, "schema": { "type": "string" } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string", + "enum": [ + "createdTime", + "startTs", + "endTs", + "type", + "ackTs", + "clearTs", + "severity", + "status" + ] + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] + } + }, + { + "name": "startTime", + "in": "query", + "description": "The start timestamp in milliseconds of the search time range over the Alarm class field: 'createdTime'.", + "required": false, + "schema": { + "type": "integer", + "format": "int64" + } + }, + { + "name": "endTime", + "in": "query", + "description": "The end timestamp in milliseconds of the search time range over the Alarm class field: 'createdTime'.", + "required": false, + "schema": { + "type": "integer", + "format": "int64" + } } ], "responses": { @@ -10225,7 +10122,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/AssetInfo" + "$ref": "#/components/schemas/PageDataAlarmInfo" } } } @@ -10346,24 +10243,32 @@ ] } }, - "/api/asset/types": { - "get": { + "/api/alarm/rule": { + "post": { "tags": [ - "asset-controller" + "alarm-rule-controller" ], - "summary": "Get Asset Types (getAssetTypes)", - "description": "Deprecated. See 'getAssetProfileNames' API from Asset Profile Controller instead.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", - "operationId": "getAssetTypes", + "summary": "Create Or Update Alarm Rule (saveAlarmRule)", + "description": "Creates or Updates the Alarm Rule. When creating alarm rule, platform generates Alarm Rule Id as [time-based UUID](https://en.wikipedia.org/wiki/Universally_unique_identifier#Version_1_(date-time_and_MAC_address)). The newly created Alarm Rule Id will be present in the response. Specify existing Alarm Rule Id to update the alarm rule. Referencing non-existing Alarm Rule Id will cause 'Not Found' error. Remove 'id', 'tenantId' from the request body example (below) to create new Alarm Rule entity. \n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "saveAlarmRule", + "requestBody": { + "description": "A JSON value representing the alarm rule.", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/AlarmRuleDefinition" + } + } + }, + "required": true + }, "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "type": "array", - "items": { - "$ref": "#/components/schemas/EntitySubtype" - } + "$ref": "#/components/schemas/AlarmRuleDefinition" } } } @@ -10380,7 +10285,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -10474,7 +10379,6 @@ } } }, - "deprecated": true, "security": [ { "HttpLoginForm": [] @@ -10485,32 +10389,32 @@ ] } }, - "/api/asset/{assetId}": { - "get": { + "/api/alarm/rule/testScript": { + "post": { "tags": [ - "asset-controller" + "alarm-rule-controller" ], - "summary": "Get Asset (getAssetById)", - "description": "Fetch the Asset object based on the provided Asset Id. If the user has the authority of 'Tenant Administrator', the server checks that the asset is owned by the same tenant. If the user has the authority of 'Customer User', the server checks that the asset is assigned to the same customer.\n\n Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getAssetById", - "parameters": [ - { - "name": "assetId", - "in": "path", - "description": "A string value representing the asset id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": true, - "schema": { - "type": "string" + "summary": "Test alarm rule TBEL expression (testAlarmRuleScript)", + "description": "Execute the alarm rule TBEL condition expression and return the result. Alarm rule expressions must return a boolean value. The format of request: \n\n```json\n{\n \"expression\": \"return temperature > 50;\",\n \"arguments\": {\n \"temperature\": { \"type\": \"SINGLE_VALUE\", \"ts\": 1739776478057, \"value\": 55 }\n }\n}\n```\n\n Expected result JSON contains \"output\" and \"error\".\n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "testAlarmRuleScript", + "requestBody": { + "description": "Test alarm rule TBEL condition expression. The expression must return a boolean value.", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/JsonNode" + } } - } - ], + }, + "required": true + }, "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/Asset" + "$ref": "#/components/schemas/JsonNode" } } } @@ -10527,7 +10431,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -10629,19 +10533,20 @@ "ApiKeyForm": [] } ] - }, - "delete": { + } + }, + "/api/alarm/rule/{alarmRuleId}": { + "get": { "tags": [ - "asset-controller" + "alarm-rule-controller" ], - "summary": "Delete asset (deleteAsset)", - "description": "Deletes the asset and all the relations (from and to the asset). Referencing non-existing asset Id will cause an error.\n\n Security check is performed to verify that the user has 'DELETE' permission for the entity (entities).", - "operationId": "deleteAsset", + "summary": "Get Alarm Rule (getAlarmRuleById)", + "description": "Fetch the Alarm Rule object based on the provided Alarm Rule Id.\n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "getAlarmRuleById", "parameters": [ { - "name": "assetId", + "name": "alarmRuleId", "in": "path", - "description": "A string value representing the asset id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { "type": "string" @@ -10650,7 +10555,14 @@ ], "responses": { "200": { - "description": "OK" + "description": "OK", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/AlarmRuleDefinition" + } + } + } }, "400": { "description": "Bad Request", @@ -10766,104 +10678,27 @@ "ApiKeyForm": [] } ] - } - }, - "/api/assetInfos/all": { - "get": { + }, + "delete": { "tags": [ - "asset-controller" + "alarm-rule-controller" ], - "summary": "Get All Asset Infos for current user (getAllAssetInfos)", - "description": "Returns a page of asset info objects owned by the tenant or the customer of a current user. Asset Info is an extension of the default Asset object that contains information about the owner name. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getAllAssetInfos", + "summary": "Delete Alarm Rule (deleteAlarmRule)", + "description": "Deletes the alarm rule. Referencing non-existing Alarm Rule Id will cause an error.\n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "deleteAlarmRule", "parameters": [ { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", + "name": "alarmRuleId", + "in": "path", "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "includeCustomers", - "in": "query", - "description": "Include customer or sub-customer entities", - "required": false, - "schema": { - "type": "boolean" - } - }, - { - "name": "assetProfileId", - "in": "query", - "description": "A string value representing the asset profile id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'substring' filter based on the asset name.", - "required": false, "schema": { "type": "string" } - }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, - "schema": { - "type": "string", - "enum": [ - "createdTime", - "name", - "type", - "label", - "customerTitle" - ] - } - }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] - } } ], "responses": { "200": { - "description": "OK", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/PageDataAssetInfo" - } - } - } + "description": "OK" }, "400": { "description": "Bad Request", @@ -10981,25 +10816,21 @@ ] } }, - "/api/assets": { + "/api/alarm/rule/{alarmRuleId}/debug": { "get": { "tags": [ - "asset-controller" + "alarm-rule-controller" ], - "summary": "Get Assets By Ids (getAssetsByIds)", - "description": "Requested assets must be owned by tenant or assigned to customer which user is performing the request. \n\n Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getAssetsByIds", + "summary": "Get latest alarm rule debug event (getLatestAlarmRuleDebugEvent)", + "description": "Gets latest alarm rule debug event for specified alarm rule id. Referencing non-existing alarm rule id will cause an error. \n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "getLatestAlarmRuleDebugEvent", "parameters": [ { - "name": "assetIds", - "in": "query", - "description": "A list of asset ids, separated by comma ','", + "name": "alarmRuleId", + "in": "path", "required": true, "schema": { - "type": "array", - "items": { - "type": "string" - } + "type": "string" } } ], @@ -11009,10 +10840,7 @@ "content": { "application/json": { "schema": { - "type": "array", - "items": { - "$ref": "#/components/schemas/Asset" - } + "$ref": "#/components/schemas/JsonNode" } } } @@ -11131,34 +10959,103 @@ "ApiKeyForm": [] } ] - }, - "post": { + } + }, + "/api/alarm/rules": { + "get": { "tags": [ - "asset-controller" + "alarm-rule-controller" ], - "summary": "Find related assets (findAssetsByQuery)", - "description": "Returns all assets that are related to the specific entity. The entity id, relation type, asset types, depth of the search, and other query parameters defined using complex 'AssetSearchQuery' object. See 'Model' tab of the Parameters for more info. \n\n Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "findAssetsByQuery", - "requestBody": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/AssetSearchQuery" - } + "summary": "Get alarm rules (getAlarmRules)", + "description": "Fetch tenant alarm rules based on the filter.\n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "getAlarmRules", + "parameters": [ + { + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", + "required": true, + "schema": { + "type": "integer", + "format": "int32" } }, - "required": true - }, + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", + "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "entityType", + "in": "query", + "description": "Entity type filter. If not specified, alarm rules for all supported entity types will be returned.", + "required": false, + "schema": { + "$ref": "#/components/schemas/EntityType" + } + }, + { + "name": "entities", + "in": "query", + "description": "Entities filter. If not specified, alarm rules for entity type filter will be returned.", + "required": false, + "schema": { + "type": "array", + "items": { + "type": "string", + "format": "uuid" + }, + "uniqueItems": true + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'substring' filter based on the calculated field name.", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string", + "enum": [ + "createdTime", + "name" + ] + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] + } + } + ], "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "type": "array", - "items": { - "$ref": "#/components/schemas/Asset" - } + "$ref": "#/components/schemas/PageDataAlarmRuleDefinitionInfo" } } } @@ -11175,7 +11072,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -11279,24 +11176,15 @@ ] } }, - "/api/customer/{customerId}/assetInfos": { + "/api/alarm/rules/names": { "get": { "tags": [ - "asset-controller" + "alarm-rule-controller" ], - "summary": "Get Customer Asset Infos (getCustomerAssetInfos)", - "description": "Returns a page of asset info objects owned by the specified customer. Asset Info is an extension of the default Asset object that contains information about the owner name. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getCustomerAssetInfos", + "summary": "Get alarm rule names (getAlarmRuleNames)", + "description": "Fetch the list of alarm rule names.\n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "getAlarmRuleNames", "parameters": [ - { - "name": "customerId", - "in": "path", - "description": "A string value representing the customer id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": true, - "schema": { - "type": "string" - } - }, { "name": "pageSize", "in": "query", @@ -11317,49 +11205,15 @@ "format": "int32" } }, - { - "name": "includeCustomers", - "in": "query", - "description": "Include customer or sub-customer entities", - "required": false, - "schema": { - "type": "boolean" - } - }, - { - "name": "assetProfileId", - "in": "query", - "description": "A string value representing the asset profile id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": false, - "schema": { - "type": "string" - } - }, { "name": "textSearch", "in": "query", - "description": "The case insensitive 'substring' filter based on the asset name.", + "description": "The case insensitive 'substring' filter based on the calculated field name.", "required": false, "schema": { "type": "string" } }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, - "schema": { - "type": "string", - "enum": [ - "createdTime", - "name", - "type", - "label", - "customerTitle" - ] - } - }, { "name": "sortOrder", "in": "query", @@ -11380,7 +11234,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataAssetInfo" + "$ref": "#/components/schemas/PageDataString" } } } @@ -11501,19 +11355,28 @@ ] } }, - "/api/customer/{customerId}/assets": { + "/api/alarm/rules/{entityType}/{entityId}": { "get": { "tags": [ - "asset-controller" + "alarm-rule-controller" ], - "summary": "Get Customer Assets (getCustomerAssets)", - "description": "Returns a page of assets objects owned by customer. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\n Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getCustomerAssets", + "summary": "Get Alarm Rules by Entity Id (getAlarmRulesByEntityId)", + "description": "Fetch the Alarm Rules based on the provided Entity Id.\n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "getAlarmRulesByEntityId", "parameters": [ { - "name": "customerId", + "name": "entityType", "in": "path", - "description": "A string value representing the customer id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "description": "A string value representing the entity type. For example, 'DEVICE'", + "required": true, + "schema": { + "type": "string" + } + }, + { + "name": "entityId", + "in": "path", + "description": "A string value representing the entity id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { "type": "string" @@ -11539,19 +11402,10 @@ "format": "int32" } }, - { - "name": "type", - "in": "query", - "description": "Asset type", - "required": false, - "schema": { - "type": "string" - } - }, { "name": "textSearch", "in": "query", - "description": "The case insensitive 'substring' filter based on the asset name.", + "description": "The case insensitive 'substring' filter based on the calculated field name.", "required": false, "schema": { "type": "string" @@ -11566,10 +11420,7 @@ "type": "string", "enum": [ "createdTime", - "name", - "type", - "label", - "customerTitle" + "name" ] } }, @@ -11593,7 +11444,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataAsset" + "$ref": "#/components/schemas/PageDataAlarmRuleDefinition" } } } @@ -11714,90 +11565,31 @@ ] } }, - "/api/entityGroup/{entityGroupId}/assets": { - "get": { + "/api/apiKey": { + "post": { "tags": [ - "asset-controller" + "api-key-controller" ], - "summary": "Get assets by Entity Group Id (getAssetsByEntityGroupId)", - "description": "Returns a page of asset objects that belongs to specified Entity Group Id. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\n Security check is performed to verify that the user has 'READ' permission for specified group.", - "operationId": "getAssetsByEntityGroupId", - "parameters": [ - { - "name": "entityGroupId", - "in": "path", - "description": "A string value representing the Entity Group Id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": true, - "schema": { - "type": "string" - } - }, - { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "string", - "minimum": 1 - } - }, - { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", - "required": true, - "schema": { - "type": "string", - "minimum": 0 - } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'substring' filter based on the asset name.", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, - "schema": { - "type": "string", - "enum": [ - "createdTime", - "name", - "type", - "label", - "customerTitle" - ] + "summary": "Save API key for user (saveApiKey)", + "description": "Creates an API key for the given user and returns the token ONCE as 'ApiKey {value}'.\n\nAvailable for any authorized user. ", + "operationId": "saveApiKey", + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ApiKeyInfo" + } } }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] - } - } - ], + "required": true + }, "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataAsset" + "$ref": "#/components/schemas/ApiKey" } } } @@ -11814,7 +11606,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -11918,35 +11710,28 @@ ] } }, - "/api/tenant/asset": { - "get": { + "/api/apiKey/{id}": { + "delete": { "tags": [ - "asset-controller" + "api-key-controller" ], - "summary": "Get Tenant Asset (getTenantAssetByName)", - "description": "Requested asset must be owned by tenant that the user belongs to. Asset name is an unique property of asset. So it can be used to identify the asset.\n\n Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getTenantAssetByName", + "summary": "Delete API key by ID (deleteApiKey)", + "description": "Deletes the API key. Referencing non-existing ApiKey Id will cause an error.\n\nAvailable for any authorized user. ", + "operationId": "deleteApiKey", "parameters": [ { - "name": "assetName", - "in": "query", - "description": "A string value representing the Asset name.", + "name": "id", + "in": "path", "required": true, "schema": { - "type": "string" + "type": "string", + "format": "uuid" } } ], "responses": { "200": { - "description": "OK", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/Asset" - } - } - } + "description": "OK" }, "400": { "description": "Bad Request", @@ -12064,90 +11849,43 @@ ] } }, - "/api/tenant/assets": { - "get": { + "/api/apiKey/{id}/description": { + "put": { "tags": [ - "asset-controller" + "api-key-controller" ], - "summary": "Get Tenant Assets (getTenantAssets)", - "description": "Returns a page of assets owned by tenant. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\n Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getTenantAssets", + "summary": "Update API key Description", + "description": "Updates the description of the existing API key by apiKeyId. Only the description can be updated. Referencing a non-existing ApiKey Id will cause a 'Not Found' error.\n\nAvailable for any authorized user. ", + "operationId": "updateApiKeyDescription", "parameters": [ { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", + "name": "id", + "in": "path", + "description": "A string value representing the api key id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "type", - "in": "query", - "description": "Asset type", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'substring' filter based on the asset name.", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, - "schema": { - "type": "string", - "enum": [ - "createdTime", - "name", - "type", - "label", - "customerTitle" - ] - } - }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, "schema": { "type": "string", - "enum": [ - "ASC", - "DESC" - ] + "format": "uuid" } } ], + "requestBody": { + "content": { + "application/json": { + "schema": { + "type": "string", + "description": "New description for the API key" + } + } + } + }, "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataAsset" + "$ref": "#/components/schemas/ApiKeyInfo" } } } @@ -12268,89 +12006,32 @@ ] } }, - "/api/user/assets": { - "get": { + "/api/apiKey/{id}/enabled/{enabledValue}": { + "put": { "tags": [ - "asset-controller" + "api-key-controller" ], - "summary": "Get Assets (getUserAssets)", - "description": "Returns a page of assets objects available for the current user. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. Asset Info is an extension of the default Asset object that contains information about the owner name. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getUserAssets", + "summary": "Enable or disable API key (enableApiKey)", + "description": "Updates api key with enabled = true/false. \n\nAvailable for any authorized user. ", + "operationId": "enableApiKey", "parameters": [ { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", + "name": "id", + "in": "path", + "description": "Unique identifier of the API key to enable/disable", "required": true, "schema": { "type": "string", - "minimum": 1 + "format": "uuid" } }, { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", + "name": "enabledValue", + "in": "path", + "description": "Enabled or disabled api key", "required": true, "schema": { - "type": "string", - "minimum": 0 - } - }, - { - "name": "type", - "in": "query", - "description": "Asset type", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "assetProfileId", - "in": "query", - "description": "A string value representing the asset profile id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'substring' filter based on the asset name.", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, - "schema": { - "type": "string", - "enum": [ - "createdTime", - "name", - "type", - "label", - "customerTitle" - ] - } - }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] + "type": "boolean" } } ], @@ -12360,7 +12041,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataAsset" + "$ref": "#/components/schemas/ApiKeyInfo" } } } @@ -12481,31 +12162,89 @@ ] } }, - "/api/assetProfile": { - "post": { + "/api/apiKeys/{userId}": { + "get": { "tags": [ - "asset-profile-controller" + "api-key-controller" ], - "summary": "Create Or Update Asset Profile (saveAssetProfile)", - "description": "Create or update the Asset Profile. When creating asset profile, platform generates asset profile id as [time-based UUID](https://en.wikipedia.org/wiki/Universally_unique_identifier#Version_1_(date-time_and_MAC_address)). The newly created asset profile id will be present in the response. Specify existing asset profile id to update the asset profile. Referencing non-existing asset profile Id will cause 'Not Found' error. \n\nAsset profile name is unique in the scope of tenant. Only one 'default' asset profile may exist in scope of tenant. Remove 'id', 'tenantId' from the request body example (below) to create new Asset Profile entity. \n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "saveAssetProfile", - "requestBody": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/AssetProfile" - } + "summary": "Get User Api Keys (getUserApiKeys)", + "description": "Returns a page of api keys owned by user. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for any authorized user. ", + "operationId": "getUserApiKeys", + "parameters": [ + { + "name": "userId", + "in": "path", + "description": "A string value representing the user id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, + "schema": { + "type": "string" } }, - "required": true - }, + { + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", + "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", + "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'substring' filter based on the description.", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string", + "enum": [ + "createdTime", + "expirationTime", + "description", + "enabled" + ] + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] + } + } + ], "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/AssetProfile" + "$ref": "#/components/schemas/PageDataApiKeyInfo" } } } @@ -12522,7 +12261,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -12626,36 +12365,85 @@ ] } }, - "/api/assetProfile/names": { - "get": { + "/api/asset": { + "post": { "tags": [ - "asset-profile-controller" + "asset-controller" ], - "summary": "Get Asset Profile names (getAssetProfileNames)", - "description": "Returns a set of unique asset profile names owned by the tenant.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", - "operationId": "getAssetProfileNames", + "summary": "Create Or Update Asset (saveAsset)", + "description": "Creates or Updates the Asset. When creating asset, platform generates Asset Id as [time-based UUID](https://en.wikipedia.org/wiki/Universally_unique_identifier#Version_1_(date-time_and_MAC_address)). The newly created Asset id will be present in the response. Specify existing Asset id to update the asset. Referencing non-existing Asset Id will cause 'Not Found' error. Remove 'id', 'tenantId' and optionally 'customerId' from the request body example (below) to create new Asset entity. \n\n Security check is performed to verify that the user has 'WRITE' permission for the entity (entities).", + "operationId": "saveAsset", "parameters": [ { - "name": "activeOnly", + "name": "entityGroupId", "in": "query", - "description": "Flag indicating whether to retrieve exclusively the names of asset profiles that are referenced by tenant's assets.", + "description": "A string value representing the Entity Group Id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'. If specified, the entity will be added to the corresponding entity group.", "required": false, "schema": { - "type": "boolean", - "default": false + "type": "string" + } + }, + { + "name": "entityGroupIds", + "in": "query", + "description": "A list of string values, separated by comma ',' representing the Entity Group Ids. For example, '784f394c-42b6-435a-983c-b7beff2784f9','a84f394c-42b6-435a-083c-b7beff2784f9'. If specified, the entity will be added to the corresponding entity groups.", + "required": false, + "schema": { + "type": "array", + "items": { + "type": "string" + } + } + }, + { + "name": "nameConflictPolicy", + "in": "query", + "description": "Optional value of name conflict policy. Possible values: FAIL or UNIQUIFY. If omitted, FAIL policy is applied. FAIL policy implies exception will be thrown if an entity with the same name already exists. UNIQUIFY policy appends a suffix to the entity name, if a name conflict occurs.", + "required": false, + "schema": { + "$ref": "#/components/schemas/NameConflictPolicy", + "default": "FAIL" + } + }, + { + "name": "uniquifySeparator", + "in": "query", + "description": "Optional value of name suffix separator used by UNIQUIFY policy. By default, underscore separator is used. For example, strategy is UNIQUIFY, separator is '-'; if a name conflict occurs for entity name 'test-name', created entity will have name like 'test-name-7fsh4f'.", + "required": false, + "schema": { + "type": "string", + "default": "_" + } + }, + { + "name": "uniquifyStrategy", + "in": "query", + "description": "Optional value of uniquify strategy used by UNIQUIFY policy. Possible values: RANDOM or INCREMENTAL. By default, RANDOM strategy is used, which means random alphanumeric string will be added as a suffix to entity name. INCREMENTAL implies the first possible number starting from 1 will be added as a name suffix. For example, strategy is UNIQUIFY, uniquify strategy is INCREMENTAL; if a name conflict occurs for entity name 'test-name', created entity will have name like 'test-name-1.", + "required": false, + "schema": { + "$ref": "#/components/schemas/UniquifyStrategy", + "default": "RANDOM" } } ], + "requestBody": { + "description": "A JSON value representing the asset.", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/Asset" + } + } + }, + "required": true + }, "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "type": "array", - "items": { - "$ref": "#/components/schemas/EntityInfo" - } + "$ref": "#/components/schemas/Asset" } } } @@ -12672,7 +12460,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -12776,41 +12564,31 @@ ] } }, - "/api/assetProfile/{assetProfileId}": { - "get": { + "/api/asset/bulk_import": { + "post": { "tags": [ - "asset-profile-controller" + "asset-controller" ], - "summary": "Get Asset Profile (getAssetProfileById)", - "description": "Fetch the Asset Profile object based on the provided Asset Profile Id. The server checks that the asset profile is owned by the same tenant. \n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "getAssetProfileById", - "parameters": [ - { - "name": "assetProfileId", - "in": "path", - "description": "A string value representing the asset profile id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": true, - "schema": { - "type": "string" + "summary": "Import the bulk of assets (processAssetsBulkImport)", + "description": "There's an ability to import the bulk of assets using the only .csv file.\n\n Security check is performed to verify that the user has 'WRITE' permission for the entity (entities).", + "operationId": "processAssetBulkImport", + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/BulkImportRequest" + } } }, - { - "name": "inlineImages", - "in": "query", - "description": "Inline images as a data URL (Base64)", - "required": false, - "schema": { - "type": "boolean" - } - } - ], + "required": true + }, "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/AssetProfile" + "$ref": "#/components/schemas/BulkImportResultAsset" } } } @@ -12827,7 +12605,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -12929,19 +12707,21 @@ "ApiKeyForm": [] } ] - }, - "delete": { + } + }, + "/api/asset/info/{assetId}": { + "get": { "tags": [ - "asset-profile-controller" + "asset-controller" ], - "summary": "Delete asset profile (deleteAssetProfile)", - "description": "Deletes the asset profile. Referencing non-existing asset profile Id will cause an error. Can't delete the asset profile if it is referenced by existing assets.\n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "deleteAssetProfile", + "summary": "Get Asset Info (getAssetInfoById)", + "description": "Fetch the Asset Info object based on the provided Asset Id. If the user has the authority of 'Tenant Administrator', the server checks that the asset is owned by the same tenant. If the user has the authority of 'Customer User', the server checks that the asset is assigned to the same customer.Asset Info is an extension of the default Asset object that contains information about the owner name. \n\n Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getAssetInfoById", "parameters": [ { - "name": "assetProfileId", + "name": "assetId", "in": "path", - "description": "A string value representing the asset profile id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "description": "A string value representing the asset id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { "type": "string" @@ -12950,7 +12730,14 @@ ], "responses": { "200": { - "description": "OK" + "description": "OK", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/AssetInfo" + } + } + } }, "400": { "description": "Bad Request", @@ -13068,32 +12855,24 @@ ] } }, - "/api/assetProfile/{assetProfileId}/default": { - "post": { + "/api/asset/types": { + "get": { "tags": [ - "asset-profile-controller" - ], - "summary": "Make Asset Profile Default (setDefaultAssetProfile)", - "description": "Marks asset profile as default within a tenant scope.\n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "setDefaultAssetProfile", - "parameters": [ - { - "name": "assetProfileId", - "in": "path", - "description": "A string value representing the asset profile id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": true, - "schema": { - "type": "string" - } - } + "asset-controller" ], + "summary": "Get Asset Types (getAssetTypes)", + "description": "Deprecated. See 'getAssetProfileNames' API from Asset Profile Controller instead.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", + "operationId": "getAssetTypes", "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/AssetProfile" + "type": "array", + "items": { + "$ref": "#/components/schemas/EntitySubtype" + } } } } @@ -13110,7 +12889,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -13204,6 +12983,7 @@ } } }, + "deprecated": true, "security": [ { "HttpLoginForm": [] @@ -13214,21 +12994,32 @@ ] } }, - "/api/assetProfileInfo/default": { + "/api/asset/{assetId}": { "get": { "tags": [ - "asset-profile-controller" + "asset-controller" + ], + "summary": "Get Asset (getAssetById)", + "description": "Fetch the Asset object based on the provided Asset Id. If the user has the authority of 'Tenant Administrator', the server checks that the asset is owned by the same tenant. If the user has the authority of 'Customer User', the server checks that the asset is assigned to the same customer.\n\n Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getAssetById", + "parameters": [ + { + "name": "assetId", + "in": "path", + "description": "A string value representing the asset id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, + "schema": { + "type": "string" + } + } ], - "summary": "Get Default Asset Profile (getDefaultAssetProfileInfo)", - "description": "Fetch the Default Asset Profile Info object. Asset Profile Info is a lightweight object that includes main information about Asset Profile. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", - "operationId": "getDefaultAssetProfileInfo", "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/AssetProfileInfo" + "$ref": "#/components/schemas/Asset" } } } @@ -13347,21 +13138,19 @@ "ApiKeyForm": [] } ] - } - }, - "/api/assetProfileInfo/{assetProfileId}": { - "get": { + }, + "delete": { "tags": [ - "asset-profile-controller" + "asset-controller" ], - "summary": "Get Asset Profile Info (getAssetProfileInfoById)", - "description": "Fetch the Asset Profile Info object based on the provided Asset Profile Id. Asset Profile Info is a lightweight object that includes main information about Asset Profile. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", - "operationId": "getAssetProfileInfoById", + "summary": "Delete asset (deleteAsset)", + "description": "Deletes the asset and all the relations (from and to the asset). Referencing non-existing asset Id will cause an error.\n\n Security check is performed to verify that the user has 'DELETE' permission for the entity (entities).", + "operationId": "deleteAsset", "parameters": [ { - "name": "assetProfileId", + "name": "assetId", "in": "path", - "description": "A string value representing the asset profile id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "description": "A string value representing the asset id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { "type": "string" @@ -13370,14 +13159,7 @@ ], "responses": { "200": { - "description": "OK", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/AssetProfileInfo" - } - } - } + "description": "OK" }, "400": { "description": "Bad Request", @@ -13495,14 +13277,14 @@ ] } }, - "/api/assetProfileInfos": { + "/api/assetInfos/all": { "get": { "tags": [ - "asset-profile-controller" + "asset-controller" ], - "summary": "Get Asset Profile infos (getAssetProfileInfos)", - "description": "Returns a page of asset profile info objects owned by tenant. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. Asset Profile Info is a lightweight object that includes main information about Asset Profile. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", - "operationId": "getAssetProfileInfos", + "summary": "Get All Asset Infos for current user (getAllAssetInfos)", + "description": "Returns a page of asset info objects owned by the tenant or the customer of a current user. Asset Info is an extension of the default Asset object that contains information about the owner name. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getAllAssetInfos", "parameters": [ { "name": "pageSize", @@ -13524,10 +13306,28 @@ "format": "int32" } }, + { + "name": "includeCustomers", + "in": "query", + "description": "Include customer or sub-customer entities", + "required": false, + "schema": { + "type": "boolean" + } + }, + { + "name": "assetProfileId", + "in": "query", + "description": "A string value representing the asset profile id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": false, + "schema": { + "type": "string" + } + }, { "name": "textSearch", "in": "query", - "description": "The case insensitive 'substring' filter based on the asset profile name.", + "description": "The case insensitive 'substring' filter based on the asset name.", "required": false, "schema": { "type": "string" @@ -13543,8 +13343,9 @@ "enum": [ "createdTime", "name", - "description", - "isDefault" + "type", + "label", + "customerTitle" ] } }, @@ -13568,7 +13369,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataAssetProfileInfo" + "$ref": "#/components/schemas/PageDataAssetInfo" } } } @@ -13689,19 +13490,19 @@ ] } }, - "/api/assetProfileInfos/list": { + "/api/assets": { "get": { "tags": [ - "asset-profile-controller" + "asset-controller" ], - "summary": "Get Asset Profiles By Ids (getAssetProfilesByIds)", - "description": "Requested asset profiles must be owned by tenant which is performing the request. \n\n Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getAssetProfilesByIds", + "summary": "Get Assets By Ids (getAssetsByIds)", + "description": "Requested assets must be owned by tenant or assigned to customer which user is performing the request. \n\n Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getAssetsByIds", "parameters": [ { - "name": "assetProfileIds", + "name": "assetIds", "in": "query", - "description": "A list of asset profile ids, separated by comma ','", + "description": "A list of asset ids, separated by comma ','", "required": true, "schema": { "type": "array", @@ -13719,7 +13520,7 @@ "schema": { "type": "array", "items": { - "$ref": "#/components/schemas/AssetProfileInfo" + "$ref": "#/components/schemas/Asset" } } } @@ -13839,82 +13640,34 @@ "ApiKeyForm": [] } ] - } - }, - "/api/assetProfiles": { - "get": { + }, + "post": { "tags": [ - "asset-profile-controller" + "asset-controller" ], - "summary": "Get Asset Profiles (getAssetProfiles)", - "description": "Returns a page of asset profile objects owned by tenant. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "getAssetProfiles", - "parameters": [ - { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", - "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'substring' filter based on the asset profile name.", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, - "schema": { - "type": "string", - "enum": [ - "createdTime", - "name", - "description", - "isDefault" - ] + "summary": "Find related assets (findAssetsByQuery)", + "description": "Returns all assets that are related to the specific entity. The entity id, relation type, asset types, depth of the search, and other query parameters defined using complex 'AssetSearchQuery' object. See 'Model' tab of the Parameters for more info. \n\n Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "findAssetsByQuery", + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/AssetSearchQuery" + } } }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] - } - } - ], + "required": true + }, "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataAssetProfile" + "type": "array", + "items": { + "$ref": "#/components/schemas/Asset" + } } } } @@ -13931,7 +13684,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -14035,15 +13788,24 @@ ] } }, - "/api/audit/logs": { + "/api/customer/{customerId}/assetInfos": { "get": { "tags": [ - "audit-log-controller" + "asset-controller" ], - "summary": "Get all audit logs (getAuditLogs)", - "description": "Returns a page of audit logs related to all entities in the scope of the current user's Tenant. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'SYS_ADMIN' or 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the audit logs.", - "operationId": "getAuditLogs", + "summary": "Get Customer Asset Infos (getCustomerAssetInfos)", + "description": "Returns a page of asset info objects owned by the specified customer. Asset Info is an extension of the default Asset object that contains information about the owner name. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getCustomerAssetInfos", "parameters": [ + { + "name": "customerId", + "in": "path", + "description": "A string value representing the customer id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, + "schema": { + "type": "string" + } + }, { "name": "pageSize", "in": "query", @@ -14064,10 +13826,28 @@ "format": "int32" } }, + { + "name": "includeCustomers", + "in": "query", + "description": "Include customer or sub-customer entities", + "required": false, + "schema": { + "type": "boolean" + } + }, + { + "name": "assetProfileId", + "in": "query", + "description": "A string value representing the asset profile id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": false, + "schema": { + "type": "string" + } + }, { "name": "textSearch", "in": "query", - "description": "The case insensitive 'substring' filter based on one of the next properties: entityType, entityName, userName, actionType, actionStatus.", + "description": "The case insensitive 'substring' filter based on the asset name.", "required": false, "schema": { "type": "string" @@ -14076,17 +13856,16 @@ { "name": "sortProperty", "in": "query", - "description": "Property of audit log to sort by. See the 'Model' tab of the Response Class for more details. Note: entityType sort property is not defined in the AuditLog class, however, it can be used to sort audit logs by types of entities that were logged.", + "description": "Property of entity to sort by", "required": false, "schema": { "type": "string", "enum": [ "createdTime", - "entityType", - "entityName", - "userName", - "actionType", - "actionStatus" + "name", + "type", + "label", + "customerTitle" ] } }, @@ -14102,35 +13881,6 @@ "DESC" ] } - }, - { - "name": "startTime", - "in": "query", - "description": "The start timestamp in milliseconds of the search time range over the AuditLog class field: 'createdTime'.", - "required": false, - "schema": { - "type": "integer", - "format": "int64" - } - }, - { - "name": "endTime", - "in": "query", - "description": "The end timestamp in milliseconds of the search time range over the AuditLog class field: 'createdTime'.", - "required": false, - "schema": { - "type": "integer", - "format": "int64" - } - }, - { - "name": "actionTypes", - "in": "query", - "description": "A String value representing comma-separated list of action types. This parameter is optional, but it can be used to filter results to fetch only audit logs of specific action types. For example, 'LOGIN', 'LOGOUT'. See the 'Model' tab of the Response Class for more details.", - "required": false, - "schema": { - "type": "string" - } } ], "responses": { @@ -14139,7 +13889,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataAuditLog" + "$ref": "#/components/schemas/PageDataAssetInfo" } } } @@ -14260,14 +14010,14 @@ ] } }, - "/api/audit/logs/customer/{customerId}": { + "/api/customer/{customerId}/assets": { "get": { "tags": [ - "audit-log-controller" + "asset-controller" ], - "summary": "Get audit logs by customer id (getAuditLogsByCustomerId)", - "description": "Returns a page of audit logs related to the targeted customer entities (devices, assets, etc.), and users actions (login, logout, etc.) that belong to this customer. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the audit logs.", - "operationId": "getAuditLogsByCustomerId", + "summary": "Get Customer Assets (getCustomerAssets)", + "description": "Returns a page of assets objects owned by customer. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\n Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getCustomerAssets", "parameters": [ { "name": "customerId", @@ -14298,10 +14048,19 @@ "format": "int32" } }, + { + "name": "type", + "in": "query", + "description": "Asset type", + "required": false, + "schema": { + "type": "string" + } + }, { "name": "textSearch", "in": "query", - "description": "The case insensitive 'substring' filter based on one of the next properties: entityType, entityName, userName, actionType, actionStatus.", + "description": "The case insensitive 'substring' filter based on the asset name.", "required": false, "schema": { "type": "string" @@ -14310,17 +14069,16 @@ { "name": "sortProperty", "in": "query", - "description": "Property of audit log to sort by. See the 'Model' tab of the Response Class for more details. Note: entityType sort property is not defined in the AuditLog class, however, it can be used to sort audit logs by types of entities that were logged.", + "description": "Property of entity to sort by", "required": false, "schema": { "type": "string", "enum": [ "createdTime", - "entityType", - "entityName", - "userName", - "actionType", - "actionStatus" + "name", + "type", + "label", + "customerTitle" ] } }, @@ -14336,35 +14094,6 @@ "DESC" ] } - }, - { - "name": "startTime", - "in": "query", - "description": "The start timestamp in milliseconds of the search time range over the AuditLog class field: 'createdTime'.", - "required": false, - "schema": { - "type": "integer", - "format": "int64" - } - }, - { - "name": "endTime", - "in": "query", - "description": "The end timestamp in milliseconds of the search time range over the AuditLog class field: 'createdTime'.", - "required": false, - "schema": { - "type": "integer", - "format": "int64" - } - }, - { - "name": "actionTypes", - "in": "query", - "description": "A String value representing comma-separated list of action types. This parameter is optional, but it can be used to filter results to fetch only audit logs of specific action types. For example, 'LOGIN', 'LOGOUT'. See the 'Model' tab of the Response Class for more details.", - "required": false, - "schema": { - "type": "string" - } } ], "responses": { @@ -14373,7 +14102,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataAuditLog" + "$ref": "#/components/schemas/PageDataAsset" } } } @@ -14494,28 +14223,19 @@ ] } }, - "/api/audit/logs/entity/{entityType}/{entityId}": { + "/api/entityGroup/{entityGroupId}/assets": { "get": { "tags": [ - "audit-log-controller" + "asset-controller" ], - "summary": "Get audit logs by entity id (getAuditLogsByEntityId)", - "description": "Returns a page of audit logs related to the actions on the targeted entity. Basically, this API call is used to get the full lifecycle of some specific entity. For example to see when a device was created, updated, assigned to some customer, or even deleted from the system. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'SYS_ADMIN' or 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the audit logs.", - "operationId": "getAuditLogsByEntityId", + "summary": "Get assets by Entity Group Id (getAssetsByEntityGroupId)", + "description": "Returns a page of asset objects that belongs to specified Entity Group Id. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\n Security check is performed to verify that the user has 'READ' permission for specified group.", + "operationId": "getAssetsByEntityGroupId", "parameters": [ { - "name": "entityType", - "in": "path", - "description": "A string value representing the entity type. For example, 'DEVICE'", - "required": true, - "schema": { - "type": "string" - } - }, - { - "name": "entityId", + "name": "entityGroupId", "in": "path", - "description": "A string value representing the entity id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "description": "A string value representing the Entity Group Id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { "type": "string" @@ -14527,8 +14247,8 @@ "description": "Maximum amount of entities in a one page", "required": true, "schema": { - "type": "integer", - "format": "int32" + "type": "string", + "minimum": 1 } }, { @@ -14537,14 +14257,14 @@ "description": "Sequence number of page starting from 0", "required": true, "schema": { - "type": "integer", - "format": "int32" + "type": "string", + "minimum": 0 } }, { "name": "textSearch", "in": "query", - "description": "The case insensitive 'substring' filter based on one of the next properties: entityType, entityName, userName, actionType, actionStatus.", + "description": "The case insensitive 'substring' filter based on the asset name.", "required": false, "schema": { "type": "string" @@ -14553,17 +14273,16 @@ { "name": "sortProperty", "in": "query", - "description": "Property of audit log to sort by. See the 'Model' tab of the Response Class for more details. Note: entityType sort property is not defined in the AuditLog class, however, it can be used to sort audit logs by types of entities that were logged.", + "description": "Property of entity to sort by", "required": false, "schema": { "type": "string", "enum": [ "createdTime", - "entityType", - "entityName", - "userName", - "actionType", - "actionStatus" + "name", + "type", + "label", + "customerTitle" ] } }, @@ -14579,35 +14298,6 @@ "DESC" ] } - }, - { - "name": "startTime", - "in": "query", - "description": "The start timestamp in milliseconds of the search time range over the AuditLog class field: 'createdTime'.", - "required": false, - "schema": { - "type": "integer", - "format": "int64" - } - }, - { - "name": "endTime", - "in": "query", - "description": "The end timestamp in milliseconds of the search time range over the AuditLog class field: 'createdTime'.", - "required": false, - "schema": { - "type": "integer", - "format": "int64" - } - }, - { - "name": "actionTypes", - "in": "query", - "description": "A String value representing comma-separated list of action types. This parameter is optional, but it can be used to filter results to fetch only audit logs of specific action types. For example, 'LOGIN', 'LOGOUT'. See the 'Model' tab of the Response Class for more details.", - "required": false, - "schema": { - "type": "string" - } } ], "responses": { @@ -14616,7 +14306,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataAuditLog" + "$ref": "#/components/schemas/PageDataAsset" } } } @@ -14737,108 +14427,20 @@ ] } }, - "/api/audit/logs/user/{userId}": { + "/api/tenant/asset": { "get": { "tags": [ - "audit-log-controller" + "asset-controller" ], - "summary": "Get audit logs by user id (getAuditLogsByUserId)", - "description": "Returns a page of audit logs related to the actions of targeted user. For example, RPC call to a particular device, or alarm acknowledgment for a specific device, etc. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the audit logs.", - "operationId": "getAuditLogsByUserId", + "summary": "Get Tenant Asset (getTenantAssetByName)", + "description": "Requested asset must be owned by tenant that the user belongs to. Asset name is an unique property of asset. So it can be used to identify the asset.\n\n Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getTenantAssetByName", "parameters": [ { - "name": "userId", - "in": "path", - "description": "A string value representing the user id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": true, - "schema": { - "type": "string" - } - }, - { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "page", + "name": "assetName", "in": "query", - "description": "Sequence number of page starting from 0", + "description": "A string value representing the Asset name.", "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'substring' filter based on one of the next properties: entityType, entityName, userName, actionType, actionStatus.", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of audit log to sort by. See the 'Model' tab of the Response Class for more details. Note: entityType sort property is not defined in the AuditLog class, however, it can be used to sort audit logs by types of entities that were logged.", - "required": false, - "schema": { - "type": "string", - "enum": [ - "createdTime", - "entityType", - "entityName", - "userName", - "actionType", - "actionStatus" - ] - } - }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] - } - }, - { - "name": "startTime", - "in": "query", - "description": "The start timestamp in milliseconds of the search time range over the AuditLog class field: 'createdTime'.", - "required": false, - "schema": { - "type": "integer", - "format": "int64" - } - }, - { - "name": "endTime", - "in": "query", - "description": "The end timestamp in milliseconds of the search time range over the AuditLog class field: 'createdTime'.", - "required": false, - "schema": { - "type": "integer", - "format": "int64" - } - }, - { - "name": "actionTypes", - "in": "query", - "description": "A String value representing comma-separated list of action types. This parameter is optional, but it can be used to filter results to fetch only audit logs of specific action types. For example, 'LOGIN', 'LOGOUT'. See the 'Model' tab of the Response Class for more details.", - "required": false, "schema": { "type": "string" } @@ -14850,7 +14452,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataAuditLog" + "$ref": "#/components/schemas/Asset" } } } @@ -14971,31 +14573,90 @@ ] } }, - "/api/auth/changePassword": { - "post": { + "/api/tenant/assets": { + "get": { "tags": [ - "auth-controller" + "asset-controller" ], - "summary": "Change password for current User (changePassword)", - "description": "Change the password for the User which credentials are used to perform this REST API call. Be aware that previously generated [JWT](https://jwt.io/) tokens will be still valid until they expire.", - "operationId": "changePassword", - "requestBody": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ChangePasswordRequest" - } + "summary": "Get Tenant Assets (getTenantAssets)", + "description": "Returns a page of assets owned by tenant. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\n Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getTenantAssets", + "parameters": [ + { + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", + "required": true, + "schema": { + "type": "integer", + "format": "int32" } }, - "required": true - }, + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", + "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "type", + "in": "query", + "description": "Asset type", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'substring' filter based on the asset name.", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string", + "enum": [ + "createdTime", + "name", + "type", + "label", + "customerTitle" + ] + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] + } + } + ], "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/JwtPair" + "$ref": "#/components/schemas/PageDataAsset" } } } @@ -15012,7 +14673,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -15116,17 +14777,102 @@ ] } }, - "/api/auth/logout": { - "post": { + "/api/user/assets": { + "get": { "tags": [ - "auth-controller" + "asset-controller" + ], + "summary": "Get Assets (getUserAssets)", + "description": "Returns a page of assets objects available for the current user. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. Asset Info is an extension of the default Asset object that contains information about the owner name. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getUserAssets", + "parameters": [ + { + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", + "required": true, + "schema": { + "type": "string", + "minimum": 1 + } + }, + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", + "required": true, + "schema": { + "type": "string", + "minimum": 0 + } + }, + { + "name": "type", + "in": "query", + "description": "Asset type", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "assetProfileId", + "in": "query", + "description": "A string value representing the asset profile id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'substring' filter based on the asset name.", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string", + "enum": [ + "createdTime", + "name", + "type", + "label", + "customerTitle" + ] + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] + } + } ], - "summary": "Logout (logout)", - "description": "Special API call to record the 'logout' of the user to the Audit Logs. Since platform uses [JWT](https://jwt.io/), the actual logout is the procedure of clearing the [JWT](https://jwt.io/) token on the client side. ", - "operationId": "logout", "responses": { "200": { - "description": "OK" + "description": "OK", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/PageDataAsset" + } + } + } }, "400": { "description": "Bad Request", @@ -15140,7 +14886,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -15244,21 +14990,31 @@ ] } }, - "/api/auth/user": { - "get": { + "/api/assetProfile": { + "post": { "tags": [ - "auth-controller" + "asset-profile-controller" ], - "summary": "Get current User (getUser)", - "description": "Get the information about the User which credentials are used to perform this REST API call.", - "operationId": "getUser", + "summary": "Create Or Update Asset Profile (saveAssetProfile)", + "description": "Create or update the Asset Profile. When creating asset profile, platform generates asset profile id as [time-based UUID](https://en.wikipedia.org/wiki/Universally_unique_identifier#Version_1_(date-time_and_MAC_address)). The newly created asset profile id will be present in the response. Specify existing asset profile id to update the asset profile. Referencing non-existing asset profile Id will cause 'Not Found' error. \n\nAsset profile name is unique in the scope of tenant. Only one 'default' asset profile may exist in scope of tenant. Remove 'id', 'tenantId' from the request body example (below) to create new Asset Profile entity. \n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "saveAssetProfile", + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/AssetProfile" + } + } + }, + "required": true + }, "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/User" + "$ref": "#/components/schemas/AssetProfile" } } } @@ -15275,7 +15031,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -15379,22 +15135,23 @@ ] } }, - "/api/noauth/activate": { + "/api/assetProfile/names": { "get": { "tags": [ - "auth-controller" + "asset-profile-controller" ], - "summary": "Check Activate User Token (checkActivateToken)", - "description": "Checks the activation token and forwards user to 'Create Password' page. If token is valid, returns '303 See Other' (redirect) response code with the correct address of 'Create Password' page and same 'activateToken' specified in the URL parameters. If token is not valid, returns '409 Conflict'. If token is expired, redirects to error page.", - "operationId": "checkActivateToken", + "summary": "Get Asset Profile names (getAssetProfileNames)", + "description": "Returns a set of unique asset profile names owned by the tenant.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", + "operationId": "getAssetProfileNames", "parameters": [ { - "name": "activateToken", + "name": "activeOnly", "in": "query", - "description": "The activate token string.", - "required": true, + "description": "Flag indicating whether to retrieve exclusively the names of asset profiles that are referenced by tenant's assets.", + "required": false, "schema": { - "type": "string" + "type": "boolean", + "default": false } } ], @@ -15404,7 +15161,10 @@ "content": { "application/json": { "schema": { - "type": "object" + "type": "array", + "items": { + "$ref": "#/components/schemas/EntityInfo" + } } } } @@ -15514,43 +15274,52 @@ } } } - } - }, - "post": { + }, + "security": [ + { + "HttpLoginForm": [] + }, + { + "ApiKeyForm": [] + } + ] + } + }, + "/api/assetProfile/{assetProfileId}": { + "get": { "tags": [ - "auth-controller" + "asset-profile-controller" ], - "summary": "Activate User", - "description": "Checks the activation token and updates corresponding user password in the database. Now the user may start using his password to login. The response already contains the [JWT](https://jwt.io) activation and refresh tokens, to simplify the user activation flow and avoid asking user to input password again after activation. If token is valid, returns the object that contains [JWT](https://jwt.io/) access and refresh tokens. If token is not valid, returns '400 Bad Request'.", - "operationId": "activateUser", + "summary": "Get Asset Profile (getAssetProfileById)", + "description": "Fetch the Asset Profile object based on the provided Asset Profile Id. The server checks that the asset profile is owned by the same tenant. \n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "getAssetProfileById", "parameters": [ { - "name": "sendActivationMail", + "name": "assetProfileId", + "in": "path", + "description": "A string value representing the asset profile id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, + "schema": { + "type": "string" + } + }, + { + "name": "inlineImages", "in": "query", + "description": "Inline images as a data URL (Base64)", "required": false, "schema": { - "type": "boolean", - "default": true + "type": "boolean" } } ], - "requestBody": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ActivateUserRequest" - } - } - }, - "required": true - }, "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/JwtPair" + "$ref": "#/components/schemas/AssetProfile" } } } @@ -15567,7 +15336,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -15660,22 +15429,28 @@ } } } - } - } - }, - "/api/noauth/resetPassword": { - "get": { + }, + "security": [ + { + "HttpLoginForm": [] + }, + { + "ApiKeyForm": [] + } + ] + }, + "delete": { "tags": [ - "auth-controller" + "asset-profile-controller" ], - "summary": "Check password reset token (checkResetToken)", - "description": "Checks the password reset token and forwards user to 'Reset Password' page. If token is valid, returns '303 See Other' (redirect) response code with the correct address of 'Reset Password' page and same 'resetToken' specified in the URL parameters. If token is not valid, returns '409 Conflict'. If token is expired, redirects to error page.", - "operationId": "checkResetToken", + "summary": "Delete asset profile (deleteAssetProfile)", + "description": "Deletes the asset profile. Referencing non-existing asset profile Id will cause an error. Can't delete the asset profile if it is referenced by existing assets.\n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "deleteAssetProfile", "parameters": [ { - "name": "resetToken", - "in": "query", - "description": "The reset token string.", + "name": "assetProfileId", + "in": "path", + "description": "A string value representing the asset profile id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { "type": "string" @@ -15684,14 +15459,7 @@ ], "responses": { "200": { - "description": "OK", - "content": { - "application/json": { - "schema": { - "type": "object" - } - } - } + "description": "OK" }, "400": { "description": "Bad Request", @@ -15798,28 +15566,46 @@ } } } - } - }, + }, + "security": [ + { + "HttpLoginForm": [] + }, + { + "ApiKeyForm": [] + } + ] + } + }, + "/api/assetProfile/{assetProfileId}/default": { "post": { "tags": [ - "auth-controller" + "asset-profile-controller" ], - "summary": "Reset password (resetPassword)", - "description": "Checks the password reset token and updates the password. If token is not valid, returns '400 Bad Request'.", - "operationId": "resetPassword", - "requestBody": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ResetPasswordRequest" - } + "summary": "Make Asset Profile Default (setDefaultAssetProfile)", + "description": "Marks asset profile as default within a tenant scope.\n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "setDefaultAssetProfile", + "parameters": [ + { + "name": "assetProfileId", + "in": "path", + "description": "A string value representing the asset profile id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, + "schema": { + "type": "string" } - }, - "required": true - }, + } + ], "responses": { "200": { - "description": "OK" + "description": "OK", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/AssetProfile" + } + } + } }, "400": { "description": "Bad Request", @@ -15926,30 +15712,35 @@ } } } - } + }, + "security": [ + { + "HttpLoginForm": [] + }, + { + "ApiKeyForm": [] + } + ] } }, - "/api/noauth/resetPasswordByEmail": { - "post": { + "/api/assetProfileInfo/default": { + "get": { "tags": [ - "auth-controller" + "asset-profile-controller" ], - "summary": "Request reset password email (requestResetPasswordByEmail)", - "description": "Request to send the reset password email if the user with specified email address is present in the database. Always return '200 OK' status for security purposes.", - "operationId": "requestResetPasswordByEmail", - "requestBody": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ResetPasswordEmailRequest" - } - } - }, - "required": true - }, + "summary": "Get Default Asset Profile (getDefaultAssetProfileInfo)", + "description": "Fetch the Default Asset Profile Info object. Asset Profile Info is a lightweight object that includes main information about Asset Profile. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", + "operationId": "getDefaultAssetProfileInfo", "responses": { "200": { - "description": "OK" + "description": "OK", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/AssetProfileInfo" + } + } + } }, "400": { "description": "Bad Request", @@ -15963,7 +15754,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -16056,24 +15847,43 @@ } } } - } + }, + "security": [ + { + "HttpLoginForm": [] + }, + { + "ApiKeyForm": [] + } + ] } }, - "/api/noauth/userPasswordPolicy": { + "/api/assetProfileInfo/{assetProfileId}": { "get": { "tags": [ - "auth-controller" + "asset-profile-controller" + ], + "summary": "Get Asset Profile Info (getAssetProfileInfoById)", + "description": "Fetch the Asset Profile Info object based on the provided Asset Profile Id. Asset Profile Info is a lightweight object that includes main information about Asset Profile. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", + "operationId": "getAssetProfileInfoById", + "parameters": [ + { + "name": "assetProfileId", + "in": "path", + "description": "A string value representing the asset profile id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, + "schema": { + "type": "string" + } + } ], - "summary": "Get the current User password policy (getUserPasswordPolicy)", - "description": "API call to get the password policy for the password validation form(s).", - "operationId": "getUserPasswordPolicy", "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/UserPasswordPolicy" + "$ref": "#/components/schemas/AssetProfileInfo" } } } @@ -16183,17 +15993,25 @@ } } } - } + }, + "security": [ + { + "HttpLoginForm": [] + }, + { + "ApiKeyForm": [] + } + ] } }, - "/api/blobEntities": { + "/api/assetProfileInfos": { "get": { "tags": [ - "blob-entity-controller" + "asset-profile-controller" ], - "summary": "Get Blob Entities (getBlobEntities)", - "description": "Returns a page of BlobEntityWithCustomerInfo object that are available for the current user. The platform uses Blob(binary large object) entities in the reporting feature, in order to store Dashboard states snapshots of different content types in base64 format. BlobEntityWithCustomerInfo represents an object that contains base info about the blob entity(name, type, contentType, etc.) and info about the customer(customerTitle, customerIsPublic) of the user that scheduled generation of the dashboard report. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getBlobEntities", + "summary": "Get Asset Profile infos (getAssetProfileInfos)", + "description": "Returns a page of asset profile info objects owned by tenant. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. Asset Profile Info is a lightweight object that includes main information about Asset Profile. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", + "operationId": "getAssetProfileInfos", "parameters": [ { "name": "pageSize", @@ -16215,19 +16033,10 @@ "format": "int32" } }, - { - "name": "type", - "in": "query", - "description": "A string value representing the blob entity type. For example, 'report'", - "required": false, - "schema": { - "type": "string" - } - }, { "name": "textSearch", "in": "query", - "description": "The case insensitive 'startsWith' filter based on the blob entity name.", + "description": "The case insensitive 'substring' filter based on the asset profile name.", "required": false, "schema": { "type": "string" @@ -16243,9 +16052,8 @@ "enum": [ "createdTime", "name", - "type", - "contentType", - "customerTitle" + "description", + "isDefault" ] } }, @@ -16261,26 +16069,6 @@ "DESC" ] } - }, - { - "name": "startTime", - "in": "query", - "description": "The start timestamp in milliseconds of the search time range over the BlobEntityWithCustomerInfo class field: 'createdTime'.", - "required": false, - "schema": { - "type": "integer", - "format": "int64" - } - }, - { - "name": "endTime", - "in": "query", - "description": "The end timestamp in milliseconds of the search time range over the BlobEntityWithCustomerInfo class field: 'createdTime'.", - "required": false, - "schema": { - "type": "integer", - "format": "int64" - } } ], "responses": { @@ -16289,7 +16077,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataBlobEntityWithCustomerInfo" + "$ref": "#/components/schemas/PageDataAssetProfileInfo" } } } @@ -16410,19 +16198,19 @@ ] } }, - "/api/blobEntities/list": { + "/api/assetProfileInfos/list": { "get": { "tags": [ - "blob-entity-controller" + "asset-profile-controller" ], - "summary": "Get Blob Entities By Ids (getBlobEntitiesByIds)", - "description": "Requested blob entities must be owned by tenant or assigned to customer which user is performing the request. The platform uses Blob(binary large object) entities in the reporting feature, in order to store Dashboard states snapshots of different content types in base64 format. BlobEntityInfo represents an object that contains base info about the blob entity(name, type, contentType, etc.). See the 'Model' tab of the Response Class for more details.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getBlobEntitiesByIds", + "summary": "Get Asset Profiles By Ids (getAssetProfilesByIds)", + "description": "Requested asset profiles must be owned by tenant which is performing the request. \n\n Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getAssetProfilesByIds", "parameters": [ { - "name": "blobEntityIds", + "name": "assetProfileIds", "in": "query", - "description": "A list of blob entity ids, separated by comma ','", + "description": "A list of asset profile ids, separated by comma ','", "required": true, "schema": { "type": "array", @@ -16440,7 +16228,7 @@ "schema": { "type": "array", "items": { - "$ref": "#/components/schemas/BlobEntityInfo" + "$ref": "#/components/schemas/AssetProfileInfo" } } } @@ -16562,23 +16350,71 @@ ] } }, - "/api/blobEntity/info/{blobEntityId}": { + "/api/assetProfiles": { "get": { "tags": [ - "blob-entity-controller" + "asset-profile-controller" ], - "summary": "Get Blob Entity With Customer Info (getBlobEntityInfoById)", - "description": "Fetch the BlobEntityWithCustomerInfo object based on the provided Blob entity Id. The platform uses Blob(binary large object) entities in the reporting feature, in order to store Dashboard states snapshots of different content types in base64 format. BlobEntityWithCustomerInfo represents an object that contains base info about the blob entity(name, type, contentType, etc.) and info about the customer(customerTitle, customerIsPublic) of the user that scheduled generation of the dashboard report. Referencing non-existing Blob entity Id will cause an error.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getBlobEntityInfoById", + "summary": "Get Asset Profiles (getAssetProfiles)", + "description": "Returns a page of asset profile objects owned by tenant. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "getAssetProfiles", "parameters": [ { - "name": "blobEntityId", - "in": "path", - "description": "A string value representing the blob entity id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", + "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'substring' filter based on the asset profile name.", + "required": false, "schema": { "type": "string" } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string", + "enum": [ + "createdTime", + "name", + "description", + "isDefault" + ] + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] + } } ], "responses": { @@ -16587,7 +16423,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/BlobEntityWithCustomerInfo" + "$ref": "#/components/schemas/PageDataAssetProfile" } } } @@ -16708,20 +16544,99 @@ ] } }, - "/api/blobEntity/{blobEntityId}": { - "delete": { + "/api/audit/logs": { + "get": { "tags": [ - "blob-entity-controller" + "audit-log-controller" ], - "summary": "Delete Blob Entity (deleteBlobEntity)", - "description": "Delete Blob entity based on the provided Blob entity Id. Referencing non-existing Blob entity Id will cause an error.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.\n\n Security check is performed to verify that the user has 'DELETE' permission for the entity (entities).", - "operationId": "deleteBlobEntity", + "summary": "Get all audit logs (getAuditLogs)", + "description": "Returns a page of audit logs related to all entities in the scope of the current user's Tenant. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'SYS_ADMIN' or 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the audit logs.", + "operationId": "getAuditLogs", "parameters": [ { - "name": "blobEntityId", - "in": "path", - "description": "A string value representing the blob entity id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", + "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'substring' filter based on one of the next properties: entityType, entityName, userName, actionType, actionStatus.", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of audit log to sort by. See the 'Model' tab of the Response Class for more details. Note: entityType sort property is not defined in the AuditLog class, however, it can be used to sort audit logs by types of entities that were logged.", + "required": false, + "schema": { + "type": "string", + "enum": [ + "createdTime", + "entityType", + "entityName", + "userName", + "actionType", + "actionStatus" + ] + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] + } + }, + { + "name": "startTime", + "in": "query", + "description": "The start timestamp in milliseconds of the search time range over the AuditLog class field: 'createdTime'.", + "required": false, + "schema": { + "type": "integer", + "format": "int64" + } + }, + { + "name": "endTime", + "in": "query", + "description": "The end timestamp in milliseconds of the search time range over the AuditLog class field: 'createdTime'.", + "required": false, + "schema": { + "type": "integer", + "format": "int64" + } + }, + { + "name": "actionTypes", + "in": "query", + "description": "A String value representing comma-separated list of action types. This parameter is optional, but it can be used to filter results to fetch only audit logs of specific action types. For example, 'LOGIN', 'LOGOUT'. See the 'Model' tab of the Response Class for more details.", + "required": false, "schema": { "type": "string" } @@ -16729,7 +16644,14 @@ ], "responses": { "200": { - "description": "OK" + "description": "OK", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/PageDataAuditLog" + } + } + } }, "400": { "description": "Bad Request", @@ -16847,20 +16769,108 @@ ] } }, - "/api/blobEntity/{blobEntityId}/download": { + "/api/audit/logs/customer/{customerId}": { "get": { "tags": [ - "blob-entity-controller" + "audit-log-controller" ], - "summary": "Download Blob Entity By Id (downloadBlobEntity)", - "description": "Download report file based on the provided Blob entity Id. Referencing non-existing Blob entity Id will cause an error.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "downloadBlobEntity", + "summary": "Get audit logs by customer id (getAuditLogsByCustomerId)", + "description": "Returns a page of audit logs related to the targeted customer entities (devices, assets, etc.), and users actions (login, logout, etc.) that belong to this customer. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the audit logs.", + "operationId": "getAuditLogsByCustomerId", "parameters": [ { - "name": "blobEntityId", + "name": "customerId", "in": "path", - "description": "A string value representing the blob entity id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "description": "A string value representing the customer id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, + "schema": { + "type": "string" + } + }, + { + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", + "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'substring' filter based on one of the next properties: entityType, entityName, userName, actionType, actionStatus.", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of audit log to sort by. See the 'Model' tab of the Response Class for more details. Note: entityType sort property is not defined in the AuditLog class, however, it can be used to sort audit logs by types of entities that were logged.", + "required": false, + "schema": { + "type": "string", + "enum": [ + "createdTime", + "entityType", + "entityName", + "userName", + "actionType", + "actionStatus" + ] + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] + } + }, + { + "name": "startTime", + "in": "query", + "description": "The start timestamp in milliseconds of the search time range over the AuditLog class field: 'createdTime'.", + "required": false, + "schema": { + "type": "integer", + "format": "int64" + } + }, + { + "name": "endTime", + "in": "query", + "description": "The end timestamp in milliseconds of the search time range over the AuditLog class field: 'createdTime'.", + "required": false, + "schema": { + "type": "integer", + "format": "int64" + } + }, + { + "name": "actionTypes", + "in": "query", + "description": "A String value representing comma-separated list of action types. This parameter is optional, but it can be used to filter results to fetch only audit logs of specific action types. For example, 'LOGIN', 'LOGOUT'. See the 'Model' tab of the Response Class for more details.", + "required": false, "schema": { "type": "string" } @@ -16872,8 +16882,7 @@ "content": { "application/json": { "schema": { - "type": "string", - "format": "binary" + "$ref": "#/components/schemas/PageDataAuditLog" } } } @@ -16994,32 +17003,129 @@ ] } }, - "/api/calculatedField": { - "post": { + "/api/audit/logs/entity/{entityType}/{entityId}": { + "get": { "tags": [ - "calculated-field-controller" + "audit-log-controller" ], - "summary": "Create Or Update Calculated Field (saveCalculatedField)", - "description": "Creates or Updates the Calculated Field. When creating calculated field, platform generates Calculated Field Id as [time-based UUID](https://en.wikipedia.org/wiki/Universally_unique_identifier#Version_1_(date-time_and_MAC_address)). The newly created Calculated Field Id will be present in the response. Specify existing Calculated Field Id to update the calculated field. Referencing non-existing Calculated Field Id will cause 'Not Found' error. Remove 'id', 'tenantId' from the request body example (below) to create new Calculated Field entity. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", - "operationId": "saveCalculatedField", - "requestBody": { - "description": "A JSON value representing the calculated field.", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/CalculatedField" - } + "summary": "Get audit logs by entity id (getAuditLogsByEntityId)", + "description": "Returns a page of audit logs related to the actions on the targeted entity. Basically, this API call is used to get the full lifecycle of some specific entity. For example to see when a device was created, updated, assigned to some customer, or even deleted from the system. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'SYS_ADMIN' or 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the audit logs.", + "operationId": "getAuditLogsByEntityId", + "parameters": [ + { + "name": "entityType", + "in": "path", + "description": "A string value representing the entity type. For example, 'DEVICE'", + "required": true, + "schema": { + "type": "string" } }, - "required": true - }, + { + "name": "entityId", + "in": "path", + "description": "A string value representing the entity id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, + "schema": { + "type": "string" + } + }, + { + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", + "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", + "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'substring' filter based on one of the next properties: entityType, entityName, userName, actionType, actionStatus.", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of audit log to sort by. See the 'Model' tab of the Response Class for more details. Note: entityType sort property is not defined in the AuditLog class, however, it can be used to sort audit logs by types of entities that were logged.", + "required": false, + "schema": { + "type": "string", + "enum": [ + "createdTime", + "entityType", + "entityName", + "userName", + "actionType", + "actionStatus" + ] + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] + } + }, + { + "name": "startTime", + "in": "query", + "description": "The start timestamp in milliseconds of the search time range over the AuditLog class field: 'createdTime'.", + "required": false, + "schema": { + "type": "integer", + "format": "int64" + } + }, + { + "name": "endTime", + "in": "query", + "description": "The end timestamp in milliseconds of the search time range over the AuditLog class field: 'createdTime'.", + "required": false, + "schema": { + "type": "integer", + "format": "int64" + } + }, + { + "name": "actionTypes", + "in": "query", + "description": "A String value representing comma-separated list of action types. This parameter is optional, but it can be used to filter results to fetch only audit logs of specific action types. For example, 'LOGIN', 'LOGOUT'. See the 'Model' tab of the Response Class for more details.", + "required": false, + "schema": { + "type": "string" + } + } + ], "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/CalculatedField" + "$ref": "#/components/schemas/PageDataAuditLog" } } } @@ -17036,7 +17142,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -17140,32 +17246,120 @@ ] } }, - "/api/calculatedField/testScript": { - "post": { + "/api/audit/logs/user/{userId}": { + "get": { "tags": [ - "calculated-field-controller" + "audit-log-controller" ], - "summary": "Test Script expression", - "description": "Execute the Script expression and return the result. The format of request: \n\n```json\n{\n \"expression\": \"var temp = 0; foreach(element: temperature.values) {temp += element.value;} var avgTemperature = temp / temperature.values.size(); var adjustedTemperature = avgTemperature + 0.1 * humidity.value; return {\\\"adjustedTemperature\\\": adjustedTemperature};\",\n \"arguments\": {\n \"temperature\": {\n \"type\": \"TS_ROLLING\",\n \"timeWindow\": {\n \"startTs\": 1739775630002,\n \"endTs\": 65432211,\n \"limit\": 5\n },\n \"values\": [\n { \"ts\": 1739775639851, \"value\": 23 },\n { \"ts\": 1739775664561, \"value\": 43 },\n { \"ts\": 1739775713079, \"value\": 15 },\n { \"ts\": 1739775999522, \"value\": 34 },\n { \"ts\": 1739776228452, \"value\": 22 }\n ]\n },\n \"humidity\": { \"type\": \"SINGLE_VALUE\", \"ts\": 1739776478057, \"value\": 23 }\n }\n}\n```\n\n Expected result JSON contains \"output\" and \"error\".\n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "testCalculatedFieldScript", - "requestBody": { - "description": "Test calculated field TBEL expression.", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/JsonNode" - } + "summary": "Get audit logs by user id (getAuditLogsByUserId)", + "description": "Returns a page of audit logs related to the actions of targeted user. For example, RPC call to a particular device, or alarm acknowledgment for a specific device, etc. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the audit logs.", + "operationId": "getAuditLogsByUserId", + "parameters": [ + { + "name": "userId", + "in": "path", + "description": "A string value representing the user id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, + "schema": { + "type": "string" } }, - "required": true - }, + { + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", + "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", + "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'substring' filter based on one of the next properties: entityType, entityName, userName, actionType, actionStatus.", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of audit log to sort by. See the 'Model' tab of the Response Class for more details. Note: entityType sort property is not defined in the AuditLog class, however, it can be used to sort audit logs by types of entities that were logged.", + "required": false, + "schema": { + "type": "string", + "enum": [ + "createdTime", + "entityType", + "entityName", + "userName", + "actionType", + "actionStatus" + ] + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] + } + }, + { + "name": "startTime", + "in": "query", + "description": "The start timestamp in milliseconds of the search time range over the AuditLog class field: 'createdTime'.", + "required": false, + "schema": { + "type": "integer", + "format": "int64" + } + }, + { + "name": "endTime", + "in": "query", + "description": "The end timestamp in milliseconds of the search time range over the AuditLog class field: 'createdTime'.", + "required": false, + "schema": { + "type": "integer", + "format": "int64" + } + }, + { + "name": "actionTypes", + "in": "query", + "description": "A String value representing comma-separated list of action types. This parameter is optional, but it can be used to filter results to fetch only audit logs of specific action types. For example, 'LOGIN', 'LOGOUT'. See the 'Model' tab of the Response Class for more details.", + "required": false, + "schema": { + "type": "string" + } + } + ], "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/JsonNode" + "$ref": "#/components/schemas/PageDataAuditLog" } } } @@ -17182,7 +17376,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -17286,31 +17480,31 @@ ] } }, - "/api/calculatedField/{calculatedFieldId}": { - "get": { + "/api/auth/changePassword": { + "post": { "tags": [ - "calculated-field-controller" + "auth-controller" ], - "summary": "Get Calculated Field (getCalculatedFieldById)", - "description": "Fetch the Calculated Field object based on the provided Calculated Field Id.", - "operationId": "getCalculatedFieldById", - "parameters": [ - { - "name": "calculatedFieldId", - "in": "path", - "required": true, - "schema": { - "type": "string" + "summary": "Change password for current User (changePassword)", + "description": "Change the password for the User which credentials are used to perform this REST API call. Be aware that previously generated [JWT](https://jwt.io/) tokens will be still valid until they expire.", + "operationId": "changePassword", + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ChangePasswordRequest" + } } - } - ], + }, + "required": true + }, "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/CalculatedField" + "$ref": "#/components/schemas/JwtPair" } } } @@ -17327,7 +17521,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -17429,24 +17623,16 @@ "ApiKeyForm": [] } ] - }, - "delete": { + } + }, + "/api/auth/logout": { + "post": { "tags": [ - "calculated-field-controller" - ], - "summary": "Delete Calculated Field (deleteCalculatedField)", - "description": "Deletes the calculated field. Referencing non-existing Calculated Field Id will cause an error.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", - "operationId": "deleteCalculatedField", - "parameters": [ - { - "name": "calculatedFieldId", - "in": "path", - "required": true, - "schema": { - "type": "string" - } - } + "auth-controller" ], + "summary": "Logout (logout)", + "description": "Special API call to record the 'logout' of the user to the Audit Logs. Since platform uses [JWT](https://jwt.io/), the actual logout is the procedure of clearing the [JWT](https://jwt.io/) token on the client side. ", + "operationId": "logout", "responses": { "200": { "description": "OK" @@ -17463,7 +17649,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -17567,31 +17753,21 @@ ] } }, - "/api/calculatedField/{calculatedFieldId}/debug": { + "/api/auth/user": { "get": { "tags": [ - "calculated-field-controller" - ], - "summary": "Get latest calculated field debug event (getLatestCalculatedFieldDebugEvent)", - "description": "Gets latest calculated field debug event for specified calculated field id. Referencing non-existing calculated field id will cause an error. \n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "getLatestCalculatedFieldDebugEvent", - "parameters": [ - { - "name": "calculatedFieldId", - "in": "path", - "required": true, - "schema": { - "type": "string" - } - } + "auth-controller" ], + "summary": "Get current User (getUser)", + "description": "Get the information about the User which credentials are used to perform this REST API call.", + "operationId": "getUser", "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/JsonNode" + "$ref": "#/components/schemas/User" } } } @@ -17712,39 +17888,22 @@ ] } }, - "/api/calculatedField/{calculatedFieldId}/reprocess": { + "/api/noauth/activate": { "get": { "tags": [ - "calculated-field-controller" + "auth-controller" ], - "summary": "Reprocess Calculated Field (reprocessCalculatedField)", - "description": "Reprocesses the calculated field.\n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "reprocessCalculatedField", + "summary": "Check Activate User Token (checkActivateToken)", + "description": "Checks the activation token and forwards user to 'Create Password' page. If token is valid, returns '303 See Other' (redirect) response code with the correct address of 'Create Password' page and same 'activateToken' specified in the URL parameters. If token is not valid, returns '409 Conflict'. If token is expired, redirects to error page.", + "operationId": "checkActivateToken", "parameters": [ { - "name": "calculatedFieldId", - "in": "path", - "required": true, - "schema": { - "type": "string" - } - }, - { - "name": "startTs", - "in": "query", - "required": true, - "schema": { - "type": "integer", - "format": "int64" - } - }, - { - "name": "endTs", + "name": "activateToken", "in": "query", + "description": "The activate token string.", "required": true, "schema": { - "type": "integer", - "format": "int64" + "type": "string" } } ], @@ -17754,7 +17913,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/Job" + "type": "object" } } } @@ -17864,42 +18023,43 @@ } } } - }, - "security": [ - { - "HttpLoginForm": [] - }, - { - "ApiKeyForm": [] - } - ] - } - }, - "/api/calculatedField/{calculatedFieldId}/reprocess/job": { - "get": { + } + }, + "post": { "tags": [ - "calculated-field-controller" + "auth-controller" ], - "summary": "getLastCalculatedFieldReprocessingJob", - "operationId": "getLastCalculatedFieldReprocessingJob", + "summary": "Activate User", + "description": "Checks the activation token and updates corresponding user password in the database. Now the user may start using his password to login. The response already contains the [JWT](https://jwt.io) activation and refresh tokens, to simplify the user activation flow and avoid asking user to input password again after activation. If token is valid, returns the object that contains [JWT](https://jwt.io/) access and refresh tokens. If token is not valid, returns '400 Bad Request'.", + "operationId": "activateUser", "parameters": [ { - "name": "calculatedFieldId", - "in": "path", - "required": true, + "name": "sendActivationMail", + "in": "query", + "required": false, "schema": { - "type": "string", - "format": "uuid" + "type": "boolean", + "default": true } } ], + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ActivateUserRequest" + } + } + }, + "required": true + }, "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/Job" + "$ref": "#/components/schemas/JwtPair" } } } @@ -17916,7 +18076,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -18009,29 +18169,22 @@ } } } - }, - "security": [ - { - "HttpLoginForm": [] - }, - { - "ApiKeyForm": [] - } - ] + } } }, - "/api/calculatedField/{calculatedFieldId}/reprocess/validate": { + "/api/noauth/resetPassword": { "get": { "tags": [ - "calculated-field-controller" + "auth-controller" ], - "summary": "Validate reprocessing capability of a calculated field (validateCalculatedFieldReprocessing)", - "description": "Checks whether the specified calculated field can be reprocessed. Returns a validation result indicating if reprocessing is allowed and, if not, provides a reason. \n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "validateCalculatedFieldReprocessing", + "summary": "Check password reset token (checkResetToken)", + "description": "Checks the password reset token and forwards user to 'Reset Password' page. If token is valid, returns '303 See Other' (redirect) response code with the correct address of 'Reset Password' page and same 'resetToken' specified in the URL parameters. If token is not valid, returns '409 Conflict'. If token is expired, redirects to error page.", + "operationId": "checkResetToken", "parameters": [ { - "name": "calculatedFieldId", - "in": "path", + "name": "resetToken", + "in": "query", + "description": "The reset token string.", "required": true, "schema": { "type": "string" @@ -18044,7 +18197,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/CfReprocessingValidationResult" + "type": "object" } } } @@ -18154,53 +18307,25 @@ } } } - }, - "security": [ - { - "HttpLoginForm": [] - }, - { - "ApiKeyForm": [] - } - ] - } - }, - "/api/calculatedField/{calculatedFieldId}/reprocessAndWait": { - "get": { + } + }, + "post": { "tags": [ - "calculated-field-controller" + "auth-controller" ], - "summary": "Reprocess Calculated Field and wait for completion (reprocessCalculatedFieldAndWait)", - "description": "Reprocesses the calculated field and waits until the job completes or fails.\n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "reprocessCalculatedFieldAndWait", - "parameters": [ - { - "name": "calculatedFieldId", - "in": "path", - "required": true, - "schema": { - "type": "string" - } - }, - { - "name": "startTs", - "in": "query", - "required": true, - "schema": { - "type": "integer", - "format": "int64" + "summary": "Reset password (resetPassword)", + "description": "Checks the password reset token and updates the password. If token is not valid, returns '400 Bad Request'.", + "operationId": "resetPassword", + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ResetPasswordRequest" + } } }, - { - "name": "endTs", - "in": "query", - "required": true, - "schema": { - "type": "integer", - "format": "int64" - } - } - ], + "required": true + }, "responses": { "200": { "description": "OK" @@ -18217,7 +18342,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -18310,119 +18435,30 @@ } } } - }, - "security": [ - { - "HttpLoginForm": [] - }, - { - "ApiKeyForm": [] - } - ] + } } }, - "/api/calculatedField/{entityType}/{entityId}": { - "get": { + "/api/noauth/resetPasswordByEmail": { + "post": { "tags": [ - "calculated-field-controller" + "auth-controller" ], - "summary": "Get Calculated Fields by Entity Id (getCalculatedFieldsByEntityId)", - "description": "Fetch the Calculated Fields based on the provided Entity Id.", - "operationId": "getCalculatedFieldsByEntityId", - "parameters": [ - { - "name": "entityType", - "in": "path", - "description": "A string value representing the entity type. For example, 'DEVICE'", - "required": true, - "schema": { - "type": "string" - } - }, - { - "name": "entityId", - "in": "path", - "description": "A string value representing the entity id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": true, - "schema": { - "type": "string" - } - }, - { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", - "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "type", - "in": "query", - "description": "Calculated field type. If not specified, all types will be returned.", - "required": false, - "schema": { - "$ref": "#/components/schemas/CalculatedFieldType" - } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'substring' filter based on the calculated field name.", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, - "schema": { - "type": "string", - "enum": [ - "createdTime", - "name" - ] + "summary": "Request reset password email (requestResetPasswordByEmail)", + "description": "Request to send the reset password email if the user with specified email address is present in the database. Always return '200 OK' status for security purposes.", + "operationId": "requestResetPasswordByEmail", + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ResetPasswordEmailRequest" + } } }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] - } - } - ], + "required": true + }, "responses": { "200": { - "description": "OK", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/PageDataCalculatedField" - } - } - } + "description": "OK" }, "400": { "description": "Bad Request", @@ -18436,7 +18472,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -18529,136 +18565,24 @@ } } } - }, - "security": [ - { - "HttpLoginForm": [] - }, - { - "ApiKeyForm": [] - } - ] + } } }, - "/api/calculatedFields": { + "/api/noauth/userPasswordPolicy": { "get": { "tags": [ - "calculated-field-controller" - ], - "summary": "Get calculated fields (getCalculatedFields)", - "description": "Fetch tenant calculated fields based on the filter.", - "operationId": "getCalculatedFields", - "parameters": [ - { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", - "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "types", - "in": "query", - "description": "Calculated field types filter.", - "required": false, - "schema": { - "type": "array", - "items": { - "$ref": "#/components/schemas/CalculatedFieldType" - }, - "uniqueItems": true - } - }, - { - "name": "entityType", - "in": "query", - "description": "Entity type filter. If not specified, calculated fields for all supported entity types will be returned.", - "required": false, - "schema": { - "$ref": "#/components/schemas/EntityType" - } - }, - { - "name": "entities", - "in": "query", - "description": "Entities filter. If not specified, calculated fields for entity type filter will be returned.", - "required": false, - "schema": { - "type": "array", - "items": { - "type": "string", - "format": "uuid" - }, - "uniqueItems": true - } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'substring' filter based on the calculated field name.", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, - "schema": { - "type": "string", - "enum": [ - "createdTime", - "name" - ] - } - }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] - } - }, - { - "name": "name", - "in": "query", - "description": "Repeatable name query parameter", - "schema": { - "type": "array", - "items": { - "type": "string" - } - } - } + "auth-controller" ], + "summary": "Get the current User password policy (getUserPasswordPolicy)", + "description": "API call to get the password policy for the password validation form(s).", + "operationId": "getUserPasswordPolicy", "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataCalculatedFieldInfo" + "$ref": "#/components/schemas/UserPasswordPolicy" } } } @@ -18768,35 +18692,18 @@ } } } - }, - "security": [ - { - "HttpLoginForm": [] - }, - { - "ApiKeyForm": [] - } - ] + } } }, - "/api/calculatedFields/names": { + "/api/blobEntities": { "get": { "tags": [ - "calculated-field-controller" + "blob-entity-controller" ], - "summary": "Get calculated field names (getCalculatedFieldNames)", - "description": "Fetch the list of calculated field names for specified type.", - "operationId": "getCalculatedFieldNames", + "summary": "Get Blob Entities (getBlobEntities)", + "description": "Returns a page of BlobEntityWithCustomerInfo object that are available for the current user. The platform uses Blob(binary large object) entities in the reporting feature, in order to store Dashboard states snapshots of different content types in base64 format. BlobEntityWithCustomerInfo represents an object that contains base info about the blob entity(name, type, contentType, etc.) and info about the customer(customerTitle, customerIsPublic) of the user that scheduled generation of the dashboard report. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getBlobEntities", "parameters": [ - { - "name": "type", - "in": "query", - "description": "Calculated field type filter.", - "required": true, - "schema": { - "$ref": "#/components/schemas/CalculatedFieldType" - } - }, { "name": "pageSize", "in": "query", @@ -18817,15 +18724,40 @@ "format": "int32" } }, + { + "name": "type", + "in": "query", + "description": "A string value representing the blob entity type. For example, 'report'", + "required": false, + "schema": { + "type": "string" + } + }, { "name": "textSearch", "in": "query", - "description": "The case insensitive 'substring' filter based on the calculated field name.", + "description": "The case insensitive 'startsWith' filter based on the blob entity name.", "required": false, "schema": { "type": "string" } }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string", + "enum": [ + "createdTime", + "name", + "type", + "contentType", + "customerTitle" + ] + } + }, { "name": "sortOrder", "in": "query", @@ -18838,6 +18770,26 @@ "DESC" ] } + }, + { + "name": "startTime", + "in": "query", + "description": "The start timestamp in milliseconds of the search time range over the BlobEntityWithCustomerInfo class field: 'createdTime'.", + "required": false, + "schema": { + "type": "integer", + "format": "int64" + } + }, + { + "name": "endTime", + "in": "query", + "description": "The end timestamp in milliseconds of the search time range over the BlobEntityWithCustomerInfo class field: 'createdTime'.", + "required": false, + "schema": { + "type": "integer", + "format": "int64" + } } ], "responses": { @@ -18846,7 +18798,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataString" + "$ref": "#/components/schemas/PageDataBlobEntityWithCustomerInfo" } } } @@ -18967,22 +18919,25 @@ ] } }, - "/api/component/{componentDescriptorClazz}": { + "/api/blobEntities/list": { "get": { "tags": [ - "component-descriptor-controller" + "blob-entity-controller" ], - "summary": "Get Component Descriptor (getComponentDescriptorByClazz)", - "description": "Gets the Component Descriptor object using class name from the path parameters. Each Component Descriptor represents configuration of specific rule node (e.g. 'Save Timeseries' or 'Send Email'.). The Component Descriptors are used by the rule chain Web UI to build the configuration forms for the rule nodes. The Component Descriptors are discovered at runtime by scanning the class path and searching for @RuleNode annotation. Once discovered, the up to date list of descriptors is persisted to the database.\n\nAvailable for users with 'SYS_ADMIN' or 'TENANT_ADMIN' authority.", - "operationId": "getComponentDescriptorByClazz", + "summary": "Get Blob Entities By Ids (getBlobEntitiesByIds)", + "description": "Requested blob entities must be owned by tenant or assigned to customer which user is performing the request. The platform uses Blob(binary large object) entities in the reporting feature, in order to store Dashboard states snapshots of different content types in base64 format. BlobEntityInfo represents an object that contains base info about the blob entity(name, type, contentType, etc.). See the 'Model' tab of the Response Class for more details.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getBlobEntitiesByIds", "parameters": [ { - "name": "componentDescriptorClazz", - "in": "path", - "description": "Component Descriptor class name", + "name": "blobEntityIds", + "in": "query", + "description": "A list of blob entity ids, separated by comma ','", "required": true, "schema": { - "type": "string" + "type": "array", + "items": { + "type": "string" + } } } ], @@ -18992,7 +18947,10 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/ComponentDescriptor" + "type": "array", + "items": { + "$ref": "#/components/schemas/BlobEntityInfo" + } } } } @@ -19113,38 +19071,22 @@ ] } }, - "/api/components": { + "/api/blobEntity/info/{blobEntityId}": { "get": { "tags": [ - "component-descriptor-controller" + "blob-entity-controller" ], - "summary": "Get Component Descriptors (getComponentDescriptorsByTypes)", - "description": "Gets the Component Descriptors using coma separated list of rule node types and optional rule chain type request parameters. Each Component Descriptor represents configuration of specific rule node (e.g. 'Save Timeseries' or 'Send Email'.). The Component Descriptors are used by the rule chain Web UI to build the configuration forms for the rule nodes. The Component Descriptors are discovered at runtime by scanning the class path and searching for @RuleNode annotation. Once discovered, the up to date list of descriptors is persisted to the database.\n\nAvailable for users with 'SYS_ADMIN' or 'TENANT_ADMIN' authority.", - "operationId": "getComponentDescriptorsByTypes", + "summary": "Get Blob Entity With Customer Info (getBlobEntityInfoById)", + "description": "Fetch the BlobEntityWithCustomerInfo object based on the provided Blob entity Id. The platform uses Blob(binary large object) entities in the reporting feature, in order to store Dashboard states snapshots of different content types in base64 format. BlobEntityWithCustomerInfo represents an object that contains base info about the blob entity(name, type, contentType, etc.) and info about the customer(customerTitle, customerIsPublic) of the user that scheduled generation of the dashboard report. Referencing non-existing Blob entity Id will cause an error.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getBlobEntityInfoById", "parameters": [ { - "name": "componentTypes", - "in": "query", - "description": "List of types of the Rule Nodes, (ENRICHMENT, FILTER, TRANSFORMATION, ACTION or EXTERNAL)", + "name": "blobEntityId", + "in": "path", + "description": "A string value representing the blob entity id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { - "type": "array", - "items": { - "type": "string" - } - } - }, - { - "name": "ruleChainType", - "in": "query", - "description": "Type of the Rule Chain", - "required": false, - "schema": { - "type": "string", - "enum": [ - "CORE", - "EDGE" - ] + "type": "string" } } ], @@ -19154,10 +19096,7 @@ "content": { "application/json": { "schema": { - "type": "array", - "items": { - "$ref": "#/components/schemas/ComponentDescriptor" - } + "$ref": "#/components/schemas/BlobEntityWithCustomerInfo" } } } @@ -19278,58 +19217,28 @@ ] } }, - "/api/components/{componentType}": { - "get": { + "/api/blobEntity/{blobEntityId}": { + "delete": { "tags": [ - "component-descriptor-controller" + "blob-entity-controller" ], - "summary": "Get Component Descriptors (getComponentDescriptorsByType)", - "description": "Gets the Component Descriptors using rule node type and optional rule chain type request parameters. Each Component Descriptor represents configuration of specific rule node (e.g. 'Save Timeseries' or 'Send Email'.). The Component Descriptors are used by the rule chain Web UI to build the configuration forms for the rule nodes. The Component Descriptors are discovered at runtime by scanning the class path and searching for @RuleNode annotation. Once discovered, the up to date list of descriptors is persisted to the database.\n\nAvailable for users with 'SYS_ADMIN' or 'TENANT_ADMIN' authority.", - "operationId": "getComponentDescriptorsByType", + "summary": "Delete Blob Entity (deleteBlobEntity)", + "description": "Delete Blob entity based on the provided Blob entity Id. Referencing non-existing Blob entity Id will cause an error.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.\n\n Security check is performed to verify that the user has 'DELETE' permission for the entity (entities).", + "operationId": "deleteBlobEntity", "parameters": [ { - "name": "componentType", + "name": "blobEntityId", "in": "path", - "description": "Type of the Rule Node", + "description": "A string value representing the blob entity id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { - "type": "string", - "enum": [ - "ENRICHMENT", - "FILTER", - "TRANSFORMATION", - "ACTION", - "EXTERNAL" - ] - } - }, - { - "name": "ruleChainType", - "in": "query", - "description": "Type of the Rule Chain", - "required": false, - "schema": { - "type": "string", - "enum": [ - "CORE", - "EDGE" - ] + "type": "string" } } ], "responses": { "200": { - "description": "OK", - "content": { - "application/json": { - "schema": { - "type": "array", - "items": { - "$ref": "#/components/schemas/ComponentDescriptor" - } - } - } - } + "description": "OK" }, "400": { "description": "Bad Request", @@ -19447,32 +19356,33 @@ ] } }, - "/api/converter": { - "post": { + "/api/blobEntity/{blobEntityId}/download": { + "get": { "tags": [ - "converter-controller" + "blob-entity-controller" ], - "summary": "Create Or Update Converter (saveConverter)", - "description": "Create or update the Converter. When creating converter, platform generates Converter Id as [time-based UUID](https://en.wikipedia.org/wiki/Universally_unique_identifier#Version_1_(date-time_and_MAC_address)). The newly created converter id will be present in the response. Specify existing Converter id to update the converter. Referencing non-existing converter Id will cause 'Not Found' error. Converter name is unique in the scope of tenant. \n\n# Converter Configuration\n\nConverter configuration (**'configuration'** field) is the JSON object that should contain one of two possible fields: **'decoder'** or **'encoder'**. The former is used when the converter has UPLINK type, the latter is used - when DOWNLINK type. It can contain both 'decoder' and 'encoder' fields, when the correct one is specified for the appropriate converter type, another one can be set to 'null'. See the examples of each one below. \n\n## Uplink Converter Configuration\n\n***Default converter may be different, depending on integration type***.\n\n```json\n{\n \"decoder\":\"// Decode an uplink message from a buffer\\n// payload - array of bytes\\n// metadata - key/value object\\n\\n/** Decoder **/\\n\\n// decode payload to string\\nvar payloadStr = decodeToString(payload);\\n\\n// decode payload to JSON\\n// var data = decodeToJson(payload);\\n\\nvar deviceName = 'Device A';\\nvar deviceType = 'thermostat';\\nvar customerName = 'customer';\\nvar groupName = 'thermostat devices';\\nvar manufacturer = 'Example corporation';\\n// use assetName and assetType instead of deviceName and deviceType\\n// to automatically create assets instead of devices.\\n// var assetName = 'Asset A';\\n// var assetType = 'building';\\n\\n// Result object with device/asset attributes/telemetry data\\nvar result = {\\n// Use deviceName and deviceType or assetName and assetType, but not both.\\n deviceName: deviceName,\\n deviceType: deviceType,\\n// assetName: assetName,\\n// assetType: assetType,\\n customerName: customerName,\\n groupName: groupName,\\n contentAwareAttributeKeys: ['manufacturer'],\\n attributes: {\\n model: 'Model A',\\n serialNumber: 'SN111',\\n integrationName: metadata['integrationName'],\\n manufacturer: manufacturer\\n },\\n telemetry: {\\n temperature: 42,\\n humidity: 80,\\n rawData: payloadStr\\n }\\n};\\n\\n/** Helper functions **/\\n\\nfunction decodeToString(payload) {\\n return String.fromCharCode.apply(String, payload);\\n}\\n\\nfunction decodeToJson(payload) {\\n // covert payload to string.\\n var str = decodeToString(payload);\\n\\n // parse string to JSON\\n var data = JSON.parse(str);\\n return data;\\n}\\n\\nreturn result;\",\n \"encoder\":null\n}\n```\n\nDecoder field in the more readable form:\n\n```text\n// Decode an uplink message from a buffer\n// payload - array of bytes\n// metadata - key/value object\n\n/** Decoder **/\n\n// decode payload to string\nvar payloadStr = decodeToString(payload);\n\n// decode payload to JSON\n// var data = decodeToJson(payload);\n\nvar deviceName = 'Device A';\nvar deviceType = 'thermostat';\nvar customerName = 'customer';\nvar groupName = 'thermostat devices';\nvar manufacturer = 'Example corporation';\n// use assetName and assetType instead of deviceName and deviceType\n// to automatically create assets instead of devices.\n// var assetName = 'Asset A';\n// var assetType = 'building';\n\n// Result object with device/asset attributes/telemetry data\nvar result = {\n// Use deviceName and deviceType or assetName and assetType, but not both.\n deviceName: deviceName,\n deviceType: deviceType,\n// assetName: assetName,\n// assetType: assetType,\n customerName: customerName,\n groupName: groupName,\n attributes: {\n model: 'Model A',\n serialNumber: 'SN111',\n integrationName: metadata['integrationName']\n manufacturer: manufacturer,\n },\n telemetry: {\n temperature: 42,\n humidity: 80,\n rawData: payloadStr\n }\n};\n\n/** Helper functions **/\n\nfunction decodeToString(payload) {\n return String.fromCharCode.apply(String, payload);\n}\n\nfunction decodeToJson(payload) {\n // covert payload to string.\n var str = decodeToString(payload);\n\n // parse string to JSON\n var data = JSON.parse(str);\n return data;\n}\n\nreturn result;\n```\n\n## Downlink Converter Configuration\n\n```json\n{\n \"decoder\":null,\n \"encoder\":\"// Encode downlink data from incoming Rule Engine message\\n\\n// msg - JSON message payload downlink message json\\n// msgType - type of message, for ex. 'ATTRIBUTES_UPDATED', 'POST_TELEMETRY_REQUEST', etc.\\n// metadata - list of key-value pairs with additional data about the message\\n// integrationMetadata - list of key-value pairs with additional data defined in Integration executing this converter\\n\\n/** Encoder **/\\n\\nvar data = {};\\n\\n// Process data from incoming message and metadata\\n\\ndata.tempFreq = msg.temperatureUploadFrequency;\\ndata.humFreq = msg.humidityUploadFrequency;\\n\\ndata.devSerialNumber = metadata['ss_serialNumber'];\\n\\n// Result object with encoded downlink payload\\nvar result = {\\n\\n // downlink data content type: JSON, TEXT or BINARY (base64 format)\\n contentType: \\\"JSON\\\",\\n\\n // downlink data\\n data: JSON.stringify(data),\\n\\n // Optional metadata object presented in key/value format\\n metadata: {\\n topic: metadata['deviceType']+'/'+metadata['deviceName']+'/upload'\\n }\\n\\n};\\n\\nreturn result;\"\n}\n```\n\nEncoder field in the more readable form:\n\n```text\n// Encode downlink data from incoming Rule Engine message\n\n// msg - JSON message payload downlink message json\n// msgType - type of message, for ex. 'ATTRIBUTES_UPDATED', 'POST_TELEMETRY_REQUEST', etc.\n// metadata - list of key-value pairs with additional data about the message\n// integrationMetadata - list of key-value pairs with additional data defined in Integration executing this converter\n\n/** Encoder **/\n\nvar data = {};\n\n// Process data from incoming message and metadata\n\ndata.tempFreq = msg.temperatureUploadFrequency;\ndata.humFreq = msg.humidityUploadFrequency;\n\ndata.devSerialNumber = metadata['ss_serialNumber'];\n\n// Result object with encoded downlink payload\nvar result = {\n\n // downlink data content type: JSON, TEXT or BINARY (base64 format)\n contentType: \"JSON\",\n\n // downlink data\n data: JSON.stringify(data),\n\n // Optional metadata object presented in key/value format\n metadata: {\n topic: metadata['deviceType']+'/'+metadata['deviceName']+'/upload'\n }\n\n};\n\nreturn result;\n```\n\nRemove 'id', 'tenantId' from the request body example (below) to create new converter entity. \n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "saveConverter", - "requestBody": { - "description": "A JSON value representing the converter.", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/Converter" - } + "summary": "Download Blob Entity By Id (downloadBlobEntity)", + "description": "Download report file based on the provided Blob entity Id. Referencing non-existing Blob entity Id will cause an error.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "downloadBlobEntity", + "parameters": [ + { + "name": "blobEntityId", + "in": "path", + "description": "A string value representing the blob entity id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, + "schema": { + "type": "string" } - }, - "required": true - }, + } + ], "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/Converter" + "type": "string", + "format": "binary" } } } @@ -19489,7 +19399,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -19593,31 +19503,20 @@ ] } }, - "/api/converter/testDownLink": { + "/api/calculatedField": { "post": { "tags": [ - "converter-controller" - ], - "summary": "Test converter function (testDownLinkConverter)", - "description": "Returns a JSON object representing the result of the processed incoming message. \n\n## Request Body Example\n\n```json\n{\n \"metadata\":{\n \"data\":\"40\"\n },\n \"msg\":\"{\\n \\\"temp\\\": 42,\\n \\\"humidity\\\": 77\\n}\",\n \"msgType\":\"POST_TELEMETRY_REQUEST\",\n \"integrationMetadata\":{\n \"integrationName\":\"Integration\"\n },\n \"encoder\":\"// Encode downlink data from incoming Rule Engine message\\n\\n// msg - JSON message payload downlink message json\\n// msgType - type of message, for ex. 'ATTRIBUTES_UPDATED', 'POST_TELEMETRY_REQUEST', etc.\\n// metadata - list of key-value pairs with additional data about the message\\n// integrationMetadata - list of key-value pairs with additional data defined in Integration executing this converter\\n\\n/** Encoder **/\\n\\nvar data = {};\\n\\n// Process data from incoming message and metadata\\n\\ndata.tempValue = msg.temp;\\ndata.humValue = msg.humidity;\\n\\ndata.devSerialNumber = metadata['ss_serialNumber'];\\n\\n// Result object with encoded downlink payload\\nvar result = {\\n\\n // downlink data content type: JSON, TEXT or BINARY (base64 format)\\n contentType: \\\"JSON\\\",\\n\\n // downlink data\\n data: JSON.stringify(data),\\n\\n // Optional metadata object presented in key/value format\\n metadata: {\\n topic: metadata['deviceType']+'/'+metadata['deviceName']+'/upload'\\n }\\n\\n};\\n\\nreturn result;\"\n}\n```\n\n * 'metadata' - message metadata pushed from the rule engine; \n * 'msg' - message data pushed from the rule engine; \n * 'msgType' - type of the message pushed from the rule engine; \n * 'integrationMetadata' - integration metadata object; \n * 'encoder' - string representation of the encoder configuration.\n\n## Response Body Example\n\n```json\n{\n \"contentType\":\"JSON\",\n \"data\":\"{\\\"tempValue\\\":42,\\\"humValue\\\":77}\",\n \"metadata\":{\n \"topic\":\"sensor/Temp Sensor/upload\"\n }\n}\n```\n\n * 'contentType' - downlink data content type; \n * 'data' - downlink data; \n * 'metadata' - optional metadata object. \n", - "operationId": "testDownLinkConverter", - "parameters": [ - { - "name": "scriptLang", - "in": "query", - "description": "Script language: JS or TBEL", - "required": false, - "schema": { - "$ref": "#/components/schemas/ScriptLanguage" - } - } + "calculated-field-controller" ], + "summary": "Create Or Update Calculated Field (saveCalculatedField)", + "description": "Creates or Updates the Calculated Field. When creating calculated field, platform generates Calculated Field Id as [time-based UUID](https://en.wikipedia.org/wiki/Universally_unique_identifier#Version_1_(date-time_and_MAC_address)). The newly created Calculated Field Id will be present in the response. Specify existing Calculated Field Id to update the calculated field. Referencing non-existing Calculated Field Id will cause 'Not Found' error. Remove 'id', 'tenantId' from the request body example (below) to create new Calculated Field entity. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", + "operationId": "saveCalculatedField", "requestBody": { - "description": "A JSON value representing the input to the converter function.", + "description": "A JSON value representing the calculated field.", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/JsonNode" + "$ref": "#/components/schemas/CalculatedField" } } }, @@ -19629,7 +19528,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/JsonNode" + "$ref": "#/components/schemas/CalculatedField" } } } @@ -19750,27 +19649,16 @@ ] } }, - "/api/converter/testUpLink": { + "/api/calculatedField/testScript": { "post": { "tags": [ - "converter-controller" - ], - "summary": "Test converter function (testUpLinkConverter)", - "description": "Returns a JSON object representing the result of the processed incoming message. \n\n## Request Body Example\n\n```json\n{\n \"metadata\":{\n },\n \"payload\":\"ewogICAgImRhdGEiOiAiZGF0YSIKfQ==\",\n \"decoder\":\"// Decode an uplink message from a buffer\\n// payload - array of bytes\\n// metadata - key/value object\\n\\n/** Decoder **/\\n\\n// decode payload to string\\nvar payloadStr = decodeToString(payload);\\n\\n// decode payload to JSON\\n// var data = decodeToJson(payload);\\n\\nvar deviceName = 'Device A';\\nvar deviceType = 'thermostat';\\nvar customerName = 'customer';\\nvar groupName = 'thermostat devices';\\nvar manufacturer = 'Example corporation';\\n// use assetName and assetType instead of deviceName and deviceType\\n// to automatically create assets instead of devices.\\n// var assetName = 'Asset A';\\n// var assetType = 'building';\\n\\n// Result object with device/asset attributes/telemetry data\\nvar result = {\\n// Use deviceName and deviceType or assetName and assetType, but not both.\\n deviceName: deviceName,\\n deviceType: deviceType,\\n// assetName: assetName,\\n// assetType: assetType,\\n customerName: customerName,\\n groupName: groupName,\\n attributes: {\\n model: 'Model A',\\n serialNumber: 'SN111',\\n integrationName: metadata['integrationName']\\n manufacturer: manufacturer\\n },\\n telemetry: {\\n temperature: 42,\\n humidity: 80,\\n rawData: payloadStr\\n }\\n};\\n\\n/** Helper functions **/\\n\\nfunction decodeToString(payload) {\\n return String.fromCharCode.apply(String, payload);\\n}\\n\\nfunction decodeToJson(payload) {\\n // covert payload to string.\\n var str = decodeToString(payload);\\n\\n // parse string to JSON\\n var data = JSON.parse(str);\\n return data;\\n}\\n\\nreturn result;\"\n}\n```\n\n * 'metadata' - integration metadata; \n * 'payload' - base64 string representation of the data; \n * 'decoder' - string representation of the decoder configuration; \n * 'converter' - JSON object representing converter.\n\n## Response Body Example\n\n```json\n{\n \"output\":\"{\\\"deviceName\\\":\\\"Device A\\\",\\\"deviceType\\\":\\\"thermostat\\\",\\\"customerName\\\":\\\"customer\\\",\\\"groupName\\\":\\\"thermostat devices\\\",\\\"attributes\\\":{\\\"model\\\":\\\"Model A\\\",\\\"serialNumber\\\":\\\"SN111\\\"},\\\"telemetry\\\":{\\\"temperature\\\":42,\\\"humidity\\\":80,\\\"rawData\\\":\\\"{\\\\n \\\\\\\"data\\\\\\\": \\\\\\\"data\\\\\\\"\\\\n}\\\"}}\",\n \"error\":\"\"\n}\n```\n\n * 'output' - string representation of the output message; \n * 'error' - string representation of the error message. \n", - "operationId": "testUpLinkConverter", - "parameters": [ - { - "name": "scriptLang", - "in": "query", - "description": "Script language: JS or TBEL", - "required": false, - "schema": { - "$ref": "#/components/schemas/ScriptLanguage" - } - } + "calculated-field-controller" ], + "summary": "Test Script expression", + "description": "Execute the Script expression and return the result. The format of request: \n\n```json\n{\n \"expression\": \"var temp = 0; foreach(element: temperature.values) {temp += element.value;} var avgTemperature = temp / temperature.values.size(); var adjustedTemperature = avgTemperature + 0.1 * humidity.value; return {\\\"adjustedTemperature\\\": adjustedTemperature};\",\n \"arguments\": {\n \"temperature\": {\n \"type\": \"TS_ROLLING\",\n \"timeWindow\": {\n \"startTs\": 1739775630002,\n \"endTs\": 65432211,\n \"limit\": 5\n },\n \"values\": [\n { \"ts\": 1739775639851, \"value\": 23 },\n { \"ts\": 1739775664561, \"value\": 43 },\n { \"ts\": 1739775713079, \"value\": 15 },\n { \"ts\": 1739775999522, \"value\": 34 },\n { \"ts\": 1739776228452, \"value\": 22 }\n ]\n },\n \"humidity\": { \"type\": \"SINGLE_VALUE\", \"ts\": 1739776478057, \"value\": 23 }\n }\n}\n```\n\n Expected result JSON contains \"output\" and \"error\".\n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "testCalculatedFieldScript", "requestBody": { - "description": "A JSON value representing the input to the converter function.", + "description": "Test calculated field TBEL expression.", "content": { "application/json": { "schema": { @@ -19907,43 +19795,31 @@ ] } }, - "/api/converter/unwrap/{integrationType}": { - "post": { + "/api/calculatedField/{calculatedFieldId}": { + "get": { "tags": [ - "converter-controller" + "calculated-field-controller" ], - "summary": "Transform input raw payload to the dedicated converter data (unwrapRawPayload)", - "description": "Returns a JSON object representing the result of the unwrapped incoming raw message. \n\n## Request Body Example\n\n```json\n{\n \"metadata\":{\n },\n \"payload\":\"ewogICAgImRhdGEiOiAiZGF0YSIKfQ==\",\n}\n``` * 'metadata' - integration metadata; \n * 'payload' - JSON object representing the input raw message.\n\n## Response Body Example\n\n * 'metadata' - integration metadata enriched with the data from the input message; \n * 'payload' - base64 string representation of the payload from the unwrapped input message; \n * 'contentType' - string representation payload contentType.", - "operationId": "unwrapRawPayload", + "summary": "Get Calculated Field (getCalculatedFieldById)", + "description": "Fetch the Calculated Field object based on the provided Calculated Field Id.", + "operationId": "getCalculatedFieldById", "parameters": [ { - "name": "integrationType", + "name": "calculatedFieldId", "in": "path", - "description": "A string value representing the integration type. One of the following:\nAPACHE_PULSAR, AWS_IOT, AWS_KINESIS, AWS_SQS, AZURE_EVENT_HUB, AZURE_IOT_HUB, AZURE_SERVICE_BUS, CHIRPSTACK, COAP, CUSTOM, HTTP, IBM_WATSON_IOT, KAFKA, LORIOT, MQTT, OCEANCONNECT, OPC_UA, PUB_SUB, RABBITMQ, SIGFOX, TCP, THINGPARK, TMOBILE_IOT_CDP, TPE, TTI, TTN, TUYA, UDP", "required": true, "schema": { - "$ref": "#/components/schemas/IntegrationType" + "type": "string" } } ], - "requestBody": { - "description": "A JSON value representing the input message.", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/JsonNode" - } - } - }, - "required": true - }, "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/JsonNode" + "$ref": "#/components/schemas/CalculatedField" } } } @@ -19960,7 +19836,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -20062,21 +19938,18 @@ "ApiKeyForm": [] } ] - } - }, - "/api/converter/{converterId}": { - "get": { + }, + "delete": { "tags": [ - "converter-controller" + "calculated-field-controller" ], - "summary": "Get Converter (getConverterById)", - "description": "Fetch the Converter object based on the provided Converter Id. The server checks that the converter is owned by the same tenant. \n\n Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getConverterById", + "summary": "Delete Calculated Field (deleteCalculatedField)", + "description": "Deletes the calculated field. Referencing non-existing Calculated Field Id will cause an error.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", + "operationId": "deleteCalculatedField", "parameters": [ { - "name": "converterId", + "name": "calculatedFieldId", "in": "path", - "description": "A string value representing the converter id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { "type": "string" @@ -20085,14 +19958,7 @@ ], "responses": { "200": { - "description": "OK", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/Converter" - } - } - } + "description": "OK" }, "400": { "description": "Bad Request", @@ -20208,19 +20074,20 @@ "ApiKeyForm": [] } ] - }, - "delete": { + } + }, + "/api/calculatedField/{calculatedFieldId}/debug": { + "get": { "tags": [ - "converter-controller" + "calculated-field-controller" ], - "summary": "Delete converter (deleteConverter)", - "description": "Deletes the converter and all the relations (from and to the converter). Referencing non-existing converter Id will cause an error. If the converter is associated with the integration, it will not be allowed for deletion.\n\n Security check is performed to verify that the user has 'DELETE' permission for the entity (entities).", - "operationId": "deleteConverter", + "summary": "Get latest calculated field debug event (getLatestCalculatedFieldDebugEvent)", + "description": "Gets latest calculated field debug event for specified calculated field id. Referencing non-existing calculated field id will cause an error. \n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "getLatestCalculatedFieldDebugEvent", "parameters": [ { - "name": "converterId", + "name": "calculatedFieldId", "in": "path", - "description": "A string value representing the converter id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { "type": "string" @@ -20229,7 +20096,14 @@ ], "responses": { "200": { - "description": "OK" + "description": "OK", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/JsonNode" + } + } + } }, "400": { "description": "Bad Request", @@ -20347,59 +20221,39 @@ ] } }, - "/api/converter/{converterId}/debugIn": { + "/api/calculatedField/{calculatedFieldId}/reprocess": { "get": { "tags": [ - "converter-controller" + "calculated-field-controller" ], - "summary": "Get latest debug input event (getLatestConverterDebugInput)", - "description": "Returns a JSON object of the latest debug event representing the input message the converter processed. \n\n## Uplink Converter Debug Input Event Example\n\n```json\n{\n \"inContentType\":\"JSON\",\n \"inContent\":\"{\\\"temp\\\":40}\",\n \"inMetadata\":\"{\\\"Header:sec-ch-ua\\\":\\\"\\\\\\\"Chromium\\\\\\\";v=\\\\\\\"94\\\\\\\", \\\\\\\"Google Chrome\\\\\\\";v=\\\\\\\"94\\\\\\\", \\\\\\\";Not A Brand\\\\\\\";v=\\\\\\\"99\\\\\\\"\\\",\\\"Header:user-agent\\\":\\\"Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/94.0.4606.71 Safari/537.36\\\",\\\"integrationName\\\":\\\"Integration\\\",\\\"Header:cookie\\\":\\\"GUID=zYSs8hymSwZKv8kHALKY; redirect_to=%2F; JSESSIONID=B0A7C8E481409CE7924E738DB04F62F9\\\",\\\"Header:sec-ch-ua-platform\\\":\\\"\\\\\\\"Linux\\\\\\\"\\\",\\\"Header:accept\\\":\\\"*/*\\\",\\\"Header:origin\\\":\\\"http://localhost:8080\\\",\\\"Header:sec-fetch-site\\\":\\\"same-origin\\\",\\\"Header:connection\\\":\\\"keep-alive\\\",\\\"Header:accept-encoding\\\":\\\"gzip, deflate, br\\\",\\\"Header:content-type\\\":\\\"application/json\\\",\\\"Header:content-length\\\":\\\"16\\\",\\\"Header:sec-fetch-mode\\\":\\\"cors\\\",\\\"Header:sec-ch-ua-mobile\\\":\\\"?0\\\",\\\"Header:sec-fetch-dest\\\":\\\"empty\\\",\\\"Header:host\\\":\\\"localhost:8080\\\",\\\"Header:referer\\\":\\\"http://localhost:8080/swagger-ui.html\\\",\\\"Header:accept-language\\\":\\\"en-US,en;q=0.9,ru-RU;q=0.8,ru;q=0.7,uk;q=0.6,und;q=0.5\\\"}\"\n}\n```\n\n * 'inContentType' - content type of the message received by the integration; \n * 'inContent' - message data received; \n * 'inMetadata' - integration metadata (e.g. headers).\n\n## Downlink Converter Debug Input Event Example\n\n```json\n{\n \"inContentType\":\"JSON\",\n \"inContent\":\"{\\\"temp\\\":42,\\\"humidity\\\":77}\",\n \"inMsgType\":\"POST_TELEMETRY_REQUEST\",\n \"inMetadata\":\"{\\\"data\\\":\\\"40\\\"}\",\n \"inIntegrationMetadata\":\"{\\\"integrationName\\\":\\\"Integration\\\"}\"\n}\n```\n\n * 'inContentType' - content type of the message received by the integration; \n * 'inContent' - content of the message pushed from the rule engine; \n * 'inMsgType' - type of the message pushed from the rule engine; \n * 'inMetadata' - content of the message metadata pushed from the rule engine; \n * 'inIntegrationMetadata' - integration metadata. \n\n\n Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getLatestConverterDebugInput", + "summary": "Reprocess Calculated Field (reprocessCalculatedField)", + "description": "Reprocesses the calculated field.\n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "reprocessCalculatedField", "parameters": [ { - "name": "converterId", + "name": "calculatedFieldId", "in": "path", - "description": "A string value representing the converter id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { "type": "string" } }, { - "name": "converterType", - "in": "query", - "description": "A string value representing the converter type. One of the following:\nUPLINK, DOWNLINK", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "integrationType", - "in": "query", - "description": "A string value representing the integration type. One of the following:\nAPACHE_PULSAR, AWS_IOT, AWS_KINESIS, AWS_SQS, AZURE_EVENT_HUB, AZURE_IOT_HUB, AZURE_SERVICE_BUS, CHIRPSTACK, COAP, CUSTOM, HTTP, IBM_WATSON_IOT, KAFKA, LORIOT, MQTT, OCEANCONNECT, OPC_UA, PUB_SUB, RABBITMQ, SIGFOX, TCP, THINGPARK, TMOBILE_IOT_CDP, TPE, TTI, TTN, TUYA, UDP", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "integrationName", + "name": "startTs", "in": "query", - "description": "A string value representing the integration name. For example, 'My New Integration'", - "required": false, + "required": true, "schema": { - "type": "string" + "type": "integer", + "format": "int64" } }, { - "name": "converterVersion", + "name": "endTs", "in": "query", - "description": "Converter version.", - "required": false, + "required": true, "schema": { "type": "integer", - "format": "int32" + "format": "int64" } } ], @@ -20409,7 +20263,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/JsonNode" + "$ref": "#/components/schemas/Job" } } } @@ -20530,89 +20384,21 @@ ] } }, - "/api/converters": { + "/api/calculatedField/{calculatedFieldId}/reprocess/job": { "get": { "tags": [ - "converter-controller" + "calculated-field-controller" ], - "summary": "Get Converters (getConverters)", - "description": "Returns a page of converters owned by tenant. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\n Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getConverters", + "summary": "getLastCalculatedFieldReprocessingJob", + "operationId": "getLastCalculatedFieldReprocessingJob", "parameters": [ { - "name": "isEdgeTemplate", - "in": "query", - "description": "Fetch edge template converters", - "required": false, - "schema": { - "type": "boolean", - "default": false - } - }, - { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "string", - "minimum": 1 - } - }, - { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", + "name": "calculatedFieldId", + "in": "path", "required": true, "schema": { "type": "string", - "minimum": 0 - } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'startsWith' filter based on the converter name.", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, - "schema": { - "type": "string", - "enum": [ - "createdTime", - "name", - "type", - "debugMode" - ] - } - }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] - } - }, - { - "name": "integrationType", - "in": "query", - "description": "A string value representing the integration type. One of the following:\nAPACHE_PULSAR, AWS_IOT, AWS_KINESIS, AWS_SQS, AZURE_EVENT_HUB, AZURE_IOT_HUB, AZURE_SERVICE_BUS, CHIRPSTACK, COAP, CUSTOM, HTTP, IBM_WATSON_IOT, KAFKA, LORIOT, MQTT, OCEANCONNECT, OPC_UA, PUB_SUB, RABBITMQ, SIGFOX, TCP, THINGPARK, TMOBILE_IOT_CDP, TPE, TTI, TTN, TUYA, UDP", - "required": false, - "schema": { - "$ref": "#/components/schemas/IntegrationType" + "format": "uuid" } } ], @@ -20622,7 +20408,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataConverter" + "$ref": "#/components/schemas/Job" } } } @@ -20743,25 +20529,21 @@ ] } }, - "/api/converters/list": { + "/api/calculatedField/{calculatedFieldId}/reprocess/validate": { "get": { "tags": [ - "converter-controller" + "calculated-field-controller" ], - "summary": "Get Converters By Ids (getConvertersByIds)", - "description": "Requested converters must be owned by tenant which is performing the request. \n\n Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getConvertersByIds", + "summary": "Validate reprocessing capability of a calculated field (validateCalculatedFieldReprocessing)", + "description": "Checks whether the specified calculated field can be reprocessed. Returns a validation result indicating if reprocessing is allowed and, if not, provides a reason. \n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "validateCalculatedFieldReprocessing", "parameters": [ { - "name": "converterIds", - "in": "query", - "description": "A list of converter ids, separated by comma ','", + "name": "calculatedFieldId", + "in": "path", "required": true, "schema": { - "type": "array", - "items": { - "type": "string" - } + "type": "string" } } ], @@ -20771,10 +20553,7 @@ "content": { "application/json": { "schema": { - "type": "array", - "items": { - "$ref": "#/components/schemas/Converter" - } + "$ref": "#/components/schemas/CfReprocessingValidationResult" } } } @@ -20895,74 +20674,45 @@ ] } }, - "/api/converter/library/{integrationType}/vendors": { + "/api/calculatedField/{calculatedFieldId}/reprocessAndWait": { "get": { "tags": [ - "converter-library-controller" + "calculated-field-controller" ], - "summary": "Get vendors (getVendors)", - "description": "Returns a list of vendors for the integration type", - "operationId": "getVendors", + "summary": "Reprocess Calculated Field and wait for completion (reprocessCalculatedFieldAndWait)", + "description": "Reprocesses the calculated field and waits until the job completes or fails.\n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "reprocessCalculatedFieldAndWait", "parameters": [ { - "name": "integrationType", + "name": "calculatedFieldId", "in": "path", "required": true, - "schema": { - "$ref": "#/components/schemas/IntegrationType" - } - }, - { - "name": "converterType", - "in": "query", - "required": false, "schema": { "type": "string" } }, { - "name": "page", + "name": "startTs", "in": "query", - "required": false, + "required": true, "schema": { "type": "integer", - "format": "int32", - "default": 0 + "format": "int64" } }, { - "name": "pageSize", + "name": "endTs", "in": "query", - "required": false, + "required": true, "schema": { "type": "integer", - "format": "int32", - "default": 2147483647 - } - }, - { - "name": "loadImages", - "in": "query", - "required": false, - "schema": { - "type": "boolean", - "default": true + "format": "int64" } } ], "responses": { "200": { - "description": "OK", - "content": { - "application/json": { - "schema": { - "type": "array", - "items": { - "$ref": "#/components/schemas/Vendor" - } - } - } - } + "description": "OK" }, "400": { "description": "Bad Request", @@ -21080,66 +20830,95 @@ ] } }, - "/api/converter/library/{integrationType}/{vendorName}/models": { + "/api/calculatedField/{entityType}/{entityId}": { "get": { "tags": [ - "converter-library-controller" + "calculated-field-controller" ], - "summary": "Get vendor models (getVendorModels)", - "description": "Returns a list of models for the vendor, integration type and converter type", - "operationId": "getVendorModels", + "summary": "Get Calculated Fields by Entity Id (getCalculatedFieldsByEntityId)", + "description": "Fetch the Calculated Fields based on the provided Entity Id.", + "operationId": "getCalculatedFieldsByEntityId", "parameters": [ { - "name": "integrationType", + "name": "entityType", "in": "path", + "description": "A string value representing the entity type. For example, 'DEVICE'", "required": true, "schema": { - "$ref": "#/components/schemas/IntegrationType" + "type": "string" } }, { - "name": "vendorName", + "name": "entityId", "in": "path", + "description": "A string value representing the entity id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { "type": "string" } }, { - "name": "converterType", + "name": "pageSize", "in": "query", - "required": false, + "description": "Maximum amount of entities in a one page", + "required": true, "schema": { - "type": "string" + "type": "integer", + "format": "int32" } }, { "name": "page", "in": "query", - "required": false, + "description": "Sequence number of page starting from 0", + "required": true, "schema": { "type": "integer", - "format": "int32", - "default": 0 + "format": "int32" } }, { - "name": "pageSize", + "name": "type", "in": "query", + "description": "Calculated field type. If not specified, all types will be returned.", "required": false, "schema": { - "type": "integer", - "format": "int32", - "default": 2147483647 + "$ref": "#/components/schemas/CalculatedFieldType" } }, { - "name": "loadImages", + "name": "textSearch", "in": "query", + "description": "The case insensitive 'substring' filter based on the calculated field name.", "required": false, "schema": { - "type": "boolean", - "default": true + "type": "string" + } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string", + "enum": [ + "createdTime", + "name" + ] + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] } } ], @@ -21149,10 +20928,7 @@ "content": { "application/json": { "schema": { - "type": "array", - "items": { - "$ref": "#/components/schemas/Model" - } + "$ref": "#/components/schemas/PageDataCalculatedField" } } } @@ -21273,47 +21049,125 @@ ] } }, - "/api/converter/library/{integrationType}/{vendorName}/{model}/downlink": { + "/api/calculatedFields": { "get": { "tags": [ - "converter-library-controller" + "calculated-field-controller" ], - "summary": "Get downlink converter (getDownlinkConverter)", - "description": "Returns downlink converter body for the vendor, integration type and model", - "operationId": "getDownlinkConverter", + "summary": "Get calculated fields (getCalculatedFields)", + "description": "Fetch tenant calculated fields based on the filter.", + "operationId": "getCalculatedFields", "parameters": [ { - "name": "integrationType", - "in": "path", + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", "required": true, "schema": { - "$ref": "#/components/schemas/IntegrationType" + "type": "integer", + "format": "int32" } }, { - "name": "vendorName", - "in": "path", + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", "required": true, "schema": { - "type": "string" + "type": "integer", + "format": "int32" } }, { - "name": "model", - "in": "path", - "required": true, + "name": "types", + "in": "query", + "description": "Calculated field types filter.", + "required": false, + "schema": { + "type": "array", + "items": { + "$ref": "#/components/schemas/CalculatedFieldType" + }, + "uniqueItems": true + } + }, + { + "name": "entityType", + "in": "query", + "description": "Entity type filter. If not specified, calculated fields for all supported entity types will be returned.", + "required": false, + "schema": { + "$ref": "#/components/schemas/EntityType" + } + }, + { + "name": "entities", + "in": "query", + "description": "Entities filter. If not specified, calculated fields for entity type filter will be returned.", + "required": false, + "schema": { + "type": "array", + "items": { + "type": "string", + "format": "uuid" + }, + "uniqueItems": true + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'substring' filter based on the calculated field name.", + "required": false, "schema": { "type": "string" } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string", + "enum": [ + "createdTime", + "name" + ] + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] + } + }, + { + "name": "name", + "in": "query", + "description": "Repeatable name query parameter", + "schema": { + "type": "array", + "items": { + "type": "string" + } + } } ], "responses": { "200": { "description": "OK", "content": { - "text/plain": { + "application/json": { "schema": { - "type": "string" + "$ref": "#/components/schemas/PageDataCalculatedFieldInfo" } } } @@ -21434,47 +21288,74 @@ ] } }, - "/api/converter/library/{integrationType}/{vendorName}/{model}/downlink/metadata": { + "/api/calculatedFields/names": { "get": { "tags": [ - "converter-library-controller" + "calculated-field-controller" ], - "summary": "Get downlink converter metadata (getDownlinkConverterMetadata)", - "description": "Returns downlink converter metadata for the vendor, integration type and model", - "operationId": "getDownlinkConverterMetadata", + "summary": "Get calculated field names (getCalculatedFieldNames)", + "description": "Fetch the list of calculated field names for specified type.", + "operationId": "getCalculatedFieldNames", "parameters": [ { - "name": "integrationType", - "in": "path", + "name": "type", + "in": "query", + "description": "Calculated field type filter.", "required": true, "schema": { - "$ref": "#/components/schemas/IntegrationType" + "$ref": "#/components/schemas/CalculatedFieldType" } }, { - "name": "vendorName", - "in": "path", + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", "required": true, "schema": { - "type": "string" + "type": "integer", + "format": "int32" } }, { - "name": "model", - "in": "path", + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'substring' filter based on the calculated field name.", + "required": false, "schema": { "type": "string" } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] + } } ], "responses": { "200": { "description": "OK", "content": { - "text/plain": { + "application/json": { "schema": { - "type": "string" + "$ref": "#/components/schemas/PageDataString" } } } @@ -21595,34 +21476,19 @@ ] } }, - "/api/converter/library/{integrationType}/{vendorName}/{model}/downlink/payload": { + "/api/component/{componentDescriptorClazz}": { "get": { "tags": [ - "converter-library-controller" + "component-descriptor-controller" ], - "summary": "Get downlink payload (getDownlinkPayload)", - "description": "Returns payload example for the downlink converter for the vendor, integration type and model", - "operationId": "getDownlinkPayload", + "summary": "Get Component Descriptor (getComponentDescriptorByClazz)", + "description": "Gets the Component Descriptor object using class name from the path parameters. Each Component Descriptor represents configuration of specific rule node (e.g. 'Save Timeseries' or 'Send Email'.). The Component Descriptors are used by the rule chain Web UI to build the configuration forms for the rule nodes. The Component Descriptors are discovered at runtime by scanning the class path and searching for @RuleNode annotation. Once discovered, the up to date list of descriptors is persisted to the database.\n\nAvailable for users with 'SYS_ADMIN' or 'TENANT_ADMIN' authority.", + "operationId": "getComponentDescriptorByClazz", "parameters": [ { - "name": "integrationType", - "in": "path", - "required": true, - "schema": { - "$ref": "#/components/schemas/IntegrationType" - } - }, - { - "name": "vendorName", - "in": "path", - "required": true, - "schema": { - "type": "string" - } - }, - { - "name": "model", + "name": "componentDescriptorClazz", "in": "path", + "description": "Component Descriptor class name", "required": true, "schema": { "type": "string" @@ -21633,9 +21499,9 @@ "200": { "description": "OK", "content": { - "text/plain": { + "application/json": { "schema": { - "type": "string" + "$ref": "#/components/schemas/ComponentDescriptor" } } } @@ -21756,37 +21622,38 @@ ] } }, - "/api/converter/library/{integrationType}/{vendorName}/{model}/uplink": { + "/api/components": { "get": { "tags": [ - "converter-library-controller" + "component-descriptor-controller" ], - "summary": "Get uplink converter (getUplinkConverter)", - "description": "Returns uplink converter body for the vendor, integration type and model", - "operationId": "getUplinkConverter", + "summary": "Get Component Descriptors (getComponentDescriptorsByTypes)", + "description": "Gets the Component Descriptors using coma separated list of rule node types and optional rule chain type request parameters. Each Component Descriptor represents configuration of specific rule node (e.g. 'Save Timeseries' or 'Send Email'.). The Component Descriptors are used by the rule chain Web UI to build the configuration forms for the rule nodes. The Component Descriptors are discovered at runtime by scanning the class path and searching for @RuleNode annotation. Once discovered, the up to date list of descriptors is persisted to the database.\n\nAvailable for users with 'SYS_ADMIN' or 'TENANT_ADMIN' authority.", + "operationId": "getComponentDescriptorsByTypes", "parameters": [ { - "name": "integrationType", - "in": "path", - "required": true, - "schema": { - "$ref": "#/components/schemas/IntegrationType" - } - }, - { - "name": "vendorName", - "in": "path", + "name": "componentTypes", + "in": "query", + "description": "List of types of the Rule Nodes, (ENRICHMENT, FILTER, TRANSFORMATION, ACTION or EXTERNAL)", "required": true, "schema": { - "type": "string" + "type": "array", + "items": { + "type": "string" + } } }, { - "name": "model", - "in": "path", - "required": true, + "name": "ruleChainType", + "in": "query", + "description": "Type of the Rule Chain", + "required": false, "schema": { - "type": "string" + "type": "string", + "enum": [ + "CORE", + "EDGE" + ] } } ], @@ -21794,9 +21661,12 @@ "200": { "description": "OK", "content": { - "text/plain": { + "application/json": { "schema": { - "type": "string" + "type": "array", + "items": { + "$ref": "#/components/schemas/ComponentDescriptor" + } } } } @@ -21917,37 +21787,42 @@ ] } }, - "/api/converter/library/{integrationType}/{vendorName}/{model}/uplink/metadata": { + "/api/components/{componentType}": { "get": { "tags": [ - "converter-library-controller" + "component-descriptor-controller" ], - "summary": "Get uplink converter metadata (getUplinkConverterMetadata)", - "description": "Returns uplink converter metadata for the vendor, integration type and model", - "operationId": "getUplinkConverterMetadata", + "summary": "Get Component Descriptors (getComponentDescriptorsByType)", + "description": "Gets the Component Descriptors using rule node type and optional rule chain type request parameters. Each Component Descriptor represents configuration of specific rule node (e.g. 'Save Timeseries' or 'Send Email'.). The Component Descriptors are used by the rule chain Web UI to build the configuration forms for the rule nodes. The Component Descriptors are discovered at runtime by scanning the class path and searching for @RuleNode annotation. Once discovered, the up to date list of descriptors is persisted to the database.\n\nAvailable for users with 'SYS_ADMIN' or 'TENANT_ADMIN' authority.", + "operationId": "getComponentDescriptorsByType", "parameters": [ { - "name": "integrationType", - "in": "path", - "required": true, - "schema": { - "$ref": "#/components/schemas/IntegrationType" - } - }, - { - "name": "vendorName", + "name": "componentType", "in": "path", + "description": "Type of the Rule Node", "required": true, "schema": { - "type": "string" + "type": "string", + "enum": [ + "ENRICHMENT", + "FILTER", + "TRANSFORMATION", + "ACTION", + "EXTERNAL" + ] } }, { - "name": "model", - "in": "path", - "required": true, + "name": "ruleChainType", + "in": "query", + "description": "Type of the Rule Chain", + "required": false, "schema": { - "type": "string" + "type": "string", + "enum": [ + "CORE", + "EDGE" + ] } } ], @@ -21955,9 +21830,12 @@ "200": { "description": "OK", "content": { - "text/plain": { + "application/json": { "schema": { - "type": "string" + "type": "array", + "items": { + "$ref": "#/components/schemas/ComponentDescriptor" + } } } } @@ -22078,47 +21956,32 @@ ] } }, - "/api/converter/library/{integrationType}/{vendorName}/{model}/uplink/payload": { - "get": { + "/api/converter": { + "post": { "tags": [ - "converter-library-controller" + "converter-controller" ], - "summary": "Get uplink payload (getUplinkPayload)", - "description": "Returns payload example for the uplink converter for the vendor, integration type and model", - "operationId": "getUplinkPayload", - "parameters": [ - { - "name": "integrationType", - "in": "path", - "required": true, - "schema": { - "$ref": "#/components/schemas/IntegrationType" - } - }, - { - "name": "vendorName", - "in": "path", - "required": true, - "schema": { - "type": "string" + "summary": "Create Or Update Converter (saveConverter)", + "description": "Create or update the Converter. When creating converter, platform generates Converter Id as [time-based UUID](https://en.wikipedia.org/wiki/Universally_unique_identifier#Version_1_(date-time_and_MAC_address)). The newly created converter id will be present in the response. Specify existing Converter id to update the converter. Referencing non-existing converter Id will cause 'Not Found' error. Converter name is unique in the scope of tenant. \n\n# Converter Configuration\n\nConverter configuration (**'configuration'** field) is the JSON object that should contain one of two possible fields: **'decoder'** or **'encoder'**. The former is used when the converter has UPLINK type, the latter is used - when DOWNLINK type. It can contain both 'decoder' and 'encoder' fields, when the correct one is specified for the appropriate converter type, another one can be set to 'null'. See the examples of each one below. \n\n## Uplink Converter Configuration\n\n***Default converter may be different, depending on integration type***.\n\n```json\n{\n \"decoder\":\"// Decode an uplink message from a buffer\\n// payload - array of bytes\\n// metadata - key/value object\\n\\n/** Decoder **/\\n\\n// decode payload to string\\nvar payloadStr = decodeToString(payload);\\n\\n// decode payload to JSON\\n// var data = decodeToJson(payload);\\n\\nvar deviceName = 'Device A';\\nvar deviceType = 'thermostat';\\nvar customerName = 'customer';\\nvar groupName = 'thermostat devices';\\nvar manufacturer = 'Example corporation';\\n// use assetName and assetType instead of deviceName and deviceType\\n// to automatically create assets instead of devices.\\n// var assetName = 'Asset A';\\n// var assetType = 'building';\\n\\n// Result object with device/asset attributes/telemetry data\\nvar result = {\\n// Use deviceName and deviceType or assetName and assetType, but not both.\\n deviceName: deviceName,\\n deviceType: deviceType,\\n// assetName: assetName,\\n// assetType: assetType,\\n customerName: customerName,\\n groupName: groupName,\\n contentAwareAttributeKeys: ['manufacturer'],\\n attributes: {\\n model: 'Model A',\\n serialNumber: 'SN111',\\n integrationName: metadata['integrationName'],\\n manufacturer: manufacturer\\n },\\n telemetry: {\\n temperature: 42,\\n humidity: 80,\\n rawData: payloadStr\\n }\\n};\\n\\n/** Helper functions **/\\n\\nfunction decodeToString(payload) {\\n return String.fromCharCode.apply(String, payload);\\n}\\n\\nfunction decodeToJson(payload) {\\n // covert payload to string.\\n var str = decodeToString(payload);\\n\\n // parse string to JSON\\n var data = JSON.parse(str);\\n return data;\\n}\\n\\nreturn result;\",\n \"encoder\":null\n}\n```\n\nDecoder field in the more readable form:\n\n```text\n// Decode an uplink message from a buffer\n// payload - array of bytes\n// metadata - key/value object\n\n/** Decoder **/\n\n// decode payload to string\nvar payloadStr = decodeToString(payload);\n\n// decode payload to JSON\n// var data = decodeToJson(payload);\n\nvar deviceName = 'Device A';\nvar deviceType = 'thermostat';\nvar customerName = 'customer';\nvar groupName = 'thermostat devices';\nvar manufacturer = 'Example corporation';\n// use assetName and assetType instead of deviceName and deviceType\n// to automatically create assets instead of devices.\n// var assetName = 'Asset A';\n// var assetType = 'building';\n\n// Result object with device/asset attributes/telemetry data\nvar result = {\n// Use deviceName and deviceType or assetName and assetType, but not both.\n deviceName: deviceName,\n deviceType: deviceType,\n// assetName: assetName,\n// assetType: assetType,\n customerName: customerName,\n groupName: groupName,\n attributes: {\n model: 'Model A',\n serialNumber: 'SN111',\n integrationName: metadata['integrationName']\n manufacturer: manufacturer,\n },\n telemetry: {\n temperature: 42,\n humidity: 80,\n rawData: payloadStr\n }\n};\n\n/** Helper functions **/\n\nfunction decodeToString(payload) {\n return String.fromCharCode.apply(String, payload);\n}\n\nfunction decodeToJson(payload) {\n // covert payload to string.\n var str = decodeToString(payload);\n\n // parse string to JSON\n var data = JSON.parse(str);\n return data;\n}\n\nreturn result;\n```\n\n## Downlink Converter Configuration\n\n```json\n{\n \"decoder\":null,\n \"encoder\":\"// Encode downlink data from incoming Rule Engine message\\n\\n// msg - JSON message payload downlink message json\\n// msgType - type of message, for ex. 'ATTRIBUTES_UPDATED', 'POST_TELEMETRY_REQUEST', etc.\\n// metadata - list of key-value pairs with additional data about the message\\n// integrationMetadata - list of key-value pairs with additional data defined in Integration executing this converter\\n\\n/** Encoder **/\\n\\nvar data = {};\\n\\n// Process data from incoming message and metadata\\n\\ndata.tempFreq = msg.temperatureUploadFrequency;\\ndata.humFreq = msg.humidityUploadFrequency;\\n\\ndata.devSerialNumber = metadata['ss_serialNumber'];\\n\\n// Result object with encoded downlink payload\\nvar result = {\\n\\n // downlink data content type: JSON, TEXT or BINARY (base64 format)\\n contentType: \\\"JSON\\\",\\n\\n // downlink data\\n data: JSON.stringify(data),\\n\\n // Optional metadata object presented in key/value format\\n metadata: {\\n topic: metadata['deviceType']+'/'+metadata['deviceName']+'/upload'\\n }\\n\\n};\\n\\nreturn result;\"\n}\n```\n\nEncoder field in the more readable form:\n\n```text\n// Encode downlink data from incoming Rule Engine message\n\n// msg - JSON message payload downlink message json\n// msgType - type of message, for ex. 'ATTRIBUTES_UPDATED', 'POST_TELEMETRY_REQUEST', etc.\n// metadata - list of key-value pairs with additional data about the message\n// integrationMetadata - list of key-value pairs with additional data defined in Integration executing this converter\n\n/** Encoder **/\n\nvar data = {};\n\n// Process data from incoming message and metadata\n\ndata.tempFreq = msg.temperatureUploadFrequency;\ndata.humFreq = msg.humidityUploadFrequency;\n\ndata.devSerialNumber = metadata['ss_serialNumber'];\n\n// Result object with encoded downlink payload\nvar result = {\n\n // downlink data content type: JSON, TEXT or BINARY (base64 format)\n contentType: \"JSON\",\n\n // downlink data\n data: JSON.stringify(data),\n\n // Optional metadata object presented in key/value format\n metadata: {\n topic: metadata['deviceType']+'/'+metadata['deviceName']+'/upload'\n }\n\n};\n\nreturn result;\n```\n\nRemove 'id', 'tenantId' from the request body example (below) to create new converter entity. \n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "saveConverter", + "requestBody": { + "description": "A JSON value representing the converter.", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/Converter" + } } }, - { - "name": "model", - "in": "path", - "required": true, - "schema": { - "type": "string" - } - } - ], + "required": true + }, "responses": { "200": { "description": "OK", "content": { - "text/plain": { + "application/json": { "schema": { - "type": "string" + "$ref": "#/components/schemas/Converter" } } } @@ -22135,7 +21998,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -22239,31 +22102,43 @@ ] } }, - "/api/customMenu": { - "get": { + "/api/converter/testDownLink": { + "post": { "tags": [ - "custom-menu-controller" + "converter-controller" ], - "summary": "Get end-user Custom Menu configuration (getCustomMenu)", - "description": "Fetch the Custom Menu configuration object for the authorized user. The custom menu is configured in the white labeling parameters and has one of three user scopes:SYSTEM, TENANT, CUSTOMER and four assignee type: NO_ASSIGN, ALL, CUSTOMERS, USERS.There are three default (assignee type: ALL) menus configured on the system level for each scope and if no other menu is configured for user, system configuration of the corresponding scope will be applied.If a custom menu with assignee type ALL is configured on the tenant level, it overrides the menu configuration of the corresponding scope on the system level. If a custom menu with assignee type USER_GROUPS is configured on the tenant level, it overrides default tenant menu.If a custom menu with assignee type CUSTOMERS is configured on tenant level for specific customer, it will be applied to all customer users.If a custom menu with assignee type ALL is configured on the customer level, it overrides the menu assigned on tenant level.If a custom menu with assignee type USER_GROUPS is configured on the customer level, it overrides default customer menu.If a custom menu is assigned to specific user, it overrides all other configuration.", - "operationId": "getCustomMenu", + "summary": "Test converter function (testDownLinkConverter)", + "description": "Returns a JSON object representing the result of the processed incoming message. \n\n## Request Body Example\n\n```json\n{\n \"metadata\":{\n \"data\":\"40\"\n },\n \"msg\":\"{\\n \\\"temp\\\": 42,\\n \\\"humidity\\\": 77\\n}\",\n \"msgType\":\"POST_TELEMETRY_REQUEST\",\n \"integrationMetadata\":{\n \"integrationName\":\"Integration\"\n },\n \"encoder\":\"// Encode downlink data from incoming Rule Engine message\\n\\n// msg - JSON message payload downlink message json\\n// msgType - type of message, for ex. 'ATTRIBUTES_UPDATED', 'POST_TELEMETRY_REQUEST', etc.\\n// metadata - list of key-value pairs with additional data about the message\\n// integrationMetadata - list of key-value pairs with additional data defined in Integration executing this converter\\n\\n/** Encoder **/\\n\\nvar data = {};\\n\\n// Process data from incoming message and metadata\\n\\ndata.tempValue = msg.temp;\\ndata.humValue = msg.humidity;\\n\\ndata.devSerialNumber = metadata['ss_serialNumber'];\\n\\n// Result object with encoded downlink payload\\nvar result = {\\n\\n // downlink data content type: JSON, TEXT or BINARY (base64 format)\\n contentType: \\\"JSON\\\",\\n\\n // downlink data\\n data: JSON.stringify(data),\\n\\n // Optional metadata object presented in key/value format\\n metadata: {\\n topic: metadata['deviceType']+'/'+metadata['deviceName']+'/upload'\\n }\\n\\n};\\n\\nreturn result;\"\n}\n```\n\n * 'metadata' - message metadata pushed from the rule engine; \n * 'msg' - message data pushed from the rule engine; \n * 'msgType' - type of the message pushed from the rule engine; \n * 'integrationMetadata' - integration metadata object; \n * 'encoder' - string representation of the encoder configuration.\n\n## Response Body Example\n\n```json\n{\n \"contentType\":\"JSON\",\n \"data\":\"{\\\"tempValue\\\":42,\\\"humValue\\\":77}\",\n \"metadata\":{\n \"topic\":\"sensor/Temp Sensor/upload\"\n }\n}\n```\n\n * 'contentType' - downlink data content type; \n * 'data' - downlink data; \n * 'metadata' - optional metadata object. \n", + "operationId": "testDownLinkConverter", "parameters": [ { - "name": "If-None-Match", - "in": "header", + "name": "scriptLang", + "in": "query", + "description": "Script language: JS or TBEL", "required": false, "schema": { - "type": "string" + "$ref": "#/components/schemas/ScriptLanguage" } } ], + "requestBody": { + "description": "A JSON value representing the input to the converter function.", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/JsonNode" + } + } + }, + "required": true + }, "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/CustomMenuConfig" + "$ref": "#/components/schemas/JsonNode" } } } @@ -22280,7 +22155,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -22382,42 +22257,33 @@ "ApiKeyForm": [] } ] - }, + } + }, + "/api/converter/testUpLink": { "post": { "tags": [ - "custom-menu-controller" + "converter-controller" ], - "summary": "Create Custom Menu (createCustomMenu)", - "description": "The api is designed to create Custom Menu without configuration. Is not applicable for update.\n\nSecurity check is performed to verify that the user has 'WRITE' permission for the custom menu with specified id.", - "operationId": "createCustomMenu", + "summary": "Test converter function (testUpLinkConverter)", + "description": "Returns a JSON object representing the result of the processed incoming message. \n\n## Request Body Example\n\n```json\n{\n \"metadata\":{\n },\n \"payload\":\"ewogICAgImRhdGEiOiAiZGF0YSIKfQ==\",\n \"decoder\":\"// Decode an uplink message from a buffer\\n// payload - array of bytes\\n// metadata - key/value object\\n\\n/** Decoder **/\\n\\n// decode payload to string\\nvar payloadStr = decodeToString(payload);\\n\\n// decode payload to JSON\\n// var data = decodeToJson(payload);\\n\\nvar deviceName = 'Device A';\\nvar deviceType = 'thermostat';\\nvar customerName = 'customer';\\nvar groupName = 'thermostat devices';\\nvar manufacturer = 'Example corporation';\\n// use assetName and assetType instead of deviceName and deviceType\\n// to automatically create assets instead of devices.\\n// var assetName = 'Asset A';\\n// var assetType = 'building';\\n\\n// Result object with device/asset attributes/telemetry data\\nvar result = {\\n// Use deviceName and deviceType or assetName and assetType, but not both.\\n deviceName: deviceName,\\n deviceType: deviceType,\\n// assetName: assetName,\\n// assetType: assetType,\\n customerName: customerName,\\n groupName: groupName,\\n attributes: {\\n model: 'Model A',\\n serialNumber: 'SN111',\\n integrationName: metadata['integrationName']\\n manufacturer: manufacturer\\n },\\n telemetry: {\\n temperature: 42,\\n humidity: 80,\\n rawData: payloadStr\\n }\\n};\\n\\n/** Helper functions **/\\n\\nfunction decodeToString(payload) {\\n return String.fromCharCode.apply(String, payload);\\n}\\n\\nfunction decodeToJson(payload) {\\n // covert payload to string.\\n var str = decodeToString(payload);\\n\\n // parse string to JSON\\n var data = JSON.parse(str);\\n return data;\\n}\\n\\nreturn result;\"\n}\n```\n\n * 'metadata' - integration metadata; \n * 'payload' - base64 string representation of the data; \n * 'decoder' - string representation of the decoder configuration; \n * 'converter' - JSON object representing converter.\n\n## Response Body Example\n\n```json\n{\n \"output\":\"{\\\"deviceName\\\":\\\"Device A\\\",\\\"deviceType\\\":\\\"thermostat\\\",\\\"customerName\\\":\\\"customer\\\",\\\"groupName\\\":\\\"thermostat devices\\\",\\\"attributes\\\":{\\\"model\\\":\\\"Model A\\\",\\\"serialNumber\\\":\\\"SN111\\\"},\\\"telemetry\\\":{\\\"temperature\\\":42,\\\"humidity\\\":80,\\\"rawData\\\":\\\"{\\\\n \\\\\\\"data\\\\\\\": \\\\\\\"data\\\\\\\"\\\\n}\\\"}}\",\n \"error\":\"\"\n}\n```\n\n * 'output' - string representation of the output message; \n * 'error' - string representation of the error message. \n", + "operationId": "testUpLinkConverter", "parameters": [ { - "name": "assignToList", - "in": "query", - "description": "A list of entity ids, separated by comma ','", - "required": false, - "schema": { - "type": "array", - "items": { - "type": "string" - } - } - }, - { - "name": "force", + "name": "scriptLang", "in": "query", - "description": "Use force if you want to create default menu that conflicts with the existing one (old one will be update NO_ASSIGN assignee type)", + "description": "Script language: JS or TBEL", "required": false, "schema": { - "type": "boolean" + "$ref": "#/components/schemas/ScriptLanguage" } } ], "requestBody": { + "description": "A JSON value representing the input to the converter function.", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/CustomMenuInfo" + "$ref": "#/components/schemas/JsonNode" } } }, @@ -22429,7 +22295,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/CustomMenu" + "$ref": "#/components/schemas/JsonNode" } } } @@ -22550,96 +22416,43 @@ ] } }, - "/api/customMenu/infos": { - "get": { + "/api/converter/unwrap/{integrationType}": { + "post": { "tags": [ - "custom-menu-controller" + "converter-controller" ], - "summary": "Get all custom menus configured at user level (getCustomMenuInfos)", - "description": "Returns a page of custom menu info objects owned by the tenant or the customer of a current user, scope and assigneeType request parameters can be used to filter the result.\n\nSecurity check is performed to verify that the user has 'READ' permission for the white labeling resource.", - "operationId": "getCustomMenuInfos", + "summary": "Transform input raw payload to the dedicated converter data (unwrapRawPayload)", + "description": "Returns a JSON object representing the result of the unwrapped incoming raw message. \n\n## Request Body Example\n\n```json\n{\n \"metadata\":{\n },\n \"payload\":\"ewogICAgImRhdGEiOiAiZGF0YSIKfQ==\",\n}\n``` * 'metadata' - integration metadata; \n * 'payload' - JSON object representing the input raw message.\n\n## Response Body Example\n\n * 'metadata' - integration metadata enriched with the data from the input message; \n * 'payload' - base64 string representation of the payload from the unwrapped input message; \n * 'contentType' - string representation payload contentType.", + "operationId": "unwrapRawPayload", "parameters": [ { - "name": "scope", - "in": "query", - "description": "Custom menu scope.", - "required": false, - "schema": { - "$ref": "#/components/schemas/CMScope" - } - }, - { - "name": "assigneeType", - "in": "query", - "description": "Custom menu assignee type.", - "required": false, - "schema": { - "$ref": "#/components/schemas/CMAssigneeType" - } - }, - { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", + "name": "integrationType", + "in": "path", + "description": "A string value representing the integration type. One of the following:\nAPACHE_PULSAR, AWS_IOT, AWS_KINESIS, AWS_SQS, AZURE_EVENT_HUB, AZURE_IOT_HUB, AZURE_SERVICE_BUS, CHIRPSTACK, COAP, CUSTOM, HTTP, IBM_WATSON_IOT, KAFKA, LORIOT, MQTT, OCEANCONNECT, OPC_UA, PUB_SUB, RABBITMQ, SIGFOX, TCP, THINGPARK, TMOBILE_IOT_CDP, TPE, TTI, TTN, TUYA, UDP", "required": true, "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'substring' filter based on the custom menu name.", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, - "schema": { - "type": "string", - "enum": [ - "createdTime", - "title" - ] - } - }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] + "$ref": "#/components/schemas/IntegrationType" } } ], + "requestBody": { + "description": "A JSON value representing the input message.", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/JsonNode" + } + } + }, + "required": true + }, "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataCustomMenuInfo" + "$ref": "#/components/schemas/JsonNode" } } } @@ -22656,7 +22469,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -22760,32 +22573,22 @@ ] } }, - "/api/customMenu/{customMenuId}": { - "delete": { + "/api/converter/{converterId}": { + "get": { "tags": [ - "custom-menu-controller" + "converter-controller" ], - "summary": "Delete custom menu (deleteCustomMenu)", - "description": "Deletes the custom menu based on the provided Custom Menu Id. Referencing non-existing custom menu Id will cause an error. If the custom menu is assigned to the list of users or customers bad request is returned.To delete a custom menu that has assignee list set 'force' request param to true ", - "operationId": "deleteCustomMenu", + "summary": "Get Converter (getConverterById)", + "description": "Fetch the Converter object based on the provided Converter Id. The server checks that the converter is owned by the same tenant. \n\n Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getConverterById", "parameters": [ { - "name": "customMenuId", + "name": "converterId", "in": "path", - "description": "A string value representing the custom menu id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "description": "A string value representing the converter id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { - "type": "string", - "format": "uuid" - } - }, - { - "name": "force", - "in": "query", - "description": "Force set to true will unassign menu before deletion", - "required": false, - "schema": { - "type": "boolean" + "type": "string" } } ], @@ -22795,7 +22598,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/CustomMenuDeleteResult" + "$ref": "#/components/schemas/Converter" } } } @@ -22914,41 +22717,28 @@ "ApiKeyForm": [] } ] - } - }, - "/api/customMenu/{customMenuId}/assigneeList": { - "get": { + }, + "delete": { "tags": [ - "custom-menu-controller" + "converter-controller" ], - "summary": "Get Custom Menu assignee list (getCustomMenuAssigneeList)", - "description": "Fetch the list of Entity Info objects that represents users or customers, or empty list if custom menu is not assigned or has NO_ASSIGN/ALL assignee type.\n\nSecurity check is performed to verify that the user has 'READ' permission for the custom menu with specified id.", - "operationId": "getCustomMenuAssigneeList", + "summary": "Delete converter (deleteConverter)", + "description": "Deletes the converter and all the relations (from and to the converter). Referencing non-existing converter Id will cause an error. If the converter is associated with the integration, it will not be allowed for deletion.\n\n Security check is performed to verify that the user has 'DELETE' permission for the entity (entities).", + "operationId": "deleteConverter", "parameters": [ { - "name": "customMenuId", + "name": "converterId", "in": "path", - "description": "A string value representing the custom menu id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "description": "A string value representing the converter id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { - "type": "string", - "format": "uuid" + "type": "string" } } ], "responses": { "200": { - "description": "OK", - "content": { - "application/json": { - "schema": { - "type": "array", - "items": { - "$ref": "#/components/schemas/EntityInfo" - } - } - } - } + "description": "OK" }, "400": { "description": "Bad Request", @@ -23066,23 +22856,59 @@ ] } }, - "/api/customMenu/{customMenuId}/config": { + "/api/converter/{converterId}/debugIn": { "get": { "tags": [ - "custom-menu-controller" + "converter-controller" ], - "summary": "Get Custom Menu configuration by id (getCustomMenuConfig)", - "description": "Fetch the Custom Menu configuration based on the provided Custom Menu Id. \n\nSecurity check is performed to verify that the user has 'READ' permission for the custom menu with specified id.", - "operationId": "getCustomMenuConfig", + "summary": "Get latest debug input event (getLatestConverterDebugInput)", + "description": "Returns a JSON object of the latest debug event representing the input message the converter processed. \n\n## Uplink Converter Debug Input Event Example\n\n```json\n{\n \"inContentType\":\"JSON\",\n \"inContent\":\"{\\\"temp\\\":40}\",\n \"inMetadata\":\"{\\\"Header:sec-ch-ua\\\":\\\"\\\\\\\"Chromium\\\\\\\";v=\\\\\\\"94\\\\\\\", \\\\\\\"Google Chrome\\\\\\\";v=\\\\\\\"94\\\\\\\", \\\\\\\";Not A Brand\\\\\\\";v=\\\\\\\"99\\\\\\\"\\\",\\\"Header:user-agent\\\":\\\"Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/94.0.4606.71 Safari/537.36\\\",\\\"integrationName\\\":\\\"Integration\\\",\\\"Header:cookie\\\":\\\"GUID=zYSs8hymSwZKv8kHALKY; redirect_to=%2F; JSESSIONID=B0A7C8E481409CE7924E738DB04F62F9\\\",\\\"Header:sec-ch-ua-platform\\\":\\\"\\\\\\\"Linux\\\\\\\"\\\",\\\"Header:accept\\\":\\\"*/*\\\",\\\"Header:origin\\\":\\\"http://localhost:8080\\\",\\\"Header:sec-fetch-site\\\":\\\"same-origin\\\",\\\"Header:connection\\\":\\\"keep-alive\\\",\\\"Header:accept-encoding\\\":\\\"gzip, deflate, br\\\",\\\"Header:content-type\\\":\\\"application/json\\\",\\\"Header:content-length\\\":\\\"16\\\",\\\"Header:sec-fetch-mode\\\":\\\"cors\\\",\\\"Header:sec-ch-ua-mobile\\\":\\\"?0\\\",\\\"Header:sec-fetch-dest\\\":\\\"empty\\\",\\\"Header:host\\\":\\\"localhost:8080\\\",\\\"Header:referer\\\":\\\"http://localhost:8080/swagger-ui.html\\\",\\\"Header:accept-language\\\":\\\"en-US,en;q=0.9,ru-RU;q=0.8,ru;q=0.7,uk;q=0.6,und;q=0.5\\\"}\"\n}\n```\n\n * 'inContentType' - content type of the message received by the integration; \n * 'inContent' - message data received; \n * 'inMetadata' - integration metadata (e.g. headers).\n\n## Downlink Converter Debug Input Event Example\n\n```json\n{\n \"inContentType\":\"JSON\",\n \"inContent\":\"{\\\"temp\\\":42,\\\"humidity\\\":77}\",\n \"inMsgType\":\"POST_TELEMETRY_REQUEST\",\n \"inMetadata\":\"{\\\"data\\\":\\\"40\\\"}\",\n \"inIntegrationMetadata\":\"{\\\"integrationName\\\":\\\"Integration\\\"}\"\n}\n```\n\n * 'inContentType' - content type of the message received by the integration; \n * 'inContent' - content of the message pushed from the rule engine; \n * 'inMsgType' - type of the message pushed from the rule engine; \n * 'inMetadata' - content of the message metadata pushed from the rule engine; \n * 'inIntegrationMetadata' - integration metadata. \n\n\n Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getLatestConverterDebugInput", "parameters": [ { - "name": "customMenuId", + "name": "converterId", "in": "path", - "description": "A string value representing the custom menu id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "description": "A string value representing the converter id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { - "type": "string", - "format": "uuid" + "type": "string" + } + }, + { + "name": "converterType", + "in": "query", + "description": "A string value representing the converter type. One of the following:\nUPLINK, DOWNLINK", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "integrationType", + "in": "query", + "description": "A string value representing the integration type. One of the following:\nAPACHE_PULSAR, AWS_IOT, AWS_KINESIS, AWS_SQS, AZURE_EVENT_HUB, AZURE_IOT_HUB, AZURE_SERVICE_BUS, CHIRPSTACK, COAP, CUSTOM, HTTP, IBM_WATSON_IOT, KAFKA, LORIOT, MQTT, OCEANCONNECT, OPC_UA, PUB_SUB, RABBITMQ, SIGFOX, TCP, THINGPARK, TMOBILE_IOT_CDP, TPE, TTI, TTN, TUYA, UDP", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "integrationName", + "in": "query", + "description": "A string value representing the integration name. For example, 'My New Integration'", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "converterVersion", + "in": "query", + "description": "Converter version.", + "required": false, + "schema": { + "type": "integer", + "format": "int32" } } ], @@ -23092,7 +22918,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/CustomMenuConfig" + "$ref": "#/components/schemas/JsonNode" } } } @@ -23211,43 +23037,101 @@ "ApiKeyForm": [] } ] - }, - "put": { + } + }, + "/api/converters": { + "get": { "tags": [ - "custom-menu-controller" + "converter-controller" ], - "summary": "Update Custom Menu configuration based on the provided Custom Menu Id (updateCustomMenuConfig)", - "description": "\n\nSecurity check is performed to verify that the user has 'WRITE' permission for the custom menu with specified id.", - "operationId": "updateCustomMenuConfig", + "summary": "Get Converters (getConverters)", + "description": "Returns a page of converters owned by tenant. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\n Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getConverters", "parameters": [ { - "name": "customMenuId", - "in": "path", - "description": "A string value representing the custom menu id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "name": "isEdgeTemplate", + "in": "query", + "description": "Fetch edge template converters", + "required": false, + "schema": { + "type": "boolean", + "default": false + } + }, + { + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", "required": true, "schema": { "type": "string", - "format": "uuid" + "minimum": 1 } - } - ], - "requestBody": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/CustomMenuConfig" - } + }, + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", + "required": true, + "schema": { + "type": "string", + "minimum": 0 } }, - "required": true - }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'startsWith' filter based on the converter name.", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string", + "enum": [ + "createdTime", + "name", + "type", + "debugMode" + ] + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] + } + }, + { + "name": "integrationType", + "in": "query", + "description": "A string value representing the integration type. One of the following:\nAPACHE_PULSAR, AWS_IOT, AWS_KINESIS, AWS_SQS, AZURE_EVENT_HUB, AZURE_IOT_HUB, AZURE_SERVICE_BUS, CHIRPSTACK, COAP, CUSTOM, HTTP, IBM_WATSON_IOT, KAFKA, LORIOT, MQTT, OCEANCONNECT, OPC_UA, PUB_SUB, RABBITMQ, SIGFOX, TCP, THINGPARK, TMOBILE_IOT_CDP, TPE, TTI, TTN, TUYA, UDP", + "required": false, + "schema": { + "$ref": "#/components/schemas/IntegrationType" + } + } + ], "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/CustomMenu" + "$ref": "#/components/schemas/PageDataConverter" } } } @@ -23368,23 +23252,25 @@ ] } }, - "/api/customMenu/{customMenuId}/info": { + "/api/converters/list": { "get": { "tags": [ - "custom-menu-controller" + "converter-controller" ], - "summary": "Get Custom Menu Info (getCustomMenuInfoById)", - "description": "Fetch the Custom Menu Info object based on the provided Custom Menu Id. \n\nSecurity check is performed to verify that the user has 'READ' permission for the custom menu with specified id.", - "operationId": "getCustomMenuInfoById", + "summary": "Get Converters By Ids (getConvertersByIds)", + "description": "Requested converters must be owned by tenant which is performing the request. \n\n Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getConvertersByIds", "parameters": [ { - "name": "customMenuId", - "in": "path", - "description": "A string value representing the custom menu id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "name": "converterIds", + "in": "query", + "description": "A list of converter ids, separated by comma ','", "required": true, "schema": { - "type": "string", - "format": "uuid" + "type": "array", + "items": { + "type": "string" + } } } ], @@ -23394,7 +23280,10 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/CustomMenuInfo" + "type": "array", + "items": { + "$ref": "#/components/schemas/Converter" + } } } } @@ -23515,40 +23404,74 @@ ] } }, - "/api/customMenu/{customMenuId}/name": { - "put": { + "/api/converter/library/{integrationType}/vendors": { + "get": { "tags": [ - "custom-menu-controller" + "converter-library-controller" ], - "summary": "Update Custom Menu name based on the provided Custom Menu Id (updateCustomMenuName)", - "description": "\n\nSecurity check is performed to verify that the user has 'WRITE' permission for the custom menu with specified id.", - "operationId": "updateCustomMenuName", + "summary": "Get vendors (getVendors)", + "description": "Returns a list of vendors for the integration type", + "operationId": "getVendors", "parameters": [ { - "name": "customMenuId", + "name": "integrationType", "in": "path", - "description": "A string value representing the custom menu id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { - "type": "string", - "format": "uuid" + "$ref": "#/components/schemas/IntegrationType" } - } - ], - "requestBody": { - "content": { - "application/json": { - "schema": { - "type": "string", - "description": "New name of the custom menu" - } + }, + { + "name": "converterType", + "in": "query", + "required": false, + "schema": { + "type": "string" } }, - "required": true - }, + { + "name": "page", + "in": "query", + "required": false, + "schema": { + "type": "integer", + "format": "int32", + "default": 0 + } + }, + { + "name": "pageSize", + "in": "query", + "required": false, + "schema": { + "type": "integer", + "format": "int32", + "default": 2147483647 + } + }, + { + "name": "loadImages", + "in": "query", + "required": false, + "schema": { + "type": "boolean", + "default": true + } + } + ], "responses": { "200": { - "description": "OK" + "description": "OK", + "content": { + "application/json": { + "schema": { + "type": "array", + "items": { + "$ref": "#/components/schemas/Vendor" + } + } + } + } }, "400": { "description": "Bad Request", @@ -23666,57 +23589,82 @@ ] } }, - "/api/customMenu/{id}/assign/{assigneeType}": { - "put": { + "/api/converter/library/{integrationType}/{vendorName}/models": { + "get": { "tags": [ - "custom-menu-controller" + "converter-library-controller" ], - "summary": "Update custom menu assignee list (updateCustomMenuAssigneeList)", - "description": "The api designed to update the list of assignees or assignee type based on the provided Custom Menu Id. To change assignee type, put new assignee type in path parameter.\n\nSecurity check is performed to verify that the user has 'WRITE' permission for the custom menu with specified id.", - "operationId": "updateCustomMenuAssigneeList", + "summary": "Get vendor models (getVendorModels)", + "description": "Returns a list of models for the vendor, integration type and converter type", + "operationId": "getVendorModels", "parameters": [ { - "name": "id", + "name": "integrationType", "in": "path", "required": true, "schema": { - "type": "string", - "format": "uuid" + "$ref": "#/components/schemas/IntegrationType" } }, { - "name": "assigneeType", + "name": "vendorName", "in": "path", "required": true, "schema": { - "$ref": "#/components/schemas/CMAssigneeType" + "type": "string" } }, { - "name": "force", + "name": "converterType", "in": "query", - "description": "Use force if you want to override default menu", "required": false, "schema": { - "type": "boolean" + "type": "string" + } + }, + { + "name": "page", + "in": "query", + "required": false, + "schema": { + "type": "integer", + "format": "int32", + "default": 0 + } + }, + { + "name": "pageSize", + "in": "query", + "required": false, + "schema": { + "type": "integer", + "format": "int32", + "default": 2147483647 + } + }, + { + "name": "loadImages", + "in": "query", + "required": false, + "schema": { + "type": "boolean", + "default": true } } ], - "requestBody": { - "content": { - "application/json": { - "schema": { - "type": "array", - "items": { - "type": "string" + "responses": { + "200": { + "description": "OK", + "content": { + "application/json": { + "schema": { + "type": "array", + "items": { + "$ref": "#/components/schemas/Model" + } } } } - } - }, - "responses": { - "200": { - "description": "OK" }, "400": { "description": "Bad Request", @@ -23834,19 +23782,34 @@ ] } }, - "/api/translation/custom/merged/{localeCode}": { + "/api/converter/library/{integrationType}/{vendorName}/{model}/downlink": { "get": { "tags": [ - "custom-translation-controller" + "converter-library-controller" ], - "summary": "Get end-user Custom Translation configuration (getMergedCustomTranslation)", - "description": "Fetch end-user Custom Translation for specified locale. The custom translation is configured in the white labeling parameters. If custom translation translation is defined on the tenant level, it overrides the custom translation of the system level. Similar, if the custom translation is defined on the customer level, it overrides the translation configuration of the tenant level.", - "operationId": "getMergedCustomTranslation", + "summary": "Get downlink converter (getDownlinkConverter)", + "description": "Returns downlink converter body for the vendor, integration type and model", + "operationId": "getDownlinkConverter", "parameters": [ { - "name": "localeCode", + "name": "integrationType", + "in": "path", + "required": true, + "schema": { + "$ref": "#/components/schemas/IntegrationType" + } + }, + { + "name": "vendorName", + "in": "path", + "required": true, + "schema": { + "type": "string" + } + }, + { + "name": "model", "in": "path", - "description": "Locale code (e.g. 'en_US').", "required": true, "schema": { "type": "string" @@ -23857,9 +23820,9 @@ "200": { "description": "OK", "content": { - "application/json": { + "text/plain": { "schema": { - "$ref": "#/components/schemas/JsonNode" + "type": "string" } } } @@ -23980,19 +23943,34 @@ ] } }, - "/api/translation/custom/{localeCode}": { + "/api/converter/library/{integrationType}/{vendorName}/{model}/downlink/metadata": { "get": { "tags": [ - "custom-translation-controller" + "converter-library-controller" ], - "summary": "Get Custom Translation configuration (getCustomTranslation)", - "description": "Fetch the Custom Translation for specified locale that corresponds to the authority of the user. The API call is designed to load the custom translation items for edition. So, the result is NOT merged with the parent level configuration. Let's assume there is a custom translation configured on a system level. And there is no custom translation items configured on a tenant level. In such a case, the API call will return empty object for the tenant administrator. \n\n Response example: \n\n```json\n{\"home\":\"MyHome\"}\n```\n\nSecurity check is performed to verify that the user has 'READ' permission for the white labeling resource.", - "operationId": "getCustomTranslation", + "summary": "Get downlink converter metadata (getDownlinkConverterMetadata)", + "description": "Returns downlink converter metadata for the vendor, integration type and model", + "operationId": "getDownlinkConverterMetadata", "parameters": [ { - "name": "localeCode", + "name": "integrationType", + "in": "path", + "required": true, + "schema": { + "$ref": "#/components/schemas/IntegrationType" + } + }, + { + "name": "vendorName", + "in": "path", + "required": true, + "schema": { + "type": "string" + } + }, + { + "name": "model", "in": "path", - "description": "Locale code (e.g. 'en_US').", "required": true, "schema": { "type": "string" @@ -24003,9 +23981,9 @@ "200": { "description": "OK", "content": { - "application/json": { + "text/plain": { "schema": { - "$ref": "#/components/schemas/JsonNode" + "type": "string" } } } @@ -24124,38 +24102,52 @@ "ApiKeyForm": [] } ] - }, - "post": { + } + }, + "/api/converter/library/{integrationType}/{vendorName}/{model}/downlink/payload": { + "get": { "tags": [ - "custom-translation-controller" + "converter-library-controller" ], - "summary": "Create Or Update Custom Translation (saveCustomTranslation)", - "description": "Creates or Updates the Custom Translation for specified locale.\n\n Request example: \n\n```json\n{\"home\":\"MyHome\"}\n```\n\nSecurity check is performed to verify that the user has 'WRITE' permission for the white labeling resource.", - "operationId": "saveCustomTranslation", + "summary": "Get downlink payload (getDownlinkPayload)", + "description": "Returns payload example for the downlink converter for the vendor, integration type and model", + "operationId": "getDownlinkPayload", "parameters": [ { - "name": "localeCode", + "name": "integrationType", + "in": "path", + "required": true, + "schema": { + "$ref": "#/components/schemas/IntegrationType" + } + }, + { + "name": "vendorName", + "in": "path", + "required": true, + "schema": { + "type": "string" + } + }, + { + "name": "model", "in": "path", - "description": "Locale code (e.g. 'en_US').", "required": true, "schema": { "type": "string" } } ], - "requestBody": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/JsonNode" - } - } - }, - "required": true - }, "responses": { "200": { - "description": "OK" + "description": "OK", + "content": { + "text/plain": { + "schema": { + "type": "string" + } + } + } }, "400": { "description": "Bad Request", @@ -24169,7 +24161,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -24271,19 +24263,36 @@ "ApiKeyForm": [] } ] - }, - "delete": { + } + }, + "/api/converter/library/{integrationType}/{vendorName}/{model}/uplink": { + "get": { "tags": [ - "custom-translation-controller" + "converter-library-controller" ], - "summary": "Delete Custom Translation for specified locale (deleteCustomTranslation)", - "description": "Delete entire custom translation settings for end-user\n\nSecurity check is performed to verify that the user has 'WRITE' permission for the white labeling resource.", - "operationId": "deleteCustomTranslation", + "summary": "Get uplink converter (getUplinkConverter)", + "description": "Returns uplink converter body for the vendor, integration type and model", + "operationId": "getUplinkConverter", "parameters": [ { - "name": "localeCode", + "name": "integrationType", + "in": "path", + "required": true, + "schema": { + "$ref": "#/components/schemas/IntegrationType" + } + }, + { + "name": "vendorName", + "in": "path", + "required": true, + "schema": { + "type": "string" + } + }, + { + "name": "model", "in": "path", - "description": "Locale code (e.g. 'en_US').", "required": true, "schema": { "type": "string" @@ -24292,7 +24301,14 @@ ], "responses": { "200": { - "description": "OK" + "description": "OK", + "content": { + "text/plain": { + "schema": { + "type": "string" + } + } + } }, "400": { "description": "Bad Request", @@ -24408,38 +24424,52 @@ "ApiKeyForm": [] } ] - }, - "patch": { + } + }, + "/api/converter/library/{integrationType}/{vendorName}/{model}/uplink/metadata": { + "get": { "tags": [ - "custom-translation-controller" + "converter-library-controller" ], - "summary": "Update Custom Translation for specified translation keys only (patchCustomTranslation)", - "description": "The API call is designed to update the custom translation for specified key only. \n\n Request example: \n\n```json\n{\"notification.active\":\"active\"}\n```\n\nSecurity check is performed to verify that the user has 'WRITE' permission for the white labeling resource.", - "operationId": "patchCustomTranslation", + "summary": "Get uplink converter metadata (getUplinkConverterMetadata)", + "description": "Returns uplink converter metadata for the vendor, integration type and model", + "operationId": "getUplinkConverterMetadata", "parameters": [ { - "name": "localeCode", + "name": "integrationType", + "in": "path", + "required": true, + "schema": { + "$ref": "#/components/schemas/IntegrationType" + } + }, + { + "name": "vendorName", + "in": "path", + "required": true, + "schema": { + "type": "string" + } + }, + { + "name": "model", "in": "path", - "description": "Locale code (e.g. 'en_US').", "required": true, "schema": { "type": "string" } } ], - "requestBody": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/JsonNode" - } - } - }, - "required": true - }, "responses": { "200": { - "description": "OK" + "description": "OK", + "content": { + "text/plain": { + "schema": { + "type": "string" + } + } + } }, "400": { "description": "Bad Request", @@ -24557,46 +24587,50 @@ ] } }, - "/api/translation/custom/{localeCode}/upload": { - "post": { + "/api/converter/library/{integrationType}/{vendorName}/{model}/uplink/payload": { + "get": { "tags": [ - "custom-translation-controller" + "converter-library-controller" ], - "summary": "Upload Custom Translation (uploadCustomTranslation)", - "description": "Upload the Custom Translation for specified locale.\n\n Request example: \n\n```json\n{\"home\":\"MyHome\"}\n```\n\nSecurity check is performed to verify that the user has 'WRITE' permission for the white labeling resource.", - "operationId": "uploadCustomTranslation", + "summary": "Get uplink payload (getUplinkPayload)", + "description": "Returns payload example for the uplink converter for the vendor, integration type and model", + "operationId": "getUplinkPayload", "parameters": [ { - "name": "localeCode", + "name": "integrationType", + "in": "path", + "required": true, + "schema": { + "$ref": "#/components/schemas/IntegrationType" + } + }, + { + "name": "vendorName", "in": "path", - "description": "Locale code (e.g. 'en_US').", "required": true, "schema": { "type": "string" } - } - ], - "requestBody": { - "content": { - "multipart/form-data": { - "schema": { - "type": "object", - "properties": { - "file": { - "type": "string", - "format": "binary" - } - }, - "required": [ - "file" - ] - } + }, + { + "name": "model", + "in": "path", + "required": true, + "schema": { + "type": "string" } } - }, + ], "responses": { "200": { - "description": "OK" + "description": "OK", + "content": { + "text/plain": { + "schema": { + "type": "string" + } + } + } }, "400": { "description": "Bad Request", @@ -24610,7 +24644,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -24714,29 +24748,19 @@ ] } }, - "/api/translation/custom/{localeCode}/{keyPath}": { - "delete": { + "/api/customMenu": { + "get": { "tags": [ - "custom-translation-controller" + "custom-menu-controller" ], - "summary": "Delete specified key of Custom Translation (deleteCustomTranslationKey) ", - "description": "The API call is designed to delete specified key of the custom translation and return as a result parent translation.(e.g. if tenant translation for key is 'value1' and customer translation is 'value2' then by deletinf key onn customer level you will get 'value1' in response) \n\nSecurity check is performed to verify that the user has 'WRITE' permission for the white labeling resource.", - "operationId": "deleteCustomTranslationKey", + "summary": "Get end-user Custom Menu configuration (getCustomMenu)", + "description": "Fetch the Custom Menu configuration object for the authorized user. The custom menu is configured in the white labeling parameters and has one of three user scopes:SYSTEM, TENANT, CUSTOMER and four assignee type: NO_ASSIGN, ALL, CUSTOMERS, USERS.There are three default (assignee type: ALL) menus configured on the system level for each scope and if no other menu is configured for user, system configuration of the corresponding scope will be applied.If a custom menu with assignee type ALL is configured on the tenant level, it overrides the menu configuration of the corresponding scope on the system level. If a custom menu with assignee type USER_GROUPS is configured on the tenant level, it overrides default tenant menu.If a custom menu with assignee type CUSTOMERS is configured on tenant level for specific customer, it will be applied to all customer users.If a custom menu with assignee type ALL is configured on the customer level, it overrides the menu assigned on tenant level.If a custom menu with assignee type USER_GROUPS is configured on the customer level, it overrides default customer menu.If a custom menu is assigned to specific user, it overrides all other configuration.", + "operationId": "getCustomMenu", "parameters": [ { - "name": "localeCode", - "in": "path", - "description": "Locale code (e.g. 'en_US').", - "required": true, - "schema": { - "type": "string" - } - }, - { - "name": "keyPath", - "in": "path", - "description": "A string value representing key of the custom translation (e.g. 'notification.active').", - "required": true, + "name": "If-None-Match", + "in": "header", + "required": false, "schema": { "type": "string" } @@ -24744,7 +24768,14 @@ ], "responses": { "200": { - "description": "OK" + "description": "OK", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/CustomMenuConfig" + } + } + } }, "400": { "description": "Bad Request", @@ -24860,30 +24891,19 @@ "ApiKeyForm": [] } ] - } - }, - "/api/customer": { + }, "post": { "tags": [ - "customer-controller" + "custom-menu-controller" ], - "summary": "Create or update Customer (saveCustomer)", - "description": "Creates or Updates the Customer. When creating customer, platform generates Customer Id as [time-based UUID](https://en.wikipedia.org/wiki/Universally_unique_identifier#Version_1_(date-time_and_MAC_address)). The newly created Customer Id will be present in the response. Specify existing Customer Id to update the Customer. Referencing non-existing Customer Id will cause 'Not Found' error.Remove 'id', 'tenantId' from the request body example (below) to create new Customer entity. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'WRITE' permission for the entity (entities).", - "operationId": "saveCustomer", + "summary": "Create Custom Menu (createCustomMenu)", + "description": "The api is designed to create Custom Menu without configuration. Is not applicable for update.\n\nSecurity check is performed to verify that the user has 'WRITE' permission for the custom menu with specified id.", + "operationId": "createCustomMenu", "parameters": [ { - "name": "entityGroupId", - "in": "query", - "description": "A string value representing the Entity Group Id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'. If specified, the entity will be added to the corresponding entity group.", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "entityGroupIds", + "name": "assignToList", "in": "query", - "description": "A list of string values, separated by comma ',' representing the Entity Group Ids. For example, '784f394c-42b6-435a-983c-b7beff2784f9','a84f394c-42b6-435a-083c-b7beff2784f9'. If specified, the entity will be added to the corresponding entity groups.", + "description": "A list of entity ids, separated by comma ','", "required": false, "schema": { "type": "array", @@ -24893,42 +24913,20 @@ } }, { - "name": "nameConflictPolicy", - "in": "query", - "description": "Optional value of name conflict policy. Possible values: FAIL or UNIQUIFY. If omitted, FAIL policy is applied. FAIL policy implies exception will be thrown if an entity with the same name already exists. UNIQUIFY policy appends a suffix to the entity name, if a name conflict occurs.", - "required": false, - "schema": { - "$ref": "#/components/schemas/NameConflictPolicy", - "default": "FAIL" - } - }, - { - "name": "uniquifySeparator", - "in": "query", - "description": "Optional value of name suffix separator used by UNIQUIFY policy. By default, underscore separator is used. For example, strategy is UNIQUIFY, separator is '-'; if a name conflict occurs for entity name 'test-name', created entity will have name like 'test-name-7fsh4f'.", - "required": false, - "schema": { - "type": "string", - "default": "_" - } - }, - { - "name": "uniquifyStrategy", + "name": "force", "in": "query", - "description": "Optional value of uniquify strategy used by UNIQUIFY policy. Possible values: RANDOM or INCREMENTAL. By default, RANDOM strategy is used, which means random alphanumeric string will be added as a suffix to entity name. INCREMENTAL implies the first possible number starting from 1 will be added as a name suffix. For example, strategy is UNIQUIFY, uniquify strategy is INCREMENTAL; if a name conflict occurs for entity name 'test-name', created entity will have name like 'test-name-1.", + "description": "Use force if you want to create default menu that conflicts with the existing one (old one will be update NO_ASSIGN assignee type)", "required": false, "schema": { - "$ref": "#/components/schemas/UniquifyStrategy", - "default": "RANDOM" + "type": "boolean" } } ], "requestBody": { - "description": "A JSON value representing the customer.", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/Customer" + "$ref": "#/components/schemas/CustomMenuInfo" } } }, @@ -24940,7 +24938,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/Customer" + "$ref": "#/components/schemas/CustomMenu" } } } @@ -25061,23 +25059,87 @@ ] } }, - "/api/customer/info/{customerId}": { + "/api/customMenu/infos": { "get": { "tags": [ - "customer-controller" + "custom-menu-controller" ], - "summary": "Get Customer info (getCustomerInfoById)", - "description": "Get the Customer info object based on the provided Customer Id. If the user has the authority of 'Tenant Administrator', the server checks that the customer is owned by the same tenant. If the user has the authority of 'Customer User', the server checks that the user belongs to the customer.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getCustomerInfoById", + "summary": "Get all custom menus configured at user level (getCustomMenuInfos)", + "description": "Returns a page of custom menu info objects owned by the tenant or the customer of a current user, scope and assigneeType request parameters can be used to filter the result.\n\nSecurity check is performed to verify that the user has 'READ' permission for the white labeling resource.", + "operationId": "getCustomMenuInfos", "parameters": [ { - "name": "customerId", - "in": "path", - "description": "A string value representing the customer id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "name": "scope", + "in": "query", + "description": "Custom menu scope.", + "required": false, + "schema": { + "$ref": "#/components/schemas/CMScope" + } + }, + { + "name": "assigneeType", + "in": "query", + "description": "Custom menu assignee type.", + "required": false, + "schema": { + "$ref": "#/components/schemas/CMAssigneeType" + } + }, + { + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", + "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'substring' filter based on the custom menu name.", + "required": false, "schema": { "type": "string" } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string", + "enum": [ + "createdTime", + "title" + ] + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] + } } ], "responses": { @@ -25086,7 +25148,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/CustomerInfo" + "$ref": "#/components/schemas/PageDataCustomMenuInfo" } } } @@ -25207,22 +25269,32 @@ ] } }, - "/api/customer/{customerId}": { - "get": { + "/api/customMenu/{customMenuId}": { + "delete": { "tags": [ - "customer-controller" + "custom-menu-controller" ], - "summary": "Get Customer (getCustomerById)", - "description": "Get the Customer object based on the provided Customer Id. If the user has the authority of 'Tenant Administrator', the server checks that the customer is owned by the same tenant. If the user has the authority of 'Customer User', the server checks that the user belongs to the customer.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getCustomerById", + "summary": "Delete custom menu (deleteCustomMenu)", + "description": "Deletes the custom menu based on the provided Custom Menu Id. Referencing non-existing custom menu Id will cause an error. If the custom menu is assigned to the list of users or customers bad request is returned.To delete a custom menu that has assignee list set 'force' request param to true ", + "operationId": "deleteCustomMenu", "parameters": [ { - "name": "customerId", + "name": "customMenuId", "in": "path", - "description": "A string value representing the customer id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "description": "A string value representing the custom menu id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { - "type": "string" + "type": "string", + "format": "uuid" + } + }, + { + "name": "force", + "in": "query", + "description": "Force set to true will unassign menu before deletion", + "required": false, + "schema": { + "type": "boolean" } } ], @@ -25232,7 +25304,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/Customer" + "$ref": "#/components/schemas/CustomMenuDeleteResult" } } } @@ -25351,28 +25423,41 @@ "ApiKeyForm": [] } ] - }, - "delete": { + } + }, + "/api/customMenu/{customMenuId}/assigneeList": { + "get": { "tags": [ - "customer-controller" + "custom-menu-controller" ], - "summary": "Delete Customer (deleteCustomer)", - "description": "Deletes the Customer and all customer Users. All assigned Dashboards, Assets, Devices, etc. will be unassigned but not deleted. Referencing non-existing Customer Id will cause an error.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'DELETE' permission for the entity (entities).", - "operationId": "deleteCustomer", + "summary": "Get Custom Menu assignee list (getCustomMenuAssigneeList)", + "description": "Fetch the list of Entity Info objects that represents users or customers, or empty list if custom menu is not assigned or has NO_ASSIGN/ALL assignee type.\n\nSecurity check is performed to verify that the user has 'READ' permission for the custom menu with specified id.", + "operationId": "getCustomMenuAssigneeList", "parameters": [ { - "name": "customerId", + "name": "customMenuId", "in": "path", - "description": "A string value representing the customer id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "description": "A string value representing the custom menu id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { - "type": "string" + "type": "string", + "format": "uuid" } } ], "responses": { "200": { - "description": "OK" + "description": "OK", + "content": { + "application/json": { + "schema": { + "type": "array", + "items": { + "$ref": "#/components/schemas/EntityInfo" + } + } + } + } }, "400": { "description": "Bad Request", @@ -25490,99 +25575,188 @@ ] } }, - "/api/customer/{customerId}/customerInfos": { + "/api/customMenu/{customMenuId}/config": { "get": { "tags": [ - "customer-controller" + "custom-menu-controller" ], - "summary": "Get Customer sub-customers Infos (getCustomerCustomerInfos)", - "description": "Returns a page of customer info objects owned by the specified customer. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getCustomerCustomerInfos", + "summary": "Get Custom Menu configuration by id (getCustomMenuConfig)", + "description": "Fetch the Custom Menu configuration based on the provided Custom Menu Id. \n\nSecurity check is performed to verify that the user has 'READ' permission for the custom menu with specified id.", + "operationId": "getCustomMenuConfig", "parameters": [ { - "name": "customerId", + "name": "customMenuId", "in": "path", - "description": "A string value representing the customer id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "description": "A string value representing the custom menu id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { - "type": "string" + "type": "string", + "format": "uuid" + } + } + ], + "responses": { + "200": { + "description": "OK", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/CustomMenuConfig" + } + } } }, - { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "integer", - "format": "int32" + "400": { + "description": "Bad Request", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-400": { + "summary": "Bad Request", + "value": { + "status": 400, + "message": "Invalid UUID string: 123", + "errorCode": 31, + "timestamp": 1609459200000 + } + } + } + } } }, - { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", - "required": true, - "schema": { - "type": "integer", - "format": "int32" + "401": { + "description": "Unauthorized", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-401": { + "summary": "Unauthorized", + "value": { + "status": 401, + "message": "Authentication failed", + "errorCode": 10, + "timestamp": 1609459200000 + } + } + } + } } }, - { - "name": "includeCustomers", - "in": "query", - "description": "Include customer or sub-customer entities", - "required": false, - "schema": { - "type": "boolean" + "403": { + "description": "Forbidden", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-403": { + "summary": "Forbidden", + "value": { + "status": 403, + "message": "You don't have permission to perform this operation!", + "errorCode": 20, + "timestamp": 1609459200000 + } + } + } + } } }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'substring' filter based on the customer title.", - "required": false, - "schema": { - "type": "string" + "404": { + "description": "Not Found", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-404": { + "summary": "Not Found", + "value": { + "status": 404, + "message": "Requested item wasn't found!", + "errorCode": 32, + "timestamp": 1609459200000 + } + } + } + } } }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, - "schema": { - "type": "string", - "enum": [ - "createdTime", - "title", - "email", - "country", - "city" - ] + "429": { + "description": "Too Many Requests", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-429": { + "summary": "Too Many Requests", + "value": { + "status": 429, + "message": "Too many requests for current tenant!", + "errorCode": 33, + "timestamp": 1609459200000 + } + } + } + } } + } + }, + "security": [ + { + "HttpLoginForm": [] }, { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, + "ApiKeyForm": [] + } + ] + }, + "put": { + "tags": [ + "custom-menu-controller" + ], + "summary": "Update Custom Menu configuration based on the provided Custom Menu Id (updateCustomMenuConfig)", + "description": "\n\nSecurity check is performed to verify that the user has 'WRITE' permission for the custom menu with specified id.", + "operationId": "updateCustomMenuConfig", + "parameters": [ + { + "name": "customMenuId", + "in": "path", + "description": "A string value representing the custom menu id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, "schema": { "type": "string", - "enum": [ - "ASC", - "DESC" - ] + "format": "uuid" } } ], + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/CustomMenuConfig" + } + } + }, + "required": true + }, "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataCustomerInfo" + "$ref": "#/components/schemas/CustomMenu" } } } @@ -25703,22 +25877,23 @@ ] } }, - "/api/customer/{customerId}/shortInfo": { + "/api/customMenu/{customMenuId}/info": { "get": { "tags": [ - "customer-controller" + "custom-menu-controller" ], - "summary": "Get short Customer info (getShortCustomerInfoById)", - "description": "Get the short customer object that contains only the title and 'isPublic' flag. If the user has the authority of 'Tenant Administrator', the server checks that the customer is owned by the same tenant. If the user has the authority of 'Customer User', the server checks that the user belongs to the customer.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getShortCustomerInfoById", + "summary": "Get Custom Menu Info (getCustomMenuInfoById)", + "description": "Fetch the Custom Menu Info object based on the provided Custom Menu Id. \n\nSecurity check is performed to verify that the user has 'READ' permission for the custom menu with specified id.", + "operationId": "getCustomMenuInfoById", "parameters": [ { - "name": "customerId", + "name": "customMenuId", "in": "path", - "description": "A string value representing the customer id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "description": "A string value representing the custom menu id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { - "type": "string" + "type": "string", + "format": "uuid" } } ], @@ -25728,7 +25903,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/JsonNode" + "$ref": "#/components/schemas/CustomMenuInfo" } } } @@ -25849,36 +26024,41 @@ ] } }, - "/api/customer/{customerId}/title": { - "get": { + "/api/customMenu/{customMenuId}/name": { + "put": { "tags": [ - "customer-controller" + "custom-menu-controller" ], - "summary": "Get Customer Title (getCustomerTitleById)", - "description": "Get the title of the customer. If the user has the authority of 'Tenant Administrator', the server checks that the customer is owned by the same tenant. If the user has the authority of 'Customer User', the server checks that the user belongs to the customer.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getCustomerTitleById", + "summary": "Update Custom Menu name based on the provided Custom Menu Id (updateCustomMenuName)", + "description": "\n\nSecurity check is performed to verify that the user has 'WRITE' permission for the custom menu with specified id.", + "operationId": "updateCustomMenuName", "parameters": [ { - "name": "customerId", + "name": "customMenuId", "in": "path", - "description": "A string value representing the customer id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "description": "A string value representing the custom menu id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { - "type": "string" + "type": "string", + "format": "uuid" } } ], - "responses": { - "200": { - "description": "OK", - "content": { - "application/text": { - "schema": { - "type": "string" - } + "requestBody": { + "content": { + "application/json": { + "schema": { + "type": "string", + "description": "New name of the custom menu" } } }, + "required": true + }, + "responses": { + "200": { + "description": "OK" + }, "400": { "description": "Bad Request", "content": { @@ -25995,93 +26175,57 @@ ] } }, - "/api/customerInfos/all": { - "get": { + "/api/customMenu/{id}/assign/{assigneeType}": { + "put": { "tags": [ - "customer-controller" + "custom-menu-controller" ], - "summary": "Get All Customer Infos for current user (getAllCustomerInfos)", - "description": "Returns a page of customer info objects owned by the tenant or the customer of a current user. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getAllCustomerInfos", + "summary": "Update custom menu assignee list (updateCustomMenuAssigneeList)", + "description": "The api designed to update the list of assignees or assignee type based on the provided Custom Menu Id. To change assignee type, put new assignee type in path parameter.\n\nSecurity check is performed to verify that the user has 'WRITE' permission for the custom menu with specified id.", + "operationId": "updateCustomMenuAssigneeList", "parameters": [ { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", + "name": "id", + "in": "path", "required": true, "schema": { - "type": "integer", - "format": "int32" + "type": "string", + "format": "uuid" } }, { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", + "name": "assigneeType", + "in": "path", "required": true, "schema": { - "type": "integer", - "format": "int32" + "$ref": "#/components/schemas/CMAssigneeType" } }, { - "name": "includeCustomers", + "name": "force", "in": "query", - "description": "Include customer or sub-customer entities", + "description": "Use force if you want to override default menu", "required": false, "schema": { "type": "boolean" } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'substring' filter based on the customer title.", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, - "schema": { - "type": "string", - "enum": [ - "createdTime", - "title", - "email", - "country", - "city" - ] - } - }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] - } } ], - "responses": { - "200": { - "description": "OK", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/PageDataCustomerInfo" + "requestBody": { + "content": { + "application/json": { + "schema": { + "type": "array", + "items": { + "type": "string" } } } + } + }, + "responses": { + "200": { + "description": "OK" }, "400": { "description": "Bad Request", @@ -26199,72 +26343,23 @@ ] } }, - "/api/customers": { + "/api/translation/custom/merged/{localeCode}": { "get": { "tags": [ - "customer-controller" + "custom-translation-controller" ], - "summary": "Get Tenant Customers (getCustomers)", - "description": "Returns a page of customers owned by tenant. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getCustomers", + "summary": "Get end-user Custom Translation configuration (getMergedCustomTranslation)", + "description": "Fetch end-user Custom Translation for specified locale. The custom translation is configured in the white labeling parameters. If custom translation translation is defined on the tenant level, it overrides the custom translation of the system level. Similar, if the custom translation is defined on the customer level, it overrides the translation configuration of the tenant level.", + "operationId": "getMergedCustomTranslation", "parameters": [ { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", + "name": "localeCode", + "in": "path", + "description": "Locale code (e.g. 'en_US').", "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'substring' filter based on the customer title.", - "required": false, "schema": { "type": "string" } - }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, - "schema": { - "type": "string", - "enum": [ - "createdTime", - "title", - "email", - "country", - "city" - ] - } - }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] - } } ], "responses": { @@ -26273,7 +26368,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataCustomer" + "$ref": "#/components/schemas/JsonNode" } } } @@ -26394,25 +26489,22 @@ ] } }, - "/api/customers/list": { + "/api/translation/custom/{localeCode}": { "get": { "tags": [ - "customer-controller" + "custom-translation-controller" ], - "summary": "Get customers by Customer Ids (getCustomersByIds)", - "description": "Returns a list of Customer objects based on the provided ids.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", - "operationId": "getCustomersByIds", + "summary": "Get Custom Translation configuration (getCustomTranslation)", + "description": "Fetch the Custom Translation for specified locale that corresponds to the authority of the user. The API call is designed to load the custom translation items for edition. So, the result is NOT merged with the parent level configuration. Let's assume there is a custom translation configured on a system level. And there is no custom translation items configured on a tenant level. In such a case, the API call will return empty object for the tenant administrator. \n\n Response example: \n\n```json\n{\"home\":\"MyHome\"}\n```\n\nSecurity check is performed to verify that the user has 'READ' permission for the white labeling resource.", + "operationId": "getCustomTranslation", "parameters": [ { - "name": "customerIds", - "in": "query", - "description": "A list of customer ids, separated by comma ','", + "name": "localeCode", + "in": "path", + "description": "Locale code (e.g. 'en_US').", "required": true, "schema": { - "type": "array", - "items": { - "type": "string" - } + "type": "string" } } ], @@ -26422,10 +26514,7 @@ "content": { "application/json": { "schema": { - "type": "array", - "items": { - "$ref": "#/components/schemas/Customer" - } + "$ref": "#/components/schemas/JsonNode" } } } @@ -26544,96 +26633,39 @@ "ApiKeyForm": [] } ] - } - }, - "/api/entityGroup/{entityGroupId}/customers": { - "get": { + }, + "post": { "tags": [ - "customer-controller" + "custom-translation-controller" ], - "summary": "Get customers by Entity Group Id (getCustomersByEntityGroupId)", - "description": "Returns a page of Customer objects that belongs to specified Entity Group Id. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\n Security check is performed to verify that the user has 'READ' permission for specified group.", - "operationId": "getCustomersByEntityGroupId", + "summary": "Create Or Update Custom Translation (saveCustomTranslation)", + "description": "Creates or Updates the Custom Translation for specified locale.\n\n Request example: \n\n```json\n{\"home\":\"MyHome\"}\n```\n\nSecurity check is performed to verify that the user has 'WRITE' permission for the white labeling resource.", + "operationId": "saveCustomTranslation", "parameters": [ { - "name": "entityGroupId", + "name": "localeCode", "in": "path", - "description": "A string value representing the Entity Group Id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": true, - "schema": { - "type": "string" - } - }, - { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "string", - "minimum": 1 - } - }, - { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", + "description": "Locale code (e.g. 'en_US').", "required": true, - "schema": { - "type": "string", - "minimum": 0 - } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'substring' filter based on the customer title.", - "required": false, "schema": { "type": "string" } - }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, - "schema": { - "type": "string", - "enum": [ - "createdTime", - "title", - "email", - "country", - "city" - ] - } - }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] - } } ], - "responses": { - "200": { - "description": "OK", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/PageDataCustomer" - } + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/JsonNode" } } }, + "required": true + }, + "responses": { + "200": { + "description": "OK" + }, "400": { "description": "Bad Request", "content": { @@ -26646,7 +26678,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -26748,21 +26780,19 @@ "ApiKeyForm": [] } ] - } - }, - "/api/tenant/customers": { - "get": { + }, + "delete": { "tags": [ - "customer-controller" + "custom-translation-controller" ], - "summary": "Get Tenant Customer by Customer title (getTenantCustomer)", - "description": "Get the Customer using Customer Title. \n\nAvailable for users with 'TENANT_ADMIN' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getTenantCustomer", + "summary": "Delete Custom Translation for specified locale (deleteCustomTranslation)", + "description": "Delete entire custom translation settings for end-user\n\nSecurity check is performed to verify that the user has 'WRITE' permission for the white labeling resource.", + "operationId": "deleteCustomTranslation", "parameters": [ { - "name": "customerTitle", - "in": "query", - "description": "A string value representing the Customer title.", + "name": "localeCode", + "in": "path", + "description": "Locale code (e.g. 'en_US').", "required": true, "schema": { "type": "string" @@ -26771,14 +26801,7 @@ ], "responses": { "200": { - "description": "OK", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/Customer" - } - } - } + "description": "OK" }, "400": { "description": "Bad Request", @@ -26894,87 +26917,39 @@ "ApiKeyForm": [] } ] - } - }, - "/api/user/customers": { - "get": { + }, + "patch": { "tags": [ - "customer-controller" + "custom-translation-controller" ], - "summary": "Get Customers (getUserCustomers)", - "description": "Returns a page of customers available for the user. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getUserCustomers", + "summary": "Update Custom Translation for specified translation keys only (patchCustomTranslation)", + "description": "The API call is designed to update the custom translation for specified key only. \n\n Request example: \n\n```json\n{\"notification.active\":\"active\"}\n```\n\nSecurity check is performed to verify that the user has 'WRITE' permission for the white labeling resource.", + "operationId": "patchCustomTranslation", "parameters": [ { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "string", - "minimum": 1 - } - }, - { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", + "name": "localeCode", + "in": "path", + "description": "Locale code (e.g. 'en_US').", "required": true, - "schema": { - "type": "string", - "minimum": 0 - } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'substring' filter based on the customer title.", - "required": false, "schema": { "type": "string" } - }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, - "schema": { - "type": "string", - "enum": [ - "createdTime", - "title", - "email", - "country", - "city" - ] - } - }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] - } } ], - "responses": { - "200": { - "description": "OK", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/PageDataCustomer" - } + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/JsonNode" } } }, + "required": true + }, + "responses": { + "200": { + "description": "OK" + }, "400": { "description": "Bad Request", "content": { @@ -27091,24 +27066,46 @@ ] } }, - "/api/customer/dashboard/home/info": { - "get": { + "/api/translation/custom/{localeCode}/upload": { + "post": { "tags": [ - "dashboard-controller" + "custom-translation-controller" ], - "summary": "Get Customer Home Dashboard Info (getCustomerHomeDashboardInfo)", - "description": "Returns the home dashboard info object that is configured as 'homeDashboardId' parameter in the 'additionalInfo' of the corresponding customer. \n\nAvailable for users with 'CUSTOMER_USER' authority.\n\nSecurity check is performed to verify that the user has 'READ' permission for the white labeling resource.", - "operationId": "getCustomerHomeDashboardInfo", - "responses": { - "200": { - "description": "OK", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/HomeDashboardInfo" - } + "summary": "Upload Custom Translation (uploadCustomTranslation)", + "description": "Upload the Custom Translation for specified locale.\n\n Request example: \n\n```json\n{\"home\":\"MyHome\"}\n```\n\nSecurity check is performed to verify that the user has 'WRITE' permission for the white labeling resource.", + "operationId": "uploadCustomTranslation", + "parameters": [ + { + "name": "localeCode", + "in": "path", + "description": "Locale code (e.g. 'en_US').", + "required": true, + "schema": { + "type": "string" + } + } + ], + "requestBody": { + "content": { + "multipart/form-data": { + "schema": { + "type": "object", + "properties": { + "file": { + "type": "string", + "format": "binary" + } + }, + "required": [ + "file" + ] } } + } + }, + "responses": { + "200": { + "description": "OK" }, "400": { "description": "Bad Request", @@ -27122,7 +27119,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -27224,24 +27221,36 @@ "ApiKeyForm": [] } ] - }, - "post": { + } + }, + "/api/translation/custom/{localeCode}/{keyPath}": { + "delete": { "tags": [ - "dashboard-controller" + "custom-translation-controller" ], - "summary": "Update Customer Home Dashboard Info (setCustomerHomeDashboardInfo)", - "description": "Update the home dashboard assignment for the current customer. \n\nAvailable for users with 'CUSTOMER_USER' authority.\n\nSecurity check is performed to verify that the user has 'WRITE' permission for the white labeling resource.", - "operationId": "setCustomerHomeDashboardInfo", - "requestBody": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/HomeDashboardInfo" - } + "summary": "Delete specified key of Custom Translation (deleteCustomTranslationKey) ", + "description": "The API call is designed to delete specified key of the custom translation and return as a result parent translation.(e.g. if tenant translation for key is 'value1' and customer translation is 'value2' then by deletinf key onn customer level you will get 'value1' in response) \n\nSecurity check is performed to verify that the user has 'WRITE' permission for the white labeling resource.", + "operationId": "deleteCustomTranslationKey", + "parameters": [ + { + "name": "localeCode", + "in": "path", + "description": "Locale code (e.g. 'en_US').", + "required": true, + "schema": { + "type": "string" } }, - "required": true - }, + { + "name": "keyPath", + "in": "path", + "description": "A string value representing key of the custom translation (e.g. 'notification.active').", + "required": true, + "schema": { + "type": "string" + } + } + ], "responses": { "200": { "description": "OK" @@ -27258,7 +27267,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -27362,96 +27371,85 @@ ] } }, - "/api/customer/{customerId}/dashboards": { - "get": { + "/api/customer": { + "post": { "tags": [ - "dashboard-controller" + "customer-controller" ], - "summary": "Get Customer Dashboards (getCustomerDashboards)", - "description": "Returns a page of dashboard info objects owned by the specified customer. The Dashboard Info object contains lightweight information about the dashboard (e.g. title, image, assigned customers) but does not contain the heavyweight configuration JSON. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getCustomerDashboards", + "summary": "Create or update Customer (saveCustomer)", + "description": "Creates or Updates the Customer. When creating customer, platform generates Customer Id as [time-based UUID](https://en.wikipedia.org/wiki/Universally_unique_identifier#Version_1_(date-time_and_MAC_address)). The newly created Customer Id will be present in the response. Specify existing Customer Id to update the Customer. Referencing non-existing Customer Id will cause 'Not Found' error.Remove 'id', 'tenantId' from the request body example (below) to create new Customer entity. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'WRITE' permission for the entity (entities).", + "operationId": "saveCustomer", "parameters": [ { - "name": "customerId", - "in": "path", - "description": "A string value representing the customer id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": true, - "schema": { - "type": "string" - } - }, - { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "page", + "name": "entityGroupId", "in": "query", - "description": "Sequence number of page starting from 0", - "required": true, + "description": "A string value representing the Entity Group Id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'. If specified, the entity will be added to the corresponding entity group.", + "required": false, "schema": { - "type": "integer", - "format": "int32" + "type": "string" } }, { - "name": "includeCustomers", + "name": "entityGroupIds", "in": "query", - "description": "Include customer or sub-customer entities", + "description": "A list of string values, separated by comma ',' representing the Entity Group Ids. For example, '784f394c-42b6-435a-983c-b7beff2784f9','a84f394c-42b6-435a-083c-b7beff2784f9'. If specified, the entity will be added to the corresponding entity groups.", "required": false, "schema": { - "type": "boolean" + "type": "array", + "items": { + "type": "string" + } } }, { - "name": "textSearch", + "name": "nameConflictPolicy", "in": "query", - "description": "The case insensitive 'substring' filter based on the dashboard title.", + "description": "Optional value of name conflict policy. Possible values: FAIL or UNIQUIFY. If omitted, FAIL policy is applied. FAIL policy implies exception will be thrown if an entity with the same name already exists. UNIQUIFY policy appends a suffix to the entity name, if a name conflict occurs.", "required": false, "schema": { - "type": "string" + "$ref": "#/components/schemas/NameConflictPolicy", + "default": "FAIL" } }, { - "name": "sortProperty", + "name": "uniquifySeparator", "in": "query", - "description": "Property of entity to sort by", + "description": "Optional value of name suffix separator used by UNIQUIFY policy. By default, underscore separator is used. For example, strategy is UNIQUIFY, separator is '-'; if a name conflict occurs for entity name 'test-name', created entity will have name like 'test-name-7fsh4f'.", "required": false, "schema": { "type": "string", - "enum": [ - "createdTime", - "title" - ] + "default": "_" } }, { - "name": "sortOrder", + "name": "uniquifyStrategy", "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "description": "Optional value of uniquify strategy used by UNIQUIFY policy. Possible values: RANDOM or INCREMENTAL. By default, RANDOM strategy is used, which means random alphanumeric string will be added as a suffix to entity name. INCREMENTAL implies the first possible number starting from 1 will be added as a name suffix. For example, strategy is UNIQUIFY, uniquify strategy is INCREMENTAL; if a name conflict occurs for entity name 'test-name', created entity will have name like 'test-name-1.", "required": false, "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] + "$ref": "#/components/schemas/UniquifyStrategy", + "default": "RANDOM" } } ], + "requestBody": { + "description": "A JSON value representing the customer.", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/Customer" + } + } + }, + "required": true + }, "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataDashboardInfo" + "$ref": "#/components/schemas/Customer" } } } @@ -27468,7 +27466,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -27572,62 +27570,32 @@ ] } }, - "/api/dashboard": { - "post": { + "/api/customer/info/{customerId}": { + "get": { "tags": [ - "dashboard-controller" + "customer-controller" ], - "summary": "Create Or Update Dashboard (saveDashboard)", - "description": "Create or update the Dashboard. When creating dashboard, platform generates Dashboard Id as [time-based UUID](https://en.wikipedia.org/wiki/Universally_unique_identifier#Version_1_(date-time_and_MAC_address)). The newly created Dashboard id will be present in the response. Specify existing Dashboard id to update the dashboard. Referencing non-existing dashboard Id will cause 'Not Found' error. Only users with 'TENANT_ADMIN') authority may create the dashboards.Remove 'id', 'tenantId' and optionally 'customerId' from the request body example (below) to create new Dashboard entity. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", - "operationId": "saveDashboard", + "summary": "Get Customer info (getCustomerInfoById)", + "description": "Get the Customer info object based on the provided Customer Id. If the user has the authority of 'Tenant Administrator', the server checks that the customer is owned by the same tenant. If the user has the authority of 'Customer User', the server checks that the user belongs to the customer.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getCustomerInfoById", "parameters": [ { - "name": "entityGroupId", - "in": "query", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "entityGroupIds", - "in": "query", - "description": "A list of entity group ids, separated by comma ','", - "required": false, - "schema": { - "type": "array", - "items": { - "type": "string" - } - } - }, - { - "name": "Accept-Encoding", - "in": "header", - "required": false, + "name": "customerId", + "in": "path", + "description": "A string value representing the customer id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, "schema": { "type": "string" } } ], - "requestBody": { - "description": "A JSON value representing the dashboard.", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/Dashboard" - } - } - }, - "required": true - }, "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/Dashboard" + "$ref": "#/components/schemas/CustomerInfo" } } } @@ -27644,7 +27612,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -27748,19 +27716,20 @@ ] } }, - "/api/dashboard/home": { + "/api/customer/{customerId}": { "get": { "tags": [ - "dashboard-controller" + "customer-controller" ], - "summary": "Get Home Dashboard (getHomeDashboard)", - "description": "Returns the home dashboard object that is configured as 'homeDashboardId' parameter in the 'additionalInfo' of the User. If 'homeDashboardId' parameter is not set on the User level and the User has authority 'CUSTOMER_USER', check the same parameter for the corresponding Customer. If 'homeDashboardId' parameter is not set on the User and Customer levels then checks the same parameter for the Tenant that owns the user. The Dashboard object is a heavyweight object that contains information about the dashboard (e.g. title, image, assigned customers) and also configuration JSON (e.g. layouts, widgets, entity aliases).\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", - "operationId": "getHomeDashboard", + "summary": "Get Customer (getCustomerById)", + "description": "Get the Customer object based on the provided Customer Id. If the user has the authority of 'Tenant Administrator', the server checks that the customer is owned by the same tenant. If the user has the authority of 'Customer User', the server checks that the user belongs to the customer.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getCustomerById", "parameters": [ { - "name": "Accept-Encoding", - "in": "header", - "required": false, + "name": "customerId", + "in": "path", + "description": "A string value representing the customer id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, "schema": { "type": "string" } @@ -27772,7 +27741,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/HomeDashboard" + "$ref": "#/components/schemas/Customer" } } } @@ -27891,26 +27860,28 @@ "ApiKeyForm": [] } ] - } - }, - "/api/dashboard/home/info": { - "get": { + }, + "delete": { "tags": [ - "dashboard-controller" + "customer-controller" + ], + "summary": "Delete Customer (deleteCustomer)", + "description": "Deletes the Customer and all customer Users. All assigned Dashboards, Assets, Devices, etc. will be unassigned but not deleted. Referencing non-existing Customer Id will cause an error.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'DELETE' permission for the entity (entities).", + "operationId": "deleteCustomer", + "parameters": [ + { + "name": "customerId", + "in": "path", + "description": "A string value representing the customer id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, + "schema": { + "type": "string" + } + } ], - "summary": "Get Home Dashboard Info (getHomeDashboardInfo)", - "description": "Returns the home dashboard info object that is configured as 'homeDashboardId' parameter in the 'additionalInfo' of the User. If 'homeDashboardId' parameter is not set on the User level and the User has authority 'CUSTOMER_USER', check the same parameter for the corresponding Customer. If 'homeDashboardId' parameter is not set on the User and Customer levels then checks the same parameter for the Tenant that owns the user. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", - "operationId": "getHomeDashboardInfo", "responses": { "200": { - "description": "OK", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/HomeDashboardInfo" - } - } - } + "description": "OK" }, "400": { "description": "Bad Request", @@ -28028,169 +27999,99 @@ ] } }, - "/api/dashboard/info/{dashboardId}": { + "/api/customer/{customerId}/customerInfos": { "get": { "tags": [ - "dashboard-controller" + "customer-controller" ], - "summary": "Get Dashboard Info (getDashboardInfoById)", - "description": "Get the information about the dashboard based on 'dashboardId' parameter. The Dashboard Info object contains lightweight information about the dashboard (e.g. title, image, assigned customers) but does not contain the heavyweight configuration JSON.", - "operationId": "getDashboardInfoById", + "summary": "Get Customer sub-customers Infos (getCustomerCustomerInfos)", + "description": "Returns a page of customer info objects owned by the specified customer. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getCustomerCustomerInfos", "parameters": [ { - "name": "dashboardId", + "name": "customerId", "in": "path", - "description": "A string value representing the dashboard id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "description": "A string value representing the customer id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { "type": "string" } - } - ], - "responses": { - "200": { - "description": "OK", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/DashboardInfo" - } - } - } }, - "400": { - "description": "Bad Request", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ThingsboardErrorResponse" - }, - "examples": { - "error-code-400": { - "summary": "Bad Request", - "value": { - "status": 400, - "message": "Invalid UUID string: 123", - "errorCode": 31, - "timestamp": 1609459200000 - } - } - } - } + { + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", + "required": true, + "schema": { + "type": "integer", + "format": "int32" } }, - "401": { - "description": "Unauthorized", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ThingsboardErrorResponse" - }, - "examples": { - "error-code-401": { - "summary": "Unauthorized", - "value": { - "status": 401, - "message": "Authentication failed", - "errorCode": 10, - "timestamp": 1609459200000 - } - } - } - } + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", + "required": true, + "schema": { + "type": "integer", + "format": "int32" } }, - "403": { - "description": "Forbidden", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ThingsboardErrorResponse" - }, - "examples": { - "error-code-403": { - "summary": "Forbidden", - "value": { - "status": 403, - "message": "You don't have permission to perform this operation!", - "errorCode": 20, - "timestamp": 1609459200000 - } - } - } - } + { + "name": "includeCustomers", + "in": "query", + "description": "Include customer or sub-customer entities", + "required": false, + "schema": { + "type": "boolean" } }, - "404": { - "description": "Not Found", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ThingsboardErrorResponse" - }, - "examples": { - "error-code-404": { - "summary": "Not Found", - "value": { - "status": 404, - "message": "Requested item wasn't found!", - "errorCode": 32, - "timestamp": 1609459200000 - } - } - } - } + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'substring' filter based on the customer title.", + "required": false, + "schema": { + "type": "string" } }, - "429": { - "description": "Too Many Requests", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ThingsboardErrorResponse" - }, - "examples": { - "error-code-429": { - "summary": "Too Many Requests", - "value": { - "status": 429, - "message": "Too many requests for current tenant!", - "errorCode": 33, - "timestamp": 1609459200000 - } - } - } - } - } - } - }, - "security": [ { - "HttpLoginForm": [] + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string", + "enum": [ + "createdTime", + "title", + "email", + "country", + "city" + ] + } }, { - "ApiKeyForm": [] + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] + } } - ] - } - }, - "/api/dashboard/maxDatapointsLimit": { - "get": { - "tags": [ - "dashboard-controller" ], - "summary": "Get max data points limit (getMaxDatapointsLimit)", - "description": "Get the maximum number of data points that dashboard may request from the server per in a single subscription command. This value impacts the time window behavior. It impacts 'Max values' parameter in case user selects 'None' as 'Data aggregation function'. It also impacts the 'Grouping interval' in case of any other 'Data aggregation function' is selected. The actual value of the limit is configurable in the system configuration file.", - "operationId": "getMaxDatapointsLimit", "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "type": "integer", - "format": "int64", - "example": 5000 + "$ref": "#/components/schemas/PageDataCustomerInfo" } } } @@ -28311,23 +28212,32 @@ ] } }, - "/api/dashboard/serverTime": { + "/api/customer/{customerId}/shortInfo": { "get": { "tags": [ - "dashboard-controller" + "customer-controller" + ], + "summary": "Get short Customer info (getShortCustomerInfoById)", + "description": "Get the short customer object that contains only the title and 'isPublic' flag. If the user has the authority of 'Tenant Administrator', the server checks that the customer is owned by the same tenant. If the user has the authority of 'Customer User', the server checks that the user belongs to the customer.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getShortCustomerInfoById", + "parameters": [ + { + "name": "customerId", + "in": "path", + "description": "A string value representing the customer id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, + "schema": { + "type": "string" + } + } ], - "summary": "Get server time (getServerTime)", - "description": "Get the server time (milliseconds since January 1, 1970 UTC). Used to adjust view of the dashboards according to the difference between browser and server time.", - "operationId": "getServerTime", "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "type": "integer", - "format": "int64", - "example": 1636023857137 + "$ref": "#/components/schemas/JsonNode" } } } @@ -28448,49 +28358,32 @@ ] } }, - "/api/dashboard/{dashboardId}": { + "/api/customer/{customerId}/title": { "get": { "tags": [ - "dashboard-controller" + "customer-controller" ], - "summary": "Get Dashboard (getDashboardById)", - "description": "Get the dashboard based on 'dashboardId' parameter. The Dashboard object is a heavyweight object that contains information about the dashboard (e.g. title, image, assigned customers) and also configuration JSON (e.g. layouts, widgets, entity aliases).\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", - "operationId": "getDashboardById", + "summary": "Get Customer Title (getCustomerTitleById)", + "description": "Get the title of the customer. If the user has the authority of 'Tenant Administrator', the server checks that the customer is owned by the same tenant. If the user has the authority of 'Customer User', the server checks that the user belongs to the customer.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getCustomerTitleById", "parameters": [ { - "name": "dashboardId", + "name": "customerId", "in": "path", - "description": "A string value representing the dashboard id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "description": "A string value representing the customer id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { "type": "string" } - }, - { - "name": "includeResources", - "in": "query", - "description": "Export used resources and replace resource links with resource metadata", - "required": false, - "schema": { - "type": "boolean" - } - }, - { - "name": "Accept-Encoding", - "in": "header", - "required": false, - "schema": { - "type": "string" - } } ], "responses": { "200": { "description": "OK", "content": { - "application/json": { + "application/text": { "schema": { - "$ref": "#/components/schemas/Dashboard" + "type": "string" } } } @@ -28609,164 +28502,82 @@ "ApiKeyForm": [] } ] - }, - "delete": { + } + }, + "/api/customerInfos/all": { + "get": { "tags": [ - "dashboard-controller" + "customer-controller" ], - "summary": "Delete the Dashboard (deleteDashboard)", - "description": "Delete the Dashboard. Only users with 'TENANT_ADMIN') authority may delete the dashboards.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", - "operationId": "deleteDashboard", + "summary": "Get All Customer Infos for current user (getAllCustomerInfos)", + "description": "Returns a page of customer info objects owned by the tenant or the customer of a current user. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getAllCustomerInfos", "parameters": [ { - "name": "dashboardId", - "in": "path", - "description": "A string value representing the dashboard id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", "required": true, "schema": { - "type": "string" - } - } - ], - "responses": { - "200": { - "description": "OK" - }, - "400": { - "description": "Bad Request", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ThingsboardErrorResponse" - }, - "examples": { - "error-code-400": { - "summary": "Bad Request", - "value": { - "status": 400, - "message": "Invalid UUID string: 123", - "errorCode": 31, - "timestamp": 1609459200000 - } - } - } - } + "type": "integer", + "format": "int32" } }, - "401": { - "description": "Unauthorized", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ThingsboardErrorResponse" - }, - "examples": { - "error-code-401": { - "summary": "Unauthorized", - "value": { - "status": 401, - "message": "Authentication failed", - "errorCode": 10, - "timestamp": 1609459200000 - } - } - } - } + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", + "required": true, + "schema": { + "type": "integer", + "format": "int32" } }, - "403": { - "description": "Forbidden", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ThingsboardErrorResponse" - }, - "examples": { - "error-code-403": { - "summary": "Forbidden", - "value": { - "status": 403, - "message": "You don't have permission to perform this operation!", - "errorCode": 20, - "timestamp": 1609459200000 - } - } - } - } + { + "name": "includeCustomers", + "in": "query", + "description": "Include customer or sub-customer entities", + "required": false, + "schema": { + "type": "boolean" } }, - "404": { - "description": "Not Found", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ThingsboardErrorResponse" - }, - "examples": { - "error-code-404": { - "summary": "Not Found", - "value": { - "status": 404, - "message": "Requested item wasn't found!", - "errorCode": 32, - "timestamp": 1609459200000 - } - } - } - } + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'substring' filter based on the customer title.", + "required": false, + "schema": { + "type": "string" } }, - "429": { - "description": "Too Many Requests", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ThingsboardErrorResponse" - }, - "examples": { - "error-code-429": { - "summary": "Too Many Requests", - "value": { - "status": 429, - "message": "Too many requests for current tenant!", - "errorCode": 33, - "timestamp": 1609459200000 - } - } - } - } - } - } - }, - "security": [ { - "HttpLoginForm": [] + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string", + "enum": [ + "createdTime", + "title", + "email", + "country", + "city" + ] + } }, { - "ApiKeyForm": [] - } - ] - } - }, - "/api/dashboards": { - "get": { - "tags": [ - "dashboard-controller" - ], - "summary": "Get dashboards by Dashboard Ids (getDashboardsByIds)", - "description": "Returns a list of DashboardInfo objects based on the provided ids. Filters the list based on the user permissions. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getDashboardsByIds", - "parameters": [ - { - "name": "dashboardIds", + "name": "sortOrder", "in": "query", - "description": "A list of dashboard ids, separated by comma ','", - "required": true, + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, "schema": { - "type": "array", - "items": { - "type": "string" - } + "type": "string", + "enum": [ + "ASC", + "DESC" + ] } } ], @@ -28776,10 +28587,7 @@ "content": { "application/json": { "schema": { - "type": "array", - "items": { - "$ref": "#/components/schemas/DashboardInfo" - } + "$ref": "#/components/schemas/PageDataCustomerInfo" } } } @@ -28900,14 +28708,14 @@ ] } }, - "/api/dashboards/all": { + "/api/customers": { "get": { "tags": [ - "dashboard-controller" + "customer-controller" ], - "summary": "Get All Dashboards for current user (getAllDashboards)", - "description": "Returns a page of dashboard info objects owned by the tenant or the customer of a current user. The Dashboard Info object contains lightweight information about the dashboard (e.g. title, image, assigned customers) but does not contain the heavyweight configuration JSON. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getAllDashboards", + "summary": "Get Tenant Customers (getCustomers)", + "description": "Returns a page of customers owned by tenant. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getCustomers", "parameters": [ { "name": "pageSize", @@ -28929,19 +28737,10 @@ "format": "int32" } }, - { - "name": "includeCustomers", - "in": "query", - "description": "Include customer or sub-customer entities", - "required": false, - "schema": { - "type": "boolean" - } - }, { "name": "textSearch", "in": "query", - "description": "The case insensitive 'substring' filter based on the dashboard title.", + "description": "The case insensitive 'substring' filter based on the customer title.", "required": false, "schema": { "type": "string" @@ -28956,7 +28755,10 @@ "type": "string", "enum": [ "createdTime", - "title" + "title", + "email", + "country", + "city" ] } }, @@ -28980,7 +28782,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataDashboardInfo" + "$ref": "#/components/schemas/PageDataCustomer" } } } @@ -29101,77 +28903,25 @@ ] } }, - "/api/entityGroup/{entityGroupId}/dashboards": { + "/api/customers/list": { "get": { "tags": [ - "dashboard-controller" + "customer-controller" ], - "summary": "Get dashboards by Entity Group Id (getDashboardsByEntityGroupId)", - "description": "Returns a page of Dashboard objects that belongs to specified Entity Group Id. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", - "operationId": "getDashboardsByEntityGroupId", + "summary": "Get customers by Customer Ids (getCustomersByIds)", + "description": "Returns a list of Customer objects based on the provided ids.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", + "operationId": "getCustomersByIds", "parameters": [ { - "name": "entityGroupId", - "in": "path", - "description": "A string value representing the Entity Group Id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": true, - "schema": { - "type": "string" - } - }, - { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "page", + "name": "customerIds", "in": "query", - "description": "Sequence number of page starting from 0", + "description": "A list of customer ids, separated by comma ','", "required": true, "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'substring' filter based on the dashboard title.", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, - "schema": { - "type": "string", - "enum": [ - "createdTime", - "title" - ] - } - }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] + "type": "array", + "items": { + "type": "string" + } } } ], @@ -29181,7 +28931,10 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataDashboardInfo" + "type": "array", + "items": { + "$ref": "#/components/schemas/Customer" + } } } } @@ -29302,14 +29055,14 @@ ] } }, - "/api/entityGroup/{entityGroupId}/dashboards/export": { + "/api/entityGroup/{entityGroupId}/customers": { "get": { "tags": [ - "dashboard-controller" + "customer-controller" ], - "summary": "Export Dashboards (exportGroupDashboards)", - "description": "Export the dashboards that belong to specified group id.The Dashboard object is a heavyweight object that contains information about the dashboard (e.g. title, image, assigned customers) and also configuration JSON (e.g. layouts, widgets, entity aliases).\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", - "operationId": "exportGroupDashboards", + "summary": "Get customers by Entity Group Id (getCustomersByEntityGroupId)", + "description": "Returns a page of Customer objects that belongs to specified Entity Group Id. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\n Security check is performed to verify that the user has 'READ' permission for specified group.", + "operationId": "getCustomersByEntityGroupId", "parameters": [ { "name": "entityGroupId", @@ -29321,22 +29074,62 @@ } }, { - "name": "limit", + "name": "pageSize", "in": "query", - "description": "Limit of the entities to export", + "description": "Maximum amount of entities in a one page", "required": true, "schema": { - "type": "integer", - "format": "int32" + "type": "string", + "minimum": 1 } }, { - "name": "Accept-Encoding", - "in": "header", + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", + "required": true, + "schema": { + "type": "string", + "minimum": 0 + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'substring' filter based on the customer title.", "required": false, "schema": { "type": "string" } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string", + "enum": [ + "createdTime", + "title", + "email", + "country", + "city" + ] + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] + } } ], "responses": { @@ -29345,10 +29138,7 @@ "content": { "application/json": { "schema": { - "type": "array", - "items": { - "$ref": "#/components/schemas/Dashboard" - } + "$ref": "#/components/schemas/PageDataCustomer" } } } @@ -29469,53 +29259,36 @@ ] } }, - "/api/entityGroup/{entityGroupId}/dashboards/import": { - "post": { + "/api/tenant/customers": { + "get": { "tags": [ - "dashboard-controller" + "customer-controller" ], - "summary": "Import Dashboards (importGroupDashboards)", - "description": "Import the dashboards to specified group.The Dashboard object is a heavyweight object that contains information about the dashboard (e.g. title, image, assigned customers) and also configuration JSON (e.g. layouts, widgets, entity aliases).\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'WRITE' permission for specified group.", - "operationId": "importGroupDashboards", + "summary": "Get Tenant Customer by Customer title (getTenantCustomer)", + "description": "Get the Customer using Customer Title. \n\nAvailable for users with 'TENANT_ADMIN' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getTenantCustomer", "parameters": [ { - "name": "entityGroupId", - "in": "path", - "description": "A string value representing the Entity Group Id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "name": "customerTitle", + "in": "query", + "description": "A string value representing the Customer title.", "required": true, "schema": { "type": "string" } - }, - { - "name": "overwrite", - "in": "query", - "description": "Overwrite dashboards with the same name", - "required": false, - "schema": { - "type": "boolean", - "default": false - } } ], - "requestBody": { - "content": { - "application/json": { - "schema": { - "type": "array", - "description": "JSON array with the dashboard objects", - "items": { - "$ref": "#/components/schemas/Dashboard" + "responses": { + "200": { + "description": "OK", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/Customer" } } } }, - "required": true - }, - "responses": { - "200": { - "description": "OK" - }, "400": { "description": "Bad Request", "content": { @@ -29528,7 +29301,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -29632,21 +29405,81 @@ ] } }, - "/api/tenant/dashboard/home/info": { + "/api/user/customers": { "get": { "tags": [ - "dashboard-controller" + "customer-controller" + ], + "summary": "Get Customers (getUserCustomers)", + "description": "Returns a page of customers available for the user. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getUserCustomers", + "parameters": [ + { + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", + "required": true, + "schema": { + "type": "string", + "minimum": 1 + } + }, + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", + "required": true, + "schema": { + "type": "string", + "minimum": 0 + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'substring' filter based on the customer title.", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string", + "enum": [ + "createdTime", + "title", + "email", + "country", + "city" + ] + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] + } + } ], - "summary": "Get Tenant Home Dashboard Info (getTenantHomeDashboardInfo)", - "description": "Returns the home dashboard info object that is configured as 'homeDashboardId' parameter in the 'additionalInfo' of the corresponding tenant. \n\nAvailable for users with 'TENANT_ADMIN' authority.\n\nSecurity check is performed to verify that the user has 'READ' permission for the white labeling resource.", - "operationId": "getTenantHomeDashboardInfo", "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/HomeDashboardInfo" + "$ref": "#/components/schemas/PageDataCustomer" } } } @@ -29765,27 +29598,26 @@ "ApiKeyForm": [] } ] - }, - "post": { + } + }, + "/api/customer/dashboard/home/info": { + "get": { "tags": [ "dashboard-controller" ], - "summary": "Update Tenant Home Dashboard Info (getTenantHomeDashboardInfo)", - "description": "Update the home dashboard assignment for the current tenant. \n\nAvailable for users with 'TENANT_ADMIN' authority.\n\nSecurity check is performed to verify that the user has 'WRITE' permission for the white labeling resource.", - "operationId": "setTenantHomeDashboardInfo", - "requestBody": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/HomeDashboardInfo" - } - } - }, - "required": true - }, + "summary": "Get Customer Home Dashboard Info (getCustomerHomeDashboardInfo)", + "description": "Returns the home dashboard info object that is configured as 'homeDashboardId' parameter in the 'additionalInfo' of the corresponding customer. \n\nAvailable for users with 'CUSTOMER_USER' authority.\n\nSecurity check is performed to verify that the user has 'READ' permission for the white labeling resource.", + "operationId": "getCustomerHomeDashboardInfo", "responses": { "200": { - "description": "OK" + "description": "OK", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/HomeDashboardInfo" + } + } + } }, "400": { "description": "Bad Request", @@ -29799,7 +29631,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -29901,92 +29733,27 @@ "ApiKeyForm": [] } ] - } - }, - "/api/tenant/dashboards": { - "get": { + }, + "post": { "tags": [ "dashboard-controller" ], - "summary": "Get Tenant Dashboards (getTenantDashboards)", - "description": "Returns a page of dashboard info objects owned by the tenant of a current user. The Dashboard Info object contains lightweight information about the dashboard (e.g. title, image, assigned customers) but does not contain the heavyweight configuration JSON. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "getTenantDashboards", - "parameters": [ - { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", - "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "mobile", - "in": "query", - "description": "Exclude dashboards that are hidden for mobile", - "required": false, - "schema": { - "type": "boolean" - } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'substring' filter based on the dashboard title.", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, - "schema": { - "type": "string", - "enum": [ - "createdTime", - "title" - ] + "summary": "Update Customer Home Dashboard Info (setCustomerHomeDashboardInfo)", + "description": "Update the home dashboard assignment for the current customer. \n\nAvailable for users with 'CUSTOMER_USER' authority.\n\nSecurity check is performed to verify that the user has 'WRITE' permission for the white labeling resource.", + "operationId": "setCustomerHomeDashboardInfo", + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/HomeDashboardInfo" + } } }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] - } - } - ], + "required": true + }, "responses": { "200": { - "description": "OK", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/PageDataDashboardInfo" - } - } - } + "description": "OK" }, "400": { "description": "Bad Request", @@ -30000,7 +29767,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -30104,19 +29871,19 @@ ] } }, - "/api/tenant/{tenantId}/dashboards": { + "/api/customer/{customerId}/dashboards": { "get": { "tags": [ "dashboard-controller" ], - "summary": "Get Tenant Dashboards by System Administrator (getTenantDashboardsByTenantId)", - "description": "Returns a page of dashboard info objects owned by tenant. The Dashboard Info object contains lightweight information about the dashboard (e.g. title, image, assigned customers) but does not contain the heavyweight configuration JSON. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'SYS_ADMIN' authority.", - "operationId": "getTenantDashboardsByTenantId", + "summary": "Get Customer Dashboards (getCustomerDashboards)", + "description": "Returns a page of dashboard info objects owned by the specified customer. The Dashboard Info object contains lightweight information about the dashboard (e.g. title, image, assigned customers) but does not contain the heavyweight configuration JSON. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getCustomerDashboards", "parameters": [ { - "name": "tenantId", + "name": "customerId", "in": "path", - "description": "A string value representing the tenant id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "description": "A string value representing the customer id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { "type": "string" @@ -30142,6 +29909,15 @@ "format": "int32" } }, + { + "name": "includeCustomers", + "in": "query", + "description": "Include customer or sub-customer entities", + "required": false, + "schema": { + "type": "boolean" + } + }, { "name": "textSearch", "in": "query", @@ -30305,105 +30081,62 @@ ] } }, - "/api/user/dashboards": { - "get": { + "/api/dashboard": { + "post": { "tags": [ "dashboard-controller" ], - "summary": "Get Dashboards (getUserDashboards)", - "description": "Returns a page of Dashboard Info objects available for specified or current user. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. The Dashboard Info object contains lightweight information about the dashboard (e.g. title, image, assigned customers) but does not contain the heavyweight configuration JSON.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getUserDashboards", + "summary": "Create Or Update Dashboard (saveDashboard)", + "description": "Create or update the Dashboard. When creating dashboard, platform generates Dashboard Id as [time-based UUID](https://en.wikipedia.org/wiki/Universally_unique_identifier#Version_1_(date-time_and_MAC_address)). The newly created Dashboard id will be present in the response. Specify existing Dashboard id to update the dashboard. Referencing non-existing dashboard Id will cause 'Not Found' error. Only users with 'TENANT_ADMIN') authority may create the dashboards.Remove 'id', 'tenantId' and optionally 'customerId' from the request body example (below) to create new Dashboard entity. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", + "operationId": "saveDashboard", "parameters": [ { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", - "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "mobile", - "in": "query", - "description": "Exclude dashboards that are hidden for mobile", - "required": false, - "schema": { - "type": "boolean" - } - }, - { - "name": "textSearch", + "name": "entityGroupId", "in": "query", - "description": "The case insensitive 'substring' filter based on the dashboard title.", "required": false, "schema": { "type": "string" } }, { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, - "schema": { - "type": "string", - "enum": [ - "createdTime", - "title" - ] - } - }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] - } - }, - { - "name": "operation", + "name": "entityGroupIds", "in": "query", - "description": "Filter by allowed operations for the current user", + "description": "A list of entity group ids, separated by comma ','", "required": false, "schema": { - "type": "string" + "type": "array", + "items": { + "type": "string" + } } }, { - "name": "userId", - "in": "query", - "description": "A string value representing the user id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "name": "Accept-Encoding", + "in": "header", "required": false, "schema": { "type": "string" } } ], + "requestBody": { + "description": "A JSON value representing the dashboard.", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/Dashboard" + } + } + }, + "required": true + }, "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataDashboardInfo" + "$ref": "#/components/schemas/Dashboard" } } } @@ -30420,7 +30153,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -30524,56 +30257,31 @@ ] } }, - "/api/report/test": { - "post": { + "/api/dashboard/home": { + "get": { "tags": [ - "dashboard-report-controller" + "dashboard-controller" ], - "summary": "Download test report (downloadTestReport)", - "description": "Generate and download test report.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", - "operationId": "downloadTestReport", + "summary": "Get Home Dashboard (getHomeDashboard)", + "description": "Returns the home dashboard object that is configured as 'homeDashboardId' parameter in the 'additionalInfo' of the User. If 'homeDashboardId' parameter is not set on the User level and the User has authority 'CUSTOMER_USER', check the same parameter for the corresponding Customer. If 'homeDashboardId' parameter is not set on the User and Customer levels then checks the same parameter for the Tenant that owns the user. The Dashboard object is a heavyweight object that contains information about the dashboard (e.g. title, image, assigned customers) and also configuration JSON (e.g. layouts, widgets, entity aliases).\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", + "operationId": "getHomeDashboard", "parameters": [ { - "name": "reportsServerEndpointUrl", - "in": "query", - "description": "A string value representing the report server endpoint.", + "name": "Accept-Encoding", + "in": "header", "required": false, "schema": { "type": "string" - }, - "example": "http://localhost:8383" + } } ], - "requestBody": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/DashboardReportConfig" - } - } - }, - "required": true - }, "responses": { "200": { "description": "OK", "content": { - "application/pdf": { - "schema": { - "type": "string", - "format": "binary" - } - }, - "image/jpeg": { - "schema": { - "type": "string", - "format": "binary" - } - }, - "image/png": { + "application/json": { "schema": { - "type": "string", - "format": "binary" + "$ref": "#/components/schemas/HomeDashboard" } } } @@ -30590,7 +30298,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -30694,55 +30402,21 @@ ] } }, - "/api/report/{dashboardId}/download": { - "post": { + "/api/dashboard/home/info": { + "get": { "tags": [ - "dashboard-report-controller" - ], - "summary": "Download dashboard report (downloadDashboardReport)", - "description": "Generate and download a report from the specified dashboard. The request payload is a JSON object with params of report. For example:\n\n```json\n{\n \"type\": \"pdf\",\n \"timezone\": \"Europe/Kiev\",\n \"timewindow\": {\n \"displayValue\": \"\",\n \"hideInterval\": false,\n \"hideLastInterval\": false,\n \"hideQuickInterval\": false,\n \"hideAggregation\": false,\n \"hideAggInterval\": false,\n \"hideTimezone\": false,\n \"selectedTab\": 0,\n \"realtime\": {\n \"realtimeType\": 0,\n \"interval\": 1000,\n \"timewindowMs\": 60000,\n \"quickInterval\": \"CURRENT_DAY\"\n },\n \"history\": {\n \"historyType\": 0,\n \"interval\": 1000,\n \"timewindowMs\": 60000,\n \"fixedTimewindow\": {\n \"startTimeMs\": 1703687976592,\n \"endTimeMs\": 1703774376592\n },\n \"quickInterval\": \"CURRENT_DAY\"\n },\n \"aggregation\": {\n \"type\": \"AVG\",\n \"limit\": 25000\n }\n },\n \"state\": null\n}\n```\n\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", - "operationId": "downloadDashboardReport", - "parameters": [ - { - "name": "dashboardId", - "in": "path", - "description": "A string value representing the dashboard id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": true, - "schema": { - "type": "string" - } - } + "dashboard-controller" ], - "requestBody": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/JsonNode" - } - } - }, - "required": true - }, + "summary": "Get Home Dashboard Info (getHomeDashboardInfo)", + "description": "Returns the home dashboard info object that is configured as 'homeDashboardId' parameter in the 'additionalInfo' of the User. If 'homeDashboardId' parameter is not set on the User level and the User has authority 'CUSTOMER_USER', check the same parameter for the corresponding Customer. If 'homeDashboardId' parameter is not set on the User and Customer levels then checks the same parameter for the Tenant that owns the user. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", + "operationId": "getHomeDashboardInfo", "responses": { "200": { "description": "OK", "content": { - "application/pdf": { - "schema": { - "type": "string", - "format": "binary" - } - }, - "image/jpeg": { - "schema": { - "type": "string", - "format": "binary" - } - }, - "image/png": { + "application/json": { "schema": { - "type": "string", - "format": "binary" + "$ref": "#/components/schemas/HomeDashboardInfo" } } } @@ -30759,7 +30433,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -30863,19 +30537,19 @@ ] } }, - "/api/device-connectivity/gateway-launch/{deviceId}/docker-compose/download": { + "/api/dashboard/info/{dashboardId}": { "get": { "tags": [ - "device-connectivity-controller" + "dashboard-controller" ], - "summary": "Download generated docker-compose.yml file for gateway (downloadGatewayDockerCompose)", - "description": "Download generated docker-compose.yml for gateway.", - "operationId": "downloadGatewayDockerCompose", + "summary": "Get Dashboard Info (getDashboardInfoById)", + "description": "Get the information about the dashboard based on 'dashboardId' parameter. The Dashboard Info object contains lightweight information about the dashboard (e.g. title, image, assigned customers) but does not contain the heavyweight configuration JSON.", + "operationId": "getDashboardInfoById", "parameters": [ { - "name": "deviceId", + "name": "dashboardId", "in": "path", - "description": "A string value representing the device id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "description": "A string value representing the dashboard id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { "type": "string" @@ -30886,10 +30560,9 @@ "200": { "description": "OK", "content": { - "application/octet-stream": { + "application/json": { "schema": { - "type": "string", - "format": "binary" + "$ref": "#/components/schemas/DashboardInfo" } } } @@ -31010,50 +30683,164 @@ ] } }, - "/api/device-connectivity/{deviceId}": { + "/api/dashboard/maxDatapointsLimit": { "get": { "tags": [ - "device-connectivity-controller" - ], - "summary": "Get commands to publish device telemetry (getDevicePublishTelemetryCommands)", - "description": "Fetch the list of commands to publish device telemetry based on device profile If the user has the authority of 'Tenant Administrator', the server checks that the device is owned by the same tenant. If the user has the authority of 'Customer User', the server checks that the device is assigned to the same customer. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", - "operationId": "getDevicePublishTelemetryCommands", - "parameters": [ - { - "name": "deviceId", - "in": "path", - "description": "A string value representing the device id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": true, - "schema": { - "type": "string" - } - } + "dashboard-controller" ], + "summary": "Get max data points limit (getMaxDatapointsLimit)", + "description": "Get the maximum number of data points that dashboard may request from the server per in a single subscription command. This value impacts the time window behavior. It impacts 'Max values' parameter in case user selects 'None' as 'Data aggregation function'. It also impacts the 'Grouping interval' in case of any other 'Data aggregation function' is selected. The actual value of the limit is configurable in the system configuration file.", + "operationId": "getMaxDatapointsLimit", "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/JsonNode" + "type": "integer", + "format": "int64", + "example": 5000 + } + } + } + }, + "400": { + "description": "Bad Request", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" }, "examples": { - "http": { - "description": "http", - "value": "curl -v -X POST http://localhost:8080/api/v1/0ySs4FTOn5WU15XLmal8/telemetry --header Content-Type:application/json --data {temperature:25}" - }, - "mqtt": { - "description": "mqtt", - "value": "mosquitto_pub -d -q 1 -h localhost -t v1/devices/me/telemetry -i myClient1 -u myUsername1 -P myPassword -m {temperature:25}" - }, - "coap": { - "description": "coap", - "value": "coap-client -m POST coap://localhost:5683/api/v1/0ySs4FTOn5WU15XLmal8/telemetry -t json -e {temperature:25}" + "error-code-400": { + "summary": "Bad Request", + "value": { + "status": 400, + "message": "Invalid UUID string: 123", + "errorCode": 31, + "timestamp": 1609459200000 + } } } } } }, + "401": { + "description": "Unauthorized", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-401": { + "summary": "Unauthorized", + "value": { + "status": 401, + "message": "Authentication failed", + "errorCode": 10, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "403": { + "description": "Forbidden", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-403": { + "summary": "Forbidden", + "value": { + "status": 403, + "message": "You don't have permission to perform this operation!", + "errorCode": 20, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "404": { + "description": "Not Found", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-404": { + "summary": "Not Found", + "value": { + "status": 404, + "message": "Requested item wasn't found!", + "errorCode": 32, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "429": { + "description": "Too Many Requests", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-429": { + "summary": "Too Many Requests", + "value": { + "status": 429, + "message": "Too many requests for current tenant!", + "errorCode": 33, + "timestamp": 1609459200000 + } + } + } + } + } + } + }, + "security": [ + { + "HttpLoginForm": [] + }, + { + "ApiKeyForm": [] + } + ] + } + }, + "/api/dashboard/serverTime": { + "get": { + "tags": [ + "dashboard-controller" + ], + "summary": "Get server time (getServerTime)", + "description": "Get the server time (milliseconds since January 1, 1970 UTC). Used to adjust view of the dashboards according to the difference between browser and server time.", + "operationId": "getServerTime", + "responses": { + "200": { + "description": "OK", + "content": { + "application/json": { + "schema": { + "type": "integer", + "format": "int64", + "example": 1636023857137 + } + } + } + }, "400": { "description": "Bad Request", "content": { @@ -31170,33 +30957,49 @@ ] } }, - "/api/device-connectivity/{protocol}/certificate/download": { + "/api/dashboard/{dashboardId}": { "get": { "tags": [ - "device-connectivity-controller" + "dashboard-controller" ], - "summary": "Download server certificate using file path defined in device.connectivity properties (downloadServerCertificate)", - "description": "Download server certificate.", - "operationId": "downloadServerCertificate", + "summary": "Get Dashboard (getDashboardById)", + "description": "Get the dashboard based on 'dashboardId' parameter. The Dashboard object is a heavyweight object that contains information about the dashboard (e.g. title, image, assigned customers) and also configuration JSON (e.g. layouts, widgets, entity aliases).\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", + "operationId": "getDashboardById", "parameters": [ { - "name": "protocol", + "name": "dashboardId", "in": "path", - "description": "A string value representing the device connectivity protocol. Possible values: 'mqtt', 'mqtts', 'http', 'https', 'coap', 'coaps'", + "description": "A string value representing the dashboard id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { "type": "string" } + }, + { + "name": "includeResources", + "in": "query", + "description": "Export used resources and replace resource links with resource metadata", + "required": false, + "schema": { + "type": "boolean" + } + }, + { + "name": "Accept-Encoding", + "in": "header", + "required": false, + "schema": { + "type": "string" + } } ], "responses": { "200": { "description": "OK", "content": { - "application/octet-stream": { + "application/json": { "schema": { - "type": "string", - "format": "binary" + "$ref": "#/components/schemas/Dashboard" } } } @@ -31315,54 +31118,28 @@ "ApiKeyForm": [] } ] - } - }, - "/api/customer/device/{deviceName}/claim": { - "post": { + }, + "delete": { "tags": [ - "device-controller" + "dashboard-controller" ], - "summary": "Claim device (claimDevice)", - "description": "Claiming makes it possible to assign a device to the specific customer using device/server side claiming data (in the form of secret key).To make this happen you have to provide unique device name and optional claiming data (it is needed only for device-side claiming).Once device is claimed, the customer becomes its owner and customer users may access device data as well as control the device. \nIn order to enable claiming devices feature a system parameter security.claim.allowClaimingByDefault should be set to true, otherwise a server-side claimingAllowed attribute with the value true is obligatory for provisioned devices. \nSee official documentation for more details regarding claiming.\n\nAvailable for users with 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'CLAIM_DEVICES' permission for the entity (entities).", - "operationId": "claimDevice", + "summary": "Delete the Dashboard (deleteDashboard)", + "description": "Delete the Dashboard. Only users with 'TENANT_ADMIN') authority may delete the dashboards.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", + "operationId": "deleteDashboard", "parameters": [ { - "name": "deviceName", + "name": "dashboardId", "in": "path", - "description": "Unique name of the device which is going to be claimed", + "description": "A string value representing the dashboard id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { "type": "string" } - }, - { - "name": "subCustomerId", - "in": "query", - "required": false, - "schema": { - "type": "string" - } } ], - "requestBody": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ClaimRequest" - } - } - } - }, "responses": { "200": { - "description": "OK", - "content": { - "application/json": { - "schema": { - "type": "string" - } - } - } + "description": "OK" }, "400": { "description": "Bad Request", @@ -31376,7 +31153,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -31478,22 +31255,27 @@ "ApiKeyForm": [] } ] - }, - "delete": { + } + }, + "/api/dashboards": { + "get": { "tags": [ - "device-controller" + "dashboard-controller" ], - "summary": "Reclaim device (reClaimDevice)", - "description": "Reclaiming means the device will be unassigned from the customer and the device will be available for claiming again.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'CLAIM_DEVICES' permission for the entity (entities).", - "operationId": "reClaimDevice", + "summary": "Get dashboards by Dashboard Ids (getDashboardsByIds)", + "description": "Returns a list of DashboardInfo objects based on the provided ids. Filters the list based on the user permissions. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getDashboardsByIds", "parameters": [ { - "name": "deviceName", - "in": "path", - "description": "Unique name of the device which is going to be reclaimed", + "name": "dashboardIds", + "in": "query", + "description": "A list of dashboard ids, separated by comma ','", "required": true, "schema": { - "type": "string" + "type": "array", + "items": { + "type": "string" + } } } ], @@ -31503,7 +31285,10 @@ "content": { "application/json": { "schema": { - "type": "string" + "type": "array", + "items": { + "$ref": "#/components/schemas/DashboardInfo" + } } } } @@ -31624,24 +31409,15 @@ ] } }, - "/api/customer/{customerId}/deviceInfos": { + "/api/dashboards/all": { "get": { "tags": [ - "device-controller" + "dashboard-controller" ], - "summary": "Get Customer Device Infos (getCustomerDeviceInfos)", - "description": "Returns a page of device info objects owned by the specified customer. Device Info is an extension of the default Device object that contains information about the owner name. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getCustomerDeviceInfos", + "summary": "Get All Dashboards for current user (getAllDashboards)", + "description": "Returns a page of dashboard info objects owned by the tenant or the customer of a current user. The Dashboard Info object contains lightweight information about the dashboard (e.g. title, image, assigned customers) but does not contain the heavyweight configuration JSON. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getAllDashboards", "parameters": [ - { - "name": "customerId", - "in": "path", - "description": "A string value representing the customer id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": true, - "schema": { - "type": "string" - } - }, { "name": "pageSize", "in": "query", @@ -31671,28 +31447,10 @@ "type": "boolean" } }, - { - "name": "deviceProfileId", - "in": "query", - "description": "A string value representing the device profile id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "active", - "in": "query", - "description": "A boolean value representing the device active flag.", - "required": false, - "schema": { - "type": "boolean" - } - }, { "name": "textSearch", "in": "query", - "description": "The case insensitive 'substring' filter based on the device name.", + "description": "The case insensitive 'substring' filter based on the dashboard title.", "required": false, "schema": { "type": "string" @@ -31707,10 +31465,7 @@ "type": "string", "enum": [ "createdTime", - "name", - "deviceProfileName", - "label", - "customerTitle" + "title" ] } }, @@ -31734,7 +31489,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataDeviceInfo" + "$ref": "#/components/schemas/PageDataDashboardInfo" } } } @@ -31855,19 +31610,19 @@ ] } }, - "/api/customer/{customerId}/devices": { + "/api/entityGroup/{entityGroupId}/dashboards": { "get": { "tags": [ - "device-controller" + "dashboard-controller" ], - "summary": "Get Customer Devices (getCustomerDevices)", - "description": "Returns a page of devices objects assigned to customer. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getCustomerDevices", + "summary": "Get dashboards by Entity Group Id (getDashboardsByEntityGroupId)", + "description": "Returns a page of Dashboard objects that belongs to specified Entity Group Id. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", + "operationId": "getDashboardsByEntityGroupId", "parameters": [ { - "name": "customerId", + "name": "entityGroupId", "in": "path", - "description": "A string value representing the customer id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "description": "A string value representing the Entity Group Id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { "type": "string" @@ -31893,19 +31648,10 @@ "format": "int32" } }, - { - "name": "type", - "in": "query", - "description": "Device type as the name of the device profile", - "required": false, - "schema": { - "type": "string" - } - }, { "name": "textSearch", "in": "query", - "description": "The case insensitive 'substring' filter based on the device name.", + "description": "The case insensitive 'substring' filter based on the dashboard title.", "required": false, "schema": { "type": "string" @@ -31920,10 +31666,7 @@ "type": "string", "enum": [ "createdTime", - "name", - "deviceProfileName", - "label", - "customerTitle" + "title" ] } }, @@ -31947,7 +31690,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataDevice" + "$ref": "#/components/schemas/PageDataDashboardInfo" } } } @@ -32068,93 +31811,53 @@ ] } }, - "/api/device": { - "post": { + "/api/entityGroup/{entityGroupId}/dashboards/export": { + "get": { "tags": [ - "device-controller" + "dashboard-controller" ], - "summary": "Create Or Update Device (saveDevice)", - "description": "Create or update the Device. When creating device, platform generates Device Id as [time-based UUID](https://en.wikipedia.org/wiki/Universally_unique_identifier#Version_1_(date-time_and_MAC_address)). Device credentials are also generated if not provided in the 'accessToken' request parameter. The newly created device id will be present in the response. Specify existing Device id to update the device. Referencing non-existing device Id will cause 'Not Found' error.\n\nDevice name is unique in the scope of tenant. Use unique identifiers like MAC or IMEI for the device names and non-unique 'label' field for user-friendly visualization purposes.Remove 'id', 'tenantId' and optionally 'customerId' from the request body example (below) to create new Device entity. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'WRITE' permission for the entity (entities).", - "operationId": "saveDevice", + "summary": "Export Dashboards (exportGroupDashboards)", + "description": "Export the dashboards that belong to specified group id.The Dashboard object is a heavyweight object that contains information about the dashboard (e.g. title, image, assigned customers) and also configuration JSON (e.g. layouts, widgets, entity aliases).\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", + "operationId": "exportGroupDashboards", "parameters": [ - { - "name": "accessToken", - "in": "query", - "description": "Optional value of the device credentials to be used during device creation. If omitted, access token will be auto-generated.", - "required": false, - "schema": { - "type": "string" - } - }, { "name": "entityGroupId", - "in": "query", - "required": false, + "in": "path", + "description": "A string value representing the Entity Group Id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, "schema": { "type": "string" } }, { - "name": "entityGroupIds", - "in": "query", - "description": "A list of entity group ids, separated by comma ','", - "required": false, - "schema": { - "type": "array", - "items": { - "type": "string" - } - } - }, - { - "name": "nameConflictPolicy", - "in": "query", - "description": "Optional value of name conflict policy. Possible values: FAIL or UNIQUIFY. If omitted, FAIL policy is applied. FAIL policy implies exception will be thrown if an entity with the same name already exists. UNIQUIFY policy appends a suffix to the entity name, if a name conflict occurs.", - "required": false, - "schema": { - "$ref": "#/components/schemas/NameConflictPolicy", - "default": "FAIL" - } - }, - { - "name": "uniquifySeparator", + "name": "limit", "in": "query", - "description": "Optional value of name suffix separator used by UNIQUIFY policy. By default, underscore separator is used. For example, strategy is UNIQUIFY, separator is '-'; if a name conflict occurs for entity name 'test-name', created entity will have name like 'test-name-7fsh4f'.", - "required": false, + "description": "Limit of the entities to export", + "required": true, "schema": { - "type": "string", - "default": "_" + "type": "integer", + "format": "int32" } }, { - "name": "uniquifyStrategy", - "in": "query", - "description": "Optional value of uniquify strategy used by UNIQUIFY policy. Possible values: RANDOM or INCREMENTAL. By default, RANDOM strategy is used, which means random alphanumeric string will be added as a suffix to entity name. INCREMENTAL implies the first possible number starting from 1 will be added as a name suffix. For example, strategy is UNIQUIFY, uniquify strategy is INCREMENTAL; if a name conflict occurs for entity name 'test-name', created entity will have name like 'test-name-1.", + "name": "Accept-Encoding", + "in": "header", "required": false, "schema": { - "$ref": "#/components/schemas/UniquifyStrategy", - "default": "RANDOM" + "type": "string" } } ], - "requestBody": { - "description": "A JSON value representing the device.", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/Device" - } - } - }, - "required": true - }, "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/Device" + "type": "array", + "items": { + "$ref": "#/components/schemas/Dashboard" + } } } } @@ -32171,7 +31874,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -32275,63 +31978,32 @@ ] } }, - "/api/device-with-credentials": { + "/api/entityGroup/{entityGroupId}/dashboards/import": { "post": { "tags": [ - "device-controller" + "dashboard-controller" ], - "summary": "Create Device (saveDevice) with credentials ", - "description": "Create or update the Device. When creating device, platform generates Device Id as [time-based UUID](https://en.wikipedia.org/wiki/Universally_unique_identifier#Version_1_(date-time_and_MAC_address)). Requires to provide the Device Credentials object as well as an existing device profile ID or use \"default\".\nYou may find the example of device with different type of credentials below: \n\n- Credentials type: **\"Access token\"** with **device profile ID** below: \n\n```json\n{\n \"device\": {\n \"name\":\"Name_DeviceWithCredantial_AccessToken\",\n \"label\":\"Label_DeviceWithCredantial_AccessToken\",\n \"deviceProfileId\":{\n \"id\":\"5636aba0-1022-11ee-9631-51fb57f69174\",\n \"entityType\":\"DEVICE_PROFILE\"\n }\n },\n \"credentials\": {\n \"credentialsType\": \"ACCESS_TOKEN\",\n \"credentialsId\": \"6hmxew8pmmzng4e3une2\"\n }\n}\n```\n\n- Credentials type: **\"Access token\"** with **device profile default** below: \n\n```json\n{\n \"device\": {\n \"name\":\"Name_DeviceWithCredantial_AccessToken_Default\",\n \"label\":\"Label_DeviceWithCredantial_AccessToken_Default\",\n \"type\": \"default\"\n },\n \"credentials\": {\n \"credentialsType\": \"ACCESS_TOKEN\",\n \"credentialsId\": \"6hmxew8pmmzng4e3une3\"\n }\n}\n```\n\n- Credentials type: **\"X509\"** with **device profile ID** below: \n\nNote: **credentialsId** - format **Sha3Hash**, **certificateValue** - format **PEM** (with \"--BEGIN CERTIFICATE----\" and -\"----END CERTIFICATE-\").\n\n```json\n{\n \"device\": {\n \"name\":\"Name_DeviceWithCredantial_X509_Certificate\",\n \"label\":\"Label_DeviceWithCredantial_X509_Certificate\",\n \"deviceProfileId\":{\n \"id\":\"9d9588c0-06c9-11ee-b618-19be30fdeb60\",\n \"entityType\":\"DEVICE_PROFILE\"\n }\n },\n \"credentials\": {\n \"credentialsType\": \"X509_CERTIFICATE\",\n \"credentialsId\": \"84f5911765abba1f96bf4165604e9e90338fc6214081a8e623b6ff9669aedb27\",\n \"credentialsValue\": \"-----BEGIN CERTIFICATE----- MIICMTCCAdegAwIBAgIUI9dBuwN6pTtK6uZ03rkiCwV4wEYwCgYIKoZIzj0EAwIwbjELMAkGA1UEBhMCVVMxETAPBgNVBAgMCE5ldyBZb3JrMRowGAYDVQQKDBFUaGluZ3NCb2FyZCwgSW5jLjEwMC4GA1UEAwwnZGV2aWNlQ2VydGlmaWNhdGVAWDUwOVByb3Zpc2lvblN0cmF0ZWd5MB4XDTIzMDMyOTE0NTYxN1oXDTI0MDMyODE0NTYxN1owbjELMAkGA1UEBhMCVVMxETAPBgNVBAgMCE5ldyBZb3JrMRowGAYDVQQKDBFUaGluZ3NCb2FyZCwgSW5jLjEwMC4GA1UEAwwnZGV2aWNlQ2VydGlmaWNhdGVAWDUwOVByb3Zpc2lvblN0cmF0ZWd5MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAE9Zo791qKQiGNBm11r4ZGxh+w+ossZL3xc46ufq5QckQHP7zkD2XDAcmP5GvdkM1sBFN9AWaCkQfNnWmfERsOOKNTMFEwHQYDVR0OBBYEFFFc5uyCyglQoZiKhzXzMcQ3BKORMB8GA1UdIwQYMBaAFFFc5uyCyglQoZiKhzXzMcQ3BKORMA8GA1UdEwEB/wQFMAMBAf8wCgYIKoZIzj0EAwIDSAAwRQIhANbA9CuhoOifZMMmqkpuld+65CR+ItKdXeRAhLMZuccuAiB0FSQB34zMutXrZj1g8Gl5OkE7YryFHbei1z0SveHR8g== -----END CERTIFICATE-----\"\n }\n}\n```\n\n- Credentials type: **\"MQTT_BASIC\"** with **device profile ID** below: \n\n```json\n{\n \"device\": {\n \"name\":\"Name_DeviceWithCredantial_MQTT_Basic\",\n \"label\":\"Label_DeviceWithCredantial_MQTT_Basic\",\n \"deviceProfileId\":{\n \"id\":\"9d9588c0-06c9-11ee-b618-19be30fdeb60\",\n \"entityType\":\"DEVICE_PROFILE\"\n }\n },\n \"credentials\": {\n \"credentialsType\": \"MQTT_BASIC\",\n \"credentialsValue\": \"{\\\"clientId\\\":\\\"5euh5nzm34bjjh1efmlt\\\",\\\"userName\\\":\\\"onasd1lgwasmjl7v2v7h\\\",\\\"password\\\":\\\"b9xtm4ny8kt9zewaga5o\\\"}\"\n }\n}\n```\n\n- You may find the example of **LwM2M** device and **RPK** credentials below: \n\nNote: LwM2M device - only existing device profile ID (Transport configuration -> Transport type: \"LWM2M\".\n\n```json\n{\n \"device\": {\n \"name\":\"Name_LwRpk00000000\",\n \"label\":\"Label_LwRpk00000000\",\n \"deviceProfileId\":{\n \"id\":\"a660bd50-10ef-11ee-8737-b5634e73c779\",\n \"entityType\":\"DEVICE_PROFILE\"\n }\n },\n \"credentials\": {\n \"credentialsType\": \"LWM2M_CREDENTIALS\",\n \"credentialsId\": \"LwRpk00000000\",\n \"credentialsValue\":\n \"{\\\"client\\\":{ \\\"endpoint\\\":\\\"LwRpk00000000\\\", \\\"securityConfigClientMode\\\":\\\"RPK\\\", \\\"key\\\":\\\"MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAEUEBxNl/RcYJNm8mk91CyVXoIJiROYDlXcSSqK6e5bDHwOW4ZiN2lNnXalyF0Jxw8MbAytnDMERXyAja5VEMeVQ==\\\" }, \\\"bootstrap\\\":{ \\\"bootstrapServer\\\":{ \\\"securityMode\\\":\\\"RPK\\\", \\\"clientPublicKeyOrId\\\":\\\"MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAEUEBxNl/RcYJNm8mk91CyVXoIJiROYDlXcSSqK6e5bDHwOW4ZiN2lNnXalyF0Jxw8MbAytnDMERXyAja5VEMeVQ==\\\", \\\"clientSecretKey\\\":\\\"MIGHAgEAMBMGByqGSM49AgEGCCqGSM49AwEHBG0wawIBAQQgd9GAx7yZW37autew5KZykn4IgRpge/tZSjnudnZJnMahRANCAARQQHE2X9Fxgk2byaT3ULJVeggmJE5gOVdxJKorp7lsMfA5bhmI3aU2ddqXIXQnHDwxsDK2cMwRFfICNrlUQx5V\\\"}, \\\"lwm2mServer\\\":{ \\\"securityMode\\\":\\\"RPK\\\", \\\"clientPublicKeyOrId\\\":\\\"MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAEUEBxNl/RcYJNm8mk91CyVXoIJiROYDlXcSSqK6e5bDHwOW4ZiN2lNnXalyF0Jxw8MbAytnDMERXyAja5VEMeVQ==\\\", \\\"clientSecretKey\\\":\\\"MIGHAgEAMBMGByqGSM49AgEGCCqGSM49AwEHBG0wawIBAQQgd9GAx7yZW37autew5KZykn4IgRpge/tZSjnudnZJnMahRANCAARQQHE2X9Fxgk2byaT3ULJVeggmJE5gOVdxJKorp7lsMfA5bhmI3aU2ddqXIXQnHDwxsDK2cMwRFfICNrlUQx5V\\\"}} }\"\n }\n}\n```\n\nRemove 'id', 'tenantId' and optionally 'customerId' from the request body example (below) to create new Device entity. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'WRITE' permission for the entity (entities).", - "operationId": "saveDeviceWithCredentials", + "summary": "Import Dashboards (importGroupDashboards)", + "description": "Import the dashboards to specified group.The Dashboard object is a heavyweight object that contains information about the dashboard (e.g. title, image, assigned customers) and also configuration JSON (e.g. layouts, widgets, entity aliases).\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'WRITE' permission for specified group.", + "operationId": "importGroupDashboards", "parameters": [ { "name": "entityGroupId", - "in": "query", - "required": false, + "in": "path", + "description": "A string value representing the Entity Group Id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, "schema": { "type": "string" } }, { - "name": "entityGroupIds", - "in": "query", - "description": "A list of entity group ids, separated by comma ','", - "required": false, - "schema": { - "type": "array", - "items": { - "type": "string" - } - } - }, - { - "name": "nameConflictPolicy", - "in": "query", - "description": "Optional value of name conflict policy. Possible values: FAIL or UNIQUIFY. If omitted, FAIL policy is applied. FAIL policy implies exception will be thrown if an entity with the same name already exists. UNIQUIFY policy appends a suffix to the entity name, if a name conflict occurs.", - "required": false, - "schema": { - "$ref": "#/components/schemas/NameConflictPolicy", - "default": "FAIL" - } - }, - { - "name": "uniquifySeparator", - "in": "query", - "description": "Optional value of name suffix separator used by UNIQUIFY policy. By default, underscore separator is used. For example, strategy is UNIQUIFY, separator is '-'; if a name conflict occurs for entity name 'test-name', created entity will have name like 'test-name-7fsh4f'.", - "required": false, - "schema": { - "type": "string", - "default": "_" - } - }, - { - "name": "uniquifyStrategy", + "name": "overwrite", "in": "query", - "description": "Optional value of uniquify strategy used by UNIQUIFY policy. Possible values: RANDOM or INCREMENTAL. By default, RANDOM strategy is used, which means random alphanumeric string will be added as a suffix to entity name. INCREMENTAL implies the first possible number starting from 1 will be added as a name suffix. For example, strategy is UNIQUIFY, uniquify strategy is INCREMENTAL; if a name conflict occurs for entity name 'test-name', created entity will have name like 'test-name-1.", + "description": "Overwrite dashboards with the same name", "required": false, "schema": { - "$ref": "#/components/schemas/UniquifyStrategy", - "default": "RANDOM" + "type": "boolean", + "default": false } } ], @@ -32339,7 +32011,11 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/SaveDeviceWithCredentialsRequest" + "type": "array", + "description": "JSON array with the dashboard objects", + "items": { + "$ref": "#/components/schemas/Dashboard" + } } } }, @@ -32347,14 +32023,7 @@ }, "responses": { "200": { - "description": "OK", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/Device" - } - } - } + "description": "OK" }, "400": { "description": "Bad Request", @@ -32472,31 +32141,21 @@ ] } }, - "/api/device/bulk_import": { - "post": { + "/api/tenant/dashboard/home/info": { + "get": { "tags": [ - "device-controller" + "dashboard-controller" ], - "summary": "Import the bulk of devices (processDevicesBulkImport)", - "description": "There's an ability to import the bulk of devices using the only .csv file. Security check is performed to verify that the user has 'WRITE' permission for the entity (entities).", - "operationId": "processDevicesBulkImport", - "requestBody": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/BulkImportRequest" - } - } - }, - "required": true - }, + "summary": "Get Tenant Home Dashboard Info (getTenantHomeDashboardInfo)", + "description": "Returns the home dashboard info object that is configured as 'homeDashboardId' parameter in the 'additionalInfo' of the corresponding tenant. \n\nAvailable for users with 'TENANT_ADMIN' authority.\n\nSecurity check is performed to verify that the user has 'READ' permission for the white labeling resource.", + "operationId": "getTenantHomeDashboardInfo", "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/BulkImportResultDevice" + "$ref": "#/components/schemas/HomeDashboardInfo" } } } @@ -32513,7 +32172,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -32615,21 +32274,19 @@ "ApiKeyForm": [] } ] - } - }, - "/api/device/credentials": { + }, "post": { "tags": [ - "device-controller" + "dashboard-controller" ], - "summary": "Update device credentials (updateDeviceCredentials)", - "description": "During device creation, platform generates random 'ACCESS_TOKEN' credentials.\nUse this method to update the device credentials. First use 'getDeviceCredentialsByDeviceId' to get the credentials id and value.\nThen use current method to update the credentials type and value. It is not possible to create multiple device credentials for the same device.\nThe structure of device credentials id and value is simple for the 'ACCESS_TOKEN' but is much more complex for the 'MQTT_BASIC' or 'LWM2M_CREDENTIALS'.\nYou may find the example of device with different type of credentials below: \n\n- Credentials type: **\"Access token\"** with **device ID** and with **device ID** below: \n\n```json\n{\n \"id\": {\n \"id\":\"c886a090-168d-11ee-87c9-6f157dbc816a\"\n },\n \"deviceId\": {\n \"id\":\"c5fb3ac0-168d-11ee-87c9-6f157dbc816a\",\n \"entityType\":\"DEVICE\"\n },\n \"credentialsType\": \"ACCESS_TOKEN\",\n \"credentialsId\": \"6hmxew8pmmzng4e3une4\"\n}\n```\n\n- Credentials type: **\"X509\"** with **device profile ID** below: \n\nNote: **credentialsId** - format **Sha3Hash**, **certificateValue** - format **PEM** (with \"--BEGIN CERTIFICATE----\" and -\"----END CERTIFICATE-\").\n\n```json\n{\n \"id\": {\n \"id\":\"309bd9c0-14f4-11ee-9fc9-d9b7463abb63\"\n },\n \"deviceId\": {\n \"id\":\"3092b200-14f4-11ee-9fc9-d9b7463abb63\",\n \"entityType\":\"DEVICE\"\n },\n \"credentialsType\": \"X509_CERTIFICATE\",\n \"credentialsId\": \"6b8adb49015500e51a527acd332b51684ab9b49b4ade03a9582a44c455e2e9b6\",\n \"credentialsValue\": \"-----BEGIN CERTIFICATE----- MIICMTCCAdegAwIBAgIUUEKxS9hTz4l+oLUMF0LV6TC/gCIwCgYIKoZIzj0EAwIwbjELMAkGA1UEBhMCVVMxETAPBgNVBAgMCE5ldyBZb3JrMRowGAYDVQQKDBFUaGluZ3NCb2FyZCwgSW5jLjEwMC4GA1UEAwwnZGV2aWNlUHJvZmlsZUNlcnRAWDUwOVByb3Zpc2lvblN0cmF0ZWd5MB4XDTIzMDMyOTE0NTczNloXDTI0MDMyODE0NTczNlowbjELMAkGA1UEBhMCVVMxETAPBgNVBAgMCE5ldyBZb3JrMRowGAYDVQQKDBFUaGluZ3NCb2FyZCwgSW5jLjEwMC4GA1UEAwwnZGV2aWNlUHJvZmlsZUNlcnRAWDUwOVByb3Zpc2lvblN0cmF0ZWd5MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAECMlWO72krDoUL9FQjUmSCetkhaEGJUfQkdSfkLSNa0GyAEIMbfmzI4zITeapunu4rGet3EMyLydQzuQanBicp6NTMFEwHQYDVR0OBBYEFHpZ78tPnztNii4Da/yCw6mhEIL3MB8GA1UdIwQYMBaAFHpZ78tPnztNii4Da/yCw6mhEIL3MA8GA1UdEwEB/wQFMAMBAf8wCgYIKoZIzj0EAwIDSAAwRQIgJ7qyMFqNcwSYkH6o+UlQXzLWfwZbNjVk+aR7foAZNGsCIQDsd7v3WQIGHiArfZeDs1DLEDuV/2h6L+ZNoGNhEKL+1A== -----END CERTIFICATE-----\"\n}\n```\n\n- Credentials type: **\"MQTT_BASIC\"** with **device profile ID** below: \n\n```json\n{\n \"id\": {\n \"id\":\"d877ffb0-14f5-11ee-9fc9-d9b7463abb63\"\n },\n \"deviceId\": {\n \"id\":\"d875dcd0-14f5-11ee-9fc9-d9b7463abb63\",\n \"entityType\":\"DEVICE\"\n },\n \"credentialsType\": \"MQTT_BASIC\",\n \"credentialsValue\": \"{\\\"clientId\\\":\\\"juy03yv4owqxcmqhqtvk\\\",\\\"userName\\\":\\\"ov19fxca0cyjn7lm7w7u\\\",\\\"password\\\":\\\"twy94he114dfi9usyk1o\\\"}\"\n}\n```\n\n- You may find the example of **LwM2M** device and **RPK** credentials below: \n\nNote: LwM2M device - only existing device profile ID (Transport configuration -> Transport type: \"LWM2M\".\n\n```json\n{\n \"id\": {\n \"id\":\"e238d4d0-1689-11ee-98c6-1713c1be5a8e\"\n },\n \"deviceId\": {\n \"id\":\"e232e160-1689-11ee-98c6-1713c1be5a8e\",\n \"entityType\":\"DEVICE\"\n },\n \"credentialsType\": \"LWM2M_CREDENTIALS\",\n \"credentialsId\": \"LwRpk00000000\",\n \"credentialsValue\":\n \"{\\\"client\\\":{ \\\"endpoint\\\":\\\"LwRpk00000000\\\", \\\"securityConfigClientMode\\\":\\\"RPK\\\", \\\"key\\\":\\\"MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAEdvBZZ2vQRK9wgDhctj6B1c7bxR3Z0wYg1+YdoYFnVUKWb+rIfTTyYK9tmQJx5Vlb5fxdLnVv1RJOPiwsLIQbAA==\\\" }, \\\"bootstrap\\\":{ \\\"bootstrapServer\\\":{ \\\"securityMode\\\":\\\"RPK\\\", \\\"clientPublicKeyOrId\\\":\\\"MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAEUEBxNl/RcYJNm8mk91CyVXoIJiROYDlXcSSqK6e5bDHwOW4ZiN2lNnXalyF0Jxw8MbAytnDMERXyAja5VEMeVQ==\\\", \\\"clientSecretKey\\\":\\\"MIGHAgEAMBMGByqGSM49AgEGCCqGSM49AwEHBG0wawIBAQQgd9GAx7yZW37autew5KZykn4IgRpge/tZSjnudnZJnMahRANCAARQQHE2X9Fxgk2byaT3ULJVeggmJE5gOVdxJKorp7lsMfA5bhmI3aU2ddqXIXQnHDwxsDK2cMwRFfICNrlUQx5V\\\"}, \\\"lwm2mServer\\\":{ \\\"securityMode\\\":\\\"RPK\\\", \\\"clientPublicKeyOrId\\\":\\\"MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAEUEBxNl/RcYJNm8mk91CyVXoIJiROYDlXcSSqK6e5bDHwOW4ZiN2lNnXalyF0Jxw8MbAytnDMERXyAja5VEMeVQ==\\\", \\\"clientSecretKey\\\":\\\"MIGHAgEAMBMGByqGSM49AgEGCCqGSM49AwEHBG0wawIBAQQgd9GAx7yZW37autew5KZykn4IgRpge/tZSjnudnZJnMahRANCAARQQHE2X9Fxgk2byaT3ULJVeggmJE5gOVdxJKorp7lsMfA5bhmI3aU2ddqXIXQnHDwxsDK2cMwRFfICNrlUQx5V\\\"}} }\"\n}\n```\n\nUpdate to real value:\n - 'id' (this is id of Device Credentials -> \"Get Device Credentials (getDeviceCredentialsByDeviceId)\",\n - 'deviceId.id' (this is id of Device).\nRemove 'tenantId' and optionally 'customerId' from the request body example (below) to create new Device entity.\n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "updateDeviceCredentials", + "summary": "Update Tenant Home Dashboard Info (getTenantHomeDashboardInfo)", + "description": "Update the home dashboard assignment for the current tenant. \n\nAvailable for users with 'TENANT_ADMIN' authority.\n\nSecurity check is performed to verify that the user has 'WRITE' permission for the white labeling resource.", + "operationId": "setTenantHomeDashboardInfo", "requestBody": { "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/DeviceCredentials" + "$ref": "#/components/schemas/HomeDashboardInfo" } } }, @@ -32637,14 +32294,7 @@ }, "responses": { "200": { - "description": "OK", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/DeviceCredentials" - } - } - } + "description": "OK" }, "400": { "description": "Bad Request", @@ -32762,23 +32412,78 @@ ] } }, - "/api/device/info/{deviceId}": { + "/api/tenant/dashboards": { "get": { "tags": [ - "device-controller" + "dashboard-controller" ], - "summary": "Get Device (getDeviceInfoById)", - "description": "Fetch the Device info object based on the provided Device Id. Device Info is an extension of the default Device object that contains information about the owner name. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getDeviceInfoById", + "summary": "Get Tenant Dashboards (getTenantDashboards)", + "description": "Returns a page of dashboard info objects owned by the tenant of a current user. The Dashboard Info object contains lightweight information about the dashboard (e.g. title, image, assigned customers) but does not contain the heavyweight configuration JSON. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "getTenantDashboards", "parameters": [ { - "name": "deviceId", - "in": "path", - "description": "A string value representing the device id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", + "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "mobile", + "in": "query", + "description": "Exclude dashboards that are hidden for mobile", + "required": false, + "schema": { + "type": "boolean" + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'substring' filter based on the dashboard title.", + "required": false, "schema": { "type": "string" } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string", + "enum": [ + "createdTime", + "title" + ] + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] + } } ], "responses": { @@ -32787,7 +32492,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/DeviceInfo" + "$ref": "#/components/schemas/PageDataDashboardInfo" } } } @@ -32908,24 +32613,87 @@ ] } }, - "/api/device/types": { + "/api/tenant/{tenantId}/dashboards": { "get": { "tags": [ - "device-controller" + "dashboard-controller" + ], + "summary": "Get Tenant Dashboards by System Administrator (getTenantDashboardsByTenantId)", + "description": "Returns a page of dashboard info objects owned by tenant. The Dashboard Info object contains lightweight information about the dashboard (e.g. title, image, assigned customers) but does not contain the heavyweight configuration JSON. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'SYS_ADMIN' authority.", + "operationId": "getTenantDashboardsByTenantId", + "parameters": [ + { + "name": "tenantId", + "in": "path", + "description": "A string value representing the tenant id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, + "schema": { + "type": "string" + } + }, + { + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", + "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", + "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'substring' filter based on the dashboard title.", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string", + "enum": [ + "createdTime", + "title" + ] + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] + } + } ], - "summary": "Get Device Types (getDeviceTypes)", - "description": "Deprecated. See 'getDeviceProfileNames' API from Device Profile Controller instead.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", - "operationId": "getDeviceTypes", "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "type": "array", - "items": { - "$ref": "#/components/schemas/EntitySubtype" - } + "$ref": "#/components/schemas/PageDataDashboardInfo" } } } @@ -33036,7 +32804,6 @@ } } }, - "deprecated": true, "security": [ { "HttpLoginForm": [] @@ -33047,20 +32814,93 @@ ] } }, - "/api/device/{deviceId}": { + "/api/user/dashboards": { "get": { "tags": [ - "device-controller" + "dashboard-controller" ], - "summary": "Get Device (getDeviceById)", - "description": "Fetch the Device object based on the provided Device Id. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getDeviceById", + "summary": "Get Dashboards (getUserDashboards)", + "description": "Returns a page of Dashboard Info objects available for specified or current user. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. The Dashboard Info object contains lightweight information about the dashboard (e.g. title, image, assigned customers) but does not contain the heavyweight configuration JSON.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getUserDashboards", "parameters": [ { - "name": "deviceId", - "in": "path", - "description": "A string value representing the device id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", + "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "mobile", + "in": "query", + "description": "Exclude dashboards that are hidden for mobile", + "required": false, + "schema": { + "type": "boolean" + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'substring' filter based on the dashboard title.", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string", + "enum": [ + "createdTime", + "title" + ] + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] + } + }, + { + "name": "operation", + "in": "query", + "description": "Filter by allowed operations for the current user", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "userId", + "in": "query", + "description": "A string value representing the user id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": false, "schema": { "type": "string" } @@ -33072,7 +32912,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/Device" + "$ref": "#/components/schemas/PageDataDashboardInfo" } } } @@ -33191,28 +33031,61 @@ "ApiKeyForm": [] } ] - }, - "delete": { + } + }, + "/api/report/test": { + "post": { "tags": [ - "device-controller" + "dashboard-report-controller" ], - "summary": "Delete device (deleteDevice)", - "description": "Deletes the device, it's credentials and all the relations (from and to the device). Referencing non-existing device Id will cause an error.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'DELETE' permission for the entity (entities).", - "operationId": "deleteDevice", + "summary": "Download test report (downloadTestReport)", + "description": "Generate and download test report.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", + "operationId": "downloadTestReport", "parameters": [ { - "name": "deviceId", - "in": "path", - "description": "A string value representing the device id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": true, + "name": "reportsServerEndpointUrl", + "in": "query", + "description": "A string value representing the report server endpoint.", + "required": false, "schema": { "type": "string" - } + }, + "example": "http://localhost:8383" } ], + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/DashboardReportConfig" + } + } + }, + "required": true + }, "responses": { "200": { - "description": "OK" + "description": "OK", + "content": { + "application/pdf": { + "schema": { + "type": "string", + "format": "binary" + } + }, + "image/jpeg": { + "schema": { + "type": "string", + "format": "binary" + } + }, + "image/png": { + "schema": { + "type": "string", + "format": "binary" + } + } + } }, "400": { "description": "Bad Request", @@ -33226,7 +33099,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -33330,32 +33203,55 @@ ] } }, - "/api/device/{deviceId}/credentials": { - "get": { + "/api/report/{dashboardId}/download": { + "post": { "tags": [ - "device-controller" + "dashboard-report-controller" ], - "summary": "Get Device Credentials (getDeviceCredentialsByDeviceId)", - "description": "If during device creation there wasn't specified any credentials, platform generates random 'ACCESS_TOKEN' credentials.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ_CREDENTIALS' permission for the entity (entities).", - "operationId": "getDeviceCredentialsByDeviceId", + "summary": "Download dashboard report (downloadDashboardReport)", + "description": "Generate and download a report from the specified dashboard. The request payload is a JSON object with params of report. For example:\n\n```json\n{\n \"type\": \"pdf\",\n \"timezone\": \"Europe/Kiev\",\n \"timewindow\": {\n \"displayValue\": \"\",\n \"hideInterval\": false,\n \"hideLastInterval\": false,\n \"hideQuickInterval\": false,\n \"hideAggregation\": false,\n \"hideAggInterval\": false,\n \"hideTimezone\": false,\n \"selectedTab\": 0,\n \"realtime\": {\n \"realtimeType\": 0,\n \"interval\": 1000,\n \"timewindowMs\": 60000,\n \"quickInterval\": \"CURRENT_DAY\"\n },\n \"history\": {\n \"historyType\": 0,\n \"interval\": 1000,\n \"timewindowMs\": 60000,\n \"fixedTimewindow\": {\n \"startTimeMs\": 1703687976592,\n \"endTimeMs\": 1703774376592\n },\n \"quickInterval\": \"CURRENT_DAY\"\n },\n \"aggregation\": {\n \"type\": \"AVG\",\n \"limit\": 25000\n }\n },\n \"state\": null\n}\n```\n\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", + "operationId": "downloadDashboardReport", "parameters": [ { - "name": "deviceId", + "name": "dashboardId", "in": "path", - "description": "A string value representing the device id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "description": "A string value representing the dashboard id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { "type": "string" } } ], + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/JsonNode" + } + } + }, + "required": true + }, "responses": { "200": { "description": "OK", "content": { - "application/json": { + "application/pdf": { "schema": { - "$ref": "#/components/schemas/DeviceCredentials" + "type": "string", + "format": "binary" + } + }, + "image/jpeg": { + "schema": { + "type": "string", + "format": "binary" + } + }, + "image/png": { + "schema": { + "type": "string", + "format": "binary" } } } @@ -33372,7 +33268,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -33476,108 +33372,33 @@ ] } }, - "/api/deviceInfos/all": { + "/api/device-connectivity/gateway-launch/{deviceId}/docker-compose/download": { "get": { "tags": [ - "device-controller" + "device-connectivity-controller" ], - "summary": "Get All Device Infos for current user (getAllDeviceInfos)", - "description": "Returns a page of device info objects owned by the tenant or the customer of a current user. Device Info is an extension of the default Device object that contains information about the owner name. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getAllDeviceInfos", + "summary": "Download generated docker-compose.yml file for gateway (downloadGatewayDockerCompose)", + "description": "Download generated docker-compose.yml for gateway.", + "operationId": "downloadGatewayDockerCompose", "parameters": [ { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", + "name": "deviceId", + "in": "path", + "description": "A string value representing the device id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "includeCustomers", - "in": "query", - "description": "Include customer or sub-customer entities", - "required": false, - "schema": { - "type": "boolean" - } - }, - { - "name": "deviceProfileId", - "in": "query", - "description": "A string value representing the device profile id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "active", - "in": "query", - "description": "A boolean value representing the device active flag.", - "required": false, - "schema": { - "type": "boolean" - } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'substring' filter based on the device name.", - "required": false, "schema": { "type": "string" } - }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, - "schema": { - "type": "string", - "enum": [ - "createdTime", - "name", - "deviceProfileName", - "label", - "customerTitle" - ] - } - }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] - } } ], "responses": { "200": { "description": "OK", "content": { - "application/json": { + "application/octet-stream": { "schema": { - "$ref": "#/components/schemas/PageDataDeviceInfo" + "type": "string", + "format": "binary" } } } @@ -33698,25 +33519,22 @@ ] } }, - "/api/devices": { + "/api/device-connectivity/{deviceId}": { "get": { "tags": [ - "device-controller" + "device-connectivity-controller" ], - "summary": "Get Devices By Ids (getDevicesByIds)", - "description": "Requested devices must be owned by tenant or assigned to customer which user is performing the request. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getDevicesByIds", + "summary": "Get commands to publish device telemetry (getDevicePublishTelemetryCommands)", + "description": "Fetch the list of commands to publish device telemetry based on device profile If the user has the authority of 'Tenant Administrator', the server checks that the device is owned by the same tenant. If the user has the authority of 'Customer User', the server checks that the device is assigned to the same customer. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", + "operationId": "getDevicePublishTelemetryCommands", "parameters": [ { - "name": "deviceIds", - "in": "query", - "description": "A list of devices ids, separated by comma ','", + "name": "deviceId", + "in": "path", + "description": "A string value representing the device id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { - "type": "array", - "items": { - "type": "string" - } + "type": "string" } } ], @@ -33726,9 +33544,20 @@ "content": { "application/json": { "schema": { - "type": "array", - "items": { - "$ref": "#/components/schemas/Device" + "$ref": "#/components/schemas/JsonNode" + }, + "examples": { + "http": { + "description": "http", + "value": "curl -v -X POST http://localhost:8080/api/v1/0ySs4FTOn5WU15XLmal8/telemetry --header Content-Type:application/json --data {temperature:25}" + }, + "mqtt": { + "description": "mqtt", + "value": "mosquitto_pub -d -q 1 -h localhost -t v1/devices/me/telemetry -i myClient1 -u myUsername1 -P myPassword -m {temperature:25}" + }, + "coap": { + "description": "coap", + "value": "coap-client -m POST coap://localhost:5683/api/v1/0ySs4FTOn5WU15XLmal8/telemetry -t json -e {temperature:25}" } } } @@ -33848,34 +33677,35 @@ "ApiKeyForm": [] } ] - }, - "post": { + } + }, + "/api/device-connectivity/{protocol}/certificate/download": { + "get": { "tags": [ - "device-controller" + "device-connectivity-controller" ], - "summary": "Find related devices (findDevicesByQuery)", - "description": "Returns all devices that are related to the specific entity. The entity id, relation type, device types, depth of the search, and other query parameters defined using complex 'DeviceSearchQuery' object. See 'Model' tab of the Parameters for more info.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "findDevicesByQuery", - "requestBody": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/DeviceSearchQuery" - } + "summary": "Download server certificate using file path defined in device.connectivity properties (downloadServerCertificate)", + "description": "Download server certificate.", + "operationId": "downloadServerCertificate", + "parameters": [ + { + "name": "protocol", + "in": "path", + "description": "A string value representing the device connectivity protocol. Possible values: 'mqtt', 'mqtts', 'http', 'https', 'coap', 'coaps'", + "required": true, + "schema": { + "type": "string" } - }, - "required": true - }, + } + ], "responses": { "200": { "description": "OK", "content": { - "application/json": { + "application/octet-stream": { "schema": { - "type": "array", - "items": { - "$ref": "#/components/schemas/Device" - } + "type": "string", + "format": "binary" } } } @@ -33892,7 +33722,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -33996,46 +33826,49 @@ ] } }, - "/api/devices/count/{otaPackageType}/{deviceProfileId}": { - "get": { + "/api/customer/device/{deviceName}/claim": { + "post": { "tags": [ "device-controller" ], - "summary": "Count devices by device profile (countByDeviceProfileAndEmptyOtaPackage)", - "description": "The platform gives an ability to load OTA (over-the-air) packages to devices. It can be done in two different ways: device scope or device profile scope.In the response you will find the number of devices with specified device profile, but without previously defined device scope OTA package. It can be useful when you want to define number of devices that will be affected with future OTA package\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "countByDeviceProfileAndEmptyOtaPackage", + "summary": "Claim device (claimDevice)", + "description": "Claiming makes it possible to assign a device to the specific customer using device/server side claiming data (in the form of secret key).To make this happen you have to provide unique device name and optional claiming data (it is needed only for device-side claiming).Once device is claimed, the customer becomes its owner and customer users may access device data as well as control the device. \nIn order to enable claiming devices feature a system parameter security.claim.allowClaimingByDefault should be set to true, otherwise a server-side claimingAllowed attribute with the value true is obligatory for provisioned devices. \nSee official documentation for more details regarding claiming.\n\nAvailable for users with 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'CLAIM_DEVICES' permission for the entity (entities).", + "operationId": "claimDevice", "parameters": [ { - "name": "otaPackageType", + "name": "deviceName", "in": "path", - "description": "OTA package type", + "description": "Unique name of the device which is going to be claimed", "required": true, "schema": { - "type": "string", - "enum": [ - "FIRMWARE", - "SOFTWARE" - ] + "type": "string" } }, { - "name": "deviceProfileId", - "in": "path", - "description": "Device Profile Id. I.g. '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": true, + "name": "subCustomerId", + "in": "query", + "required": false, "schema": { "type": "string" } } ], + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ClaimRequest" + } + } + } + }, "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "type": "integer", - "format": "int64" + "type": "string" } } } @@ -34052,7 +33885,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -34154,41 +33987,19 @@ "ApiKeyForm": [] } ] - } - }, - "/api/devices/count/{otaPackageType}/{otaPackageId}/{entityGroupId}": { - "get": { + }, + "delete": { "tags": [ "device-controller" ], - "summary": "Count devices by device profile (countByDeviceProfileAndEmptyOtaPackage)", - "description": "The platform gives an ability to load OTA (over-the-air) packages to devices. It can be done in two different ways: device scope or device profile scope.In the response you will find the number of devices with specified device profile, but without previously defined device scope OTA package. It can be useful when you want to define number of devices that will be affected with future OTA package\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "countByDeviceGroupAndEmptyOtaPackage", + "summary": "Reclaim device (reClaimDevice)", + "description": "Reclaiming means the device will be unassigned from the customer and the device will be available for claiming again.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'CLAIM_DEVICES' permission for the entity (entities).", + "operationId": "reClaimDevice", "parameters": [ { - "name": "otaPackageType", - "in": "path", - "description": "OTA package type", - "required": true, - "schema": { - "type": "string", - "enum": [ - "FIRMWARE", - "SOFTWARE" - ] - } - }, - { - "name": "otaPackageId", - "in": "path", - "required": true, - "schema": { - "type": "string" - } - }, - { - "name": "entityGroupId", + "name": "deviceName", "in": "path", + "description": "Unique name of the device which is going to be reclaimed", "required": true, "schema": { "type": "string" @@ -34201,8 +34012,7 @@ "content": { "application/json": { "schema": { - "type": "integer", - "format": "int64" + "type": "string" } } } @@ -34323,19 +34133,19 @@ ] } }, - "/api/entityGroup/{entityGroupId}/devices": { + "/api/customer/{customerId}/deviceInfos": { "get": { "tags": [ "device-controller" ], - "summary": "Get devices by Entity Group Id (getDevicesByEntityGroupId)", - "description": "Returns a page of Device objects that belongs to specified Entity Group Id. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", - "operationId": "getDevicesByEntityGroupId", + "summary": "Get Customer Device Infos (getCustomerDeviceInfos)", + "description": "Returns a page of device info objects owned by the specified customer. Device Info is an extension of the default Device object that contains information about the owner name. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getCustomerDeviceInfos", "parameters": [ { - "name": "entityGroupId", + "name": "customerId", "in": "path", - "description": "A string value representing the Entity Group Id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "description": "A string value representing the customer id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { "type": "string" @@ -34347,8 +34157,8 @@ "description": "Maximum amount of entities in a one page", "required": true, "schema": { - "type": "string", - "minimum": 1 + "type": "integer", + "format": "int32" } }, { @@ -34357,8 +34167,35 @@ "description": "Sequence number of page starting from 0", "required": true, "schema": { - "type": "string", - "minimum": 0 + "type": "integer", + "format": "int32" + } + }, + { + "name": "includeCustomers", + "in": "query", + "description": "Include customer or sub-customer entities", + "required": false, + "schema": { + "type": "boolean" + } + }, + { + "name": "deviceProfileId", + "in": "query", + "description": "A string value representing the device profile id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "active", + "in": "query", + "description": "A boolean value representing the device active flag.", + "required": false, + "schema": { + "type": "boolean" } }, { @@ -34406,7 +34243,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataDevice" + "$ref": "#/components/schemas/PageDataDeviceInfo" } } } @@ -34527,161 +34364,24 @@ ] } }, - "/api/tenant/device": { + "/api/customer/{customerId}/devices": { "get": { "tags": [ "device-controller" ], - "summary": "Get Tenant Device (getTenantDevice)", - "description": "Requested device must be owned by tenant that the user belongs to. Device name is an unique property of device. So it can be used to identify the device.\n\nAvailable for users with 'TENANT_ADMIN' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getTenantDeviceByName", + "summary": "Get Customer Devices (getCustomerDevices)", + "description": "Returns a page of devices objects assigned to customer. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getCustomerDevices", "parameters": [ { - "name": "deviceName", - "in": "query", - "description": "A string value representing the Device name.", + "name": "customerId", + "in": "path", + "description": "A string value representing the customer id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { "type": "string" } - } - ], - "responses": { - "200": { - "description": "OK", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/Device" - } - } - } - }, - "400": { - "description": "Bad Request", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ThingsboardErrorResponse" - }, - "examples": { - "error-code-400": { - "summary": "Bad Request", - "value": { - "status": 400, - "message": "Invalid UUID string: 123", - "errorCode": 31, - "timestamp": 1609459200000 - } - } - } - } - } - }, - "401": { - "description": "Unauthorized", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ThingsboardErrorResponse" - }, - "examples": { - "error-code-401": { - "summary": "Unauthorized", - "value": { - "status": 401, - "message": "Authentication failed", - "errorCode": 10, - "timestamp": 1609459200000 - } - } - } - } - } - }, - "403": { - "description": "Forbidden", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ThingsboardErrorResponse" - }, - "examples": { - "error-code-403": { - "summary": "Forbidden", - "value": { - "status": 403, - "message": "You don't have permission to perform this operation!", - "errorCode": 20, - "timestamp": 1609459200000 - } - } - } - } - } - }, - "404": { - "description": "Not Found", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ThingsboardErrorResponse" - }, - "examples": { - "error-code-404": { - "summary": "Not Found", - "value": { - "status": 404, - "message": "Requested item wasn't found!", - "errorCode": 32, - "timestamp": 1609459200000 - } - } - } - } - } - }, - "429": { - "description": "Too Many Requests", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ThingsboardErrorResponse" - }, - "examples": { - "error-code-429": { - "summary": "Too Many Requests", - "value": { - "status": 429, - "message": "Too many requests for current tenant!", - "errorCode": 33, - "timestamp": 1609459200000 - } - } - } - } - } - } - }, - "security": [ - { - "HttpLoginForm": [] }, - { - "ApiKeyForm": [] - } - ] - } - }, - "/api/tenant/devices": { - "get": { - "tags": [ - "device-controller" - ], - "summary": "Get Tenant Devices (getTenantDevices)", - "description": "Returns a page of devices owned by tenant. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getTenantDevices", - "parameters": [ { "name": "pageSize", "in": "query", @@ -34877,34 +34577,86 @@ ] } }, - "/api/tenant/{tenantId}/device/{deviceId}": { + "/api/device": { "post": { "tags": [ "device-controller" ], - "summary": "Assign device to tenant (assignDeviceToTenant)", - "description": "Creates assignment of the device to tenant. Thereafter tenant will be able to reassign the device to a customer.\n\nAvailable for users with 'TENANT_ADMIN' authority. Security check is performed to verify that the user has 'ASSIGN_TO_TENANT' permission for the entity (entities).", - "operationId": "assignDeviceToTenant", + "summary": "Create Or Update Device (saveDevice)", + "description": "Create or update the Device. When creating device, platform generates Device Id as [time-based UUID](https://en.wikipedia.org/wiki/Universally_unique_identifier#Version_1_(date-time_and_MAC_address)). Device credentials are also generated if not provided in the 'accessToken' request parameter. The newly created device id will be present in the response. Specify existing Device id to update the device. Referencing non-existing device Id will cause 'Not Found' error.\n\nDevice name is unique in the scope of tenant. Use unique identifiers like MAC or IMEI for the device names and non-unique 'label' field for user-friendly visualization purposes.Remove 'id', 'tenantId' and optionally 'customerId' from the request body example (below) to create new Device entity. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'WRITE' permission for the entity (entities).", + "operationId": "saveDevice", "parameters": [ { - "name": "tenantId", - "in": "path", - "description": "A string value representing the tenant id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": true, + "name": "accessToken", + "in": "query", + "description": "Optional value of the device credentials to be used during device creation. If omitted, access token will be auto-generated.", + "required": false, "schema": { "type": "string" } }, { - "name": "deviceId", - "in": "path", - "description": "A string value representing the device id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": true, + "name": "entityGroupId", + "in": "query", + "required": false, "schema": { "type": "string" } + }, + { + "name": "entityGroupIds", + "in": "query", + "description": "A list of entity group ids, separated by comma ','", + "required": false, + "schema": { + "type": "array", + "items": { + "type": "string" + } + } + }, + { + "name": "nameConflictPolicy", + "in": "query", + "description": "Optional value of name conflict policy. Possible values: FAIL or UNIQUIFY. If omitted, FAIL policy is applied. FAIL policy implies exception will be thrown if an entity with the same name already exists. UNIQUIFY policy appends a suffix to the entity name, if a name conflict occurs.", + "required": false, + "schema": { + "$ref": "#/components/schemas/NameConflictPolicy", + "default": "FAIL" + } + }, + { + "name": "uniquifySeparator", + "in": "query", + "description": "Optional value of name suffix separator used by UNIQUIFY policy. By default, underscore separator is used. For example, strategy is UNIQUIFY, separator is '-'; if a name conflict occurs for entity name 'test-name', created entity will have name like 'test-name-7fsh4f'.", + "required": false, + "schema": { + "type": "string", + "default": "_" + } + }, + { + "name": "uniquifyStrategy", + "in": "query", + "description": "Optional value of uniquify strategy used by UNIQUIFY policy. Possible values: RANDOM or INCREMENTAL. By default, RANDOM strategy is used, which means random alphanumeric string will be added as a suffix to entity name. INCREMENTAL implies the first possible number starting from 1 will be added as a name suffix. For example, strategy is UNIQUIFY, uniquify strategy is INCREMENTAL; if a name conflict occurs for entity name 'test-name', created entity will have name like 'test-name-1.", + "required": false, + "schema": { + "$ref": "#/components/schemas/UniquifyStrategy", + "default": "RANDOM" + } } ], + "requestBody": { + "description": "A JSON value representing the device.", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/Device" + } + } + }, + "required": true + }, "responses": { "200": { "description": "OK", @@ -35032,90 +34784,83 @@ ] } }, - "/api/user/devices": { - "get": { + "/api/device-with-credentials": { + "post": { "tags": [ "device-controller" ], - "summary": "Get Devices (getUserDevices)", - "description": "Returns a page of devices that are available for the current user. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getUserDevices", + "summary": "Create Device (saveDevice) with credentials ", + "description": "Create or update the Device. When creating device, platform generates Device Id as [time-based UUID](https://en.wikipedia.org/wiki/Universally_unique_identifier#Version_1_(date-time_and_MAC_address)). Requires to provide the Device Credentials object as well as an existing device profile ID or use \"default\".\nYou may find the example of device with different type of credentials below: \n\n- Credentials type: **\"Access token\"** with **device profile ID** below: \n\n```json\n{\n \"device\": {\n \"name\":\"Name_DeviceWithCredantial_AccessToken\",\n \"label\":\"Label_DeviceWithCredantial_AccessToken\",\n \"deviceProfileId\":{\n \"id\":\"5636aba0-1022-11ee-9631-51fb57f69174\",\n \"entityType\":\"DEVICE_PROFILE\"\n }\n },\n \"credentials\": {\n \"credentialsType\": \"ACCESS_TOKEN\",\n \"credentialsId\": \"6hmxew8pmmzng4e3une2\"\n }\n}\n```\n\n- Credentials type: **\"Access token\"** with **device profile default** below: \n\n```json\n{\n \"device\": {\n \"name\":\"Name_DeviceWithCredantial_AccessToken_Default\",\n \"label\":\"Label_DeviceWithCredantial_AccessToken_Default\",\n \"type\": \"default\"\n },\n \"credentials\": {\n \"credentialsType\": \"ACCESS_TOKEN\",\n \"credentialsId\": \"6hmxew8pmmzng4e3une3\"\n }\n}\n```\n\n- Credentials type: **\"X509\"** with **device profile ID** below: \n\nNote: **credentialsId** - format **Sha3Hash**, **certificateValue** - format **PEM** (with \"--BEGIN CERTIFICATE----\" and -\"----END CERTIFICATE-\").\n\n```json\n{\n \"device\": {\n \"name\":\"Name_DeviceWithCredantial_X509_Certificate\",\n \"label\":\"Label_DeviceWithCredantial_X509_Certificate\",\n \"deviceProfileId\":{\n \"id\":\"9d9588c0-06c9-11ee-b618-19be30fdeb60\",\n \"entityType\":\"DEVICE_PROFILE\"\n }\n },\n \"credentials\": {\n \"credentialsType\": \"X509_CERTIFICATE\",\n \"credentialsId\": \"84f5911765abba1f96bf4165604e9e90338fc6214081a8e623b6ff9669aedb27\",\n \"credentialsValue\": \"-----BEGIN CERTIFICATE----- MIICMTCCAdegAwIBAgIUI9dBuwN6pTtK6uZ03rkiCwV4wEYwCgYIKoZIzj0EAwIwbjELMAkGA1UEBhMCVVMxETAPBgNVBAgMCE5ldyBZb3JrMRowGAYDVQQKDBFUaGluZ3NCb2FyZCwgSW5jLjEwMC4GA1UEAwwnZGV2aWNlQ2VydGlmaWNhdGVAWDUwOVByb3Zpc2lvblN0cmF0ZWd5MB4XDTIzMDMyOTE0NTYxN1oXDTI0MDMyODE0NTYxN1owbjELMAkGA1UEBhMCVVMxETAPBgNVBAgMCE5ldyBZb3JrMRowGAYDVQQKDBFUaGluZ3NCb2FyZCwgSW5jLjEwMC4GA1UEAwwnZGV2aWNlQ2VydGlmaWNhdGVAWDUwOVByb3Zpc2lvblN0cmF0ZWd5MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAE9Zo791qKQiGNBm11r4ZGxh+w+ossZL3xc46ufq5QckQHP7zkD2XDAcmP5GvdkM1sBFN9AWaCkQfNnWmfERsOOKNTMFEwHQYDVR0OBBYEFFFc5uyCyglQoZiKhzXzMcQ3BKORMB8GA1UdIwQYMBaAFFFc5uyCyglQoZiKhzXzMcQ3BKORMA8GA1UdEwEB/wQFMAMBAf8wCgYIKoZIzj0EAwIDSAAwRQIhANbA9CuhoOifZMMmqkpuld+65CR+ItKdXeRAhLMZuccuAiB0FSQB34zMutXrZj1g8Gl5OkE7YryFHbei1z0SveHR8g== -----END CERTIFICATE-----\"\n }\n}\n```\n\n- Credentials type: **\"MQTT_BASIC\"** with **device profile ID** below: \n\n```json\n{\n \"device\": {\n \"name\":\"Name_DeviceWithCredantial_MQTT_Basic\",\n \"label\":\"Label_DeviceWithCredantial_MQTT_Basic\",\n \"deviceProfileId\":{\n \"id\":\"9d9588c0-06c9-11ee-b618-19be30fdeb60\",\n \"entityType\":\"DEVICE_PROFILE\"\n }\n },\n \"credentials\": {\n \"credentialsType\": \"MQTT_BASIC\",\n \"credentialsValue\": \"{\\\"clientId\\\":\\\"5euh5nzm34bjjh1efmlt\\\",\\\"userName\\\":\\\"onasd1lgwasmjl7v2v7h\\\",\\\"password\\\":\\\"b9xtm4ny8kt9zewaga5o\\\"}\"\n }\n}\n```\n\n- You may find the example of **LwM2M** device and **RPK** credentials below: \n\nNote: LwM2M device - only existing device profile ID (Transport configuration -> Transport type: \"LWM2M\".\n\n```json\n{\n \"device\": {\n \"name\":\"Name_LwRpk00000000\",\n \"label\":\"Label_LwRpk00000000\",\n \"deviceProfileId\":{\n \"id\":\"a660bd50-10ef-11ee-8737-b5634e73c779\",\n \"entityType\":\"DEVICE_PROFILE\"\n }\n },\n \"credentials\": {\n \"credentialsType\": \"LWM2M_CREDENTIALS\",\n \"credentialsId\": \"LwRpk00000000\",\n \"credentialsValue\":\n \"{\\\"client\\\":{ \\\"endpoint\\\":\\\"LwRpk00000000\\\", \\\"securityConfigClientMode\\\":\\\"RPK\\\", \\\"key\\\":\\\"MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAEUEBxNl/RcYJNm8mk91CyVXoIJiROYDlXcSSqK6e5bDHwOW4ZiN2lNnXalyF0Jxw8MbAytnDMERXyAja5VEMeVQ==\\\" }, \\\"bootstrap\\\":{ \\\"bootstrapServer\\\":{ \\\"securityMode\\\":\\\"RPK\\\", \\\"clientPublicKeyOrId\\\":\\\"MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAEUEBxNl/RcYJNm8mk91CyVXoIJiROYDlXcSSqK6e5bDHwOW4ZiN2lNnXalyF0Jxw8MbAytnDMERXyAja5VEMeVQ==\\\", \\\"clientSecretKey\\\":\\\"MIGHAgEAMBMGByqGSM49AgEGCCqGSM49AwEHBG0wawIBAQQgd9GAx7yZW37autew5KZykn4IgRpge/tZSjnudnZJnMahRANCAARQQHE2X9Fxgk2byaT3ULJVeggmJE5gOVdxJKorp7lsMfA5bhmI3aU2ddqXIXQnHDwxsDK2cMwRFfICNrlUQx5V\\\"}, \\\"lwm2mServer\\\":{ \\\"securityMode\\\":\\\"RPK\\\", \\\"clientPublicKeyOrId\\\":\\\"MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAEUEBxNl/RcYJNm8mk91CyVXoIJiROYDlXcSSqK6e5bDHwOW4ZiN2lNnXalyF0Jxw8MbAytnDMERXyAja5VEMeVQ==\\\", \\\"clientSecretKey\\\":\\\"MIGHAgEAMBMGByqGSM49AgEGCCqGSM49AwEHBG0wawIBAQQgd9GAx7yZW37autew5KZykn4IgRpge/tZSjnudnZJnMahRANCAARQQHE2X9Fxgk2byaT3ULJVeggmJE5gOVdxJKorp7lsMfA5bhmI3aU2ddqXIXQnHDwxsDK2cMwRFfICNrlUQx5V\\\"}} }\"\n }\n}\n```\n\nRemove 'id', 'tenantId' and optionally 'customerId' from the request body example (below) to create new Device entity. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'WRITE' permission for the entity (entities).", + "operationId": "saveDeviceWithCredentials", "parameters": [ { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "string", - "minimum": 1 - } - }, - { - "name": "page", + "name": "entityGroupId", "in": "query", - "description": "Sequence number of page starting from 0", - "required": true, + "required": false, "schema": { - "type": "string", - "minimum": 0 + "type": "string" } }, { - "name": "type", + "name": "entityGroupIds", "in": "query", - "description": "Device type as the name of the device profile", + "description": "A list of entity group ids, separated by comma ','", "required": false, "schema": { - "type": "string" + "type": "array", + "items": { + "type": "string" + } } }, { - "name": "textSearch", + "name": "nameConflictPolicy", "in": "query", - "description": "The case insensitive 'substring' filter based on the device name.", + "description": "Optional value of name conflict policy. Possible values: FAIL or UNIQUIFY. If omitted, FAIL policy is applied. FAIL policy implies exception will be thrown if an entity with the same name already exists. UNIQUIFY policy appends a suffix to the entity name, if a name conflict occurs.", "required": false, "schema": { - "type": "string" + "$ref": "#/components/schemas/NameConflictPolicy", + "default": "FAIL" } }, { - "name": "sortProperty", + "name": "uniquifySeparator", "in": "query", - "description": "Property of entity to sort by", + "description": "Optional value of name suffix separator used by UNIQUIFY policy. By default, underscore separator is used. For example, strategy is UNIQUIFY, separator is '-'; if a name conflict occurs for entity name 'test-name', created entity will have name like 'test-name-7fsh4f'.", "required": false, "schema": { "type": "string", - "enum": [ - "createdTime", - "name", - "deviceProfileName", - "label", - "customerTitle" - ] + "default": "_" } }, { - "name": "sortOrder", + "name": "uniquifyStrategy", "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "description": "Optional value of uniquify strategy used by UNIQUIFY policy. Possible values: RANDOM or INCREMENTAL. By default, RANDOM strategy is used, which means random alphanumeric string will be added as a suffix to entity name. INCREMENTAL implies the first possible number starting from 1 will be added as a name suffix. For example, strategy is UNIQUIFY, uniquify strategy is INCREMENTAL; if a name conflict occurs for entity name 'test-name', created entity will have name like 'test-name-1.", "required": false, "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] + "$ref": "#/components/schemas/UniquifyStrategy", + "default": "RANDOM" } } ], + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/SaveDeviceWithCredentialsRequest" + } + } + }, + "required": true + }, "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataDevice" + "$ref": "#/components/schemas/Device" } } } @@ -35132,7 +34877,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -35236,18 +34981,19 @@ ] } }, - "/api/deviceGroupOtaPackage": { + "/api/device/bulk_import": { "post": { "tags": [ - "device-group-ota-package-controller" + "device-controller" ], - "summary": "saveDeviceGroupOtaPackage", - "operationId": "saveDeviceGroupOtaPackage", + "summary": "Import the bulk of devices (processDevicesBulkImport)", + "description": "There's an ability to import the bulk of devices using the only .csv file. Security check is performed to verify that the user has 'WRITE' permission for the entity (entities).", + "operationId": "processDevicesBulkImport", "requestBody": { "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/DeviceGroupOtaPackage" + "$ref": "#/components/schemas/BulkImportRequest" } } }, @@ -35259,7 +35005,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/DeviceGroupOtaPackage" + "$ref": "#/components/schemas/BulkImportResultDevice" } } } @@ -35380,38 +35126,31 @@ ] } }, - "/api/deviceGroupOtaPackage/{groupId}/{firmwareType}": { - "get": { + "/api/device/credentials": { + "post": { "tags": [ - "device-group-ota-package-controller" + "device-controller" ], - "summary": "getFirmwareById", - "operationId": "getFirmwareById", - "parameters": [ - { - "name": "groupId", - "in": "path", - "required": true, - "schema": { - "type": "string" + "summary": "Update device credentials (updateDeviceCredentials)", + "description": "During device creation, platform generates random 'ACCESS_TOKEN' credentials.\nUse this method to update the device credentials. First use 'getDeviceCredentialsByDeviceId' to get the credentials id and value.\nThen use current method to update the credentials type and value. It is not possible to create multiple device credentials for the same device.\nThe structure of device credentials id and value is simple for the 'ACCESS_TOKEN' but is much more complex for the 'MQTT_BASIC' or 'LWM2M_CREDENTIALS'.\nYou may find the example of device with different type of credentials below: \n\n- Credentials type: **\"Access token\"** with **device ID** and with **device ID** below: \n\n```json\n{\n \"id\": {\n \"id\":\"c886a090-168d-11ee-87c9-6f157dbc816a\"\n },\n \"deviceId\": {\n \"id\":\"c5fb3ac0-168d-11ee-87c9-6f157dbc816a\",\n \"entityType\":\"DEVICE\"\n },\n \"credentialsType\": \"ACCESS_TOKEN\",\n \"credentialsId\": \"6hmxew8pmmzng4e3une4\"\n}\n```\n\n- Credentials type: **\"X509\"** with **device profile ID** below: \n\nNote: **credentialsId** - format **Sha3Hash**, **certificateValue** - format **PEM** (with \"--BEGIN CERTIFICATE----\" and -\"----END CERTIFICATE-\").\n\n```json\n{\n \"id\": {\n \"id\":\"309bd9c0-14f4-11ee-9fc9-d9b7463abb63\"\n },\n \"deviceId\": {\n \"id\":\"3092b200-14f4-11ee-9fc9-d9b7463abb63\",\n \"entityType\":\"DEVICE\"\n },\n \"credentialsType\": \"X509_CERTIFICATE\",\n \"credentialsId\": \"6b8adb49015500e51a527acd332b51684ab9b49b4ade03a9582a44c455e2e9b6\",\n \"credentialsValue\": \"-----BEGIN CERTIFICATE----- MIICMTCCAdegAwIBAgIUUEKxS9hTz4l+oLUMF0LV6TC/gCIwCgYIKoZIzj0EAwIwbjELMAkGA1UEBhMCVVMxETAPBgNVBAgMCE5ldyBZb3JrMRowGAYDVQQKDBFUaGluZ3NCb2FyZCwgSW5jLjEwMC4GA1UEAwwnZGV2aWNlUHJvZmlsZUNlcnRAWDUwOVByb3Zpc2lvblN0cmF0ZWd5MB4XDTIzMDMyOTE0NTczNloXDTI0MDMyODE0NTczNlowbjELMAkGA1UEBhMCVVMxETAPBgNVBAgMCE5ldyBZb3JrMRowGAYDVQQKDBFUaGluZ3NCb2FyZCwgSW5jLjEwMC4GA1UEAwwnZGV2aWNlUHJvZmlsZUNlcnRAWDUwOVByb3Zpc2lvblN0cmF0ZWd5MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAECMlWO72krDoUL9FQjUmSCetkhaEGJUfQkdSfkLSNa0GyAEIMbfmzI4zITeapunu4rGet3EMyLydQzuQanBicp6NTMFEwHQYDVR0OBBYEFHpZ78tPnztNii4Da/yCw6mhEIL3MB8GA1UdIwQYMBaAFHpZ78tPnztNii4Da/yCw6mhEIL3MA8GA1UdEwEB/wQFMAMBAf8wCgYIKoZIzj0EAwIDSAAwRQIgJ7qyMFqNcwSYkH6o+UlQXzLWfwZbNjVk+aR7foAZNGsCIQDsd7v3WQIGHiArfZeDs1DLEDuV/2h6L+ZNoGNhEKL+1A== -----END CERTIFICATE-----\"\n}\n```\n\n- Credentials type: **\"MQTT_BASIC\"** with **device profile ID** below: \n\n```json\n{\n \"id\": {\n \"id\":\"d877ffb0-14f5-11ee-9fc9-d9b7463abb63\"\n },\n \"deviceId\": {\n \"id\":\"d875dcd0-14f5-11ee-9fc9-d9b7463abb63\",\n \"entityType\":\"DEVICE\"\n },\n \"credentialsType\": \"MQTT_BASIC\",\n \"credentialsValue\": \"{\\\"clientId\\\":\\\"juy03yv4owqxcmqhqtvk\\\",\\\"userName\\\":\\\"ov19fxca0cyjn7lm7w7u\\\",\\\"password\\\":\\\"twy94he114dfi9usyk1o\\\"}\"\n}\n```\n\n- You may find the example of **LwM2M** device and **RPK** credentials below: \n\nNote: LwM2M device - only existing device profile ID (Transport configuration -> Transport type: \"LWM2M\".\n\n```json\n{\n \"id\": {\n \"id\":\"e238d4d0-1689-11ee-98c6-1713c1be5a8e\"\n },\n \"deviceId\": {\n \"id\":\"e232e160-1689-11ee-98c6-1713c1be5a8e\",\n \"entityType\":\"DEVICE\"\n },\n \"credentialsType\": \"LWM2M_CREDENTIALS\",\n \"credentialsId\": \"LwRpk00000000\",\n \"credentialsValue\":\n \"{\\\"client\\\":{ \\\"endpoint\\\":\\\"LwRpk00000000\\\", \\\"securityConfigClientMode\\\":\\\"RPK\\\", \\\"key\\\":\\\"MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAEdvBZZ2vQRK9wgDhctj6B1c7bxR3Z0wYg1+YdoYFnVUKWb+rIfTTyYK9tmQJx5Vlb5fxdLnVv1RJOPiwsLIQbAA==\\\" }, \\\"bootstrap\\\":{ \\\"bootstrapServer\\\":{ \\\"securityMode\\\":\\\"RPK\\\", \\\"clientPublicKeyOrId\\\":\\\"MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAEUEBxNl/RcYJNm8mk91CyVXoIJiROYDlXcSSqK6e5bDHwOW4ZiN2lNnXalyF0Jxw8MbAytnDMERXyAja5VEMeVQ==\\\", \\\"clientSecretKey\\\":\\\"MIGHAgEAMBMGByqGSM49AgEGCCqGSM49AwEHBG0wawIBAQQgd9GAx7yZW37autew5KZykn4IgRpge/tZSjnudnZJnMahRANCAARQQHE2X9Fxgk2byaT3ULJVeggmJE5gOVdxJKorp7lsMfA5bhmI3aU2ddqXIXQnHDwxsDK2cMwRFfICNrlUQx5V\\\"}, \\\"lwm2mServer\\\":{ \\\"securityMode\\\":\\\"RPK\\\", \\\"clientPublicKeyOrId\\\":\\\"MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAEUEBxNl/RcYJNm8mk91CyVXoIJiROYDlXcSSqK6e5bDHwOW4ZiN2lNnXalyF0Jxw8MbAytnDMERXyAja5VEMeVQ==\\\", \\\"clientSecretKey\\\":\\\"MIGHAgEAMBMGByqGSM49AgEGCCqGSM49AwEHBG0wawIBAQQgd9GAx7yZW37autew5KZykn4IgRpge/tZSjnudnZJnMahRANCAARQQHE2X9Fxgk2byaT3ULJVeggmJE5gOVdxJKorp7lsMfA5bhmI3aU2ddqXIXQnHDwxsDK2cMwRFfICNrlUQx5V\\\"}} }\"\n}\n```\n\nUpdate to real value:\n - 'id' (this is id of Device Credentials -> \"Get Device Credentials (getDeviceCredentialsByDeviceId)\",\n - 'deviceId.id' (this is id of Device).\nRemove 'tenantId' and optionally 'customerId' from the request body example (below) to create new Device entity.\n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "updateDeviceCredentials", + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/DeviceCredentials" + } } }, - { - "name": "firmwareType", - "in": "path", - "required": true, - "schema": { - "type": "string" - } - } - ], + "required": true + }, "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/DeviceGroupOtaPackage" + "$ref": "#/components/schemas/DeviceCredentials" } } } @@ -35428,7 +35167,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -35532,17 +35271,19 @@ ] } }, - "/api/deviceGroupOtaPackage/{id}": { - "delete": { + "/api/device/info/{deviceId}": { + "get": { "tags": [ - "device-group-ota-package-controller" + "device-controller" ], - "summary": "deleteDeviceGroupOtaPackage", - "operationId": "deleteDeviceGroupOtaPackage", + "summary": "Get Device (getDeviceInfoById)", + "description": "Fetch the Device info object based on the provided Device Id. Device Info is an extension of the default Device object that contains information about the owner name. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getDeviceInfoById", "parameters": [ { - "name": "id", + "name": "deviceId", "in": "path", + "description": "A string value representing the device id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { "type": "string" @@ -35551,7 +35292,14 @@ ], "responses": { "200": { - "description": "OK" + "description": "OK", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/DeviceInfo" + } + } + } }, "400": { "description": "Bad Request", @@ -35669,31 +35417,24 @@ ] } }, - "/api/deviceProfile": { - "post": { + "/api/device/types": { + "get": { "tags": [ - "device-profile-controller" + "device-controller" ], - "summary": "Create Or Update Device Profile (saveDeviceProfile)", - "description": "Create or update the Device Profile. When creating device profile, platform generates device profile id as [time-based UUID](https://en.wikipedia.org/wiki/Universally_unique_identifier#Version_1_(date-time_and_MAC_address)). The newly created device profile id will be present in the response. Specify existing device profile id to update the device profile. Referencing non-existing device profile Id will cause 'Not Found' error. \n\nDevice profile name is unique in the scope of tenant. Only one 'default' device profile may exist in scope of tenant.\n\n# Device profile data definition\n\nDevice profile data object contains device provision strategy and transport type configuration for device connectivity. Let's review some examples. First one is the default device profile data configuration and second one - the custom one. \n\n```json\n{\n \"configuration\":{\n \"type\":\"DEFAULT\"\n },\n \"provisionConfiguration\":{\n \"type\":\"DISABLED\",\n \"provisionDeviceSecret\":null\n },\n \"transportConfiguration\":{\n \"type\":\"DEFAULT\"\n }\n}\n```\n\n```json\n{\n \"configuration\":{\n \"type\":\"DEFAULT\"\n },\n \"provisionConfiguration\":{\n \"type\":\"ALLOW_CREATE_NEW_DEVICES\",\n \"provisionDeviceSecret\":\"vaxb9hzqdbz3oqukvomg\"\n },\n \"transportConfiguration\":{\n \"type\":\"MQTT\",\n \"deviceTelemetryTopic\":\"v1/devices/me/telemetry\",\n \"deviceAttributesTopic\":\"v1/devices/me/attributes\",\n \"transportPayloadTypeConfiguration\":{\n \"transportPayloadType\":\"PROTOBUF\",\n \"deviceTelemetryProtoSchema\":\"syntax =\\\"proto3\\\";\\npackage telemetry;\\n\\nmessage SensorDataReading {\\n\\n optional double temperature = 1;\\n optional double humidity = 2;\\n InnerObject innerObject = 3;\\n\\n message InnerObject {\\n optional string key1 = 1;\\n optional bool key2 = 2;\\n optional double key3 = 3;\\n optional int32 key4 = 4;\\n optional string key5 = 5;\\n }\\n}\",\n \"deviceAttributesProtoSchema\":\"syntax =\\\"proto3\\\";\\npackage attributes;\\n\\nmessage SensorConfiguration {\\n optional string firmwareVersion = 1;\\n optional string serialNumber = 2;\\n}\",\n \"deviceRpcRequestProtoSchema\":\"syntax =\\\"proto3\\\";\\npackage rpc;\\n\\nmessage RpcRequestMsg {\\n optional string method = 1;\\n optional int32 requestId = 2;\\n optional string params = 3;\\n}\",\n \"deviceRpcResponseProtoSchema\":\"syntax =\\\"proto3\\\";\\npackage rpc;\\n\\nmessage RpcResponseMsg {\\n optional string payload = 1;\\n}\"\n }\n }\n}\n```\n\nLet's review some specific objects examples related to the device profile configuration:# Provision Configuration\n\nThere are 3 types of device provision configuration for the device profile: \n * 'DISABLED';\n * 'ALLOW_CREATE_NEW_DEVICES';\n * 'CHECK_PRE_PROVISIONED_DEVICES'.\n\nPlease refer to the [docs](https://thingsboard.io/docs/user-guide/device-provisioning/) for more details.\n\n# Transport Configuration\n\n5 transport configuration types are available:\n * 'DEFAULT';\n * 'MQTT';\n * 'LWM2M';\n * 'COAP';\n * 'SNMP'.\n\nDefault type supports basic MQTT, HTTP, CoAP and LwM2M transports. Please refer to the [docs](https://thingsboard.io/docs/user-guide/device-profiles/#transport-configuration) for more details about other types.\n\nSee another example of COAP transport configuration below:\n\n```json\n{\n \"type\":\"COAP\",\n \"clientSettings\":{\n \"edrxCycle\":null,\n \"powerMode\":\"DRX\",\n \"psmActivityTimer\":null,\n \"pagingTransmissionWindow\":null\n },\n \"coapDeviceTypeConfiguration\":{\n \"coapDeviceType\":\"DEFAULT\",\n \"transportPayloadTypeConfiguration\":{\n \"transportPayloadType\":\"JSON\"\n }\n }\n}\n```Remove 'id', 'tenantId' from the request body example (below) to create new Device Profile entity. \n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "saveDeviceProfile", - "requestBody": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/DeviceProfile" - } - } - }, - "required": true - }, + "summary": "Get Device Types (getDeviceTypes)", + "description": "Deprecated. See 'getDeviceProfileNames' API from Device Profile Controller instead.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", + "operationId": "getDeviceTypes", "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/DeviceProfile" + "type": "array", + "items": { + "$ref": "#/components/schemas/EntitySubtype" + } } } } @@ -35710,7 +35451,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -35804,6 +35545,7 @@ } } }, + "deprecated": true, "security": [ { "HttpLoginForm": [] @@ -35814,20 +35556,20 @@ ] } }, - "/api/deviceProfile/devices/keys/attributes": { + "/api/device/{deviceId}": { "get": { "tags": [ - "device-profile-controller" + "device-controller" ], - "summary": "Get attribute keys (getAttributesKeys)", - "description": "Get a set of unique attribute keys used by devices that belong to specified profile. If profile is not set returns a list of unique keys among all profiles. The call is used for auto-complete in the UI forms. The implementation limits the number of devices that participate in search to 100 as a trade of between accurate results and time-consuming queries. \n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "getAttributesKeys", + "summary": "Get Device (getDeviceById)", + "description": "Fetch the Device object based on the provided Device Id. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getDeviceById", "parameters": [ { - "name": "deviceProfileId", - "in": "query", - "description": "A string value representing the device profile id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": false, + "name": "deviceId", + "in": "path", + "description": "A string value representing the device id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, "schema": { "type": "string" } @@ -35839,10 +35581,7 @@ "content": { "application/json": { "schema": { - "type": "array", - "items": { - "type": "string" - } + "$ref": "#/components/schemas/Device" } } } @@ -35961,22 +35700,20 @@ "ApiKeyForm": [] } ] - } - }, - "/api/deviceProfile/devices/keys/timeseries": { - "get": { + }, + "delete": { "tags": [ - "device-profile-controller" + "device-controller" ], - "summary": "Get time series keys (getDeviceProfileTimeseriesKeys)", - "description": "Get a set of unique time series keys used by devices that belong to specified profile. If profile is not set returns a list of unique keys among all profiles. The call is used for auto-complete in the UI forms. The implementation limits the number of devices that participate in search to 100 as a trade of between accurate results and time-consuming queries. \n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "getDeviceProfileTimeseriesKeys", + "summary": "Delete device (deleteDevice)", + "description": "Deletes the device, it's credentials and all the relations (from and to the device). Referencing non-existing device Id will cause an error.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'DELETE' permission for the entity (entities).", + "operationId": "deleteDevice", "parameters": [ { - "name": "deviceProfileId", - "in": "query", - "description": "A string value representing the device profile id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": false, + "name": "deviceId", + "in": "path", + "description": "A string value representing the device id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, "schema": { "type": "string" } @@ -35984,17 +35721,7 @@ ], "responses": { "200": { - "description": "OK", - "content": { - "application/json": { - "schema": { - "type": "array", - "items": { - "type": "string" - } - } - } - } + "description": "OK" }, "400": { "description": "Bad Request", @@ -36112,23 +35839,22 @@ ] } }, - "/api/deviceProfile/names": { + "/api/device/{deviceId}/credentials": { "get": { "tags": [ - "device-profile-controller" + "device-controller" ], - "summary": "Get Device Profile names (getDeviceProfileNames)", - "description": "Returns a set of unique device profile names owned by the tenant.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", - "operationId": "getDeviceProfileNames", + "summary": "Get Device Credentials (getDeviceCredentialsByDeviceId)", + "description": "If during device creation there wasn't specified any credentials, platform generates random 'ACCESS_TOKEN' credentials.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ_CREDENTIALS' permission for the entity (entities).", + "operationId": "getDeviceCredentialsByDeviceId", "parameters": [ { - "name": "activeOnly", - "in": "query", - "description": "Flag indicating whether to retrieve exclusively the names of device profiles that are referenced by tenant's devices.", - "required": false, + "name": "deviceId", + "in": "path", + "description": "A string value representing the device id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, "schema": { - "type": "boolean", - "default": false + "type": "string" } } ], @@ -36138,10 +35864,7 @@ "content": { "application/json": { "schema": { - "type": "array", - "items": { - "$ref": "#/components/schemas/EntityInfo" - } + "$ref": "#/components/schemas/DeviceCredentials" } } } @@ -36262,32 +35985,99 @@ ] } }, - "/api/deviceProfile/{deviceProfileId}": { + "/api/deviceInfos/all": { "get": { "tags": [ - "device-profile-controller" + "device-controller" ], - "summary": "Get Device Profile (getDeviceProfileById)", - "description": "Fetch the Device Profile object based on the provided Device Profile Id. The server checks that the device profile is owned by the same tenant. \n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "getDeviceProfileById", + "summary": "Get All Device Infos for current user (getAllDeviceInfos)", + "description": "Returns a page of device info objects owned by the tenant or the customer of a current user. Device Info is an extension of the default Device object that contains information about the owner name. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getAllDeviceInfos", "parameters": [ + { + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", + "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", + "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "includeCustomers", + "in": "query", + "description": "Include customer or sub-customer entities", + "required": false, + "schema": { + "type": "boolean" + } + }, { "name": "deviceProfileId", - "in": "path", + "in": "query", "description": "A string value representing the device profile id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": true, + "required": false, "schema": { "type": "string" } }, { - "name": "inlineImages", + "name": "active", "in": "query", - "description": "Inline images as a data URL (Base64)", + "description": "A boolean value representing the device active flag.", "required": false, "schema": { "type": "boolean" } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'substring' filter based on the device name.", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string", + "enum": [ + "createdTime", + "name", + "deviceProfileName", + "label", + "customerTitle" + ] + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] + } } ], "responses": { @@ -36296,7 +36086,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/DeviceProfile" + "$ref": "#/components/schemas/PageDataDeviceInfo" } } } @@ -36415,28 +36205,43 @@ "ApiKeyForm": [] } ] - }, - "delete": { + } + }, + "/api/devices": { + "get": { "tags": [ - "device-profile-controller" + "device-controller" ], - "summary": "Delete device profile (deleteDeviceProfile)", - "description": "Deletes the device profile. Referencing non-existing device profile Id will cause an error. Can't delete the device profile if it is referenced by existing devices.\n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "deleteDeviceProfile", + "summary": "Get Devices By Ids (getDevicesByIds)", + "description": "Requested devices must be owned by tenant or assigned to customer which user is performing the request. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getDevicesByIds", "parameters": [ { - "name": "deviceProfileId", - "in": "path", - "description": "A string value representing the device profile id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "name": "deviceIds", + "in": "query", + "description": "A list of devices ids, separated by comma ','", "required": true, "schema": { - "type": "string" + "type": "array", + "items": { + "type": "string" + } } } ], "responses": { "200": { - "description": "OK" + "description": "OK", + "content": { + "application/json": { + "schema": { + "type": "array", + "items": { + "$ref": "#/components/schemas/Device" + } + } + } + } }, "400": { "description": "Bad Request", @@ -36552,34 +36357,34 @@ "ApiKeyForm": [] } ] - } - }, - "/api/deviceProfile/{deviceProfileId}/default": { + }, "post": { "tags": [ - "device-profile-controller" + "device-controller" ], - "summary": "Make Device Profile Default (setDefaultDeviceProfile)", - "description": "Marks device profile as default within a tenant scope.\n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "setDefaultDeviceProfile", - "parameters": [ - { - "name": "deviceProfileId", - "in": "path", - "description": "A string value representing the device profile id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": true, - "schema": { - "type": "string" + "summary": "Find related devices (findDevicesByQuery)", + "description": "Returns all devices that are related to the specific entity. The entity id, relation type, device types, depth of the search, and other query parameters defined using complex 'DeviceSearchQuery' object. See 'Model' tab of the Parameters for more info.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "findDevicesByQuery", + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/DeviceSearchQuery" + } } - } - ], + }, + "required": true + }, "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/DeviceProfile" + "type": "array", + "items": { + "$ref": "#/components/schemas/Device" + } } } } @@ -36700,21 +36505,46 @@ ] } }, - "/api/deviceProfileInfo/default": { + "/api/devices/count/{otaPackageType}/{deviceProfileId}": { "get": { "tags": [ - "device-profile-controller" + "device-controller" + ], + "summary": "Count devices by device profile (countByDeviceProfileAndEmptyOtaPackage)", + "description": "The platform gives an ability to load OTA (over-the-air) packages to devices. It can be done in two different ways: device scope or device profile scope.In the response you will find the number of devices with specified device profile, but without previously defined device scope OTA package. It can be useful when you want to define number of devices that will be affected with future OTA package\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "countByDeviceProfileAndEmptyOtaPackage", + "parameters": [ + { + "name": "otaPackageType", + "in": "path", + "description": "OTA package type", + "required": true, + "schema": { + "type": "string", + "enum": [ + "FIRMWARE", + "SOFTWARE" + ] + } + }, + { + "name": "deviceProfileId", + "in": "path", + "description": "Device Profile Id. I.g. '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, + "schema": { + "type": "string" + } + } ], - "summary": "Get Default Device Profile (getDefaultDeviceProfileInfo)", - "description": "Fetch the Default Device Profile Info object. Device Profile Info is a lightweight object that includes main information about Device Profile excluding the heavyweight configuration object. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", - "operationId": "getDefaultDeviceProfileInfo", "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/DeviceProfileInfo" + "type": "integer", + "format": "int64" } } } @@ -36835,19 +36665,39 @@ ] } }, - "/api/deviceProfileInfo/{deviceProfileId}": { + "/api/devices/count/{otaPackageType}/{otaPackageId}/{entityGroupId}": { "get": { "tags": [ - "device-profile-controller" + "device-controller" ], - "summary": "Get Device Profile Info (getDeviceProfileInfoById)", - "description": "Fetch the Device Profile Info object based on the provided Device Profile Id. Device Profile Info is a lightweight object that includes main information about Device Profile excluding the heavyweight configuration object. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", - "operationId": "getDeviceProfileInfoById", + "summary": "Count devices by device profile (countByDeviceProfileAndEmptyOtaPackage)", + "description": "The platform gives an ability to load OTA (over-the-air) packages to devices. It can be done in two different ways: device scope or device profile scope.In the response you will find the number of devices with specified device profile, but without previously defined device scope OTA package. It can be useful when you want to define number of devices that will be affected with future OTA package\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "countByDeviceGroupAndEmptyOtaPackage", "parameters": [ { - "name": "deviceProfileId", + "name": "otaPackageType", + "in": "path", + "description": "OTA package type", + "required": true, + "schema": { + "type": "string", + "enum": [ + "FIRMWARE", + "SOFTWARE" + ] + } + }, + { + "name": "otaPackageId", + "in": "path", + "required": true, + "schema": { + "type": "string" + } + }, + { + "name": "entityGroupId", "in": "path", - "description": "A string value representing the device profile id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { "type": "string" @@ -36860,7 +36710,8 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/DeviceProfileInfo" + "type": "integer", + "format": "int64" } } } @@ -36981,23 +36832,32 @@ ] } }, - "/api/deviceProfileInfos": { + "/api/entityGroup/{entityGroupId}/devices": { "get": { "tags": [ - "device-profile-controller" + "device-controller" ], - "summary": "Get Device Profiles for transport type (getDeviceProfileInfos)", - "description": "Returns a page of devices profile info objects owned by tenant. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. Device Profile Info is a lightweight object that includes main information about Device Profile excluding the heavyweight configuration object. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", - "operationId": "getDeviceProfileInfos", + "summary": "Get devices by Entity Group Id (getDevicesByEntityGroupId)", + "description": "Returns a page of Device objects that belongs to specified Entity Group Id. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", + "operationId": "getDevicesByEntityGroupId", "parameters": [ + { + "name": "entityGroupId", + "in": "path", + "description": "A string value representing the Entity Group Id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, + "schema": { + "type": "string" + } + }, { "name": "pageSize", "in": "query", "description": "Maximum amount of entities in a one page", "required": true, "schema": { - "type": "integer", - "format": "int32" + "type": "string", + "minimum": 1 } }, { @@ -37006,14 +36866,14 @@ "description": "Sequence number of page starting from 0", "required": true, "schema": { - "type": "integer", - "format": "int32" + "type": "string", + "minimum": 0 } }, { "name": "textSearch", "in": "query", - "description": "The case insensitive 'substring' filter based on the device profile name.", + "description": "The case insensitive 'substring' filter based on the device name.", "required": false, "schema": { "type": "string" @@ -37029,10 +36889,9 @@ "enum": [ "createdTime", "name", - "type", - "transportType", - "description", - "isDefault" + "deviceProfileName", + "label", + "customerTitle" ] } }, @@ -37048,22 +36907,6 @@ "DESC" ] } - }, - { - "name": "transportType", - "in": "query", - "description": "Type of the transport", - "required": false, - "schema": { - "type": "string", - "enum": [ - "DEFAULT", - "MQTT", - "COAP", - "LWM2M", - "SNMP" - ] - } } ], "responses": { @@ -37072,7 +36915,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataDeviceProfileInfo" + "$ref": "#/components/schemas/PageDataDevice" } } } @@ -37193,25 +37036,22 @@ ] } }, - "/api/deviceProfileInfos/list": { + "/api/tenant/device": { "get": { "tags": [ - "device-profile-controller" + "device-controller" ], - "summary": "Get Device Profile Infos By Ids (getDeviceProfileInfosByIds)", - "description": "Requested device profiles must be owned by tenant which is performing the request. \n\n Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getDeviceProfileInfosByIds", + "summary": "Get Tenant Device (getTenantDevice)", + "description": "Requested device must be owned by tenant that the user belongs to. Device name is an unique property of device. So it can be used to identify the device.\n\nAvailable for users with 'TENANT_ADMIN' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getTenantDeviceByName", "parameters": [ { - "name": "deviceProfileIds", + "name": "deviceName", "in": "query", - "description": "A list of device profile ids, separated by comma ','", + "description": "A string value representing the Device name.", "required": true, "schema": { - "type": "array", - "items": { - "type": "string" - } + "type": "string" } } ], @@ -37221,10 +37061,7 @@ "content": { "application/json": { "schema": { - "type": "array", - "items": { - "$ref": "#/components/schemas/DeviceProfileInfo" - } + "$ref": "#/components/schemas/Device" } } } @@ -37345,14 +37182,14 @@ ] } }, - "/api/deviceProfiles": { + "/api/tenant/devices": { "get": { "tags": [ - "device-profile-controller" + "device-controller" ], - "summary": "Get Device Profiles (getDeviceProfiles)", - "description": "Returns a page of devices profile objects owned by tenant. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "getDeviceProfiles", + "summary": "Get Tenant Devices (getTenantDevices)", + "description": "Returns a page of devices owned by tenant. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getTenantDevices", "parameters": [ { "name": "pageSize", @@ -37374,10 +37211,19 @@ "format": "int32" } }, + { + "name": "type", + "in": "query", + "description": "Device type as the name of the device profile", + "required": false, + "schema": { + "type": "string" + } + }, { "name": "textSearch", "in": "query", - "description": "The case insensitive 'substring' filter based on the device profile name.", + "description": "The case insensitive 'substring' filter based on the device name.", "required": false, "schema": { "type": "string" @@ -37393,10 +37239,9 @@ "enum": [ "createdTime", "name", - "type", - "transportType", - "description", - "isDefault" + "deviceProfileName", + "label", + "customerTitle" ] } }, @@ -37420,7 +37265,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataDeviceProfile" + "$ref": "#/components/schemas/PageDataDevice" } } } @@ -37541,45 +37386,41 @@ ] } }, - "/api/domain": { + "/api/tenant/{tenantId}/device/{deviceId}": { "post": { "tags": [ - "domain-controller" + "device-controller" ], - "summary": "Save or Update Domain (saveDomain)", - "description": "Create or update the Domain. When creating domain, platform generates Domain Id as [time-based UUID](https://en.wikipedia.org/wiki/Universally_unique_identifier#Version_1_(date-time_and_MAC_address)). The newly created Domain Id will be present in the response. Specify existing Domain Id to update the domain. Referencing non-existing Domain Id will cause 'Not Found' error.\n\nDomain name is unique for entire platform setup.\n\n\n\nAvailable for users with 'SYS_ADMIN' or 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", - "operationId": "saveDomain", + "summary": "Assign device to tenant (assignDeviceToTenant)", + "description": "Creates assignment of the device to tenant. Thereafter tenant will be able to reassign the device to a customer.\n\nAvailable for users with 'TENANT_ADMIN' authority. Security check is performed to verify that the user has 'ASSIGN_TO_TENANT' permission for the entity (entities).", + "operationId": "assignDeviceToTenant", "parameters": [ { - "name": "oauth2ClientIds", - "in": "query", - "description": "A list of oauth2 client registration ids, separated by comma ','", - "required": false, + "name": "tenantId", + "in": "path", + "description": "A string value representing the tenant id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, "schema": { - "type": "array", - "items": { - "type": "string" - } + "type": "string" + } + }, + { + "name": "deviceId", + "in": "path", + "description": "A string value representing the device id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, + "schema": { + "type": "string" } } ], - "requestBody": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/Domain" - } - } - }, - "required": true - }, "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/Domain" + "$ref": "#/components/schemas/Device" } } } @@ -37700,22 +37541,80 @@ ] } }, - "/api/domain/info/{id}": { + "/api/user/devices": { "get": { "tags": [ - "domain-controller" + "device-controller" ], - "summary": "Get Domain info by Id (getDomainInfoById)", - "description": "\n\nAvailable for users with 'SYS_ADMIN' or 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", - "operationId": "getDomainInfoById", + "summary": "Get Devices (getUserDevices)", + "description": "Returns a page of devices that are available for the current user. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getUserDevices", "parameters": [ { - "name": "id", - "in": "path", + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", "required": true, "schema": { "type": "string", - "format": "uuid" + "minimum": 1 + } + }, + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", + "required": true, + "schema": { + "type": "string", + "minimum": 0 + } + }, + { + "name": "type", + "in": "query", + "description": "Device type as the name of the device profile", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'substring' filter based on the device name.", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string", + "enum": [ + "createdTime", + "name", + "deviceProfileName", + "label", + "customerTitle" + ] + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] } } ], @@ -37725,7 +37624,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/DomainInfo" + "$ref": "#/components/schemas/PageDataDevice" } } } @@ -37846,70 +37745,30 @@ ] } }, - "/api/domain/infos": { - "get": { + "/api/deviceGroupOtaPackage": { + "post": { "tags": [ - "domain-controller" + "device-group-ota-package-controller" ], - "summary": "Get Domain infos (getDomainInfos)", - "description": "\n\nAvailable for users with 'SYS_ADMIN' or 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", - "operationId": "getDomainInfos", - "parameters": [ - { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", - "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "textSearch", - "in": "query", - "description": "Case-insensitive 'substring' filter based on domain's name", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, - "schema": { - "type": "string" + "summary": "saveDeviceGroupOtaPackage", + "operationId": "saveDeviceGroupOtaPackage", + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/DeviceGroupOtaPackage" + } } }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string" - } - } - ], + "required": true + }, "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataDomainInfo" + "$ref": "#/components/schemas/DeviceGroupOtaPackage" } } } @@ -37926,7 +37785,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -38030,28 +37889,41 @@ ] } }, - "/api/domain/{id}": { - "delete": { + "/api/deviceGroupOtaPackage/{groupId}/{firmwareType}": { + "get": { "tags": [ - "domain-controller" + "device-group-ota-package-controller" ], - "summary": "Delete Domain by ID (deleteDomain)", - "description": "Deletes Domain by ID. Referencing non-existing domain Id will cause an error.\n\nAvailable for users with 'SYS_ADMIN' or 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", - "operationId": "deleteDomain", + "summary": "getFirmwareById", + "operationId": "getFirmwareById", "parameters": [ { - "name": "id", + "name": "groupId", "in": "path", "required": true, "schema": { - "type": "string", - "format": "uuid" + "type": "string" + } + }, + { + "name": "firmwareType", + "in": "path", + "required": true, + "schema": { + "type": "string" } } ], "responses": { "200": { - "description": "OK" + "description": "OK", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/DeviceGroupOtaPackage" + } + } + } }, "400": { "description": "Bad Request", @@ -38169,39 +38041,23 @@ ] } }, - "/api/domain/{id}/oauth2Clients": { - "put": { + "/api/deviceGroupOtaPackage/{id}": { + "delete": { "tags": [ - "domain-controller" + "device-group-ota-package-controller" ], - "summary": "Update oauth2 clients (updateDomainOauth2Clients)", - "description": "Update oauth2 clients for the specified domain. \n\nAvailable for users with 'SYS_ADMIN' or 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", - "operationId": "updateDomainOauth2Clients", + "summary": "deleteDeviceGroupOtaPackage", + "operationId": "deleteDeviceGroupOtaPackage", "parameters": [ { "name": "id", "in": "path", "required": true, "schema": { - "type": "string", - "format": "uuid" + "type": "string" } } ], - "requestBody": { - "content": { - "application/json": { - "schema": { - "type": "array", - "items": { - "type": "string", - "format": "uuid" - } - } - } - }, - "required": true - }, "responses": { "200": { "description": "OK" @@ -38322,108 +38178,31 @@ ] } }, - "/api/customer/{customerId}/edgeInfos": { - "get": { + "/api/deviceProfile": { + "post": { "tags": [ - "edge-controller" + "device-profile-controller" ], - "summary": "Get Customer Edge Infos (getCustomerEdgeInfos)", - "description": "Returns a page of edge info objects owned by the specified customer. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getCustomerEdgeInfos", - "parameters": [ - { - "name": "customerId", - "in": "path", - "description": "A string value representing the customer id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": true, - "schema": { - "type": "string" - } - }, - { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", - "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "includeCustomers", - "in": "query", - "description": "Include customer or sub-customer entities", - "required": false, - "schema": { - "type": "boolean" - } - }, - { - "name": "type", - "in": "query", - "description": "A string value representing the edge type. For example, 'default'", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'substring' filter based on the edge name.", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, - "schema": { - "type": "string", - "enum": [ - "createdTime", - "name", - "type", - "label", - "customerTitle" - ] + "summary": "Create Or Update Device Profile (saveDeviceProfile)", + "description": "Create or update the Device Profile. When creating device profile, platform generates device profile id as [time-based UUID](https://en.wikipedia.org/wiki/Universally_unique_identifier#Version_1_(date-time_and_MAC_address)). The newly created device profile id will be present in the response. Specify existing device profile id to update the device profile. Referencing non-existing device profile Id will cause 'Not Found' error. \n\nDevice profile name is unique in the scope of tenant. Only one 'default' device profile may exist in scope of tenant.\n\n# Device profile data definition\n\nDevice profile data object contains device provision strategy and transport type configuration for device connectivity. Let's review some examples. First one is the default device profile data configuration and second one - the custom one. \n\n```json\n{\n \"configuration\":{\n \"type\":\"DEFAULT\"\n },\n \"provisionConfiguration\":{\n \"type\":\"DISABLED\",\n \"provisionDeviceSecret\":null\n },\n \"transportConfiguration\":{\n \"type\":\"DEFAULT\"\n }\n}\n```\n\n```json\n{\n \"configuration\":{\n \"type\":\"DEFAULT\"\n },\n \"provisionConfiguration\":{\n \"type\":\"ALLOW_CREATE_NEW_DEVICES\",\n \"provisionDeviceSecret\":\"vaxb9hzqdbz3oqukvomg\"\n },\n \"transportConfiguration\":{\n \"type\":\"MQTT\",\n \"deviceTelemetryTopic\":\"v1/devices/me/telemetry\",\n \"deviceAttributesTopic\":\"v1/devices/me/attributes\",\n \"transportPayloadTypeConfiguration\":{\n \"transportPayloadType\":\"PROTOBUF\",\n \"deviceTelemetryProtoSchema\":\"syntax =\\\"proto3\\\";\\npackage telemetry;\\n\\nmessage SensorDataReading {\\n\\n optional double temperature = 1;\\n optional double humidity = 2;\\n InnerObject innerObject = 3;\\n\\n message InnerObject {\\n optional string key1 = 1;\\n optional bool key2 = 2;\\n optional double key3 = 3;\\n optional int32 key4 = 4;\\n optional string key5 = 5;\\n }\\n}\",\n \"deviceAttributesProtoSchema\":\"syntax =\\\"proto3\\\";\\npackage attributes;\\n\\nmessage SensorConfiguration {\\n optional string firmwareVersion = 1;\\n optional string serialNumber = 2;\\n}\",\n \"deviceRpcRequestProtoSchema\":\"syntax =\\\"proto3\\\";\\npackage rpc;\\n\\nmessage RpcRequestMsg {\\n optional string method = 1;\\n optional int32 requestId = 2;\\n optional string params = 3;\\n}\",\n \"deviceRpcResponseProtoSchema\":\"syntax =\\\"proto3\\\";\\npackage rpc;\\n\\nmessage RpcResponseMsg {\\n optional string payload = 1;\\n}\"\n }\n }\n}\n```\n\nLet's review some specific objects examples related to the device profile configuration:# Provision Configuration\n\nThere are 3 types of device provision configuration for the device profile: \n * 'DISABLED';\n * 'ALLOW_CREATE_NEW_DEVICES';\n * 'CHECK_PRE_PROVISIONED_DEVICES'.\n\nPlease refer to the [docs](https://thingsboard.io/docs/user-guide/device-provisioning/) for more details.\n\n# Transport Configuration\n\n5 transport configuration types are available:\n * 'DEFAULT';\n * 'MQTT';\n * 'LWM2M';\n * 'COAP';\n * 'SNMP'.\n\nDefault type supports basic MQTT, HTTP, CoAP and LwM2M transports. Please refer to the [docs](https://thingsboard.io/docs/user-guide/device-profiles/#transport-configuration) for more details about other types.\n\nSee another example of COAP transport configuration below:\n\n```json\n{\n \"type\":\"COAP\",\n \"clientSettings\":{\n \"edrxCycle\":null,\n \"powerMode\":\"DRX\",\n \"psmActivityTimer\":null,\n \"pagingTransmissionWindow\":null\n },\n \"coapDeviceTypeConfiguration\":{\n \"coapDeviceType\":\"DEFAULT\",\n \"transportPayloadTypeConfiguration\":{\n \"transportPayloadType\":\"JSON\"\n }\n }\n}\n```Remove 'id', 'tenantId' from the request body example (below) to create new Device Profile entity. \n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "saveDeviceProfile", + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/DeviceProfile" + } } }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] - } - } - ], + "required": true + }, "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataEdgeInfo" + "$ref": "#/components/schemas/DeviceProfile" } } } @@ -38440,7 +38219,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -38544,90 +38323,23 @@ ] } }, - "/api/customer/{customerId}/edges": { + "/api/deviceProfile/devices/keys/attributes": { "get": { "tags": [ - "edge-controller" + "device-profile-controller" ], - "summary": "Get Customer Edges (getCustomerEdges)", - "description": "Returns a page of edges objects assigned to customer. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", - "operationId": "getCustomerEdges", + "summary": "Get attribute keys (getAttributesKeys)", + "description": "Get a set of unique attribute keys used by devices that belong to specified profile. If profile is not set returns a list of unique keys among all profiles. The call is used for auto-complete in the UI forms. The implementation limits the number of devices that participate in search to 100 as a trade of between accurate results and time-consuming queries. \n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "getAttributesKeys", "parameters": [ { - "name": "customerId", - "in": "path", - "description": "A string value representing the customer id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": true, - "schema": { - "type": "string" - } - }, - { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", - "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "type", - "in": "query", - "description": "A string value representing the edge type. For example, 'default'", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "textSearch", + "name": "deviceProfileId", "in": "query", - "description": "The case insensitive 'substring' filter based on the edge name.", + "description": "A string value representing the device profile id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": false, "schema": { "type": "string" } - }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, - "schema": { - "type": "string", - "enum": [ - "createdTime", - "name", - "type", - "label", - "customerTitle" - ] - } - }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] - } } ], "responses": { @@ -38636,7 +38348,10 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataEdge" + "type": "array", + "items": { + "type": "string" + } } } } @@ -38757,53 +38472,35 @@ ] } }, - "/api/edge": { - "post": { + "/api/deviceProfile/devices/keys/timeseries": { + "get": { "tags": [ - "edge-controller" + "device-profile-controller" ], - "summary": "Create Or Update Edge (saveEdge)", - "description": "Create or update the Edge. When creating edge, platform generates Edge Id as [time-based UUID](https://en.wikipedia.org/wiki/Universally_unique_identifier#Version_1_(date-time_and_MAC_address)). The newly created edge id will be present in the response. Specify existing Edge id to update the edge. Referencing non-existing Edge Id will cause 'Not Found' error.\n\nEdge name is unique in the scope of tenant. Use unique identifiers like MAC or IMEI for the edge names and non-unique 'label' field for user-friendly visualization purposes.Remove 'id', 'tenantId' and optionally 'customerId' from the request body example (below) to create new Edge entity. ", - "operationId": "saveEdge", + "summary": "Get time series keys (getDeviceProfileTimeseriesKeys)", + "description": "Get a set of unique time series keys used by devices that belong to specified profile. If profile is not set returns a list of unique keys among all profiles. The call is used for auto-complete in the UI forms. The implementation limits the number of devices that participate in search to 100 as a trade of between accurate results and time-consuming queries. \n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "getDeviceProfileTimeseriesKeys", "parameters": [ { - "name": "entityGroupId", + "name": "deviceProfileId", "in": "query", + "description": "A string value representing the device profile id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": false, "schema": { "type": "string" } - }, - { - "name": "entityGroupIds", - "in": "query", - "description": "A list of entity group ids, separated by comma ','", - "required": false, - "schema": { - "type": "array", - "items": { - "type": "string" - } - } } ], - "requestBody": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/Edge" - } - } - }, - "required": true - }, "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/Edge" + "type": "array", + "items": { + "type": "string" + } } } } @@ -38820,7 +38517,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -38924,31 +38621,36 @@ ] } }, - "/api/edge/bulk_import": { - "post": { + "/api/deviceProfile/names": { + "get": { "tags": [ - "edge-controller" + "device-profile-controller" ], - "summary": "Import the bulk of edges (processEdgesBulkImport)", - "description": "There's an ability to import the bulk of edges using the only .csv file.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", - "operationId": "processEdgesBulkImport", - "requestBody": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/BulkImportRequest" - } + "summary": "Get Device Profile names (getDeviceProfileNames)", + "description": "Returns a set of unique device profile names owned by the tenant.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", + "operationId": "getDeviceProfileNames", + "parameters": [ + { + "name": "activeOnly", + "in": "query", + "description": "Flag indicating whether to retrieve exclusively the names of device profiles that are referenced by tenant's devices.", + "required": false, + "schema": { + "type": "boolean", + "default": false } - }, - "required": true - }, + } + ], "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/BulkImportResultEdge" + "type": "array", + "items": { + "$ref": "#/components/schemas/EntityInfo" + } } } } @@ -38965,7 +38667,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -39069,23 +38771,32 @@ ] } }, - "/api/edge/info/{edgeId}": { + "/api/deviceProfile/{deviceProfileId}": { "get": { "tags": [ - "edge-controller" + "device-profile-controller" ], - "summary": "Get Edge Info (getEdgeInfoById)", - "description": "Get the Edge info object based on the provided Edge Id. If the user has the authority of 'Tenant Administrator', the server checks that the edge is owned by the same tenant. If the user has the authority of 'Customer User', the server checks that the edge is assigned to the same customer.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", - "operationId": "getEdgeInfoById", + "summary": "Get Device Profile (getDeviceProfileById)", + "description": "Fetch the Device Profile object based on the provided Device Profile Id. The server checks that the device profile is owned by the same tenant. \n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "getDeviceProfileById", "parameters": [ { - "name": "edgeId", + "name": "deviceProfileId", "in": "path", - "description": "A string value representing the edge id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "description": "A string value representing the device profile id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { "type": "string" } + }, + { + "name": "inlineImages", + "in": "query", + "description": "Inline images as a data URL (Base64)", + "required": false, + "schema": { + "type": "boolean" + } } ], "responses": { @@ -39094,7 +38805,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/EdgeInfo" + "$ref": "#/components/schemas/DeviceProfile" } } } @@ -39213,38 +38924,161 @@ "ApiKeyForm": [] } ] - } - }, - "/api/edge/instructions/install/{edgeId}/{method}": { - "get": { + }, + "delete": { "tags": [ - "edge-controller" + "device-profile-controller" ], - "summary": "Get Edge Install Instructions (getEdgeInstallInstructions)", - "description": "Get an install instructions for provided edge id.If the user has the authority of 'Tenant Administrator', the server checks that the edge is owned by the same tenant. If the user has the authority of 'Customer User', the server checks that the edge is assigned to the same customer.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", - "operationId": "getEdgeInstallInstructions", + "summary": "Delete device profile (deleteDeviceProfile)", + "description": "Deletes the device profile. Referencing non-existing device profile Id will cause an error. Can't delete the device profile if it is referenced by existing devices.\n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "deleteDeviceProfile", "parameters": [ { - "name": "edgeId", + "name": "deviceProfileId", "in": "path", - "description": "A string value representing the edge id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "description": "A string value representing the device profile id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { "type": "string" } + } + ], + "responses": { + "200": { + "description": "OK" }, + "400": { + "description": "Bad Request", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-400": { + "summary": "Bad Request", + "value": { + "status": 400, + "message": "Invalid UUID string: 123", + "errorCode": 31, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "401": { + "description": "Unauthorized", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-401": { + "summary": "Unauthorized", + "value": { + "status": 401, + "message": "Authentication failed", + "errorCode": 10, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "403": { + "description": "Forbidden", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-403": { + "summary": "Forbidden", + "value": { + "status": 403, + "message": "You don't have permission to perform this operation!", + "errorCode": 20, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "404": { + "description": "Not Found", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-404": { + "summary": "Not Found", + "value": { + "status": 404, + "message": "Requested item wasn't found!", + "errorCode": 32, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "429": { + "description": "Too Many Requests", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-429": { + "summary": "Too Many Requests", + "value": { + "status": 429, + "message": "Too many requests for current tenant!", + "errorCode": 33, + "timestamp": 1609459200000 + } + } + } + } + } + } + }, + "security": [ { - "name": "method", + "HttpLoginForm": [] + }, + { + "ApiKeyForm": [] + } + ] + } + }, + "/api/deviceProfile/{deviceProfileId}/default": { + "post": { + "tags": [ + "device-profile-controller" + ], + "summary": "Make Device Profile Default (setDefaultDeviceProfile)", + "description": "Marks device profile as default within a tenant scope.\n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "setDefaultDeviceProfile", + "parameters": [ + { + "name": "deviceProfileId", "in": "path", - "description": "Installation method ('docker', 'ubuntu' or 'centos')", + "description": "A string value representing the device profile id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { - "type": "string", - "enum": [ - "docker", - "ubuntu", - "centos" - ] + "type": "string" } } ], @@ -39254,7 +39088,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/EdgeInstructions" + "$ref": "#/components/schemas/DeviceProfile" } } } @@ -39271,7 +39105,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -39375,46 +39209,21 @@ ] } }, - "/api/edge/instructions/upgrade/{edgeVersion}/{method}": { + "/api/deviceProfileInfo/default": { "get": { "tags": [ - "edge-controller" - ], - "summary": "Get Edge Upgrade Instructions (getEdgeUpgradeInstructions)", - "description": "Get an upgrade instructions for provided edge version.If the user has the authority of 'Tenant Administrator', the server checks that the edge is owned by the same tenant. If the user has the authority of 'Customer User', the server checks that the edge is assigned to the same customer.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", - "operationId": "getEdgeUpgradeInstructions", - "parameters": [ - { - "name": "edgeVersion", - "in": "path", - "description": "Edge version", - "required": true, - "schema": { - "type": "string" - } - }, - { - "name": "method", - "in": "path", - "description": "Upgrade method ('docker', 'ubuntu' or 'centos')", - "required": true, - "schema": { - "type": "string", - "enum": [ - "docker", - "ubuntu", - "centos" - ] - } - } + "device-profile-controller" ], + "summary": "Get Default Device Profile (getDefaultDeviceProfileInfo)", + "description": "Fetch the Default Device Profile Info object. Device Profile Info is a lightweight object that includes main information about Device Profile excluding the heavyweight configuration object. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", + "operationId": "getDefaultDeviceProfileInfo", "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/EdgeInstructions" + "$ref": "#/components/schemas/DeviceProfileInfo" } } } @@ -39535,19 +39344,19 @@ ] } }, - "/api/edge/missingToRelatedRuleChains/{edgeId}": { + "/api/deviceProfileInfo/{deviceProfileId}": { "get": { "tags": [ - "edge-controller" + "device-profile-controller" ], - "summary": "Find missing rule chains (findMissingToRelatedRuleChains)", - "description": "Returns list of rule chains ids that are not assigned to particular edge, but these rule chains are present in the already assigned rule chains to edge.\n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "findMissingToRelatedRuleChains", + "summary": "Get Device Profile Info (getDeviceProfileInfoById)", + "description": "Fetch the Device Profile Info object based on the provided Device Profile Id. Device Profile Info is a lightweight object that includes main information about Device Profile excluding the heavyweight configuration object. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", + "operationId": "getDeviceProfileInfoById", "parameters": [ { - "name": "edgeId", + "name": "deviceProfileId", "in": "path", - "description": "A string value representing the edge id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "description": "A string value representing the device profile id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { "type": "string" @@ -39560,7 +39369,7 @@ "content": { "application/json": { "schema": { - "type": "string" + "$ref": "#/components/schemas/DeviceProfileInfo" } } } @@ -39681,23 +39490,89 @@ ] } }, - "/api/edge/sync/{edgeId}": { - "post": { + "/api/deviceProfileInfos": { + "get": { "tags": [ - "edge-controller" + "device-profile-controller" ], - "summary": "Sync edge (syncEdge)", - "description": "Starts synchronization process between edge and cloud. \nAll entities that are assigned to particular edge are going to be send to remote edge service.\n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "syncEdge", + "summary": "Get Device Profiles for transport type (getDeviceProfileInfos)", + "description": "Returns a page of devices profile info objects owned by tenant. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. Device Profile Info is a lightweight object that includes main information about Device Profile excluding the heavyweight configuration object. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", + "operationId": "getDeviceProfileInfos", "parameters": [ { - "name": "edgeId", - "in": "path", - "description": "A string value representing the edge id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", + "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'substring' filter based on the device profile name.", + "required": false, "schema": { "type": "string" } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string", + "enum": [ + "createdTime", + "name", + "type", + "transportType", + "description", + "isDefault" + ] + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] + } + }, + { + "name": "transportType", + "in": "query", + "description": "Type of the transport", + "required": false, + "schema": { + "type": "string", + "enum": [ + "DEFAULT", + "MQTT", + "COAP", + "LWM2M", + "SNMP" + ] + } } ], "responses": { @@ -39706,7 +39581,7 @@ "content": { "application/json": { "schema": { - "type": "string" + "$ref": "#/components/schemas/PageDataDeviceProfileInfo" } } } @@ -39723,7 +39598,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -39827,14 +39702,28 @@ ] } }, - "/api/edge/types": { + "/api/deviceProfileInfos/list": { "get": { "tags": [ - "edge-controller" + "device-profile-controller" + ], + "summary": "Get Device Profile Infos By Ids (getDeviceProfileInfosByIds)", + "description": "Requested device profiles must be owned by tenant which is performing the request. \n\n Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getDeviceProfileInfosByIds", + "parameters": [ + { + "name": "deviceProfileIds", + "in": "query", + "description": "A list of device profile ids, separated by comma ','", + "required": true, + "schema": { + "type": "array", + "items": { + "type": "string" + } + } + } ], - "summary": "Get Edge Types (getEdgeTypes)", - "description": "Returns a set of unique edge types based on edges that are either owned by the tenant or assigned to the customer which user is performing the request.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", - "operationId": "getEdgeTypes", "responses": { "200": { "description": "OK", @@ -39843,7 +39732,7 @@ "schema": { "type": "array", "items": { - "$ref": "#/components/schemas/EntitySubtype" + "$ref": "#/components/schemas/DeviceProfileInfo" } } } @@ -39965,23 +39854,73 @@ ] } }, - "/api/edge/{edgeId}": { + "/api/deviceProfiles": { "get": { "tags": [ - "edge-controller" + "device-profile-controller" ], - "summary": "Get Edge (getEdgeById)", - "description": "Get the Edge object based on the provided Edge Id. If the user has the authority of 'Tenant Administrator', the server checks that the edge is owned by the same tenant. If the user has the authority of 'Customer User', the server checks that the edge is assigned to the same customer.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", - "operationId": "getEdgeById", + "summary": "Get Device Profiles (getDeviceProfiles)", + "description": "Returns a page of devices profile objects owned by tenant. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "getDeviceProfiles", "parameters": [ { - "name": "edgeId", - "in": "path", - "description": "A string value representing the edge id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", + "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'substring' filter based on the device profile name.", + "required": false, "schema": { "type": "string" } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string", + "enum": [ + "createdTime", + "name", + "type", + "transportType", + "description", + "isDefault" + ] + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] + } } ], "responses": { @@ -39990,7 +39929,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/Edge" + "$ref": "#/components/schemas/PageDataDeviceProfile" } } } @@ -40109,28 +40048,50 @@ "ApiKeyForm": [] } ] - }, - "delete": { + } + }, + "/api/domain": { + "post": { "tags": [ - "edge-controller" + "domain-controller" ], - "summary": "Delete edge (deleteEdge)", - "description": "Deletes the edge. Referencing non-existing edge Id will cause an error.\n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "deleteEdge", + "summary": "Save or Update Domain (saveDomain)", + "description": "Create or update the Domain. When creating domain, platform generates Domain Id as [time-based UUID](https://en.wikipedia.org/wiki/Universally_unique_identifier#Version_1_(date-time_and_MAC_address)). The newly created Domain Id will be present in the response. Specify existing Domain Id to update the domain. Referencing non-existing Domain Id will cause 'Not Found' error.\n\nDomain name is unique for entire platform setup.\n\n\n\nAvailable for users with 'SYS_ADMIN' or 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", + "operationId": "saveDomain", "parameters": [ { - "name": "edgeId", - "in": "path", - "description": "A string value representing the edge id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": true, + "name": "oauth2ClientIds", + "in": "query", + "description": "A list of oauth2 client registration ids, separated by comma ','", + "required": false, "schema": { - "type": "string" + "type": "array", + "items": { + "type": "string" + } } } ], + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/Domain" + } + } + }, + "required": true + }, "responses": { "200": { - "description": "OK" + "description": "OK", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/Domain" + } + } + } }, "400": { "description": "Bad Request", @@ -40144,7 +40105,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -40248,22 +40209,22 @@ ] } }, - "/api/edge/{edgeId}/upgrade/available": { + "/api/domain/info/{id}": { "get": { "tags": [ - "edge-controller" + "domain-controller" ], - "summary": "Is edge upgrade enabled (isEdgeUpgradeAvailable)", - "description": "Returns 'true' if upgrade available for connected edge, 'false' - otherwise.", - "operationId": "isEdgeUpgradeAvailable", + "summary": "Get Domain info by Id (getDomainInfoById)", + "description": "\n\nAvailable for users with 'SYS_ADMIN' or 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", + "operationId": "getDomainInfoById", "parameters": [ { - "name": "edgeId", + "name": "id", "in": "path", - "description": "A string value representing the edge id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { - "type": "string" + "type": "string", + "format": "uuid" } } ], @@ -40273,7 +40234,7 @@ "content": { "application/json": { "schema": { - "type": "boolean" + "$ref": "#/components/schemas/DomainInfo" } } } @@ -40394,29 +40355,58 @@ ] } }, - "/api/edge/{edgeId}/{ruleChainId}/root": { - "post": { + "/api/domain/infos": { + "get": { "tags": [ - "edge-controller" + "domain-controller" ], - "summary": "Set root rule chain for provided edge (setEdgeRootRuleChain)", - "description": "Change root rule chain of the edge to the new provided rule chain. \nThis operation will send a notification to update root rule chain on remote edge service.\n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "setEdgeRootRuleChain", + "summary": "Get Domain infos (getDomainInfos)", + "description": "\n\nAvailable for users with 'SYS_ADMIN' or 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", + "operationId": "getDomainInfos", "parameters": [ { - "name": "edgeId", - "in": "path", - "description": "A string value representing the edge id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", "required": true, "schema": { - "type": "string" + "type": "integer", + "format": "int32" } }, { - "name": "ruleChainId", - "in": "path", - "description": "A string value representing the rule chain id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "textSearch", + "in": "query", + "description": "Case-insensitive 'substring' filter based on domain's name", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, "schema": { "type": "string" } @@ -40428,7 +40418,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/Edge" + "$ref": "#/components/schemas/PageDataDomainInfo" } } } @@ -40445,7 +40435,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -40549,102 +40539,28 @@ ] } }, - "/api/edgeInfos/all": { - "get": { + "/api/domain/{id}": { + "delete": { "tags": [ - "edge-controller" + "domain-controller" ], - "summary": "Get All Edge Infos for current user (getAllEdgeInfos)", - "description": "Returns a page of edge info objects owned by the tenant or the customer of a current user. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getAllEdgeInfos", + "summary": "Delete Domain by ID (deleteDomain)", + "description": "Deletes Domain by ID. Referencing non-existing domain Id will cause an error.\n\nAvailable for users with 'SYS_ADMIN' or 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", + "operationId": "deleteDomain", "parameters": [ { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", + "name": "id", + "in": "path", "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "includeCustomers", - "in": "query", - "description": "Include customer or sub-customer entities", - "required": false, - "schema": { - "type": "boolean" - } - }, - { - "name": "type", - "in": "query", - "description": "A string value representing the edge type. For example, 'default'", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'substring' filter based on the edge name.", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, "schema": { "type": "string", - "enum": [ - "createdTime", - "name", - "type", - "label", - "customerTitle" - ] - } - }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] + "format": "uuid" } } ], "responses": { "200": { - "description": "OK", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/PageDataEdgeInfo" - } - } - } + "description": "OK" }, "400": { "description": "Bad Request", @@ -40762,85 +40678,43 @@ ] } }, - "/api/edges": { - "get": { + "/api/domain/{id}/oauth2Clients": { + "put": { "tags": [ - "edge-controller" + "domain-controller" ], - "summary": "Get Tenant Edges (getEdges)", - "description": "Returns a page of edges owned by tenant. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "getEdges", + "summary": "Update oauth2 clients (updateDomainOauth2Clients)", + "description": "Update oauth2 clients for the specified domain. \n\nAvailable for users with 'SYS_ADMIN' or 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", + "operationId": "updateDomainOauth2Clients", "parameters": [ { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", + "name": "id", + "in": "path", "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'substring' filter based on the edge name.", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, - "schema": { - "type": "string", - "enum": [ - "createdTime", - "name", - "type", - "label", - "customerTitle" - ] - } - }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, "schema": { "type": "string", - "enum": [ - "ASC", - "DESC" - ] + "format": "uuid" } } ], - "responses": { - "200": { - "description": "OK", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/PageDataEdge" + "requestBody": { + "content": { + "application/json": { + "schema": { + "type": "array", + "items": { + "type": "string", + "format": "uuid" } } } }, + "required": true + }, + "responses": { + "200": { + "description": "OK" + }, "400": { "description": "Bad Request", "content": { @@ -40955,34 +40829,110 @@ "ApiKeyForm": [] } ] - }, - "post": { + } + }, + "/api/customer/{customerId}/edgeInfos": { + "get": { "tags": [ "edge-controller" ], - "summary": "Find related edges (findEdgesByQuery)", - "description": "Returns all edges that are related to the specific entity. The entity id, relation type, edge types, depth of the search, and other query parameters defined using complex 'EdgeSearchQuery' object. See 'Model' tab of the Parameters for more info.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", - "operationId": "findEdgesByQuery", - "requestBody": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/EdgeSearchQuery" - } + "summary": "Get Customer Edge Infos (getCustomerEdgeInfos)", + "description": "Returns a page of edge info objects owned by the specified customer. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getCustomerEdgeInfos", + "parameters": [ + { + "name": "customerId", + "in": "path", + "description": "A string value representing the customer id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, + "schema": { + "type": "string" } }, - "required": true - }, + { + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", + "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", + "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "includeCustomers", + "in": "query", + "description": "Include customer or sub-customer entities", + "required": false, + "schema": { + "type": "boolean" + } + }, + { + "name": "type", + "in": "query", + "description": "A string value representing the edge type. For example, 'default'", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'substring' filter based on the edge name.", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string", + "enum": [ + "createdTime", + "name", + "type", + "label", + "customerTitle" + ] + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] + } + } + ], "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "type": "array", - "items": { - "$ref": "#/components/schemas/Edge" - } + "$ref": "#/components/schemas/PageDataEdgeInfo" } } } @@ -40999,7 +40949,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -41103,21 +41053,99 @@ ] } }, - "/api/edges/enabled": { + "/api/customer/{customerId}/edges": { "get": { "tags": [ "edge-controller" ], - "summary": "Is edges support enabled (isEdgesSupportEnabled)", - "description": "Returns 'true' if edges support enabled on server, 'false' - otherwise.", - "operationId": "isEdgesSupportEnabled", + "summary": "Get Customer Edges (getCustomerEdges)", + "description": "Returns a page of edges objects assigned to customer. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", + "operationId": "getCustomerEdges", + "parameters": [ + { + "name": "customerId", + "in": "path", + "description": "A string value representing the customer id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, + "schema": { + "type": "string" + } + }, + { + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", + "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", + "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "type", + "in": "query", + "description": "A string value representing the edge type. For example, 'default'", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'substring' filter based on the edge name.", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string", + "enum": [ + "createdTime", + "name", + "type", + "label", + "customerTitle" + ] + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] + } + } + ], "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "type": "boolean" + "$ref": "#/components/schemas/PageDataEdge" } } } @@ -41238,20 +41266,28 @@ ] } }, - "/api/edges/list": { - "get": { + "/api/edge": { + "post": { "tags": [ "edge-controller" ], - "summary": "Get Edges By Ids (getEdgeList)", - "description": "Requested edges must be owned by tenant or assigned to customer which user is performing the request.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", - "operationId": "getEdgeList", + "summary": "Create Or Update Edge (saveEdge)", + "description": "Create or update the Edge. When creating edge, platform generates Edge Id as [time-based UUID](https://en.wikipedia.org/wiki/Universally_unique_identifier#Version_1_(date-time_and_MAC_address)). The newly created edge id will be present in the response. Specify existing Edge id to update the edge. Referencing non-existing Edge Id will cause 'Not Found' error.\n\nEdge name is unique in the scope of tenant. Use unique identifiers like MAC or IMEI for the edge names and non-unique 'label' field for user-friendly visualization purposes.Remove 'id', 'tenantId' and optionally 'customerId' from the request body example (below) to create new Edge entity. ", + "operationId": "saveEdge", "parameters": [ { - "name": "edgeIds", + "name": "entityGroupId", "in": "query", - "description": "A list of edges ids, separated by comma ','", - "required": true, + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "entityGroupIds", + "in": "query", + "description": "A list of entity group ids, separated by comma ','", + "required": false, "schema": { "type": "array", "items": { @@ -41260,16 +41296,23 @@ } } ], + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/Edge" + } + } + }, + "required": true + }, "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "type": "array", - "items": { - "$ref": "#/components/schemas/Edge" - } + "$ref": "#/components/schemas/Edge" } } } @@ -41286,7 +41329,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -41390,90 +41433,31 @@ ] } }, - "/api/entityGroup/{entityGroupId}/edges": { - "get": { + "/api/edge/bulk_import": { + "post": { "tags": [ "edge-controller" ], - "summary": "Get edges by Entity Group Id (getEdgesByEntityGroupId)", - "description": "Returns a page of Edge objects that belongs to specified Entity Group Id. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", - "operationId": "getEdgesByEntityGroupId", - "parameters": [ - { - "name": "entityGroupId", - "in": "path", - "description": "A string value representing the Entity Group Id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": true, - "schema": { - "type": "string" - } - }, - { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "string", - "minimum": 1 - } - }, - { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", - "required": true, - "schema": { - "type": "string", - "minimum": 1 - } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'substring' filter based on the edge name.", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, - "schema": { - "type": "string", - "enum": [ - "createdTime", - "name", - "type", - "label", - "customerTitle" - ] + "summary": "Import the bulk of edges (processEdgesBulkImport)", + "description": "There's an ability to import the bulk of edges using the only .csv file.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", + "operationId": "processEdgesBulkImport", + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/BulkImportRequest" + } } }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] - } - } - ], + "required": true + }, "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataEdge" + "$ref": "#/components/schemas/BulkImportResultEdge" } } } @@ -41490,7 +41474,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -41594,26 +41578,19 @@ ] } }, - "/api/license/activateInstance": { - "post": { + "/api/edge/info/{edgeId}": { + "get": { "tags": [ "edge-controller" ], - "summary": "Activate edge instance (activateInstance)", - "description": "Activates edge license on license portal.", - "operationId": "activateInstance", + "summary": "Get Edge Info (getEdgeInfoById)", + "description": "Get the Edge info object based on the provided Edge Id. If the user has the authority of 'Tenant Administrator', the server checks that the edge is owned by the same tenant. If the user has the authority of 'Customer User', the server checks that the edge is assigned to the same customer.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", + "operationId": "getEdgeInfoById", "parameters": [ { - "name": "licenseSecret", - "in": "query", - "required": true, - "schema": { - "type": "string" - } - }, - { - "name": "releaseDate", - "in": "query", + "name": "edgeId", + "in": "path", + "description": "A string value representing the edge id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { "type": "string" @@ -41626,7 +41603,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/JsonNode" + "$ref": "#/components/schemas/EdgeInfo" } } } @@ -41643,7 +41620,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -41747,31 +41724,46 @@ ] } }, - "/api/license/checkInstance": { - "post": { + "/api/edge/instructions/install/{edgeId}/{method}": { + "get": { "tags": [ "edge-controller" ], - "summary": "Check edge license (checkInstance)", - "description": "Checks license request from edge service by forwarding request to license portal.", - "operationId": "checkInstance", - "requestBody": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/JsonNode" - } + "summary": "Get Edge Install Instructions (getEdgeInstallInstructions)", + "description": "Get an install instructions for provided edge id.If the user has the authority of 'Tenant Administrator', the server checks that the edge is owned by the same tenant. If the user has the authority of 'Customer User', the server checks that the edge is assigned to the same customer.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", + "operationId": "getEdgeInstallInstructions", + "parameters": [ + { + "name": "edgeId", + "in": "path", + "description": "A string value representing the edge id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, + "schema": { + "type": "string" } }, - "required": true - }, + { + "name": "method", + "in": "path", + "description": "Installation method ('docker', 'ubuntu' or 'centos')", + "required": true, + "schema": { + "type": "string", + "enum": [ + "docker", + "ubuntu", + "centos" + ] + } + } + ], "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/JsonNode" + "$ref": "#/components/schemas/EdgeInstructions" } } } @@ -41788,7 +41780,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -41892,23 +41884,37 @@ ] } }, - "/api/tenant/edge": { + "/api/edge/instructions/upgrade/{edgeVersion}/{method}": { "get": { "tags": [ "edge-controller" ], - "summary": "Get Tenant Edge by name (getTenantEdgeByName)", - "description": "Requested edge must be owned by tenant or customer that the user belongs to. Edge name is an unique property of edge. So it can be used to identify the edge.\n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "getTenantEdgeByName", + "summary": "Get Edge Upgrade Instructions (getEdgeUpgradeInstructions)", + "description": "Get an upgrade instructions for provided edge version.If the user has the authority of 'Tenant Administrator', the server checks that the edge is owned by the same tenant. If the user has the authority of 'Customer User', the server checks that the edge is assigned to the same customer.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", + "operationId": "getEdgeUpgradeInstructions", "parameters": [ { - "name": "edgeName", - "in": "query", - "description": "Unique name of the edge", + "name": "edgeVersion", + "in": "path", + "description": "Edge version", "required": true, "schema": { "type": "string" } + }, + { + "name": "method", + "in": "path", + "description": "Upgrade method ('docker', 'ubuntu' or 'centos')", + "required": true, + "schema": { + "type": "string", + "enum": [ + "docker", + "ubuntu", + "centos" + ] + } } ], "responses": { @@ -41917,7 +41923,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/Edge" + "$ref": "#/components/schemas/EdgeInstructions" } } } @@ -42038,81 +42044,23 @@ ] } }, - "/api/tenant/edges": { + "/api/edge/missingToRelatedRuleChains/{edgeId}": { "get": { "tags": [ "edge-controller" ], - "summary": "Get Tenant Edges (getTenantEdges)", - "description": "Returns a page of edges owned by tenant. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "getTenantEdges", + "summary": "Find missing rule chains (findMissingToRelatedRuleChains)", + "description": "Returns list of rule chains ids that are not assigned to particular edge, but these rule chains are present in the already assigned rule chains to edge.\n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "findMissingToRelatedRuleChains", "parameters": [ { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", + "name": "edgeId", + "in": "path", + "description": "A string value representing the edge id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "type", - "in": "query", - "description": "A string value representing the edge type. For example, 'default'", - "required": false, "schema": { "type": "string" } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'substring' filter based on the edge name.", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, - "schema": { - "type": "string", - "enum": [ - "createdTime", - "name", - "type", - "label", - "customerTitle" - ] - } - }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] - } } ], "responses": { @@ -42121,7 +42069,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataEdge" + "type": "string" } } } @@ -42242,81 +42190,23 @@ ] } }, - "/api/user/edges": { - "get": { + "/api/edge/sync/{edgeId}": { + "post": { "tags": [ "edge-controller" ], - "summary": "Get Edges (getUserEdges)", - "description": "Returns a page of edges available for current user. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getUserEdges", + "summary": "Sync edge (syncEdge)", + "description": "Starts synchronization process between edge and cloud. \nAll entities that are assigned to particular edge are going to be send to remote edge service.\n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "syncEdge", "parameters": [ { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "string", - "minimum": 1 - } - }, - { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", + "name": "edgeId", + "in": "path", + "description": "A string value representing the edge id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, - "schema": { - "type": "string", - "minimum": 0 - } - }, - { - "name": "type", - "in": "query", - "description": "A string value representing the edge type. For example, 'default'", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'substring' filter based on the edge name.", - "required": false, "schema": { "type": "string" } - }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, - "schema": { - "type": "string", - "enum": [ - "createdTime", - "name", - "type", - "label", - "customerTitle" - ] - } - }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] - } } ], "responses": { @@ -42325,7 +42215,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataEdge" + "type": "string" } } } @@ -42342,7 +42232,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -42446,110 +42336,24 @@ ] } }, - "/api/edge/{edgeId}/events": { + "/api/edge/types": { "get": { "tags": [ - "edge-event-controller" - ], - "summary": "Get Edge Events (getEdgeEvents)", - "description": "Returns a page of edge events for the requested edge. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. ", - "operationId": "getEdgeEvents", - "parameters": [ - { - "name": "edgeId", - "in": "path", - "description": "A string value representing the edge id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": true, - "schema": { - "type": "string" - } - }, - { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", - "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'substring' filter based on the edge event type name.", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, - "schema": { - "type": "string", - "enum": [ - "createdTime", - "name", - "type", - "label", - "customerTitle" - ] - } - }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] - } - }, - { - "name": "startTime", - "in": "query", - "description": "Timestamp. Edge events with creation time before it won't be queried", - "required": false, - "schema": { - "type": "integer", - "format": "int64" - } - }, - { - "name": "endTime", - "in": "query", - "description": "Timestamp. Edge events with creation time after it won't be queried", - "required": false, - "schema": { - "type": "integer", - "format": "int64" - } - } + "edge-controller" ], + "summary": "Get Edge Types (getEdgeTypes)", + "description": "Returns a set of unique edge types based on edges that are either owned by the tenant or assigned to the customer which user is performing the request.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", + "operationId": "getEdgeTypes", "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataEdgeEvent" + "type": "array", + "items": { + "$ref": "#/components/schemas/EntitySubtype" + } } } } @@ -42670,176 +42474,19 @@ ] } }, - "/api/entities/vc/branches": { - "get": { - "tags": [ - "entities-version-control-controller" - ], - "summary": "List branches (listBranches)", - "description": "Lists branches available in the remote repository. \n\nResponse example: \n```json\n[\n {\n \"name\": \"master\",\n \"default\": true\n },\n {\n \"name\": \"dev\",\n \"default\": false\n },\n {\n \"name\": \"dev-2\",\n \"default\": false\n }\n]\n```", - "operationId": "listBranches", - "responses": { - "200": { - "description": "OK", - "content": { - "application/json": { - "schema": { - "type": "array", - "items": { - "$ref": "#/components/schemas/BranchInfo" - } - } - } - } - }, - "400": { - "description": "Bad Request", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ThingsboardErrorResponse" - }, - "examples": { - "error-code-400": { - "summary": "Bad Request", - "value": { - "status": 400, - "message": "Invalid UUID string: 123", - "errorCode": 31, - "timestamp": 1609459200000 - } - } - } - } - } - }, - "401": { - "description": "Unauthorized", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ThingsboardErrorResponse" - }, - "examples": { - "error-code-401": { - "summary": "Unauthorized", - "value": { - "status": 401, - "message": "Authentication failed", - "errorCode": 10, - "timestamp": 1609459200000 - } - } - } - } - } - }, - "403": { - "description": "Forbidden", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ThingsboardErrorResponse" - }, - "examples": { - "error-code-403": { - "summary": "Forbidden", - "value": { - "status": 403, - "message": "You don't have permission to perform this operation!", - "errorCode": 20, - "timestamp": 1609459200000 - } - } - } - } - } - }, - "404": { - "description": "Not Found", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ThingsboardErrorResponse" - }, - "examples": { - "error-code-404": { - "summary": "Not Found", - "value": { - "status": 404, - "message": "Requested item wasn't found!", - "errorCode": 32, - "timestamp": 1609459200000 - } - } - } - } - } - }, - "429": { - "description": "Too Many Requests", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ThingsboardErrorResponse" - }, - "examples": { - "error-code-429": { - "summary": "Too Many Requests", - "value": { - "status": 429, - "message": "Too many requests for current tenant!", - "errorCode": 33, - "timestamp": 1609459200000 - } - } - } - } - } - } - }, - "security": [ - { - "HttpLoginForm": [] - }, - { - "ApiKeyForm": [] - } - ] - } - }, - "/api/entities/vc/diff/{entityType}/{internalEntityUuid}": { + "/api/edge/{edgeId}": { "get": { "tags": [ - "entities-version-control-controller" + "edge-controller" ], - "summary": "Compare entity data to version (compareEntityDataToVersion)", - "description": "Returns an object with current entity data and the one at a specific version. Entity data structure is the same as stored in a repository. \n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "compareEntityDataToVersion", + "summary": "Get Edge (getEdgeById)", + "description": "Get the Edge object based on the provided Edge Id. If the user has the authority of 'Tenant Administrator', the server checks that the edge is owned by the same tenant. If the user has the authority of 'Customer User', the server checks that the edge is assigned to the same customer.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", + "operationId": "getEdgeById", "parameters": [ { - "name": "entityType", - "in": "path", - "description": "A string value representing the entity type. For example, 'DEVICE'", - "required": true, - "schema": { - "$ref": "#/components/schemas/EntityType" - } - }, - { - "name": "internalEntityUuid", + "name": "edgeId", "in": "path", - "description": "A string value representing the entity id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": true, - "schema": { - "type": "string", - "format": "uuid" - } - }, - { - "name": "versionId", - "in": "query", - "description": "Version id, for example fd82625bdd7d6131cf8027b44ee967012ecaf990. Represents commit hash.", + "description": "A string value representing the edge id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { "type": "string" @@ -42852,7 +42499,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/EntityDataDiff" + "$ref": "#/components/schemas/Edge" } } } @@ -42971,37 +42618,28 @@ "ApiKeyForm": [] } ] - } - }, - "/api/entities/vc/entity": { - "post": { + }, + "delete": { "tags": [ - "entities-version-control-controller" + "edge-controller" ], - "summary": "Load entities version (loadEntitiesVersion)", - "description": "Loads specific version of remote entities (or single entity) by request. Supported entity types: CUSTOMER, ASSET, RULE_CHAIN, DASHBOARD, DEVICE_PROFILE, DEVICE, ENTITY_VIEW, WIDGETS_BUNDLE, CONVERTER, INTEGRATION, ROLE and USER group.\n\nThere are multiple types of request. Each of them requires branch name (`branch`) and version id (`versionId`). Request of type `SINGLE_ENTITY` is needed to restore a concrete version of a specific entity. It contains id of a remote entity (`externalEntityId`), internal entity id (`internalEntityId`) and additional configuration (`config`):\n- `loadRelations` - to update relations list (in case `saveRelations` option was enabled during version creation);\n- `loadAttributes` - to load entity attributes (if `saveAttributes` config option was enabled);\n- `loadCredentials` - to update device credentials (if `saveCredentials` option was enabled during version creation);\n- `loadPermissions` - when loading user group, to update group permission list;\n- `loadGroupEntities` - when loading an entity group, to load its entities as well;\n- `autoGenerateIntegrationKey` - if loading integration version, to autogenerate routing key.\n\nAn example of such request:\n```json\n{\n \"type\": \"SINGLE_ENTITY\",\n \n \"branch\": \"dev\",\n \"versionId\": \"b3c28d722d328324c7c15b0b30047b0c40011cf7\",\n \n \"externalEntityId\": {\n \"entityType\": \"DEVICE\",\n \"id\": \"b7944123-d4f4-11ec-847b-0f432358ab48\"\n },\n \"config\": {\n \"loadRelations\": false,\n \"loadAttributes\": true,\n \"loadCredentials\": true\n }\n}\n```\n\nAnother request type (`ENTITY_TYPE`) is needed to load specific version of the whole entity types. It contains a structure with entity types to load and configs for each entity type (`entityTypes`). For each specified entity type, the method will load all remote entities of this type that are present at the version. A config for each entity type contains the same options as in `SINGLE_ENTITY` request type, and additionally contains following options:\n- `removeOtherEntities` - to remove local entities that are not present on the remote - basically to overwrite local entity type with the remote one;\n- `findExistingEntityByName` - when you are loading some remote entities that are not yet present at this tenant, try to find existing entity by name and update it rather than create new.\n\nHere is an example of the request to completely restore version of the whole device entity type:\n```json\n{\n \"type\": \"ENTITY_TYPE\",\n\n \"branch\": \"dev\",\n \"versionId\": \"b3c28d722d328324c7c15b0b30047b0c40011cf7\",\n\n \"entityTypes\": {\n \"DEVICE\": {\n \"removeOtherEntities\": true,\n \"findExistingEntityByName\": false,\n \"loadRelations\": true,\n \"loadAttributes\": true,\n \"loadCredentials\": true\n }\n }\n}\n```\n\nThe response will contain generated request UUID that is to be used to check the status of operation via `getVersionLoadRequestStatus`.\n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "loadEntitiesVersion", - "requestBody": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/VersionLoadRequest" - } + "summary": "Delete edge (deleteEdge)", + "description": "Deletes the edge. Referencing non-existing edge Id will cause an error.\n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "deleteEdge", + "parameters": [ + { + "name": "edgeId", + "in": "path", + "description": "A string value representing the edge id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, + "schema": { + "type": "string" } - }, - "required": true - }, + } + ], "responses": { "200": { - "description": "OK", - "content": { - "application/json": { - "schema": { - "type": "string", - "format": "uuid" - } - } - } + "description": "OK" }, "400": { "description": "Bad Request", @@ -43015,7 +42653,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -43119,28 +42757,19 @@ ] } }, - "/api/entities/vc/entity/{entityType}/{versionId}": { + "/api/edge/{edgeId}/upgrade/available": { "get": { "tags": [ - "entities-version-control-controller" + "edge-controller" ], - "summary": "List entities at version (listEntitiesAtVersion)", - "description": "Returns a list of remote entities of a specific entity type that are available at a concrete version. \nEach entity item in the result has `externalId` property. Entities order will be the same as in the repository.\n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "listEntitiesAtVersion", + "summary": "Is edge upgrade enabled (isEdgeUpgradeAvailable)", + "description": "Returns 'true' if upgrade available for connected edge, 'false' - otherwise.", + "operationId": "isEdgeUpgradeAvailable", "parameters": [ { - "name": "entityType", - "in": "path", - "description": "A string value representing the entity type. For example, 'DEVICE'", - "required": true, - "schema": { - "$ref": "#/components/schemas/EntityType" - } - }, - { - "name": "versionId", + "name": "edgeId", "in": "path", - "description": "Version id, for example fd82625bdd7d6131cf8027b44ee967012ecaf990. Represents commit hash.", + "description": "A string value representing the edge id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { "type": "string" @@ -43153,10 +42782,7 @@ "content": { "application/json": { "schema": { - "type": "array", - "items": { - "$ref": "#/components/schemas/VersionedEntityInfo" - } + "type": "boolean" } } } @@ -43277,23 +42903,31 @@ ] } }, - "/api/entities/vc/entity/{requestId}/status": { - "get": { + "/api/edge/{edgeId}/{ruleChainId}/root": { + "post": { "tags": [ - "entities-version-control-controller" + "edge-controller" ], - "summary": "Get version load request status (getVersionLoadRequestStatus)", - "description": "Returns the status of previously made version load request. The structure contains following parameters:\n- `done` - if the request was successfully processed;\n- `result` - a list of load results for each entity type:\n - `created` - created entities count;\n - `updated` - updated entities count;\n - `deleted` - removed entities count;\n - `groupsCreated` - created entity groups count;\n - `groupsUpdated` - updated entity groups count;\n - `groupsDeleted` - removed entity groups count.\n- `error` - if an error occurred during processing, error info:\n - `type` - error type;\n - `source` - an external id of remote entity;\n - `target` - if failed to find referenced entity by external id - this external id;\n - `message` - error message.\n\nAn example of successfully processed request status:\n```json\n{\n \"done\": true,\n \"result\": [\n {\n \"entityType\": \"DEVICE\",\n \"created\": 10,\n \"updated\": 5,\n \"deleted\": 5,\n \"groupsCreated\": 1,\n \"groupsUpdated\": 1,\n \"groupsDeleted\": 1\n },\n {\n \"entityType\": \"ASSET\",\n \"created\": 4,\n \"updated\": 0,\n \"deleted\": 8,\n \"groupsCreated\": 1,\n \"groupsUpdated\": 0,\n \"groupsDeleted\": 2\n }\n ]\n}\n```\n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "getVersionLoadRequestStatus", + "summary": "Set root rule chain for provided edge (setEdgeRootRuleChain)", + "description": "Change root rule chain of the edge to the new provided rule chain. \nThis operation will send a notification to update root rule chain on remote edge service.\n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "setEdgeRootRuleChain", "parameters": [ { - "name": "requestId", + "name": "edgeId", "in": "path", - "description": "A string value representing the version control request id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "description": "A string value representing the edge id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { - "type": "string", - "format": "uuid" + "type": "string" + } + }, + { + "name": "ruleChainId", + "in": "path", + "description": "A string value representing the rule chain id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, + "schema": { + "type": "string" } } ], @@ -43303,7 +42937,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/VersionLoadResult" + "$ref": "#/components/schemas/Edge" } } } @@ -43320,7 +42954,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -43424,200 +43058,89 @@ ] } }, - "/api/entities/vc/entity/{versionId}": { + "/api/edgeInfos/all": { "get": { "tags": [ - "entities-version-control-controller" + "edge-controller" ], - "summary": "List all entities at version (listAllEntitiesAtVersion)", - "description": "Returns a list of all remote entities available in a specific version. Response type is the same as for listAllEntitiesAtVersion API method. \nReturned entities order will be the same as in the repository.\n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "listAllEntitiesAtVersion", + "summary": "Get All Edge Infos for current user (getAllEdgeInfos)", + "description": "Returns a page of edge info objects owned by the tenant or the customer of a current user. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getAllEdgeInfos", "parameters": [ { - "name": "versionId", - "in": "path", - "description": "Version id, for example fd82625bdd7d6131cf8027b44ee967012ecaf990. Represents commit hash.", + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", "required": true, "schema": { - "type": "string" - } - } - ], - "responses": { - "200": { - "description": "OK", - "content": { - "application/json": { - "schema": { - "type": "array", - "items": { - "$ref": "#/components/schemas/VersionedEntityInfo" - } - } - } - } - }, - "400": { - "description": "Bad Request", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ThingsboardErrorResponse" - }, - "examples": { - "error-code-400": { - "summary": "Bad Request", - "value": { - "status": 400, - "message": "Invalid UUID string: 123", - "errorCode": 31, - "timestamp": 1609459200000 - } - } - } - } - } - }, - "401": { - "description": "Unauthorized", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ThingsboardErrorResponse" - }, - "examples": { - "error-code-401": { - "summary": "Unauthorized", - "value": { - "status": 401, - "message": "Authentication failed", - "errorCode": 10, - "timestamp": 1609459200000 - } - } - } - } - } - }, - "403": { - "description": "Forbidden", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ThingsboardErrorResponse" - }, - "examples": { - "error-code-403": { - "summary": "Forbidden", - "value": { - "status": 403, - "message": "You don't have permission to perform this operation!", - "errorCode": 20, - "timestamp": 1609459200000 - } - } - } - } + "type": "integer", + "format": "int32" } }, - "404": { - "description": "Not Found", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ThingsboardErrorResponse" - }, - "examples": { - "error-code-404": { - "summary": "Not Found", - "value": { - "status": 404, - "message": "Requested item wasn't found!", - "errorCode": 32, - "timestamp": 1609459200000 - } - } - } - } + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", + "required": true, + "schema": { + "type": "integer", + "format": "int32" } }, - "429": { - "description": "Too Many Requests", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ThingsboardErrorResponse" - }, - "examples": { - "error-code-429": { - "summary": "Too Many Requests", - "value": { - "status": 429, - "message": "Too many requests for current tenant!", - "errorCode": 33, - "timestamp": 1609459200000 - } - } - } - } - } - } - }, - "security": [ { - "HttpLoginForm": [] + "name": "includeCustomers", + "in": "query", + "description": "Include customer or sub-customer entities", + "required": false, + "schema": { + "type": "boolean" + } }, { - "ApiKeyForm": [] - } - ] - } - }, - "/api/entities/vc/info/{versionId}/{entityType}/{externalEntityUuid}": { - "get": { - "tags": [ - "entities-version-control-controller" - ], - "summary": "Get entity data info (getEntityDataInfo)", - "description": "Retrieves short info about the remote entity by external id at a concrete version. \nReturned entity data info contains following properties: `hasRelations` (whether stored entity data contains relations), `hasAttributes` (contains attributes), `hasCredentials` (whether stored device data has credentials), `hasPermissions` (user group data contains group permission list) and `hasGroupEntities` (entity group data contains group entities).\n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "getEntityDataInfo", - "parameters": [ - { - "name": "versionId", - "in": "path", - "description": "Version id, for example fd82625bdd7d6131cf8027b44ee967012ecaf990. Represents commit hash.", - "required": true, + "name": "type", + "in": "query", + "description": "A string value representing the edge type. For example, 'default'", + "required": false, "schema": { "type": "string" } }, { - "name": "entityType", - "in": "path", - "description": "A string value representing the entity type. For example, 'DEVICE'", - "required": true, + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'substring' filter based on the edge name.", + "required": false, "schema": { - "$ref": "#/components/schemas/EntityType" + "type": "string" } }, { - "name": "externalEntityUuid", - "in": "path", - "description": "A string value representing external entity id", - "required": true, + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, "schema": { "type": "string", - "format": "uuid" + "enum": [ + "createdTime", + "name", + "type", + "label", + "customerTitle" + ] } }, { - "name": "internalEntityId", + "name": "sortOrder", "in": "query", - "description": "A string value representing the entity id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", "required": false, "schema": { "type": "string", - "format": "uuid" + "enum": [ + "ASC", + "DESC" + ] } } ], @@ -43627,7 +43150,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/EntityDataInfo" + "$ref": "#/components/schemas/PageDataEdgeInfo" } } } @@ -43748,24 +43271,15 @@ ] } }, - "/api/entities/vc/version": { + "/api/edges": { "get": { "tags": [ - "entities-version-control-controller" + "edge-controller" ], - "summary": "List all versions (listVersions)", - "description": "Lists all available versions in a branch for all entity types. \nIf specified branch does not exist - empty page data will be returned. The response format is the same as for `listEntityVersions` API method.\n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "listVersions", + "summary": "Get Tenant Edges (getEdges)", + "description": "Returns a page of edges owned by tenant. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "getEdges", "parameters": [ - { - "name": "branch", - "in": "query", - "description": "The name of the working branch, for example 'master'", - "required": true, - "schema": { - "type": "string" - } - }, { "name": "pageSize", "in": "query", @@ -43789,7 +43303,7 @@ { "name": "textSearch", "in": "query", - "description": "The case insensitive 'substring' filter based on the entity version name.", + "description": "The case insensitive 'substring' filter based on the edge name.", "required": false, "schema": { "type": "string" @@ -43803,7 +43317,11 @@ "schema": { "type": "string", "enum": [ - "timestamp" + "createdTime", + "name", + "type", + "label", + "customerTitle" ] } }, @@ -43827,7 +43345,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataEntityVersion" + "$ref": "#/components/schemas/PageDataEdge" } } } @@ -43949,16 +43467,16 @@ }, "post": { "tags": [ - "entities-version-control-controller" + "edge-controller" ], - "summary": "Save entities version (saveEntitiesVersion)", - "description": "Creates a new version of entities (or a single entity) by request.\nSupported entity types: CUSTOMER, ASSET, RULE_CHAIN, DASHBOARD, DEVICE_PROFILE, DEVICE, ENTITY_VIEW, WIDGETS_BUNDLE, CONVERTER, INTEGRATION, ROLE and USER group.\n\nThere are two available types of request: `SINGLE_ENTITY` and `COMPLEX`. Each of them contains version name (`versionName`) and name of a branch (`branch`) to create version (commit) in. If specified branch does not exists in a remote repo, then new empty branch will be created. Request of the `SINGLE_ENTITY` type has id of an entity (`entityId`) and additional configuration (`config`) which has following options: \n- `saveRelations` - whether to add inbound and outbound relations of type COMMON to created entity version;\n- `saveAttributes` - to save attributes of server scope (and also shared scope for devices);\n- `saveCredentials` - when saving a version of a device, to add its credentials to the version;\n- `savePermissions` - when saving a user group - to save group permission list;\n- `saveGroupEntities` - when saving an entity group - to save its entities as well.\n\nAn example of a `SINGLE_ENTITY` version create request:\n```json\n{\n \"type\": \"SINGLE_ENTITY\",\n\n \"versionName\": \"Version 1.0\",\n \"branch\": \"dev\",\n\n \"entityId\": {\n \"entityType\": \"DEVICE\",\n \"id\": \"b79448e0-d4f4-11ec-847b-0f432358ab48\"\n },\n \"config\": {\n \"saveRelations\": true,\n \"saveAttributes\": true,\n \"saveCredentials\": false\n }\n}\n```\n\nSecond request type (`COMPLEX`), additionally to `branch` and `versionName`, contains following properties:\n- `entityTypes` - a structure with entity types to export and configuration for each entity type; this configuration has all the options available for `SINGLE_ENTITY` and additionally has these ones: \n - `allEntities` and `entityIds` - if you want to save the version of all entities of the entity type then set `allEntities` param to true, otherwise set it to false and specify `entityIds` - in case entity type is group entity, list of specific entity groups, or if not - list of entities;\n - `syncStrategy` - synchronization strategy to use for this entity type: when set to `OVERWRITE` then the list of remote entities of this type will be overwritten by newly added entities. If set to `MERGE` - existing remote entities of this entity type will not be removed, new entities will just be added on top (or existing remote entities will be updated).\n- `syncStrategy` - default synchronization strategy to use when it is not specified for an entity type.\n\nExample for this type of request:\n```json\n{\n \"type\": \"COMPLEX\",\n\n \"versionName\": \"Devices and profiles: release 2\",\n \"branch\": \"master\",\n\n \"syncStrategy\": \"OVERWRITE\",\n \"entityTypes\": {\n \"DEVICE\": {\n \"syncStrategy\": null,\n \"allEntities\": true,\n \"saveRelations\": true,\n \"saveAttributes\": true,\n \"saveCredentials\": true\n },\n \"DEVICE_PROFILE\": {\n \"syncStrategy\": \"MERGE\",\n \"allEntities\": false,\n \"entityIds\": [\n \"b79448e0-d4f4-11ec-847b-0f432358ab48\"\n ],\n \"saveRelations\": true\n }\n }\n}\n```\n\nResponse wil contain generated request UUID, that can be then used to retrieve status of operation via `getVersionCreateRequestStatus`.\n\n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "saveEntitiesVersion", + "summary": "Find related edges (findEdgesByQuery)", + "description": "Returns all edges that are related to the specific entity. The entity id, relation type, edge types, depth of the search, and other query parameters defined using complex 'EdgeSearchQuery' object. See 'Model' tab of the Parameters for more info.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", + "operationId": "findEdgesByQuery", "requestBody": { "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/VersionCreateRequest" + "$ref": "#/components/schemas/EdgeSearchQuery" } } }, @@ -43970,8 +43488,10 @@ "content": { "application/json": { "schema": { - "type": "string", - "format": "uuid" + "type": "array", + "items": { + "$ref": "#/components/schemas/Edge" + } } } } @@ -44092,95 +43612,21 @@ ] } }, - "/api/entities/vc/version/{entityType}": { + "/api/edges/enabled": { "get": { "tags": [ - "entities-version-control-controller" - ], - "summary": "List entity type versions (listEntityTypeVersions)", - "description": "Returns list of versions of an entity type in a branch. This is a collected list of versions that were created for entities of this type in a remote branch. \nIf specified branch does not exist - empty page data will be returned. The response structure is the same as for `listEntityVersions` API method.\n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "listEntityTypeVersions", - "parameters": [ - { - "name": "entityType", - "in": "path", - "description": "A string value representing the entity type. For example, 'DEVICE'", - "required": true, - "schema": { - "$ref": "#/components/schemas/EntityType" - } - }, - { - "name": "branch", - "in": "query", - "description": "The name of the working branch, for example 'master'", - "required": true, - "schema": { - "type": "string" - } - }, - { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", - "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'substring' filter based on the entity version name.", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, - "schema": { - "type": "string", - "enum": [ - "timestamp" - ] - } - }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] - } - } + "edge-controller" ], + "summary": "Is edges support enabled (isEdgesSupportEnabled)", + "description": "Returns 'true' if edges support enabled on server, 'false' - otherwise.", + "operationId": "isEdgesSupportEnabled", "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataEntityVersion" + "type": "boolean" } } } @@ -44301,104 +43747,25 @@ ] } }, - "/api/entities/vc/version/{entityType}/{externalEntityUuid}": { + "/api/edges/list": { "get": { "tags": [ - "entities-version-control-controller" + "edge-controller" ], - "summary": "List entity versions (listEntityVersions)", - "description": "Returns list of versions for a specific entity in a concrete branch. \nYou need to specify external id of an entity to list versions for. This is `externalId` property of an entity, or otherwise if not set - simply id of this entity. \nIf specified branch does not exist - empty page data will be returned. \n\nEach version info item has timestamp, id, name and author. Version id can then be used to restore the version. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nResponse example: \n```json\n{\n \"data\": [\n {\n \"timestamp\": 1655198593000,\n \"id\": \"fd82625bdd7d6131cf8027b44ee967012ecaf990\",\n \"name\": \"Devices and assets - v2.0\",\n \"author\": \"John Doe (johndoe@gmail.com)\"\n },\n {\n \"timestamp\": 1655198528000,\n \"id\": \"682adcffa9c8a2f863af6f00c4850323acbd4219\",\n \"name\": \"Update my device\",\n \"author\": \"John Doe (johndoe@gmail.com)\"\n },\n {\n \"timestamp\": 1655198280000,\n \"id\": \"d2a6087c2b30e18cc55e7cdda345a8d0dfb959a4\",\n \"name\": \"Devices and assets - v1.0\",\n \"author\": \"John Doe (johndoe@gmail.com)\"\n }\n ],\n \"totalPages\": 1,\n \"totalElements\": 3,\n \"hasNext\": false\n}\n```\n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "listEntityVersions", + "summary": "Get Edges By Ids (getEdgeList)", + "description": "Requested edges must be owned by tenant or assigned to customer which user is performing the request.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority.", + "operationId": "getEdgeList", "parameters": [ { - "name": "entityType", - "in": "path", - "description": "A string value representing the entity type. For example, 'DEVICE'", - "required": true, - "schema": { - "$ref": "#/components/schemas/EntityType" - } - }, - { - "name": "externalEntityUuid", - "in": "path", - "description": "A string value representing external entity id. This is `externalId` property of an entity, or otherwise if not set - simply id of this entity.", - "required": true, - "schema": { - "type": "string", - "format": "uuid" - } - }, - { - "name": "branch", - "in": "query", - "description": "The name of the working branch, for example 'master'", - "required": true, - "schema": { - "type": "string" - } - }, - { - "name": "internalEntityId", - "in": "query", - "required": false, - "schema": { - "type": "string", - "format": "uuid" - } - }, - { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "page", + "name": "edgeIds", "in": "query", - "description": "Sequence number of page starting from 0", + "description": "A list of edges ids, separated by comma ','", "required": true, "schema": { - "type": "integer", - "format": "int32" - } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'substring' filter based on the entity version name.", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, - "schema": { - "type": "string", - "enum": [ - "timestamp" - ] - } - }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] + "type": "array", + "items": { + "type": "string" + } } } ], @@ -44408,7 +43775,10 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataEntityVersion" + "type": "array", + "items": { + "$ref": "#/components/schemas/Edge" + } } } } @@ -44529,23 +43899,80 @@ ] } }, - "/api/entities/vc/version/{requestId}/status": { + "/api/entityGroup/{entityGroupId}/edges": { "get": { "tags": [ - "entities-version-control-controller" + "edge-controller" ], - "summary": "Get version create request status (getVersionCreateRequestStatus)", - "description": "Returns the status of previously made version create request. \n\nThis status contains following properties:\n- `done` - whether request processing is finished;\n- `version` - created version info: timestamp, version id (commit hash), commit name and commit author;\n- `added` - count of items that were created in the remote repo;\n- `modified` - modified items count;\n- `removed` - removed items count;\n- `error` - error message, if an error occurred while handling the request.\n\nAn example of successful status:\n```json\n{\n \"done\": true,\n \"added\": 10,\n \"modified\": 2,\n \"removed\": 5,\n \"version\": {\n \"timestamp\": 1655198528000,\n \"id\":\"8a834dd389ed80e0759ba8ee338b3f1fd160a114\",\n \"name\": \"My devices v2.0\",\n \"author\": \"John Doe\"\n },\n \"error\": null\n}\n```\n\nAvailable for users with 'TENANT_ADMIN' authority.", - "operationId": "getVersionCreateRequestStatus", + "summary": "Get edges by Entity Group Id (getEdgesByEntityGroupId)", + "description": "Returns a page of Edge objects that belongs to specified Entity Group Id. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", + "operationId": "getEdgesByEntityGroupId", "parameters": [ { - "name": "requestId", + "name": "entityGroupId", "in": "path", - "description": "A string value representing the version control request id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "description": "A string value representing the Entity Group Id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, + "schema": { + "type": "string" + } + }, + { + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", "required": true, "schema": { "type": "string", - "format": "uuid" + "minimum": 1 + } + }, + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", + "required": true, + "schema": { + "type": "string", + "minimum": 1 + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'substring' filter based on the edge name.", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string", + "enum": [ + "createdTime", + "name", + "type", + "label", + "customerTitle" + ] + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] } } ], @@ -44555,7 +43982,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/VersionCreationResult" + "$ref": "#/components/schemas/PageDataEdge" } } } @@ -44676,38 +44103,29 @@ ] } }, - "/api/allEntityGroups/edge/{edgeId}/{groupType}": { - "get": { + "/api/license/activateInstance": { + "post": { "tags": [ - "entity-group-controller" + "edge-controller" ], - "summary": "Get All Edge Entity Groups by entity type (getAllEdgeEntityGroups)", - "description": "Fetch the list of Entity Group Info objects based on the provided Entity Type and assigned to the provided Edge entity. Entity group allows you to group multiple entities of the same entity type (Device, Asset, Customer, User, Dashboard, etc). Entity Group always have an owner - particular Tenant or Customer. Each entity may belong to multiple groups simultaneously.Entity Group Info extends Entity Group object and adds 'ownerIds' - a list of owner ids.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getAllEdgeEntityGroups", + "summary": "Activate edge instance (activateInstance)", + "description": "Activates edge license on license portal.", + "operationId": "activateInstance", "parameters": [ { - "name": "edgeId", - "in": "path", - "description": "A string value representing the edge id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "name": "licenseSecret", + "in": "query", "required": true, "schema": { "type": "string" } }, { - "name": "groupType", - "in": "path", - "description": "EntityGroup type", + "name": "releaseDate", + "in": "query", "required": true, "schema": { - "type": "string", - "enum": [ - "ASSET", - "DEVICE", - "USER", - "ENTITY_VIEW", - "DASHBOARD" - ] + "type": "string" } } ], @@ -44717,10 +44135,7 @@ "content": { "application/json": { "schema": { - "type": "array", - "items": { - "$ref": "#/components/schemas/EntityGroupInfo" - } + "$ref": "#/components/schemas/JsonNode" } } } @@ -44737,7 +44152,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -44841,57 +44256,31 @@ ] } }, - "/api/edge/{edgeId}/entityGroup/{entityGroupId}/{groupType}": { + "/api/license/checkInstance": { "post": { "tags": [ - "entity-group-controller" + "edge-controller" ], - "summary": "Assign entity group to edge (assignEntityGroupToEdge)", - "description": "Creates assignment of an existing entity group to an instance of The Edge. Assignment works in async way - first, notification event pushed to edge service queue on platform. Second, remote edge service will receive a copy of assignment entity group (Edge will receive this instantly, if it's currently connected, or once it's going to be connected to platform). Third, once entity group will be delivered to edge service, edge will request entities of this group to be send to edge. Once entities will be delivered to edge service, they are going to be available for usage on remote edge instance.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'WRITE' permission for the entity (entities).", - "operationId": "assignEntityGroupToEdge", - "parameters": [ - { - "name": "edgeId", - "in": "path", - "description": "A string value representing the edge id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": true, - "schema": { - "type": "string" - } - }, - { - "name": "groupType", - "in": "path", - "description": "EntityGroup type", - "required": true, - "schema": { - "type": "string", - "enum": [ - "ASSET", - "DEVICE", - "USER", - "ENTITY_VIEW", - "DASHBOARD" - ] + "summary": "Check edge license (checkInstance)", + "description": "Checks license request from edge service by forwarding request to license portal.", + "operationId": "checkInstance", + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/JsonNode" + } } }, - { - "name": "entityGroupId", - "in": "path", - "description": "A string value representing the Entity Group Id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": true, - "schema": { - "type": "string" - } - } - ], + "required": true + }, "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/EntityGroup" + "$ref": "#/components/schemas/JsonNode" } } } @@ -45010,44 +44399,21 @@ "ApiKeyForm": [] } ] - }, - "delete": { + } + }, + "/api/tenant/edge": { + "get": { "tags": [ - "entity-group-controller" + "edge-controller" ], - "summary": "Unassign entity group from edge (unassignEntityGroupFromEdge)", - "description": "Clears assignment of the entity group to the edge. Unassignment works in async way - first, 'unassign' notification event pushed to edge queue on platform. Second, remote edge service will receive an 'unassign' command to remove entity group (Edge will receive this instantly, if it's currently connected, or once it's going to be connected to platform). Third, once 'unassign' command will be delivered to edge service, it's going to remove entity group and entities inside this group locally.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'WRITE' permission for the entity (entities).", - "operationId": "unassignEntityGroupFromEdge", + "summary": "Get Tenant Edge by name (getTenantEdgeByName)", + "description": "Requested edge must be owned by tenant or customer that the user belongs to. Edge name is an unique property of edge. So it can be used to identify the edge.\n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "getTenantEdgeByName", "parameters": [ { - "name": "edgeId", - "in": "path", - "description": "A string value representing the edge id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": true, - "schema": { - "type": "string" - } - }, - { - "name": "groupType", - "in": "path", - "description": "EntityGroup type", - "required": true, - "schema": { - "type": "string", - "enum": [ - "ASSET", - "DEVICE", - "USER", - "ENTITY_VIEW", - "DASHBOARD" - ] - } - }, - { - "name": "entityGroupId", - "in": "path", - "description": "A string value representing the Entity Group Id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "name": "edgeName", + "in": "query", + "description": "Unique name of the edge", "required": true, "schema": { "type": "string" @@ -45060,7 +44426,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/EntityGroup" + "$ref": "#/components/schemas/Edge" } } } @@ -45181,31 +44547,90 @@ ] } }, - "/api/entityGroup": { - "post": { + "/api/tenant/edges": { + "get": { "tags": [ - "entity-group-controller" + "edge-controller" ], - "summary": "Create Or Update Entity Group (saveEntityGroup)", - "description": "Create or update the Entity Group. When creating Entity Group, platform generates Entity Group Id as [time-based UUID](https://en.wikipedia.org/wiki/Universally_unique_identifier#Version_1_(date-time_and_MAC_address)). The newly created Entity Group Id will be present in the response. Specify existing Entity Group Id to update the group. Referencing non-existing Entity Group Id will cause 'Not Found' error.Remove 'id', 'tenantId' and optionally 'ownerId' from the request body example (below) to create new Entity Group entity. When 'ownerId' is not set (or null), it defaults to the current user's owner (Tenant for tenant admins, Customer for customer users). \n\nEntity group name is unique in the scope of owner and entity type. For example, you can't create two tenant device groups called 'Water meters'. However, you may create device and asset group with the same name. And also you may create groups with the same name for two different customers of the same tenant. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'WRITE' permission for specified group.", - "operationId": "saveEntityGroup", - "requestBody": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/EntityGroup" - } + "summary": "Get Tenant Edges (getTenantEdges)", + "description": "Returns a page of edges owned by tenant. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "getTenantEdges", + "parameters": [ + { + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", + "required": true, + "schema": { + "type": "integer", + "format": "int32" } }, - "required": true - }, + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", + "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "type", + "in": "query", + "description": "A string value representing the edge type. For example, 'default'", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'substring' filter based on the edge name.", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string", + "enum": [ + "createdTime", + "name", + "type", + "label", + "customerTitle" + ] + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] + } + } + ], "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/EntityGroupInfo" + "$ref": "#/components/schemas/PageDataEdge" } } } @@ -45222,7 +44647,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -45326,53 +44751,79 @@ ] } }, - "/api/entityGroup/all/{ownerType}/{ownerId}/{groupType}": { + "/api/user/edges": { "get": { "tags": [ - "entity-group-controller" + "edge-controller" ], - "summary": "Get special group All by owner and entity type (getEntityGroupsByOwnerAndType)", - "description": "Fetch reserved group 'All' based on the provided Owner Id and Entity Type. Entity group allows you to group multiple entities of the same entity type (Device, Asset, Customer, User, Dashboard, etc). Entity Group always have an owner - particular Tenant or Customer. Each entity may belong to multiple groups simultaneously.Entity Group Info extends Entity Group object and adds 'ownerIds' - a list of owner ids.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", - "operationId": "getEntityGroupAllByOwnerAndType", + "summary": "Get Edges (getUserEdges)", + "description": "Returns a page of edges available for current user. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getUserEdges", "parameters": [ { - "name": "ownerType", - "in": "path", - "description": "Tenant or Customer", + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", "required": true, "schema": { "type": "string", - "enum": [ - "TENANT", - "CUSTOMER" - ] + "minimum": 1 } }, { - "name": "ownerId", - "in": "path", - "description": "A string value representing the Tenant or Customer id", + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", "required": true, + "schema": { + "type": "string", + "minimum": 0 + } + }, + { + "name": "type", + "in": "query", + "description": "A string value representing the edge type. For example, 'default'", + "required": false, "schema": { "type": "string" - }, - "example": "784f394c-42b6-435a-983c-b7beff2784f9" + } }, { - "name": "groupType", - "in": "path", - "description": "Entity Group type", - "required": true, + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'substring' filter based on the edge name.", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, "schema": { "type": "string", "enum": [ - "CUSTOMER", - "ASSET", - "DEVICE", - "USER", - "ENTITY_VIEW", - "DASHBOARD", - "EDGE" + "createdTime", + "name", + "type", + "label", + "customerTitle" + ] + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" ] } } @@ -45383,7 +44834,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/EntityGroupInfo" + "$ref": "#/components/schemas/PageDataEdge" } } } @@ -45504,23 +44955,101 @@ ] } }, - "/api/entityGroup/{entityGroupId}": { + "/api/edge/{edgeId}/events": { "get": { "tags": [ - "entity-group-controller" + "edge-event-controller" ], - "summary": "Get Entity Group Info (getEntityGroupById)", - "description": "Fetch the Entity Group object based on the provided Entity Group Id. Entity group allows you to group multiple entities of the same entity type (Device, Asset, Customer, User, Dashboard, etc). Entity Group always have an owner - particular Tenant or Customer. Each entity may belong to multiple groups simultaneously.Entity Group Info extends Entity Group object and adds 'ownerIds' - a list of owner ids.\n\nEntity group name is unique in the scope of owner and entity type. For example, you can't create two tenant device groups called 'Water meters'. However, you may create device and asset group with the same name. And also you may create groups with the same name for two different customers of the same tenant. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", - "operationId": "getEntityGroupById", + "summary": "Get Edge Events (getEdgeEvents)", + "description": "Returns a page of edge events for the requested edge. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. ", + "operationId": "getEdgeEvents", "parameters": [ { - "name": "entityGroupId", + "name": "edgeId", "in": "path", - "description": "A string value representing the Entity Group Id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "description": "A string value representing the edge id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { "type": "string" } + }, + { + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", + "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", + "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'substring' filter based on the edge event type name.", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string", + "enum": [ + "createdTime", + "name", + "type", + "label", + "customerTitle" + ] + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] + } + }, + { + "name": "startTime", + "in": "query", + "description": "Timestamp. Edge events with creation time before it won't be queried", + "required": false, + "schema": { + "type": "integer", + "format": "int64" + } + }, + { + "name": "endTime", + "in": "query", + "description": "Timestamp. Edge events with creation time after it won't be queried", + "required": false, + "schema": { + "type": "integer", + "format": "int64" + } } ], "responses": { @@ -45529,7 +45058,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/EntityGroupInfo" + "$ref": "#/components/schemas/PageDataEdgeEvent" } } } @@ -45648,28 +45177,29 @@ "ApiKeyForm": [] } ] - }, - "delete": { + } + }, + "/api/entities/vc/branches": { + "get": { "tags": [ - "entity-group-controller" - ], - "summary": "Delete Entity Group (deleteEntityGroup)", - "description": "Deletes the entity group but does not delete the entities in the group, since they are also present in reserved group 'All'. Referencing non-existing Entity Group Id will cause an error.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'DELETE' permission for specified group.", - "operationId": "deleteEntityGroup", - "parameters": [ - { - "name": "entityGroupId", - "in": "path", - "description": "A string value representing the Entity Group Id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": true, - "schema": { - "type": "string" - } - } + "entities-version-control-controller" ], + "summary": "List branches (listBranches)", + "description": "Lists branches available in the remote repository. \n\nResponse example: \n```json\n[\n {\n \"name\": \"master\",\n \"default\": true\n },\n {\n \"name\": \"dev\",\n \"default\": false\n },\n {\n \"name\": \"dev-2\",\n \"default\": false\n }\n]\n```", + "operationId": "listBranches", "responses": { "200": { - "description": "OK" + "description": "OK", + "content": { + "application/json": { + "schema": { + "type": "array", + "items": { + "$ref": "#/components/schemas/BranchInfo" + } + } + } + } }, "400": { "description": "Bad Request", @@ -45787,43 +45317,55 @@ ] } }, - "/api/entityGroup/{entityGroupId}/addEntities": { - "post": { + "/api/entities/vc/diff/{entityType}/{internalEntityUuid}": { + "get": { "tags": [ - "entity-group-controller" + "entities-version-control-controller" ], - "summary": "Add entities to the group (addEntitiesToEntityGroup)", - "description": "Add entities to the specified entity group. This operation is idempotent: entities that are already members of the group are silently ignored. Entity group allows you to group multiple entities of the same entity type (Device, Asset, Customer, User, Dashboard, etc). Entity Group always have an owner - particular Tenant or Customer. Each entity may belong to multiple groups simultaneously.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'ADD_TO_GROUP' permission for specified group.", - "operationId": "addEntitiesToEntityGroup", + "summary": "Compare entity data to version (compareEntityDataToVersion)", + "description": "Returns an object with current entity data and the one at a specific version. Entity data structure is the same as stored in a repository. \n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "compareEntityDataToVersion", "parameters": [ { - "name": "entityGroupId", + "name": "entityType", "in": "path", - "description": "A string value representing the Entity Group Id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "description": "A string value representing the entity type. For example, 'DEVICE'", + "required": true, + "schema": { + "$ref": "#/components/schemas/EntityType" + } + }, + { + "name": "internalEntityUuid", + "in": "path", + "description": "A string value representing the entity id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, + "schema": { + "type": "string", + "format": "uuid" + } + }, + { + "name": "versionId", + "in": "query", + "description": "Version id, for example fd82625bdd7d6131cf8027b44ee967012ecaf990. Represents commit hash.", "required": true, "schema": { "type": "string" } } ], - "requestBody": { - "content": { - "application/json": { - "schema": { - "type": "array", - "description": "A list of entity ids", - "items": { - "type": "string" + "responses": { + "200": { + "description": "OK", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/EntityDataDiff" } } } }, - "required": true - }, - "responses": { - "200": { - "description": "OK" - }, "400": { "description": "Bad Request", "content": { @@ -45836,7 +45378,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -45940,34 +45482,19 @@ ] } }, - "/api/entityGroup/{entityGroupId}/deleteEntities": { + "/api/entities/vc/entity": { "post": { "tags": [ - "entity-group-controller" - ], - "summary": "Remove entities from the group (removeEntitiesFromEntityGroup)", - "description": "Removes entities from the specified entity group. Entity group allows you to group multiple entities of the same entity type (Device, Asset, Customer, User, Dashboard, etc). Entity Group always have an owner - particular Tenant or Customer. Each entity may belong to multiple groups simultaneously.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'REMOVE_FROM_GROUP' permission for specified group.", - "operationId": "removeEntitiesFromEntityGroup", - "parameters": [ - { - "name": "entityGroupId", - "in": "path", - "description": "A string value representing the Entity Group Id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": true, - "schema": { - "type": "string" - } - } + "entities-version-control-controller" ], + "summary": "Load entities version (loadEntitiesVersion)", + "description": "Loads specific version of remote entities (or single entity) by request. Supported entity types: CUSTOMER, ASSET, RULE_CHAIN, DASHBOARD, DEVICE_PROFILE, DEVICE, ENTITY_VIEW, WIDGETS_BUNDLE, CONVERTER, INTEGRATION, ROLE and USER group.\n\nThere are multiple types of request. Each of them requires branch name (`branch`) and version id (`versionId`). Request of type `SINGLE_ENTITY` is needed to restore a concrete version of a specific entity. It contains id of a remote entity (`externalEntityId`), internal entity id (`internalEntityId`) and additional configuration (`config`):\n- `loadRelations` - to update relations list (in case `saveRelations` option was enabled during version creation);\n- `loadAttributes` - to load entity attributes (if `saveAttributes` config option was enabled);\n- `loadCredentials` - to update device credentials (if `saveCredentials` option was enabled during version creation);\n- `loadPermissions` - when loading user group, to update group permission list;\n- `loadGroupEntities` - when loading an entity group, to load its entities as well;\n- `autoGenerateIntegrationKey` - if loading integration version, to autogenerate routing key.\n\nAn example of such request:\n```json\n{\n \"type\": \"SINGLE_ENTITY\",\n \n \"branch\": \"dev\",\n \"versionId\": \"b3c28d722d328324c7c15b0b30047b0c40011cf7\",\n \n \"externalEntityId\": {\n \"entityType\": \"DEVICE\",\n \"id\": \"b7944123-d4f4-11ec-847b-0f432358ab48\"\n },\n \"config\": {\n \"loadRelations\": false,\n \"loadAttributes\": true,\n \"loadCredentials\": true\n }\n}\n```\n\nAnother request type (`ENTITY_TYPE`) is needed to load specific version of the whole entity types. It contains a structure with entity types to load and configs for each entity type (`entityTypes`). For each specified entity type, the method will load all remote entities of this type that are present at the version. A config for each entity type contains the same options as in `SINGLE_ENTITY` request type, and additionally contains following options:\n- `removeOtherEntities` - to remove local entities that are not present on the remote - basically to overwrite local entity type with the remote one;\n- `findExistingEntityByName` - when you are loading some remote entities that are not yet present at this tenant, try to find existing entity by name and update it rather than create new.\n\nHere is an example of the request to completely restore version of the whole device entity type:\n```json\n{\n \"type\": \"ENTITY_TYPE\",\n\n \"branch\": \"dev\",\n \"versionId\": \"b3c28d722d328324c7c15b0b30047b0c40011cf7\",\n\n \"entityTypes\": {\n \"DEVICE\": {\n \"removeOtherEntities\": true,\n \"findExistingEntityByName\": false,\n \"loadRelations\": true,\n \"loadAttributes\": true,\n \"loadCredentials\": true\n }\n }\n}\n```\n\nThe response will contain generated request UUID that is to be used to check the status of operation via `getVersionLoadRequestStatus`.\n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "loadEntitiesVersion", "requestBody": { "content": { "application/json": { "schema": { - "type": "array", - "description": "A list of entity ids", - "items": { - "type": "string" - } + "$ref": "#/components/schemas/VersionLoadRequest" } } }, @@ -45975,7 +45502,15 @@ }, "responses": { "200": { - "description": "OK" + "description": "OK", + "content": { + "application/json": { + "schema": { + "type": "string", + "format": "uuid" + } + } + } }, "400": { "description": "Bad Request", @@ -46093,74 +45628,32 @@ ] } }, - "/api/entityGroup/{entityGroupId}/entities": { + "/api/entities/vc/entity/{entityType}/{versionId}": { "get": { "tags": [ - "entity-group-controller" + "entities-version-control-controller" ], - "summary": "Get Group Entities (getEntities)", - "description": "Returns a page of Short Entity View objects that belongs to specified Entity Group Id. Short Entity View object contains the entity id and number of fields (attributes, telemetry, etc). List of those fields is configurable and defined in the group configuration.You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", - "operationId": "getEntities", + "summary": "List entities at version (listEntitiesAtVersion)", + "description": "Returns a list of remote entities of a specific entity type that are available at a concrete version. \nEach entity item in the result has `externalId` property. Entities order will be the same as in the repository.\n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "listEntitiesAtVersion", "parameters": [ { - "name": "entityGroupId", + "name": "entityType", "in": "path", - "description": "A string value representing the Entity Group Id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": true, - "schema": { - "type": "string" - } - }, - { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", + "description": "A string value representing the entity type. For example, 'DEVICE'", "required": true, "schema": { - "type": "string", - "minimum": 1 + "$ref": "#/components/schemas/EntityType" } }, { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", + "name": "versionId", + "in": "path", + "description": "Version id, for example fd82625bdd7d6131cf8027b44ee967012ecaf990. Represents commit hash.", "required": true, - "schema": { - "type": "string", - "minimum": 0 - } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'startsWith' filter based on the entity group name.", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, "schema": { "type": "string" } - }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] - } } ], "responses": { @@ -46169,7 +45662,10 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataShortEntityView" + "type": "array", + "items": { + "$ref": "#/components/schemas/VersionedEntityInfo" + } } } } @@ -46290,28 +45786,36 @@ ] } }, - "/api/entityGroup/{entityGroupId}/makePrivate": { - "post": { + "/api/entities/vc/entity/{requestId}/status": { + "get": { "tags": [ - "entity-group-controller" + "entities-version-control-controller" ], - "summary": "Make Entity Group Private (makeEntityGroupPrivate)", - "description": "Make the entity group not available for non authorized users. Every group is private by default. This call is useful to hide the group that was previously made public.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'WRITE' permission for specified group.", - "operationId": "makeEntityGroupPrivate", + "summary": "Get version load request status (getVersionLoadRequestStatus)", + "description": "Returns the status of previously made version load request. The structure contains following parameters:\n- `done` - if the request was successfully processed;\n- `result` - a list of load results for each entity type:\n - `created` - created entities count;\n - `updated` - updated entities count;\n - `deleted` - removed entities count;\n - `groupsCreated` - created entity groups count;\n - `groupsUpdated` - updated entity groups count;\n - `groupsDeleted` - removed entity groups count.\n- `error` - if an error occurred during processing, error info:\n - `type` - error type;\n - `source` - an external id of remote entity;\n - `target` - if failed to find referenced entity by external id - this external id;\n - `message` - error message.\n\nAn example of successfully processed request status:\n```json\n{\n \"done\": true,\n \"result\": [\n {\n \"entityType\": \"DEVICE\",\n \"created\": 10,\n \"updated\": 5,\n \"deleted\": 5,\n \"groupsCreated\": 1,\n \"groupsUpdated\": 1,\n \"groupsDeleted\": 1\n },\n {\n \"entityType\": \"ASSET\",\n \"created\": 4,\n \"updated\": 0,\n \"deleted\": 8,\n \"groupsCreated\": 1,\n \"groupsUpdated\": 0,\n \"groupsDeleted\": 2\n }\n ]\n}\n```\n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "getVersionLoadRequestStatus", "parameters": [ { - "name": "entityGroupId", + "name": "requestId", "in": "path", - "description": "A string value representing the Entity Group Id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "description": "A string value representing the version control request id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { - "type": "string" + "type": "string", + "format": "uuid" } } ], "responses": { "200": { - "description": "OK" + "description": "OK", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/VersionLoadResult" + } + } + } }, "400": { "description": "Bad Request", @@ -46325,7 +45829,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -46429,19 +45933,19 @@ ] } }, - "/api/entityGroup/{entityGroupId}/makePublic": { - "post": { + "/api/entities/vc/entity/{versionId}": { + "get": { "tags": [ - "entity-group-controller" + "entities-version-control-controller" ], - "summary": "Make Entity Group Publicly available (makeEntityGroupPublic)", - "description": "Make the entity group available for non authorized users. Useful for public dashboards that will be embedded into the public websites. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'WRITE' permission for specified group.", - "operationId": "makeEntityGroupPublic", + "summary": "List all entities at version (listAllEntitiesAtVersion)", + "description": "Returns a list of all remote entities available in a specific version. Response type is the same as for listAllEntitiesAtVersion API method. \nReturned entities order will be the same as in the repository.\n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "listAllEntitiesAtVersion", "parameters": [ { - "name": "entityGroupId", + "name": "versionId", "in": "path", - "description": "A string value representing the Entity Group Id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "description": "Version id, for example fd82625bdd7d6131cf8027b44ee967012ecaf990. Represents commit hash.", "required": true, "schema": { "type": "string" @@ -46450,156 +45954,17 @@ ], "responses": { "200": { - "description": "OK" - }, - "400": { - "description": "Bad Request", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ThingsboardErrorResponse" - }, - "examples": { - "error-code-400": { - "summary": "Bad Request", - "value": { - "status": 400, - "message": "Invalid request body", - "errorCode": 31, - "timestamp": 1609459200000 - } - } - } - } - } - }, - "401": { - "description": "Unauthorized", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ThingsboardErrorResponse" - }, - "examples": { - "error-code-401": { - "summary": "Unauthorized", - "value": { - "status": 401, - "message": "Authentication failed", - "errorCode": 10, - "timestamp": 1609459200000 - } - } - } - } - } - }, - "403": { - "description": "Forbidden", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ThingsboardErrorResponse" - }, - "examples": { - "error-code-403": { - "summary": "Forbidden", - "value": { - "status": 403, - "message": "You don't have permission to perform this operation!", - "errorCode": 20, - "timestamp": 1609459200000 - } - } - } - } - } - }, - "404": { - "description": "Not Found", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ThingsboardErrorResponse" - }, - "examples": { - "error-code-404": { - "summary": "Not Found", - "value": { - "status": 404, - "message": "Requested item wasn't found!", - "errorCode": 32, - "timestamp": 1609459200000 - } - } - } - } - } - }, - "429": { - "description": "Too Many Requests", + "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/ThingsboardErrorResponse" - }, - "examples": { - "error-code-429": { - "summary": "Too Many Requests", - "value": { - "status": 429, - "message": "Too many requests for current tenant!", - "errorCode": 33, - "timestamp": 1609459200000 - } + "type": "array", + "items": { + "$ref": "#/components/schemas/VersionedEntityInfo" } } } } - } - }, - "security": [ - { - "HttpLoginForm": [] - }, - { - "ApiKeyForm": [] - } - ] - } - }, - "/api/entityGroup/{entityGroupId}/share": { - "post": { - "tags": [ - "entity-group-controller" - ], - "summary": "Share the Entity Group (shareEntityGroup)", - "description": "Share the entity group with certain user group based on the provided Share Group Request. The request is quite flexible and processing of the request involves multiple security checks using platform RBAC feature.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'WRITE' permission for specified group.", - "operationId": "shareEntityGroup", - "parameters": [ - { - "name": "entityGroupId", - "in": "path", - "description": "A string value representing the Entity Group Id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": true, - "schema": { - "type": "string" - } - } - ], - "requestBody": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ShareGroupRequest" - } - } - }, - "required": true - }, - "responses": { - "200": { - "description": "OK" }, "400": { "description": "Bad Request", @@ -46613,7 +45978,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -46717,31 +46082,51 @@ ] } }, - "/api/entityGroup/{entityGroupId}/{entityId}": { + "/api/entities/vc/info/{versionId}/{entityType}/{externalEntityUuid}": { "get": { "tags": [ - "entity-group-controller" + "entities-version-control-controller" ], - "summary": "Get Group Entity (getGroupEntity)", - "description": "Fetch the Short Entity View object based on the group and entity id. Short Entity View object contains the entity id and number of fields (attributes, telemetry, etc). List of those fields is configurable and defined in the group configuration.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", - "operationId": "getGroupEntity", + "summary": "Get entity data info (getEntityDataInfo)", + "description": "Retrieves short info about the remote entity by external id at a concrete version. \nReturned entity data info contains following properties: `hasRelations` (whether stored entity data contains relations), `hasAttributes` (contains attributes), `hasCredentials` (whether stored device data has credentials), `hasPermissions` (user group data contains group permission list) and `hasGroupEntities` (entity group data contains group entities).\n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "getEntityDataInfo", "parameters": [ { - "name": "entityGroupId", + "name": "versionId", "in": "path", - "description": "A string value representing the Entity Group Id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "description": "Version id, for example fd82625bdd7d6131cf8027b44ee967012ecaf990. Represents commit hash.", "required": true, "schema": { "type": "string" } }, { - "name": "entityId", + "name": "entityType", "in": "path", - "description": "A string value representing the entity id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "description": "A string value representing the entity type. For example, 'DEVICE'", "required": true, "schema": { - "type": "string" + "$ref": "#/components/schemas/EntityType" + } + }, + { + "name": "externalEntityUuid", + "in": "path", + "description": "A string value representing external entity id", + "required": true, + "schema": { + "type": "string", + "format": "uuid" + } + }, + { + "name": "internalEntityId", + "in": "query", + "description": "A string value representing the entity id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": false, + "schema": { + "type": "string", + "format": "uuid" } } ], @@ -46751,7 +46136,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/ShortEntityView" + "$ref": "#/components/schemas/EntityDataInfo" } } } @@ -46872,46 +46257,89 @@ ] } }, - "/api/entityGroup/{entityGroupId}/{userGroupId}/{roleId}/share": { - "post": { + "/api/entities/vc/version": { + "get": { "tags": [ - "entity-group-controller" + "entities-version-control-controller" ], - "summary": "Share the Entity Group with User group (shareEntityGroupToChildOwnerUserGroup)", - "description": "Share the entity group with specified user group using specified role. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'WRITE' permission for specified group.", - "operationId": "shareEntityGroupToChildOwnerUserGroup", + "summary": "List all versions (listVersions)", + "description": "Lists all available versions in a branch for all entity types. \nIf specified branch does not exist - empty page data will be returned. The response format is the same as for `listEntityVersions` API method.\n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "listVersions", "parameters": [ { - "name": "entityGroupId", - "in": "path", - "description": "A string value representing the Entity Group Id that you would like to share. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "name": "branch", + "in": "query", + "description": "The name of the working branch, for example 'master'", "required": true, "schema": { "type": "string" } }, { - "name": "userGroupId", - "in": "path", - "description": "A string value representing the Entity(User) Group Id that you would like to share with. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", "required": true, "schema": { - "type": "string" + "type": "integer", + "format": "int32" } }, { - "name": "roleId", - "in": "path", - "description": "A string value representing the Role Id that describes set of permissions you would like to share (read, write, etc). For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'substring' filter based on the entity version name.", + "required": false, "schema": { "type": "string" } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string", + "enum": [ + "timestamp" + ] + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] + } } ], "responses": { "200": { - "description": "OK" + "description": "OK", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/PageDataEntityVersion" + } + } + } }, "400": { "description": "Bad Request", @@ -46925,7 +46353,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -47027,75 +46455,32 @@ "ApiKeyForm": [] } ] - } - }, - "/api/entityGroup/{ownerType}/{ownerId}/{groupType}/{groupName}": { - "get": { + }, + "post": { "tags": [ - "entity-group-controller" + "entities-version-control-controller" ], - "summary": "Get Entity Group by owner, type and name (getEntityGroupByOwnerAndNameAndType)", - "description": "Fetch the Entity Group object based on the provided Entity Group Id. Entity group allows you to group multiple entities of the same entity type (Device, Asset, Customer, User, Dashboard, etc). Entity Group always have an owner - particular Tenant or Customer. Each entity may belong to multiple groups simultaneously.Entity Group Info extends Entity Group object and adds 'ownerIds' - a list of owner ids.\n\nEntity group name is unique in the scope of owner and entity type. For example, you can't create two tenant device groups called 'Water meters'. However, you may create device and asset group with the same name. And also you may create groups with the same name for two different customers of the same tenant. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", - "operationId": "getEntityGroupByOwnerAndNameAndType", - "parameters": [ - { - "name": "ownerType", - "in": "path", - "description": "Tenant or Customer", - "required": true, - "schema": { - "type": "string", - "enum": [ - "TENANT", - "CUSTOMER" - ] - } - }, - { - "name": "ownerId", - "in": "path", - "description": "A string value representing the Tenant or Customer id", - "required": true, - "schema": { - "type": "string" - }, - "example": "784f394c-42b6-435a-983c-b7beff2784f9" - }, - { - "name": "groupType", - "in": "path", - "description": "Entity Group type", - "required": true, - "schema": { - "type": "string", - "enum": [ - "CUSTOMER", - "ASSET", - "DEVICE", - "USER", - "ENTITY_VIEW", - "DASHBOARD", - "EDGE" - ] + "summary": "Save entities version (saveEntitiesVersion)", + "description": "Creates a new version of entities (or a single entity) by request.\nSupported entity types: CUSTOMER, ASSET, RULE_CHAIN, DASHBOARD, DEVICE_PROFILE, DEVICE, ENTITY_VIEW, WIDGETS_BUNDLE, CONVERTER, INTEGRATION, ROLE and USER group.\n\nThere are two available types of request: `SINGLE_ENTITY` and `COMPLEX`. Each of them contains version name (`versionName`) and name of a branch (`branch`) to create version (commit) in. If specified branch does not exists in a remote repo, then new empty branch will be created. Request of the `SINGLE_ENTITY` type has id of an entity (`entityId`) and additional configuration (`config`) which has following options: \n- `saveRelations` - whether to add inbound and outbound relations of type COMMON to created entity version;\n- `saveAttributes` - to save attributes of server scope (and also shared scope for devices);\n- `saveCredentials` - when saving a version of a device, to add its credentials to the version;\n- `savePermissions` - when saving a user group - to save group permission list;\n- `saveGroupEntities` - when saving an entity group - to save its entities as well.\n\nAn example of a `SINGLE_ENTITY` version create request:\n```json\n{\n \"type\": \"SINGLE_ENTITY\",\n\n \"versionName\": \"Version 1.0\",\n \"branch\": \"dev\",\n\n \"entityId\": {\n \"entityType\": \"DEVICE\",\n \"id\": \"b79448e0-d4f4-11ec-847b-0f432358ab48\"\n },\n \"config\": {\n \"saveRelations\": true,\n \"saveAttributes\": true,\n \"saveCredentials\": false\n }\n}\n```\n\nSecond request type (`COMPLEX`), additionally to `branch` and `versionName`, contains following properties:\n- `entityTypes` - a structure with entity types to export and configuration for each entity type; this configuration has all the options available for `SINGLE_ENTITY` and additionally has these ones: \n - `allEntities` and `entityIds` - if you want to save the version of all entities of the entity type then set `allEntities` param to true, otherwise set it to false and specify `entityIds` - in case entity type is group entity, list of specific entity groups, or if not - list of entities;\n - `syncStrategy` - synchronization strategy to use for this entity type: when set to `OVERWRITE` then the list of remote entities of this type will be overwritten by newly added entities. If set to `MERGE` - existing remote entities of this entity type will not be removed, new entities will just be added on top (or existing remote entities will be updated).\n- `syncStrategy` - default synchronization strategy to use when it is not specified for an entity type.\n\nExample for this type of request:\n```json\n{\n \"type\": \"COMPLEX\",\n\n \"versionName\": \"Devices and profiles: release 2\",\n \"branch\": \"master\",\n\n \"syncStrategy\": \"OVERWRITE\",\n \"entityTypes\": {\n \"DEVICE\": {\n \"syncStrategy\": null,\n \"allEntities\": true,\n \"saveRelations\": true,\n \"saveAttributes\": true,\n \"saveCredentials\": true\n },\n \"DEVICE_PROFILE\": {\n \"syncStrategy\": \"MERGE\",\n \"allEntities\": false,\n \"entityIds\": [\n \"b79448e0-d4f4-11ec-847b-0f432358ab48\"\n ],\n \"saveRelations\": true\n }\n }\n}\n```\n\nResponse wil contain generated request UUID, that can be then used to retrieve status of operation via `getVersionCreateRequestStatus`.\n\n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "saveEntitiesVersion", + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/VersionCreateRequest" + } } }, - { - "name": "groupName", - "in": "path", - "description": "Entity Group name", - "required": true, - "schema": { - "type": "string" - } - } - ], + "required": true + }, "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/EntityGroupInfo" + "type": "string", + "format": "uuid" } } } @@ -47112,7 +46497,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -47216,23 +46601,86 @@ ] } }, - "/api/entityGroupInfo/{entityGroupId}": { + "/api/entities/vc/version/{entityType}": { "get": { "tags": [ - "entity-group-controller" + "entities-version-control-controller" ], - "summary": "Get Entity Group Entity Info (getEntityGroupEntityInfoById)", - "description": "Fetch the Entity Group Entity Info object based on the provided Entity Group Id. Entity Info is a lightweight object that contains only id and name of the entity group. \n\nEntity group name is unique in the scope of owner and entity type. For example, you can't create two tenant device groups called 'Water meters'. However, you may create device and asset group with the same name. And also you may create groups with the same name for two different customers of the same tenant. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", - "operationId": "getEntityGroupEntityInfoById", + "summary": "List entity type versions (listEntityTypeVersions)", + "description": "Returns list of versions of an entity type in a branch. This is a collected list of versions that were created for entities of this type in a remote branch. \nIf specified branch does not exist - empty page data will be returned. The response structure is the same as for `listEntityVersions` API method.\n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "listEntityTypeVersions", "parameters": [ { - "name": "entityGroupId", + "name": "entityType", "in": "path", - "description": "A string value representing the Entity Group Id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "description": "A string value representing the entity type. For example, 'DEVICE'", + "required": true, + "schema": { + "$ref": "#/components/schemas/EntityType" + } + }, + { + "name": "branch", + "in": "query", + "description": "The name of the working branch, for example 'master'", + "required": true, + "schema": { + "type": "string" + } + }, + { + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", + "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'substring' filter based on the entity version name.", + "required": false, "schema": { "type": "string" } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string", + "enum": [ + "timestamp" + ] + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] + } } ], "responses": { @@ -47241,7 +46689,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/EntityInfo" + "$ref": "#/components/schemas/PageDataEntityVersion" } } } @@ -47362,25 +46810,104 @@ ] } }, - "/api/entityGroupInfos": { + "/api/entities/vc/version/{entityType}/{externalEntityUuid}": { "get": { "tags": [ - "entity-group-controller" + "entities-version-control-controller" ], - "summary": "Get Entity Group Entity Infos by Ids (getEntityGroupEntityInfosByIds)", - "description": "Fetch the list of Entity Group Entity Info objects based on the provided entity group ids list. Entity Info is a lightweight object that contains only id and name of the entity group. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", - "operationId": "getEntityGroupEntityInfosByIds", + "summary": "List entity versions (listEntityVersions)", + "description": "Returns list of versions for a specific entity in a concrete branch. \nYou need to specify external id of an entity to list versions for. This is `externalId` property of an entity, or otherwise if not set - simply id of this entity. \nIf specified branch does not exist - empty page data will be returned. \n\nEach version info item has timestamp, id, name and author. Version id can then be used to restore the version. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nResponse example: \n```json\n{\n \"data\": [\n {\n \"timestamp\": 1655198593000,\n \"id\": \"fd82625bdd7d6131cf8027b44ee967012ecaf990\",\n \"name\": \"Devices and assets - v2.0\",\n \"author\": \"John Doe (johndoe@gmail.com)\"\n },\n {\n \"timestamp\": 1655198528000,\n \"id\": \"682adcffa9c8a2f863af6f00c4850323acbd4219\",\n \"name\": \"Update my device\",\n \"author\": \"John Doe (johndoe@gmail.com)\"\n },\n {\n \"timestamp\": 1655198280000,\n \"id\": \"d2a6087c2b30e18cc55e7cdda345a8d0dfb959a4\",\n \"name\": \"Devices and assets - v1.0\",\n \"author\": \"John Doe (johndoe@gmail.com)\"\n }\n ],\n \"totalPages\": 1,\n \"totalElements\": 3,\n \"hasNext\": false\n}\n```\n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "listEntityVersions", "parameters": [ { - "name": "entityGroupIds", + "name": "entityType", + "in": "path", + "description": "A string value representing the entity type. For example, 'DEVICE'", + "required": true, + "schema": { + "$ref": "#/components/schemas/EntityType" + } + }, + { + "name": "externalEntityUuid", + "in": "path", + "description": "A string value representing external entity id. This is `externalId` property of an entity, or otherwise if not set - simply id of this entity.", + "required": true, + "schema": { + "type": "string", + "format": "uuid" + } + }, + { + "name": "branch", "in": "query", - "description": "A list of group ids, separated by comma ','", + "description": "The name of the working branch, for example 'master'", "required": true, "schema": { - "type": "array", - "items": { - "type": "string" - } + "type": "string" + } + }, + { + "name": "internalEntityId", + "in": "query", + "required": false, + "schema": { + "type": "string", + "format": "uuid" + } + }, + { + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", + "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", + "required": true, + "schema": { + "type": "integer", + "format": "int32" + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'substring' filter based on the entity version name.", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string", + "enum": [ + "timestamp" + ] + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] } } ], @@ -47390,10 +46917,7 @@ "content": { "application/json": { "schema": { - "type": "array", - "items": { - "$ref": "#/components/schemas/EntityInfo" - } + "$ref": "#/components/schemas/PageDataEntityVersion" } } } @@ -47514,91 +47038,23 @@ ] } }, - "/api/entityGroupInfos/{groupType}": { + "/api/entities/vc/version/{requestId}/status": { "get": { "tags": [ - "entity-group-controller" + "entities-version-control-controller" ], - "summary": "Get Entity Group Entity Infos by entity type and page link (getEntityGroupEntityInfosByTypeAndPageLink)", - "description": "Returns a page of Entity Group Entity Info objects based on the provided Entity Type and Page Link. Entity Info is a lightweight object that contains only id and name of the entity group. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", - "operationId": "getEntityGroupEntityInfosByTypeAndPageLink", + "summary": "Get version create request status (getVersionCreateRequestStatus)", + "description": "Returns the status of previously made version create request. \n\nThis status contains following properties:\n- `done` - whether request processing is finished;\n- `version` - created version info: timestamp, version id (commit hash), commit name and commit author;\n- `added` - count of items that were created in the remote repo;\n- `modified` - modified items count;\n- `removed` - removed items count;\n- `error` - error message, if an error occurred while handling the request.\n\nAn example of successful status:\n```json\n{\n \"done\": true,\n \"added\": 10,\n \"modified\": 2,\n \"removed\": 5,\n \"version\": {\n \"timestamp\": 1655198528000,\n \"id\":\"8a834dd389ed80e0759ba8ee338b3f1fd160a114\",\n \"name\": \"My devices v2.0\",\n \"author\": \"John Doe\"\n },\n \"error\": null\n}\n```\n\nAvailable for users with 'TENANT_ADMIN' authority.", + "operationId": "getVersionCreateRequestStatus", "parameters": [ { - "name": "groupType", + "name": "requestId", "in": "path", - "description": "Entity Group type", - "required": true, - "schema": { - "type": "string", - "enum": [ - "CUSTOMER", - "ASSET", - "DEVICE", - "USER", - "ENTITY_VIEW", - "DASHBOARD", - "EDGE" - ] - } - }, - { - "name": "includeShared", - "in": "query", - "description": "Whether to include shared entity groups.", - "required": false, - "schema": { - "type": "boolean" - } - }, - { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "string", - "minimum": 1 - } - }, - { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", + "description": "A string value representing the version control request id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { "type": "string", - "minimum": 0 - } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'startsWith' filter based on the entity group name.", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] + "format": "uuid" } } ], @@ -47608,7 +47064,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataEntityInfo" + "$ref": "#/components/schemas/VersionCreationResult" } } } @@ -47729,81 +47185,37 @@ ] } }, - "/api/entityGroupInfos/{groupType}/shared": { + "/api/allEntityGroups/edge/{edgeId}/{groupType}": { "get": { "tags": [ "entity-group-controller" ], - "summary": "Get Shared Entity Group Entity Infos by entity type and page link (getSharedEntityGroupEntityInfosByTypeAndPageLink)", - "description": "Returns a page of Shared Entity Group Entity Info objects based on the provided Entity Type and Page Link. Entity Info is a lightweight object that contains only id and name of the entity group. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", - "operationId": "getSharedEntityGroupEntityInfosByTypeAndPageLink", + "summary": "Get All Edge Entity Groups by entity type (getAllEdgeEntityGroups)", + "description": "Fetch the list of Entity Group Info objects based on the provided Entity Type and assigned to the provided Edge entity. Entity group allows you to group multiple entities of the same entity type (Device, Asset, Customer, User, Dashboard, etc). Entity Group always have an owner - particular Tenant or Customer. Each entity may belong to multiple groups simultaneously.Entity Group Info extends Entity Group object and adds 'ownerIds' - a list of owner ids.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getAllEdgeEntityGroups", "parameters": [ { - "name": "groupType", + "name": "edgeId", "in": "path", - "description": "Entity Group type", - "required": true, - "schema": { - "type": "string", - "enum": [ - "CUSTOMER", - "ASSET", - "DEVICE", - "USER", - "ENTITY_VIEW", - "DASHBOARD", - "EDGE" - ] - } - }, - { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "string", - "minimum": 1 - } - }, - { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", + "description": "A string value representing the edge id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, - "schema": { - "type": "string", - "minimum": 0 - } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'startsWith' filter based on the entity group name.", - "required": false, "schema": { "type": "string" } }, { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, + "name": "groupType", + "in": "path", + "description": "EntityGroup type", + "required": true, "schema": { "type": "string", "enum": [ - "ASC", - "DESC" + "ASSET", + "DEVICE", + "USER", + "ENTITY_VIEW", + "DASHBOARD" ] } } @@ -47814,7 +47226,10 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataEntityInfo" + "type": "array", + "items": { + "$ref": "#/components/schemas/EntityGroupInfo" + } } } } @@ -47935,106 +47350,48 @@ ] } }, - "/api/entityGroupInfos/{ownerType}/{ownerId}/{groupType}": { - "get": { + "/api/edge/{edgeId}/entityGroup/{entityGroupId}/{groupType}": { + "post": { "tags": [ "entity-group-controller" ], - "summary": "Get Entity Group Entity Infos by owner and entity type and page link (getEntityGroupEntityInfosByOwnerAndTypeAndPageLink)", - "description": "Returns a page of Entity Group Entity Info objects based on the provided Owner Id and Entity Type and Page Link. Entity Info is a lightweight object that contains only id and name of the entity group. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", - "operationId": "getEntityGroupEntityInfosByOwnerAndTypeAndPageLink", + "summary": "Assign entity group to edge (assignEntityGroupToEdge)", + "description": "Creates assignment of an existing entity group to an instance of The Edge. Assignment works in async way - first, notification event pushed to edge service queue on platform. Second, remote edge service will receive a copy of assignment entity group (Edge will receive this instantly, if it's currently connected, or once it's going to be connected to platform). Third, once entity group will be delivered to edge service, edge will request entities of this group to be send to edge. Once entities will be delivered to edge service, they are going to be available for usage on remote edge instance.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'WRITE' permission for the entity (entities).", + "operationId": "assignEntityGroupToEdge", "parameters": [ { - "name": "ownerType", - "in": "path", - "description": "Tenant or Customer", - "required": true, - "schema": { - "type": "string", - "enum": [ - "TENANT", - "CUSTOMER" - ] - } - }, - { - "name": "ownerId", + "name": "edgeId", "in": "path", - "description": "A string value representing the Tenant or Customer id", + "description": "A string value representing the edge id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { "type": "string" - }, - "example": "784f394c-42b6-435a-983c-b7beff2784f9" + } }, { "name": "groupType", "in": "path", - "description": "Entity Group type", + "description": "EntityGroup type", "required": true, "schema": { "type": "string", "enum": [ - "CUSTOMER", "ASSET", "DEVICE", "USER", "ENTITY_VIEW", - "DASHBOARD", - "EDGE" + "DASHBOARD" ] } }, { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "string", - "minimum": 1 - } - }, - { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", + "name": "entityGroupId", + "in": "path", + "description": "A string value representing the Entity Group Id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, - "schema": { - "type": "string", - "minimum": 0 - } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'startsWith' filter based on the entity group name.", - "required": false, "schema": { "type": "string" } - }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] - } } ], "responses": { @@ -48043,7 +47400,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataEntityInfo" + "$ref": "#/components/schemas/EntityGroup" } } } @@ -48060,7 +47417,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -48162,108 +47519,48 @@ "ApiKeyForm": [] } ] - } - }, - "/api/entityGroupInfosHierarchy/{ownerType}/{ownerId}/{groupType}": { - "get": { + }, + "delete": { "tags": [ "entity-group-controller" ], - "summary": "Get Entity Group Entity Infos for all owners starting from specified than ending with owner of current user (getEntityGroupEntityInfosHierarchyByOwnerAndTypeAndPageLink)", - "description": "Returns a page of Entity Group Entity Info objects based on the provided Owner Id and Entity Type and Page Link. Entity Info is a lightweight object that contains only id and name of the entity group. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", - "operationId": "getEntityGroupEntityInfosHierarchyByOwnerAndTypeAndPageLink", + "summary": "Unassign entity group from edge (unassignEntityGroupFromEdge)", + "description": "Clears assignment of the entity group to the edge. Unassignment works in async way - first, 'unassign' notification event pushed to edge queue on platform. Second, remote edge service will receive an 'unassign' command to remove entity group (Edge will receive this instantly, if it's currently connected, or once it's going to be connected to platform). Third, once 'unassign' command will be delivered to edge service, it's going to remove entity group and entities inside this group locally.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'WRITE' permission for the entity (entities).", + "operationId": "unassignEntityGroupFromEdge", "parameters": [ { - "name": "ownerType", - "in": "path", - "description": "Tenant or Customer", - "required": true, - "schema": { - "type": "string", - "enum": [ - "TENANT", - "CUSTOMER" - ] - } - }, - { - "name": "ownerId", + "name": "edgeId", "in": "path", - "description": "A string value representing the Tenant or Customer id", + "description": "A string value representing the edge id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { "type": "string" - }, - "example": "784f394c-42b6-435a-983c-b7beff2784f9" + } }, { "name": "groupType", "in": "path", - "description": "Entity Group type", + "description": "EntityGroup type", "required": true, "schema": { "type": "string", "enum": [ - "CUSTOMER", "ASSET", "DEVICE", "USER", "ENTITY_VIEW", - "DASHBOARD", - "EDGE" + "DASHBOARD" ] } }, { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "string", - "minimum": 1 - } - }, - { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", + "name": "entityGroupId", + "in": "path", + "description": "A string value representing the Entity Group Id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, - "schema": { - "type": "string", - "minimum": 0 - } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'startsWith' filter based on the entity group name.", - "required": false, "schema": { "type": "string" } - }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] - } } ], "responses": { @@ -48272,7 +47569,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataEntityInfo" + "$ref": "#/components/schemas/EntityGroup" } } } @@ -48393,99 +47690,31 @@ ] } }, - "/api/entityGroups/edge/{edgeId}/{groupType}": { - "get": { + "/api/entityGroup": { + "post": { "tags": [ "entity-group-controller" ], - "summary": "Get Edge Entity Groups by entity type (getEdgeEntityGroups)", - "description": "Returns a page of Entity Group Info objects based on the provided Entity Type and assigned to the provided Edge entity. Entity group allows you to group multiple entities of the same entity type (Device, Asset, Customer, User, Dashboard, etc). Entity Group always have an owner - particular Tenant or Customer. Each entity may belong to multiple groups simultaneously.Entity Group Info extends Entity Group object and adds 'ownerIds' - a list of owner ids.You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getEdgeEntityGroups", - "parameters": [ - { - "name": "edgeId", - "in": "path", - "description": "A string value representing the edge id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", - "required": true, - "schema": { - "type": "string" - } - }, - { - "name": "groupType", - "in": "path", - "description": "EntityGroup type", - "required": true, - "schema": { - "type": "string", - "enum": [ - "ASSET", - "DEVICE", - "USER", - "ENTITY_VIEW", - "DASHBOARD" - ] - } - }, - { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "string", - "minimum": 1 - } - }, - { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", - "required": true, - "schema": { - "type": "string", - "minimum": 0 - } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'startsWith' filter based on the entity group name.", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, - "schema": { - "type": "string" + "summary": "Create Or Update Entity Group (saveEntityGroup)", + "description": "Create or update the Entity Group. When creating Entity Group, platform generates Entity Group Id as [time-based UUID](https://en.wikipedia.org/wiki/Universally_unique_identifier#Version_1_(date-time_and_MAC_address)). The newly created Entity Group Id will be present in the response. Specify existing Entity Group Id to update the group. Referencing non-existing Entity Group Id will cause 'Not Found' error.Remove 'id', 'tenantId' and optionally 'ownerId' from the request body example (below) to create new Entity Group entity. When 'ownerId' is not set (or null), it defaults to the current user's owner (Tenant for tenant admins, Customer for customer users). \n\nEntity group name is unique in the scope of owner and entity type. For example, you can't create two tenant device groups called 'Water meters'. However, you may create device and asset group with the same name. And also you may create groups with the same name for two different customers of the same tenant. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'WRITE' permission for specified group.", + "operationId": "saveEntityGroup", + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/EntityGroup" + } } }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] - } - } - ], + "required": true + }, "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataEntityGroupInfo" + "$ref": "#/components/schemas/EntityGroupInfo" } } } @@ -48502,7 +47731,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -48606,25 +47835,54 @@ ] } }, - "/api/entityGroups/list": { + "/api/entityGroup/all/{ownerType}/{ownerId}/{groupType}": { "get": { "tags": [ "entity-group-controller" ], - "summary": "Get Entity Groups by Ids (getEntityGroupsByIds)", - "description": "Fetch the list of Entity Group Info objects based on the provided entity group ids list. Entity group allows you to group multiple entities of the same entity type (Device, Asset, Customer, User, Dashboard, etc). Entity Group always have an owner - particular Tenant or Customer. Each entity may belong to multiple groups simultaneously.Entity Group Info extends Entity Group object and adds 'ownerIds' - a list of owner ids.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", - "operationId": "getEntityGroupsByIds", + "summary": "Get special group All by owner and entity type (getEntityGroupsByOwnerAndType)", + "description": "Fetch reserved group 'All' based on the provided Owner Id and Entity Type. Entity group allows you to group multiple entities of the same entity type (Device, Asset, Customer, User, Dashboard, etc). Entity Group always have an owner - particular Tenant or Customer. Each entity may belong to multiple groups simultaneously.Entity Group Info extends Entity Group object and adds 'ownerIds' - a list of owner ids.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", + "operationId": "getEntityGroupAllByOwnerAndType", "parameters": [ { - "name": "entityGroupIds", - "in": "query", - "description": "A list of group ids, separated by comma ','", + "name": "ownerType", + "in": "path", + "description": "Tenant or Customer", "required": true, "schema": { - "type": "array", - "items": { - "type": "string" - } + "type": "string", + "enum": [ + "TENANT", + "CUSTOMER" + ] + } + }, + { + "name": "ownerId", + "in": "path", + "description": "A string value representing the Tenant or Customer id", + "required": true, + "schema": { + "type": "string" + }, + "example": "784f394c-42b6-435a-983c-b7beff2784f9" + }, + { + "name": "groupType", + "in": "path", + "description": "Entity Group type", + "required": true, + "schema": { + "type": "string", + "enum": [ + "CUSTOMER", + "ASSET", + "DEVICE", + "USER", + "ENTITY_VIEW", + "DASHBOARD", + "EDGE" + ] } } ], @@ -48634,10 +47892,7 @@ "content": { "application/json": { "schema": { - "type": "array", - "items": { - "$ref": "#/components/schemas/EntityGroupInfo" - } + "$ref": "#/components/schemas/EntityGroupInfo" } } } @@ -48758,37 +48013,19 @@ ] } }, - "/api/entityGroups/{entityType}/{entityId}": { + "/api/entityGroup/{entityGroupId}": { "get": { "tags": [ "entity-group-controller" ], - "summary": "Get Entity Groups by Entity Id (getEntityGroupsForEntity)", - "description": "Returns a list of groups that contain the specified Entity Id. For example, all device groups that contain specific device. The list always contain at least one element - special group 'All'.You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getEntityGroupsForEntity", + "summary": "Get Entity Group Info (getEntityGroupById)", + "description": "Fetch the Entity Group object based on the provided Entity Group Id. Entity group allows you to group multiple entities of the same entity type (Device, Asset, Customer, User, Dashboard, etc). Entity Group always have an owner - particular Tenant or Customer. Each entity may belong to multiple groups simultaneously.Entity Group Info extends Entity Group object and adds 'ownerIds' - a list of owner ids.\n\nEntity group name is unique in the scope of owner and entity type. For example, you can't create two tenant device groups called 'Water meters'. However, you may create device and asset group with the same name. And also you may create groups with the same name for two different customers of the same tenant. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", + "operationId": "getEntityGroupById", "parameters": [ { - "name": "entityType", - "in": "path", - "description": "Entity Group type", - "required": true, - "schema": { - "type": "string", - "enum": [ - "CUSTOMER", - "ASSET", - "DEVICE", - "USER", - "ENTITY_VIEW", - "DASHBOARD", - "EDGE" - ] - } - }, - { - "name": "entityId", + "name": "entityGroupId", "in": "path", - "description": "A string value representing the entity id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "description": "A string value representing the Entity Group Id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { "type": "string" @@ -48801,10 +48038,7 @@ "content": { "application/json": { "schema": { - "type": "array", - "items": { - "$ref": "#/components/schemas/EntityGroupId" - } + "$ref": "#/components/schemas/EntityGroupInfo" } } } @@ -48923,106 +48157,28 @@ "ApiKeyForm": [] } ] - } - }, - "/api/entityGroups/{groupType}": { - "get": { + }, + "delete": { "tags": [ "entity-group-controller" ], - "summary": "Get Entity Groups by entity type and page link (getEntityGroupsByTypeAndPageLink)", - "description": "Returns a page of Entity Group Info objects based on the provided Entity Type and Page Link. Entity group allows you to group multiple entities of the same entity type (Device, Asset, Customer, User, Dashboard, etc). Entity Group always have an owner - particular Tenant or Customer. Each entity may belong to multiple groups simultaneously.Entity Group Info extends Entity Group object and adds 'ownerIds' - a list of owner ids.You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", - "operationId": "getEntityGroupsByTypeAndPageLink", + "summary": "Delete Entity Group (deleteEntityGroup)", + "description": "Deletes the entity group but does not delete the entities in the group, since they are also present in reserved group 'All'. Referencing non-existing Entity Group Id will cause an error.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'DELETE' permission for specified group.", + "operationId": "deleteEntityGroup", "parameters": [ { - "name": "groupType", + "name": "entityGroupId", "in": "path", - "description": "Entity Group type", - "required": true, - "schema": { - "type": "string", - "enum": [ - "CUSTOMER", - "ASSET", - "DEVICE", - "USER", - "ENTITY_VIEW", - "DASHBOARD", - "EDGE" - ] - } - }, - { - "name": "includeShared", - "in": "query", - "description": "Whether to include shared entity groups.", - "required": false, - "schema": { - "type": "boolean" - } - }, - { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "string", - "minimum": 1 - } - }, - { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", + "description": "A string value representing the Entity Group Id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, - "schema": { - "type": "string", - "minimum": 0 - } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'startsWith' filter based on the entity group name.", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, "schema": { "type": "string" } - }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] - } } ], "responses": { "200": { - "description": "OK", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/PageDataEntityGroupInfo" - } - } - } + "description": "OK" }, "400": { "description": "Bad Request", @@ -49140,57 +48296,43 @@ ] } }, - "/api/entityGroups/{groupType}/all": { - "get": { + "/api/entityGroup/{entityGroupId}/addEntities": { + "post": { "tags": [ "entity-group-controller" ], - "summary": "Get Entity Groups by entity type (getAllEntityGroupsByType)", - "description": "Fetch the list of Entity Group Info objects based on the provided Entity Type. Entity group allows you to group multiple entities of the same entity type (Device, Asset, Customer, User, Dashboard, etc). Entity Group always have an owner - particular Tenant or Customer. Each entity may belong to multiple groups simultaneously.Entity Group Info extends Entity Group object and adds 'ownerIds' - a list of owner ids.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", - "operationId": "getAllEntityGroupsByType", + "summary": "Add entities to the group (addEntitiesToEntityGroup)", + "description": "Add entities to the specified entity group. This operation is idempotent: entities that are already members of the group are silently ignored. Entity group allows you to group multiple entities of the same entity type (Device, Asset, Customer, User, Dashboard, etc). Entity Group always have an owner - particular Tenant or Customer. Each entity may belong to multiple groups simultaneously.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'ADD_TO_GROUP' permission for specified group.", + "operationId": "addEntitiesToEntityGroup", "parameters": [ { - "name": "groupType", + "name": "entityGroupId", "in": "path", - "description": "Entity Group type", + "description": "A string value representing the Entity Group Id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { - "type": "string", - "enum": [ - "CUSTOMER", - "ASSET", - "DEVICE", - "USER", - "ENTITY_VIEW", - "DASHBOARD", - "EDGE" - ] - } - }, - { - "name": "includeShared", - "in": "query", - "description": "Whether to include shared entity groups.", - "required": false, - "schema": { - "type": "boolean" + "type": "string" } } ], - "responses": { - "200": { - "description": "OK", - "content": { - "application/json": { - "schema": { - "type": "array", - "items": { - "$ref": "#/components/schemas/EntityGroupInfo" - } + "requestBody": { + "content": { + "application/json": { + "schema": { + "type": "array", + "description": "A list of entity ids", + "items": { + "type": "string" } } } }, + "required": true + }, + "responses": { + "200": { + "description": "OK" + }, "400": { "description": "Bad Request", "content": { @@ -49203,7 +48345,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -49307,96 +48449,43 @@ ] } }, - "/api/entityGroups/{groupType}/shared": { - "get": { + "/api/entityGroup/{entityGroupId}/deleteEntities": { + "post": { "tags": [ "entity-group-controller" ], - "summary": "Get Shared Entity Groups by entity type and page link (getSharedEntityGroupsByTypeAndPageLink)", - "description": "Returns a page of Shared Entity Group Info objects based on the provided Entity Type and Page Link. Entity group allows you to group multiple entities of the same entity type (Device, Asset, Customer, User, Dashboard, etc). Entity Group always have an owner - particular Tenant or Customer. Each entity may belong to multiple groups simultaneously.Entity Group Info extends Entity Group object and adds 'ownerIds' - a list of owner ids.You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", - "operationId": "getSharedEntityGroupsByTypeAndPageLink", + "summary": "Remove entities from the group (removeEntitiesFromEntityGroup)", + "description": "Removes entities from the specified entity group. Entity group allows you to group multiple entities of the same entity type (Device, Asset, Customer, User, Dashboard, etc). Entity Group always have an owner - particular Tenant or Customer. Each entity may belong to multiple groups simultaneously.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'REMOVE_FROM_GROUP' permission for specified group.", + "operationId": "removeEntitiesFromEntityGroup", "parameters": [ { - "name": "groupType", + "name": "entityGroupId", "in": "path", - "description": "Entity Group type", - "required": true, - "schema": { - "type": "string", - "enum": [ - "CUSTOMER", - "ASSET", - "DEVICE", - "USER", - "ENTITY_VIEW", - "DASHBOARD", - "EDGE" - ] - } - }, - { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "string", - "minimum": 1 - } - }, - { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", + "description": "A string value representing the Entity Group Id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, - "schema": { - "type": "string", - "minimum": 0 - } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'startsWith' filter based on the entity group name.", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, "schema": { "type": "string" } - }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] - } } ], - "responses": { - "200": { - "description": "OK", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/PageDataEntityGroupInfo" + "requestBody": { + "content": { + "application/json": { + "schema": { + "type": "array", + "description": "A list of entity ids", + "items": { + "type": "string" } } } }, + "required": true + }, + "responses": { + "200": { + "description": "OK" + }, "400": { "description": "Bad Request", "content": { @@ -49409,7 +48498,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -49513,30 +48602,72 @@ ] } }, - "/api/entityGroups/{groupType}/shared/all": { + "/api/entityGroup/{entityGroupId}/entities": { "get": { "tags": [ "entity-group-controller" ], - "summary": "Get Shared Entity Groups by entity type (getAllSharedEntityGroups)", - "description": "Fetch the list of Shared Entity Group Info objects based on the provided Entity Type. Entity group allows you to group multiple entities of the same entity type (Device, Asset, Customer, User, Dashboard, etc). Entity Group always have an owner - particular Tenant or Customer. Each entity may belong to multiple groups simultaneously.Entity Group Info extends Entity Group object and adds 'ownerIds' - a list of owner ids.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", - "operationId": "getAllSharedEntityGroups", + "summary": "Get Group Entities (getEntities)", + "description": "Returns a page of Short Entity View objects that belongs to specified Entity Group Id. Short Entity View object contains the entity id and number of fields (attributes, telemetry, etc). List of those fields is configurable and defined in the group configuration.You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", + "operationId": "getEntities", "parameters": [ { - "name": "groupType", + "name": "entityGroupId", "in": "path", - "description": "Entity Group type", + "description": "A string value representing the Entity Group Id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, + "schema": { + "type": "string" + } + }, + { + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", "required": true, + "schema": { + "type": "string", + "minimum": 1 + } + }, + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", + "required": true, + "schema": { + "type": "string", + "minimum": 0 + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'startsWith' filter based on the entity group name.", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, "schema": { "type": "string", "enum": [ - "CUSTOMER", - "ASSET", - "DEVICE", - "USER", - "ENTITY_VIEW", - "DASHBOARD", - "EDGE" + "ASC", + "DESC" ] } } @@ -49547,10 +48678,7 @@ "content": { "application/json": { "schema": { - "type": "array", - "items": { - "$ref": "#/components/schemas/EntityGroupInfo" - } + "$ref": "#/components/schemas/PageDataShortEntityView" } } } @@ -49671,118 +48799,28 @@ ] } }, - "/api/entityGroups/{ownerType}/{ownerId}/{groupType}": { - "get": { + "/api/entityGroup/{entityGroupId}/makePrivate": { + "post": { "tags": [ "entity-group-controller" ], - "summary": "Get Entity Groups by owner and entity type and page link (getEntityGroupsByOwnerAndTypeAndPageLink)", - "description": "Returns a page of Entity Group objects based on the provided Owner Id and Entity Type and Page Link. Entity group allows you to group multiple entities of the same entity type (Device, Asset, Customer, User, Dashboard, etc). Entity Group always have an owner - particular Tenant or Customer. Each entity may belong to multiple groups simultaneously.You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", - "operationId": "getEntityGroupsByOwnerAndTypeAndPageLink", + "summary": "Make Entity Group Private (makeEntityGroupPrivate)", + "description": "Make the entity group not available for non authorized users. Every group is private by default. This call is useful to hide the group that was previously made public.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'WRITE' permission for specified group.", + "operationId": "makeEntityGroupPrivate", "parameters": [ { - "name": "ownerType", - "in": "path", - "description": "Tenant or Customer", - "required": true, - "schema": { - "type": "string", - "enum": [ - "TENANT", - "CUSTOMER" - ] - } - }, - { - "name": "ownerId", - "in": "path", - "description": "A string value representing the Tenant or Customer id", - "required": true, - "schema": { - "type": "string" - }, - "example": "784f394c-42b6-435a-983c-b7beff2784f9" - }, - { - "name": "groupType", + "name": "entityGroupId", "in": "path", - "description": "Entity Group type", - "required": true, - "schema": { - "type": "string", - "enum": [ - "CUSTOMER", - "ASSET", - "DEVICE", - "USER", - "ENTITY_VIEW", - "DASHBOARD", - "EDGE" - ] - } - }, - { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "string", - "minimum": 1 - } - }, - { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", + "description": "A string value representing the Entity Group Id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, - "schema": { - "type": "string", - "minimum": 0 - } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'startsWith' filter based on the entity group name.", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, "schema": { "type": "string" } - }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] - } } ], "responses": { "200": { - "description": "OK", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/PageDataEntityGroupInfo" - } - } - } + "description": "OK" }, "400": { "description": "Bad Request", @@ -49796,7 +48834,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -49900,70 +48938,28 @@ ] } }, - "/api/entityGroups/{ownerType}/{ownerId}/{groupType}/all": { - "get": { + "/api/entityGroup/{entityGroupId}/makePublic": { + "post": { "tags": [ "entity-group-controller" ], - "summary": "Get Entity Groups by owner and entity type (getAllEntityGroupsByOwnerAndType)", - "description": "Fetch the list of Entity Group Info objects based on the provided Owner Id and Entity Type. Entity group allows you to group multiple entities of the same entity type (Device, Asset, Customer, User, Dashboard, etc). Entity Group always have an owner - particular Tenant or Customer. Each entity may belong to multiple groups simultaneously.Entity Group Info extends Entity Group object and adds 'ownerIds' - a list of owner ids.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", - "operationId": "getAllEntityGroupsByOwnerAndType", + "summary": "Make Entity Group Publicly available (makeEntityGroupPublic)", + "description": "Make the entity group available for non authorized users. Useful for public dashboards that will be embedded into the public websites. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'WRITE' permission for specified group.", + "operationId": "makeEntityGroupPublic", "parameters": [ { - "name": "ownerType", - "in": "path", - "description": "Tenant or Customer", - "required": true, - "schema": { - "type": "string", - "enum": [ - "TENANT", - "CUSTOMER" - ] - } - }, - { - "name": "ownerId", + "name": "entityGroupId", "in": "path", - "description": "A string value representing the Tenant or Customer id", + "description": "A string value representing the Entity Group Id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { "type": "string" - }, - "example": "784f394c-42b6-435a-983c-b7beff2784f9" - }, - { - "name": "groupType", - "in": "path", - "description": "Entity Group type", - "required": true, - "schema": { - "type": "string", - "enum": [ - "CUSTOMER", - "ASSET", - "DEVICE", - "USER", - "ENTITY_VIEW", - "DASHBOARD", - "EDGE" - ] } } ], "responses": { "200": { - "description": "OK", - "content": { - "application/json": { - "schema": { - "type": "array", - "items": { - "$ref": "#/components/schemas/EntityGroupInfo" - } - } - } - } + "description": "OK" }, "400": { "description": "Bad Request", @@ -49977,7 +48973,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -50081,119 +49077,39 @@ ] } }, - "/api/entityGroupsHierarchy/{ownerType}/{ownerId}/{groupType}": { - "get": { + "/api/entityGroup/{entityGroupId}/share": { + "post": { "tags": [ "entity-group-controller" ], - "summary": "Get Entity Groups for all owners starting from specified than ending with owner of current user (getEntityGroupsHierarchyByOwnerAndTypeAndPageLink)", - "description": "Returns a page of Entity Group objects based on the provided Owner Id and Entity Type and Page Link. Entity group allows you to group multiple entities of the same entity type (Device, Asset, Customer, User, Dashboard, etc). Entity Group always have an owner - particular Tenant or Customer. Each entity may belong to multiple groups simultaneously.You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", - "operationId": "getEntityGroupsHierarchyByOwnerAndTypeAndPageLink", + "summary": "Share the Entity Group (shareEntityGroup)", + "description": "Share the entity group with certain user group based on the provided Share Group Request. The request is quite flexible and processing of the request involves multiple security checks using platform RBAC feature.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'WRITE' permission for specified group.", + "operationId": "shareEntityGroup", "parameters": [ { - "name": "ownerType", - "in": "path", - "description": "Tenant or Customer", - "required": true, - "schema": { - "type": "string", - "enum": [ - "TENANT", - "CUSTOMER" - ] - } - }, - { - "name": "ownerId", - "in": "path", - "description": "A string value representing the Tenant or Customer id", - "required": true, - "schema": { - "type": "string" - }, - "example": "784f394c-42b6-435a-983c-b7beff2784f9" - }, - { - "name": "groupType", + "name": "entityGroupId", "in": "path", - "description": "Entity Group type", - "required": true, - "schema": { - "type": "string", - "enum": [ - "CUSTOMER", - "ASSET", - "DEVICE", - "USER", - "ENTITY_VIEW", - "DASHBOARD", - "EDGE" - ] - } - }, - { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", - "required": true, - "schema": { - "type": "string", - "minimum": 1 - } - }, - { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", + "description": "A string value representing the Entity Group Id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, - "schema": { - "type": "string", - "minimum": 0 - } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'startsWith' filter based on the entity group name.", - "required": false, - "schema": { - "type": "string" - } - }, - { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, "schema": { "type": "string" } - }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] - } } ], - "responses": { - "200": { - "description": "OK", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/PageDataEntityGroupInfo" - } + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ShareGroupRequest" } } }, + "required": true + }, + "responses": { + "200": { + "description": "OK" + }, "400": { "description": "Bad Request", "content": { @@ -50206,7 +49122,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -50310,37 +49226,32 @@ ] } }, - "/api/ownerInfo/{ownerType}/{ownerId}": { + "/api/entityGroup/{entityGroupId}/{entityId}": { "get": { "tags": [ "entity-group-controller" ], - "summary": "Get Owner Info (getOwnerInfo)", - "description": "Fetch the owner info (tenant or customer) presented as Entity Info object based on the provided owner Id. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", - "operationId": "getOwnerInfo", + "summary": "Get Group Entity (getGroupEntity)", + "description": "Fetch the Short Entity View object based on the group and entity id. Short Entity View object contains the entity id and number of fields (attributes, telemetry, etc). List of those fields is configurable and defined in the group configuration.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", + "operationId": "getGroupEntity", "parameters": [ { - "name": "ownerType", + "name": "entityGroupId", "in": "path", - "description": "Tenant or Customer", + "description": "A string value representing the Entity Group Id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { - "type": "string", - "enum": [ - "TENANT", - "CUSTOMER" - ] + "type": "string" } }, { - "name": "ownerId", + "name": "entityId", "in": "path", - "description": "A string value representing the Tenant or Customer id", + "description": "A string value representing the entity id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { "type": "string" - }, - "example": "784f394c-42b6-435a-983c-b7beff2784f9" + } } ], "responses": { @@ -50349,7 +49260,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/EntityInfo" + "$ref": "#/components/schemas/ShortEntityView" } } } @@ -50470,77 +49381,46 @@ ] } }, - "/api/ownerInfos": { - "get": { + "/api/entityGroup/{entityGroupId}/{userGroupId}/{roleId}/share": { + "post": { "tags": [ "entity-group-controller" ], - "summary": "Get Owner Infos (getOwnerInfos)", - "description": "Provides a rage view of Customers that the current user has READ access to. If the current user is Tenant administrator, the result set also contains the tenant. The call is designed for the UI auto-complete component to show tenant and all possible Customers that the user may select to change the owner of the particular entity or entity group.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getOwnerInfos", + "summary": "Share the Entity Group with User group (shareEntityGroupToChildOwnerUserGroup)", + "description": "Share the entity group with specified user group using specified role. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'WRITE' permission for specified group.", + "operationId": "shareEntityGroupToChildOwnerUserGroup", "parameters": [ { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", + "name": "entityGroupId", + "in": "path", + "description": "A string value representing the Entity Group Id that you would like to share. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, "schema": { - "type": "string", - "minimum": 1 + "type": "string" } }, { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", + "name": "userGroupId", + "in": "path", + "description": "A string value representing the Entity(User) Group Id that you would like to share with. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", "required": true, - "schema": { - "type": "string", - "minimum": 0 - } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'startsWith' filter based on the entity group name.", - "required": false, "schema": { "type": "string" } }, { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, + "name": "roleId", + "in": "path", + "description": "A string value representing the Role Id that describes set of permissions you would like to share (read, write, etc). For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, "schema": { "type": "string" } - }, - { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, - "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] - } } ], "responses": { "200": { - "description": "OK", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/PageDataEntityInfo" - } - } - } + "description": "OK" }, "400": { "description": "Bad Request", @@ -50554,7 +49434,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid UUID string: 123", + "message": "Invalid request body", "errorCode": 31, "timestamp": 1609459200000 } @@ -50658,64 +49538,63 @@ ] } }, - "/api/owners": { + "/api/entityGroup/{ownerType}/{ownerId}/{groupType}/{groupName}": { "get": { "tags": [ "entity-group-controller" ], - "summary": "Get Owners (getOwners)", - "description": "Provides a rage view of Customers that the current user has READ access to. If the current user is Tenant administrator, the result set also contains the tenant. The call is designed for the UI auto-complete component to show tenant and all possible Customers that the user may select to change the owner of the particular entity or entity group.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", - "operationId": "getOwners", + "summary": "Get Entity Group by owner, type and name (getEntityGroupByOwnerAndNameAndType)", + "description": "Fetch the Entity Group object based on the provided Entity Group Id. Entity group allows you to group multiple entities of the same entity type (Device, Asset, Customer, User, Dashboard, etc). Entity Group always have an owner - particular Tenant or Customer. Each entity may belong to multiple groups simultaneously.Entity Group Info extends Entity Group object and adds 'ownerIds' - a list of owner ids.\n\nEntity group name is unique in the scope of owner and entity type. For example, you can't create two tenant device groups called 'Water meters'. However, you may create device and asset group with the same name. And also you may create groups with the same name for two different customers of the same tenant. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", + "operationId": "getEntityGroupByOwnerAndNameAndType", "parameters": [ { - "name": "pageSize", - "in": "query", - "description": "Maximum amount of entities in a one page", + "name": "ownerType", + "in": "path", + "description": "Tenant or Customer", "required": true, "schema": { "type": "string", - "minimum": 1 + "enum": [ + "TENANT", + "CUSTOMER" + ] } }, { - "name": "page", - "in": "query", - "description": "Sequence number of page starting from 0", + "name": "ownerId", + "in": "path", + "description": "A string value representing the Tenant or Customer id", "required": true, - "schema": { - "type": "string", - "minimum": 0 - } - }, - { - "name": "textSearch", - "in": "query", - "description": "The case insensitive 'startsWith' filter based on the entity group name.", - "required": false, "schema": { "type": "string" - } + }, + "example": "784f394c-42b6-435a-983c-b7beff2784f9" }, { - "name": "sortProperty", - "in": "query", - "description": "Property of entity to sort by", - "required": false, + "name": "groupType", + "in": "path", + "description": "Entity Group type", + "required": true, "schema": { - "type": "string" + "type": "string", + "enum": [ + "CUSTOMER", + "ASSET", + "DEVICE", + "USER", + "ENTITY_VIEW", + "DASHBOARD", + "EDGE" + ] } }, { - "name": "sortOrder", - "in": "query", - "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", - "required": false, + "name": "groupName", + "in": "path", + "description": "Entity Group name", + "required": true, "schema": { - "type": "string", - "enum": [ - "ASC", - "DESC" - ] + "type": "string" } } ], @@ -50725,7 +49604,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataContactBasedObject" + "$ref": "#/components/schemas/EntityGroupInfo" } } } @@ -50846,32 +49725,32 @@ ] } }, - "/api/alarmsQuery/count": { - "post": { + "/api/entityGroupInfo/{entityGroupId}": { + "get": { "tags": [ - "entity-query-controller" + "entity-group-controller" ], - "summary": "Count Alarms by Query (countAlarmsByQuery)", - "description": "Returns the number of alarms that match the query definition.", - "operationId": "countAlarmsByQuery", - "requestBody": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/AlarmCountQuery" - } + "summary": "Get Entity Group Entity Info (getEntityGroupEntityInfoById)", + "description": "Fetch the Entity Group Entity Info object based on the provided Entity Group Id. Entity Info is a lightweight object that contains only id and name of the entity group. \n\nEntity group name is unique in the scope of owner and entity type. For example, you can't create two tenant device groups called 'Water meters'. However, you may create device and asset group with the same name. And also you may create groups with the same name for two different customers of the same tenant. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", + "operationId": "getEntityGroupEntityInfoById", + "parameters": [ + { + "name": "entityGroupId", + "in": "path", + "description": "A string value representing the Entity Group Id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, + "schema": { + "type": "string" } - }, - "required": true - }, + } + ], "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "type": "integer", - "format": "int64" + "$ref": "#/components/schemas/EntityInfo" } } } @@ -50888,7 +49767,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -50992,31 +49871,38 @@ ] } }, - "/api/alarmsQuery/find": { - "post": { + "/api/entityGroupInfos": { + "get": { "tags": [ - "entity-query-controller" + "entity-group-controller" ], - "summary": "Find Alarms by Query", - "description": "This method description defines how Alarm Data Query extends the Entity Data Query. See method 'Find Entity Data by Query' first to get the info about 'Entity Data Query'.\n\n The platform will first search the entities that match the entity and key filters. Then, the platform will use 'Alarm Page Link' to filter the alarms related to those entities. Finally, platform fetch the properties of alarm that are defined in the **'alarmFields'** and combine them with the other entity, attribute and latest time series fields to return the result. \n\n See example of the alarm query below. The query will search first 100 active alarms with type 'Temperature Alarm' or 'Fire Alarm' for any device with current temperature > 0. The query will return combination of the entity fields: name of the device, device model and latest temperature reading and alarms fields: createdTime, type, severity and status: \n\n```json\n{\n \"entityFilter\": {\n \"type\": \"entityType\",\n \"resolveMultiple\": true,\n \"entityType\": \"DEVICE\"\n },\n \"pageLink\": {\n \"page\": 0,\n \"pageSize\": 100,\n \"textSearch\": null,\n \"searchPropagatedAlarms\": false,\n \"statusList\": [\n \"ACTIVE\"\n ],\n \"severityList\": [\n \"CRITICAL\",\n \"MAJOR\"\n ],\n \"typeList\": [\n \"Temperature Alarm\",\n \"Fire Alarm\"\n ],\n \"sortOrder\": {\n \"key\": {\n \"key\": \"createdTime\",\n \"type\": \"ALARM_FIELD\"\n },\n \"direction\": \"DESC\"\n },\n \"timeWindow\": 86400000\n },\n \"keyFilters\": [\n {\n \"key\": {\n \"type\": \"TIME_SERIES\",\n \"key\": \"temperature\"\n },\n \"valueType\": \"NUMERIC\",\n \"predicate\": {\n \"operation\": \"GREATER\",\n \"value\": {\n \"defaultValue\": 0,\n \"dynamicValue\": null\n },\n \"type\": \"NUMERIC\"\n }\n }\n ],\n \"alarmFields\": [\n {\n \"type\": \"ALARM_FIELD\",\n \"key\": \"createdTime\"\n },\n {\n \"type\": \"ALARM_FIELD\",\n \"key\": \"type\"\n },\n {\n \"type\": \"ALARM_FIELD\",\n \"key\": \"severity\"\n },\n {\n \"type\": \"ALARM_FIELD\",\n \"key\": \"status\"\n }\n ],\n \"entityFields\": [\n {\n \"type\": \"ENTITY_FIELD\",\n \"key\": \"name\"\n }\n ],\n \"latestValues\": [\n {\n \"type\": \"ATTRIBUTE\",\n \"key\": \"model\"\n },\n {\n \"type\": \"TIME_SERIES\",\n \"key\": \"temperature\"\n }\n ]\n}\n```", - "operationId": "findAlarmDataByQuery", - "requestBody": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/AlarmDataQuery" + "summary": "Get Entity Group Entity Infos by Ids (getEntityGroupEntityInfosByIds)", + "description": "Fetch the list of Entity Group Entity Info objects based on the provided entity group ids list. Entity Info is a lightweight object that contains only id and name of the entity group. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", + "operationId": "getEntityGroupEntityInfosByIds", + "parameters": [ + { + "name": "entityGroupIds", + "in": "query", + "description": "A list of group ids, separated by comma ','", + "required": true, + "schema": { + "type": "array", + "items": { + "type": "string" } } - }, - "required": true - }, + } + ], "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/PageDataAlarmData" + "type": "array", + "items": { + "$ref": "#/components/schemas/EntityInfo" + } } } } @@ -51033,7 +49919,7 @@ "summary": "Bad Request", "value": { "status": 400, - "message": "Invalid request body", + "message": "Invalid UUID string: 123", "errorCode": 31, "timestamp": 1609459200000 } @@ -51137,20 +50023,3643 @@ ] } }, - "/api/edqs/state": { + "/api/entityGroupInfos/{groupType}": { "get": { "tags": [ - "entity-query-controller" + "entity-group-controller" + ], + "summary": "Get Entity Group Entity Infos by entity type and page link (getEntityGroupEntityInfosByTypeAndPageLink)", + "description": "Returns a page of Entity Group Entity Info objects based on the provided Entity Type and Page Link. Entity Info is a lightweight object that contains only id and name of the entity group. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", + "operationId": "getEntityGroupEntityInfosByTypeAndPageLink", + "parameters": [ + { + "name": "groupType", + "in": "path", + "description": "Entity Group type", + "required": true, + "schema": { + "type": "string", + "enum": [ + "CUSTOMER", + "ASSET", + "DEVICE", + "USER", + "ENTITY_VIEW", + "DASHBOARD", + "EDGE" + ] + } + }, + { + "name": "includeShared", + "in": "query", + "description": "Whether to include shared entity groups.", + "required": false, + "schema": { + "type": "boolean" + } + }, + { + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", + "required": true, + "schema": { + "type": "string", + "minimum": 1 + } + }, + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", + "required": true, + "schema": { + "type": "string", + "minimum": 0 + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'startsWith' filter based on the entity group name.", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] + } + } ], - "summary": "getEdqsState", - "operationId": "getEdqsState", "responses": { "200": { "description": "OK", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/EdqsState" + "$ref": "#/components/schemas/PageDataEntityInfo" + } + } + } + }, + "400": { + "description": "Bad Request", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-400": { + "summary": "Bad Request", + "value": { + "status": 400, + "message": "Invalid UUID string: 123", + "errorCode": 31, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "401": { + "description": "Unauthorized", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-401": { + "summary": "Unauthorized", + "value": { + "status": 401, + "message": "Authentication failed", + "errorCode": 10, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "403": { + "description": "Forbidden", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-403": { + "summary": "Forbidden", + "value": { + "status": 403, + "message": "You don't have permission to perform this operation!", + "errorCode": 20, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "404": { + "description": "Not Found", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-404": { + "summary": "Not Found", + "value": { + "status": 404, + "message": "Requested item wasn't found!", + "errorCode": 32, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "429": { + "description": "Too Many Requests", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-429": { + "summary": "Too Many Requests", + "value": { + "status": 429, + "message": "Too many requests for current tenant!", + "errorCode": 33, + "timestamp": 1609459200000 + } + } + } + } + } + } + }, + "security": [ + { + "HttpLoginForm": [] + }, + { + "ApiKeyForm": [] + } + ] + } + }, + "/api/entityGroupInfos/{groupType}/shared": { + "get": { + "tags": [ + "entity-group-controller" + ], + "summary": "Get Shared Entity Group Entity Infos by entity type and page link (getSharedEntityGroupEntityInfosByTypeAndPageLink)", + "description": "Returns a page of Shared Entity Group Entity Info objects based on the provided Entity Type and Page Link. Entity Info is a lightweight object that contains only id and name of the entity group. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", + "operationId": "getSharedEntityGroupEntityInfosByTypeAndPageLink", + "parameters": [ + { + "name": "groupType", + "in": "path", + "description": "Entity Group type", + "required": true, + "schema": { + "type": "string", + "enum": [ + "CUSTOMER", + "ASSET", + "DEVICE", + "USER", + "ENTITY_VIEW", + "DASHBOARD", + "EDGE" + ] + } + }, + { + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", + "required": true, + "schema": { + "type": "string", + "minimum": 1 + } + }, + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", + "required": true, + "schema": { + "type": "string", + "minimum": 0 + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'startsWith' filter based on the entity group name.", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] + } + } + ], + "responses": { + "200": { + "description": "OK", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/PageDataEntityInfo" + } + } + } + }, + "400": { + "description": "Bad Request", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-400": { + "summary": "Bad Request", + "value": { + "status": 400, + "message": "Invalid UUID string: 123", + "errorCode": 31, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "401": { + "description": "Unauthorized", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-401": { + "summary": "Unauthorized", + "value": { + "status": 401, + "message": "Authentication failed", + "errorCode": 10, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "403": { + "description": "Forbidden", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-403": { + "summary": "Forbidden", + "value": { + "status": 403, + "message": "You don't have permission to perform this operation!", + "errorCode": 20, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "404": { + "description": "Not Found", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-404": { + "summary": "Not Found", + "value": { + "status": 404, + "message": "Requested item wasn't found!", + "errorCode": 32, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "429": { + "description": "Too Many Requests", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-429": { + "summary": "Too Many Requests", + "value": { + "status": 429, + "message": "Too many requests for current tenant!", + "errorCode": 33, + "timestamp": 1609459200000 + } + } + } + } + } + } + }, + "security": [ + { + "HttpLoginForm": [] + }, + { + "ApiKeyForm": [] + } + ] + } + }, + "/api/entityGroupInfos/{ownerType}/{ownerId}/{groupType}": { + "get": { + "tags": [ + "entity-group-controller" + ], + "summary": "Get Entity Group Entity Infos by owner and entity type and page link (getEntityGroupEntityInfosByOwnerAndTypeAndPageLink)", + "description": "Returns a page of Entity Group Entity Info objects based on the provided Owner Id and Entity Type and Page Link. Entity Info is a lightweight object that contains only id and name of the entity group. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", + "operationId": "getEntityGroupEntityInfosByOwnerAndTypeAndPageLink", + "parameters": [ + { + "name": "ownerType", + "in": "path", + "description": "Tenant or Customer", + "required": true, + "schema": { + "type": "string", + "enum": [ + "TENANT", + "CUSTOMER" + ] + } + }, + { + "name": "ownerId", + "in": "path", + "description": "A string value representing the Tenant or Customer id", + "required": true, + "schema": { + "type": "string" + }, + "example": "784f394c-42b6-435a-983c-b7beff2784f9" + }, + { + "name": "groupType", + "in": "path", + "description": "Entity Group type", + "required": true, + "schema": { + "type": "string", + "enum": [ + "CUSTOMER", + "ASSET", + "DEVICE", + "USER", + "ENTITY_VIEW", + "DASHBOARD", + "EDGE" + ] + } + }, + { + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", + "required": true, + "schema": { + "type": "string", + "minimum": 1 + } + }, + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", + "required": true, + "schema": { + "type": "string", + "minimum": 0 + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'startsWith' filter based on the entity group name.", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] + } + } + ], + "responses": { + "200": { + "description": "OK", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/PageDataEntityInfo" + } + } + } + }, + "400": { + "description": "Bad Request", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-400": { + "summary": "Bad Request", + "value": { + "status": 400, + "message": "Invalid UUID string: 123", + "errorCode": 31, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "401": { + "description": "Unauthorized", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-401": { + "summary": "Unauthorized", + "value": { + "status": 401, + "message": "Authentication failed", + "errorCode": 10, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "403": { + "description": "Forbidden", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-403": { + "summary": "Forbidden", + "value": { + "status": 403, + "message": "You don't have permission to perform this operation!", + "errorCode": 20, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "404": { + "description": "Not Found", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-404": { + "summary": "Not Found", + "value": { + "status": 404, + "message": "Requested item wasn't found!", + "errorCode": 32, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "429": { + "description": "Too Many Requests", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-429": { + "summary": "Too Many Requests", + "value": { + "status": 429, + "message": "Too many requests for current tenant!", + "errorCode": 33, + "timestamp": 1609459200000 + } + } + } + } + } + } + }, + "security": [ + { + "HttpLoginForm": [] + }, + { + "ApiKeyForm": [] + } + ] + } + }, + "/api/entityGroupInfosHierarchy/{ownerType}/{ownerId}/{groupType}": { + "get": { + "tags": [ + "entity-group-controller" + ], + "summary": "Get Entity Group Entity Infos for all owners starting from specified than ending with owner of current user (getEntityGroupEntityInfosHierarchyByOwnerAndTypeAndPageLink)", + "description": "Returns a page of Entity Group Entity Info objects based on the provided Owner Id and Entity Type and Page Link. Entity Info is a lightweight object that contains only id and name of the entity group. You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", + "operationId": "getEntityGroupEntityInfosHierarchyByOwnerAndTypeAndPageLink", + "parameters": [ + { + "name": "ownerType", + "in": "path", + "description": "Tenant or Customer", + "required": true, + "schema": { + "type": "string", + "enum": [ + "TENANT", + "CUSTOMER" + ] + } + }, + { + "name": "ownerId", + "in": "path", + "description": "A string value representing the Tenant or Customer id", + "required": true, + "schema": { + "type": "string" + }, + "example": "784f394c-42b6-435a-983c-b7beff2784f9" + }, + { + "name": "groupType", + "in": "path", + "description": "Entity Group type", + "required": true, + "schema": { + "type": "string", + "enum": [ + "CUSTOMER", + "ASSET", + "DEVICE", + "USER", + "ENTITY_VIEW", + "DASHBOARD", + "EDGE" + ] + } + }, + { + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", + "required": true, + "schema": { + "type": "string", + "minimum": 1 + } + }, + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", + "required": true, + "schema": { + "type": "string", + "minimum": 0 + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'startsWith' filter based on the entity group name.", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] + } + } + ], + "responses": { + "200": { + "description": "OK", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/PageDataEntityInfo" + } + } + } + }, + "400": { + "description": "Bad Request", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-400": { + "summary": "Bad Request", + "value": { + "status": 400, + "message": "Invalid UUID string: 123", + "errorCode": 31, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "401": { + "description": "Unauthorized", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-401": { + "summary": "Unauthorized", + "value": { + "status": 401, + "message": "Authentication failed", + "errorCode": 10, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "403": { + "description": "Forbidden", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-403": { + "summary": "Forbidden", + "value": { + "status": 403, + "message": "You don't have permission to perform this operation!", + "errorCode": 20, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "404": { + "description": "Not Found", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-404": { + "summary": "Not Found", + "value": { + "status": 404, + "message": "Requested item wasn't found!", + "errorCode": 32, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "429": { + "description": "Too Many Requests", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-429": { + "summary": "Too Many Requests", + "value": { + "status": 429, + "message": "Too many requests for current tenant!", + "errorCode": 33, + "timestamp": 1609459200000 + } + } + } + } + } + } + }, + "security": [ + { + "HttpLoginForm": [] + }, + { + "ApiKeyForm": [] + } + ] + } + }, + "/api/entityGroups/edge/{edgeId}/{groupType}": { + "get": { + "tags": [ + "entity-group-controller" + ], + "summary": "Get Edge Entity Groups by entity type (getEdgeEntityGroups)", + "description": "Returns a page of Entity Group Info objects based on the provided Entity Type and assigned to the provided Edge entity. Entity group allows you to group multiple entities of the same entity type (Device, Asset, Customer, User, Dashboard, etc). Entity Group always have an owner - particular Tenant or Customer. Each entity may belong to multiple groups simultaneously.Entity Group Info extends Entity Group object and adds 'ownerIds' - a list of owner ids.You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getEdgeEntityGroups", + "parameters": [ + { + "name": "edgeId", + "in": "path", + "description": "A string value representing the edge id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, + "schema": { + "type": "string" + } + }, + { + "name": "groupType", + "in": "path", + "description": "EntityGroup type", + "required": true, + "schema": { + "type": "string", + "enum": [ + "ASSET", + "DEVICE", + "USER", + "ENTITY_VIEW", + "DASHBOARD" + ] + } + }, + { + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", + "required": true, + "schema": { + "type": "string", + "minimum": 1 + } + }, + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", + "required": true, + "schema": { + "type": "string", + "minimum": 0 + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'startsWith' filter based on the entity group name.", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] + } + } + ], + "responses": { + "200": { + "description": "OK", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/PageDataEntityGroupInfo" + } + } + } + }, + "400": { + "description": "Bad Request", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-400": { + "summary": "Bad Request", + "value": { + "status": 400, + "message": "Invalid UUID string: 123", + "errorCode": 31, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "401": { + "description": "Unauthorized", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-401": { + "summary": "Unauthorized", + "value": { + "status": 401, + "message": "Authentication failed", + "errorCode": 10, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "403": { + "description": "Forbidden", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-403": { + "summary": "Forbidden", + "value": { + "status": 403, + "message": "You don't have permission to perform this operation!", + "errorCode": 20, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "404": { + "description": "Not Found", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-404": { + "summary": "Not Found", + "value": { + "status": 404, + "message": "Requested item wasn't found!", + "errorCode": 32, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "429": { + "description": "Too Many Requests", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-429": { + "summary": "Too Many Requests", + "value": { + "status": 429, + "message": "Too many requests for current tenant!", + "errorCode": 33, + "timestamp": 1609459200000 + } + } + } + } + } + } + }, + "security": [ + { + "HttpLoginForm": [] + }, + { + "ApiKeyForm": [] + } + ] + } + }, + "/api/entityGroups/list": { + "get": { + "tags": [ + "entity-group-controller" + ], + "summary": "Get Entity Groups by Ids (getEntityGroupsByIds)", + "description": "Fetch the list of Entity Group Info objects based on the provided entity group ids list. Entity group allows you to group multiple entities of the same entity type (Device, Asset, Customer, User, Dashboard, etc). Entity Group always have an owner - particular Tenant or Customer. Each entity may belong to multiple groups simultaneously.Entity Group Info extends Entity Group object and adds 'ownerIds' - a list of owner ids.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", + "operationId": "getEntityGroupsByIds", + "parameters": [ + { + "name": "entityGroupIds", + "in": "query", + "description": "A list of group ids, separated by comma ','", + "required": true, + "schema": { + "type": "array", + "items": { + "type": "string" + } + } + } + ], + "responses": { + "200": { + "description": "OK", + "content": { + "application/json": { + "schema": { + "type": "array", + "items": { + "$ref": "#/components/schemas/EntityGroupInfo" + } + } + } + } + }, + "400": { + "description": "Bad Request", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-400": { + "summary": "Bad Request", + "value": { + "status": 400, + "message": "Invalid UUID string: 123", + "errorCode": 31, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "401": { + "description": "Unauthorized", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-401": { + "summary": "Unauthorized", + "value": { + "status": 401, + "message": "Authentication failed", + "errorCode": 10, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "403": { + "description": "Forbidden", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-403": { + "summary": "Forbidden", + "value": { + "status": 403, + "message": "You don't have permission to perform this operation!", + "errorCode": 20, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "404": { + "description": "Not Found", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-404": { + "summary": "Not Found", + "value": { + "status": 404, + "message": "Requested item wasn't found!", + "errorCode": 32, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "429": { + "description": "Too Many Requests", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-429": { + "summary": "Too Many Requests", + "value": { + "status": 429, + "message": "Too many requests for current tenant!", + "errorCode": 33, + "timestamp": 1609459200000 + } + } + } + } + } + } + }, + "security": [ + { + "HttpLoginForm": [] + }, + { + "ApiKeyForm": [] + } + ] + } + }, + "/api/entityGroups/{entityType}/{entityId}": { + "get": { + "tags": [ + "entity-group-controller" + ], + "summary": "Get Entity Groups by Entity Id (getEntityGroupsForEntity)", + "description": "Returns a list of groups that contain the specified Entity Id. For example, all device groups that contain specific device. The list always contain at least one element - special group 'All'.You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getEntityGroupsForEntity", + "parameters": [ + { + "name": "entityType", + "in": "path", + "description": "Entity Group type", + "required": true, + "schema": { + "type": "string", + "enum": [ + "CUSTOMER", + "ASSET", + "DEVICE", + "USER", + "ENTITY_VIEW", + "DASHBOARD", + "EDGE" + ] + } + }, + { + "name": "entityId", + "in": "path", + "description": "A string value representing the entity id. For example, '784f394c-42b6-435a-983c-b7beff2784f9'", + "required": true, + "schema": { + "type": "string" + } + } + ], + "responses": { + "200": { + "description": "OK", + "content": { + "application/json": { + "schema": { + "type": "array", + "items": { + "$ref": "#/components/schemas/EntityGroupId" + } + } + } + } + }, + "400": { + "description": "Bad Request", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-400": { + "summary": "Bad Request", + "value": { + "status": 400, + "message": "Invalid UUID string: 123", + "errorCode": 31, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "401": { + "description": "Unauthorized", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-401": { + "summary": "Unauthorized", + "value": { + "status": 401, + "message": "Authentication failed", + "errorCode": 10, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "403": { + "description": "Forbidden", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-403": { + "summary": "Forbidden", + "value": { + "status": 403, + "message": "You don't have permission to perform this operation!", + "errorCode": 20, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "404": { + "description": "Not Found", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-404": { + "summary": "Not Found", + "value": { + "status": 404, + "message": "Requested item wasn't found!", + "errorCode": 32, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "429": { + "description": "Too Many Requests", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-429": { + "summary": "Too Many Requests", + "value": { + "status": 429, + "message": "Too many requests for current tenant!", + "errorCode": 33, + "timestamp": 1609459200000 + } + } + } + } + } + } + }, + "security": [ + { + "HttpLoginForm": [] + }, + { + "ApiKeyForm": [] + } + ] + } + }, + "/api/entityGroups/{groupType}": { + "get": { + "tags": [ + "entity-group-controller" + ], + "summary": "Get Entity Groups by entity type and page link (getEntityGroupsByTypeAndPageLink)", + "description": "Returns a page of Entity Group Info objects based on the provided Entity Type and Page Link. Entity group allows you to group multiple entities of the same entity type (Device, Asset, Customer, User, Dashboard, etc). Entity Group always have an owner - particular Tenant or Customer. Each entity may belong to multiple groups simultaneously.Entity Group Info extends Entity Group object and adds 'ownerIds' - a list of owner ids.You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", + "operationId": "getEntityGroupsByTypeAndPageLink", + "parameters": [ + { + "name": "groupType", + "in": "path", + "description": "Entity Group type", + "required": true, + "schema": { + "type": "string", + "enum": [ + "CUSTOMER", + "ASSET", + "DEVICE", + "USER", + "ENTITY_VIEW", + "DASHBOARD", + "EDGE" + ] + } + }, + { + "name": "includeShared", + "in": "query", + "description": "Whether to include shared entity groups.", + "required": false, + "schema": { + "type": "boolean" + } + }, + { + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", + "required": true, + "schema": { + "type": "string", + "minimum": 1 + } + }, + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", + "required": true, + "schema": { + "type": "string", + "minimum": 0 + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'startsWith' filter based on the entity group name.", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] + } + } + ], + "responses": { + "200": { + "description": "OK", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/PageDataEntityGroupInfo" + } + } + } + }, + "400": { + "description": "Bad Request", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-400": { + "summary": "Bad Request", + "value": { + "status": 400, + "message": "Invalid UUID string: 123", + "errorCode": 31, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "401": { + "description": "Unauthorized", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-401": { + "summary": "Unauthorized", + "value": { + "status": 401, + "message": "Authentication failed", + "errorCode": 10, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "403": { + "description": "Forbidden", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-403": { + "summary": "Forbidden", + "value": { + "status": 403, + "message": "You don't have permission to perform this operation!", + "errorCode": 20, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "404": { + "description": "Not Found", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-404": { + "summary": "Not Found", + "value": { + "status": 404, + "message": "Requested item wasn't found!", + "errorCode": 32, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "429": { + "description": "Too Many Requests", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-429": { + "summary": "Too Many Requests", + "value": { + "status": 429, + "message": "Too many requests for current tenant!", + "errorCode": 33, + "timestamp": 1609459200000 + } + } + } + } + } + } + }, + "security": [ + { + "HttpLoginForm": [] + }, + { + "ApiKeyForm": [] + } + ] + } + }, + "/api/entityGroups/{groupType}/all": { + "get": { + "tags": [ + "entity-group-controller" + ], + "summary": "Get Entity Groups by entity type (getAllEntityGroupsByType)", + "description": "Fetch the list of Entity Group Info objects based on the provided Entity Type. Entity group allows you to group multiple entities of the same entity type (Device, Asset, Customer, User, Dashboard, etc). Entity Group always have an owner - particular Tenant or Customer. Each entity may belong to multiple groups simultaneously.Entity Group Info extends Entity Group object and adds 'ownerIds' - a list of owner ids.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", + "operationId": "getAllEntityGroupsByType", + "parameters": [ + { + "name": "groupType", + "in": "path", + "description": "Entity Group type", + "required": true, + "schema": { + "type": "string", + "enum": [ + "CUSTOMER", + "ASSET", + "DEVICE", + "USER", + "ENTITY_VIEW", + "DASHBOARD", + "EDGE" + ] + } + }, + { + "name": "includeShared", + "in": "query", + "description": "Whether to include shared entity groups.", + "required": false, + "schema": { + "type": "boolean" + } + } + ], + "responses": { + "200": { + "description": "OK", + "content": { + "application/json": { + "schema": { + "type": "array", + "items": { + "$ref": "#/components/schemas/EntityGroupInfo" + } + } + } + } + }, + "400": { + "description": "Bad Request", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-400": { + "summary": "Bad Request", + "value": { + "status": 400, + "message": "Invalid UUID string: 123", + "errorCode": 31, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "401": { + "description": "Unauthorized", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-401": { + "summary": "Unauthorized", + "value": { + "status": 401, + "message": "Authentication failed", + "errorCode": 10, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "403": { + "description": "Forbidden", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-403": { + "summary": "Forbidden", + "value": { + "status": 403, + "message": "You don't have permission to perform this operation!", + "errorCode": 20, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "404": { + "description": "Not Found", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-404": { + "summary": "Not Found", + "value": { + "status": 404, + "message": "Requested item wasn't found!", + "errorCode": 32, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "429": { + "description": "Too Many Requests", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-429": { + "summary": "Too Many Requests", + "value": { + "status": 429, + "message": "Too many requests for current tenant!", + "errorCode": 33, + "timestamp": 1609459200000 + } + } + } + } + } + } + }, + "security": [ + { + "HttpLoginForm": [] + }, + { + "ApiKeyForm": [] + } + ] + } + }, + "/api/entityGroups/{groupType}/shared": { + "get": { + "tags": [ + "entity-group-controller" + ], + "summary": "Get Shared Entity Groups by entity type and page link (getSharedEntityGroupsByTypeAndPageLink)", + "description": "Returns a page of Shared Entity Group Info objects based on the provided Entity Type and Page Link. Entity group allows you to group multiple entities of the same entity type (Device, Asset, Customer, User, Dashboard, etc). Entity Group always have an owner - particular Tenant or Customer. Each entity may belong to multiple groups simultaneously.Entity Group Info extends Entity Group object and adds 'ownerIds' - a list of owner ids.You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", + "operationId": "getSharedEntityGroupsByTypeAndPageLink", + "parameters": [ + { + "name": "groupType", + "in": "path", + "description": "Entity Group type", + "required": true, + "schema": { + "type": "string", + "enum": [ + "CUSTOMER", + "ASSET", + "DEVICE", + "USER", + "ENTITY_VIEW", + "DASHBOARD", + "EDGE" + ] + } + }, + { + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", + "required": true, + "schema": { + "type": "string", + "minimum": 1 + } + }, + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", + "required": true, + "schema": { + "type": "string", + "minimum": 0 + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'startsWith' filter based on the entity group name.", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] + } + } + ], + "responses": { + "200": { + "description": "OK", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/PageDataEntityGroupInfo" + } + } + } + }, + "400": { + "description": "Bad Request", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-400": { + "summary": "Bad Request", + "value": { + "status": 400, + "message": "Invalid UUID string: 123", + "errorCode": 31, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "401": { + "description": "Unauthorized", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-401": { + "summary": "Unauthorized", + "value": { + "status": 401, + "message": "Authentication failed", + "errorCode": 10, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "403": { + "description": "Forbidden", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-403": { + "summary": "Forbidden", + "value": { + "status": 403, + "message": "You don't have permission to perform this operation!", + "errorCode": 20, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "404": { + "description": "Not Found", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-404": { + "summary": "Not Found", + "value": { + "status": 404, + "message": "Requested item wasn't found!", + "errorCode": 32, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "429": { + "description": "Too Many Requests", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-429": { + "summary": "Too Many Requests", + "value": { + "status": 429, + "message": "Too many requests for current tenant!", + "errorCode": 33, + "timestamp": 1609459200000 + } + } + } + } + } + } + }, + "security": [ + { + "HttpLoginForm": [] + }, + { + "ApiKeyForm": [] + } + ] + } + }, + "/api/entityGroups/{groupType}/shared/all": { + "get": { + "tags": [ + "entity-group-controller" + ], + "summary": "Get Shared Entity Groups by entity type (getAllSharedEntityGroups)", + "description": "Fetch the list of Shared Entity Group Info objects based on the provided Entity Type. Entity group allows you to group multiple entities of the same entity type (Device, Asset, Customer, User, Dashboard, etc). Entity Group always have an owner - particular Tenant or Customer. Each entity may belong to multiple groups simultaneously.Entity Group Info extends Entity Group object and adds 'ownerIds' - a list of owner ids.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", + "operationId": "getAllSharedEntityGroups", + "parameters": [ + { + "name": "groupType", + "in": "path", + "description": "Entity Group type", + "required": true, + "schema": { + "type": "string", + "enum": [ + "CUSTOMER", + "ASSET", + "DEVICE", + "USER", + "ENTITY_VIEW", + "DASHBOARD", + "EDGE" + ] + } + } + ], + "responses": { + "200": { + "description": "OK", + "content": { + "application/json": { + "schema": { + "type": "array", + "items": { + "$ref": "#/components/schemas/EntityGroupInfo" + } + } + } + } + }, + "400": { + "description": "Bad Request", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-400": { + "summary": "Bad Request", + "value": { + "status": 400, + "message": "Invalid UUID string: 123", + "errorCode": 31, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "401": { + "description": "Unauthorized", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-401": { + "summary": "Unauthorized", + "value": { + "status": 401, + "message": "Authentication failed", + "errorCode": 10, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "403": { + "description": "Forbidden", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-403": { + "summary": "Forbidden", + "value": { + "status": 403, + "message": "You don't have permission to perform this operation!", + "errorCode": 20, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "404": { + "description": "Not Found", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-404": { + "summary": "Not Found", + "value": { + "status": 404, + "message": "Requested item wasn't found!", + "errorCode": 32, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "429": { + "description": "Too Many Requests", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-429": { + "summary": "Too Many Requests", + "value": { + "status": 429, + "message": "Too many requests for current tenant!", + "errorCode": 33, + "timestamp": 1609459200000 + } + } + } + } + } + } + }, + "security": [ + { + "HttpLoginForm": [] + }, + { + "ApiKeyForm": [] + } + ] + } + }, + "/api/entityGroups/{ownerType}/{ownerId}/{groupType}": { + "get": { + "tags": [ + "entity-group-controller" + ], + "summary": "Get Entity Groups by owner and entity type and page link (getEntityGroupsByOwnerAndTypeAndPageLink)", + "description": "Returns a page of Entity Group objects based on the provided Owner Id and Entity Type and Page Link. Entity group allows you to group multiple entities of the same entity type (Device, Asset, Customer, User, Dashboard, etc). Entity Group always have an owner - particular Tenant or Customer. Each entity may belong to multiple groups simultaneously.You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", + "operationId": "getEntityGroupsByOwnerAndTypeAndPageLink", + "parameters": [ + { + "name": "ownerType", + "in": "path", + "description": "Tenant or Customer", + "required": true, + "schema": { + "type": "string", + "enum": [ + "TENANT", + "CUSTOMER" + ] + } + }, + { + "name": "ownerId", + "in": "path", + "description": "A string value representing the Tenant or Customer id", + "required": true, + "schema": { + "type": "string" + }, + "example": "784f394c-42b6-435a-983c-b7beff2784f9" + }, + { + "name": "groupType", + "in": "path", + "description": "Entity Group type", + "required": true, + "schema": { + "type": "string", + "enum": [ + "CUSTOMER", + "ASSET", + "DEVICE", + "USER", + "ENTITY_VIEW", + "DASHBOARD", + "EDGE" + ] + } + }, + { + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", + "required": true, + "schema": { + "type": "string", + "minimum": 1 + } + }, + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", + "required": true, + "schema": { + "type": "string", + "minimum": 0 + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'startsWith' filter based on the entity group name.", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] + } + } + ], + "responses": { + "200": { + "description": "OK", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/PageDataEntityGroupInfo" + } + } + } + }, + "400": { + "description": "Bad Request", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-400": { + "summary": "Bad Request", + "value": { + "status": 400, + "message": "Invalid UUID string: 123", + "errorCode": 31, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "401": { + "description": "Unauthorized", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-401": { + "summary": "Unauthorized", + "value": { + "status": 401, + "message": "Authentication failed", + "errorCode": 10, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "403": { + "description": "Forbidden", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-403": { + "summary": "Forbidden", + "value": { + "status": 403, + "message": "You don't have permission to perform this operation!", + "errorCode": 20, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "404": { + "description": "Not Found", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-404": { + "summary": "Not Found", + "value": { + "status": 404, + "message": "Requested item wasn't found!", + "errorCode": 32, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "429": { + "description": "Too Many Requests", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-429": { + "summary": "Too Many Requests", + "value": { + "status": 429, + "message": "Too many requests for current tenant!", + "errorCode": 33, + "timestamp": 1609459200000 + } + } + } + } + } + } + }, + "security": [ + { + "HttpLoginForm": [] + }, + { + "ApiKeyForm": [] + } + ] + } + }, + "/api/entityGroups/{ownerType}/{ownerId}/{groupType}/all": { + "get": { + "tags": [ + "entity-group-controller" + ], + "summary": "Get Entity Groups by owner and entity type (getAllEntityGroupsByOwnerAndType)", + "description": "Fetch the list of Entity Group Info objects based on the provided Owner Id and Entity Type. Entity group allows you to group multiple entities of the same entity type (Device, Asset, Customer, User, Dashboard, etc). Entity Group always have an owner - particular Tenant or Customer. Each entity may belong to multiple groups simultaneously.Entity Group Info extends Entity Group object and adds 'ownerIds' - a list of owner ids.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", + "operationId": "getAllEntityGroupsByOwnerAndType", + "parameters": [ + { + "name": "ownerType", + "in": "path", + "description": "Tenant or Customer", + "required": true, + "schema": { + "type": "string", + "enum": [ + "TENANT", + "CUSTOMER" + ] + } + }, + { + "name": "ownerId", + "in": "path", + "description": "A string value representing the Tenant or Customer id", + "required": true, + "schema": { + "type": "string" + }, + "example": "784f394c-42b6-435a-983c-b7beff2784f9" + }, + { + "name": "groupType", + "in": "path", + "description": "Entity Group type", + "required": true, + "schema": { + "type": "string", + "enum": [ + "CUSTOMER", + "ASSET", + "DEVICE", + "USER", + "ENTITY_VIEW", + "DASHBOARD", + "EDGE" + ] + } + } + ], + "responses": { + "200": { + "description": "OK", + "content": { + "application/json": { + "schema": { + "type": "array", + "items": { + "$ref": "#/components/schemas/EntityGroupInfo" + } + } + } + } + }, + "400": { + "description": "Bad Request", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-400": { + "summary": "Bad Request", + "value": { + "status": 400, + "message": "Invalid UUID string: 123", + "errorCode": 31, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "401": { + "description": "Unauthorized", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-401": { + "summary": "Unauthorized", + "value": { + "status": 401, + "message": "Authentication failed", + "errorCode": 10, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "403": { + "description": "Forbidden", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-403": { + "summary": "Forbidden", + "value": { + "status": 403, + "message": "You don't have permission to perform this operation!", + "errorCode": 20, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "404": { + "description": "Not Found", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-404": { + "summary": "Not Found", + "value": { + "status": 404, + "message": "Requested item wasn't found!", + "errorCode": 32, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "429": { + "description": "Too Many Requests", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-429": { + "summary": "Too Many Requests", + "value": { + "status": 429, + "message": "Too many requests for current tenant!", + "errorCode": 33, + "timestamp": 1609459200000 + } + } + } + } + } + } + }, + "security": [ + { + "HttpLoginForm": [] + }, + { + "ApiKeyForm": [] + } + ] + } + }, + "/api/entityGroupsHierarchy/{ownerType}/{ownerId}/{groupType}": { + "get": { + "tags": [ + "entity-group-controller" + ], + "summary": "Get Entity Groups for all owners starting from specified than ending with owner of current user (getEntityGroupsHierarchyByOwnerAndTypeAndPageLink)", + "description": "Returns a page of Entity Group objects based on the provided Owner Id and Entity Type and Page Link. Entity group allows you to group multiple entities of the same entity type (Device, Asset, Customer, User, Dashboard, etc). Entity Group always have an owner - particular Tenant or Customer. Each entity may belong to multiple groups simultaneously.You can specify parameters to filter the results. The result is wrapped with PageData object that allows you to iterate over result set using pagination. See response schema for more details. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", + "operationId": "getEntityGroupsHierarchyByOwnerAndTypeAndPageLink", + "parameters": [ + { + "name": "ownerType", + "in": "path", + "description": "Tenant or Customer", + "required": true, + "schema": { + "type": "string", + "enum": [ + "TENANT", + "CUSTOMER" + ] + } + }, + { + "name": "ownerId", + "in": "path", + "description": "A string value representing the Tenant or Customer id", + "required": true, + "schema": { + "type": "string" + }, + "example": "784f394c-42b6-435a-983c-b7beff2784f9" + }, + { + "name": "groupType", + "in": "path", + "description": "Entity Group type", + "required": true, + "schema": { + "type": "string", + "enum": [ + "CUSTOMER", + "ASSET", + "DEVICE", + "USER", + "ENTITY_VIEW", + "DASHBOARD", + "EDGE" + ] + } + }, + { + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", + "required": true, + "schema": { + "type": "string", + "minimum": 1 + } + }, + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", + "required": true, + "schema": { + "type": "string", + "minimum": 0 + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'startsWith' filter based on the entity group name.", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] + } + } + ], + "responses": { + "200": { + "description": "OK", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/PageDataEntityGroupInfo" + } + } + } + }, + "400": { + "description": "Bad Request", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-400": { + "summary": "Bad Request", + "value": { + "status": 400, + "message": "Invalid UUID string: 123", + "errorCode": 31, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "401": { + "description": "Unauthorized", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-401": { + "summary": "Unauthorized", + "value": { + "status": 401, + "message": "Authentication failed", + "errorCode": 10, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "403": { + "description": "Forbidden", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-403": { + "summary": "Forbidden", + "value": { + "status": 403, + "message": "You don't have permission to perform this operation!", + "errorCode": 20, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "404": { + "description": "Not Found", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-404": { + "summary": "Not Found", + "value": { + "status": 404, + "message": "Requested item wasn't found!", + "errorCode": 32, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "429": { + "description": "Too Many Requests", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-429": { + "summary": "Too Many Requests", + "value": { + "status": 429, + "message": "Too many requests for current tenant!", + "errorCode": 33, + "timestamp": 1609459200000 + } + } + } + } + } + } + }, + "security": [ + { + "HttpLoginForm": [] + }, + { + "ApiKeyForm": [] + } + ] + } + }, + "/api/ownerInfo/{ownerType}/{ownerId}": { + "get": { + "tags": [ + "entity-group-controller" + ], + "summary": "Get Owner Info (getOwnerInfo)", + "description": "Fetch the owner info (tenant or customer) presented as Entity Info object based on the provided owner Id. \n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for specified group.", + "operationId": "getOwnerInfo", + "parameters": [ + { + "name": "ownerType", + "in": "path", + "description": "Tenant or Customer", + "required": true, + "schema": { + "type": "string", + "enum": [ + "TENANT", + "CUSTOMER" + ] + } + }, + { + "name": "ownerId", + "in": "path", + "description": "A string value representing the Tenant or Customer id", + "required": true, + "schema": { + "type": "string" + }, + "example": "784f394c-42b6-435a-983c-b7beff2784f9" + } + ], + "responses": { + "200": { + "description": "OK", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/EntityInfo" + } + } + } + }, + "400": { + "description": "Bad Request", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-400": { + "summary": "Bad Request", + "value": { + "status": 400, + "message": "Invalid UUID string: 123", + "errorCode": 31, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "401": { + "description": "Unauthorized", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-401": { + "summary": "Unauthorized", + "value": { + "status": 401, + "message": "Authentication failed", + "errorCode": 10, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "403": { + "description": "Forbidden", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-403": { + "summary": "Forbidden", + "value": { + "status": 403, + "message": "You don't have permission to perform this operation!", + "errorCode": 20, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "404": { + "description": "Not Found", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-404": { + "summary": "Not Found", + "value": { + "status": 404, + "message": "Requested item wasn't found!", + "errorCode": 32, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "429": { + "description": "Too Many Requests", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-429": { + "summary": "Too Many Requests", + "value": { + "status": 429, + "message": "Too many requests for current tenant!", + "errorCode": 33, + "timestamp": 1609459200000 + } + } + } + } + } + } + }, + "security": [ + { + "HttpLoginForm": [] + }, + { + "ApiKeyForm": [] + } + ] + } + }, + "/api/ownerInfos": { + "get": { + "tags": [ + "entity-group-controller" + ], + "summary": "Get Owner Infos (getOwnerInfos)", + "description": "Provides a rage view of Customers that the current user has READ access to. If the current user is Tenant administrator, the result set also contains the tenant. The call is designed for the UI auto-complete component to show tenant and all possible Customers that the user may select to change the owner of the particular entity or entity group.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getOwnerInfos", + "parameters": [ + { + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", + "required": true, + "schema": { + "type": "string", + "minimum": 1 + } + }, + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", + "required": true, + "schema": { + "type": "string", + "minimum": 0 + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'startsWith' filter based on the entity group name.", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] + } + } + ], + "responses": { + "200": { + "description": "OK", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/PageDataEntityInfo" + } + } + } + }, + "400": { + "description": "Bad Request", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-400": { + "summary": "Bad Request", + "value": { + "status": 400, + "message": "Invalid UUID string: 123", + "errorCode": 31, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "401": { + "description": "Unauthorized", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-401": { + "summary": "Unauthorized", + "value": { + "status": 401, + "message": "Authentication failed", + "errorCode": 10, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "403": { + "description": "Forbidden", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-403": { + "summary": "Forbidden", + "value": { + "status": 403, + "message": "You don't have permission to perform this operation!", + "errorCode": 20, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "404": { + "description": "Not Found", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-404": { + "summary": "Not Found", + "value": { + "status": 404, + "message": "Requested item wasn't found!", + "errorCode": 32, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "429": { + "description": "Too Many Requests", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-429": { + "summary": "Too Many Requests", + "value": { + "status": 429, + "message": "Too many requests for current tenant!", + "errorCode": 33, + "timestamp": 1609459200000 + } + } + } + } + } + } + }, + "security": [ + { + "HttpLoginForm": [] + }, + { + "ApiKeyForm": [] + } + ] + } + }, + "/api/owners": { + "get": { + "tags": [ + "entity-group-controller" + ], + "summary": "Get Owners (getOwners)", + "description": "Provides a rage view of Customers that the current user has READ access to. If the current user is Tenant administrator, the result set also contains the tenant. The call is designed for the UI auto-complete component to show tenant and all possible Customers that the user may select to change the owner of the particular entity or entity group.\n\nAvailable for users with 'TENANT_ADMIN' or 'CUSTOMER_USER' authority. Security check is performed to verify that the user has 'READ' permission for the entity (entities).", + "operationId": "getOwners", + "parameters": [ + { + "name": "pageSize", + "in": "query", + "description": "Maximum amount of entities in a one page", + "required": true, + "schema": { + "type": "string", + "minimum": 1 + } + }, + { + "name": "page", + "in": "query", + "description": "Sequence number of page starting from 0", + "required": true, + "schema": { + "type": "string", + "minimum": 0 + } + }, + { + "name": "textSearch", + "in": "query", + "description": "The case insensitive 'startsWith' filter based on the entity group name.", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortProperty", + "in": "query", + "description": "Property of entity to sort by", + "required": false, + "schema": { + "type": "string" + } + }, + { + "name": "sortOrder", + "in": "query", + "description": "Sort order. ASC (ASCENDING) or DESC (DESCENDING)", + "required": false, + "schema": { + "type": "string", + "enum": [ + "ASC", + "DESC" + ] + } + } + ], + "responses": { + "200": { + "description": "OK", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/PageDataContactBasedObject" + } + } + } + }, + "400": { + "description": "Bad Request", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-400": { + "summary": "Bad Request", + "value": { + "status": 400, + "message": "Invalid UUID string: 123", + "errorCode": 31, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "401": { + "description": "Unauthorized", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-401": { + "summary": "Unauthorized", + "value": { + "status": 401, + "message": "Authentication failed", + "errorCode": 10, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "403": { + "description": "Forbidden", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-403": { + "summary": "Forbidden", + "value": { + "status": 403, + "message": "You don't have permission to perform this operation!", + "errorCode": 20, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "404": { + "description": "Not Found", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-404": { + "summary": "Not Found", + "value": { + "status": 404, + "message": "Requested item wasn't found!", + "errorCode": 32, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "429": { + "description": "Too Many Requests", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-429": { + "summary": "Too Many Requests", + "value": { + "status": 429, + "message": "Too many requests for current tenant!", + "errorCode": 33, + "timestamp": 1609459200000 + } + } + } + } + } + } + }, + "security": [ + { + "HttpLoginForm": [] + }, + { + "ApiKeyForm": [] + } + ] + } + }, + "/api/alarmsQuery/count": { + "post": { + "tags": [ + "entity-query-controller" + ], + "summary": "Count Alarms by Query (countAlarmsByQuery)", + "description": "Returns the number of alarms that match the query definition.", + "operationId": "countAlarmsByQuery", + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/AlarmCountQuery" + } + } + }, + "required": true + }, + "responses": { + "200": { + "description": "OK", + "content": { + "application/json": { + "schema": { + "type": "integer", + "format": "int64" + } + } + } + }, + "400": { + "description": "Bad Request", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-400": { + "summary": "Bad Request", + "value": { + "status": 400, + "message": "Invalid request body", + "errorCode": 31, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "401": { + "description": "Unauthorized", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-401": { + "summary": "Unauthorized", + "value": { + "status": 401, + "message": "Authentication failed", + "errorCode": 10, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "403": { + "description": "Forbidden", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-403": { + "summary": "Forbidden", + "value": { + "status": 403, + "message": "You don't have permission to perform this operation!", + "errorCode": 20, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "404": { + "description": "Not Found", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-404": { + "summary": "Not Found", + "value": { + "status": 404, + "message": "Requested item wasn't found!", + "errorCode": 32, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "429": { + "description": "Too Many Requests", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-429": { + "summary": "Too Many Requests", + "value": { + "status": 429, + "message": "Too many requests for current tenant!", + "errorCode": 33, + "timestamp": 1609459200000 + } + } + } + } + } + } + }, + "security": [ + { + "HttpLoginForm": [] + }, + { + "ApiKeyForm": [] + } + ] + } + }, + "/api/alarmsQuery/find": { + "post": { + "tags": [ + "entity-query-controller" + ], + "summary": "Find Alarms by Query", + "description": "This method description defines how Alarm Data Query extends the Entity Data Query. See method 'Find Entity Data by Query' first to get the info about 'Entity Data Query'.\n\n The platform will first search the entities that match the entity and key filters. Then, the platform will use 'Alarm Page Link' to filter the alarms related to those entities. Finally, platform fetch the properties of alarm that are defined in the **'alarmFields'** and combine them with the other entity, attribute and latest time series fields to return the result. \n\n See example of the alarm query below. The query will search first 100 active alarms with type 'Temperature Alarm' or 'Fire Alarm' for any device with current temperature > 0. The query will return combination of the entity fields: name of the device, device model and latest temperature reading and alarms fields: createdTime, type, severity and status: \n\n```json\n{\n \"entityFilter\": {\n \"type\": \"entityType\",\n \"resolveMultiple\": true,\n \"entityType\": \"DEVICE\"\n },\n \"pageLink\": {\n \"page\": 0,\n \"pageSize\": 100,\n \"textSearch\": null,\n \"searchPropagatedAlarms\": false,\n \"statusList\": [\n \"ACTIVE\"\n ],\n \"severityList\": [\n \"CRITICAL\",\n \"MAJOR\"\n ],\n \"typeList\": [\n \"Temperature Alarm\",\n \"Fire Alarm\"\n ],\n \"sortOrder\": {\n \"key\": {\n \"key\": \"createdTime\",\n \"type\": \"ALARM_FIELD\"\n },\n \"direction\": \"DESC\"\n },\n \"timeWindow\": 86400000\n },\n \"keyFilters\": [\n {\n \"key\": {\n \"type\": \"TIME_SERIES\",\n \"key\": \"temperature\"\n },\n \"valueType\": \"NUMERIC\",\n \"predicate\": {\n \"operation\": \"GREATER\",\n \"value\": {\n \"defaultValue\": 0,\n \"dynamicValue\": null\n },\n \"type\": \"NUMERIC\"\n }\n }\n ],\n \"alarmFields\": [\n {\n \"type\": \"ALARM_FIELD\",\n \"key\": \"createdTime\"\n },\n {\n \"type\": \"ALARM_FIELD\",\n \"key\": \"type\"\n },\n {\n \"type\": \"ALARM_FIELD\",\n \"key\": \"severity\"\n },\n {\n \"type\": \"ALARM_FIELD\",\n \"key\": \"status\"\n }\n ],\n \"entityFields\": [\n {\n \"type\": \"ENTITY_FIELD\",\n \"key\": \"name\"\n }\n ],\n \"latestValues\": [\n {\n \"type\": \"ATTRIBUTE\",\n \"key\": \"model\"\n },\n {\n \"type\": \"TIME_SERIES\",\n \"key\": \"temperature\"\n }\n ]\n}\n```", + "operationId": "findAlarmDataByQuery", + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/AlarmDataQuery" + } + } + }, + "required": true + }, + "responses": { + "200": { + "description": "OK", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/PageDataAlarmData" + } + } + } + }, + "400": { + "description": "Bad Request", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-400": { + "summary": "Bad Request", + "value": { + "status": 400, + "message": "Invalid request body", + "errorCode": 31, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "401": { + "description": "Unauthorized", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-401": { + "summary": "Unauthorized", + "value": { + "status": 401, + "message": "Authentication failed", + "errorCode": 10, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "403": { + "description": "Forbidden", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-403": { + "summary": "Forbidden", + "value": { + "status": 403, + "message": "You don't have permission to perform this operation!", + "errorCode": 20, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "404": { + "description": "Not Found", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-404": { + "summary": "Not Found", + "value": { + "status": 404, + "message": "Requested item wasn't found!", + "errorCode": 32, + "timestamp": 1609459200000 + } + } + } + } + } + }, + "429": { + "description": "Too Many Requests", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ThingsboardErrorResponse" + }, + "examples": { + "error-code-429": { + "summary": "Too Many Requests", + "value": { + "status": 429, + "message": "Too many requests for current tenant!", + "errorCode": 33, + "timestamp": 1609459200000 + } + } + } + } + } + } + }, + "security": [ + { + "HttpLoginForm": [] + }, + { + "ApiKeyForm": [] + } + ] + } + }, + "/api/edqs/state": { + "get": { + "tags": [ + "entity-query-controller" + ], + "summary": "getEdqsState", + "operationId": "getEdqsState", + "responses": { + "200": { + "description": "OK", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/EdqsState" } } } @@ -117597,7 +120106,8 @@ "EMAIL", "SMS", "ALARM", - "REPORT" + "REPORT", + "AI" ] }, "ApiKey": { @@ -118534,6 +121044,12 @@ "type": "object", "description": "Contains unique time series and attribute key names discovered from entities matching a query,\noptionally including a sample value for each key.", "properties": { + "totalEntities": { + "type": "integer", + "format": "int32", + "description": "Total number of entities that matched the query filter.", + "example": 5 + }, "entityTypes": { "type": "array", "description": "Set of entity types found among the matched entities.", @@ -118564,7 +121080,8 @@ } }, "required": [ - "entityTypes" + "entityTypes", + "totalEntities" ] }, "AwsSnsSmsProviderConfiguration": { @@ -119650,6 +122167,13 @@ "none" ] }, + "ChatType": { + "type": "string", + "enum": [ + "GENERIC", + "SOLUTION_BUILDER" + ] + }, "CheckPreProvisionedDevicesDeviceProfileProvisionConfiguration": { "allOf": [ { @@ -121717,6 +124241,11 @@ "format": "int64", "example": 10000 }, + "maxAiCredits": { + "type": "integer", + "format": "int64", + "example": 10000 + }, "tenantServerRestLimitsConfiguration": { "type": "string" }, @@ -121882,6 +124411,9 @@ "type": "integer", "format": "int64", "example": 60 + }, + "aiChatRequestsPerTenantRateLimit": { + "type": "string" } } } @@ -127378,7 +129910,8 @@ "EMAILS", "WS_SUBSCRIPTIONS", "CALCULATED_FIELD_DEBUG_EVENTS", - "TRENDZ_PUBLIC_SYNC" + "TRENDZ_PUBLIC_SYNC", + "AI_CHAT_REQUESTS" ] }, "LineSeriesSettings": { @@ -134723,6 +137256,7 @@ "REPORT_TEMPLATE", "REPORT", "AI_MODEL", + "AI", "API_KEY" ] }, @@ -136256,6 +138790,7 @@ "MOBILE" ] }, + "ServerSentEventString": {}, "ShareGroupRequest": { "type": "object", "description": "The Share Group Request JSON", @@ -137066,6 +139601,13 @@ } } }, + "SolutionStep": { + "type": "string", + "enum": [ + "INITIAL_CONFIGURATION", + "DASHBOARDS_CONFIGURATION" + ] + }, "SolutionTemplateLevel": { "type": "string", "enum": [ @@ -139828,6 +142370,14 @@ "maxReports": { "type": "integer", "format": "int64" + }, + "aiCredits": { + "type": "integer", + "format": "int64" + }, + "maxAiCredits": { + "type": "integer", + "format": "int64" } } }, diff --git a/pe/src/main/java/org/thingsboard/client/api/ThingsboardApi.java b/pe/src/main/java/org/thingsboard/client/api/ThingsboardApi.java index a4948188..7e2b810f 100644 --- a/pe/src/main/java/org/thingsboard/client/api/ThingsboardApi.java +++ b/pe/src/main/java/org/thingsboard/client/api/ThingsboardApi.java @@ -59,6 +59,7 @@ import org.thingsboard.client.model.CalculatedFieldType; import org.thingsboard.client.model.CfReprocessingValidationResult; import org.thingsboard.client.model.ChangePasswordRequest; +import org.thingsboard.client.model.ChatType; import org.thingsboard.client.model.ClaimRequest; import org.thingsboard.client.model.ComponentDescriptor; import org.thingsboard.client.model.Converter; @@ -265,6 +266,7 @@ import org.thingsboard.client.model.SolutionExportResponse; import org.thingsboard.client.model.SolutionImportResult; import org.thingsboard.client.model.SolutionInstallResponse; +import org.thingsboard.client.model.SolutionStep; import org.thingsboard.client.model.SolutionValidationResult; import org.thingsboard.client.model.SystemInfo; import org.thingsboard.client.model.TbChatRequest; @@ -2153,6 +2155,97 @@ private HttpRequest.Builder changePasswordRequestBuilder(@Nonnull ChangePassword return localVarRequestBuilder; } + /** + * chat + * + * @param solutionId (required) + * @param step (required) + * @param body (required) + * @return com.fasterxml.jackson.databind.JsonNode + * @throws ApiException if fails to make API call + */ + public com.fasterxml.jackson.databind.JsonNode chat(@Nonnull UUID solutionId, @Nonnull SolutionStep step, @Nonnull String body) throws ApiException { + ApiResponse localVarResponse = chatWithHttpInfo(solutionId, step, body, null); + return localVarResponse.getData(); + } + + /** + * chat + * + * @param solutionId (required) + * @param step (required) + * @param body (required) + * @param headers Optional headers to include in the request + * @return ApiResponse<com.fasterxml.jackson.databind.JsonNode> + * @throws ApiException if fails to make API call + */ + public ApiResponse chatWithHttpInfo(@Nonnull UUID solutionId, @Nonnull SolutionStep step, @Nonnull String body, Map headers) throws ApiException { + HttpRequest.Builder localVarRequestBuilder = chatRequestBuilder(solutionId, step, body, headers); + try { + HttpResponse localVarResponse = memberVarHttpClient.send( + localVarRequestBuilder.build(), + HttpResponse.BodyHandlers.ofInputStream()); + if (memberVarResponseInterceptor != null) { + memberVarResponseInterceptor.accept(localVarResponse); + } + InputStream localVarResponseBody = null; + try { + if (localVarResponse.statusCode()/ 100 != 2) { + throw getApiException("chat", localVarResponse); + } + localVarResponseBody = ApiClient.getResponseBody(localVarResponse); + if (localVarResponseBody == null) { + return new ApiResponse(localVarResponse.statusCode(), localVarResponse.headers().map(), null); + } + String responseBody = new String(localVarResponseBody.readAllBytes()); + com.fasterxml.jackson.databind.JsonNode responseValue = responseBody.isBlank()? null: memberVarObjectMapper.readValue(responseBody, new TypeReference() {}); + return new ApiResponse(localVarResponse.statusCode(), localVarResponse.headers().map(), responseValue); + } finally { + if (localVarResponseBody != null) { + localVarResponseBody.close(); + } + } + } catch (IOException e) { + throw new ApiException(e); + } + catch (InterruptedException e) { + Thread.currentThread().interrupt(); + throw new ApiException(e); + } + } + + private HttpRequest.Builder chatRequestBuilder(@Nonnull UUID solutionId, @Nonnull SolutionStep step, @Nonnull String body, Map headers) throws ApiException { + // verify the required parameter 'solutionId' is set + if (solutionId == null) { + throw new ApiException(400, "Missing the required parameter 'solutionId' when calling chat"); + } + // verify the required parameter 'step' is set + if (step == null) { + throw new ApiException(400, "Missing the required parameter 'step' when calling chat"); + } + // verify the required parameter 'body' is set + if (body == null) { + throw new ApiException(400, "Missing the required parameter 'body' when calling chat"); + } + HttpRequest.Builder localVarRequestBuilder = HttpRequest.newBuilder(); + String localVarPath = "/api/ai/solution/{solutionId}/{step}/chat" + .replace("{solutionId}", ApiClient.urlEncode(solutionId.toString())) + .replace("{step}", ApiClient.urlEncode(step.toString())); + localVarRequestBuilder.uri(URI.create(memberVarBaseUri + localVarPath)); + localVarRequestBuilder.header("Content-Type", "application/json"); + localVarRequestBuilder.header("Accept", "application/json"); + localVarRequestBuilder.method("POST", HttpRequest.BodyPublishers.ofString(body)); + if (memberVarReadTimeout != null) { + localVarRequestBuilder.timeout(memberVarReadTimeout); + } + // Add custom headers if provided + localVarRequestBuilder = HttpRequestBuilderExtensions.withAdditionalHeaders(localVarRequestBuilder, headers); + if (memberVarInterceptor != null) { + memberVarInterceptor.accept(localVarRequestBuilder); + } + return localVarRequestBuilder; + } + /** * Check Activate User Token (checkActivateToken) * Checks the activation token and forwards user to 'Create Password' page. If token is valid, returns '303 See Other' (redirect) response code with the correct address of 'Create Password' page and same 'activateToken' specified in the URL parameters. If token is not valid, returns '409 Conflict'. If token is expired, redirects to error page. @@ -3029,6 +3122,86 @@ private HttpRequest.Builder clearEventsRequestBuilder(@Nonnull String entityType return localVarRequestBuilder; } + /** + * clearStep + * + * @param solutionId (required) + * @param step (required) + * @throws ApiException if fails to make API call + */ + public void clearStep(@Nonnull UUID solutionId, @Nonnull SolutionStep step) throws ApiException { + clearStepWithHttpInfo(solutionId, step, null); + } + + /** + * clearStep + * + * @param solutionId (required) + * @param step (required) + * @param headers Optional headers to include in the request + * @return ApiResponse<Void> + * @throws ApiException if fails to make API call + */ + public ApiResponse clearStepWithHttpInfo(@Nonnull UUID solutionId, @Nonnull SolutionStep step, Map headers) throws ApiException { + HttpRequest.Builder localVarRequestBuilder = clearStepRequestBuilder(solutionId, step, headers); + try { + HttpResponse localVarResponse = memberVarHttpClient.send( + localVarRequestBuilder.build(), + HttpResponse.BodyHandlers.ofInputStream()); + if (memberVarResponseInterceptor != null) { + memberVarResponseInterceptor.accept(localVarResponse); + } + InputStream localVarResponseBody = null; + try { + if (localVarResponse.statusCode()/ 100 != 2) { + throw getApiException("clearStep", localVarResponse); + } + localVarResponseBody = ApiClient.getResponseBody(localVarResponse); + if (localVarResponseBody != null) { + localVarResponseBody.readAllBytes(); + } + return new ApiResponse(localVarResponse.statusCode(), localVarResponse.headers().map(), null); + } finally { + if (localVarResponseBody != null) { + localVarResponseBody.close(); + } + } + } catch (IOException e) { + throw new ApiException(e); + } + catch (InterruptedException e) { + Thread.currentThread().interrupt(); + throw new ApiException(e); + } + } + + private HttpRequest.Builder clearStepRequestBuilder(@Nonnull UUID solutionId, @Nonnull SolutionStep step, Map headers) throws ApiException { + // verify the required parameter 'solutionId' is set + if (solutionId == null) { + throw new ApiException(400, "Missing the required parameter 'solutionId' when calling clearStep"); + } + // verify the required parameter 'step' is set + if (step == null) { + throw new ApiException(400, "Missing the required parameter 'step' when calling clearStep"); + } + HttpRequest.Builder localVarRequestBuilder = HttpRequest.newBuilder(); + String localVarPath = "/api/ai/solution/{solutionId}/{step}/clear" + .replace("{solutionId}", ApiClient.urlEncode(solutionId.toString())) + .replace("{step}", ApiClient.urlEncode(step.toString())); + localVarRequestBuilder.uri(URI.create(memberVarBaseUri + localVarPath)); + localVarRequestBuilder.header("Accept", "application/json"); + localVarRequestBuilder.method("DELETE", HttpRequest.BodyPublishers.noBody()); + if (memberVarReadTimeout != null) { + localVarRequestBuilder.timeout(memberVarReadTimeout); + } + // Add custom headers if provided + localVarRequestBuilder = HttpRequestBuilderExtensions.withAdditionalHeaders(localVarRequestBuilder, headers); + if (memberVarInterceptor != null) { + memberVarInterceptor.accept(localVarRequestBuilder); + } + return localVarRequestBuilder; + } + /** * Compare entity data to version (compareEntityDataToVersion) * Returns an object with current entity data and the one at a specific version. Entity data structure is the same as stored in a repository. Available for users with 'TENANT_ADMIN' authority. @@ -3542,6 +3715,88 @@ private HttpRequest.Builder countEntitiesByQueryRequestBuilder(@Nonnull EntityCo return localVarRequestBuilder; } + /** + * createChat + * + * @param body (required) + * @return com.fasterxml.jackson.databind.JsonNode + * @throws ApiException if fails to make API call + */ + public com.fasterxml.jackson.databind.JsonNode createChat(@Nullable Object body) throws ApiException { + ApiResponse localVarResponse = createChatWithHttpInfo(body, null); + return localVarResponse.getData(); + } + + /** + * createChat + * + * @param body (required) + * @param headers Optional headers to include in the request + * @return ApiResponse<com.fasterxml.jackson.databind.JsonNode> + * @throws ApiException if fails to make API call + */ + public ApiResponse createChatWithHttpInfo(@Nullable Object body, Map headers) throws ApiException { + HttpRequest.Builder localVarRequestBuilder = createChatRequestBuilder(body, headers); + try { + HttpResponse localVarResponse = memberVarHttpClient.send( + localVarRequestBuilder.build(), + HttpResponse.BodyHandlers.ofInputStream()); + if (memberVarResponseInterceptor != null) { + memberVarResponseInterceptor.accept(localVarResponse); + } + InputStream localVarResponseBody = null; + try { + if (localVarResponse.statusCode()/ 100 != 2) { + throw getApiException("createChat", localVarResponse); + } + localVarResponseBody = ApiClient.getResponseBody(localVarResponse); + if (localVarResponseBody == null) { + return new ApiResponse(localVarResponse.statusCode(), localVarResponse.headers().map(), null); + } + String responseBody = new String(localVarResponseBody.readAllBytes()); + com.fasterxml.jackson.databind.JsonNode responseValue = responseBody.isBlank()? null: memberVarObjectMapper.readValue(responseBody, new TypeReference() {}); + return new ApiResponse(localVarResponse.statusCode(), localVarResponse.headers().map(), responseValue); + } finally { + if (localVarResponseBody != null) { + localVarResponseBody.close(); + } + } + } catch (IOException e) { + throw new ApiException(e); + } + catch (InterruptedException e) { + Thread.currentThread().interrupt(); + throw new ApiException(e); + } + } + + private HttpRequest.Builder createChatRequestBuilder(@Nullable Object body, Map headers) throws ApiException { + // verify the required parameter 'body' is set + if (body == null) { + throw new ApiException(400, "Missing the required parameter 'body' when calling createChat"); + } + HttpRequest.Builder localVarRequestBuilder = HttpRequest.newBuilder(); + String localVarPath = "/api/ai/chats"; + localVarRequestBuilder.uri(URI.create(memberVarBaseUri + localVarPath)); + localVarRequestBuilder.header("Content-Type", "application/json"); + localVarRequestBuilder.header("Accept", "application/json"); + try { + byte[] localVarPostBody = memberVarObjectMapper.writeValueAsBytes(body); + localVarRequestBuilder.method("POST", HttpRequest.BodyPublishers.ofByteArray(localVarPostBody)); + } catch (IOException e) { + throw new ApiException(e); + } + if (memberVarReadTimeout != null) { + localVarRequestBuilder.timeout(memberVarReadTimeout); + } + // Add custom headers if provided + localVarRequestBuilder = HttpRequestBuilderExtensions.withAdditionalHeaders(localVarRequestBuilder, headers); + if (memberVarInterceptor != null) { + memberVarInterceptor.accept(localVarRequestBuilder); + } + return localVarRequestBuilder; + } + /** * Create Custom Menu (createCustomMenu) * The api is designed to create Custom Menu without configuration. Is not applicable for update. Security check is performed to verify that the user has 'WRITE' permission for the custom menu with specified id. @@ -3804,6 +4059,83 @@ private HttpRequest.Builder createReportRequestBuilder(@Nullable CreateReportReq return localVarRequestBuilder; } + /** + * createSolution + * + * @param solutionId (required) + * @return com.fasterxml.jackson.databind.JsonNode + * @throws ApiException if fails to make API call + */ + public com.fasterxml.jackson.databind.JsonNode createSolution(@Nonnull UUID solutionId) throws ApiException { + ApiResponse localVarResponse = createSolutionWithHttpInfo(solutionId, null); + return localVarResponse.getData(); + } + + /** + * createSolution + * + * @param solutionId (required) + * @param headers Optional headers to include in the request + * @return ApiResponse<com.fasterxml.jackson.databind.JsonNode> + * @throws ApiException if fails to make API call + */ + public ApiResponse createSolutionWithHttpInfo(@Nonnull UUID solutionId, Map headers) throws ApiException { + HttpRequest.Builder localVarRequestBuilder = createSolutionRequestBuilder(solutionId, headers); + try { + HttpResponse localVarResponse = memberVarHttpClient.send( + localVarRequestBuilder.build(), + HttpResponse.BodyHandlers.ofInputStream()); + if (memberVarResponseInterceptor != null) { + memberVarResponseInterceptor.accept(localVarResponse); + } + InputStream localVarResponseBody = null; + try { + if (localVarResponse.statusCode()/ 100 != 2) { + throw getApiException("createSolution", localVarResponse); + } + localVarResponseBody = ApiClient.getResponseBody(localVarResponse); + if (localVarResponseBody == null) { + return new ApiResponse(localVarResponse.statusCode(), localVarResponse.headers().map(), null); + } + String responseBody = new String(localVarResponseBody.readAllBytes()); + com.fasterxml.jackson.databind.JsonNode responseValue = responseBody.isBlank()? null: memberVarObjectMapper.readValue(responseBody, new TypeReference() {}); + return new ApiResponse(localVarResponse.statusCode(), localVarResponse.headers().map(), responseValue); + } finally { + if (localVarResponseBody != null) { + localVarResponseBody.close(); + } + } + } catch (IOException e) { + throw new ApiException(e); + } + catch (InterruptedException e) { + Thread.currentThread().interrupt(); + throw new ApiException(e); + } + } + + private HttpRequest.Builder createSolutionRequestBuilder(@Nonnull UUID solutionId, Map headers) throws ApiException { + // verify the required parameter 'solutionId' is set + if (solutionId == null) { + throw new ApiException(400, "Missing the required parameter 'solutionId' when calling createSolution"); + } + HttpRequest.Builder localVarRequestBuilder = HttpRequest.newBuilder(); + String localVarPath = "/api/ai/solution/{solutionId}/create" + .replace("{solutionId}", ApiClient.urlEncode(solutionId.toString())); + localVarRequestBuilder.uri(URI.create(memberVarBaseUri + localVarPath)); + localVarRequestBuilder.header("Accept", "application/json"); + localVarRequestBuilder.method("POST", HttpRequest.BodyPublishers.noBody()); + if (memberVarReadTimeout != null) { + localVarRequestBuilder.timeout(memberVarReadTimeout); + } + // Add custom headers if provided + localVarRequestBuilder = HttpRequestBuilderExtensions.withAdditionalHeaders(localVarRequestBuilder, headers); + if (memberVarInterceptor != null) { + memberVarInterceptor.accept(localVarRequestBuilder); + } + return localVarRequestBuilder; + } + /** * Delete AI model by ID (deleteAiModelById) * Deletes the AI model record by its `id`. If a record with the specified `id` exists, the record is deleted and the endpoint returns `true`. If no such record exists, the endpoint returns `false`. Available for users with 'TENANT_ADMIN' authority. @@ -4542,6 +4874,79 @@ private HttpRequest.Builder deleteCalculatedFieldRequestBuilder(@Nonnull String return localVarRequestBuilder; } + /** + * deleteChat + * + * @param chatId (required) + * @throws ApiException if fails to make API call + */ + public void deleteChat(@Nonnull UUID chatId) throws ApiException { + deleteChatWithHttpInfo(chatId, null); + } + + /** + * deleteChat + * + * @param chatId (required) + * @param headers Optional headers to include in the request + * @return ApiResponse<Void> + * @throws ApiException if fails to make API call + */ + public ApiResponse deleteChatWithHttpInfo(@Nonnull UUID chatId, Map headers) throws ApiException { + HttpRequest.Builder localVarRequestBuilder = deleteChatRequestBuilder(chatId, headers); + try { + HttpResponse localVarResponse = memberVarHttpClient.send( + localVarRequestBuilder.build(), + HttpResponse.BodyHandlers.ofInputStream()); + if (memberVarResponseInterceptor != null) { + memberVarResponseInterceptor.accept(localVarResponse); + } + InputStream localVarResponseBody = null; + try { + if (localVarResponse.statusCode()/ 100 != 2) { + throw getApiException("deleteChat", localVarResponse); + } + localVarResponseBody = ApiClient.getResponseBody(localVarResponse); + if (localVarResponseBody != null) { + localVarResponseBody.readAllBytes(); + } + return new ApiResponse(localVarResponse.statusCode(), localVarResponse.headers().map(), null); + } finally { + if (localVarResponseBody != null) { + localVarResponseBody.close(); + } + } + } catch (IOException e) { + throw new ApiException(e); + } + catch (InterruptedException e) { + Thread.currentThread().interrupt(); + throw new ApiException(e); + } + } + + private HttpRequest.Builder deleteChatRequestBuilder(@Nonnull UUID chatId, Map headers) throws ApiException { + // verify the required parameter 'chatId' is set + if (chatId == null) { + throw new ApiException(400, "Missing the required parameter 'chatId' when calling deleteChat"); + } + HttpRequest.Builder localVarRequestBuilder = HttpRequest.newBuilder(); + String localVarPath = "/api/ai/chats/{chatId}" + .replace("{chatId}", ApiClient.urlEncode(chatId.toString())); + localVarRequestBuilder.uri(URI.create(memberVarBaseUri + localVarPath)); + localVarRequestBuilder.header("Accept", "application/json"); + localVarRequestBuilder.method("DELETE", HttpRequest.BodyPublishers.noBody()); + if (memberVarReadTimeout != null) { + localVarRequestBuilder.timeout(memberVarReadTimeout); + } + // Add custom headers if provided + localVarRequestBuilder = HttpRequestBuilderExtensions.withAdditionalHeaders(localVarRequestBuilder, headers); + if (memberVarInterceptor != null) { + memberVarInterceptor.accept(localVarRequestBuilder); + } + return localVarRequestBuilder; + } + /** * Delete OAuth2 client registration template by id (deleteClientRegistrationTemplate) Available for users with 'SYS_ADMIN' authority. * Client registration template is OAuth2 provider configuration template with default settings for registering new OAuth2 clients @@ -8111,98 +8516,25 @@ private HttpRequest.Builder deleteSecretRequestBuilder(@Nonnull UUID id, Map deleteTenantWithHttpInfo(@Nonnull String tenantId, Map headers) throws ApiException { - HttpRequest.Builder localVarRequestBuilder = deleteTenantRequestBuilder(tenantId, headers); - try { - HttpResponse localVarResponse = memberVarHttpClient.send( - localVarRequestBuilder.build(), - HttpResponse.BodyHandlers.ofInputStream()); - if (memberVarResponseInterceptor != null) { - memberVarResponseInterceptor.accept(localVarResponse); - } - InputStream localVarResponseBody = null; - try { - if (localVarResponse.statusCode()/ 100 != 2) { - throw getApiException("deleteTenant", localVarResponse); - } - localVarResponseBody = ApiClient.getResponseBody(localVarResponse); - if (localVarResponseBody != null) { - localVarResponseBody.readAllBytes(); - } - return new ApiResponse(localVarResponse.statusCode(), localVarResponse.headers().map(), null); - } finally { - if (localVarResponseBody != null) { - localVarResponseBody.close(); - } - } - } catch (IOException e) { - throw new ApiException(e); - } - catch (InterruptedException e) { - Thread.currentThread().interrupt(); - throw new ApiException(e); - } - } - - private HttpRequest.Builder deleteTenantRequestBuilder(@Nonnull String tenantId, Map headers) throws ApiException { - // verify the required parameter 'tenantId' is set - if (tenantId == null) { - throw new ApiException(400, "Missing the required parameter 'tenantId' when calling deleteTenant"); - } - HttpRequest.Builder localVarRequestBuilder = HttpRequest.newBuilder(); - String localVarPath = "/api/tenant/{tenantId}" - .replace("{tenantId}", ApiClient.urlEncode(tenantId.toString())); - localVarRequestBuilder.uri(URI.create(memberVarBaseUri + localVarPath)); - localVarRequestBuilder.header("Accept", "application/json"); - localVarRequestBuilder.method("DELETE", HttpRequest.BodyPublishers.noBody()); - if (memberVarReadTimeout != null) { - localVarRequestBuilder.timeout(memberVarReadTimeout); - } - // Add custom headers if provided - localVarRequestBuilder = HttpRequestBuilderExtensions.withAdditionalHeaders(localVarRequestBuilder, headers); - if (memberVarInterceptor != null) { - memberVarInterceptor.accept(localVarRequestBuilder); - } - return localVarRequestBuilder; - } - - /** - * Delete Tenant Profile (deleteTenantProfile) - * Deletes the tenant profile. Referencing non-existing tenant profile Id will cause an error. Referencing profile that is used by the tenants will cause an error. Available for users with 'SYS_ADMIN' authority. - * @param tenantProfileId A string value representing the tenant profile id. For example, '784f394c-42b6-435a-983c-b7beff2784f9' (required) + * deleteSolution + * + * @param solutionId (required) * @throws ApiException if fails to make API call */ - public void deleteTenantProfile(@Nonnull String tenantProfileId) throws ApiException { - deleteTenantProfileWithHttpInfo(tenantProfileId, null); + public void deleteSolution(@Nonnull UUID solutionId) throws ApiException { + deleteSolutionWithHttpInfo(solutionId, null); } /** - * Delete Tenant Profile (deleteTenantProfile) - * Deletes the tenant profile. Referencing non-existing tenant profile Id will cause an error. Referencing profile that is used by the tenants will cause an error. Available for users with 'SYS_ADMIN' authority. - * @param tenantProfileId A string value representing the tenant profile id. For example, '784f394c-42b6-435a-983c-b7beff2784f9' (required) + * deleteSolution + * + * @param solutionId (required) * @param headers Optional headers to include in the request * @return ApiResponse<Void> * @throws ApiException if fails to make API call */ - public ApiResponse deleteTenantProfileWithHttpInfo(@Nonnull String tenantProfileId, Map headers) throws ApiException { - HttpRequest.Builder localVarRequestBuilder = deleteTenantProfileRequestBuilder(tenantProfileId, headers); + public ApiResponse deleteSolutionWithHttpInfo(@Nonnull UUID solutionId, Map headers) throws ApiException { + HttpRequest.Builder localVarRequestBuilder = deleteSolutionRequestBuilder(solutionId, headers); try { HttpResponse localVarResponse = memberVarHttpClient.send( localVarRequestBuilder.build(), @@ -8213,7 +8545,7 @@ public ApiResponse deleteTenantProfileWithHttpInfo(@Nonnull String tenantP InputStream localVarResponseBody = null; try { if (localVarResponse.statusCode()/ 100 != 2) { - throw getApiException("deleteTenantProfile", localVarResponse); + throw getApiException("deleteSolution", localVarResponse); } localVarResponseBody = ApiClient.getResponseBody(localVarResponse); if (localVarResponseBody != null) { @@ -8234,14 +8566,14 @@ public ApiResponse deleteTenantProfileWithHttpInfo(@Nonnull String tenantP } } - private HttpRequest.Builder deleteTenantProfileRequestBuilder(@Nonnull String tenantProfileId, Map headers) throws ApiException { - // verify the required parameter 'tenantProfileId' is set - if (tenantProfileId == null) { - throw new ApiException(400, "Missing the required parameter 'tenantProfileId' when calling deleteTenantProfile"); + private HttpRequest.Builder deleteSolutionRequestBuilder(@Nonnull UUID solutionId, Map headers) throws ApiException { + // verify the required parameter 'solutionId' is set + if (solutionId == null) { + throw new ApiException(400, "Missing the required parameter 'solutionId' when calling deleteSolution"); } HttpRequest.Builder localVarRequestBuilder = HttpRequest.newBuilder(); - String localVarPath = "/api/tenantProfile/{tenantProfileId}" - .replace("{tenantProfileId}", ApiClient.urlEncode(tenantProfileId.toString())); + String localVarPath = "/api/ai/solution/{solutionId}" + .replace("{solutionId}", ApiClient.urlEncode(solutionId.toString())); localVarRequestBuilder.uri(URI.create(memberVarBaseUri + localVarPath)); localVarRequestBuilder.header("Accept", "application/json"); localVarRequestBuilder.method("DELETE", HttpRequest.BodyPublishers.noBody()); @@ -8257,115 +8589,25 @@ private HttpRequest.Builder deleteTenantProfileRequestBuilder(@Nonnull String te } /** - * Delete 2FA account config (deleteTwoFaAccountConfig) - * Delete 2FA config for a given 2FA provider type. Returns whole account's 2FA settings object. Available for any authorized user. - * @param providerType (required) - * @return AccountTwoFaSettings - * @throws ApiException if fails to make API call - */ - public AccountTwoFaSettings deleteTwoFaAccountConfig(@Nonnull TwoFaProviderType providerType) throws ApiException { - ApiResponse localVarResponse = deleteTwoFaAccountConfigWithHttpInfo(providerType, null); - return localVarResponse.getData(); - } - - /** - * Delete 2FA account config (deleteTwoFaAccountConfig) - * Delete 2FA config for a given 2FA provider type. Returns whole account's 2FA settings object. Available for any authorized user. - * @param providerType (required) - * @param headers Optional headers to include in the request - * @return ApiResponse<AccountTwoFaSettings> - * @throws ApiException if fails to make API call - */ - public ApiResponse deleteTwoFaAccountConfigWithHttpInfo(@Nonnull TwoFaProviderType providerType, Map headers) throws ApiException { - HttpRequest.Builder localVarRequestBuilder = deleteTwoFaAccountConfigRequestBuilder(providerType, headers); - try { - HttpResponse localVarResponse = memberVarHttpClient.send( - localVarRequestBuilder.build(), - HttpResponse.BodyHandlers.ofInputStream()); - if (memberVarResponseInterceptor != null) { - memberVarResponseInterceptor.accept(localVarResponse); - } - InputStream localVarResponseBody = null; - try { - if (localVarResponse.statusCode()/ 100 != 2) { - throw getApiException("deleteTwoFaAccountConfig", localVarResponse); - } - localVarResponseBody = ApiClient.getResponseBody(localVarResponse); - if (localVarResponseBody == null) { - return new ApiResponse(localVarResponse.statusCode(), localVarResponse.headers().map(), null); - } - String responseBody = new String(localVarResponseBody.readAllBytes()); - AccountTwoFaSettings responseValue = responseBody.isBlank()? null: memberVarObjectMapper.readValue(responseBody, new TypeReference() {}); - return new ApiResponse(localVarResponse.statusCode(), localVarResponse.headers().map(), responseValue); - } finally { - if (localVarResponseBody != null) { - localVarResponseBody.close(); - } - } - } catch (IOException e) { - throw new ApiException(e); - } - catch (InterruptedException e) { - Thread.currentThread().interrupt(); - throw new ApiException(e); - } - } - - private HttpRequest.Builder deleteTwoFaAccountConfigRequestBuilder(@Nonnull TwoFaProviderType providerType, Map headers) throws ApiException { - // verify the required parameter 'providerType' is set - if (providerType == null) { - throw new ApiException(400, "Missing the required parameter 'providerType' when calling deleteTwoFaAccountConfig"); - } - HttpRequest.Builder localVarRequestBuilder = HttpRequest.newBuilder(); - String localVarPath = "/api/2fa/account/config"; - List localVarQueryParams = new ArrayList<>(); - StringJoiner localVarQueryStringJoiner = new StringJoiner("&"); - String localVarQueryParameterBaseName; - localVarQueryParameterBaseName = "providerType"; - localVarQueryParams.addAll(ApiClient.parameterToPairs("providerType", providerType)); - if (!localVarQueryParams.isEmpty() || localVarQueryStringJoiner.length() != 0) { - StringJoiner queryJoiner = new StringJoiner("&"); - localVarQueryParams.forEach(p -> queryJoiner.add(p.getName() + '=' + p.getValue())); - if (localVarQueryStringJoiner.length() != 0) { - queryJoiner.add(localVarQueryStringJoiner.toString()); - } - localVarRequestBuilder.uri(URI.create(memberVarBaseUri + localVarPath + '?' + queryJoiner.toString())); - } else { - localVarRequestBuilder.uri(URI.create(memberVarBaseUri + localVarPath)); - } - localVarRequestBuilder.header("Accept", "application/json"); - localVarRequestBuilder.method("DELETE", HttpRequest.BodyPublishers.noBody()); - if (memberVarReadTimeout != null) { - localVarRequestBuilder.timeout(memberVarReadTimeout); - } - // Add custom headers if provided - localVarRequestBuilder = HttpRequestBuilderExtensions.withAdditionalHeaders(localVarRequestBuilder, headers); - if (memberVarInterceptor != null) { - memberVarInterceptor.accept(localVarRequestBuilder); - } - return localVarRequestBuilder; - } - - /** - * Delete User (deleteUser) - * Deletes the User, it's credentials and all the relations (from and to the User). Referencing non-existing User Id will cause an error. Security check is performed to verify that the user has 'DELETE' permission for the entity (entities). - * @param userId A string value representing the user id. For example, '784f394c-42b6-435a-983c-b7beff2784f9' (required) + * Delete Tenant (deleteTenant) + * Deletes the tenant, it's customers, rule chains, devices and all other related entities. Referencing non-existing tenant Id will cause an error. Available for users with 'SYS_ADMIN' or 'TENANT_ADMIN' authority. + * @param tenantId A string value representing the tenant id. For example, '784f394c-42b6-435a-983c-b7beff2784f9' (required) * @throws ApiException if fails to make API call */ - public void deleteUser(@Nonnull String userId) throws ApiException { - deleteUserWithHttpInfo(userId, null); + public void deleteTenant(@Nonnull String tenantId) throws ApiException { + deleteTenantWithHttpInfo(tenantId, null); } /** - * Delete User (deleteUser) - * Deletes the User, it's credentials and all the relations (from and to the User). Referencing non-existing User Id will cause an error. Security check is performed to verify that the user has 'DELETE' permission for the entity (entities). - * @param userId A string value representing the user id. For example, '784f394c-42b6-435a-983c-b7beff2784f9' (required) + * Delete Tenant (deleteTenant) + * Deletes the tenant, it's customers, rule chains, devices and all other related entities. Referencing non-existing tenant Id will cause an error. Available for users with 'SYS_ADMIN' or 'TENANT_ADMIN' authority. + * @param tenantId A string value representing the tenant id. For example, '784f394c-42b6-435a-983c-b7beff2784f9' (required) * @param headers Optional headers to include in the request * @return ApiResponse<Void> * @throws ApiException if fails to make API call */ - public ApiResponse deleteUserWithHttpInfo(@Nonnull String userId, Map headers) throws ApiException { - HttpRequest.Builder localVarRequestBuilder = deleteUserRequestBuilder(userId, headers); + public ApiResponse deleteTenantWithHttpInfo(@Nonnull String tenantId, Map headers) throws ApiException { + HttpRequest.Builder localVarRequestBuilder = deleteTenantRequestBuilder(tenantId, headers); try { HttpResponse localVarResponse = memberVarHttpClient.send( localVarRequestBuilder.build(), @@ -8376,7 +8618,243 @@ public ApiResponse deleteUserWithHttpInfo(@Nonnull String userId, Map(localVarResponse.statusCode(), localVarResponse.headers().map(), null); + } finally { + if (localVarResponseBody != null) { + localVarResponseBody.close(); + } + } + } catch (IOException e) { + throw new ApiException(e); + } + catch (InterruptedException e) { + Thread.currentThread().interrupt(); + throw new ApiException(e); + } + } + + private HttpRequest.Builder deleteTenantRequestBuilder(@Nonnull String tenantId, Map headers) throws ApiException { + // verify the required parameter 'tenantId' is set + if (tenantId == null) { + throw new ApiException(400, "Missing the required parameter 'tenantId' when calling deleteTenant"); + } + HttpRequest.Builder localVarRequestBuilder = HttpRequest.newBuilder(); + String localVarPath = "/api/tenant/{tenantId}" + .replace("{tenantId}", ApiClient.urlEncode(tenantId.toString())); + localVarRequestBuilder.uri(URI.create(memberVarBaseUri + localVarPath)); + localVarRequestBuilder.header("Accept", "application/json"); + localVarRequestBuilder.method("DELETE", HttpRequest.BodyPublishers.noBody()); + if (memberVarReadTimeout != null) { + localVarRequestBuilder.timeout(memberVarReadTimeout); + } + // Add custom headers if provided + localVarRequestBuilder = HttpRequestBuilderExtensions.withAdditionalHeaders(localVarRequestBuilder, headers); + if (memberVarInterceptor != null) { + memberVarInterceptor.accept(localVarRequestBuilder); + } + return localVarRequestBuilder; + } + + /** + * Delete Tenant Profile (deleteTenantProfile) + * Deletes the tenant profile. Referencing non-existing tenant profile Id will cause an error. Referencing profile that is used by the tenants will cause an error. Available for users with 'SYS_ADMIN' authority. + * @param tenantProfileId A string value representing the tenant profile id. For example, '784f394c-42b6-435a-983c-b7beff2784f9' (required) + * @throws ApiException if fails to make API call + */ + public void deleteTenantProfile(@Nonnull String tenantProfileId) throws ApiException { + deleteTenantProfileWithHttpInfo(tenantProfileId, null); + } + + /** + * Delete Tenant Profile (deleteTenantProfile) + * Deletes the tenant profile. Referencing non-existing tenant profile Id will cause an error. Referencing profile that is used by the tenants will cause an error. Available for users with 'SYS_ADMIN' authority. + * @param tenantProfileId A string value representing the tenant profile id. For example, '784f394c-42b6-435a-983c-b7beff2784f9' (required) + * @param headers Optional headers to include in the request + * @return ApiResponse<Void> + * @throws ApiException if fails to make API call + */ + public ApiResponse deleteTenantProfileWithHttpInfo(@Nonnull String tenantProfileId, Map headers) throws ApiException { + HttpRequest.Builder localVarRequestBuilder = deleteTenantProfileRequestBuilder(tenantProfileId, headers); + try { + HttpResponse localVarResponse = memberVarHttpClient.send( + localVarRequestBuilder.build(), + HttpResponse.BodyHandlers.ofInputStream()); + if (memberVarResponseInterceptor != null) { + memberVarResponseInterceptor.accept(localVarResponse); + } + InputStream localVarResponseBody = null; + try { + if (localVarResponse.statusCode()/ 100 != 2) { + throw getApiException("deleteTenantProfile", localVarResponse); + } + localVarResponseBody = ApiClient.getResponseBody(localVarResponse); + if (localVarResponseBody != null) { + localVarResponseBody.readAllBytes(); + } + return new ApiResponse(localVarResponse.statusCode(), localVarResponse.headers().map(), null); + } finally { + if (localVarResponseBody != null) { + localVarResponseBody.close(); + } + } + } catch (IOException e) { + throw new ApiException(e); + } + catch (InterruptedException e) { + Thread.currentThread().interrupt(); + throw new ApiException(e); + } + } + + private HttpRequest.Builder deleteTenantProfileRequestBuilder(@Nonnull String tenantProfileId, Map headers) throws ApiException { + // verify the required parameter 'tenantProfileId' is set + if (tenantProfileId == null) { + throw new ApiException(400, "Missing the required parameter 'tenantProfileId' when calling deleteTenantProfile"); + } + HttpRequest.Builder localVarRequestBuilder = HttpRequest.newBuilder(); + String localVarPath = "/api/tenantProfile/{tenantProfileId}" + .replace("{tenantProfileId}", ApiClient.urlEncode(tenantProfileId.toString())); + localVarRequestBuilder.uri(URI.create(memberVarBaseUri + localVarPath)); + localVarRequestBuilder.header("Accept", "application/json"); + localVarRequestBuilder.method("DELETE", HttpRequest.BodyPublishers.noBody()); + if (memberVarReadTimeout != null) { + localVarRequestBuilder.timeout(memberVarReadTimeout); + } + // Add custom headers if provided + localVarRequestBuilder = HttpRequestBuilderExtensions.withAdditionalHeaders(localVarRequestBuilder, headers); + if (memberVarInterceptor != null) { + memberVarInterceptor.accept(localVarRequestBuilder); + } + return localVarRequestBuilder; + } + + /** + * Delete 2FA account config (deleteTwoFaAccountConfig) + * Delete 2FA config for a given 2FA provider type. Returns whole account's 2FA settings object. Available for any authorized user. + * @param providerType (required) + * @return AccountTwoFaSettings + * @throws ApiException if fails to make API call + */ + public AccountTwoFaSettings deleteTwoFaAccountConfig(@Nonnull TwoFaProviderType providerType) throws ApiException { + ApiResponse localVarResponse = deleteTwoFaAccountConfigWithHttpInfo(providerType, null); + return localVarResponse.getData(); + } + + /** + * Delete 2FA account config (deleteTwoFaAccountConfig) + * Delete 2FA config for a given 2FA provider type. Returns whole account's 2FA settings object. Available for any authorized user. + * @param providerType (required) + * @param headers Optional headers to include in the request + * @return ApiResponse<AccountTwoFaSettings> + * @throws ApiException if fails to make API call + */ + public ApiResponse deleteTwoFaAccountConfigWithHttpInfo(@Nonnull TwoFaProviderType providerType, Map headers) throws ApiException { + HttpRequest.Builder localVarRequestBuilder = deleteTwoFaAccountConfigRequestBuilder(providerType, headers); + try { + HttpResponse localVarResponse = memberVarHttpClient.send( + localVarRequestBuilder.build(), + HttpResponse.BodyHandlers.ofInputStream()); + if (memberVarResponseInterceptor != null) { + memberVarResponseInterceptor.accept(localVarResponse); + } + InputStream localVarResponseBody = null; + try { + if (localVarResponse.statusCode()/ 100 != 2) { + throw getApiException("deleteTwoFaAccountConfig", localVarResponse); + } + localVarResponseBody = ApiClient.getResponseBody(localVarResponse); + if (localVarResponseBody == null) { + return new ApiResponse(localVarResponse.statusCode(), localVarResponse.headers().map(), null); + } + String responseBody = new String(localVarResponseBody.readAllBytes()); + AccountTwoFaSettings responseValue = responseBody.isBlank()? null: memberVarObjectMapper.readValue(responseBody, new TypeReference() {}); + return new ApiResponse(localVarResponse.statusCode(), localVarResponse.headers().map(), responseValue); + } finally { + if (localVarResponseBody != null) { + localVarResponseBody.close(); + } + } + } catch (IOException e) { + throw new ApiException(e); + } + catch (InterruptedException e) { + Thread.currentThread().interrupt(); + throw new ApiException(e); + } + } + + private HttpRequest.Builder deleteTwoFaAccountConfigRequestBuilder(@Nonnull TwoFaProviderType providerType, Map headers) throws ApiException { + // verify the required parameter 'providerType' is set + if (providerType == null) { + throw new ApiException(400, "Missing the required parameter 'providerType' when calling deleteTwoFaAccountConfig"); + } + HttpRequest.Builder localVarRequestBuilder = HttpRequest.newBuilder(); + String localVarPath = "/api/2fa/account/config"; + List localVarQueryParams = new ArrayList<>(); + StringJoiner localVarQueryStringJoiner = new StringJoiner("&"); + String localVarQueryParameterBaseName; + localVarQueryParameterBaseName = "providerType"; + localVarQueryParams.addAll(ApiClient.parameterToPairs("providerType", providerType)); + if (!localVarQueryParams.isEmpty() || localVarQueryStringJoiner.length() != 0) { + StringJoiner queryJoiner = new StringJoiner("&"); + localVarQueryParams.forEach(p -> queryJoiner.add(p.getName() + '=' + p.getValue())); + if (localVarQueryStringJoiner.length() != 0) { + queryJoiner.add(localVarQueryStringJoiner.toString()); + } + localVarRequestBuilder.uri(URI.create(memberVarBaseUri + localVarPath + '?' + queryJoiner.toString())); + } else { + localVarRequestBuilder.uri(URI.create(memberVarBaseUri + localVarPath)); + } + localVarRequestBuilder.header("Accept", "application/json"); + localVarRequestBuilder.method("DELETE", HttpRequest.BodyPublishers.noBody()); + if (memberVarReadTimeout != null) { + localVarRequestBuilder.timeout(memberVarReadTimeout); + } + // Add custom headers if provided + localVarRequestBuilder = HttpRequestBuilderExtensions.withAdditionalHeaders(localVarRequestBuilder, headers); + if (memberVarInterceptor != null) { + memberVarInterceptor.accept(localVarRequestBuilder); + } + return localVarRequestBuilder; + } + + /** + * Delete User (deleteUser) + * Deletes the User, it's credentials and all the relations (from and to the User). Referencing non-existing User Id will cause an error. Security check is performed to verify that the user has 'DELETE' permission for the entity (entities). + * @param userId A string value representing the user id. For example, '784f394c-42b6-435a-983c-b7beff2784f9' (required) + * @throws ApiException if fails to make API call + */ + public void deleteUser(@Nonnull String userId) throws ApiException { + deleteUserWithHttpInfo(userId, null); + } + + /** + * Delete User (deleteUser) + * Deletes the User, it's credentials and all the relations (from and to the User). Referencing non-existing User Id will cause an error. Security check is performed to verify that the user has 'DELETE' permission for the entity (entities). + * @param userId A string value representing the user id. For example, '784f394c-42b6-435a-983c-b7beff2784f9' (required) + * @param headers Optional headers to include in the request + * @return ApiResponse<Void> + * @throws ApiException if fails to make API call + */ + public ApiResponse deleteUserWithHttpInfo(@Nonnull String userId, Map headers) throws ApiException { + HttpRequest.Builder localVarRequestBuilder = deleteUserRequestBuilder(userId, headers); + try { + HttpResponse localVarResponse = memberVarHttpClient.send( + localVarRequestBuilder.build(), + HttpResponse.BodyHandlers.ofInputStream()); + if (memberVarResponseInterceptor != null) { + memberVarResponseInterceptor.accept(localVarResponse); + } + InputStream localVarResponseBody = null; + try { + if (localVarResponse.statusCode()/ 100 != 2) { + throw getApiException("deleteUser", localVarResponse); } localVarResponseBody = ApiClient.getResponseBody(localVarResponse); if (localVarResponseBody != null) { @@ -20238,6 +20716,83 @@ private HttpRequest.Builder getCalculatedFieldsByEntityIdRequestBuilder(@Nonnull return localVarRequestBuilder; } + /** + * getChatMessages + * + * @param chatId (required) + * @return com.fasterxml.jackson.databind.JsonNode + * @throws ApiException if fails to make API call + */ + public com.fasterxml.jackson.databind.JsonNode getChatMessages(@Nonnull UUID chatId) throws ApiException { + ApiResponse localVarResponse = getChatMessagesWithHttpInfo(chatId, null); + return localVarResponse.getData(); + } + + /** + * getChatMessages + * + * @param chatId (required) + * @param headers Optional headers to include in the request + * @return ApiResponse<com.fasterxml.jackson.databind.JsonNode> + * @throws ApiException if fails to make API call + */ + public ApiResponse getChatMessagesWithHttpInfo(@Nonnull UUID chatId, Map headers) throws ApiException { + HttpRequest.Builder localVarRequestBuilder = getChatMessagesRequestBuilder(chatId, headers); + try { + HttpResponse localVarResponse = memberVarHttpClient.send( + localVarRequestBuilder.build(), + HttpResponse.BodyHandlers.ofInputStream()); + if (memberVarResponseInterceptor != null) { + memberVarResponseInterceptor.accept(localVarResponse); + } + InputStream localVarResponseBody = null; + try { + if (localVarResponse.statusCode()/ 100 != 2) { + throw getApiException("getChatMessages", localVarResponse); + } + localVarResponseBody = ApiClient.getResponseBody(localVarResponse); + if (localVarResponseBody == null) { + return new ApiResponse(localVarResponse.statusCode(), localVarResponse.headers().map(), null); + } + String responseBody = new String(localVarResponseBody.readAllBytes()); + com.fasterxml.jackson.databind.JsonNode responseValue = responseBody.isBlank()? null: memberVarObjectMapper.readValue(responseBody, new TypeReference() {}); + return new ApiResponse(localVarResponse.statusCode(), localVarResponse.headers().map(), responseValue); + } finally { + if (localVarResponseBody != null) { + localVarResponseBody.close(); + } + } + } catch (IOException e) { + throw new ApiException(e); + } + catch (InterruptedException e) { + Thread.currentThread().interrupt(); + throw new ApiException(e); + } + } + + private HttpRequest.Builder getChatMessagesRequestBuilder(@Nonnull UUID chatId, Map headers) throws ApiException { + // verify the required parameter 'chatId' is set + if (chatId == null) { + throw new ApiException(400, "Missing the required parameter 'chatId' when calling getChatMessages"); + } + HttpRequest.Builder localVarRequestBuilder = HttpRequest.newBuilder(); + String localVarPath = "/api/ai/chats/{chatId}/messages" + .replace("{chatId}", ApiClient.urlEncode(chatId.toString())); + localVarRequestBuilder.uri(URI.create(memberVarBaseUri + localVarPath)); + localVarRequestBuilder.header("Accept", "application/json"); + localVarRequestBuilder.method("GET", HttpRequest.BodyPublishers.noBody()); + if (memberVarReadTimeout != null) { + localVarRequestBuilder.timeout(memberVarReadTimeout); + } + // Add custom headers if provided + localVarRequestBuilder = HttpRequestBuilderExtensions.withAdditionalHeaders(localVarRequestBuilder, headers); + if (memberVarInterceptor != null) { + memberVarInterceptor.accept(localVarRequestBuilder); + } + return localVarRequestBuilder; + } + /** * Get Component Descriptor (getComponentDescriptorByClazz) * Gets the Component Descriptor object using class name from the path parameters. Each Component Descriptor represents configuration of specific rule node (e.g. 'Save Timeseries' or 'Send Email'.). The Component Descriptors are used by the rule chain Web UI to build the configuration forms for the rule nodes. The Component Descriptors are discovered at runtime by scanning the class path and searching for @RuleNode annotation. Once discovered, the up to date list of descriptors is persisted to the database. Available for users with 'SYS_ADMIN' or 'TENANT_ADMIN' authority. @@ -40485,6 +41040,83 @@ private HttpRequest.Builder getSignUpSelfRegistrationParamsRequestBuilder(@Nulla return localVarRequestBuilder; } + /** + * getSolution + * + * @param solutionId (required) + * @return com.fasterxml.jackson.databind.JsonNode + * @throws ApiException if fails to make API call + */ + public com.fasterxml.jackson.databind.JsonNode getSolution(@Nonnull UUID solutionId) throws ApiException { + ApiResponse localVarResponse = getSolutionWithHttpInfo(solutionId, null); + return localVarResponse.getData(); + } + + /** + * getSolution + * + * @param solutionId (required) + * @param headers Optional headers to include in the request + * @return ApiResponse<com.fasterxml.jackson.databind.JsonNode> + * @throws ApiException if fails to make API call + */ + public ApiResponse getSolutionWithHttpInfo(@Nonnull UUID solutionId, Map headers) throws ApiException { + HttpRequest.Builder localVarRequestBuilder = getSolutionRequestBuilder(solutionId, headers); + try { + HttpResponse localVarResponse = memberVarHttpClient.send( + localVarRequestBuilder.build(), + HttpResponse.BodyHandlers.ofInputStream()); + if (memberVarResponseInterceptor != null) { + memberVarResponseInterceptor.accept(localVarResponse); + } + InputStream localVarResponseBody = null; + try { + if (localVarResponse.statusCode()/ 100 != 2) { + throw getApiException("getSolution", localVarResponse); + } + localVarResponseBody = ApiClient.getResponseBody(localVarResponse); + if (localVarResponseBody == null) { + return new ApiResponse(localVarResponse.statusCode(), localVarResponse.headers().map(), null); + } + String responseBody = new String(localVarResponseBody.readAllBytes()); + com.fasterxml.jackson.databind.JsonNode responseValue = responseBody.isBlank()? null: memberVarObjectMapper.readValue(responseBody, new TypeReference() {}); + return new ApiResponse(localVarResponse.statusCode(), localVarResponse.headers().map(), responseValue); + } finally { + if (localVarResponseBody != null) { + localVarResponseBody.close(); + } + } + } catch (IOException e) { + throw new ApiException(e); + } + catch (InterruptedException e) { + Thread.currentThread().interrupt(); + throw new ApiException(e); + } + } + + private HttpRequest.Builder getSolutionRequestBuilder(@Nonnull UUID solutionId, Map headers) throws ApiException { + // verify the required parameter 'solutionId' is set + if (solutionId == null) { + throw new ApiException(400, "Missing the required parameter 'solutionId' when calling getSolution"); + } + HttpRequest.Builder localVarRequestBuilder = HttpRequest.newBuilder(); + String localVarPath = "/api/ai/solution/{solutionId}" + .replace("{solutionId}", ApiClient.urlEncode(solutionId.toString())); + localVarRequestBuilder.uri(URI.create(memberVarBaseUri + localVarPath)); + localVarRequestBuilder.header("Accept", "application/json"); + localVarRequestBuilder.method("GET", HttpRequest.BodyPublishers.noBody()); + if (memberVarReadTimeout != null) { + localVarRequestBuilder.timeout(memberVarReadTimeout); + } + // Add custom headers if provided + localVarRequestBuilder = HttpRequestBuilderExtensions.withAdditionalHeaders(localVarRequestBuilder, headers); + if (memberVarInterceptor != null) { + memberVarInterceptor.accept(localVarRequestBuilder); + } + return localVarRequestBuilder; + } + /** * Get Solution template details (getSolutionTemplateDetails) * Get a solution template details based on the provided id Security check is performed to verify that the user has 'READ' permission for the entity (entities). @@ -40709,6 +41341,76 @@ private HttpRequest.Builder getSolutionTemplateInstructionsRequestBuilder(@Nonnu return localVarRequestBuilder; } + /** + * getSolutions + * + * @return com.fasterxml.jackson.databind.JsonNode + * @throws ApiException if fails to make API call + */ + public com.fasterxml.jackson.databind.JsonNode getSolutions() throws ApiException { + ApiResponse localVarResponse = getSolutionsWithHttpInfo(null); + return localVarResponse.getData(); + } + + /** + * getSolutions + * + * @param headers Optional headers to include in the request + * @return ApiResponse<com.fasterxml.jackson.databind.JsonNode> + * @throws ApiException if fails to make API call + */ + public ApiResponse getSolutionsWithHttpInfo(Map headers) throws ApiException { + HttpRequest.Builder localVarRequestBuilder = getSolutionsRequestBuilder(headers); + try { + HttpResponse localVarResponse = memberVarHttpClient.send( + localVarRequestBuilder.build(), + HttpResponse.BodyHandlers.ofInputStream()); + if (memberVarResponseInterceptor != null) { + memberVarResponseInterceptor.accept(localVarResponse); + } + InputStream localVarResponseBody = null; + try { + if (localVarResponse.statusCode()/ 100 != 2) { + throw getApiException("getSolutions", localVarResponse); + } + localVarResponseBody = ApiClient.getResponseBody(localVarResponse); + if (localVarResponseBody == null) { + return new ApiResponse(localVarResponse.statusCode(), localVarResponse.headers().map(), null); + } + String responseBody = new String(localVarResponseBody.readAllBytes()); + com.fasterxml.jackson.databind.JsonNode responseValue = responseBody.isBlank()? null: memberVarObjectMapper.readValue(responseBody, new TypeReference() {}); + return new ApiResponse(localVarResponse.statusCode(), localVarResponse.headers().map(), responseValue); + } finally { + if (localVarResponseBody != null) { + localVarResponseBody.close(); + } + } + } catch (IOException e) { + throw new ApiException(e); + } + catch (InterruptedException e) { + Thread.currentThread().interrupt(); + throw new ApiException(e); + } + } + + private HttpRequest.Builder getSolutionsRequestBuilder(Map headers) throws ApiException { + HttpRequest.Builder localVarRequestBuilder = HttpRequest.newBuilder(); + String localVarPath = "/api/ai/solution/infos"; + localVarRequestBuilder.uri(URI.create(memberVarBaseUri + localVarPath)); + localVarRequestBuilder.header("Accept", "application/json"); + localVarRequestBuilder.method("GET", HttpRequest.BodyPublishers.noBody()); + if (memberVarReadTimeout != null) { + localVarRequestBuilder.timeout(memberVarReadTimeout); + } + // Add custom headers if provided + localVarRequestBuilder = HttpRequestBuilderExtensions.withAdditionalHeaders(localVarRequestBuilder, headers); + if (memberVarInterceptor != null) { + memberVarInterceptor.accept(localVarRequestBuilder); + } + return localVarRequestBuilder; + } + /** * Get system info (getSystemInfo) * Get main information about system. Available for users with 'SYS_ADMIN' authority. @@ -49639,6 +50341,92 @@ private HttpRequest.Builder importSolutionRequestBuilder(@Nonnull SolutionData s return localVarRequestBuilder; } + /** + * installSolution + * + * @param solutionId (required) + * @param xAuthorization (required) + * @return com.fasterxml.jackson.databind.JsonNode + * @throws ApiException if fails to make API call + */ + public com.fasterxml.jackson.databind.JsonNode installSolution(@Nonnull UUID solutionId, @Nonnull String xAuthorization) throws ApiException { + ApiResponse localVarResponse = installSolutionWithHttpInfo(solutionId, xAuthorization, null); + return localVarResponse.getData(); + } + + /** + * installSolution + * + * @param solutionId (required) + * @param xAuthorization (required) + * @param headers Optional headers to include in the request + * @return ApiResponse<com.fasterxml.jackson.databind.JsonNode> + * @throws ApiException if fails to make API call + */ + public ApiResponse installSolutionWithHttpInfo(@Nonnull UUID solutionId, @Nonnull String xAuthorization, Map headers) throws ApiException { + HttpRequest.Builder localVarRequestBuilder = installSolutionRequestBuilder(solutionId, xAuthorization, headers); + try { + HttpResponse localVarResponse = memberVarHttpClient.send( + localVarRequestBuilder.build(), + HttpResponse.BodyHandlers.ofInputStream()); + if (memberVarResponseInterceptor != null) { + memberVarResponseInterceptor.accept(localVarResponse); + } + InputStream localVarResponseBody = null; + try { + if (localVarResponse.statusCode()/ 100 != 2) { + throw getApiException("installSolution", localVarResponse); + } + localVarResponseBody = ApiClient.getResponseBody(localVarResponse); + if (localVarResponseBody == null) { + return new ApiResponse(localVarResponse.statusCode(), localVarResponse.headers().map(), null); + } + String responseBody = new String(localVarResponseBody.readAllBytes()); + com.fasterxml.jackson.databind.JsonNode responseValue = responseBody.isBlank()? null: memberVarObjectMapper.readValue(responseBody, new TypeReference() {}); + return new ApiResponse(localVarResponse.statusCode(), localVarResponse.headers().map(), responseValue); + } finally { + if (localVarResponseBody != null) { + localVarResponseBody.close(); + } + } + } catch (IOException e) { + throw new ApiException(e); + } + catch (InterruptedException e) { + Thread.currentThread().interrupt(); + throw new ApiException(e); + } + } + + private HttpRequest.Builder installSolutionRequestBuilder(@Nonnull UUID solutionId, @Nonnull String xAuthorization, Map headers) throws ApiException { + // verify the required parameter 'solutionId' is set + if (solutionId == null) { + throw new ApiException(400, "Missing the required parameter 'solutionId' when calling installSolution"); + } + // verify the required parameter 'xAuthorization' is set + if (xAuthorization == null) { + throw new ApiException(400, "Missing the required parameter 'xAuthorization' when calling installSolution"); + } + HttpRequest.Builder localVarRequestBuilder = HttpRequest.newBuilder(); + String localVarPath = "/api/ai/solution/{solutionId}/install" + .replace("{solutionId}", ApiClient.urlEncode(solutionId.toString())); + localVarRequestBuilder.uri(URI.create(memberVarBaseUri + localVarPath)); + if (xAuthorization != null) { + localVarRequestBuilder.header("X-Authorization", xAuthorization.toString()); + } + localVarRequestBuilder.header("Accept", "application/json"); + localVarRequestBuilder.method("POST", HttpRequest.BodyPublishers.noBody()); + if (memberVarReadTimeout != null) { + localVarRequestBuilder.timeout(memberVarReadTimeout); + } + // Add custom headers if provided + localVarRequestBuilder = HttpRequestBuilderExtensions.withAdditionalHeaders(localVarRequestBuilder, headers); + if (memberVarInterceptor != null) { + memberVarInterceptor.accept(localVarRequestBuilder); + } + return localVarRequestBuilder; + } + /** * Install Solution Template (installSolutionTemplate) * Install solution template based on the provided id Security check is performed to verify that the user has 'WRITE' permission for the entity (entities). @@ -50290,6 +51078,83 @@ private HttpRequest.Builder listBranchesRequestBuilder(Map heade return localVarRequestBuilder; } + /** + * listChats + * + * @param chatType (required) + * @return com.fasterxml.jackson.databind.JsonNode + * @throws ApiException if fails to make API call + */ + public com.fasterxml.jackson.databind.JsonNode listChats(@Nonnull ChatType chatType) throws ApiException { + ApiResponse localVarResponse = listChatsWithHttpInfo(chatType, null); + return localVarResponse.getData(); + } + + /** + * listChats + * + * @param chatType (required) + * @param headers Optional headers to include in the request + * @return ApiResponse<com.fasterxml.jackson.databind.JsonNode> + * @throws ApiException if fails to make API call + */ + public ApiResponse listChatsWithHttpInfo(@Nonnull ChatType chatType, Map headers) throws ApiException { + HttpRequest.Builder localVarRequestBuilder = listChatsRequestBuilder(chatType, headers); + try { + HttpResponse localVarResponse = memberVarHttpClient.send( + localVarRequestBuilder.build(), + HttpResponse.BodyHandlers.ofInputStream()); + if (memberVarResponseInterceptor != null) { + memberVarResponseInterceptor.accept(localVarResponse); + } + InputStream localVarResponseBody = null; + try { + if (localVarResponse.statusCode()/ 100 != 2) { + throw getApiException("listChats", localVarResponse); + } + localVarResponseBody = ApiClient.getResponseBody(localVarResponse); + if (localVarResponseBody == null) { + return new ApiResponse(localVarResponse.statusCode(), localVarResponse.headers().map(), null); + } + String responseBody = new String(localVarResponseBody.readAllBytes()); + com.fasterxml.jackson.databind.JsonNode responseValue = responseBody.isBlank()? null: memberVarObjectMapper.readValue(responseBody, new TypeReference() {}); + return new ApiResponse(localVarResponse.statusCode(), localVarResponse.headers().map(), responseValue); + } finally { + if (localVarResponseBody != null) { + localVarResponseBody.close(); + } + } + } catch (IOException e) { + throw new ApiException(e); + } + catch (InterruptedException e) { + Thread.currentThread().interrupt(); + throw new ApiException(e); + } + } + + private HttpRequest.Builder listChatsRequestBuilder(@Nonnull ChatType chatType, Map headers) throws ApiException { + // verify the required parameter 'chatType' is set + if (chatType == null) { + throw new ApiException(400, "Missing the required parameter 'chatType' when calling listChats"); + } + HttpRequest.Builder localVarRequestBuilder = HttpRequest.newBuilder(); + String localVarPath = "/api/ai/chats/{chatType}" + .replace("{chatType}", ApiClient.urlEncode(chatType.toString())); + localVarRequestBuilder.uri(URI.create(memberVarBaseUri + localVarPath)); + localVarRequestBuilder.header("Accept", "application/json"); + localVarRequestBuilder.method("GET", HttpRequest.BodyPublishers.noBody()); + if (memberVarReadTimeout != null) { + localVarRequestBuilder.timeout(memberVarReadTimeout); + } + // Add custom headers if provided + localVarRequestBuilder = HttpRequestBuilderExtensions.withAdditionalHeaders(localVarRequestBuilder, headers); + if (memberVarInterceptor != null) { + memberVarInterceptor.accept(localVarRequestBuilder); + } + return localVarRequestBuilder; + } + /** * List entities at version (listEntitiesAtVersion) * Returns a list of remote entities of a specific entity type that are available at a concrete version. Each entity item in the result has `externalId` property. Entities order will be the same as in the repository. Available for users with 'TENANT_ADMIN' authority. @@ -53580,6 +54445,88 @@ private HttpRequest.Builder resetPasswordRequestBuilder(@Nonnull ResetPasswordRe return localVarRequestBuilder; } + /** + * resolveToolApproval + * + * @param body (required) + * @return com.fasterxml.jackson.databind.JsonNode + * @throws ApiException if fails to make API call + */ + public com.fasterxml.jackson.databind.JsonNode resolveToolApproval(@Nullable Object body) throws ApiException { + ApiResponse localVarResponse = resolveToolApprovalWithHttpInfo(body, null); + return localVarResponse.getData(); + } + + /** + * resolveToolApproval + * + * @param body (required) + * @param headers Optional headers to include in the request + * @return ApiResponse<com.fasterxml.jackson.databind.JsonNode> + * @throws ApiException if fails to make API call + */ + public ApiResponse resolveToolApprovalWithHttpInfo(@Nullable Object body, Map headers) throws ApiException { + HttpRequest.Builder localVarRequestBuilder = resolveToolApprovalRequestBuilder(body, headers); + try { + HttpResponse localVarResponse = memberVarHttpClient.send( + localVarRequestBuilder.build(), + HttpResponse.BodyHandlers.ofInputStream()); + if (memberVarResponseInterceptor != null) { + memberVarResponseInterceptor.accept(localVarResponse); + } + InputStream localVarResponseBody = null; + try { + if (localVarResponse.statusCode()/ 100 != 2) { + throw getApiException("resolveToolApproval", localVarResponse); + } + localVarResponseBody = ApiClient.getResponseBody(localVarResponse); + if (localVarResponseBody == null) { + return new ApiResponse(localVarResponse.statusCode(), localVarResponse.headers().map(), null); + } + String responseBody = new String(localVarResponseBody.readAllBytes()); + com.fasterxml.jackson.databind.JsonNode responseValue = responseBody.isBlank()? null: memberVarObjectMapper.readValue(responseBody, new TypeReference() {}); + return new ApiResponse(localVarResponse.statusCode(), localVarResponse.headers().map(), responseValue); + } finally { + if (localVarResponseBody != null) { + localVarResponseBody.close(); + } + } + } catch (IOException e) { + throw new ApiException(e); + } + catch (InterruptedException e) { + Thread.currentThread().interrupt(); + throw new ApiException(e); + } + } + + private HttpRequest.Builder resolveToolApprovalRequestBuilder(@Nullable Object body, Map headers) throws ApiException { + // verify the required parameter 'body' is set + if (body == null) { + throw new ApiException(400, "Missing the required parameter 'body' when calling resolveToolApproval"); + } + HttpRequest.Builder localVarRequestBuilder = HttpRequest.newBuilder(); + String localVarPath = "/api/ai/tools/resolve-approval"; + localVarRequestBuilder.uri(URI.create(memberVarBaseUri + localVarPath)); + localVarRequestBuilder.header("Content-Type", "application/json"); + localVarRequestBuilder.header("Accept", "application/json"); + try { + byte[] localVarPostBody = memberVarObjectMapper.writeValueAsBytes(body); + localVarRequestBuilder.method("POST", HttpRequest.BodyPublishers.ofByteArray(localVarPostBody)); + } catch (IOException e) { + throw new ApiException(e); + } + if (memberVarReadTimeout != null) { + localVarRequestBuilder.timeout(memberVarReadTimeout); + } + // Add custom headers if provided + localVarRequestBuilder = HttpRequestBuilderExtensions.withAdditionalHeaders(localVarRequestBuilder, headers); + if (memberVarInterceptor != null) { + memberVarInterceptor.accept(localVarRequestBuilder); + } + return localVarRequestBuilder; + } + /** * Creates or Updates the Administration Settings (saveAdminSettings) * Creates or Updates the Administration Settings. Platform generates random Administration Settings Id during settings creation. The Administration Settings Id will be present in the response. Specify the Administration Settings Id when you would like to update the Administration Settings. Referencing non-existing Administration Settings Id will cause an error. Available for users with 'SYS_ADMIN' or 'TENANT_ADMIN' authority. Security check is performed to verify that the user has 'WRITE' permission for the 'ADMIN_SETTINGS' (for 'SYS_ADMIN' authority) or 'WHITE_LABELING' (for 'TENANT_ADMIN' authority) resource. @@ -59838,6 +60785,99 @@ private HttpRequest.Builder sendAddonAccessErrorRequestBuilder(@Nonnull String a return localVarRequestBuilder; } + /** + * sendChatMessage + * + * @param chatId (required) + * @param xAuthorization (required) + * @param body (required) + * @return List<Object> + * @throws ApiException if fails to make API call + */ + public List sendChatMessage(@Nonnull UUID chatId, @Nonnull String xAuthorization, @Nonnull String body) throws ApiException { + ApiResponse> localVarResponse = sendChatMessageWithHttpInfo(chatId, xAuthorization, body, null); + return localVarResponse.getData(); + } + + /** + * sendChatMessage + * + * @param chatId (required) + * @param xAuthorization (required) + * @param body (required) + * @param headers Optional headers to include in the request + * @return ApiResponse<List<Object>> + * @throws ApiException if fails to make API call + */ + public ApiResponse> sendChatMessageWithHttpInfo(@Nonnull UUID chatId, @Nonnull String xAuthorization, @Nonnull String body, Map headers) throws ApiException { + HttpRequest.Builder localVarRequestBuilder = sendChatMessageRequestBuilder(chatId, xAuthorization, body, headers); + try { + HttpResponse localVarResponse = memberVarHttpClient.send( + localVarRequestBuilder.build(), + HttpResponse.BodyHandlers.ofInputStream()); + if (memberVarResponseInterceptor != null) { + memberVarResponseInterceptor.accept(localVarResponse); + } + InputStream localVarResponseBody = null; + try { + if (localVarResponse.statusCode()/ 100 != 2) { + throw getApiException("sendChatMessage", localVarResponse); + } + localVarResponseBody = ApiClient.getResponseBody(localVarResponse); + if (localVarResponseBody == null) { + return new ApiResponse>(localVarResponse.statusCode(), localVarResponse.headers().map(), null); + } + String responseBody = new String(localVarResponseBody.readAllBytes()); + List responseValue = responseBody.isBlank()? null: memberVarObjectMapper.readValue(responseBody, new TypeReference>() {}); + return new ApiResponse>(localVarResponse.statusCode(), localVarResponse.headers().map(), responseValue); + } finally { + if (localVarResponseBody != null) { + localVarResponseBody.close(); + } + } + } catch (IOException e) { + throw new ApiException(e); + } + catch (InterruptedException e) { + Thread.currentThread().interrupt(); + throw new ApiException(e); + } + } + + private HttpRequest.Builder sendChatMessageRequestBuilder(@Nonnull UUID chatId, @Nonnull String xAuthorization, @Nonnull String body, Map headers) throws ApiException { + // verify the required parameter 'chatId' is set + if (chatId == null) { + throw new ApiException(400, "Missing the required parameter 'chatId' when calling sendChatMessage"); + } + // verify the required parameter 'xAuthorization' is set + if (xAuthorization == null) { + throw new ApiException(400, "Missing the required parameter 'xAuthorization' when calling sendChatMessage"); + } + // verify the required parameter 'body' is set + if (body == null) { + throw new ApiException(400, "Missing the required parameter 'body' when calling sendChatMessage"); + } + HttpRequest.Builder localVarRequestBuilder = HttpRequest.newBuilder(); + String localVarPath = "/api/ai/chats/{chatId}/messages" + .replace("{chatId}", ApiClient.urlEncode(chatId.toString())); + localVarRequestBuilder.uri(URI.create(memberVarBaseUri + localVarPath)); + if (xAuthorization != null) { + localVarRequestBuilder.header("X-Authorization", xAuthorization.toString()); + } + localVarRequestBuilder.header("Content-Type", "text/plain"); + localVarRequestBuilder.header("Accept", "text/event-stream, application/json"); + localVarRequestBuilder.method("POST", HttpRequest.BodyPublishers.ofString(body)); + if (memberVarReadTimeout != null) { + localVarRequestBuilder.timeout(memberVarReadTimeout); + } + // Add custom headers if provided + localVarRequestBuilder = HttpRequestBuilderExtensions.withAdditionalHeaders(localVarRequestBuilder, headers); + if (memberVarInterceptor != null) { + memberVarInterceptor.accept(localVarRequestBuilder); + } + return localVarRequestBuilder; + } + /** * Send request to AI chat model (sendChatRequest) * Submits a single prompt - made up of an optional system message and a required user message - to the specified AI chat model and returns either the generated answer or an error envelope. Available for users with 'TENANT_ADMIN' authority. @@ -61276,6 +62316,76 @@ private HttpRequest.Builder signUpRequestBuilder(@Nonnull SignUpRequest signUpRe return localVarRequestBuilder; } + /** + * startNew + * + * @return com.fasterxml.jackson.databind.JsonNode + * @throws ApiException if fails to make API call + */ + public com.fasterxml.jackson.databind.JsonNode startNew() throws ApiException { + ApiResponse localVarResponse = startNewWithHttpInfo(null); + return localVarResponse.getData(); + } + + /** + * startNew + * + * @param headers Optional headers to include in the request + * @return ApiResponse<com.fasterxml.jackson.databind.JsonNode> + * @throws ApiException if fails to make API call + */ + public ApiResponse startNewWithHttpInfo(Map headers) throws ApiException { + HttpRequest.Builder localVarRequestBuilder = startNewRequestBuilder(headers); + try { + HttpResponse localVarResponse = memberVarHttpClient.send( + localVarRequestBuilder.build(), + HttpResponse.BodyHandlers.ofInputStream()); + if (memberVarResponseInterceptor != null) { + memberVarResponseInterceptor.accept(localVarResponse); + } + InputStream localVarResponseBody = null; + try { + if (localVarResponse.statusCode()/ 100 != 2) { + throw getApiException("startNew", localVarResponse); + } + localVarResponseBody = ApiClient.getResponseBody(localVarResponse); + if (localVarResponseBody == null) { + return new ApiResponse(localVarResponse.statusCode(), localVarResponse.headers().map(), null); + } + String responseBody = new String(localVarResponseBody.readAllBytes()); + com.fasterxml.jackson.databind.JsonNode responseValue = responseBody.isBlank()? null: memberVarObjectMapper.readValue(responseBody, new TypeReference() {}); + return new ApiResponse(localVarResponse.statusCode(), localVarResponse.headers().map(), responseValue); + } finally { + if (localVarResponseBody != null) { + localVarResponseBody.close(); + } + } + } catch (IOException e) { + throw new ApiException(e); + } + catch (InterruptedException e) { + Thread.currentThread().interrupt(); + throw new ApiException(e); + } + } + + private HttpRequest.Builder startNewRequestBuilder(Map headers) throws ApiException { + HttpRequest.Builder localVarRequestBuilder = HttpRequest.newBuilder(); + String localVarPath = "/api/ai/solution/start"; + localVarRequestBuilder.uri(URI.create(memberVarBaseUri + localVarPath)); + localVarRequestBuilder.header("Accept", "application/json"); + localVarRequestBuilder.method("POST", HttpRequest.BodyPublishers.noBody()); + if (memberVarReadTimeout != null) { + localVarRequestBuilder.timeout(memberVarReadTimeout); + } + // Add custom headers if provided + localVarRequestBuilder = HttpRequestBuilderExtensions.withAdditionalHeaders(localVarRequestBuilder, headers); + if (memberVarInterceptor != null) { + memberVarInterceptor.accept(localVarRequestBuilder); + } + return localVarRequestBuilder; + } + /** * Submit 2FA account config (submitTwoFaAccountConfig) * Submit 2FA account config to prepare for a future verification. Basically, this method will send a verification code for a given account config, if this has sense for a chosen 2FA provider. This code is needed to then verify and save the account config. Example of EMAIL 2FA account config: ``` { \"providerType\": \"EMAIL\", \"useByDefault\": true, \"email\": \"separate-email-for-2fa@thingsboard.org\" } ``` Example of SMS 2FA account config: ``` { \"providerType\": \"SMS\", \"useByDefault\": false, \"phoneNumber\": \"+38012312321\" } ``` For TOTP this method does nothing. Will throw an error (Bad Request) if submitted account config is not valid, or if the provider is not configured for usage. Available for any authorized user. @@ -62460,6 +63570,92 @@ private HttpRequest.Builder unassignSchedulerEventFromEdgeRequestBuilder(@Nonnul return localVarRequestBuilder; } + /** + * uninstallSolution + * + * @param solutionId (required) + * @param xAuthorization (required) + * @return com.fasterxml.jackson.databind.JsonNode + * @throws ApiException if fails to make API call + */ + public com.fasterxml.jackson.databind.JsonNode uninstallSolution(@Nonnull UUID solutionId, @Nonnull String xAuthorization) throws ApiException { + ApiResponse localVarResponse = uninstallSolutionWithHttpInfo(solutionId, xAuthorization, null); + return localVarResponse.getData(); + } + + /** + * uninstallSolution + * + * @param solutionId (required) + * @param xAuthorization (required) + * @param headers Optional headers to include in the request + * @return ApiResponse<com.fasterxml.jackson.databind.JsonNode> + * @throws ApiException if fails to make API call + */ + public ApiResponse uninstallSolutionWithHttpInfo(@Nonnull UUID solutionId, @Nonnull String xAuthorization, Map headers) throws ApiException { + HttpRequest.Builder localVarRequestBuilder = uninstallSolutionRequestBuilder(solutionId, xAuthorization, headers); + try { + HttpResponse localVarResponse = memberVarHttpClient.send( + localVarRequestBuilder.build(), + HttpResponse.BodyHandlers.ofInputStream()); + if (memberVarResponseInterceptor != null) { + memberVarResponseInterceptor.accept(localVarResponse); + } + InputStream localVarResponseBody = null; + try { + if (localVarResponse.statusCode()/ 100 != 2) { + throw getApiException("uninstallSolution", localVarResponse); + } + localVarResponseBody = ApiClient.getResponseBody(localVarResponse); + if (localVarResponseBody == null) { + return new ApiResponse(localVarResponse.statusCode(), localVarResponse.headers().map(), null); + } + String responseBody = new String(localVarResponseBody.readAllBytes()); + com.fasterxml.jackson.databind.JsonNode responseValue = responseBody.isBlank()? null: memberVarObjectMapper.readValue(responseBody, new TypeReference() {}); + return new ApiResponse(localVarResponse.statusCode(), localVarResponse.headers().map(), responseValue); + } finally { + if (localVarResponseBody != null) { + localVarResponseBody.close(); + } + } + } catch (IOException e) { + throw new ApiException(e); + } + catch (InterruptedException e) { + Thread.currentThread().interrupt(); + throw new ApiException(e); + } + } + + private HttpRequest.Builder uninstallSolutionRequestBuilder(@Nonnull UUID solutionId, @Nonnull String xAuthorization, Map headers) throws ApiException { + // verify the required parameter 'solutionId' is set + if (solutionId == null) { + throw new ApiException(400, "Missing the required parameter 'solutionId' when calling uninstallSolution"); + } + // verify the required parameter 'xAuthorization' is set + if (xAuthorization == null) { + throw new ApiException(400, "Missing the required parameter 'xAuthorization' when calling uninstallSolution"); + } + HttpRequest.Builder localVarRequestBuilder = HttpRequest.newBuilder(); + String localVarPath = "/api/ai/solution/{solutionId}/uninstall" + .replace("{solutionId}", ApiClient.urlEncode(solutionId.toString())); + localVarRequestBuilder.uri(URI.create(memberVarBaseUri + localVarPath)); + if (xAuthorization != null) { + localVarRequestBuilder.header("X-Authorization", xAuthorization.toString()); + } + localVarRequestBuilder.header("Accept", "application/json"); + localVarRequestBuilder.method("DELETE", HttpRequest.BodyPublishers.noBody()); + if (memberVarReadTimeout != null) { + localVarRequestBuilder.timeout(memberVarReadTimeout); + } + // Add custom headers if provided + localVarRequestBuilder = HttpRequestBuilderExtensions.withAdditionalHeaders(localVarRequestBuilder, headers); + if (memberVarInterceptor != null) { + memberVarInterceptor.accept(localVarRequestBuilder); + } + return localVarRequestBuilder; + } + /** * Uninstall Solution Template (uninstallSolutionTemplate) * Uninstall solution template based on the provided id Security check is performed to verify that the user has 'DELETE' permission for the entity (entities). @@ -62779,6 +63975,91 @@ private HttpRequest.Builder updateApiKeyDescriptionRequestBuilder(@Nonnull UUID return localVarRequestBuilder; } + /** + * updateChat + * + * @param chatId (required) + * @param body (required) + * @throws ApiException if fails to make API call + */ + public void updateChat(@Nonnull UUID chatId, @Nullable Object body) throws ApiException { + updateChatWithHttpInfo(chatId, body, null); + } + + /** + * updateChat + * + * @param chatId (required) + * @param body (required) + * @param headers Optional headers to include in the request + * @return ApiResponse<Void> + * @throws ApiException if fails to make API call + */ + public ApiResponse updateChatWithHttpInfo(@Nonnull UUID chatId, @Nullable Object body, Map headers) throws ApiException { + HttpRequest.Builder localVarRequestBuilder = updateChatRequestBuilder(chatId, body, headers); + try { + HttpResponse localVarResponse = memberVarHttpClient.send( + localVarRequestBuilder.build(), + HttpResponse.BodyHandlers.ofInputStream()); + if (memberVarResponseInterceptor != null) { + memberVarResponseInterceptor.accept(localVarResponse); + } + InputStream localVarResponseBody = null; + try { + if (localVarResponse.statusCode()/ 100 != 2) { + throw getApiException("updateChat", localVarResponse); + } + localVarResponseBody = ApiClient.getResponseBody(localVarResponse); + if (localVarResponseBody != null) { + localVarResponseBody.readAllBytes(); + } + return new ApiResponse(localVarResponse.statusCode(), localVarResponse.headers().map(), null); + } finally { + if (localVarResponseBody != null) { + localVarResponseBody.close(); + } + } + } catch (IOException e) { + throw new ApiException(e); + } + catch (InterruptedException e) { + Thread.currentThread().interrupt(); + throw new ApiException(e); + } + } + + private HttpRequest.Builder updateChatRequestBuilder(@Nonnull UUID chatId, @Nullable Object body, Map headers) throws ApiException { + // verify the required parameter 'chatId' is set + if (chatId == null) { + throw new ApiException(400, "Missing the required parameter 'chatId' when calling updateChat"); + } + // verify the required parameter 'body' is set + if (body == null) { + throw new ApiException(400, "Missing the required parameter 'body' when calling updateChat"); + } + HttpRequest.Builder localVarRequestBuilder = HttpRequest.newBuilder(); + String localVarPath = "/api/ai/chats/{chatId}" + .replace("{chatId}", ApiClient.urlEncode(chatId.toString())); + localVarRequestBuilder.uri(URI.create(memberVarBaseUri + localVarPath)); + localVarRequestBuilder.header("Content-Type", "application/json"); + localVarRequestBuilder.header("Accept", "application/json"); + try { + byte[] localVarPostBody = memberVarObjectMapper.writeValueAsBytes(body); + localVarRequestBuilder.method("PATCH", HttpRequest.BodyPublishers.ofByteArray(localVarPostBody)); + } catch (IOException e) { + throw new ApiException(e); + } + if (memberVarReadTimeout != null) { + localVarRequestBuilder.timeout(memberVarReadTimeout); + } + // Add custom headers if provided + localVarRequestBuilder = HttpRequestBuilderExtensions.withAdditionalHeaders(localVarRequestBuilder, headers); + if (memberVarInterceptor != null) { + memberVarInterceptor.accept(localVarRequestBuilder); + } + return localVarRequestBuilder; + } + /** * Update custom menu assignee list (updateCustomMenuAssigneeList) * The api designed to update the list of assignees or assignee type based on the provided Custom Menu Id. To change assignee type, put new assignee type in path parameter. Security check is performed to verify that the user has 'WRITE' permission for the custom menu with specified id. @@ -63052,6 +64333,102 @@ private HttpRequest.Builder updateCustomMenuNameRequestBuilder(@Nonnull UUID cus return localVarRequestBuilder; } + /** + * updateData + * + * @param solutionId (required) + * @param dataKey (required) + * @param body (required) + * @return com.fasterxml.jackson.databind.JsonNode + * @throws ApiException if fails to make API call + */ + public com.fasterxml.jackson.databind.JsonNode updateData(@Nonnull UUID solutionId, @Nonnull String dataKey, @Nullable Object body) throws ApiException { + ApiResponse localVarResponse = updateDataWithHttpInfo(solutionId, dataKey, body, null); + return localVarResponse.getData(); + } + + /** + * updateData + * + * @param solutionId (required) + * @param dataKey (required) + * @param body (required) + * @param headers Optional headers to include in the request + * @return ApiResponse<com.fasterxml.jackson.databind.JsonNode> + * @throws ApiException if fails to make API call + */ + public ApiResponse updateDataWithHttpInfo(@Nonnull UUID solutionId, @Nonnull String dataKey, @Nullable Object body, Map headers) throws ApiException { + HttpRequest.Builder localVarRequestBuilder = updateDataRequestBuilder(solutionId, dataKey, body, headers); + try { + HttpResponse localVarResponse = memberVarHttpClient.send( + localVarRequestBuilder.build(), + HttpResponse.BodyHandlers.ofInputStream()); + if (memberVarResponseInterceptor != null) { + memberVarResponseInterceptor.accept(localVarResponse); + } + InputStream localVarResponseBody = null; + try { + if (localVarResponse.statusCode()/ 100 != 2) { + throw getApiException("updateData", localVarResponse); + } + localVarResponseBody = ApiClient.getResponseBody(localVarResponse); + if (localVarResponseBody == null) { + return new ApiResponse(localVarResponse.statusCode(), localVarResponse.headers().map(), null); + } + String responseBody = new String(localVarResponseBody.readAllBytes()); + com.fasterxml.jackson.databind.JsonNode responseValue = responseBody.isBlank()? null: memberVarObjectMapper.readValue(responseBody, new TypeReference() {}); + return new ApiResponse(localVarResponse.statusCode(), localVarResponse.headers().map(), responseValue); + } finally { + if (localVarResponseBody != null) { + localVarResponseBody.close(); + } + } + } catch (IOException e) { + throw new ApiException(e); + } + catch (InterruptedException e) { + Thread.currentThread().interrupt(); + throw new ApiException(e); + } + } + + private HttpRequest.Builder updateDataRequestBuilder(@Nonnull UUID solutionId, @Nonnull String dataKey, @Nullable Object body, Map headers) throws ApiException { + // verify the required parameter 'solutionId' is set + if (solutionId == null) { + throw new ApiException(400, "Missing the required parameter 'solutionId' when calling updateData"); + } + // verify the required parameter 'dataKey' is set + if (dataKey == null) { + throw new ApiException(400, "Missing the required parameter 'dataKey' when calling updateData"); + } + // verify the required parameter 'body' is set + if (body == null) { + throw new ApiException(400, "Missing the required parameter 'body' when calling updateData"); + } + HttpRequest.Builder localVarRequestBuilder = HttpRequest.newBuilder(); + String localVarPath = "/api/ai/solution/{solutionId}/{dataKey}" + .replace("{solutionId}", ApiClient.urlEncode(solutionId.toString())) + .replace("{dataKey}", ApiClient.urlEncode(dataKey.toString())); + localVarRequestBuilder.uri(URI.create(memberVarBaseUri + localVarPath)); + localVarRequestBuilder.header("Content-Type", "application/json"); + localVarRequestBuilder.header("Accept", "application/json"); + try { + byte[] localVarPostBody = memberVarObjectMapper.writeValueAsBytes(body); + localVarRequestBuilder.method("PUT", HttpRequest.BodyPublishers.ofByteArray(localVarPostBody)); + } catch (IOException e) { + throw new ApiException(e); + } + if (memberVarReadTimeout != null) { + localVarRequestBuilder.timeout(memberVarReadTimeout); + } + // Add custom headers if provided + localVarRequestBuilder = HttpRequestBuilderExtensions.withAdditionalHeaders(localVarRequestBuilder, headers); + if (memberVarInterceptor != null) { + memberVarInterceptor.accept(localVarRequestBuilder); + } + return localVarRequestBuilder; + } + /** * Update device credentials (updateDeviceCredentials) * During device creation, platform generates random 'ACCESS_TOKEN' credentials. Use this method to update the device credentials. First use 'getDeviceCredentialsByDeviceId' to get the credentials id and value. Then use current method to update the credentials type and value. It is not possible to create multiple device credentials for the same device. The structure of device credentials id and value is simple for the 'ACCESS_TOKEN' but is much more complex for the 'MQTT_BASIC' or 'LWM2M_CREDENTIALS'. You may find the example of device with different type of credentials below: - Credentials type: **\"Access token\"** with **device ID** and with **device ID** below: ```json { \"id\": { \"id\":\"c886a090-168d-11ee-87c9-6f157dbc816a\" }, \"deviceId\": { \"id\":\"c5fb3ac0-168d-11ee-87c9-6f157dbc816a\", \"entityType\":\"DEVICE\" }, \"credentialsType\": \"ACCESS_TOKEN\", \"credentialsId\": \"6hmxew8pmmzng4e3une4\" } ``` - Credentials type: **\"X509\"** with **device profile ID** below: Note: **credentialsId** - format **Sha3Hash**, **certificateValue** - format **PEM** (with \"--BEGIN CERTIFICATE----\" and -\"----END CERTIFICATE-\"). ```json { \"id\": { \"id\":\"309bd9c0-14f4-11ee-9fc9-d9b7463abb63\" }, \"deviceId\": { \"id\":\"3092b200-14f4-11ee-9fc9-d9b7463abb63\", \"entityType\":\"DEVICE\" }, \"credentialsType\": \"X509_CERTIFICATE\", \"credentialsId\": \"6b8adb49015500e51a527acd332b51684ab9b49b4ade03a9582a44c455e2e9b6\", \"credentialsValue\": \"-----BEGIN CERTIFICATE----- MIICMTCCAdegAwIBAgIUUEKxS9hTz4l+oLUMF0LV6TC/gCIwCgYIKoZIzj0EAwIwbjELMAkGA1UEBhMCVVMxETAPBgNVBAgMCE5ldyBZb3JrMRowGAYDVQQKDBFUaGluZ3NCb2FyZCwgSW5jLjEwMC4GA1UEAwwnZGV2aWNlUHJvZmlsZUNlcnRAWDUwOVByb3Zpc2lvblN0cmF0ZWd5MB4XDTIzMDMyOTE0NTczNloXDTI0MDMyODE0NTczNlowbjELMAkGA1UEBhMCVVMxETAPBgNVBAgMCE5ldyBZb3JrMRowGAYDVQQKDBFUaGluZ3NCb2FyZCwgSW5jLjEwMC4GA1UEAwwnZGV2aWNlUHJvZmlsZUNlcnRAWDUwOVByb3Zpc2lvblN0cmF0ZWd5MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAECMlWO72krDoUL9FQjUmSCetkhaEGJUfQkdSfkLSNa0GyAEIMbfmzI4zITeapunu4rGet3EMyLydQzuQanBicp6NTMFEwHQYDVR0OBBYEFHpZ78tPnztNii4Da/yCw6mhEIL3MB8GA1UdIwQYMBaAFHpZ78tPnztNii4Da/yCw6mhEIL3MA8GA1UdEwEB/wQFMAMBAf8wCgYIKoZIzj0EAwIDSAAwRQIgJ7qyMFqNcwSYkH6o+UlQXzLWfwZbNjVk+aR7foAZNGsCIQDsd7v3WQIGHiArfZeDs1DLEDuV/2h6L+ZNoGNhEKL+1A== -----END CERTIFICATE-----\" } ``` - Credentials type: **\"MQTT_BASIC\"** with **device profile ID** below: ```json { \"id\": { \"id\":\"d877ffb0-14f5-11ee-9fc9-d9b7463abb63\" }, \"deviceId\": { \"id\":\"d875dcd0-14f5-11ee-9fc9-d9b7463abb63\", \"entityType\":\"DEVICE\" }, \"credentialsType\": \"MQTT_BASIC\", \"credentialsValue\": \"{\\\"clientId\\\":\\\"juy03yv4owqxcmqhqtvk\\\",\\\"userName\\\":\\\"ov19fxca0cyjn7lm7w7u\\\",\\\"password\\\":\\\"twy94he114dfi9usyk1o\\\"}\" } ``` - You may find the example of **LwM2M** device and **RPK** credentials below: Note: LwM2M device - only existing device profile ID (Transport configuration -> Transport type: \"LWM2M\". ```json { \"id\": { \"id\":\"e238d4d0-1689-11ee-98c6-1713c1be5a8e\" }, \"deviceId\": { \"id\":\"e232e160-1689-11ee-98c6-1713c1be5a8e\", \"entityType\":\"DEVICE\" }, \"credentialsType\": \"LWM2M_CREDENTIALS\", \"credentialsId\": \"LwRpk00000000\", \"credentialsValue\": \"{\\\"client\\\":{ \\\"endpoint\\\":\\\"LwRpk00000000\\\", \\\"securityConfigClientMode\\\":\\\"RPK\\\", \\\"key\\\":\\\"MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAEdvBZZ2vQRK9wgDhctj6B1c7bxR3Z0wYg1+YdoYFnVUKWb+rIfTTyYK9tmQJx5Vlb5fxdLnVv1RJOPiwsLIQbAA==\\\" }, \\\"bootstrap\\\":{ \\\"bootstrapServer\\\":{ \\\"securityMode\\\":\\\"RPK\\\", \\\"clientPublicKeyOrId\\\":\\\"MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAEUEBxNl/RcYJNm8mk91CyVXoIJiROYDlXcSSqK6e5bDHwOW4ZiN2lNnXalyF0Jxw8MbAytnDMERXyAja5VEMeVQ==\\\", \\\"clientSecretKey\\\":\\\"MIGHAgEAMBMGByqGSM49AgEGCCqGSM49AwEHBG0wawIBAQQgd9GAx7yZW37autew5KZykn4IgRpge/tZSjnudnZJnMahRANCAARQQHE2X9Fxgk2byaT3ULJVeggmJE5gOVdxJKorp7lsMfA5bhmI3aU2ddqXIXQnHDwxsDK2cMwRFfICNrlUQx5V\\\"}, \\\"lwm2mServer\\\":{ \\\"securityMode\\\":\\\"RPK\\\", \\\"clientPublicKeyOrId\\\":\\\"MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAEUEBxNl/RcYJNm8mk91CyVXoIJiROYDlXcSSqK6e5bDHwOW4ZiN2lNnXalyF0Jxw8MbAytnDMERXyAja5VEMeVQ==\\\", \\\"clientSecretKey\\\":\\\"MIGHAgEAMBMGByqGSM49AgEGCCqGSM49AwEHBG0wawIBAQQgd9GAx7yZW37autew5KZykn4IgRpge/tZSjnudnZJnMahRANCAARQQHE2X9Fxgk2byaT3ULJVeggmJE5gOVdxJKorp7lsMfA5bhmI3aU2ddqXIXQnHDwxsDK2cMwRFfICNrlUQx5V\\\"}} }\" } ``` Update to real value: - 'id' (this is id of Device Credentials -> \"Get Device Credentials (getDeviceCredentialsByDeviceId)\", - 'deviceId.id' (this is id of Device). Remove 'tenantId' and optionally 'customerId' from the request body example (below) to create new Device entity. Available for users with 'TENANT_ADMIN' authority. diff --git a/pe/src/main/java/org/thingsboard/client/model/ApiFeature.java b/pe/src/main/java/org/thingsboard/client/model/ApiFeature.java index c1383fac..0033a2ea 100644 --- a/pe/src/main/java/org/thingsboard/client/model/ApiFeature.java +++ b/pe/src/main/java/org/thingsboard/client/model/ApiFeature.java @@ -48,7 +48,9 @@ public enum ApiFeature { ALARM("ALARM"), - REPORT("REPORT"); + REPORT("REPORT"), + + AI("AI"); private String value; diff --git a/pe/src/main/java/org/thingsboard/client/model/AvailableEntityKeysV2.java b/pe/src/main/java/org/thingsboard/client/model/AvailableEntityKeysV2.java index 61df0e32..cf138b21 100644 --- a/pe/src/main/java/org/thingsboard/client/model/AvailableEntityKeysV2.java +++ b/pe/src/main/java/org/thingsboard/client/model/AvailableEntityKeysV2.java @@ -47,12 +47,17 @@ * Contains unique time series and attribute key names discovered from entities matching a query, optionally including a sample value for each key. */ @JsonPropertyOrder({ + AvailableEntityKeysV2.JSON_PROPERTY_TOTAL_ENTITIES, AvailableEntityKeysV2.JSON_PROPERTY_ENTITY_TYPES, AvailableEntityKeysV2.JSON_PROPERTY_TIMESERIES, AvailableEntityKeysV2.JSON_PROPERTY_ATTRIBUTES }) @Generated(value = "org.openapitools.codegen.languages.JavaClientCodegen", comments = "Generator version: 7.20.0") public class AvailableEntityKeysV2 { + public static final String JSON_PROPERTY_TOTAL_ENTITIES = "totalEntities"; + @Nonnull + private Integer totalEntities; + public static final String JSON_PROPERTY_ENTITY_TYPES = "entityTypes"; @Nonnull private Set entityTypes = new LinkedHashSet<>(); @@ -68,6 +73,30 @@ public class AvailableEntityKeysV2 { public AvailableEntityKeysV2() { } + public AvailableEntityKeysV2 totalEntities(@Nonnull Integer totalEntities) { + this.totalEntities = totalEntities; + return this; + } + + /** + * Total number of entities that matched the query filter. + * @return totalEntities + */ + @Nonnull + @JsonProperty(value = JSON_PROPERTY_TOTAL_ENTITIES, required = true) + @JsonInclude(value = JsonInclude.Include.ALWAYS) + public Integer getTotalEntities() { + return totalEntities; + } + + + @JsonProperty(value = JSON_PROPERTY_TOTAL_ENTITIES, required = true) + @JsonInclude(value = JsonInclude.Include.ALWAYS) + public void setTotalEntities(@Nonnull Integer totalEntities) { + this.totalEntities = totalEntities; + } + + public AvailableEntityKeysV2 entityTypes(@Nonnull Set entityTypes) { this.entityTypes = entityTypes; return this; @@ -177,20 +206,22 @@ public boolean equals(Object o) { return false; } AvailableEntityKeysV2 availableEntityKeysV2 = (AvailableEntityKeysV2) o; - return Objects.equals(this.entityTypes, availableEntityKeysV2.entityTypes) && + return Objects.equals(this.totalEntities, availableEntityKeysV2.totalEntities) && + Objects.equals(this.entityTypes, availableEntityKeysV2.entityTypes) && Objects.equals(this.timeseries, availableEntityKeysV2.timeseries) && Objects.equals(this.attributes, availableEntityKeysV2.attributes); } @Override public int hashCode() { - return Objects.hash(entityTypes, timeseries, attributes); + return Objects.hash(totalEntities, entityTypes, timeseries, attributes); } @Override public String toString() { StringBuilder sb = new StringBuilder(); sb.append("class AvailableEntityKeysV2 {\n"); + sb.append(" totalEntities: ").append(toIndentedString(totalEntities)).append("\n"); sb.append(" entityTypes: ").append(toIndentedString(entityTypes)).append("\n"); sb.append(" timeseries: ").append(toIndentedString(timeseries)).append("\n"); sb.append(" attributes: ").append(toIndentedString(attributes)).append("\n"); @@ -241,6 +272,11 @@ public String toUrlQueryString(String prefix) { StringJoiner joiner = new StringJoiner("&"); + // add `totalEntities` to the URL query string + if (getTotalEntities() != null) { + joiner.add(String.format(java.util.Locale.ROOT, "%stotalEntities%s=%s", prefix, suffix, ApiClient.urlEncode(ApiClient.valueToString(getTotalEntities())))); + } + // add `entityTypes` to the URL query string if (getEntityTypes() != null) { int i = 0; diff --git a/pe/src/main/java/org/thingsboard/client/model/ChatType.java b/pe/src/main/java/org/thingsboard/client/model/ChatType.java new file mode 100644 index 00000000..d207f22f --- /dev/null +++ b/pe/src/main/java/org/thingsboard/client/model/ChatType.java @@ -0,0 +1,80 @@ +/** + * Copyright © 2026-2026 ThingsBoard, Inc. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package org.thingsboard.client.model; + +import java.net.URLEncoder; +import java.nio.charset.StandardCharsets; +import java.util.StringJoiner; +import java.util.Objects; +import java.util.Map; +import java.util.HashMap; +import com.fasterxml.jackson.annotation.JsonPropertyOrder; + + +import com.fasterxml.jackson.annotation.JsonCreator; +import com.fasterxml.jackson.annotation.JsonValue; + +/** + * Gets or Sets ChatType + */ +public enum ChatType { + + GENERIC("GENERIC"), + + SOLUTION_BUILDER("SOLUTION_BUILDER"); + + private String value; + + ChatType(String value) { + this.value = value; + } + + @JsonValue + public String getValue() { + return value; + } + + @Override + public String toString() { + return String.valueOf(value); + } + + @JsonCreator + public static ChatType fromValue(String value) { + for (ChatType b : ChatType.values()) { + if (b.value.equals(value)) { + return b; + } + } + throw new IllegalArgumentException("Unexpected value '" + value + "'"); + } + + /** + * Convert the instance into URL query string. + * + * @param prefix prefix of the query string + * @return URL query string + */ + public String toUrlQueryString(String prefix) { + if (prefix == null) { + prefix = ""; + } + + return String.format(java.util.Locale.ROOT, "%s=%s", prefix, this.toString()); + } + +} + diff --git a/pe/src/main/java/org/thingsboard/client/model/DefaultTenantProfileConfiguration.java b/pe/src/main/java/org/thingsboard/client/model/DefaultTenantProfileConfiguration.java index 00852d42..680fcb30 100644 --- a/pe/src/main/java/org/thingsboard/client/model/DefaultTenantProfileConfiguration.java +++ b/pe/src/main/java/org/thingsboard/client/model/DefaultTenantProfileConfiguration.java @@ -88,6 +88,7 @@ DefaultTenantProfileConfiguration.JSON_PROPERTY_MAX_SMS, DefaultTenantProfileConfiguration.JSON_PROPERTY_MAX_CREATED_ALARMS, DefaultTenantProfileConfiguration.JSON_PROPERTY_MAX_GENERATED_REPORTS, + DefaultTenantProfileConfiguration.JSON_PROPERTY_MAX_AI_CREDITS, DefaultTenantProfileConfiguration.JSON_PROPERTY_TENANT_SERVER_REST_LIMITS_CONFIGURATION, DefaultTenantProfileConfiguration.JSON_PROPERTY_CUSTOMER_SERVER_REST_LIMITS_CONFIGURATION, DefaultTenantProfileConfiguration.JSON_PROPERTY_MAX_WS_SESSIONS_PER_TENANT, @@ -128,7 +129,8 @@ DefaultTenantProfileConfiguration.JSON_PROPERTY_MIN_ALLOWED_AGGREGATION_INTERVAL_IN_SEC_FOR_C_F, DefaultTenantProfileConfiguration.JSON_PROPERTY_INTERMEDIATE_AGGREGATION_INTERVAL_IN_SEC_FOR_C_F, DefaultTenantProfileConfiguration.JSON_PROPERTY_CF_REEVALUATION_CHECK_INTERVAL, - DefaultTenantProfileConfiguration.JSON_PROPERTY_ALARMS_REEVALUATION_INTERVAL + DefaultTenantProfileConfiguration.JSON_PROPERTY_ALARMS_REEVALUATION_INTERVAL, + DefaultTenantProfileConfiguration.JSON_PROPERTY_AI_CHAT_REQUESTS_PER_TENANT_RATE_LIMIT }) @Generated(value = "org.openapitools.codegen.languages.JavaClientCodegen", comments = "Generator version: 7.20.0") @JsonIgnoreProperties( @@ -322,6 +324,10 @@ public class DefaultTenantProfileConfiguration extends TenantProfileConfiguratio @Nullable private Long maxGeneratedReports; + public static final String JSON_PROPERTY_MAX_AI_CREDITS = "maxAiCredits"; + @Nullable + private Long maxAiCredits; + public static final String JSON_PROPERTY_TENANT_SERVER_REST_LIMITS_CONFIGURATION = "tenantServerRestLimitsConfiguration"; @Nullable private String tenantServerRestLimitsConfiguration; @@ -486,6 +492,10 @@ public class DefaultTenantProfileConfiguration extends TenantProfileConfiguratio @Nullable private Long alarmsReevaluationInterval; + public static final String JSON_PROPERTY_AI_CHAT_REQUESTS_PER_TENANT_RATE_LIMIT = "aiChatRequestsPerTenantRateLimit"; + @Nullable + private String aiChatRequestsPerTenantRateLimit; + public DefaultTenantProfileConfiguration() { } @@ -1593,6 +1603,30 @@ public void setMaxGeneratedReports(@Nullable Long maxGeneratedReports) { } + public DefaultTenantProfileConfiguration maxAiCredits(@Nullable Long maxAiCredits) { + this.maxAiCredits = maxAiCredits; + return this; + } + + /** + * Get maxAiCredits + * @return maxAiCredits + */ + @Nullable + @JsonProperty(value = JSON_PROPERTY_MAX_AI_CREDITS, required = false) + @JsonInclude(value = JsonInclude.Include.USE_DEFAULTS) + public Long getMaxAiCredits() { + return maxAiCredits; + } + + + @JsonProperty(value = JSON_PROPERTY_MAX_AI_CREDITS, required = false) + @JsonInclude(value = JsonInclude.Include.USE_DEFAULTS) + public void setMaxAiCredits(@Nullable Long maxAiCredits) { + this.maxAiCredits = maxAiCredits; + } + + public DefaultTenantProfileConfiguration tenantServerRestLimitsConfiguration(@Nullable String tenantServerRestLimitsConfiguration) { this.tenantServerRestLimitsConfiguration = tenantServerRestLimitsConfiguration; return this; @@ -2577,6 +2611,30 @@ public void setAlarmsReevaluationInterval(@Nullable Long alarmsReevaluationInter } + public DefaultTenantProfileConfiguration aiChatRequestsPerTenantRateLimit(@Nullable String aiChatRequestsPerTenantRateLimit) { + this.aiChatRequestsPerTenantRateLimit = aiChatRequestsPerTenantRateLimit; + return this; + } + + /** + * Get aiChatRequestsPerTenantRateLimit + * @return aiChatRequestsPerTenantRateLimit + */ + @Nullable + @JsonProperty(value = JSON_PROPERTY_AI_CHAT_REQUESTS_PER_TENANT_RATE_LIMIT, required = false) + @JsonInclude(value = JsonInclude.Include.USE_DEFAULTS) + public String getAiChatRequestsPerTenantRateLimit() { + return aiChatRequestsPerTenantRateLimit; + } + + + @JsonProperty(value = JSON_PROPERTY_AI_CHAT_REQUESTS_PER_TENANT_RATE_LIMIT, required = false) + @JsonInclude(value = JsonInclude.Include.USE_DEFAULTS) + public void setAiChatRequestsPerTenantRateLimit(@Nullable String aiChatRequestsPerTenantRateLimit) { + this.aiChatRequestsPerTenantRateLimit = aiChatRequestsPerTenantRateLimit; + } + + /** * Return true if this DefaultTenantProfileConfiguration object is equal to o. */ @@ -2635,6 +2693,7 @@ public boolean equals(Object o) { Objects.equals(this.maxSms, defaultTenantProfileConfiguration.maxSms) && Objects.equals(this.maxCreatedAlarms, defaultTenantProfileConfiguration.maxCreatedAlarms) && Objects.equals(this.maxGeneratedReports, defaultTenantProfileConfiguration.maxGeneratedReports) && + Objects.equals(this.maxAiCredits, defaultTenantProfileConfiguration.maxAiCredits) && Objects.equals(this.tenantServerRestLimitsConfiguration, defaultTenantProfileConfiguration.tenantServerRestLimitsConfiguration) && Objects.equals(this.customerServerRestLimitsConfiguration, defaultTenantProfileConfiguration.customerServerRestLimitsConfiguration) && Objects.equals(this.maxWsSessionsPerTenant, defaultTenantProfileConfiguration.maxWsSessionsPerTenant) && @@ -2676,12 +2735,13 @@ public boolean equals(Object o) { Objects.equals(this.intermediateAggregationIntervalInSecForCF, defaultTenantProfileConfiguration.intermediateAggregationIntervalInSecForCF) && Objects.equals(this.cfReevaluationCheckInterval, defaultTenantProfileConfiguration.cfReevaluationCheckInterval) && Objects.equals(this.alarmsReevaluationInterval, defaultTenantProfileConfiguration.alarmsReevaluationInterval) && + Objects.equals(this.aiChatRequestsPerTenantRateLimit, defaultTenantProfileConfiguration.aiChatRequestsPerTenantRateLimit) && super.equals(o); } @Override public int hashCode() { - return Objects.hash(maxDevices, maxAssets, maxCustomers, maxUsers, maxDashboards, maxRuleChains, maxEdges, maxResourcesInBytes, maxOtaPackagesInBytes, maxResourceSize, maxReportSizeInBytes, maxIntegrations, maxConverters, maxSchedulerEvents, transportTenantMsgRateLimit, transportTenantTelemetryMsgRateLimit, transportTenantTelemetryDataPointsRateLimit, transportDeviceMsgRateLimit, transportDeviceTelemetryMsgRateLimit, transportDeviceTelemetryDataPointsRateLimit, transportGatewayMsgRateLimit, transportGatewayTelemetryMsgRateLimit, transportGatewayTelemetryDataPointsRateLimit, transportGatewayDeviceMsgRateLimit, transportGatewayDeviceTelemetryMsgRateLimit, transportGatewayDeviceTelemetryDataPointsRateLimit, integrationMsgsPerTenantRateLimit, integrationMsgsPerDeviceRateLimit, integrationMsgsPerAssetRateLimit, tenantEntityExportRateLimit, tenantEntityImportRateLimit, tenantNotificationRequestsRateLimit, tenantNotificationRequestsPerRuleRateLimit, maxTransportMessages, maxTransportDataPoints, maxREExecutions, maxJSExecutions, maxTbelExecutions, maxDPStorageDays, maxRuleNodeExecutionsPerMessage, maxDebugModeDurationMinutes, maxEmails, smsEnabled, maxSms, maxCreatedAlarms, maxGeneratedReports, tenantServerRestLimitsConfiguration, customerServerRestLimitsConfiguration, maxWsSessionsPerTenant, maxWsSessionsPerCustomer, maxWsSessionsPerRegularUser, maxWsSessionsPerPublicUser, wsMsgQueueLimitPerSession, maxWsSubscriptionsPerTenant, maxWsSubscriptionsPerCustomer, maxWsSubscriptionsPerRegularUser, maxWsSubscriptionsPerPublicUser, wsUpdatesPerSessionRateLimit, cassandraReadQueryTenantCoreRateLimits, cassandraWriteQueryTenantCoreRateLimits, cassandraReadQueryTenantRuleEngineRateLimits, cassandraWriteQueryTenantRuleEngineRateLimits, edgeEventRateLimits, edgeEventRateLimitsPerEdge, edgeUplinkMessagesRateLimits, edgeUplinkMessagesRateLimitsPerEdge, defaultStorageTtlDays, alarmsTtlDays, rpcTtlDays, queueStatsTtlDays, ruleEngineExceptionsTtlDays, blobEntityTtlDays, reportTtlDays, warnThreshold, maxCalculatedFieldsPerEntity, maxArgumentsPerCF, minAllowedScheduledUpdateIntervalInSecForCF, maxRelationLevelPerCfArgument, maxRelatedEntitiesToReturnPerCfArgument, maxDataPointsPerRollingArg, maxStateSizeInKBytes, maxSingleValueArgumentSizeInKBytes, minAllowedDeduplicationIntervalInSecForCF, minAllowedAggregationIntervalInSecForCF, intermediateAggregationIntervalInSecForCF, cfReevaluationCheckInterval, alarmsReevaluationInterval, super.hashCode()); + return Objects.hash(maxDevices, maxAssets, maxCustomers, maxUsers, maxDashboards, maxRuleChains, maxEdges, maxResourcesInBytes, maxOtaPackagesInBytes, maxResourceSize, maxReportSizeInBytes, maxIntegrations, maxConverters, maxSchedulerEvents, transportTenantMsgRateLimit, transportTenantTelemetryMsgRateLimit, transportTenantTelemetryDataPointsRateLimit, transportDeviceMsgRateLimit, transportDeviceTelemetryMsgRateLimit, transportDeviceTelemetryDataPointsRateLimit, transportGatewayMsgRateLimit, transportGatewayTelemetryMsgRateLimit, transportGatewayTelemetryDataPointsRateLimit, transportGatewayDeviceMsgRateLimit, transportGatewayDeviceTelemetryMsgRateLimit, transportGatewayDeviceTelemetryDataPointsRateLimit, integrationMsgsPerTenantRateLimit, integrationMsgsPerDeviceRateLimit, integrationMsgsPerAssetRateLimit, tenantEntityExportRateLimit, tenantEntityImportRateLimit, tenantNotificationRequestsRateLimit, tenantNotificationRequestsPerRuleRateLimit, maxTransportMessages, maxTransportDataPoints, maxREExecutions, maxJSExecutions, maxTbelExecutions, maxDPStorageDays, maxRuleNodeExecutionsPerMessage, maxDebugModeDurationMinutes, maxEmails, smsEnabled, maxSms, maxCreatedAlarms, maxGeneratedReports, maxAiCredits, tenantServerRestLimitsConfiguration, customerServerRestLimitsConfiguration, maxWsSessionsPerTenant, maxWsSessionsPerCustomer, maxWsSessionsPerRegularUser, maxWsSessionsPerPublicUser, wsMsgQueueLimitPerSession, maxWsSubscriptionsPerTenant, maxWsSubscriptionsPerCustomer, maxWsSubscriptionsPerRegularUser, maxWsSubscriptionsPerPublicUser, wsUpdatesPerSessionRateLimit, cassandraReadQueryTenantCoreRateLimits, cassandraWriteQueryTenantCoreRateLimits, cassandraReadQueryTenantRuleEngineRateLimits, cassandraWriteQueryTenantRuleEngineRateLimits, edgeEventRateLimits, edgeEventRateLimitsPerEdge, edgeUplinkMessagesRateLimits, edgeUplinkMessagesRateLimitsPerEdge, defaultStorageTtlDays, alarmsTtlDays, rpcTtlDays, queueStatsTtlDays, ruleEngineExceptionsTtlDays, blobEntityTtlDays, reportTtlDays, warnThreshold, maxCalculatedFieldsPerEntity, maxArgumentsPerCF, minAllowedScheduledUpdateIntervalInSecForCF, maxRelationLevelPerCfArgument, maxRelatedEntitiesToReturnPerCfArgument, maxDataPointsPerRollingArg, maxStateSizeInKBytes, maxSingleValueArgumentSizeInKBytes, minAllowedDeduplicationIntervalInSecForCF, minAllowedAggregationIntervalInSecForCF, intermediateAggregationIntervalInSecForCF, cfReevaluationCheckInterval, alarmsReevaluationInterval, aiChatRequestsPerTenantRateLimit, super.hashCode()); } @Override @@ -2735,6 +2795,7 @@ public String toString() { sb.append(" maxSms: ").append(toIndentedString(maxSms)).append("\n"); sb.append(" maxCreatedAlarms: ").append(toIndentedString(maxCreatedAlarms)).append("\n"); sb.append(" maxGeneratedReports: ").append(toIndentedString(maxGeneratedReports)).append("\n"); + sb.append(" maxAiCredits: ").append(toIndentedString(maxAiCredits)).append("\n"); sb.append(" tenantServerRestLimitsConfiguration: ").append(toIndentedString(tenantServerRestLimitsConfiguration)).append("\n"); sb.append(" customerServerRestLimitsConfiguration: ").append(toIndentedString(customerServerRestLimitsConfiguration)).append("\n"); sb.append(" maxWsSessionsPerTenant: ").append(toIndentedString(maxWsSessionsPerTenant)).append("\n"); @@ -2776,6 +2837,7 @@ public String toString() { sb.append(" intermediateAggregationIntervalInSecForCF: ").append(toIndentedString(intermediateAggregationIntervalInSecForCF)).append("\n"); sb.append(" cfReevaluationCheckInterval: ").append(toIndentedString(cfReevaluationCheckInterval)).append("\n"); sb.append(" alarmsReevaluationInterval: ").append(toIndentedString(alarmsReevaluationInterval)).append("\n"); + sb.append(" aiChatRequestsPerTenantRateLimit: ").append(toIndentedString(aiChatRequestsPerTenantRateLimit)).append("\n"); sb.append("}"); return sb.toString(); } @@ -3058,6 +3120,11 @@ public String toUrlQueryString(String prefix) { joiner.add(String.format(java.util.Locale.ROOT, "%smaxGeneratedReports%s=%s", prefix, suffix, ApiClient.urlEncode(ApiClient.valueToString(getMaxGeneratedReports())))); } + // add `maxAiCredits` to the URL query string + if (getMaxAiCredits() != null) { + joiner.add(String.format(java.util.Locale.ROOT, "%smaxAiCredits%s=%s", prefix, suffix, ApiClient.urlEncode(ApiClient.valueToString(getMaxAiCredits())))); + } + // add `tenantServerRestLimitsConfiguration` to the URL query string if (getTenantServerRestLimitsConfiguration() != null) { joiner.add(String.format(java.util.Locale.ROOT, "%stenantServerRestLimitsConfiguration%s=%s", prefix, suffix, ApiClient.urlEncode(ApiClient.valueToString(getTenantServerRestLimitsConfiguration())))); @@ -3263,6 +3330,11 @@ public String toUrlQueryString(String prefix) { joiner.add(String.format(java.util.Locale.ROOT, "%salarmsReevaluationInterval%s=%s", prefix, suffix, ApiClient.urlEncode(ApiClient.valueToString(getAlarmsReevaluationInterval())))); } + // add `aiChatRequestsPerTenantRateLimit` to the URL query string + if (getAiChatRequestsPerTenantRateLimit() != null) { + joiner.add(String.format(java.util.Locale.ROOT, "%saiChatRequestsPerTenantRateLimit%s=%s", prefix, suffix, ApiClient.urlEncode(ApiClient.valueToString(getAiChatRequestsPerTenantRateLimit())))); + } + return joiner.toString(); } static { diff --git a/pe/src/main/java/org/thingsboard/client/model/LimitedApi.java b/pe/src/main/java/org/thingsboard/client/model/LimitedApi.java index ec058a0c..2942590f 100644 --- a/pe/src/main/java/org/thingsboard/client/model/LimitedApi.java +++ b/pe/src/main/java/org/thingsboard/client/model/LimitedApi.java @@ -100,7 +100,9 @@ public enum LimitedApi { CALCULATED_FIELD_DEBUG_EVENTS("CALCULATED_FIELD_DEBUG_EVENTS"), - TRENDZ_PUBLIC_SYNC("TRENDZ_PUBLIC_SYNC"); + TRENDZ_PUBLIC_SYNC("TRENDZ_PUBLIC_SYNC"), + + AI_CHAT_REQUESTS("AI_CHAT_REQUESTS"); private String value; diff --git a/pe/src/main/java/org/thingsboard/client/model/Resource.java b/pe/src/main/java/org/thingsboard/client/model/Resource.java index 75601f07..a22ff99f 100644 --- a/pe/src/main/java/org/thingsboard/client/model/Resource.java +++ b/pe/src/main/java/org/thingsboard/client/model/Resource.java @@ -136,6 +136,8 @@ public enum Resource { AI_MODEL("AI_MODEL"), + AI("AI"), + API_KEY("API_KEY"); private String value; diff --git a/pe/src/main/java/org/thingsboard/client/model/SolutionStep.java b/pe/src/main/java/org/thingsboard/client/model/SolutionStep.java new file mode 100644 index 00000000..d2ed177b --- /dev/null +++ b/pe/src/main/java/org/thingsboard/client/model/SolutionStep.java @@ -0,0 +1,80 @@ +/** + * Copyright © 2026-2026 ThingsBoard, Inc. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package org.thingsboard.client.model; + +import java.net.URLEncoder; +import java.nio.charset.StandardCharsets; +import java.util.StringJoiner; +import java.util.Objects; +import java.util.Map; +import java.util.HashMap; +import com.fasterxml.jackson.annotation.JsonPropertyOrder; + + +import com.fasterxml.jackson.annotation.JsonCreator; +import com.fasterxml.jackson.annotation.JsonValue; + +/** + * Gets or Sets SolutionStep + */ +public enum SolutionStep { + + INITIAL_CONFIGURATION("INITIAL_CONFIGURATION"), + + DASHBOARDS_CONFIGURATION("DASHBOARDS_CONFIGURATION"); + + private String value; + + SolutionStep(String value) { + this.value = value; + } + + @JsonValue + public String getValue() { + return value; + } + + @Override + public String toString() { + return String.valueOf(value); + } + + @JsonCreator + public static SolutionStep fromValue(String value) { + for (SolutionStep b : SolutionStep.values()) { + if (b.value.equals(value)) { + return b; + } + } + throw new IllegalArgumentException("Unexpected value '" + value + "'"); + } + + /** + * Convert the instance into URL query string. + * + * @param prefix prefix of the query string + * @return URL query string + */ + public String toUrlQueryString(String prefix) { + if (prefix == null) { + prefix = ""; + } + + return String.format(java.util.Locale.ROOT, "%s=%s", prefix, this.toString()); + } + +} + diff --git a/pe/src/main/java/org/thingsboard/client/model/UsageInfo.java b/pe/src/main/java/org/thingsboard/client/model/UsageInfo.java index 8df63a37..22892827 100644 --- a/pe/src/main/java/org/thingsboard/client/model/UsageInfo.java +++ b/pe/src/main/java/org/thingsboard/client/model/UsageInfo.java @@ -63,7 +63,9 @@ UsageInfo.JSON_PROPERTY_ALARMS, UsageInfo.JSON_PROPERTY_MAX_ALARMS, UsageInfo.JSON_PROPERTY_REPORTS, - UsageInfo.JSON_PROPERTY_MAX_REPORTS + UsageInfo.JSON_PROPERTY_MAX_REPORTS, + UsageInfo.JSON_PROPERTY_AI_CREDITS, + UsageInfo.JSON_PROPERTY_MAX_AI_CREDITS }) @Generated(value = "org.openapitools.codegen.languages.JavaClientCodegen", comments = "Generator version: 7.20.0") public class UsageInfo { @@ -175,6 +177,14 @@ public class UsageInfo { @Nullable private Long maxReports; + public static final String JSON_PROPERTY_AI_CREDITS = "aiCredits"; + @Nullable + private Long aiCredits; + + public static final String JSON_PROPERTY_MAX_AI_CREDITS = "maxAiCredits"; + @Nullable + private Long maxAiCredits; + public UsageInfo() { } @@ -826,6 +836,54 @@ public void setMaxReports(@Nullable Long maxReports) { } + public UsageInfo aiCredits(@Nullable Long aiCredits) { + this.aiCredits = aiCredits; + return this; + } + + /** + * Get aiCredits + * @return aiCredits + */ + @Nullable + @JsonProperty(value = JSON_PROPERTY_AI_CREDITS, required = false) + @JsonInclude(value = JsonInclude.Include.USE_DEFAULTS) + public Long getAiCredits() { + return aiCredits; + } + + + @JsonProperty(value = JSON_PROPERTY_AI_CREDITS, required = false) + @JsonInclude(value = JsonInclude.Include.USE_DEFAULTS) + public void setAiCredits(@Nullable Long aiCredits) { + this.aiCredits = aiCredits; + } + + + public UsageInfo maxAiCredits(@Nullable Long maxAiCredits) { + this.maxAiCredits = maxAiCredits; + return this; + } + + /** + * Get maxAiCredits + * @return maxAiCredits + */ + @Nullable + @JsonProperty(value = JSON_PROPERTY_MAX_AI_CREDITS, required = false) + @JsonInclude(value = JsonInclude.Include.USE_DEFAULTS) + public Long getMaxAiCredits() { + return maxAiCredits; + } + + + @JsonProperty(value = JSON_PROPERTY_MAX_AI_CREDITS, required = false) + @JsonInclude(value = JsonInclude.Include.USE_DEFAULTS) + public void setMaxAiCredits(@Nullable Long maxAiCredits) { + this.maxAiCredits = maxAiCredits; + } + + /** * Return true if this UsageInfo object is equal to o. */ @@ -864,12 +922,14 @@ public boolean equals(Object o) { Objects.equals(this.alarms, usageInfo.alarms) && Objects.equals(this.maxAlarms, usageInfo.maxAlarms) && Objects.equals(this.reports, usageInfo.reports) && - Objects.equals(this.maxReports, usageInfo.maxReports); + Objects.equals(this.maxReports, usageInfo.maxReports) && + Objects.equals(this.aiCredits, usageInfo.aiCredits) && + Objects.equals(this.maxAiCredits, usageInfo.maxAiCredits); } @Override public int hashCode() { - return Objects.hash(devices, maxDevices, assets, maxAssets, customers, maxCustomers, users, maxUsers, dashboards, maxDashboards, edges, maxEdges, transportMessages, maxTransportMessages, jsExecutions, tbelExecutions, maxJsExecutions, maxTbelExecutions, emails, maxEmails, sms, maxSms, smsEnabled, alarms, maxAlarms, reports, maxReports); + return Objects.hash(devices, maxDevices, assets, maxAssets, customers, maxCustomers, users, maxUsers, dashboards, maxDashboards, edges, maxEdges, transportMessages, maxTransportMessages, jsExecutions, tbelExecutions, maxJsExecutions, maxTbelExecutions, emails, maxEmails, sms, maxSms, smsEnabled, alarms, maxAlarms, reports, maxReports, aiCredits, maxAiCredits); } @Override @@ -903,6 +963,8 @@ public String toString() { sb.append(" maxAlarms: ").append(toIndentedString(maxAlarms)).append("\n"); sb.append(" reports: ").append(toIndentedString(reports)).append("\n"); sb.append(" maxReports: ").append(toIndentedString(maxReports)).append("\n"); + sb.append(" aiCredits: ").append(toIndentedString(aiCredits)).append("\n"); + sb.append(" maxAiCredits: ").append(toIndentedString(maxAiCredits)).append("\n"); sb.append("}"); return sb.toString(); } @@ -1085,6 +1147,16 @@ public String toUrlQueryString(String prefix) { joiner.add(String.format(java.util.Locale.ROOT, "%smaxReports%s=%s", prefix, suffix, ApiClient.urlEncode(ApiClient.valueToString(getMaxReports())))); } + // add `aiCredits` to the URL query string + if (getAiCredits() != null) { + joiner.add(String.format(java.util.Locale.ROOT, "%saiCredits%s=%s", prefix, suffix, ApiClient.urlEncode(ApiClient.valueToString(getAiCredits())))); + } + + // add `maxAiCredits` to the URL query string + if (getMaxAiCredits() != null) { + joiner.add(String.format(java.util.Locale.ROOT, "%smaxAiCredits%s=%s", prefix, suffix, ApiClient.urlEncode(ApiClient.valueToString(getMaxAiCredits())))); + } + return joiner.toString(); } }