From c230e3fdcd65111f22b93f088174ffcfdef5092c Mon Sep 17 00:00:00 2001 From: nickAS21 Date: Tue, 2 Feb 2021 11:47:11 +0200 Subject: [PATCH] Lwm2m: front: add key to profile - refactoring-light start2 --- .../src/main/resources/thingsboard.yml | 1 - .../lwm2m/server/LwM2MTransportHandler.java | 50 ++-- .../lwm2m/server/LwM2MTransportRequest.java | 2 +- .../server/LwM2MTransportServiceImpl.java | 219 ++++++++---------- .../lwm2m/server/client/LwM2MClient.java | 3 +- ...erveValue.java => LwM2MClientProfile.java} | 9 +- .../secure/LwM2mInMemorySecurityStore.java | 24 +- .../lwm2m/LwM2MTransportConfigServer.java | 4 - ...ile-transport-configuration.component.html | 4 +- .../assets/locale/locale.constant-en_US.json | 4 +- 10 files changed, 157 insertions(+), 163 deletions(-) rename common/transport/lwm2m/src/main/java/org/thingsboard/server/transport/lwm2m/server/client/{AttrTelemetryObserveValue.java => LwM2MClientProfile.java} (86%) diff --git a/application/src/main/resources/thingsboard.yml b/application/src/main/resources/thingsboard.yml index 9f661a462d..461d2f04c8 100644 --- a/application/src/main/resources/thingsboard.yml +++ b/application/src/main/resources/thingsboard.yml @@ -581,7 +581,6 @@ transport: request_pool_size: "${LWM2M_REQUEST_POOL_SIZE:100}" request_error_pool_size: "${LWM2M_REQUEST_ERROR_POOL_SIZE:10}" registered_pool_size: "${LWM2M_REGISTERED_POOL_SIZE:10}" - client_update_value_after_connect: "${CLIENT_UPDATE_VALUE_AFTER_CONNECT:false}" update_registered_pool_size: "${LWM2M_UPDATE_REGISTERED_POOL_SIZE:10}" un_registered_pool_size: "${LWM2M_UN_REGISTERED_POOL_SIZE:10}" secure: diff --git a/common/transport/lwm2m/src/main/java/org/thingsboard/server/transport/lwm2m/server/LwM2MTransportHandler.java b/common/transport/lwm2m/src/main/java/org/thingsboard/server/transport/lwm2m/server/LwM2MTransportHandler.java index 249ee78344..11db9e8c2c 100644 --- a/common/transport/lwm2m/src/main/java/org/thingsboard/server/transport/lwm2m/server/LwM2MTransportHandler.java +++ b/common/transport/lwm2m/src/main/java/org/thingsboard/server/transport/lwm2m/server/LwM2MTransportHandler.java @@ -36,7 +36,7 @@ import org.nustaq.serialization.FSTConfiguration; import org.thingsboard.server.common.data.DeviceProfile; import org.thingsboard.server.common.data.device.profile.Lwm2mDeviceProfileTransportConfiguration; import org.thingsboard.server.common.transport.TransportServiceCallback; -import org.thingsboard.server.transport.lwm2m.server.client.AttrTelemetryObserveValue; +import org.thingsboard.server.transport.lwm2m.server.client.LwM2MClientProfile; import org.thingsboard.server.transport.lwm2m.server.client.LwM2MClient; import java.io.File; @@ -70,7 +70,8 @@ public class LwM2MTransportHandler { public static final long DEFAULT_TIMEOUT = 2 * 60 * 1000L; // 2min in ms public static final String OBSERVE_ATTRIBUTE_TELEMETRY = "observeAttr"; - public static final String KEYNAME = "keyName"; + public static final String CLIENT_LWM2M_SETTINGS = "clientLwM2mSettings"; + public static final String KEY_NAME = "keyName"; public static final String OBSERVE = "observe"; public static final String BOOTSTRAP = "bootstrap"; public static final String SERVERS = "servers"; @@ -187,18 +188,22 @@ public class LwM2MTransportHandler { return null; } - public static AttrTelemetryObserveValue getNewProfileParameters(JsonObject profilesConfigData) { - AttrTelemetryObserveValue attrTelemetryObserveValue = new AttrTelemetryObserveValue(); - attrTelemetryObserveValue.setPostKeyNameProfile(profilesConfigData.get(KEYNAME).getAsJsonObject()); - attrTelemetryObserveValue.setPostAttributeProfile(profilesConfigData.get(ATTRIBUTE).getAsJsonArray()); - attrTelemetryObserveValue.setPostTelemetryProfile(profilesConfigData.get(TELEMETRY).getAsJsonArray()); - attrTelemetryObserveValue.setPostObserveProfile(profilesConfigData.get(OBSERVE).getAsJsonArray()); - return attrTelemetryObserveValue; + public static LwM2MClientProfile getNewProfileParameters(JsonObject profilesConfigData) { + LwM2MClientProfile lwM2MClientProfile = new LwM2MClientProfile(); + lwM2MClientProfile.setPostClientLwM2mSettings(profilesConfigData.get(CLIENT_LWM2M_SETTINGS).getAsJsonObject()); + lwM2MClientProfile.setPostKeyNameProfile(profilesConfigData.get(OBSERVE_ATTRIBUTE_TELEMETRY).getAsJsonObject().get(KEY_NAME).getAsJsonObject()); + lwM2MClientProfile.setPostAttributeProfile(profilesConfigData.get(OBSERVE_ATTRIBUTE_TELEMETRY).getAsJsonObject().get(ATTRIBUTE).getAsJsonArray()); + lwM2MClientProfile.setPostTelemetryProfile(profilesConfigData.get(OBSERVE_ATTRIBUTE_TELEMETRY).getAsJsonObject().get(TELEMETRY).getAsJsonArray()); + lwM2MClientProfile.setPostObserveProfile(profilesConfigData.get(OBSERVE_ATTRIBUTE_TELEMETRY).getAsJsonObject().get(OBSERVE).getAsJsonArray()); + return lwM2MClientProfile; } /** * @return deviceProfileBody with Observe&Attribute&Telemetry From Thingsboard - * Example: with pathResource (use only pathResource) + * Example: + * property: {"clientLwM2mSettings": { + * clientUpdateValueAfterConnect: false; + * } * property: "observeAttr" * {"keyName": { * "/3/0/1": "modelNumber", @@ -209,15 +214,14 @@ public class LwM2MTransportHandler { * "telemetry":["/1/0/1","/2/0/1","/6/0/1"], * "observe":["/2/0","/2/0/0","/4/0/2"]} */ - public static JsonObject getObserveAttrTelemetryFromThingsboard(DeviceProfile deviceProfile) { + public static LwM2MClientProfile getLwM2MClientProfileFromThingsboard(DeviceProfile deviceProfile) { if (deviceProfile != null && ((Lwm2mDeviceProfileTransportConfiguration) deviceProfile.getProfileData().getTransportConfiguration()).getProperties().size() > 0) { -// Lwm2mDeviceProfileTransportConfiguration lwm2mDeviceProfileTransportConfiguration = (Lwm2mDeviceProfileTransportConfiguration) deviceProfile.getProfileData().getTransportConfiguration(); - Object observeAttr = ((Lwm2mDeviceProfileTransportConfiguration) deviceProfile.getProfileData().getTransportConfiguration()).getProperties(); + Object profile = ((Lwm2mDeviceProfileTransportConfiguration) deviceProfile.getProfileData().getTransportConfiguration()).getProperties(); try { ObjectMapper mapper = new ObjectMapper(); - String observeAttrStr = mapper.writeValueAsString(observeAttr); - JsonObject objectMsg = (observeAttrStr != null) ? validateJson(observeAttrStr) : null; - return (getValidateCredentialsBodyFromThingsboard(objectMsg)) ? objectMsg.get(OBSERVE_ATTRIBUTE_TELEMETRY).getAsJsonObject() : null; + String profileStr = mapper.writeValueAsString(profile); + JsonObject profileJson = (profileStr != null) ? validateJson(profileStr) : null; + return (getValidateCredentialsBodyFromThingsboard(profileJson)) ? LwM2MTransportHandler.getNewProfileParameters(profileJson) : null; } catch (IOException e) { log.error("", e); } @@ -240,15 +244,23 @@ public class LwM2MTransportHandler { return null; } + public static boolean getClientUpdateValueAfterConnect (LwM2MClientProfile profile) { + return profile.getPostClientLwM2mSettings().getAsJsonObject().has("clientUpdateValueAfterConnect") && + profile.getPostClientLwM2mSettings().getAsJsonObject().get("clientUpdateValueAfterConnect").getAsBoolean(); + } + private static boolean getValidateCredentialsBodyFromThingsboard(JsonObject objectMsg) { return (objectMsg != null && !objectMsg.isJsonNull() && + objectMsg.has(CLIENT_LWM2M_SETTINGS) && + !objectMsg.get(CLIENT_LWM2M_SETTINGS).isJsonNull() && + objectMsg.get(CLIENT_LWM2M_SETTINGS).isJsonObject() && objectMsg.has(OBSERVE_ATTRIBUTE_TELEMETRY) && !objectMsg.get(OBSERVE_ATTRIBUTE_TELEMETRY).isJsonNull() && objectMsg.get(OBSERVE_ATTRIBUTE_TELEMETRY).isJsonObject() && - objectMsg.get(OBSERVE_ATTRIBUTE_TELEMETRY).getAsJsonObject().has(KEYNAME) && - !objectMsg.get(OBSERVE_ATTRIBUTE_TELEMETRY).getAsJsonObject().get(KEYNAME).isJsonNull() && - objectMsg.get(OBSERVE_ATTRIBUTE_TELEMETRY).getAsJsonObject().get(KEYNAME).isJsonObject() && + objectMsg.get(OBSERVE_ATTRIBUTE_TELEMETRY).getAsJsonObject().has(KEY_NAME) && + !objectMsg.get(OBSERVE_ATTRIBUTE_TELEMETRY).getAsJsonObject().get(KEY_NAME).isJsonNull() && + objectMsg.get(OBSERVE_ATTRIBUTE_TELEMETRY).getAsJsonObject().get(KEY_NAME).isJsonObject() && objectMsg.get(OBSERVE_ATTRIBUTE_TELEMETRY).getAsJsonObject().has(ATTRIBUTE) && !objectMsg.get(OBSERVE_ATTRIBUTE_TELEMETRY).getAsJsonObject().get(ATTRIBUTE).isJsonNull() && objectMsg.get(OBSERVE_ATTRIBUTE_TELEMETRY).getAsJsonObject().get(ATTRIBUTE).isJsonArray() && diff --git a/common/transport/lwm2m/src/main/java/org/thingsboard/server/transport/lwm2m/server/LwM2MTransportRequest.java b/common/transport/lwm2m/src/main/java/org/thingsboard/server/transport/lwm2m/server/LwM2MTransportRequest.java index 1c4590ace8..e9e2a08fe4 100644 --- a/common/transport/lwm2m/src/main/java/org/thingsboard/server/transport/lwm2m/server/LwM2MTransportRequest.java +++ b/common/transport/lwm2m/src/main/java/org/thingsboard/server/transport/lwm2m/server/LwM2MTransportRequest.java @@ -226,7 +226,7 @@ public class LwM2MTransportRequest { String msg = String.format(LOG_LW2M_ERROR + ": sendRequest: Resource path - %s msg No SendRequest to Client", target); service.sentLogsToThingsboard(msg, registration); log.error("[{}] - [{}] No SendRequest", target); - this.handleResponseError(registration, target, lwM2MClient, isDelayedUpdate); + this.handleResponseError(registration, target, lwM2MClient, true); } } diff --git a/common/transport/lwm2m/src/main/java/org/thingsboard/server/transport/lwm2m/server/LwM2MTransportServiceImpl.java b/common/transport/lwm2m/src/main/java/org/thingsboard/server/transport/lwm2m/server/LwM2MTransportServiceImpl.java index a02aa1b29d..0b27366f98 100644 --- a/common/transport/lwm2m/src/main/java/org/thingsboard/server/transport/lwm2m/server/LwM2MTransportServiceImpl.java +++ b/common/transport/lwm2m/src/main/java/org/thingsboard/server/transport/lwm2m/server/LwM2MTransportServiceImpl.java @@ -21,11 +21,10 @@ import com.google.gson.JsonElement; import com.google.gson.JsonObject; import lombok.extern.slf4j.Slf4j; import org.eclipse.leshan.core.model.ResourceModel; -import org.eclipse.leshan.core.node.LwM2mMultipleResource; import org.eclipse.leshan.core.node.LwM2mObject; import org.eclipse.leshan.core.node.LwM2mObjectInstance; import org.eclipse.leshan.core.node.LwM2mPath; -import org.eclipse.leshan.core.node.LwM2mSingleResource; +import org.eclipse.leshan.core.node.LwM2mResource; import org.eclipse.leshan.core.observation.Observation; import org.eclipse.leshan.core.request.ContentFormat; import org.eclipse.leshan.core.request.WriteRequest; @@ -47,8 +46,8 @@ import org.thingsboard.server.gen.transport.TransportProtos.SessionEvent; import org.thingsboard.server.gen.transport.TransportProtos.SessionInfoProto; import org.thingsboard.server.gen.transport.TransportProtos.ToTransportUpdateCredentialsProto; import org.thingsboard.server.gen.transport.TransportProtos.ValidateDeviceCredentialsResponseMsg; -import org.thingsboard.server.transport.lwm2m.server.client.AttrTelemetryObserveValue; import org.thingsboard.server.transport.lwm2m.server.client.LwM2MClient; +import org.thingsboard.server.transport.lwm2m.server.client.LwM2MClientProfile; import org.thingsboard.server.transport.lwm2m.server.client.ResourceValue; import org.thingsboard.server.transport.lwm2m.server.client.ResultsAnalyzerParameters; import org.thingsboard.server.transport.lwm2m.server.secure.LwM2mInMemorySecurityStore; @@ -71,7 +70,6 @@ import java.util.concurrent.ConcurrentMap; import java.util.concurrent.ExecutorService; import java.util.concurrent.Executors; import java.util.concurrent.TimeUnit; -import java.util.concurrent.atomic.AtomicBoolean; import java.util.concurrent.locks.Lock; import java.util.concurrent.locks.ReadWriteLock; import java.util.concurrent.locks.ReentrantReadWriteLock; @@ -153,8 +151,8 @@ public class LwM2MTransportServiceImpl implements LwM2MTransportService { lwM2MClient.setLwM2MTransportServiceImpl(this); lwM2MClient.setSessionUuid(UUID.randomUUID()); this.sentLogsToThingsboard(LOG_LW2M_INFO + ": Client Registered", registration); - this.setLwM2mFromClientValue(lwServer, registration, lwM2MClient); - lwM2MClient.setClientUpdateValueAfterConnect(this.context.getCtxServer().isClientUpdateValueAfterConnect()); + LwM2MClientProfile lwM2MClientProfile = lwM2mInMemorySecurityStore.getProfile(registration.getId()); + this.setLwM2mFromClientValue(lwServer, registration, lwM2MClient, lwM2MClientProfile); SessionInfoProto sessionInfo = this.getValidateSessionInfo(registration); if (sessionInfo != null) { lwM2MClient.setDeviceUuid(new UUID(sessionInfo.getDeviceIdMSB(), sessionInfo.getDeviceIdLSB())); @@ -165,7 +163,7 @@ public class LwM2MTransportServiceImpl implements LwM2MTransportService { transportService.process(sessionInfo, DefaultTransportService.getSessionEventMsg(SessionEvent.OPEN), null); transportService.process(sessionInfo, TransportProtos.SubscribeToAttributeUpdatesMsg.newBuilder().build(), null); this.sentLogsToThingsboard(LOG_LW2M_INFO + ": Client create after Registration", registration); - if (this.context.getCtxServer().isClientUpdateValueAfterConnect()) { + if (LwM2MTransportHandler.getClientUpdateValueAfterConnect(lwM2MClientProfile)) { this.putDelayedUpdateResourcesThingsboard(lwM2MClient); } } else { @@ -255,7 +253,7 @@ public class LwM2MTransportServiceImpl implements LwM2MTransportService { * Removes a profile if not used in sessions */ private void syncSessionsAndProfiles() { - Map profilesClone = lwM2mInMemorySecurityStore.getProfiles().entrySet() + Map profilesClone = lwM2mInMemorySecurityStore.getProfiles().entrySet() .stream() .collect(Collectors.toMap(Map.Entry::getKey, Map.Entry::getValue)); profilesClone.forEach((k, v) -> { @@ -285,9 +283,26 @@ public class LwM2MTransportServiceImpl implements LwM2MTransportService { * @param registration - Registration LwM2M Client * @param lwM2MClient - object with All parameters off client */ - private void setLwM2mFromClientValue(LeshanServer lwServer, Registration registration, LwM2MClient lwM2MClient) { + private void setLwM2mFromClientValue(LeshanServer lwServer, Registration registration, LwM2MClient lwM2MClient, LwM2MClientProfile lwM2MClientProfile) { // #1.1 // get all instances in client + Set clientInstances = this.getAllInstancesInClient(registration); + if (clientInstances != null && LwM2MTransportHandler.getClientUpdateValueAfterConnect(lwM2MClientProfile)) { + lwM2MClient.getPendingRequests().addAll(clientInstances); + // #2 + clientInstances.forEach(path -> { + lwM2MTransportRequest.sendAllRequest(lwServer, registration, path, GET_TYPE_OPER_READ, ContentFormat.TLV.getName(), + lwM2MClient, null, null, this.context.getCtxServer().getTimeout(), false); + }); + } else { + // #1.2 + this.onSentObserveToClient(lwServer, registration); + } + + } + + // get all instances in client + private Set getAllInstancesInClient(Registration registration) { Set clientInstances = ConcurrentHashMap.newKeySet(); Arrays.stream(registration.getObjectLinks()).forEach(url -> { LwM2mPath pathIds = new LwM2mPath(url.getUrl()); @@ -295,27 +310,7 @@ public class LwM2MTransportServiceImpl implements LwM2MTransportService { clientInstances.add(url.getUrl()); } }); - if (this.context.getCtxServer().isClientUpdateValueAfterConnect()) { - lwM2MClient.getPendingRequests().addAll(clientInstances); - } else { - // #1.2 - UUID profileUUid = lwM2mInMemorySecurityStore.getSessions().get(registration.getId()).getProfileUuid(); - JsonArray observeValue = lwM2mInMemorySecurityStore.getProfiles().get(profileUUid).getPostObserveProfile(); - observeValue.forEach(path -> { - String[] resPath = path.getAsString().split("/"); - String instance = "/" + resPath[1] + "/" + resPath[2]; - if (clientInstances.contains(instance)) { - lwM2MClient.getPendingRequests().add(path.getAsString()); - } - } - ); - } - - // #2 - lwM2MClient.getPendingRequests().forEach(path -> { - lwM2MTransportRequest.sendAllRequest(lwServer, registration, path, GET_TYPE_OPER_READ, ContentFormat.TLV.getName(), - lwM2MClient, null, null, this.context.getCtxServer().getTimeout(), false); - }); + return (clientInstances.size() > 0) ? clientInstances : null; } /** @@ -463,7 +458,7 @@ public class LwM2MTransportServiceImpl implements LwM2MTransportService { * @return ArrayList keyNames from profile attr resources shared!!!! && IsWritable */ private List getNamesAttrFromProfileIsWritable(LwM2MClient lwM2MClient) { - AttrTelemetryObserveValue profile = lwM2mInMemorySecurityStore.getProfile(lwM2MClient.getProfileUuid()); + LwM2MClientProfile profile = lwM2mInMemorySecurityStore.getProfile(lwM2MClient.getProfileUuid()); Set attrSet = new Gson().fromJson(profile.getPostAttributeProfile(), Set.class); ConcurrentMap keyNamesMap = new Gson().fromJson(profile.getPostKeyNameProfile().toString(), ConcurrentHashMap.class); @@ -484,7 +479,7 @@ public class LwM2MTransportServiceImpl implements LwM2MTransportService { * #1 - get AttrName/TelemetryName with value: * #1.1 from Client * #1.2 from LwM2MClient: - * -- resourceId == path from AttrTelemetryObserveValue.postAttributeProfile/postTelemetryProfile/postObserveProfile + * -- resourceId == path from LwM2MClientProfile.postAttributeProfile/postTelemetryProfile/postObserveProfile * -- AttrName/TelemetryName == resourceName from ModelObject.objectModel, value from ModelObject.instance.resource(resourceId) * #2 - set Attribute/Telemetry * @@ -539,8 +534,8 @@ public class LwM2MTransportServiceImpl implements LwM2MTransportService { * (attributes/telemetry): new {name(Attr/Telemetry):value} */ private void getParametersFromProfile(JsonObject attributes, JsonObject telemetry, Registration registration, Set path) { - AttrTelemetryObserveValue attrTelemetryObserveValue = lwM2mInMemorySecurityStore.getProfiles().get(lwM2mInMemorySecurityStore.getSessions().get(registration.getId()).getProfileUuid()); - attrTelemetryObserveValue.getPostAttributeProfile().forEach(p -> { + LwM2MClientProfile lwM2MClientProfile = lwM2mInMemorySecurityStore.getProfiles().get(lwM2mInMemorySecurityStore.getSessions().get(registration.getId()).getProfileUuid()); + lwM2MClientProfile.getPostAttributeProfile().forEach(p -> { LwM2mPath pathIds = new LwM2mPath(p.getAsString().toString()); if (pathIds.isResource()) { if (path == null || path.contains(p.getAsString())) { @@ -548,7 +543,7 @@ public class LwM2MTransportServiceImpl implements LwM2MTransportService { } } }); - attrTelemetryObserveValue.getPostTelemetryProfile().forEach(p -> { + lwM2MClientProfile.getPostTelemetryProfile().forEach(p -> { LwM2mPath pathIds = new LwM2mPath(p.getAsString().toString()); if (pathIds.isResource()) { if (path == null || path.contains(p.getAsString())) { @@ -609,20 +604,20 @@ public class LwM2MTransportServiceImpl implements LwM2MTransportService { if (lwServer.getObservationService().getObservations(registration).size() > 0) { this.setCancelObservations(lwServer, registration); } - UUID profileUUid = lwM2mInMemorySecurityStore.getSessions().get(registration.getId()).getProfileUuid(); - AttrTelemetryObserveValue attrTelemetryObserveValue = lwM2mInMemorySecurityStore.getProfiles().get(profileUUid); - attrTelemetryObserveValue.getPostObserveProfile().forEach(p -> { + LwM2MClientProfile lwM2MClientProfile = lwM2mInMemorySecurityStore.getProfile(registration.getId()); + Set clientInstances = this.getAllInstancesInClient(registration); + lwM2MClientProfile.getPostObserveProfile().forEach(p -> { // #1.1 - String target = (getValidateObserve(attrTelemetryObserveValue.getPostAttributeProfile(), p.getAsString().toString())) ? - p.getAsString().toString() : (getValidateObserve(attrTelemetryObserveValue.getPostTelemetryProfile(), p.getAsString().toString())) ? - p.getAsString().toString() : null; - if (target != null) { + String target = p.getAsString().toString(); + String[] resPath = target.split("/"); + String instance = "/" + resPath[1] + "/" + resPath[2]; + if (clientInstances.contains(instance)) { // #2 - if (this.getResourceValueToString(lwM2mInMemorySecurityStore.getSessions().get(registration.getId()), target) != null) { - lwM2MTransportRequest.sendAllRequest(lwServer, registration, target, GET_TYPE_OPER_OBSERVE, - null, null, null, null, this.context.getCtxServer().getTimeout(), - false); - } +// if (this.getResourceValueToString(lwM2mInMemorySecurityStore.getSessions().get(registration.getId()), target) != null) { + lwM2MTransportRequest.sendAllRequest(lwServer, registration, target, GET_TYPE_OPER_OBSERVE, + null, null, null, null, this.context.getCtxServer().getTimeout(), + false); +// } } }); } @@ -648,19 +643,19 @@ public class LwM2MTransportServiceImpl implements LwM2MTransportService { * @param path - recourse from postObserveProfile * @return rez - true if path observe is in attribute/telemetry */ - private boolean getValidateObserve(JsonElement parameters, String path) { - AtomicBoolean rez = new AtomicBoolean(false); - if (parameters.isJsonArray()) { - parameters.getAsJsonArray().forEach(p -> { - if (p.getAsString().toString().equals(path)) rez.set(true); - } - ); - } else if (parameters.isJsonObject()) { - rez.set((parameters.getAsJsonObject().entrySet()).stream().map(json -> json.toString()) - .filter(path::equals).findAny().orElse(null) != null); - } - return rez.get(); - } +// private boolean getValidateObserve(JsonElement parameters, String path) { +// AtomicBoolean rez = new AtomicBoolean(false); +// if (parameters.isJsonArray()) { +// parameters.getAsJsonArray().forEach(p -> { +// if (p.getAsString().toString().equals(path)) rez.set(true); +// } +// ); +// } else if (parameters.isJsonObject()) { +// rez.set((parameters.getAsJsonObject().entrySet()).stream().map(json -> json.toString()) +// .filter(path::equals).findAny().orElse(null) != null); +// } +// return rez.get(); +// } /** * Sending observe value to thingsboard from ObservationListener.onResponse: object, instance, SingleResource or MultipleResource @@ -673,15 +668,15 @@ public class LwM2MTransportServiceImpl implements LwM2MTransportService { public void onObservationResponse(Registration registration, String path, ReadResponse response) { if (response.getContent() != null) { if (response.getContent() instanceof LwM2mObject) { -// LwM2mObject content = (LwM2mObject) response.getContent(); + LwM2mObject lwM2mObject = (LwM2mObject) response.getContent(); } else if (response.getContent() instanceof LwM2mObjectInstance) { -// LwM2mObjectInstance content = (LwM2mObjectInstance) response.getContent(); - } else if (response.getContent() instanceof LwM2mSingleResource) { - LwM2mSingleResource content = (LwM2mSingleResource) response.getContent(); - this.onObservationSetResourcesValue(registration, content.getValue(), null, path); - } else if (response.getContent() instanceof LwM2mMultipleResource) { - LwM2mMultipleResource content = (LwM2mMultipleResource) response.getContent(); - this.onObservationSetResourcesValue(registration, null, content.getValues(), path); + LwM2mObjectInstance lwM2mObjectInstance = (LwM2mObjectInstance) response.getContent(); + } else if (response.getContent() instanceof LwM2mResource) { + LwM2mResource lwM2mResource = (LwM2mResource) response.getContent(); + this.onObservationSetResourcesValue(registration, lwM2mResource, path); +// } else if (response.getContent() instanceof LwM2mMultipleResource) { +// LwM2mMultipleResource resource = (LwM2mMultipleResource) response.getContent(); +// this.onObservationSetResourcesValue(registration, null, resource.getValues(), path); } } } @@ -692,39 +687,17 @@ public class LwM2MTransportServiceImpl implements LwM2MTransportService { * #2 Update new Resources (replace old Resource Value on new Resource Value) * * @param registration - Registration LwM2M Client - * @param value - LwM2mSingleResource response.getContent() - * @param values - LwM2mSingleResource response.getContent() + * @param - LwM2mSingleResource response.getContent() + * @param - LwM2mSingleResource response.getContent() * @param path - resource */ - private void onObservationSetResourcesValue(Registration registration, Object value, Map values, String path) { - boolean isChange = false; - try { - writeLock.lock(); - // #1 - LwM2MClient lwM2MClient = lwM2mInMemorySecurityStore.getLwM2MClientWithReg(registration, null); - LwM2mPath pathIds = new LwM2mPath(path); - ResourceModel.Type resModelType = context.getCtxServer().getResourceModelType(registration, pathIds); - ResourceValue resValueOld = lwM2MClient.getResources().get(path); - // #2 - if (resValueOld.isMultiInstances() && !values.toString().equals(resValueOld.getResourceValue().toString())) { - lwM2MClient.getResources().get(path).setValues(values); - isChange = true; - } else if (!LwM2MTransportHandler.equalsResourceValue(resValueOld.getValue(), value, resModelType, pathIds)) { - lwM2MClient.getResources().get(path).setValue(value); - log.warn("upDateResize: [{}] [{}] [{}] [{}]", lwM2MClient.getEndPoint(), lwM2MClient.getResources().size(), value, path); - isChange = true; - } - } catch (Exception e) { - log.error("#1_1 Update ResourcesValue after Observation is unsuccessfully path: [{}] value: [{}] [{}]", path, value, e.toString()); - } finally { - writeLock.unlock(); - } - - if (isChange) { - Set paths = new HashSet<>(); - paths.add(path); - this.updateAttrTelemetry(registration, false, paths); - } + private void onObservationSetResourcesValue(Registration registration, LwM2mResource lwM2mResource, String path) { + LwM2MClient lwM2MClient = lwM2mInMemorySecurityStore.getLwM2MClientWithReg(registration, null); + lwM2MClient.updateResourceValue(path, lwM2mResource); + log.warn("upDateResize: [{}] [{}] [{}]", lwM2MClient.getEndPoint(), lwM2MClient.getResources().size(), path); + Set paths = new HashSet<>(); + paths.add(path); + this.updateAttrTelemetry(registration, false, paths); } /** @@ -738,7 +711,7 @@ public class LwM2MTransportServiceImpl implements LwM2MTransportService { /** * Update - sent request in change value resources in Client * Path to resources from profile equal keyName or from ModelObject equal name - * Only for resources: isWritable && isPresent as attribute in profile -> AttrTelemetryObserveValue (format: CamelCase) + * Only for resources: isWritable && isPresent as attribute in profile -> LwM2MClientProfile (format: CamelCase) * Delete - nothing * * * @param msg - @@ -750,7 +723,7 @@ public class LwM2MTransportServiceImpl implements LwM2MTransportService { String path = this.getPathAttributeUpdate(sessionInfo, de.getKey()); String value = de.getValue().getAsString(); LwM2MClient lwM2MClient = lwM2mInMemorySecurityStore.getSession(new UUID(sessionInfo.getSessionIdMSB(), sessionInfo.getSessionIdLSB())).entrySet().iterator().next().getValue(); - AttrTelemetryObserveValue profile = lwM2mInMemorySecurityStore.getProfile(new UUID(sessionInfo.getDeviceProfileIdMSB(), sessionInfo.getDeviceProfileIdLSB())); + LwM2MClientProfile profile = lwM2mInMemorySecurityStore.getProfile(new UUID(sessionInfo.getDeviceProfileIdMSB(), sessionInfo.getDeviceProfileIdLSB())); ResourceModel resourceModel = context.getCtxServer().getResourceModel(lwM2MClient.getRegistration(), new LwM2mPath(path)); if (!path.isEmpty() && (this.validatePathInAttrProfile(profile, path) || this.validatePathInTelemetryProfile(profile, path))) { if (resourceModel != null && resourceModel.operations.isWritable()) { @@ -775,7 +748,7 @@ public class LwM2MTransportServiceImpl implements LwM2MTransportService { /** * Get path to resource from profile equal keyName or from ModelObject equal name - * Only for resource: isWritable && isPresent as attribute in profile -> AttrTelemetryObserveValue (format: CamelCase) + * Only for resource: isWritable && isPresent as attribute in profile -> LwM2MClientProfile (format: CamelCase) * * @param sessionInfo - * @param name - @@ -792,7 +765,7 @@ public class LwM2MTransportServiceImpl implements LwM2MTransportService { * @param path - * @return true if path isPresent in postAttributeProfile */ - private boolean validatePathInAttrProfile(AttrTelemetryObserveValue profile, String path) { + private boolean validatePathInAttrProfile(LwM2MClientProfile profile, String path) { Set attributesSet = new Gson().fromJson(profile.getPostAttributeProfile(), Set.class); return attributesSet.stream().filter(p -> p.equals(path)).findFirst().isPresent(); } @@ -802,7 +775,7 @@ public class LwM2MTransportServiceImpl implements LwM2MTransportService { * @param path - * @return true if path isPresent in postAttributeProfile */ - private boolean validatePathInTelemetryProfile(AttrTelemetryObserveValue profile, String path) { + private boolean validatePathInTelemetryProfile(LwM2MClientProfile profile, String path) { Set telemetriesSet = new Gson().fromJson(profile.getPostTelemetryProfile(), Set.class); return telemetriesSet.stream().filter(p -> p.equals(path)).findFirst().isPresent(); } @@ -816,7 +789,7 @@ public class LwM2MTransportServiceImpl implements LwM2MTransportService { * @return - */ private String getPathAttributeUpdateProfile(TransportProtos.SessionInfoProto sessionInfo, String name) { - AttrTelemetryObserveValue profile = lwM2mInMemorySecurityStore.getProfile(new UUID(sessionInfo.getDeviceProfileIdMSB(), sessionInfo.getDeviceProfileIdLSB())); + LwM2MClientProfile profile = lwM2mInMemorySecurityStore.getProfile(new UUID(sessionInfo.getDeviceProfileIdMSB(), sessionInfo.getDeviceProfileIdLSB())); return profile.getPostKeyNameProfile().getAsJsonObject().entrySet().stream() .filter(e -> e.getValue().getAsString().equals(name)).findFirst().map(Map.Entry::getKey) .orElse(""); @@ -830,14 +803,16 @@ public class LwM2MTransportServiceImpl implements LwM2MTransportService { * @param request - */ public void onAttributeUpdateOk(Registration registration, String path, WriteRequest request, boolean isDelayedUpdate) { - ResourceModel resource = context.getCtxServer().getResourceModel(registration, new LwM2mPath(path)); - if (resource.multiple) { - this.onObservationSetResourcesValue(registration, null, ((LwM2mSingleResource) request.getNode()).getValues(), path); - } else { - this.onObservationSetResourcesValue(registration, ((LwM2mSingleResource) request.getNode()).getValue(), null, path); +// ResourceModel resource = context.getCtxServer().getResourceModel(registration, new LwM2mPath(path)); +// if (resource.multiple) { + this.onObservationSetResourcesValue(registration, ((LwM2mResource) request.getNode()), path); +// } else { +// this.onObservationSetResourcesValue(registration, ((LwM2mSingleResource) request.getNode()).getValue(), null, path); +// } + if (isDelayedUpdate) { + lwM2mInMemorySecurityStore.getLwM2MClientWithReg(registration, null) + .onSuccessOrErrorDelayedRequests(request.getPath().toString()); } - if (isDelayedUpdate) lwM2mInMemorySecurityStore.getLwM2MClientWithReg(registration, null) - .onSuccessOrErrorDelayedRequests(request.getPath().toString()); } /** @@ -909,24 +884,24 @@ public class LwM2MTransportServiceImpl implements LwM2MTransportService { */ private void onDeviceUpdateChangeProfile(Set registrationIds, DeviceProfile deviceProfile) { - AttrTelemetryObserveValue attrTelemetryObserveValueOld = lwM2mInMemorySecurityStore.getProfiles().get(deviceProfile.getUuidId()); + LwM2MClientProfile lwM2MClientProfileOld = lwM2mInMemorySecurityStore.getProfiles().get(deviceProfile.getUuidId()); if (lwM2mInMemorySecurityStore.addUpdateProfileParameters(deviceProfile)) { // #1 - JsonArray attributeOld = attrTelemetryObserveValueOld.getPostAttributeProfile(); + JsonArray attributeOld = lwM2MClientProfileOld.getPostAttributeProfile(); Set attributeSetOld = new Gson().fromJson(attributeOld, Set.class); - JsonArray telemetryOld = attrTelemetryObserveValueOld.getPostTelemetryProfile(); + JsonArray telemetryOld = lwM2MClientProfileOld.getPostTelemetryProfile(); Set telemetrySetOld = new Gson().fromJson(telemetryOld, Set.class); - JsonArray observeOld = attrTelemetryObserveValueOld.getPostObserveProfile(); - JsonObject keyNameOld = attrTelemetryObserveValueOld.getPostKeyNameProfile(); + JsonArray observeOld = lwM2MClientProfileOld.getPostObserveProfile(); + JsonObject keyNameOld = lwM2MClientProfileOld.getPostKeyNameProfile(); - AttrTelemetryObserveValue attrTelemetryObserveValueNew = lwM2mInMemorySecurityStore.getProfiles().get(deviceProfile.getUuidId()); - JsonArray attributeNew = attrTelemetryObserveValueNew.getPostAttributeProfile(); + LwM2MClientProfile lwM2MClientProfileNew = lwM2mInMemorySecurityStore.getProfiles().get(deviceProfile.getUuidId()); + JsonArray attributeNew = lwM2MClientProfileNew.getPostAttributeProfile(); Set attributeSetNew = new Gson().fromJson(attributeNew, Set.class); - JsonArray telemetryNew = attrTelemetryObserveValueNew.getPostTelemetryProfile(); + JsonArray telemetryNew = lwM2MClientProfileNew.getPostTelemetryProfile(); Set telemetrySetNew = new Gson().fromJson(telemetryNew, Set.class); - JsonArray observeNew = attrTelemetryObserveValueNew.getPostObserveProfile(); - JsonObject keyNameNew = attrTelemetryObserveValueNew.getPostKeyNameProfile(); + JsonArray observeNew = lwM2MClientProfileNew.getPostObserveProfile(); + JsonObject keyNameNew = lwM2MClientProfileNew.getPostKeyNameProfile(); // #3 ResultsAnalyzerParameters sentAttrToThingsboard = new ResultsAnalyzerParameters(); diff --git a/common/transport/lwm2m/src/main/java/org/thingsboard/server/transport/lwm2m/server/client/LwM2MClient.java b/common/transport/lwm2m/src/main/java/org/thingsboard/server/transport/lwm2m/server/client/LwM2MClient.java index 7d32fe5f8a..553ed9af4b 100644 --- a/common/transport/lwm2m/src/main/java/org/thingsboard/server/transport/lwm2m/server/client/LwM2MClient.java +++ b/common/transport/lwm2m/src/main/java/org/thingsboard/server/transport/lwm2m/server/client/LwM2MClient.java @@ -59,7 +59,6 @@ public class LwM2MClient implements Cloneable { private Set delayedRequestsId; private Map responses; private final LwM2mValueConverterImpl converter; - private boolean clientUpdateValueAfterConnect; public Object clone() throws CloneNotSupportedException { return super.clone(); @@ -114,7 +113,7 @@ public class LwM2MClient implements Cloneable { if (this.responses.size() == 0) this.responses = new ConcurrentHashMap<>(); } - private void updateResourceValue(String pathRez, LwM2mResource rez) { + public void updateResourceValue(String pathRez, LwM2mResource rez) { if (rez instanceof LwM2mMultipleResource){ this.resources.put(pathRez, new ResourceValue(rez.getValues(), null, true)); } diff --git a/common/transport/lwm2m/src/main/java/org/thingsboard/server/transport/lwm2m/server/client/AttrTelemetryObserveValue.java b/common/transport/lwm2m/src/main/java/org/thingsboard/server/transport/lwm2m/server/client/LwM2MClientProfile.java similarity index 86% rename from common/transport/lwm2m/src/main/java/org/thingsboard/server/transport/lwm2m/server/client/AttrTelemetryObserveValue.java rename to common/transport/lwm2m/src/main/java/org/thingsboard/server/transport/lwm2m/server/client/LwM2MClientProfile.java index ab8dacc56c..77f7a67646 100644 --- a/common/transport/lwm2m/src/main/java/org/thingsboard/server/transport/lwm2m/server/client/AttrTelemetryObserveValue.java +++ b/common/transport/lwm2m/src/main/java/org/thingsboard/server/transport/lwm2m/server/client/LwM2MClientProfile.java @@ -20,7 +20,14 @@ import com.google.gson.JsonObject; import lombok.Data; @Data -public class AttrTelemetryObserveValue { +public class LwM2MClientProfile { + /** + * {"clientLwM2mSettings": { + * clientUpdateValueAfterConnect: false; + * } + **/ + JsonObject postClientLwM2mSettings; + /** * {"keyName": { * "/3/0/1": "modelNumber", diff --git a/common/transport/lwm2m/src/main/java/org/thingsboard/server/transport/lwm2m/server/secure/LwM2mInMemorySecurityStore.java b/common/transport/lwm2m/src/main/java/org/thingsboard/server/transport/lwm2m/server/secure/LwM2mInMemorySecurityStore.java index fa35ea70e4..b49193434d 100644 --- a/common/transport/lwm2m/src/main/java/org/thingsboard/server/transport/lwm2m/server/secure/LwM2mInMemorySecurityStore.java +++ b/common/transport/lwm2m/src/main/java/org/thingsboard/server/transport/lwm2m/server/secure/LwM2mInMemorySecurityStore.java @@ -15,7 +15,6 @@ */ package org.thingsboard.server.transport.lwm2m.server.secure; -import com.google.gson.JsonObject; import lombok.extern.slf4j.Slf4j; import org.eclipse.leshan.core.util.Hex; import org.eclipse.leshan.server.californium.LeshanServer; @@ -32,8 +31,8 @@ import org.thingsboard.server.transport.lwm2m.secure.LwM2MSecurityMode; import org.thingsboard.server.transport.lwm2m.secure.LwM2mCredentialsSecurityInfoValidator; import org.thingsboard.server.transport.lwm2m.secure.ReadResultSecurityStore; import org.thingsboard.server.transport.lwm2m.server.LwM2MTransportHandler; -import org.thingsboard.server.transport.lwm2m.server.client.AttrTelemetryObserveValue; import org.thingsboard.server.transport.lwm2m.server.client.LwM2MClient; +import org.thingsboard.server.transport.lwm2m.server.client.LwM2MClientProfile; import org.thingsboard.server.transport.lwm2m.utils.TypeServer; import java.util.Collection; @@ -60,7 +59,7 @@ public class LwM2mInMemorySecurityStore extends InMemorySecurityStore { private final Lock readLock = readWriteLock.readLock(); private final Lock writeLock = readWriteLock.writeLock(); private final Map sessions = new ConcurrentHashMap<>(); - private Map profiles = new ConcurrentHashMap<>(); + private Map profiles = new ConcurrentHashMap<>(); private SecurityStoreListener listener; @Autowired @@ -228,23 +227,28 @@ public class LwM2mInMemorySecurityStore extends InMemorySecurityStore { return this.sessions; } - public Map getProfiles() { + public Map getProfiles() { return this.profiles; } - public AttrTelemetryObserveValue getProfile(UUID profileUuId) { + public LwM2MClientProfile getProfile(UUID profileUuId) { return this.profiles.get(profileUuId); } - public Map setProfiles(Map profiles) { + public LwM2MClientProfile getProfile(String registrationId) { + UUID profileUUid = this.getSessions().get(registrationId).getProfileUuid(); + return this.getProfiles().get(profileUUid); + } + + public Map setProfiles(Map profiles) { return this.profiles = profiles; } public boolean addUpdateProfileParameters(DeviceProfile deviceProfile) { - JsonObject profilesConfigData = LwM2MTransportHandler.getObserveAttrTelemetryFromThingsboard(deviceProfile); - if (profilesConfigData != null) { - profiles.put(deviceProfile.getUuidId(), LwM2MTransportHandler.getNewProfileParameters(profilesConfigData)); + LwM2MClientProfile lwM2MClientProfile = LwM2MTransportHandler.getLwM2MClientProfileFromThingsboard(deviceProfile); + if (lwM2MClientProfile != null) { + profiles.put(deviceProfile.getUuidId(), lwM2MClientProfile); } - return (profilesConfigData != null); + return (lwM2MClientProfile != null); } } diff --git a/common/transport/transport-api/src/main/java/org/thingsboard/server/common/transport/lwm2m/LwM2MTransportConfigServer.java b/common/transport/transport-api/src/main/java/org/thingsboard/server/common/transport/lwm2m/LwM2MTransportConfigServer.java index 5fe68f7dab..dfe2b75fef 100644 --- a/common/transport/transport-api/src/main/java/org/thingsboard/server/common/transport/lwm2m/LwM2MTransportConfigServer.java +++ b/common/transport/transport-api/src/main/java/org/thingsboard/server/common/transport/lwm2m/LwM2MTransportConfigServer.java @@ -118,10 +118,6 @@ public class LwM2MTransportConfigServer { @Value("${transport.lwm2m.registered_pool_size:}") private int registeredPoolSize; - @Getter - @Value("${transport.lwm2m.client_update_value_after_connect:}") - private boolean clientUpdateValueAfterConnect; - @Getter @Value("${transport.lwm2m.update_registered_pool_size:}") private int updateRegisteredPoolSize; diff --git a/ui-ngx/src/app/modules/home/components/profile/device/lwm2m/lwm2m-device-profile-transport-configuration.component.html b/ui-ngx/src/app/modules/home/components/profile/device/lwm2m/lwm2m-device-profile-transport-configuration.component.html index 15bd9034c0..7f833e8df6 100644 --- a/ui-ngx/src/app/modules/home/components/profile/device/lwm2m/lwm2m-device-profile-transport-configuration.component.html +++ b/ui-ngx/src/app/modules/home/components/profile/device/lwm2m/lwm2m-device-profile-transport-configuration.component.html @@ -26,7 +26,9 @@ { count: +lwm2mDeviceProfileFormGroup.get('clientUpdateValueAfterConnect').value, value: lwm2mDeviceProfileFormGroup.get('clientUpdateValueAfterConnect').value }) | async }}" matTooltipPosition="above"> - {{ 'device-profile.lwm2m.client-update-value-after-connect' | translate }} + {{ translate.get('device-profile.lwm2m.client-update-value-after-connect', + { count: +lwm2mDeviceProfileFormGroup.get('clientUpdateValueAfterConnect').value, + value: lwm2mDeviceProfileFormGroup.get('clientUpdateValueAfterConnect').value }) | async }}
diff --git a/ui-ngx/src/assets/locale/locale.constant-en_US.json b/ui-ngx/src/assets/locale/locale.constant-en_US.json index 437f7c8214..02d15f8857 100644 --- a/ui-ngx/src/assets/locale/locale.constant-en_US.json +++ b/ui-ngx/src/assets/locale/locale.constant-en_US.json @@ -1103,8 +1103,8 @@ "schedule-time-to": "To", "schedule-days-of-week-required": "At least one day of week should be selected.", "lwm2m": { - "client-update-value-after-connect": "Query client resource values after connecting ", - "client-update-value-after-connect-tip": "{ count, plural, 1 {After connecting the Client, we get All resource values for all objects} other {Once connected to the client, requests are sent to the observer from the profile configuration.} }", + "client-update-value-after-connect": "{ count, plural, 1 {Request to the client after registration for All resource values} other {Request to the client after registration to read values only as attributes or telemetry} }", + "client-update-value-after-connect-tip": "{ count, plural, 1 {Request to the client after registration to read all resource values for all objects} other {Request to the client after registration to read the values of the resources marked as attribute or telemetry from the profile configuration.} }", "object-list": "Object list", "object-list-empty": "No objects selected.", "no-objects-matching": "No objects matching '{{object}}' were found.",