|
@@ -15,9 +15,7 @@ |
|
@@ -15,9 +15,7 @@ |
15
|
*/
|
15
|
*/
|
16
|
package org.thingsboard.server.controller;
|
16
|
package org.thingsboard.server.controller;
|
17
|
|
17
|
|
18
|
-import com.fasterxml.jackson.core.JsonProcessingException;
|
|
|
19
|
import com.fasterxml.jackson.databind.JsonNode;
|
18
|
import com.fasterxml.jackson.databind.JsonNode;
|
20
|
-import com.fasterxml.jackson.databind.ObjectMapper;
|
|
|
21
|
import com.google.common.base.Function;
|
19
|
import com.google.common.base.Function;
|
22
|
import com.google.common.util.concurrent.FutureCallback;
|
20
|
import com.google.common.util.concurrent.FutureCallback;
|
23
|
import com.google.common.util.concurrent.Futures;
|
21
|
import com.google.common.util.concurrent.Futures;
|
|
@@ -46,6 +44,7 @@ import org.springframework.web.bind.annotation.RequestParam; |
|
@@ -46,6 +44,7 @@ import org.springframework.web.bind.annotation.RequestParam; |
46
|
import org.springframework.web.bind.annotation.ResponseBody;
|
44
|
import org.springframework.web.bind.annotation.ResponseBody;
|
47
|
import org.springframework.web.bind.annotation.RestController;
|
45
|
import org.springframework.web.bind.annotation.RestController;
|
48
|
import org.springframework.web.context.request.async.DeferredResult;
|
46
|
import org.springframework.web.context.request.async.DeferredResult;
|
|
|
47
|
+import org.thingsboard.common.util.JacksonUtil;
|
49
|
import org.thingsboard.common.util.ThingsBoardThreadFactory;
|
48
|
import org.thingsboard.common.util.ThingsBoardThreadFactory;
|
50
|
import org.thingsboard.rule.engine.api.msg.DeviceAttributesEventNotificationMsg;
|
49
|
import org.thingsboard.rule.engine.api.msg.DeviceAttributesEventNotificationMsg;
|
51
|
import org.thingsboard.server.common.data.DataConstants;
|
50
|
import org.thingsboard.server.common.data.DataConstants;
|
|
@@ -90,7 +89,6 @@ import org.thingsboard.server.service.telemetry.exception.UncheckedApiException; |
|
@@ -90,7 +89,6 @@ import org.thingsboard.server.service.telemetry.exception.UncheckedApiException; |
90
|
import javax.annotation.Nullable;
|
89
|
import javax.annotation.Nullable;
|
91
|
import javax.annotation.PostConstruct;
|
90
|
import javax.annotation.PostConstruct;
|
92
|
import javax.annotation.PreDestroy;
|
91
|
import javax.annotation.PreDestroy;
|
93
|
-import java.io.IOException;
|
|
|
94
|
import java.util.ArrayList;
|
92
|
import java.util.ArrayList;
|
95
|
import java.util.Arrays;
|
93
|
import java.util.Arrays;
|
96
|
import java.util.HashSet;
|
94
|
import java.util.HashSet;
|
|
@@ -103,12 +101,41 @@ import java.util.concurrent.Executors; |
|
@@ -103,12 +101,41 @@ import java.util.concurrent.Executors; |
103
|
import java.util.concurrent.TimeUnit;
|
101
|
import java.util.concurrent.TimeUnit;
|
104
|
import java.util.stream.Collectors;
|
102
|
import java.util.stream.Collectors;
|
105
|
|
103
|
|
|
|
104
|
+import static org.thingsboard.server.controller.ControllerConstants.ATTRIBUTES_JSON_REQUEST_DESCRIPTION;
|
|
|
105
|
+import static org.thingsboard.server.controller.ControllerConstants.ATTRIBUTES_KEYS_DESCRIPTION;
|
|
|
106
|
+import static org.thingsboard.server.controller.ControllerConstants.ATTRIBUTES_SCOPE_ALLOWED_VALUES;
|
|
|
107
|
+import static org.thingsboard.server.controller.ControllerConstants.ATTRIBUTES_SCOPE_DESCRIPTION;
|
|
|
108
|
+import static org.thingsboard.server.controller.ControllerConstants.ATTRIBUTE_DATA_EXAMPLE;
|
|
|
109
|
+import static org.thingsboard.server.controller.ControllerConstants.DEVICE_ID;
|
106
|
import static org.thingsboard.server.controller.ControllerConstants.DEVICE_ID_PARAM_DESCRIPTION;
|
110
|
import static org.thingsboard.server.controller.ControllerConstants.DEVICE_ID_PARAM_DESCRIPTION;
|
|
|
111
|
+import static org.thingsboard.server.controller.ControllerConstants.ENTITY_ATTRIBUTE_SCOPES;
|
107
|
import static org.thingsboard.server.controller.ControllerConstants.ENTITY_ID_PARAM_DESCRIPTION;
|
112
|
import static org.thingsboard.server.controller.ControllerConstants.ENTITY_ID_PARAM_DESCRIPTION;
|
108
|
import static org.thingsboard.server.controller.ControllerConstants.ENTITY_TYPE_PARAM_DESCRIPTION;
|
113
|
import static org.thingsboard.server.controller.ControllerConstants.ENTITY_TYPE_PARAM_DESCRIPTION;
|
|
|
114
|
+import static org.thingsboard.server.controller.ControllerConstants.INVALID_ENTITY_ID_OR_ENTITY_TYPE_DESCRIPTION;
|
|
|
115
|
+import static org.thingsboard.server.controller.ControllerConstants.INVALID_STRUCTURE_OF_THE_REQUEST;
|
|
|
116
|
+import static org.thingsboard.server.controller.ControllerConstants.LATEST_TS_NON_STRICT_DATA_EXAMPLE;
|
|
|
117
|
+import static org.thingsboard.server.controller.ControllerConstants.LATEST_TS_STRICT_DATA_EXAMPLE;
|
|
|
118
|
+import static org.thingsboard.server.controller.ControllerConstants.MARKDOWN_CODE_BLOCK_END;
|
|
|
119
|
+import static org.thingsboard.server.controller.ControllerConstants.MARKDOWN_CODE_BLOCK_START;
|
|
|
120
|
+import static org.thingsboard.server.controller.ControllerConstants.SAVE_ATTIRIBUTES_STATUS_BAD_REQUEST;
|
|
|
121
|
+import static org.thingsboard.server.controller.ControllerConstants.SAVE_ATTIRIBUTES_STATUS_OK;
|
|
|
122
|
+import static org.thingsboard.server.controller.ControllerConstants.SAVE_ATTRIBUTES_REQUEST_PAYLOAD;
|
|
|
123
|
+import static org.thingsboard.server.controller.ControllerConstants.SAVE_ENTITY_ATTRIBUTES_STATUS_INTERNAL_SERVER_ERROR;
|
|
|
124
|
+import static org.thingsboard.server.controller.ControllerConstants.SAVE_ENTITY_ATTRIBUTES_STATUS_OK;
|
|
|
125
|
+import static org.thingsboard.server.controller.ControllerConstants.SAVE_ENTITY_ATTRIBUTES_STATUS_UNAUTHORIZED;
|
|
|
126
|
+import static org.thingsboard.server.controller.ControllerConstants.SAVE_ENTITY_TIMESERIES_STATUS_INTERNAL_SERVER_ERROR;
|
|
|
127
|
+import static org.thingsboard.server.controller.ControllerConstants.SAVE_ENTITY_TIMESERIES_STATUS_OK;
|
|
|
128
|
+import static org.thingsboard.server.controller.ControllerConstants.SAVE_ENTITY_TIMESERIES_STATUS_UNAUTHORIZED;
|
|
|
129
|
+import static org.thingsboard.server.controller.ControllerConstants.SAVE_TIMESERIES_REQUEST_PAYLOAD;
|
109
|
import static org.thingsboard.server.controller.ControllerConstants.SORT_ORDER_ALLOWABLE_VALUES;
|
130
|
import static org.thingsboard.server.controller.ControllerConstants.SORT_ORDER_ALLOWABLE_VALUES;
|
110
|
import static org.thingsboard.server.controller.ControllerConstants.SORT_ORDER_DESCRIPTION;
|
131
|
import static org.thingsboard.server.controller.ControllerConstants.SORT_ORDER_DESCRIPTION;
|
|
|
132
|
+import static org.thingsboard.server.controller.ControllerConstants.STRICT_DATA_TYPES_DESCRIPTION;
|
|
|
133
|
+import static org.thingsboard.server.controller.ControllerConstants.TELEMETRY_JSON_REQUEST_DESCRIPTION;
|
|
|
134
|
+import static org.thingsboard.server.controller.ControllerConstants.TELEMETRY_KEYS_BASE_DESCRIPTION;
|
|
|
135
|
+import static org.thingsboard.server.controller.ControllerConstants.TELEMETRY_KEYS_DESCRIPTION;
|
|
|
136
|
+import static org.thingsboard.server.controller.ControllerConstants.TELEMETRY_SCOPE_DESCRIPTION;
|
111
|
import static org.thingsboard.server.controller.ControllerConstants.TENANT_OR_CUSTOMER_AUTHORITY_PARAGRAPH;
|
137
|
import static org.thingsboard.server.controller.ControllerConstants.TENANT_OR_CUSTOMER_AUTHORITY_PARAGRAPH;
|
|
|
138
|
+import static org.thingsboard.server.controller.ControllerConstants.TS_STRICT_DATA_EXAMPLE;
|
112
|
|
139
|
|
113
|
|
140
|
|
114
|
/**
|
141
|
/**
|
|
@@ -120,48 +147,6 @@ import static org.thingsboard.server.controller.ControllerConstants.TENANT_OR_CU |
|
@@ -120,48 +147,6 @@ import static org.thingsboard.server.controller.ControllerConstants.TENANT_OR_CU |
120
|
@Slf4j
|
147
|
@Slf4j
|
121
|
public class TelemetryController extends BaseController {
|
148
|
public class TelemetryController extends BaseController {
|
122
|
|
149
|
|
123
|
- private static final String ATTRIBUTES_SCOPE_DESCRIPTION = "A string value representing the attributes scope. For example, 'SERVER_SCOPE'.";
|
|
|
124
|
- private static final String ATTRIBUTES_KEYS_DESCRIPTION = "A string value representing the comma-separated list of attributes keys. For example, 'active,inactivityAlarmTime'.";
|
|
|
125
|
- private static final String ATTRIBUTES_SCOPE_ALLOWED_VALUES = "SERVER_SCOPE, CLIENT_SCOPE, SHARED_SCOPE";
|
|
|
126
|
- private static final String ATTRIBUTES_JSON_REQUEST_DESCRIPTION = "A string value representing the json object. For example, '{\"key\":\"value\"}'";
|
|
|
127
|
- private static final String ATTRIBUTE_DATA_CLASS_DESCRIPTION = "AttributeData class represents information regarding a particular attribute and includes the next parameters: 'lastUpdatesTs' - a long value representing the timestamp of the last attribute modification in milliseconds. 'key' - attribute key name, and 'value' - attribute value.";
|
|
|
128
|
- private static final String GET_ALL_ATTRIBUTES_BASE_DESCRIPTION = "Returns a JSON structure that represents a list of AttributeData class objects for the selected entity based on the specified comma-separated list of attribute key names. " + ATTRIBUTE_DATA_CLASS_DESCRIPTION;
|
|
|
129
|
- private static final String GET_ALL_ATTRIBUTES_BY_SCOPE_BASE_DESCRIPTION = "Returns a JSON structure that represents a list of AttributeData class objects for the selected entity based on the attributes scope selected and a comma-separated list of attribute key names. " + ATTRIBUTE_DATA_CLASS_DESCRIPTION;
|
|
|
130
|
-
|
|
|
131
|
- private static final String TS_DATA_CLASS_DESCRIPTION = "TsData class is a timeseries data point for specific telemetry key that includes 'value' - object value, and 'ts' - a long value representing timestamp in milliseconds for this value. ";
|
|
|
132
|
-
|
|
|
133
|
- private static final String TELEMETRY_KEYS_BASE_DESCRIPTION = "A string value representing the comma-separated list of telemetry keys.";
|
|
|
134
|
- private static final String TELEMETRY_KEYS_DESCRIPTION = TELEMETRY_KEYS_BASE_DESCRIPTION + " If keys are not selected, the result will return all latest timeseries. For example, 'temp,humidity'.";
|
|
|
135
|
- private static final String TELEMETRY_SCOPE_DESCRIPTION = "Value is not used in the API call implementation. However, you need to specify whatever value cause scope is a path variable.";
|
|
|
136
|
- private static final String TELEMETRY_JSON_REQUEST_DESCRIPTION = "A string value representing the json object. For example, '{\"key\":\"value\"}' or '{\"ts\":1527863043000,\"values\":{\"key1\":\"value1\",\"key2\":\"value2\"}}' or [{\"ts\":1527863043000,\"values\":{\"key1\":\"value1\",\"key2\":\"value2\"}}, {\"ts\":1527863053000,\"values\":{\"key1\":\"value3\",\"key2\":\"value4\"}}]";
|
|
|
137
|
-
|
|
|
138
|
-
|
|
|
139
|
- private static final String STRICT_DATA_TYPES_DESCRIPTION = "A boolean value to specify if values of selected telemetry keys will represent string values(by default) or use strict data type.";
|
|
|
140
|
- private static final String INVALID_ENTITY_ID_OR_ENTITY_TYPE_DESCRIPTION = "Referencing a non-existing entity Id or invalid entity type will cause an error. ";
|
|
|
141
|
-
|
|
|
142
|
- private static final String SAVE_ENTITY_ATTRIBUTES_DESCRIPTION = "Creates or updates the entity attributes based on entity id, entity type, specified attributes scope " +
|
|
|
143
|
- "and request payload that represents a JSON object with key-value format of attributes to create or update. " +
|
|
|
144
|
- "For example, '{\"temperature\": 26}'. Key is a unique parameter and cannot be overwritten. Only value can be overwritten for the key. ";
|
|
|
145
|
- private static final String SAVE_ATTIRIBUTES_STATUS_OK = "Attribute from the request was created or updated. ";
|
|
|
146
|
- private static final String INVALID_STRUCTURE_OF_THE_REQUEST = "Invalid structure of the request";
|
|
|
147
|
- private static final String SAVE_ATTIRIBUTES_STATUS_BAD_REQUEST = INVALID_STRUCTURE_OF_THE_REQUEST + " or invalid attributes scope provided.";
|
|
|
148
|
- private static final String SAVE_ENTITY_ATTRIBUTES_STATUS_OK = "Platform creates an audit log event about entity attributes updates with action type 'ATTRIBUTES_UPDATED', " +
|
|
|
149
|
- "and also sends event msg to the rule engine with msg type 'ATTRIBUTES_UPDATED'.";
|
|
|
150
|
- private static final String SAVE_ENTITY_ATTRIBUTES_STATUS_UNAUTHORIZED = "User is not authorized to save entity attributes for selected entity. Most likely, User belongs to different Customer or Tenant.";
|
|
|
151
|
- private static final String SAVE_ENTITY_ATTRIBUTES_STATUS_INTERNAL_SERVER_ERROR = "The exception was thrown during processing the request. " +
|
|
|
152
|
- "Platform creates an audit log event about entity attributes updates with action type 'ATTRIBUTES_UPDATED' that includes an error stacktrace.";
|
|
|
153
|
- private static final String SAVE_ENTITY_TIMESERIES_DESCRIPTION = "Creates or updates the entity timeseries based on entity id, entity type " +
|
|
|
154
|
- "and request payload that represents a JSON object with key-value or ts-values format. " +
|
|
|
155
|
- "For example, '{\"temperature\": 26}' or '{\"ts\":1634712287000,\"values\":{\"temperature\":26, \"humidity\":87}}', " +
|
|
|
156
|
- "or JSON array with inner objects inside of ts-values format. " +
|
|
|
157
|
- "For example, '[{\"ts\":1634712287000,\"values\":{\"temperature\":26, \"humidity\":87}}, {\"ts\":1634712588000,\"values\":{\"temperature\":25, \"humidity\":88}}]'. " +
|
|
|
158
|
- "The scope parameter is not used in the API call implementation but should be specified whatever value because it is used as a path variable. ";
|
|
|
159
|
- private static final String SAVE_ENTITY_TIMESERIES_STATUS_OK = "Timeseries from the request was created or updated. " +
|
|
|
160
|
- "Platform creates an audit log event about entity timeseries updates with action type 'TIMESERIES_UPDATED'.";
|
|
|
161
|
- private static final String SAVE_ENTITY_TIMESERIES_STATUS_UNAUTHORIZED = "User is not authorized to save entity timeseries for selected entity. Most likely, User belongs to different Customer or Tenant.";
|
|
|
162
|
- private static final String SAVE_ENTITY_TIMESERIES_STATUS_INTERNAL_SERVER_ERROR = "The exception was thrown during processing the request. " +
|
|
|
163
|
- "Platform creates an audit log event about entity timeseries updates with action type 'TIMESERIES_UPDATED' that includes an error stacktrace.";
|
|
|
164
|
-
|
|
|
165
|
@Autowired
|
150
|
@Autowired
|
166
|
private TimeseriesService tsService;
|
151
|
private TimeseriesService tsService;
|
167
|
|
152
|
|
|
@@ -173,8 +158,6 @@ public class TelemetryController extends BaseController { |
|
@@ -173,8 +158,6 @@ public class TelemetryController extends BaseController { |
173
|
|
158
|
|
174
|
private ExecutorService executor;
|
159
|
private ExecutorService executor;
|
175
|
|
160
|
|
176
|
- private static final ObjectMapper mapper = new ObjectMapper();
|
|
|
177
|
-
|
|
|
178
|
@PostConstruct
|
161
|
@PostConstruct
|
179
|
public void initExecutor() {
|
162
|
public void initExecutor() {
|
180
|
executor = Executors.newSingleThreadExecutor(ThingsBoardThreadFactory.forName("telemetry-controller"));
|
163
|
executor = Executors.newSingleThreadExecutor(ThingsBoardThreadFactory.forName("telemetry-controller"));
|
|
@@ -188,96 +171,117 @@ public class TelemetryController extends BaseController { |
|
@@ -188,96 +171,117 @@ public class TelemetryController extends BaseController { |
188
|
}
|
171
|
}
|
189
|
|
172
|
|
190
|
@ApiOperation(value = "Get all attribute keys (getAttributeKeys)",
|
173
|
@ApiOperation(value = "Get all attribute keys (getAttributeKeys)",
|
191
|
- notes = "Returns a list of all attribute key names for the selected entity. " +
|
|
|
192
|
- "In the case of device entity specified, a response will include merged attribute key names list from each scope: " +
|
|
|
193
|
- "SERVER_SCOPE, CLIENT_SCOPE, SHARED_SCOPE. "
|
|
|
194
|
- + INVALID_ENTITY_ID_OR_ENTITY_TYPE_DESCRIPTION + TENANT_OR_CUSTOMER_AUTHORITY_PARAGRAPH,
|
174
|
+ notes = "Returns a set of unique attribute key names for the selected entity. " +
|
|
|
175
|
+ "The response will include merged key names set for all attribute scopes:" +
|
|
|
176
|
+ "\n\n * SERVER_SCOPE - supported for all entity types;" +
|
|
|
177
|
+ "\n * CLIENT_SCOPE - supported for devices;" +
|
|
|
178
|
+ "\n * SHARED_SCOPE - supported for devices. "
|
|
|
179
|
+ + "\n\n" + INVALID_ENTITY_ID_OR_ENTITY_TYPE_DESCRIPTION + TENANT_OR_CUSTOMER_AUTHORITY_PARAGRAPH,
|
195
|
produces = MediaType.APPLICATION_JSON_VALUE)
|
180
|
produces = MediaType.APPLICATION_JSON_VALUE)
|
196
|
@PreAuthorize("hasAnyAuthority('SYS_ADMIN', 'TENANT_ADMIN', 'CUSTOMER_USER')")
|
181
|
@PreAuthorize("hasAnyAuthority('SYS_ADMIN', 'TENANT_ADMIN', 'CUSTOMER_USER')")
|
197
|
@RequestMapping(value = "/{entityType}/{entityId}/keys/attributes", method = RequestMethod.GET)
|
182
|
@RequestMapping(value = "/{entityType}/{entityId}/keys/attributes", method = RequestMethod.GET)
|
198
|
@ResponseBody
|
183
|
@ResponseBody
|
199
|
public DeferredResult<ResponseEntity> getAttributeKeys(
|
184
|
public DeferredResult<ResponseEntity> getAttributeKeys(
|
200
|
- @ApiParam(value = ENTITY_TYPE_PARAM_DESCRIPTION) @PathVariable("entityType") String entityType,
|
|
|
201
|
- @ApiParam(value = ENTITY_ID_PARAM_DESCRIPTION) @PathVariable("entityId") String entityIdStr) throws ThingsboardException {
|
185
|
+ @ApiParam(value = ENTITY_TYPE_PARAM_DESCRIPTION, required = true, defaultValue = "DEVICE") @PathVariable("entityType") String entityType,
|
|
|
186
|
+ @ApiParam(value = ENTITY_ID_PARAM_DESCRIPTION, required = true) @PathVariable("entityId") String entityIdStr) throws ThingsboardException {
|
202
|
return accessValidator.validateEntityAndCallback(getCurrentUser(), Operation.READ_ATTRIBUTES, entityType, entityIdStr, this::getAttributeKeysCallback);
|
187
|
return accessValidator.validateEntityAndCallback(getCurrentUser(), Operation.READ_ATTRIBUTES, entityType, entityIdStr, this::getAttributeKeysCallback);
|
203
|
}
|
188
|
}
|
204
|
|
189
|
|
205
|
- @ApiOperation(value = "Get all attributes keys by scope (getAttributeKeysByScope)",
|
|
|
206
|
- notes = "Returns a list of attribute key names from the specified attributes scope for the selected entity. " +
|
|
|
207
|
- "If scope parameter is omitted, Get all attribute keys(getAttributeKeys) API will be called. "
|
|
|
208
|
- + INVALID_ENTITY_ID_OR_ENTITY_TYPE_DESCRIPTION + TENANT_OR_CUSTOMER_AUTHORITY_PARAGRAPH,
|
190
|
+ @ApiOperation(value = "Get all attribute keys by scope (getAttributeKeysByScope)",
|
|
|
191
|
+ notes = "Returns a set of unique attribute key names for the selected entity and attributes scope: " +
|
|
|
192
|
+ "\n\n * SERVER_SCOPE - supported for all entity types;" +
|
|
|
193
|
+ "\n * CLIENT_SCOPE - supported for devices;" +
|
|
|
194
|
+ "\n * SHARED_SCOPE - supported for devices. "
|
|
|
195
|
+ + "\n\n" + INVALID_ENTITY_ID_OR_ENTITY_TYPE_DESCRIPTION + TENANT_OR_CUSTOMER_AUTHORITY_PARAGRAPH,
|
209
|
produces = MediaType.APPLICATION_JSON_VALUE)
|
196
|
produces = MediaType.APPLICATION_JSON_VALUE)
|
210
|
@PreAuthorize("hasAnyAuthority('SYS_ADMIN', 'TENANT_ADMIN', 'CUSTOMER_USER')")
|
197
|
@PreAuthorize("hasAnyAuthority('SYS_ADMIN', 'TENANT_ADMIN', 'CUSTOMER_USER')")
|
211
|
@RequestMapping(value = "/{entityType}/{entityId}/keys/attributes/{scope}", method = RequestMethod.GET)
|
198
|
@RequestMapping(value = "/{entityType}/{entityId}/keys/attributes/{scope}", method = RequestMethod.GET)
|
212
|
@ResponseBody
|
199
|
@ResponseBody
|
213
|
public DeferredResult<ResponseEntity> getAttributeKeysByScope(
|
200
|
public DeferredResult<ResponseEntity> getAttributeKeysByScope(
|
214
|
- @ApiParam(value = ENTITY_TYPE_PARAM_DESCRIPTION) @PathVariable("entityType") String entityType,
|
|
|
215
|
- @ApiParam(value = ENTITY_ID_PARAM_DESCRIPTION) @PathVariable("entityId") String entityIdStr,
|
|
|
216
|
- @ApiParam(value = ATTRIBUTES_SCOPE_DESCRIPTION, allowableValues = ATTRIBUTES_SCOPE_ALLOWED_VALUES) @PathVariable("scope") String scope) throws ThingsboardException {
|
201
|
+ @ApiParam(value = ENTITY_TYPE_PARAM_DESCRIPTION, required = true, defaultValue = "DEVICE") @PathVariable("entityType") String entityType,
|
|
|
202
|
+ @ApiParam(value = ENTITY_ID_PARAM_DESCRIPTION, required = true) @PathVariable("entityId") String entityIdStr,
|
|
|
203
|
+ @ApiParam(value = ATTRIBUTES_SCOPE_DESCRIPTION, required = true, allowableValues = ATTRIBUTES_SCOPE_ALLOWED_VALUES) @PathVariable("scope") String scope) throws ThingsboardException {
|
217
|
return accessValidator.validateEntityAndCallback(getCurrentUser(), Operation.READ_ATTRIBUTES, entityType, entityIdStr,
|
204
|
return accessValidator.validateEntityAndCallback(getCurrentUser(), Operation.READ_ATTRIBUTES, entityType, entityIdStr,
|
218
|
(result, tenantId, entityId) -> getAttributeKeysCallback(result, tenantId, entityId, scope));
|
205
|
(result, tenantId, entityId) -> getAttributeKeysCallback(result, tenantId, entityId, scope));
|
219
|
}
|
206
|
}
|
220
|
|
207
|
|
221
|
@ApiOperation(value = "Get attributes (getAttributes)",
|
208
|
@ApiOperation(value = "Get attributes (getAttributes)",
|
222
|
- notes = GET_ALL_ATTRIBUTES_BASE_DESCRIPTION + " If 'keys' parameter is omitted, AttributeData class objects will be added to the response for all existing keys of the selected entity. " +
|
|
|
223
|
- INVALID_ENTITY_ID_OR_ENTITY_TYPE_DESCRIPTION + TENANT_OR_CUSTOMER_AUTHORITY_PARAGRAPH,
|
209
|
+ notes = "Returns all attributes that belong to specified entity. Use optional 'keys' parameter to return specific attributes."
|
|
|
210
|
+ + "\n Example of the result: \n\n"
|
|
|
211
|
+ + MARKDOWN_CODE_BLOCK_START
|
|
|
212
|
+ + ATTRIBUTE_DATA_EXAMPLE
|
|
|
213
|
+ + MARKDOWN_CODE_BLOCK_END
|
|
|
214
|
+ + "\n\n " + INVALID_ENTITY_ID_OR_ENTITY_TYPE_DESCRIPTION + TENANT_OR_CUSTOMER_AUTHORITY_PARAGRAPH,
|
224
|
produces = MediaType.APPLICATION_JSON_VALUE)
|
215
|
produces = MediaType.APPLICATION_JSON_VALUE)
|
225
|
@PreAuthorize("hasAnyAuthority('SYS_ADMIN', 'TENANT_ADMIN', 'CUSTOMER_USER')")
|
216
|
@PreAuthorize("hasAnyAuthority('SYS_ADMIN', 'TENANT_ADMIN', 'CUSTOMER_USER')")
|
226
|
@RequestMapping(value = "/{entityType}/{entityId}/values/attributes", method = RequestMethod.GET)
|
217
|
@RequestMapping(value = "/{entityType}/{entityId}/values/attributes", method = RequestMethod.GET)
|
227
|
@ResponseBody
|
218
|
@ResponseBody
|
228
|
public DeferredResult<ResponseEntity> getAttributes(
|
219
|
public DeferredResult<ResponseEntity> getAttributes(
|
229
|
- @ApiParam(value = ENTITY_TYPE_PARAM_DESCRIPTION) @PathVariable("entityType") String entityType,
|
|
|
230
|
- @ApiParam(value = ENTITY_ID_PARAM_DESCRIPTION) @PathVariable("entityId") String entityIdStr,
|
220
|
+ @ApiParam(value = ENTITY_TYPE_PARAM_DESCRIPTION, required = true, defaultValue = "DEVICE") @PathVariable("entityType") String entityType,
|
|
|
221
|
+ @ApiParam(value = ENTITY_ID_PARAM_DESCRIPTION, required = true) @PathVariable("entityId") String entityIdStr,
|
231
|
@ApiParam(value = ATTRIBUTES_KEYS_DESCRIPTION) @RequestParam(name = "keys", required = false) String keysStr) throws ThingsboardException {
|
222
|
@ApiParam(value = ATTRIBUTES_KEYS_DESCRIPTION) @RequestParam(name = "keys", required = false) String keysStr) throws ThingsboardException {
|
232
|
SecurityUser user = getCurrentUser();
|
223
|
SecurityUser user = getCurrentUser();
|
233
|
return accessValidator.validateEntityAndCallback(getCurrentUser(), Operation.READ_ATTRIBUTES, entityType, entityIdStr,
|
224
|
return accessValidator.validateEntityAndCallback(getCurrentUser(), Operation.READ_ATTRIBUTES, entityType, entityIdStr,
|
234
|
(result, tenantId, entityId) -> getAttributeValuesCallback(result, user, entityId, null, keysStr));
|
225
|
(result, tenantId, entityId) -> getAttributeValuesCallback(result, user, entityId, null, keysStr));
|
235
|
}
|
226
|
}
|
236
|
|
227
|
|
|
|
228
|
+
|
237
|
@ApiOperation(value = "Get attributes by scope (getAttributesByScope)",
|
229
|
@ApiOperation(value = "Get attributes by scope (getAttributesByScope)",
|
238
|
- notes = GET_ALL_ATTRIBUTES_BY_SCOPE_BASE_DESCRIPTION + " In case that 'keys' parameter is not selected, " +
|
|
|
239
|
- "AttributeData class objects will be added to the response for all existing attribute keys from the " +
|
|
|
240
|
- "specified attributes scope of the selected entity. If 'scope' parameter is omitted, " +
|
|
|
241
|
- "Get attributes (getAttributes) API will be called. " + INVALID_ENTITY_ID_OR_ENTITY_TYPE_DESCRIPTION + TENANT_OR_CUSTOMER_AUTHORITY_PARAGRAPH,
|
230
|
+ notes = "Returns all attributes of a specified scope that belong to specified entity." +
|
|
|
231
|
+ ENTITY_ATTRIBUTE_SCOPES +
|
|
|
232
|
+ "Use optional 'keys' parameter to return specific attributes."
|
|
|
233
|
+ + "\n Example of the result: \n\n"
|
|
|
234
|
+ + MARKDOWN_CODE_BLOCK_START
|
|
|
235
|
+ + ATTRIBUTE_DATA_EXAMPLE
|
|
|
236
|
+ + MARKDOWN_CODE_BLOCK_END
|
|
|
237
|
+ + "\n\n " + INVALID_ENTITY_ID_OR_ENTITY_TYPE_DESCRIPTION + TENANT_OR_CUSTOMER_AUTHORITY_PARAGRAPH,
|
242
|
produces = MediaType.APPLICATION_JSON_VALUE)
|
238
|
produces = MediaType.APPLICATION_JSON_VALUE)
|
243
|
@PreAuthorize("hasAnyAuthority('SYS_ADMIN', 'TENANT_ADMIN', 'CUSTOMER_USER')")
|
239
|
@PreAuthorize("hasAnyAuthority('SYS_ADMIN', 'TENANT_ADMIN', 'CUSTOMER_USER')")
|
244
|
@RequestMapping(value = "/{entityType}/{entityId}/values/attributes/{scope}", method = RequestMethod.GET)
|
240
|
@RequestMapping(value = "/{entityType}/{entityId}/values/attributes/{scope}", method = RequestMethod.GET)
|
245
|
@ResponseBody
|
241
|
@ResponseBody
|
246
|
public DeferredResult<ResponseEntity> getAttributesByScope(
|
242
|
public DeferredResult<ResponseEntity> getAttributesByScope(
|
247
|
- @ApiParam(value = ENTITY_TYPE_PARAM_DESCRIPTION) @PathVariable("entityType") String entityType,
|
|
|
248
|
- @ApiParam(value = ENTITY_ID_PARAM_DESCRIPTION) @PathVariable("entityId") String entityIdStr,
|
|
|
249
|
- @ApiParam(value = ATTRIBUTES_SCOPE_DESCRIPTION, allowableValues = ATTRIBUTES_SCOPE_ALLOWED_VALUES) @PathVariable("scope") String scope,
|
243
|
+ @ApiParam(value = ENTITY_TYPE_PARAM_DESCRIPTION, required = true, defaultValue = "DEVICE") @PathVariable("entityType") String entityType,
|
|
|
244
|
+ @ApiParam(value = ENTITY_ID_PARAM_DESCRIPTION, required = true) @PathVariable("entityId") String entityIdStr,
|
|
|
245
|
+ @ApiParam(value = ATTRIBUTES_SCOPE_DESCRIPTION, allowableValues = ATTRIBUTES_SCOPE_ALLOWED_VALUES, required = true) @PathVariable("scope") String scope,
|
250
|
@ApiParam(value = ATTRIBUTES_KEYS_DESCRIPTION) @RequestParam(name = "keys", required = false) String keysStr) throws ThingsboardException {
|
246
|
@ApiParam(value = ATTRIBUTES_KEYS_DESCRIPTION) @RequestParam(name = "keys", required = false) String keysStr) throws ThingsboardException {
|
251
|
SecurityUser user = getCurrentUser();
|
247
|
SecurityUser user = getCurrentUser();
|
252
|
return accessValidator.validateEntityAndCallback(getCurrentUser(), Operation.READ_ATTRIBUTES, entityType, entityIdStr,
|
248
|
return accessValidator.validateEntityAndCallback(getCurrentUser(), Operation.READ_ATTRIBUTES, entityType, entityIdStr,
|
253
|
(result, tenantId, entityId) -> getAttributeValuesCallback(result, user, entityId, scope, keysStr));
|
249
|
(result, tenantId, entityId) -> getAttributeValuesCallback(result, user, entityId, scope, keysStr));
|
254
|
}
|
250
|
}
|
255
|
|
251
|
|
256
|
- @ApiOperation(value = "Get timeseries keys (getTimeseriesKeys)",
|
|
|
257
|
- notes = "Returns a list of all telemetry key names for the selected entity based on entity id and entity type specified. " +
|
|
|
258
|
- INVALID_ENTITY_ID_OR_ENTITY_TYPE_DESCRIPTION + TENANT_OR_CUSTOMER_AUTHORITY_PARAGRAPH,
|
252
|
+ @ApiOperation(value = "Get time-series keys (getTimeseriesKeys)",
|
|
|
253
|
+ notes = "Returns a set of unique time-series key names for the selected entity. " +
|
|
|
254
|
+ "\n\n" + INVALID_ENTITY_ID_OR_ENTITY_TYPE_DESCRIPTION + TENANT_OR_CUSTOMER_AUTHORITY_PARAGRAPH,
|
259
|
produces = MediaType.APPLICATION_JSON_VALUE)
|
255
|
produces = MediaType.APPLICATION_JSON_VALUE)
|
260
|
@PreAuthorize("hasAnyAuthority('SYS_ADMIN', 'TENANT_ADMIN', 'CUSTOMER_USER')")
|
256
|
@PreAuthorize("hasAnyAuthority('SYS_ADMIN', 'TENANT_ADMIN', 'CUSTOMER_USER')")
|
261
|
@RequestMapping(value = "/{entityType}/{entityId}/keys/timeseries", method = RequestMethod.GET)
|
257
|
@RequestMapping(value = "/{entityType}/{entityId}/keys/timeseries", method = RequestMethod.GET)
|
262
|
@ResponseBody
|
258
|
@ResponseBody
|
263
|
public DeferredResult<ResponseEntity> getTimeseriesKeys(
|
259
|
public DeferredResult<ResponseEntity> getTimeseriesKeys(
|
264
|
- @ApiParam(value = ENTITY_TYPE_PARAM_DESCRIPTION) @PathVariable("entityType") String entityType,
|
|
|
265
|
- @ApiParam(value = ENTITY_ID_PARAM_DESCRIPTION) @PathVariable("entityId") String entityIdStr) throws ThingsboardException {
|
260
|
+ @ApiParam(value = ENTITY_TYPE_PARAM_DESCRIPTION, required = true, defaultValue = "DEVICE") @PathVariable("entityType") String entityType,
|
|
|
261
|
+ @ApiParam(value = ENTITY_ID_PARAM_DESCRIPTION, required = true) @PathVariable("entityId") String entityIdStr) throws ThingsboardException {
|
266
|
return accessValidator.validateEntityAndCallback(getCurrentUser(), Operation.READ_TELEMETRY, entityType, entityIdStr,
|
262
|
return accessValidator.validateEntityAndCallback(getCurrentUser(), Operation.READ_TELEMETRY, entityType, entityIdStr,
|
267
|
(result, tenantId, entityId) -> Futures.addCallback(tsService.findAllLatest(tenantId, entityId), getTsKeysToResponseCallback(result), MoreExecutors.directExecutor()));
|
263
|
(result, tenantId, entityId) -> Futures.addCallback(tsService.findAllLatest(tenantId, entityId), getTsKeysToResponseCallback(result), MoreExecutors.directExecutor()));
|
268
|
}
|
264
|
}
|
269
|
|
265
|
|
270
|
- @ApiOperation(value = "Get latest timeseries (getLatestTimeseries)",
|
|
|
271
|
- notes = "Returns a JSON structure that represents a Map, where the map key is a telemetry key name " +
|
|
|
272
|
- "and map value - is a singleton list of TsData class objects. "
|
|
|
273
|
- + TS_DATA_CLASS_DESCRIPTION + INVALID_ENTITY_ID_OR_ENTITY_TYPE_DESCRIPTION + TENANT_OR_CUSTOMER_AUTHORITY_PARAGRAPH,
|
266
|
+ @ApiOperation(value = "Get latest time-series value (getLatestTimeseries)",
|
|
|
267
|
+ notes = "Returns all time-series that belong to specified entity. Use optional 'keys' parameter to return specific time-series." +
|
|
|
268
|
+ " The result is a JSON object. The format of the values depends on the 'useStrictDataTypes' parameter." +
|
|
|
269
|
+ " By default, all time-series values are converted to strings: \n\n"
|
|
|
270
|
+ + MARKDOWN_CODE_BLOCK_START
|
|
|
271
|
+ + LATEST_TS_NON_STRICT_DATA_EXAMPLE
|
|
|
272
|
+ + MARKDOWN_CODE_BLOCK_END
|
|
|
273
|
+ + "\n\n However, it is possible to request the values without conversion ('useStrictDataTypes'=true): \n\n"
|
|
|
274
|
+ + MARKDOWN_CODE_BLOCK_START
|
|
|
275
|
+ + LATEST_TS_STRICT_DATA_EXAMPLE
|
|
|
276
|
+ + MARKDOWN_CODE_BLOCK_END
|
|
|
277
|
+ + "\n\n " + INVALID_ENTITY_ID_OR_ENTITY_TYPE_DESCRIPTION + TENANT_OR_CUSTOMER_AUTHORITY_PARAGRAPH,
|
274
|
produces = MediaType.APPLICATION_JSON_VALUE)
|
278
|
produces = MediaType.APPLICATION_JSON_VALUE)
|
275
|
@PreAuthorize("hasAnyAuthority('SYS_ADMIN', 'TENANT_ADMIN', 'CUSTOMER_USER')")
|
279
|
@PreAuthorize("hasAnyAuthority('SYS_ADMIN', 'TENANT_ADMIN', 'CUSTOMER_USER')")
|
276
|
@RequestMapping(value = "/{entityType}/{entityId}/values/timeseries", method = RequestMethod.GET)
|
280
|
@RequestMapping(value = "/{entityType}/{entityId}/values/timeseries", method = RequestMethod.GET)
|
277
|
@ResponseBody
|
281
|
@ResponseBody
|
278
|
public DeferredResult<ResponseEntity> getLatestTimeseries(
|
282
|
public DeferredResult<ResponseEntity> getLatestTimeseries(
|
279
|
- @ApiParam(value = ENTITY_TYPE_PARAM_DESCRIPTION) @PathVariable("entityType") String entityType,
|
|
|
280
|
- @ApiParam(value = ENTITY_ID_PARAM_DESCRIPTION) @PathVariable("entityId") String entityIdStr,
|
283
|
+ @ApiParam(value = ENTITY_TYPE_PARAM_DESCRIPTION, required = true, defaultValue = "DEVICE") @PathVariable("entityType") String entityType,
|
|
|
284
|
+ @ApiParam(value = ENTITY_ID_PARAM_DESCRIPTION, required = true) @PathVariable("entityId") String entityIdStr,
|
281
|
@ApiParam(value = TELEMETRY_KEYS_DESCRIPTION) @RequestParam(name = "keys", required = false) String keysStr,
|
285
|
@ApiParam(value = TELEMETRY_KEYS_DESCRIPTION) @RequestParam(name = "keys", required = false) String keysStr,
|
282
|
@ApiParam(value = STRICT_DATA_TYPES_DESCRIPTION)
|
286
|
@ApiParam(value = STRICT_DATA_TYPES_DESCRIPTION)
|
283
|
@RequestParam(name = "useStrictDataTypes", required = false, defaultValue = "false") Boolean useStrictDataTypes) throws ThingsboardException {
|
287
|
@RequestParam(name = "useStrictDataTypes", required = false, defaultValue = "false") Boolean useStrictDataTypes) throws ThingsboardException {
|
|
@@ -286,24 +290,26 @@ public class TelemetryController extends BaseController { |
|
@@ -286,24 +290,26 @@ public class TelemetryController extends BaseController { |
286
|
(result, tenantId, entityId) -> getLatestTimeseriesValuesCallback(result, user, entityId, keysStr, useStrictDataTypes));
|
290
|
(result, tenantId, entityId) -> getLatestTimeseriesValuesCallback(result, user, entityId, keysStr, useStrictDataTypes));
|
287
|
}
|
291
|
}
|
288
|
|
292
|
|
289
|
- @ApiOperation(value = "Get timeseries (getTimeseries)",
|
|
|
290
|
- notes = "Returns a JSON structure that represents a Map, where the map key is a telemetry key name " +
|
|
|
291
|
- "and map value - is a list of TsData class objects. " + TS_DATA_CLASS_DESCRIPTION +
|
|
|
292
|
- "This method allows us to group original data into intervals and aggregate it using one of the aggregation methods or just limit the number of TsData objects to fetch for each key specified. " +
|
|
|
293
|
- "See the desription of the request parameters for more details. " +
|
|
|
294
|
- "The result can also be sorted in ascending or descending order. "
|
|
|
295
|
- + INVALID_ENTITY_ID_OR_ENTITY_TYPE_DESCRIPTION + TENANT_OR_CUSTOMER_AUTHORITY_PARAGRAPH,
|
293
|
+ @ApiOperation(value = "Get time-series data (getTimeseries)",
|
|
|
294
|
+ notes = "Returns a range of time-series values for specified entity. " +
|
|
|
295
|
+ "Returns not aggregated data by default. " +
|
|
|
296
|
+ "Use aggregation function ('agg') and aggregation interval ('interval') to enable aggregation of the results on the database / server side. " +
|
|
|
297
|
+ "The aggregation is generally more efficient then fetching all records. \n\n"
|
|
|
298
|
+ + MARKDOWN_CODE_BLOCK_START
|
|
|
299
|
+ + TS_STRICT_DATA_EXAMPLE
|
|
|
300
|
+ + MARKDOWN_CODE_BLOCK_END
|
|
|
301
|
+ + "\n\n" + INVALID_ENTITY_ID_OR_ENTITY_TYPE_DESCRIPTION + TENANT_OR_CUSTOMER_AUTHORITY_PARAGRAPH,
|
296
|
produces = MediaType.APPLICATION_JSON_VALUE)
|
302
|
produces = MediaType.APPLICATION_JSON_VALUE)
|
297
|
@PreAuthorize("hasAnyAuthority('SYS_ADMIN', 'TENANT_ADMIN', 'CUSTOMER_USER')")
|
303
|
@PreAuthorize("hasAnyAuthority('SYS_ADMIN', 'TENANT_ADMIN', 'CUSTOMER_USER')")
|
298
|
@RequestMapping(value = "/{entityType}/{entityId}/values/timeseries", method = RequestMethod.GET, params = {"keys", "startTs", "endTs"})
|
304
|
@RequestMapping(value = "/{entityType}/{entityId}/values/timeseries", method = RequestMethod.GET, params = {"keys", "startTs", "endTs"})
|
299
|
@ResponseBody
|
305
|
@ResponseBody
|
300
|
public DeferredResult<ResponseEntity> getTimeseries(
|
306
|
public DeferredResult<ResponseEntity> getTimeseries(
|
301
|
- @ApiParam(value = ENTITY_TYPE_PARAM_DESCRIPTION) @PathVariable("entityType") String entityType,
|
|
|
302
|
- @ApiParam(value = ENTITY_ID_PARAM_DESCRIPTION) @PathVariable("entityId") String entityIdStr,
|
|
|
303
|
- @ApiParam(value = TELEMETRY_KEYS_BASE_DESCRIPTION) @RequestParam(name = "keys") String keys,
|
|
|
304
|
- @ApiParam(value = "A long value representing the start timestamp of search time range in milliseconds.")
|
307
|
+ @ApiParam(value = ENTITY_TYPE_PARAM_DESCRIPTION, required = true, defaultValue = "DEVICE") @PathVariable("entityType") String entityType,
|
|
|
308
|
+ @ApiParam(value = ENTITY_ID_PARAM_DESCRIPTION, required = true) @PathVariable("entityId") String entityIdStr,
|
|
|
309
|
+ @ApiParam(value = TELEMETRY_KEYS_BASE_DESCRIPTION, required = true) @RequestParam(name = "keys") String keys,
|
|
|
310
|
+ @ApiParam(value = "A long value representing the start timestamp of the time range in milliseconds, UTC.")
|
305
|
@RequestParam(name = "startTs") Long startTs,
|
311
|
@RequestParam(name = "startTs") Long startTs,
|
306
|
- @ApiParam(value = "A long value representing the end timestamp of search time range in milliseconds.")
|
312
|
+ @ApiParam(value = "A long value representing the end timestamp of the time range in milliseconds, UTC.")
|
307
|
@RequestParam(name = "endTs") Long endTs,
|
313
|
@RequestParam(name = "endTs") Long endTs,
|
308
|
@ApiParam(value = "A long value representing the aggregation interval range in milliseconds.")
|
314
|
@ApiParam(value = "A long value representing the aggregation interval range in milliseconds.")
|
309
|
@RequestParam(name = "interval", defaultValue = "0") Long interval,
|
315
|
@RequestParam(name = "interval", defaultValue = "0") Long interval,
|
|
@@ -329,11 +335,10 @@ public class TelemetryController extends BaseController { |
|
@@ -329,11 +335,10 @@ public class TelemetryController extends BaseController { |
329
|
});
|
335
|
});
|
330
|
}
|
336
|
}
|
331
|
|
337
|
|
332
|
- @ApiOperation(value = "Save or update device attributes (saveDeviceAttributes)",
|
|
|
333
|
- notes = "Creates or updates the device attributes based on device id, specified attribute scope, " +
|
|
|
334
|
- "and request payload that represents a JSON object with key-value format of attributes to create or update. " +
|
|
|
335
|
- "For example, '{\"temperature\": 26}'. Key is a unique parameter and cannot be overwritten. Only value can " +
|
|
|
336
|
- "be overwritten for the key. " + TENANT_OR_CUSTOMER_AUTHORITY_PARAGRAPH,
|
338
|
+ @ApiOperation(value = "Save device attributes (saveDeviceAttributes)",
|
|
|
339
|
+ notes = "Creates or updates the device attributes based on device id and specified attribute scope. " +
|
|
|
340
|
+ SAVE_ATTRIBUTES_REQUEST_PAYLOAD
|
|
|
341
|
+ + TENANT_OR_CUSTOMER_AUTHORITY_PARAGRAPH,
|
337
|
produces = MediaType.APPLICATION_JSON_VALUE)
|
342
|
produces = MediaType.APPLICATION_JSON_VALUE)
|
338
|
@ApiResponses(value = {
|
343
|
@ApiResponses(value = {
|
339
|
@ApiResponse(code = 200, message = SAVE_ATTIRIBUTES_STATUS_OK +
|
344
|
@ApiResponse(code = 200, message = SAVE_ATTIRIBUTES_STATUS_OK +
|
|
@@ -348,15 +353,18 @@ public class TelemetryController extends BaseController { |
|
@@ -348,15 +353,18 @@ public class TelemetryController extends BaseController { |
348
|
@RequestMapping(value = "/{deviceId}/{scope}", method = RequestMethod.POST)
|
353
|
@RequestMapping(value = "/{deviceId}/{scope}", method = RequestMethod.POST)
|
349
|
@ResponseBody
|
354
|
@ResponseBody
|
350
|
public DeferredResult<ResponseEntity> saveDeviceAttributes(
|
355
|
public DeferredResult<ResponseEntity> saveDeviceAttributes(
|
351
|
- @ApiParam(value = DEVICE_ID_PARAM_DESCRIPTION) @PathVariable("deviceId") String deviceIdStr,
|
|
|
352
|
- @ApiParam(value = ATTRIBUTES_SCOPE_DESCRIPTION, allowableValues = ATTRIBUTES_SCOPE_ALLOWED_VALUES) @PathVariable("scope") String scope,
|
|
|
353
|
- @ApiParam(value = ATTRIBUTES_JSON_REQUEST_DESCRIPTION) @RequestBody JsonNode request) throws ThingsboardException {
|
356
|
+ @ApiParam(value = DEVICE_ID_PARAM_DESCRIPTION, required = true) @PathVariable("deviceId") String deviceIdStr,
|
|
|
357
|
+ @ApiParam(value = ATTRIBUTES_SCOPE_DESCRIPTION, allowableValues = ATTRIBUTES_SCOPE_ALLOWED_VALUES, required = true) @PathVariable("scope") String scope,
|
|
|
358
|
+ @ApiParam(value = ATTRIBUTES_JSON_REQUEST_DESCRIPTION, required = true) @RequestBody JsonNode request) throws ThingsboardException {
|
354
|
EntityId entityId = EntityIdFactory.getByTypeAndUuid(EntityType.DEVICE, deviceIdStr);
|
359
|
EntityId entityId = EntityIdFactory.getByTypeAndUuid(EntityType.DEVICE, deviceIdStr);
|
355
|
return saveAttributes(getTenantId(), entityId, scope, request);
|
360
|
return saveAttributes(getTenantId(), entityId, scope, request);
|
356
|
}
|
361
|
}
|
357
|
|
362
|
|
358
|
- @ApiOperation(value = "Save or update attributes (saveEntityAttributesV1)",
|
|
|
359
|
- notes = SAVE_ENTITY_ATTRIBUTES_DESCRIPTION + INVALID_ENTITY_ID_OR_ENTITY_TYPE_DESCRIPTION + TENANT_OR_CUSTOMER_AUTHORITY_PARAGRAPH,
|
363
|
+ @ApiOperation(value = "Save entity attributes (saveEntityAttributesV1)",
|
|
|
364
|
+ notes = "Creates or updates the entity attributes based on Entity Id and the specified attribute scope. " +
|
|
|
365
|
+ ENTITY_ATTRIBUTE_SCOPES +
|
|
|
366
|
+ SAVE_ATTRIBUTES_REQUEST_PAYLOAD
|
|
|
367
|
+ + INVALID_ENTITY_ID_OR_ENTITY_TYPE_DESCRIPTION + TENANT_OR_CUSTOMER_AUTHORITY_PARAGRAPH,
|
360
|
produces = MediaType.APPLICATION_JSON_VALUE)
|
368
|
produces = MediaType.APPLICATION_JSON_VALUE)
|
361
|
@ApiResponses(value = {
|
369
|
@ApiResponses(value = {
|
362
|
@ApiResponse(code = 200, message = SAVE_ATTIRIBUTES_STATUS_OK + SAVE_ENTITY_ATTRIBUTES_STATUS_OK),
|
370
|
@ApiResponse(code = 200, message = SAVE_ATTIRIBUTES_STATUS_OK + SAVE_ENTITY_ATTRIBUTES_STATUS_OK),
|
|
@@ -368,16 +376,19 @@ public class TelemetryController extends BaseController { |
|
@@ -368,16 +376,19 @@ public class TelemetryController extends BaseController { |
368
|
@RequestMapping(value = "/{entityType}/{entityId}/{scope}", method = RequestMethod.POST)
|
376
|
@RequestMapping(value = "/{entityType}/{entityId}/{scope}", method = RequestMethod.POST)
|
369
|
@ResponseBody
|
377
|
@ResponseBody
|
370
|
public DeferredResult<ResponseEntity> saveEntityAttributesV1(
|
378
|
public DeferredResult<ResponseEntity> saveEntityAttributesV1(
|
371
|
- @ApiParam(value = ENTITY_TYPE_PARAM_DESCRIPTION) @PathVariable("entityType") String entityType,
|
|
|
372
|
- @ApiParam(value = ENTITY_ID_PARAM_DESCRIPTION) @PathVariable("entityId") String entityIdStr,
|
379
|
+ @ApiParam(value = ENTITY_TYPE_PARAM_DESCRIPTION, required = true, defaultValue = "DEVICE") @PathVariable("entityType") String entityType,
|
|
|
380
|
+ @ApiParam(value = ENTITY_ID_PARAM_DESCRIPTION, required = true) @PathVariable("entityId") String entityIdStr,
|
373
|
@ApiParam(value = ATTRIBUTES_SCOPE_DESCRIPTION, allowableValues = ATTRIBUTES_SCOPE_ALLOWED_VALUES) @PathVariable("scope") String scope,
|
381
|
@ApiParam(value = ATTRIBUTES_SCOPE_DESCRIPTION, allowableValues = ATTRIBUTES_SCOPE_ALLOWED_VALUES) @PathVariable("scope") String scope,
|
374
|
- @ApiParam(value = ATTRIBUTES_JSON_REQUEST_DESCRIPTION) @RequestBody JsonNode request) throws ThingsboardException {
|
382
|
+ @ApiParam(value = ATTRIBUTES_JSON_REQUEST_DESCRIPTION, required = true) @RequestBody JsonNode request) throws ThingsboardException {
|
375
|
EntityId entityId = EntityIdFactory.getByTypeAndId(entityType, entityIdStr);
|
383
|
EntityId entityId = EntityIdFactory.getByTypeAndId(entityType, entityIdStr);
|
376
|
return saveAttributes(getTenantId(), entityId, scope, request);
|
384
|
return saveAttributes(getTenantId(), entityId, scope, request);
|
377
|
}
|
385
|
}
|
378
|
|
386
|
|
379
|
- @ApiOperation(value = "Save or update attributes (saveEntityAttributesV2)",
|
|
|
380
|
- notes = SAVE_ENTITY_ATTRIBUTES_DESCRIPTION + INVALID_ENTITY_ID_OR_ENTITY_TYPE_DESCRIPTION + TENANT_OR_CUSTOMER_AUTHORITY_PARAGRAPH,
|
387
|
+ @ApiOperation(value = "Save entity attributes (saveEntityAttributesV2)",
|
|
|
388
|
+ notes = "Creates or updates the entity attributes based on Entity Id and the specified attribute scope. " +
|
|
|
389
|
+ ENTITY_ATTRIBUTE_SCOPES +
|
|
|
390
|
+ SAVE_ATTRIBUTES_REQUEST_PAYLOAD
|
|
|
391
|
+ + INVALID_ENTITY_ID_OR_ENTITY_TYPE_DESCRIPTION + TENANT_OR_CUSTOMER_AUTHORITY_PARAGRAPH,
|
381
|
produces = MediaType.APPLICATION_JSON_VALUE)
|
392
|
produces = MediaType.APPLICATION_JSON_VALUE)
|
382
|
@ApiResponses(value = {
|
393
|
@ApiResponses(value = {
|
383
|
@ApiResponse(code = 200, message = SAVE_ATTIRIBUTES_STATUS_OK + SAVE_ENTITY_ATTRIBUTES_STATUS_OK),
|
394
|
@ApiResponse(code = 200, message = SAVE_ATTIRIBUTES_STATUS_OK + SAVE_ENTITY_ATTRIBUTES_STATUS_OK),
|
|
@@ -389,16 +400,20 @@ public class TelemetryController extends BaseController { |
|
@@ -389,16 +400,20 @@ public class TelemetryController extends BaseController { |
389
|
@RequestMapping(value = "/{entityType}/{entityId}/attributes/{scope}", method = RequestMethod.POST)
|
400
|
@RequestMapping(value = "/{entityType}/{entityId}/attributes/{scope}", method = RequestMethod.POST)
|
390
|
@ResponseBody
|
401
|
@ResponseBody
|
391
|
public DeferredResult<ResponseEntity> saveEntityAttributesV2(
|
402
|
public DeferredResult<ResponseEntity> saveEntityAttributesV2(
|
392
|
- @ApiParam(value = ENTITY_TYPE_PARAM_DESCRIPTION) @PathVariable("entityType") String entityType,
|
|
|
393
|
- @ApiParam(value = ENTITY_ID_PARAM_DESCRIPTION) @PathVariable("entityId") String entityIdStr,
|
|
|
394
|
- @ApiParam(value = ATTRIBUTES_SCOPE_DESCRIPTION, allowableValues = ATTRIBUTES_SCOPE_ALLOWED_VALUES) @PathVariable("scope") String scope,
|
|
|
395
|
- @ApiParam(value = ATTRIBUTES_JSON_REQUEST_DESCRIPTION) @RequestBody JsonNode request) throws ThingsboardException {
|
403
|
+ @ApiParam(value = ENTITY_TYPE_PARAM_DESCRIPTION, required = true, defaultValue = "DEVICE") @PathVariable("entityType") String entityType,
|
|
|
404
|
+ @ApiParam(value = ENTITY_ID_PARAM_DESCRIPTION, required = true) @PathVariable("entityId") String entityIdStr,
|
|
|
405
|
+ @ApiParam(value = ATTRIBUTES_SCOPE_DESCRIPTION, allowableValues = ATTRIBUTES_SCOPE_ALLOWED_VALUES, required = true) @PathVariable("scope") String scope,
|
|
|
406
|
+ @ApiParam(value = ATTRIBUTES_JSON_REQUEST_DESCRIPTION, required = true) @RequestBody JsonNode request) throws ThingsboardException {
|
396
|
EntityId entityId = EntityIdFactory.getByTypeAndId(entityType, entityIdStr);
|
407
|
EntityId entityId = EntityIdFactory.getByTypeAndId(entityType, entityIdStr);
|
397
|
return saveAttributes(getTenantId(), entityId, scope, request);
|
408
|
return saveAttributes(getTenantId(), entityId, scope, request);
|
398
|
}
|
409
|
}
|
399
|
|
410
|
|
400
|
- @ApiOperation(value = "Save or update telemetry (saveEntityTelemetry)",
|
|
|
401
|
- notes = SAVE_ENTITY_TIMESERIES_DESCRIPTION + INVALID_ENTITY_ID_OR_ENTITY_TYPE_DESCRIPTION + TENANT_OR_CUSTOMER_AUTHORITY_PARAGRAPH,
|
411
|
+
|
|
|
412
|
+ @ApiOperation(value = "Save or update time-series data (saveEntityTelemetry)",
|
|
|
413
|
+ notes = "Creates or updates the entity time-series data based on the Entity Id and request payload." +
|
|
|
414
|
+ SAVE_TIMESERIES_REQUEST_PAYLOAD +
|
|
|
415
|
+ "\n\n The scope parameter is not used in the API call implementation but should be specified whatever value because it is used as a path variable. "
|
|
|
416
|
+ + INVALID_ENTITY_ID_OR_ENTITY_TYPE_DESCRIPTION + TENANT_OR_CUSTOMER_AUTHORITY_PARAGRAPH,
|
402
|
produces = MediaType.APPLICATION_JSON_VALUE)
|
417
|
produces = MediaType.APPLICATION_JSON_VALUE)
|
403
|
@ApiResponses(value = {
|
418
|
@ApiResponses(value = {
|
404
|
@ApiResponse(code = 200, message = SAVE_ENTITY_TIMESERIES_STATUS_OK),
|
419
|
@ApiResponse(code = 200, message = SAVE_ENTITY_TIMESERIES_STATUS_OK),
|
|
@@ -410,16 +425,19 @@ public class TelemetryController extends BaseController { |
|
@@ -410,16 +425,19 @@ public class TelemetryController extends BaseController { |
410
|
@RequestMapping(value = "/{entityType}/{entityId}/timeseries/{scope}", method = RequestMethod.POST)
|
425
|
@RequestMapping(value = "/{entityType}/{entityId}/timeseries/{scope}", method = RequestMethod.POST)
|
411
|
@ResponseBody
|
426
|
@ResponseBody
|
412
|
public DeferredResult<ResponseEntity> saveEntityTelemetry(
|
427
|
public DeferredResult<ResponseEntity> saveEntityTelemetry(
|
413
|
- @ApiParam(value = ENTITY_TYPE_PARAM_DESCRIPTION) @PathVariable("entityType") String entityType,
|
|
|
414
|
- @ApiParam(value = ENTITY_ID_PARAM_DESCRIPTION) @PathVariable("entityId") String entityIdStr,
|
|
|
415
|
- @ApiParam(value = TELEMETRY_SCOPE_DESCRIPTION) @PathVariable("scope") String scope,
|
|
|
416
|
- @ApiParam(value = TELEMETRY_JSON_REQUEST_DESCRIPTION) @RequestBody String requestBody) throws ThingsboardException {
|
428
|
+ @ApiParam(value = ENTITY_TYPE_PARAM_DESCRIPTION, required = true, defaultValue = "DEVICE") @PathVariable("entityType") String entityType,
|
|
|
429
|
+ @ApiParam(value = ENTITY_ID_PARAM_DESCRIPTION, required = true) @PathVariable("entityId") String entityIdStr,
|
|
|
430
|
+ @ApiParam(value = TELEMETRY_SCOPE_DESCRIPTION, required = true, allowableValues = "ANY") @PathVariable("scope") String scope,
|
|
|
431
|
+ @ApiParam(value = TELEMETRY_JSON_REQUEST_DESCRIPTION, required = true) @RequestBody String requestBody) throws ThingsboardException {
|
417
|
EntityId entityId = EntityIdFactory.getByTypeAndId(entityType, entityIdStr);
|
432
|
EntityId entityId = EntityIdFactory.getByTypeAndId(entityType, entityIdStr);
|
418
|
return saveTelemetry(getTenantId(), entityId, requestBody, 0L);
|
433
|
return saveTelemetry(getTenantId(), entityId, requestBody, 0L);
|
419
|
}
|
434
|
}
|
420
|
|
435
|
|
421
|
- @ApiOperation(value = "Save or update telemetry with TTL (saveEntityTelemetryWithTTL)",
|
|
|
422
|
- notes = SAVE_ENTITY_TIMESERIES_DESCRIPTION + "The ttl parameter used only in case of Cassandra DB use for timeseries data storage. "
|
436
|
+ @ApiOperation(value = "Save or update time-series data with TTL (saveEntityTelemetryWithTTL)",
|
|
|
437
|
+ notes = "Creates or updates the entity time-series data based on the Entity Id and request payload." +
|
|
|
438
|
+ SAVE_TIMESERIES_REQUEST_PAYLOAD +
|
|
|
439
|
+ "\n\n The scope parameter is not used in the API call implementation but should be specified whatever value because it is used as a path variable. "
|
|
|
440
|
+ + "\n\nThe ttl parameter takes affect only in case of Cassandra DB."
|
423
|
+ INVALID_ENTITY_ID_OR_ENTITY_TYPE_DESCRIPTION + TENANT_OR_CUSTOMER_AUTHORITY_PARAGRAPH,
|
441
|
+ INVALID_ENTITY_ID_OR_ENTITY_TYPE_DESCRIPTION + TENANT_OR_CUSTOMER_AUTHORITY_PARAGRAPH,
|
424
|
produces = MediaType.APPLICATION_JSON_VALUE)
|
442
|
produces = MediaType.APPLICATION_JSON_VALUE)
|
425
|
@ApiResponses(value = {
|
443
|
@ApiResponses(value = {
|
|
@@ -432,19 +450,21 @@ public class TelemetryController extends BaseController { |
|
@@ -432,19 +450,21 @@ public class TelemetryController extends BaseController { |
432
|
@RequestMapping(value = "/{entityType}/{entityId}/timeseries/{scope}/{ttl}", method = RequestMethod.POST)
|
450
|
@RequestMapping(value = "/{entityType}/{entityId}/timeseries/{scope}/{ttl}", method = RequestMethod.POST)
|
433
|
@ResponseBody
|
451
|
@ResponseBody
|
434
|
public DeferredResult<ResponseEntity> saveEntityTelemetryWithTTL(
|
452
|
public DeferredResult<ResponseEntity> saveEntityTelemetryWithTTL(
|
435
|
- @ApiParam(value = ENTITY_TYPE_PARAM_DESCRIPTION) @PathVariable("entityType") String entityType,
|
|
|
436
|
- @ApiParam(value = ENTITY_ID_PARAM_DESCRIPTION) @PathVariable("entityId") String entityIdStr,
|
|
|
437
|
- @ApiParam(value = TELEMETRY_SCOPE_DESCRIPTION) @PathVariable("scope") String scope,
|
|
|
438
|
- @ApiParam(value = "A long value representing TTL (Time to Live) parameter.") @PathVariable("ttl") Long ttl,
|
|
|
439
|
- @ApiParam(value = TELEMETRY_JSON_REQUEST_DESCRIPTION) @RequestBody String requestBody) throws ThingsboardException {
|
453
|
+ @ApiParam(value = ENTITY_TYPE_PARAM_DESCRIPTION, required = true, defaultValue = "DEVICE") @PathVariable("entityType") String entityType,
|
|
|
454
|
+ @ApiParam(value = ENTITY_ID_PARAM_DESCRIPTION, required = true) @PathVariable("entityId") String entityIdStr,
|
|
|
455
|
+ @ApiParam(value = TELEMETRY_SCOPE_DESCRIPTION, required = true, allowableValues = "ANY") @PathVariable("scope") String scope,
|
|
|
456
|
+ @ApiParam(value = "A long value representing TTL (Time to Live) parameter.", required = true) @PathVariable("ttl") Long ttl,
|
|
|
457
|
+ @ApiParam(value = TELEMETRY_JSON_REQUEST_DESCRIPTION, required = true) @RequestBody String requestBody) throws ThingsboardException {
|
440
|
EntityId entityId = EntityIdFactory.getByTypeAndId(entityType, entityIdStr);
|
458
|
EntityId entityId = EntityIdFactory.getByTypeAndId(entityType, entityIdStr);
|
441
|
return saveTelemetry(getTenantId(), entityId, requestBody, ttl);
|
459
|
return saveTelemetry(getTenantId(), entityId, requestBody, ttl);
|
442
|
}
|
460
|
}
|
443
|
|
461
|
|
444
|
- @ApiOperation(value = "Delete entity timeseries (deleteEntityTimeseries)",
|
|
|
445
|
- notes = "Delete timeseries for selected entity based on entity id, entity type, keys " +
|
|
|
446
|
- "and removal time range. To delete all data for keys parameter 'deleteAllDataForKeys' should be set to true, " +
|
|
|
447
|
- "otherwise, will be deleted data that is in range of the selected time interval. " + TENANT_OR_CUSTOMER_AUTHORITY_PARAGRAPH,
|
462
|
+ @ApiOperation(value = "Delete entity time-series data (deleteEntityTimeseries)",
|
|
|
463
|
+ notes = "Delete time-series for selected entity based on entity id, entity type and keys." +
|
|
|
464
|
+ " Use 'deleteAllDataForKeys' to delete all time-series data." +
|
|
|
465
|
+ " Use 'startTs' and 'endTs' to specify time-range instead. " +
|
|
|
466
|
+ " Use 'rewriteLatestIfDeleted' to rewrite latest value (stored in separate table for performance) after deletion of the time range. " +
|
|
|
467
|
+ TENANT_OR_CUSTOMER_AUTHORITY_PARAGRAPH,
|
448
|
produces = MediaType.APPLICATION_JSON_VALUE)
|
468
|
produces = MediaType.APPLICATION_JSON_VALUE)
|
449
|
@ApiResponses(value = {
|
469
|
@ApiResponses(value = {
|
450
|
@ApiResponse(code = 200, message = "Timeseries for the selected keys in the request was removed. " +
|
470
|
@ApiResponse(code = 200, message = "Timeseries for the selected keys in the request was removed. " +
|
|
@@ -458,9 +478,9 @@ public class TelemetryController extends BaseController { |
|
@@ -458,9 +478,9 @@ public class TelemetryController extends BaseController { |
458
|
@RequestMapping(value = "/{entityType}/{entityId}/timeseries/delete", method = RequestMethod.DELETE)
|
478
|
@RequestMapping(value = "/{entityType}/{entityId}/timeseries/delete", method = RequestMethod.DELETE)
|
459
|
@ResponseBody
|
479
|
@ResponseBody
|
460
|
public DeferredResult<ResponseEntity> deleteEntityTimeseries(
|
480
|
public DeferredResult<ResponseEntity> deleteEntityTimeseries(
|
461
|
- @ApiParam(value = ENTITY_TYPE_PARAM_DESCRIPTION) @PathVariable("entityType") String entityType,
|
|
|
462
|
- @ApiParam(value = ENTITY_ID_PARAM_DESCRIPTION) @PathVariable("entityId") String entityIdStr,
|
|
|
463
|
- @ApiParam(value = TELEMETRY_KEYS_DESCRIPTION) @RequestParam(name = "keys") String keysStr,
|
481
|
+ @ApiParam(value = ENTITY_TYPE_PARAM_DESCRIPTION, required = true, defaultValue = "DEVICE") @PathVariable("entityType") String entityType,
|
|
|
482
|
+ @ApiParam(value = ENTITY_ID_PARAM_DESCRIPTION, required = true) @PathVariable("entityId") String entityIdStr,
|
|
|
483
|
+ @ApiParam(value = TELEMETRY_KEYS_DESCRIPTION, required = true) @RequestParam(name = "keys") String keysStr,
|
464
|
@ApiParam(value = "A boolean value to specify if should be deleted all data for selected keys or only data that are in the selected time range.")
|
484
|
@ApiParam(value = "A boolean value to specify if should be deleted all data for selected keys or only data that are in the selected time range.")
|
465
|
@RequestParam(name = "deleteAllDataForKeys", defaultValue = "false") boolean deleteAllDataForKeys,
|
485
|
@RequestParam(name = "deleteAllDataForKeys", defaultValue = "false") boolean deleteAllDataForKeys,
|
466
|
@ApiParam(value = "A long value representing the start timestamp of removal time range in milliseconds.")
|
486
|
@ApiParam(value = "A long value representing the start timestamp of removal time range in milliseconds.")
|
|
@@ -501,7 +521,7 @@ public class TelemetryController extends BaseController { |
|
@@ -501,7 +521,7 @@ public class TelemetryController extends BaseController { |
501
|
deleteTsKvQueries.add(new BaseDeleteTsKvQuery(key, deleteFromTs, deleteToTs, rewriteLatestIfDeleted));
|
521
|
deleteTsKvQueries.add(new BaseDeleteTsKvQuery(key, deleteFromTs, deleteToTs, rewriteLatestIfDeleted));
|
502
|
}
|
522
|
}
|
503
|
ListenableFuture<List<Void>> future = tsService.remove(user.getTenantId(), entityId, deleteTsKvQueries);
|
523
|
ListenableFuture<List<Void>> future = tsService.remove(user.getTenantId(), entityId, deleteTsKvQueries);
|
504
|
- Futures.addCallback(future, new FutureCallback<List<Void>>() {
|
524
|
+ Futures.addCallback(future, new FutureCallback<>() {
|
505
|
@Override
|
525
|
@Override
|
506
|
public void onSuccess(@Nullable List<Void> tmp) {
|
526
|
public void onSuccess(@Nullable List<Void> tmp) {
|
507
|
logTimeseriesDeleted(user, entityId, keys, deleteFromTs, deleteToTs, null);
|
527
|
logTimeseriesDeleted(user, entityId, keys, deleteFromTs, deleteToTs, null);
|
|
@@ -517,9 +537,9 @@ public class TelemetryController extends BaseController { |
|
@@ -517,9 +537,9 @@ public class TelemetryController extends BaseController { |
517
|
});
|
537
|
});
|
518
|
}
|
538
|
}
|
519
|
|
539
|
|
520
|
- @ApiOperation(value = "Delete device attributes (deleteEntityAttributes)",
|
|
|
521
|
- notes = "Delete device attributes from the specified attributes scope based on device id and a list of keys to delete. " +
|
|
|
522
|
- "Selected keys will be deleted only if there are exist in the specified attribute scope. Referencing a non-existing device Id will cause an error" + TENANT_OR_CUSTOMER_AUTHORITY_PARAGRAPH,
|
540
|
+ @ApiOperation(value = "Delete device attributes (deleteDeviceAttributes)",
|
|
|
541
|
+ notes = "Delete device attributes using provided Device Id, scope and a list of keys. " +
|
|
|
542
|
+ "Referencing a non-existing Device Id will cause an error" + TENANT_OR_CUSTOMER_AUTHORITY_PARAGRAPH,
|
523
|
produces = MediaType.APPLICATION_JSON_VALUE)
|
543
|
produces = MediaType.APPLICATION_JSON_VALUE)
|
524
|
@ApiResponses(value = {
|
544
|
@ApiResponses(value = {
|
525
|
@ApiResponse(code = 200, message = "Device attributes was removed for the selected keys in the request. " +
|
545
|
@ApiResponse(code = 200, message = "Device attributes was removed for the selected keys in the request. " +
|
|
@@ -532,17 +552,17 @@ public class TelemetryController extends BaseController { |
|
@@ -532,17 +552,17 @@ public class TelemetryController extends BaseController { |
532
|
@PreAuthorize("hasAnyAuthority('SYS_ADMIN', 'TENANT_ADMIN', 'CUSTOMER_USER')")
|
552
|
@PreAuthorize("hasAnyAuthority('SYS_ADMIN', 'TENANT_ADMIN', 'CUSTOMER_USER')")
|
533
|
@RequestMapping(value = "/{deviceId}/{scope}", method = RequestMethod.DELETE)
|
553
|
@RequestMapping(value = "/{deviceId}/{scope}", method = RequestMethod.DELETE)
|
534
|
@ResponseBody
|
554
|
@ResponseBody
|
535
|
- public DeferredResult<ResponseEntity> deleteEntityAttributes(
|
|
|
536
|
- @ApiParam(value = DEVICE_ID_PARAM_DESCRIPTION) @PathVariable("deviceId") String deviceIdStr,
|
|
|
537
|
- @ApiParam(value = ATTRIBUTES_SCOPE_DESCRIPTION, allowableValues = ATTRIBUTES_SCOPE_ALLOWED_VALUES) @PathVariable("scope") String scope,
|
|
|
538
|
- @ApiParam(value = ATTRIBUTES_KEYS_DESCRIPTION) @RequestParam(name = "keys") String keysStr) throws ThingsboardException {
|
555
|
+ public DeferredResult<ResponseEntity> deleteDeviceAttributes(
|
|
|
556
|
+ @ApiParam(value = DEVICE_ID_PARAM_DESCRIPTION, required = true) @PathVariable(DEVICE_ID) String deviceIdStr,
|
|
|
557
|
+ @ApiParam(value = ATTRIBUTES_SCOPE_DESCRIPTION, allowableValues = ATTRIBUTES_SCOPE_ALLOWED_VALUES, required = true) @PathVariable("scope") String scope,
|
|
|
558
|
+ @ApiParam(value = ATTRIBUTES_KEYS_DESCRIPTION, required = true) @RequestParam(name = "keys") String keysStr) throws ThingsboardException {
|
539
|
EntityId entityId = EntityIdFactory.getByTypeAndUuid(EntityType.DEVICE, deviceIdStr);
|
559
|
EntityId entityId = EntityIdFactory.getByTypeAndUuid(EntityType.DEVICE, deviceIdStr);
|
540
|
return deleteAttributes(entityId, scope, keysStr);
|
560
|
return deleteAttributes(entityId, scope, keysStr);
|
541
|
}
|
561
|
}
|
542
|
|
562
|
|
543
|
@ApiOperation(value = "Delete entity attributes (deleteEntityAttributes)",
|
563
|
@ApiOperation(value = "Delete entity attributes (deleteEntityAttributes)",
|
544
|
- notes = "Delete entity attributes from the specified attributes scope based on entity id, entity type and a list of keys to delete. " +
|
|
|
545
|
- "Selected keys will be deleted only if there are exist in the specified attribute scope." + INVALID_ENTITY_ID_OR_ENTITY_TYPE_DESCRIPTION + TENANT_OR_CUSTOMER_AUTHORITY_PARAGRAPH,
|
564
|
+ notes = "Delete entity attributes using provided Entity Id, scope and a list of keys. " +
|
|
|
565
|
+ INVALID_ENTITY_ID_OR_ENTITY_TYPE_DESCRIPTION + TENANT_OR_CUSTOMER_AUTHORITY_PARAGRAPH,
|
546
|
produces = MediaType.APPLICATION_JSON_VALUE)
|
566
|
produces = MediaType.APPLICATION_JSON_VALUE)
|
547
|
@ApiResponses(value = {
|
567
|
@ApiResponses(value = {
|
548
|
@ApiResponse(code = 200, message = "Entity attributes was removed for the selected keys in the request. " +
|
568
|
@ApiResponse(code = 200, message = "Entity attributes was removed for the selected keys in the request. " +
|
|
@@ -556,10 +576,10 @@ public class TelemetryController extends BaseController { |
|
@@ -556,10 +576,10 @@ public class TelemetryController extends BaseController { |
556
|
@RequestMapping(value = "/{entityType}/{entityId}/{scope}", method = RequestMethod.DELETE)
|
576
|
@RequestMapping(value = "/{entityType}/{entityId}/{scope}", method = RequestMethod.DELETE)
|
557
|
@ResponseBody
|
577
|
@ResponseBody
|
558
|
public DeferredResult<ResponseEntity> deleteEntityAttributes(
|
578
|
public DeferredResult<ResponseEntity> deleteEntityAttributes(
|
559
|
- @ApiParam(value = ENTITY_TYPE_PARAM_DESCRIPTION) @PathVariable("entityType") String entityType,
|
|
|
560
|
- @ApiParam(value = ENTITY_ID_PARAM_DESCRIPTION) @PathVariable("entityId") String entityIdStr,
|
|
|
561
|
- @ApiParam(value = ATTRIBUTES_SCOPE_DESCRIPTION, allowableValues = ATTRIBUTES_SCOPE_ALLOWED_VALUES) @PathVariable("scope") String scope,
|
|
|
562
|
- @ApiParam(value = ATTRIBUTES_KEYS_DESCRIPTION) @RequestParam(name = "keys") String keysStr) throws ThingsboardException {
|
579
|
+ @ApiParam(value = ENTITY_TYPE_PARAM_DESCRIPTION, required = true, defaultValue = "DEVICE") @PathVariable("entityType") String entityType,
|
|
|
580
|
+ @ApiParam(value = ENTITY_ID_PARAM_DESCRIPTION, required = true) @PathVariable("entityId") String entityIdStr,
|
|
|
581
|
+ @ApiParam(value = ATTRIBUTES_SCOPE_DESCRIPTION, required = true, allowableValues = ATTRIBUTES_SCOPE_ALLOWED_VALUES) @PathVariable("scope") String scope,
|
|
|
582
|
+ @ApiParam(value = ATTRIBUTES_KEYS_DESCRIPTION, required = true) @RequestParam(name = "keys") String keysStr) throws ThingsboardException {
|
563
|
EntityId entityId = EntityIdFactory.getByTypeAndId(entityType, entityIdStr);
|
583
|
EntityId entityId = EntityIdFactory.getByTypeAndId(entityType, entityIdStr);
|
564
|
return deleteAttributes(entityId, scope, keysStr);
|
584
|
return deleteAttributes(entityId, scope, keysStr);
|
565
|
}
|
585
|
}
|
|
@@ -732,7 +752,7 @@ public class TelemetryController extends BaseController { |
|
@@ -732,7 +752,7 @@ public class TelemetryController extends BaseController { |
732
|
}
|
752
|
}
|
733
|
|
753
|
|
734
|
private FutureCallback<List<TsKvEntry>> getTsKeysToResponseCallback(final DeferredResult<ResponseEntity> response) {
|
754
|
private FutureCallback<List<TsKvEntry>> getTsKeysToResponseCallback(final DeferredResult<ResponseEntity> response) {
|
735
|
- return new FutureCallback<List<TsKvEntry>>() {
|
755
|
+ return new FutureCallback<>() {
|
736
|
@Override
|
756
|
@Override
|
737
|
public void onSuccess(List<TsKvEntry> values) {
|
757
|
public void onSuccess(List<TsKvEntry> values) {
|
738
|
List<String> keys = values.stream().map(KvEntry::getKey).collect(Collectors.toList());
|
758
|
List<String> keys = values.stream().map(KvEntry::getKey).collect(Collectors.toList());
|
|
@@ -767,7 +787,7 @@ public class TelemetryController extends BaseController { |
|
@@ -767,7 +787,7 @@ public class TelemetryController extends BaseController { |
767
|
private FutureCallback<List<AttributeKvEntry>> getAttributeValuesToResponseCallback(final DeferredResult<ResponseEntity> response,
|
787
|
private FutureCallback<List<AttributeKvEntry>> getAttributeValuesToResponseCallback(final DeferredResult<ResponseEntity> response,
|
768
|
final SecurityUser user, final String scope,
|
788
|
final SecurityUser user, final String scope,
|
769
|
final EntityId entityId, final List<String> keyList) {
|
789
|
final EntityId entityId, final List<String> keyList) {
|
770
|
- return new FutureCallback<List<AttributeKvEntry>>() {
|
790
|
+ return new FutureCallback<>() {
|
771
|
@Override
|
791
|
@Override
|
772
|
public void onSuccess(List<AttributeKvEntry> attributes) {
|
792
|
public void onSuccess(List<AttributeKvEntry> attributes) {
|
773
|
List<AttributeData> values = attributes.stream().map(attribute ->
|
793
|
List<AttributeData> values = attributes.stream().map(attribute ->
|
|
@@ -787,7 +807,7 @@ public class TelemetryController extends BaseController { |
|
@@ -787,7 +807,7 @@ public class TelemetryController extends BaseController { |
787
|
}
|
807
|
}
|
788
|
|
808
|
|
789
|
private FutureCallback<List<TsKvEntry>> getTsKvListCallback(final DeferredResult<ResponseEntity> response, Boolean useStrictDataTypes) {
|
809
|
private FutureCallback<List<TsKvEntry>> getTsKvListCallback(final DeferredResult<ResponseEntity> response, Boolean useStrictDataTypes) {
|
790
|
- return new FutureCallback<List<TsKvEntry>>() {
|
810
|
+ return new FutureCallback<>() {
|
791
|
@Override
|
811
|
@Override
|
792
|
public void onSuccess(List<TsKvEntry> data) {
|
812
|
public void onSuccess(List<TsKvEntry> data) {
|
793
|
Map<String, List<TsData>> result = new LinkedHashMap<>();
|
813
|
Map<String, List<TsData>> result = new LinkedHashMap<>();
|
|
@@ -907,16 +927,16 @@ public class TelemetryController extends BaseController { |
|
@@ -907,16 +927,16 @@ public class TelemetryController extends BaseController { |
907
|
|
927
|
|
908
|
private String toJsonStr(JsonNode value) {
|
928
|
private String toJsonStr(JsonNode value) {
|
909
|
try {
|
929
|
try {
|
910
|
- return mapper.writeValueAsString(value);
|
|
|
911
|
- } catch (JsonProcessingException e) {
|
930
|
+ return JacksonUtil.toString(value);
|
|
|
931
|
+ } catch (IllegalArgumentException e) {
|
912
|
throw new JsonParseException("Can't parse jsonValue: " + value, e);
|
932
|
throw new JsonParseException("Can't parse jsonValue: " + value, e);
|
913
|
}
|
933
|
}
|
914
|
}
|
934
|
}
|
915
|
|
935
|
|
916
|
private JsonNode toJsonNode(String value) {
|
936
|
private JsonNode toJsonNode(String value) {
|
917
|
try {
|
937
|
try {
|
918
|
- return mapper.readTree(value);
|
|
|
919
|
- } catch (IOException e) {
|
938
|
+ return JacksonUtil.toJsonNode(value);
|
|
|
939
|
+ } catch (IllegalArgumentException e) {
|
920
|
throw new JsonParseException("Can't parse jsonValue: " + value, e);
|
940
|
throw new JsonParseException("Can't parse jsonValue: " + value, e);
|
921
|
}
|
941
|
}
|
922
|
}
|
942
|
}
|