Commit 0a2477da79a342d6943fcc4574d89d62c1d7ef45
Committed by
GitHub
Merge pull request #4238 from thingsboard/add-models
Add models
Showing
30 changed files
with
395 additions
and
126 deletions
... | ... | @@ -23,12 +23,12 @@ import org.springframework.web.bind.annotation.RequestMethod; |
23 | 23 | import org.springframework.web.bind.annotation.RequestParam; |
24 | 24 | import org.springframework.web.bind.annotation.ResponseBody; |
25 | 25 | import org.springframework.web.bind.annotation.RestController; |
26 | +import org.thingsboard.server.common.data.Resource; | |
27 | +import org.thingsboard.server.common.data.ResourceType; | |
26 | 28 | import org.thingsboard.server.common.data.exception.ThingsboardException; |
27 | 29 | import org.thingsboard.server.common.data.id.TenantId; |
28 | 30 | import org.thingsboard.server.common.data.page.PageData; |
29 | 31 | import org.thingsboard.server.common.data.page.PageLink; |
30 | -import org.thingsboard.server.common.data.Resource; | |
31 | -import org.thingsboard.server.common.data.ResourceType; | |
32 | 32 | import org.thingsboard.server.dao.resource.ResourceService; |
33 | 33 | import org.thingsboard.server.queue.util.TbCoreComponent; |
34 | 34 | ... | ... |
... | ... | @@ -17,19 +17,23 @@ package org.thingsboard.server.service.install; |
17 | 17 | |
18 | 18 | import com.fasterxml.jackson.databind.JsonNode; |
19 | 19 | import lombok.extern.slf4j.Slf4j; |
20 | +import org.eclipse.leshan.core.model.DDFFileParser; | |
21 | +import org.eclipse.leshan.core.model.DefaultDDFFileValidator; | |
22 | +import org.eclipse.leshan.core.model.InvalidDDFFileException; | |
23 | +import org.eclipse.leshan.core.model.ObjectModel; | |
20 | 24 | import org.springframework.beans.factory.annotation.Autowired; |
21 | 25 | import org.springframework.beans.factory.annotation.Value; |
22 | 26 | import org.springframework.stereotype.Component; |
23 | 27 | import org.springframework.util.StringUtils; |
24 | 28 | import org.thingsboard.server.common.data.Dashboard; |
29 | +import org.thingsboard.server.common.data.Resource; | |
30 | +import org.thingsboard.server.common.data.ResourceType; | |
25 | 31 | import org.thingsboard.server.common.data.id.CustomerId; |
26 | 32 | import org.thingsboard.server.common.data.id.EntityId; |
27 | 33 | import org.thingsboard.server.common.data.id.TenantId; |
28 | 34 | import org.thingsboard.server.common.data.oauth2.OAuth2ClientRegistrationTemplate; |
29 | 35 | import org.thingsboard.server.common.data.rule.RuleChain; |
30 | 36 | import org.thingsboard.server.common.data.rule.RuleChainMetaData; |
31 | -import org.thingsboard.server.common.data.Resource; | |
32 | -import org.thingsboard.server.common.data.ResourceType; | |
33 | 37 | import org.thingsboard.server.common.data.widget.WidgetType; |
34 | 38 | import org.thingsboard.server.common.data.widget.WidgetsBundle; |
35 | 39 | import org.thingsboard.server.dao.dashboard.DashboardService; |
... | ... | @@ -39,6 +43,8 @@ import org.thingsboard.server.dao.rule.RuleChainService; |
39 | 43 | import org.thingsboard.server.dao.widget.WidgetTypeService; |
40 | 44 | import org.thingsboard.server.dao.widget.WidgetsBundleService; |
41 | 45 | |
46 | +import java.io.ByteArrayInputStream; | |
47 | +import java.io.File; | |
42 | 48 | import java.io.IOException; |
43 | 49 | import java.nio.file.DirectoryStream; |
44 | 50 | import java.nio.file.Files; |
... | ... | @@ -196,18 +202,23 @@ public class InstallScripts { |
196 | 202 | } |
197 | 203 | |
198 | 204 | public void loadSystemLwm2mResources() throws Exception { |
205 | +// Path modelsDir = Paths.get("/home/nick/Igor_project/thingsboard_ce_3_2_docker/thingsboard/common/transport/lwm2m/src/main/resources/models/"); | |
199 | 206 | Path modelsDir = Paths.get(getDataDir(), MODELS_DIR); |
200 | 207 | if (Files.isDirectory(modelsDir)) { |
201 | 208 | try (DirectoryStream<Path> dirStream = Files.newDirectoryStream(modelsDir, path -> path.toString().endsWith(XML_EXT))) { |
202 | 209 | dirStream.forEach( |
203 | 210 | path -> { |
204 | 211 | try { |
205 | - Resource resource = new Resource(); | |
206 | - resource.setTenantId(TenantId.SYS_TENANT_ID); | |
207 | - resource.setResourceType(ResourceType.LWM2M_MODEL); | |
208 | - resource.setResourceId(path.getFileName().toString()); | |
209 | - resource.setValue(Base64.getEncoder().encodeToString(Files.readAllBytes(path))); | |
210 | - resourceService.saveResource(resource); | |
212 | + byte[] fileBytes = Files.readAllBytes(path); | |
213 | + String key = getObjectModelLwm2mValid(fileBytes, path.getFileName().toString(), new DefaultDDFFileValidator()); | |
214 | + if (key != null) { | |
215 | + Resource resource = new Resource(); | |
216 | + resource.setTenantId(TenantId.SYS_TENANT_ID); | |
217 | + resource.setResourceType(ResourceType.LWM2M_MODEL); | |
218 | + resource.setResourceId(key); | |
219 | + resource.setValue(Base64.getEncoder().encodeToString(fileBytes)); | |
220 | + resourceService.saveResource(resource); | |
221 | + } | |
211 | 222 | } catch (Exception e) { |
212 | 223 | log.error("Unable to load lwm2m model [{}]", path.toString()); |
213 | 224 | throw new RuntimeException("Unable to load lwm2m model", e); |
... | ... | @@ -218,17 +229,43 @@ public class InstallScripts { |
218 | 229 | } |
219 | 230 | |
220 | 231 | Path jksPath = Paths.get(getDataDir(), CREDENTIALS_DIR, "serverKeyStore.jks"); |
221 | - try { | |
222 | - Resource resource = new Resource(); | |
223 | - resource.setTenantId(TenantId.SYS_TENANT_ID); | |
224 | - resource.setResourceType(ResourceType.JKS); | |
225 | - resource.setResourceId(jksPath.getFileName().toString()); | |
226 | - resource.setValue(Base64.getEncoder().encodeToString(Files.readAllBytes(jksPath))); | |
227 | - resourceService.saveResource(resource); | |
228 | - } catch (Exception e) { | |
229 | - log.error("Unable to load lwm2m serverKeyStore [{}]", jksPath.toString()); | |
230 | - throw new RuntimeException("Unable to load l2m2m serverKeyStore", e); | |
231 | - } | |
232 | + try { | |
233 | + Resource resource = new Resource(); | |
234 | + resource.setTenantId(TenantId.SYS_TENANT_ID); | |
235 | + resource.setResourceType(ResourceType.JKS); | |
236 | + resource.setResourceId(jksPath.getFileName().toString()); | |
237 | + resource.setValue(Base64.getEncoder().encodeToString(Files.readAllBytes(jksPath))); | |
238 | + resourceService.saveResource(resource); | |
239 | + } catch (Exception e) { | |
240 | + log.error("Unable to load lwm2m serverKeyStore [{}]", jksPath.toString()); | |
241 | + throw new RuntimeException("Unable to load l2m2m serverKeyStore", e); | |
242 | + } | |
243 | + } | |
244 | + | |
245 | + private String getObjectModelLwm2mValid(byte[] xmlByte, String streamName, DefaultDDFFileValidator ddfValidator) { | |
246 | + try { | |
247 | + DDFFileParser ddfFileParser = new DDFFileParser(ddfValidator); | |
248 | + ObjectModel objectModel = ddfFileParser.parseEx(new ByteArrayInputStream(xmlByte), streamName).get(0); | |
249 | + return objectModel.id + "##" + objectModel.getVersion(); | |
250 | + } catch (IOException | InvalidDDFFileException e) { | |
251 | + log.error("Could not parse the XML file [{}]", streamName, e); | |
252 | + return null; | |
253 | + } | |
254 | + | |
255 | + } | |
256 | + | |
257 | + private void removeFile(Path modelsDir, String nameFile, byte[] fileBytes) { | |
258 | + String path = "/home/nick/Igor_project/thingsboard_ce_3_2_docker/thingsboard/common/transport/lwm2m/src/main/resources/models/"; | |
259 | + File file = new File(path + nameFile); | |
260 | + if (!file.isDirectory()) { | |
261 | + try { | |
262 | + Files.write(Paths.get(path + "server/" + nameFile), fileBytes); | |
263 | + file.delete(); | |
264 | + } catch (IOException e) { | |
265 | + e.printStackTrace(); | |
266 | + } | |
267 | + | |
268 | + } | |
232 | 269 | } |
233 | 270 | |
234 | 271 | public void loadDashboards(TenantId tenantId, CustomerId customerId) throws Exception { | ... | ... |
... | ... | @@ -447,6 +447,7 @@ public class SqlDatabaseUpgradeService implements DatabaseEntitiesUpgradeService |
447 | 447 | " );"); |
448 | 448 | |
449 | 449 | conn.createStatement().execute("UPDATE tb_schema_settings SET schema_version = 3003000;"); |
450 | + installScripts.loadSystemLwm2mResources(); | |
450 | 451 | } catch (Exception e) { |
451 | 452 | log.error("Failed updating schema!!!", e); |
452 | 453 | } | ... | ... |
... | ... | @@ -33,7 +33,6 @@ import org.thingsboard.server.common.data.page.PageLink; |
33 | 33 | import org.thingsboard.server.common.transport.lwm2m.LwM2MTransportConfigBootstrap; |
34 | 34 | import org.thingsboard.server.common.transport.lwm2m.LwM2MTransportConfigServer; |
35 | 35 | import org.thingsboard.server.dao.service.Validator; |
36 | -import org.thingsboard.server.queue.util.TbLwM2mTransportComponent; | |
37 | 36 | import org.thingsboard.server.transport.lwm2m.secure.LwM2MSecurityMode; |
38 | 37 | |
39 | 38 | import java.math.BigInteger; |
... | ... | @@ -102,8 +101,8 @@ public class LwM2MModelsRepository { |
102 | 101 | */ |
103 | 102 | private List<LwM2mObject> getLwm2mObjects(Predicate<? super ObjectModel> predicate, String sortProperty, String sortOrder) { |
104 | 103 | List<LwM2mObject> lwM2mObjects = new ArrayList<>(); |
105 | - List<ObjectModel> listObjects = (predicate == null) ? this.contextServer.getModelsValue() : | |
106 | - contextServer.getModelsValue().stream() | |
104 | + List<ObjectModel> listObjects = (predicate == null) ? this.contextServer.getModelsValueCommon() : | |
105 | + contextServer.getModelsValueCommon().stream() | |
107 | 106 | .filter(predicate) |
108 | 107 | .collect(Collectors.toList()); |
109 | 108 | ... | ... |
... | ... | @@ -26,6 +26,7 @@ import org.thingsboard.server.common.data.Device; |
26 | 26 | import org.thingsboard.server.common.data.DeviceProfile; |
27 | 27 | import org.thingsboard.server.common.data.EntityType; |
28 | 28 | import org.thingsboard.server.common.data.HasName; |
29 | +import org.thingsboard.server.common.data.Resource; | |
29 | 30 | import org.thingsboard.server.common.data.Tenant; |
30 | 31 | import org.thingsboard.server.common.data.TenantProfile; |
31 | 32 | import org.thingsboard.server.common.data.id.DeviceId; |
... | ... | @@ -34,7 +35,6 @@ import org.thingsboard.server.common.data.id.EntityId; |
34 | 35 | import org.thingsboard.server.common.data.id.RuleChainId; |
35 | 36 | import org.thingsboard.server.common.data.id.TenantId; |
36 | 37 | import org.thingsboard.server.common.data.plugin.ComponentLifecycleEvent; |
37 | -import org.thingsboard.server.common.data.Resource; | |
38 | 38 | import org.thingsboard.server.common.msg.TbMsg; |
39 | 39 | import org.thingsboard.server.common.msg.plugin.ComponentLifecycleMsg; |
40 | 40 | import org.thingsboard.server.common.msg.queue.ServiceType; | ... | ... |
... | ... | @@ -19,12 +19,12 @@ import org.thingsboard.rule.engine.api.msg.ToDeviceActorNotificationMsg; |
19 | 19 | import org.thingsboard.server.common.data.ApiUsageState; |
20 | 20 | import org.thingsboard.server.common.data.Device; |
21 | 21 | import org.thingsboard.server.common.data.DeviceProfile; |
22 | +import org.thingsboard.server.common.data.Resource; | |
22 | 23 | import org.thingsboard.server.common.data.Tenant; |
23 | 24 | import org.thingsboard.server.common.data.TenantProfile; |
24 | 25 | import org.thingsboard.server.common.data.id.EntityId; |
25 | 26 | import org.thingsboard.server.common.data.id.TenantId; |
26 | 27 | import org.thingsboard.server.common.data.plugin.ComponentLifecycleEvent; |
27 | -import org.thingsboard.server.common.data.Resource; | |
28 | 28 | import org.thingsboard.server.common.msg.TbMsg; |
29 | 29 | import org.thingsboard.server.common.msg.queue.TopicPartitionInfo; |
30 | 30 | import org.thingsboard.server.gen.transport.TransportProtos; | ... | ... |
... | ... | @@ -31,6 +31,8 @@ import org.thingsboard.server.common.data.DataConstants; |
31 | 31 | import org.thingsboard.server.common.data.Device; |
32 | 32 | import org.thingsboard.server.common.data.DeviceProfile; |
33 | 33 | import org.thingsboard.server.common.data.EntityType; |
34 | +import org.thingsboard.server.common.data.Resource; | |
35 | +import org.thingsboard.server.common.data.ResourceType; | |
34 | 36 | import org.thingsboard.server.common.data.TenantProfile; |
35 | 37 | import org.thingsboard.server.common.data.device.credentials.BasicMqttCredentials; |
36 | 38 | import org.thingsboard.server.common.data.device.credentials.ProvisionDeviceCredentialsData; |
... | ... | @@ -42,8 +44,6 @@ import org.thingsboard.server.common.data.id.TenantId; |
42 | 44 | import org.thingsboard.server.common.data.relation.EntityRelation; |
43 | 45 | import org.thingsboard.server.common.data.security.DeviceCredentials; |
44 | 46 | import org.thingsboard.server.common.data.security.DeviceCredentialsType; |
45 | -import org.thingsboard.server.common.data.Resource; | |
46 | -import org.thingsboard.server.common.data.ResourceType; | |
47 | 47 | import org.thingsboard.server.common.msg.EncryptionUtil; |
48 | 48 | import org.thingsboard.server.common.msg.TbMsg; |
49 | 49 | import org.thingsboard.server.common.msg.TbMsgDataType; | ... | ... |
... | ... | @@ -15,11 +15,13 @@ |
15 | 15 | */ |
16 | 16 | package org.thingsboard.server.dao.resource; |
17 | 17 | |
18 | +import org.thingsboard.server.common.data.Resource; | |
19 | +import org.thingsboard.server.common.data.ResourceType; | |
18 | 20 | import org.thingsboard.server.common.data.id.TenantId; |
19 | 21 | import org.thingsboard.server.common.data.page.PageData; |
20 | 22 | import org.thingsboard.server.common.data.page.PageLink; |
21 | -import org.thingsboard.server.common.data.Resource; | |
22 | -import org.thingsboard.server.common.data.ResourceType; | |
23 | + | |
24 | +import java.util.List; | |
23 | 25 | |
24 | 26 | |
25 | 27 | public interface ResourceService { |
... | ... | @@ -29,6 +31,8 @@ public interface ResourceService { |
29 | 31 | |
30 | 32 | PageData<Resource> findResourcesByTenantId(TenantId tenantId, PageLink pageLink); |
31 | 33 | |
34 | + List<Resource> findResourcesByTenantIdResourceType(TenantId tenantId, ResourceType resourceType); | |
35 | + | |
32 | 36 | void deleteResource(TenantId tenantId, ResourceType resourceType, String resourceId); |
33 | 37 | |
34 | 38 | void deleteResourcesByTenantId(TenantId tenantId); | ... | ... |
common/data/src/main/java/org/thingsboard/server/common/data/transport/resource/Resource.java
0 → 100644
1 | +/** | |
2 | + * Copyright © 2016-2021 The Thingsboard Authors | |
3 | + * | |
4 | + * Licensed under the Apache License, Version 2.0 (the "License"); | |
5 | + * you may not use this file except in compliance with the License. | |
6 | + * You may obtain a copy of the License at | |
7 | + * | |
8 | + * http://www.apache.org/licenses/LICENSE-2.0 | |
9 | + * | |
10 | + * Unless required by applicable law or agreed to in writing, software | |
11 | + * distributed under the License is distributed on an "AS IS" BASIS, | |
12 | + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |
13 | + * See the License for the specific language governing permissions and | |
14 | + * limitations under the License. | |
15 | + */ | |
16 | +package org.thingsboard.server.common.data.transport.resource; | |
17 | + | |
18 | +import lombok.Data; | |
19 | +import org.thingsboard.server.common.data.HasTenantId; | |
20 | +import org.thingsboard.server.common.data.id.TenantId; | |
21 | + | |
22 | +@Data | |
23 | +public class Resource implements HasTenantId { | |
24 | + private TenantId tenantId; | |
25 | + private ResourceType resourceType; | |
26 | + private String resourceId; | |
27 | + private String value; | |
28 | + | |
29 | + @Override | |
30 | + public String toString() { | |
31 | + return "Resource{" + | |
32 | + "tenantId=" + tenantId + | |
33 | + ", resourceType=" + resourceType + | |
34 | + ", resourceId='" + resourceId + '\'' + | |
35 | + '}'; | |
36 | + } | |
37 | +} | ... | ... |
common/data/src/main/java/org/thingsboard/server/common/data/transport/resource/ResourceType.java
0 → 100644
1 | +/** | |
2 | + * Copyright © 2016-2021 The Thingsboard Authors | |
3 | + * | |
4 | + * Licensed under the Apache License, Version 2.0 (the "License"); | |
5 | + * you may not use this file except in compliance with the License. | |
6 | + * You may obtain a copy of the License at | |
7 | + * | |
8 | + * http://www.apache.org/licenses/LICENSE-2.0 | |
9 | + * | |
10 | + * Unless required by applicable law or agreed to in writing, software | |
11 | + * distributed under the License is distributed on an "AS IS" BASIS, | |
12 | + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |
13 | + * See the License for the specific language governing permissions and | |
14 | + * limitations under the License. | |
15 | + */ | |
16 | +package org.thingsboard.server.common.data.transport.resource; | |
17 | + | |
18 | +public enum ResourceType { | |
19 | + LWM2M_MODEL, JKS, PKCS_12 | |
20 | +} | ... | ... |
... | ... | @@ -17,7 +17,6 @@ package org.thingsboard.server.transport.lwm2m.bootstrap; |
17 | 17 | |
18 | 18 | import lombok.extern.slf4j.Slf4j; |
19 | 19 | import org.eclipse.californium.scandium.config.DtlsConnectorConfig; |
20 | -import org.eclipse.leshan.core.model.StaticModel; | |
21 | 20 | import org.eclipse.leshan.core.util.Hex; |
22 | 21 | import org.eclipse.leshan.server.bootstrap.BootstrapSessionManager; |
23 | 22 | import org.eclipse.leshan.server.californium.bootstrap.LeshanBootstrapServer; |
... | ... | @@ -94,7 +93,7 @@ public class LwM2MTransportBootstrapServerConfiguration { |
94 | 93 | builder.setCoapConfig(getCoapConfig(bootstrapPortNoSec, bootstrapSecurePort)); |
95 | 94 | |
96 | 95 | /** Define model provider (Create Models )*/ |
97 | - builder.setModel(new StaticModel(contextS.getLwM2MTransportConfigServer().getModelsValue())); | |
96 | +// builder.setModel(new StaticModel(contextS.getLwM2MTransportConfigServer().getModelsValueCommon())); | |
98 | 97 | |
99 | 98 | /** Create credentials */ |
100 | 99 | this.setServerWithCredentials(builder); | ... | ... |
... | ... | @@ -16,13 +16,13 @@ |
16 | 16 | package org.thingsboard.server.transport.lwm2m.server; |
17 | 17 | /** |
18 | 18 | * Copyright © 2016-2020 The Thingsboard Authors |
19 | - * | |
19 | + * <p> | |
20 | 20 | * Licensed under the Apache License, Version 2.0 (the "License"); |
21 | 21 | * you may not use this file except in compliance with the License. |
22 | 22 | * You may obtain a copy of the License at |
23 | - * | |
23 | + * <p> | |
24 | 24 | * http://www.apache.org/licenses/LICENSE-2.0 |
25 | - * | |
25 | + * <p> | |
26 | 26 | * Unless required by applicable law or agreed to in writing, software |
27 | 27 | * distributed under the License is distributed on an "AS IS" BASIS, |
28 | 28 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
... | ... | @@ -34,16 +34,27 @@ import com.google.gson.JsonElement; |
34 | 34 | import com.google.gson.JsonObject; |
35 | 35 | import lombok.Getter; |
36 | 36 | import lombok.extern.slf4j.Slf4j; |
37 | +import org.eclipse.leshan.core.model.DDFFileParser; | |
38 | +import org.eclipse.leshan.core.model.DefaultDDFFileValidator; | |
39 | +import org.eclipse.leshan.core.model.InvalidDDFFileException; | |
40 | +import org.eclipse.leshan.core.model.ObjectModel; | |
37 | 41 | import org.springframework.stereotype.Component; |
38 | 42 | import org.thingsboard.server.common.transport.TransportContext; |
43 | +import org.thingsboard.server.common.transport.TransportResourceCache; | |
39 | 44 | import org.thingsboard.server.common.transport.TransportService; |
40 | 45 | import org.thingsboard.server.common.transport.TransportServiceCallback; |
41 | 46 | import org.thingsboard.server.common.transport.adaptor.AdaptorException; |
42 | 47 | import org.thingsboard.server.common.transport.lwm2m.LwM2MTransportConfigServer; |
43 | -import org.thingsboard.server.gen.transport.TransportProtos; | |
48 | +import org.thingsboard.server.gen.transport.TransportProtos.PostAttributeMsg; | |
49 | +import org.thingsboard.server.gen.transport.TransportProtos.PostTelemetryMsg; | |
50 | +import org.thingsboard.server.gen.transport.TransportProtos.SessionInfoProto; | |
51 | +import org.thingsboard.server.gen.transport.TransportProtos.ValidateDeviceCredentialsResponseMsg; | |
44 | 52 | import org.thingsboard.server.queue.util.TbLwM2mTransportComponent; |
45 | 53 | import org.thingsboard.server.transport.lwm2m.server.adaptors.LwM2MJsonAdaptor; |
46 | 54 | |
55 | +import java.io.ByteArrayInputStream; | |
56 | +import java.io.IOException; | |
57 | + | |
47 | 58 | import static org.thingsboard.server.transport.lwm2m.server.LwM2mTransportHandler.LOG_LW2M_TELEMETRY; |
48 | 59 | |
49 | 60 | @Slf4j |
... | ... | @@ -56,12 +67,16 @@ public class LwM2mTransportContextServer extends TransportContext { |
56 | 67 | |
57 | 68 | private final TransportService transportService; |
58 | 69 | |
70 | + private final TransportResourceCache transportResourceCache; | |
71 | + | |
72 | + | |
59 | 73 | @Getter |
60 | 74 | private final LwM2MJsonAdaptor adaptor; |
61 | 75 | |
62 | - public LwM2mTransportContextServer(LwM2MTransportConfigServer lwM2MTransportConfigServer, TransportService transportService, LwM2MJsonAdaptor adaptor) { | |
76 | + public LwM2mTransportContextServer(LwM2MTransportConfigServer lwM2MTransportConfigServer, TransportService transportService, TransportResourceCache transportResourceCache, LwM2MJsonAdaptor adaptor) { | |
63 | 77 | this.lwM2MTransportConfigServer = lwM2MTransportConfigServer; |
64 | 78 | this.transportService = transportService; |
79 | + this.transportResourceCache = transportResourceCache; | |
65 | 80 | this.adaptor = adaptor; |
66 | 81 | } |
67 | 82 | |
... | ... | @@ -69,6 +84,10 @@ public class LwM2mTransportContextServer extends TransportContext { |
69 | 84 | return this.lwM2MTransportConfigServer; |
70 | 85 | } |
71 | 86 | |
87 | + public TransportResourceCache getTransportResourceCache() { | |
88 | + return this.transportResourceCache; | |
89 | + } | |
90 | + | |
72 | 91 | /** |
73 | 92 | * Sent to Thingsboard Attribute || Telemetry |
74 | 93 | * |
... | ... | @@ -89,14 +108,14 @@ public class LwM2mTransportContextServer extends TransportContext { |
89 | 108 | }; |
90 | 109 | } |
91 | 110 | |
92 | - public void sentParametersOnThingsboard(JsonElement msg, String topicName, TransportProtos.SessionInfoProto sessionInfo) { | |
111 | + public void sentParametersOnThingsboard(JsonElement msg, String topicName, SessionInfoProto sessionInfo) { | |
93 | 112 | try { |
94 | 113 | if (topicName.equals(LwM2mTransportHandler.DEVICE_ATTRIBUTES_TOPIC)) { |
95 | - TransportProtos.PostAttributeMsg postAttributeMsg = adaptor.convertToPostAttributes(msg); | |
114 | + PostAttributeMsg postAttributeMsg = adaptor.convertToPostAttributes(msg); | |
96 | 115 | TransportServiceCallback call = this.getPubAckCallbackSentAttrTelemetry(postAttributeMsg); |
97 | 116 | transportService.process(sessionInfo, postAttributeMsg, this.getPubAckCallbackSentAttrTelemetry(call)); |
98 | 117 | } else if (topicName.equals(LwM2mTransportHandler.DEVICE_TELEMETRY_TOPIC)) { |
99 | - TransportProtos.PostTelemetryMsg postTelemetryMsg = adaptor.convertToPostTelemetry(msg); | |
118 | + PostTelemetryMsg postTelemetryMsg = adaptor.convertToPostTelemetry(msg); | |
100 | 119 | TransportServiceCallback call = this.getPubAckCallbackSentAttrTelemetry(postTelemetryMsg); |
101 | 120 | transportService.process(sessionInfo, postTelemetryMsg, this.getPubAckCallbackSentAttrTelemetry(call)); |
102 | 121 | } |
... | ... | @@ -115,8 +134,8 @@ public class LwM2mTransportContextServer extends TransportContext { |
115 | 134 | /** |
116 | 135 | * @return - sessionInfo after access connect client |
117 | 136 | */ |
118 | - public TransportProtos.SessionInfoProto getValidateSessionInfo(TransportProtos.ValidateDeviceCredentialsResponseMsg msg, long mostSignificantBits, long leastSignificantBits) { | |
119 | - return TransportProtos.SessionInfoProto.newBuilder() | |
137 | + public SessionInfoProto getValidateSessionInfo(ValidateDeviceCredentialsResponseMsg msg, long mostSignificantBits, long leastSignificantBits) { | |
138 | + return SessionInfoProto.newBuilder() | |
120 | 139 | .setNodeId(this.getNodeId()) |
121 | 140 | .setSessionIdMSB(mostSignificantBits) |
122 | 141 | .setSessionIdLSB(leastSignificantBits) |
... | ... | @@ -131,4 +150,13 @@ public class LwM2mTransportContextServer extends TransportContext { |
131 | 150 | .build(); |
132 | 151 | } |
133 | 152 | |
153 | + public ObjectModel parseFromXmlToObjectModel(byte[] xmlByte, String streamName, DefaultDDFFileValidator ddfValidator) { | |
154 | + try { | |
155 | + DDFFileParser ddfFileParser = new DDFFileParser(ddfValidator); | |
156 | + return ddfFileParser.parseEx(new ByteArrayInputStream(xmlByte), streamName).get(0); | |
157 | + } catch (IOException | InvalidDDFFileException e) { | |
158 | + log.error("Could not parse the XML file [{}]", streamName, e); | |
159 | + return null; | |
160 | + } | |
161 | + } | |
134 | 162 | } | ... | ... |
... | ... | @@ -35,6 +35,7 @@ import org.eclipse.leshan.server.californium.LeshanServerBuilder; |
35 | 35 | import org.nustaq.serialization.FSTConfiguration; |
36 | 36 | import org.thingsboard.server.common.data.DeviceProfile; |
37 | 37 | import org.thingsboard.server.common.data.device.profile.Lwm2mDeviceProfileTransportConfiguration; |
38 | +import org.thingsboard.server.common.data.id.TenantId; | |
38 | 39 | import org.thingsboard.server.common.transport.TransportServiceCallback; |
39 | 40 | import org.thingsboard.server.transport.lwm2m.server.client.LwM2mClient; |
40 | 41 | import org.thingsboard.server.transport.lwm2m.server.client.LwM2mClientProfile; |
... | ... | @@ -188,8 +189,9 @@ public class LwM2mTransportHandler { |
188 | 189 | return null; |
189 | 190 | } |
190 | 191 | |
191 | - public static LwM2mClientProfile getNewProfileParameters(JsonObject profilesConfigData) { | |
192 | + public static LwM2mClientProfile getNewProfileParameters(JsonObject profilesConfigData, TenantId tenantId) { | |
192 | 193 | LwM2mClientProfile lwM2MClientProfile = new LwM2mClientProfile(); |
194 | + lwM2MClientProfile.setTenantId(tenantId); | |
193 | 195 | lwM2MClientProfile.setPostClientLwM2mSettings(profilesConfigData.get(CLIENT_LWM2M_SETTINGS).getAsJsonObject()); |
194 | 196 | lwM2MClientProfile.setPostKeyNameProfile(profilesConfigData.get(OBSERVE_ATTRIBUTE_TELEMETRY).getAsJsonObject().get(KEY_NAME).getAsJsonObject()); |
195 | 197 | lwM2MClientProfile.setPostAttributeProfile(profilesConfigData.get(OBSERVE_ATTRIBUTE_TELEMETRY).getAsJsonObject().get(ATTRIBUTE).getAsJsonArray()); |
... | ... | @@ -221,7 +223,7 @@ public class LwM2mTransportHandler { |
221 | 223 | ObjectMapper mapper = new ObjectMapper(); |
222 | 224 | String profileStr = mapper.writeValueAsString(profile); |
223 | 225 | JsonObject profileJson = (profileStr != null) ? validateJson(profileStr) : null; |
224 | - return (getValidateCredentialsBodyFromThingsboard(profileJson)) ? LwM2mTransportHandler.getNewProfileParameters(profileJson) : null; | |
226 | + return (getValidateCredentialsBodyFromThingsboard(profileJson)) ? LwM2mTransportHandler.getNewProfileParameters(profileJson, deviceProfile.getTenantId()) : null; | |
225 | 227 | } catch (IOException e) { |
226 | 228 | log.error("", e); |
227 | 229 | } | ... | ... |
... | ... | @@ -47,7 +47,6 @@ import org.eclipse.leshan.core.util.Hex; |
47 | 47 | import org.eclipse.leshan.core.util.NamedThreadFactory; |
48 | 48 | import org.eclipse.leshan.server.californium.LeshanServer; |
49 | 49 | import org.eclipse.leshan.server.registration.Registration; |
50 | -import org.springframework.beans.factory.annotation.Autowired; | |
51 | 50 | import org.springframework.stereotype.Service; |
52 | 51 | import org.thingsboard.server.queue.util.TbLwM2mTransportComponent; |
53 | 52 | import org.thingsboard.server.transport.lwm2m.server.client.LwM2mClient; |
... | ... | @@ -88,13 +87,13 @@ public class LwM2mTransportRequest { |
88 | 87 | |
89 | 88 | private final LeshanServer leshanServer; |
90 | 89 | |
91 | - @Autowired | |
92 | - private LwM2mTransportServiceImpl serviceImpl; | |
90 | + private final LwM2mTransportServiceImpl serviceImpl; | |
93 | 91 | |
94 | - public LwM2mTransportRequest(LwM2mTransportContextServer context, LwM2mClientContext lwM2mClientContext, LeshanServer leshanServer) { | |
92 | + public LwM2mTransportRequest(LwM2mTransportContextServer context, LwM2mClientContext lwM2mClientContext, LeshanServer leshanServer, LwM2mTransportServiceImpl serviceImpl) { | |
95 | 93 | this.context = context; |
96 | 94 | this.lwM2mClientContext = lwM2mClientContext; |
97 | 95 | this.leshanServer = leshanServer; |
96 | + this.serviceImpl = serviceImpl; | |
98 | 97 | } |
99 | 98 | |
100 | 99 | @PostConstruct |
... | ... | @@ -230,6 +229,7 @@ public class LwM2mTransportRequest { |
230 | 229 | private void sendRequest(Registration registration, DownlinkRequest request, long timeoutInMs) { |
231 | 230 | LwM2mClient lwM2MClient = lwM2mClientContext.getLwM2mClientWithReg(registration, null); |
232 | 231 | leshanServer.send(registration, request, timeoutInMs, (ResponseCallback<?>) response -> { |
232 | + | |
233 | 233 | if (!lwM2MClient.isInit()) { |
234 | 234 | lwM2MClient.initValue(this.serviceImpl, request.getPath().toString()); |
235 | 235 | } | ... | ... |
... | ... | @@ -24,14 +24,13 @@ import org.eclipse.leshan.server.californium.LeshanServer; |
24 | 24 | import org.eclipse.leshan.server.californium.LeshanServerBuilder; |
25 | 25 | import org.eclipse.leshan.server.californium.registration.CaliforniumRegistrationStore; |
26 | 26 | import org.eclipse.leshan.server.model.LwM2mModelProvider; |
27 | -import org.eclipse.leshan.server.model.VersionedModelProvider; | |
28 | 27 | import org.eclipse.leshan.server.security.DefaultAuthorizer; |
29 | 28 | import org.eclipse.leshan.server.security.EditableSecurityStore; |
30 | 29 | import org.eclipse.leshan.server.security.SecurityChecker; |
31 | -import org.springframework.beans.factory.annotation.Autowired; | |
32 | 30 | import org.springframework.context.annotation.Bean; |
33 | 31 | import org.springframework.stereotype.Component; |
34 | 32 | import org.thingsboard.server.queue.util.TbLwM2mTransportComponent; |
33 | +import org.thingsboard.server.transport.lwm2m.server.client.LwM2mClientContext; | |
35 | 34 | import org.thingsboard.server.transport.lwm2m.utils.LwM2mValueConverterImpl; |
36 | 35 | |
37 | 36 | import java.math.BigInteger; |
... | ... | @@ -61,21 +60,23 @@ import static org.eclipse.californium.scandium.dtls.cipher.CipherSuite.TLS_PSK_W |
61 | 60 | import static org.thingsboard.server.transport.lwm2m.server.LwM2mTransportHandler.getCoapConfig; |
62 | 61 | |
63 | 62 | @Slf4j |
64 | -@Component("LwM2MTransportServerConfiguration") | |
63 | +@Component | |
65 | 64 | @TbLwM2mTransportComponent |
66 | 65 | public class LwM2mTransportServerConfiguration { |
67 | 66 | private PublicKey publicKey; |
68 | 67 | private PrivateKey privateKey; |
69 | 68 | private boolean pskMode = false; |
69 | + private final LwM2mTransportContextServer context; | |
70 | + private final CaliforniumRegistrationStore registrationStore; | |
71 | + private final EditableSecurityStore securityStore; | |
72 | + private final LwM2mClientContext lwM2mClientContext; | |
70 | 73 | |
71 | - @Autowired | |
72 | - private LwM2mTransportContextServer context; | |
73 | - | |
74 | - @Autowired | |
75 | - private CaliforniumRegistrationStore registrationStore; | |
76 | - | |
77 | - @Autowired | |
78 | - private EditableSecurityStore securityStore; | |
74 | + public LwM2mTransportServerConfiguration(LwM2mTransportContextServer context, CaliforniumRegistrationStore registrationStore, EditableSecurityStore securityStore, LwM2mClientContext lwM2mClientContext) { | |
75 | + this.context = context; | |
76 | + this.registrationStore = registrationStore; | |
77 | + this.securityStore = securityStore; | |
78 | + this.lwM2mClientContext = lwM2mClientContext; | |
79 | + } | |
79 | 80 | |
80 | 81 | @Bean |
81 | 82 | public LeshanServer getLeshanServer() { |
... | ... | @@ -95,7 +96,8 @@ public class LwM2mTransportServerConfiguration { |
95 | 96 | builder.setCoapConfig(getCoapConfig(serverPortNoSec, serverSecurePort)); |
96 | 97 | |
97 | 98 | /** Define model provider (Create Models )*/ |
98 | - LwM2mModelProvider modelProvider = new VersionedModelProvider(this.context.getLwM2MTransportConfigServer().getModelsValue()); | |
99 | + LwM2mModelProvider modelProvider = new LwM2mVersionedModelProvider(this.lwM2mClientContext, this.context); | |
100 | + this.context.getLwM2MTransportConfigServer().setModelProvider(modelProvider); | |
99 | 101 | builder.setObjectModelProvider(modelProvider); |
100 | 102 | |
101 | 103 | /** Create credentials */ | ... | ... |
... | ... | @@ -652,21 +652,6 @@ public class LwM2mTransportServiceImpl implements LwM2mTransportService { |
652 | 652 | return (clientInstances.size() > 0) ? clientInstances : null; |
653 | 653 | } |
654 | 654 | |
655 | -// /** | |
656 | -// * get AttrName/TelemetryName with value from Client | |
657 | -// * | |
658 | -// * @param registration - | |
659 | -// * @return - JsonObject, format: {name: value}} | |
660 | -// */ | |
661 | -// private JsonObject getAttributeClient(Registration registration) { | |
662 | -// if (registration.getAdditionalRegistrationAttributes().size() > 0) { | |
663 | -// JsonObject resNameValues = new JsonObject(); | |
664 | -// registration.getAdditionalRegistrationAttributes().forEach(resNameValues::addProperty); | |
665 | -// return resNameValues; | |
666 | -// } | |
667 | -// return null; | |
668 | -// } | |
669 | - | |
670 | 655 | /** |
671 | 656 | * @param attributes - new JsonObject |
672 | 657 | * @param telemetry - new JsonObject | ... | ... |
1 | +/** | |
2 | + * Copyright © 2016-2021 The Thingsboard Authors | |
3 | + * | |
4 | + * Licensed under the Apache License, Version 2.0 (the "License"); | |
5 | + * you may not use this file except in compliance with the License. | |
6 | + * You may obtain a copy of the License at | |
7 | + * | |
8 | + * http://www.apache.org/licenses/LICENSE-2.0 | |
9 | + * | |
10 | + * Unless required by applicable law or agreed to in writing, software | |
11 | + * distributed under the License is distributed on an "AS IS" BASIS, | |
12 | + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |
13 | + * See the License for the specific language governing permissions and | |
14 | + * limitations under the License. | |
15 | + */ | |
16 | +package org.thingsboard.server.transport.lwm2m.server; | |
17 | + | |
18 | +import lombok.extern.slf4j.Slf4j; | |
19 | +import org.eclipse.leshan.core.model.DefaultDDFFileValidator; | |
20 | +import org.eclipse.leshan.core.model.LwM2mModel; | |
21 | +import org.eclipse.leshan.core.model.ObjectModel; | |
22 | +import org.eclipse.leshan.core.model.ResourceModel; | |
23 | +import org.eclipse.leshan.server.model.LwM2mModelProvider; | |
24 | +import org.eclipse.leshan.server.registration.Registration; | |
25 | +import org.thingsboard.server.common.data.id.TenantId; | |
26 | +import org.thingsboard.server.transport.lwm2m.server.client.LwM2mClientContext; | |
27 | + | |
28 | +import java.util.ArrayList; | |
29 | +import java.util.Base64; | |
30 | +import java.util.Collection; | |
31 | +import java.util.Iterator; | |
32 | +import java.util.Map; | |
33 | + | |
34 | +import static org.thingsboard.server.common.data.ResourceType.LWM2M_MODEL; | |
35 | + | |
36 | +@Slf4j | |
37 | +public class LwM2mVersionedModelProvider implements LwM2mModelProvider { | |
38 | + | |
39 | + /** | |
40 | + * int objectId | |
41 | + * String version ("1.01") | |
42 | + * Key = objectId + "##" + version | |
43 | + * Value = TenantId | |
44 | + */ | |
45 | + private final LwM2mClientContext lwM2mClientContext; | |
46 | + private final LwM2mTransportContextServer lwM2mTransportContextServer; | |
47 | + | |
48 | + public LwM2mVersionedModelProvider(LwM2mClientContext lwM2mClientContext, LwM2mTransportContextServer lwM2mTransportContextServer) { | |
49 | + this.lwM2mClientContext = lwM2mClientContext; | |
50 | + this.lwM2mTransportContextServer = lwM2mTransportContextServer; | |
51 | + } | |
52 | + private String getIdVer(ObjectModel objectModel) { | |
53 | + return objectModel.id + "##" + ((objectModel.getVersion() == null || objectModel.getVersion().isEmpty()) ? ObjectModel.DEFAULT_VERSION : objectModel.getVersion()); | |
54 | + } | |
55 | + | |
56 | + private String getIdVer(Integer objectId, String version) { | |
57 | + return objectId != null ? objectId + "##" + ((version == null || version.isEmpty()) ? ObjectModel.DEFAULT_VERSION : version) : null; | |
58 | + } | |
59 | + | |
60 | + /** | |
61 | + * Update repository if need | |
62 | + * | |
63 | + * @param registration | |
64 | + * @return | |
65 | + */ | |
66 | + @Override | |
67 | + public LwM2mModel getObjectModel(Registration registration) { | |
68 | + return new DynamicModel(registration | |
69 | + ); | |
70 | + } | |
71 | + | |
72 | + private class DynamicModel implements LwM2mModel { | |
73 | + | |
74 | + private final Registration registration; | |
75 | + private final TenantId tenantId; | |
76 | + | |
77 | + public DynamicModel(Registration registration) { | |
78 | + this.registration = registration; | |
79 | + this.tenantId = lwM2mClientContext.getProfile(registration).getTenantId(); | |
80 | + } | |
81 | + | |
82 | + @Override | |
83 | + public ResourceModel getResourceModel(int objectId, int resourceId) { | |
84 | + try { | |
85 | + ObjectModel objectModel = getObjectModel(objectId); | |
86 | + if (objectModel != null) | |
87 | + return objectModel.resources.get(resourceId); | |
88 | + else | |
89 | + return null; | |
90 | + } catch (Exception e) { | |
91 | + log.error("", e); | |
92 | + return null; | |
93 | + } | |
94 | + } | |
95 | + | |
96 | + @Override | |
97 | + public ObjectModel getObjectModel(int objectId) { | |
98 | + String version = registration.getSupportedVersion(objectId); | |
99 | + if (version != null) { | |
100 | + return this.getObjectModelDynamic(objectId, version); | |
101 | + } | |
102 | + return null; | |
103 | + } | |
104 | + | |
105 | + @Override | |
106 | + public Collection<ObjectModel> getObjectModels() { | |
107 | + Map<Integer, String> supportedObjects = this.registration.getSupportedObject(); | |
108 | + Collection<ObjectModel> result = new ArrayList(supportedObjects.size()); | |
109 | + Iterator i$ = supportedObjects.entrySet().iterator(); | |
110 | + | |
111 | + while (i$.hasNext()) { | |
112 | + Map.Entry<Integer, String> supportedObject = (Map.Entry) i$.next(); | |
113 | + ObjectModel objectModel = this.getObjectModelDynamic((Integer) supportedObject.getKey(), (String) supportedObject.getValue()); | |
114 | + if (objectModel != null) { | |
115 | + result.add(objectModel); | |
116 | + } | |
117 | + } | |
118 | + return result; | |
119 | + } | |
120 | + | |
121 | + private ObjectModel getObjectModelDynamic(Integer objectId, String version) { | |
122 | + String key = getIdVer(objectId, version); | |
123 | + String xmlB64 = lwM2mTransportContextServer.getTransportResourceCache().get( | |
124 | + this.tenantId, | |
125 | + LWM2M_MODEL, | |
126 | + key). | |
127 | + getValue(); | |
128 | + return xmlB64 != null && !xmlB64.isEmpty() ? | |
129 | + lwM2mTransportContextServer.parseFromXmlToObjectModel( | |
130 | + Base64.getDecoder().decode(xmlB64), | |
131 | + key + ".xml", | |
132 | + new DefaultDDFFileValidator()) : | |
133 | + null; | |
134 | + } | |
135 | + } | |
136 | +} | ... | ... |
... | ... | @@ -15,7 +15,6 @@ |
15 | 15 | */ |
16 | 16 | package org.thingsboard.server.transport.lwm2m.server.client; |
17 | 17 | |
18 | -import lombok.extern.slf4j.Slf4j; | |
19 | 18 | import org.eclipse.leshan.server.registration.Registration; |
20 | 19 | import org.eclipse.leshan.server.security.EditableSecurityStore; |
21 | 20 | import org.springframework.stereotype.Service; |
... | ... | @@ -105,6 +104,7 @@ public class LwM2mClientContextImpl implements LwM2mClientContext { |
105 | 104 | |
106 | 105 | /** |
107 | 106 | * Add new LwM2MClient to session |
107 | + * | |
108 | 108 | * @param identity- |
109 | 109 | * @return SecurityInfo. If error - SecurityInfoError |
110 | 110 | * and log: | ... | ... |
... | ... | @@ -19,15 +19,18 @@ import com.google.gson.Gson; |
19 | 19 | import com.google.gson.JsonArray; |
20 | 20 | import com.google.gson.JsonObject; |
21 | 21 | import lombok.Data; |
22 | +import org.thingsboard.server.common.data.id.TenantId; | |
22 | 23 | |
23 | 24 | @Data |
24 | 25 | public class LwM2mClientProfile { |
26 | + | |
27 | + private TenantId tenantId; | |
25 | 28 | /** |
26 | 29 | * {"clientLwM2mSettings": { |
27 | 30 | * clientUpdateValueAfterConnect: false; |
28 | 31 | * } |
29 | 32 | **/ |
30 | - JsonObject postClientLwM2mSettings; | |
33 | + private JsonObject postClientLwM2mSettings; | |
31 | 34 | |
32 | 35 | /** |
33 | 36 | * {"keyName": { |
... | ... | @@ -36,22 +39,22 @@ public class LwM2mClientProfile { |
36 | 39 | * "/3/0/2": "serialNumber" |
37 | 40 | * } |
38 | 41 | **/ |
39 | - JsonObject postKeyNameProfile; | |
42 | + private JsonObject postKeyNameProfile; | |
40 | 43 | |
41 | 44 | /** |
42 | 45 | * [ "/2/0/0", "/2/0/1"] |
43 | 46 | */ |
44 | - JsonArray postAttributeProfile; | |
47 | + private JsonArray postAttributeProfile; | |
45 | 48 | |
46 | 49 | /** |
47 | 50 | * [ "/2/0/0", "/2/0/1"] |
48 | 51 | */ |
49 | - JsonArray postTelemetryProfile; | |
52 | + private JsonArray postTelemetryProfile; | |
50 | 53 | |
51 | 54 | /** |
52 | 55 | * [ "/2/0/0", "/2/0/1"] |
53 | 56 | */ |
54 | - JsonArray postObserveProfile; | |
57 | + private JsonArray postObserveProfile; | |
55 | 58 | |
56 | 59 | public LwM2mClientProfile clone() { |
57 | 60 | LwM2mClientProfile lwM2mClientProfile = new LwM2mClientProfile(); | ... | ... |
... | ... | @@ -26,10 +26,13 @@ import org.eclipse.leshan.core.util.StringUtils; |
26 | 26 | import javax.xml.datatype.DatatypeConfigurationException; |
27 | 27 | import javax.xml.datatype.DatatypeFactory; |
28 | 28 | import javax.xml.datatype.XMLGregorianCalendar; |
29 | +import java.math.BigInteger; | |
29 | 30 | import java.text.DateFormat; |
30 | 31 | import java.text.SimpleDateFormat; |
31 | 32 | import java.util.Date; |
32 | 33 | |
34 | +import static org.eclipse.leshan.core.model.ResourceModel.Type.OPAQUE; | |
35 | + | |
33 | 36 | @Slf4j |
34 | 37 | public class LwM2mValueConverterImpl implements LwM2mValueConverter { |
35 | 38 | |
... | ... | @@ -51,6 +54,9 @@ public class LwM2mValueConverterImpl implements LwM2mValueConverter { |
51 | 54 | /** expected type */ |
52 | 55 | return value; |
53 | 56 | } |
57 | + if (currentType == null) { | |
58 | + currentType = OPAQUE; | |
59 | + } | |
54 | 60 | |
55 | 61 | switch (expectedType) { |
56 | 62 | case INTEGER: |
... | ... | @@ -130,7 +136,13 @@ public class LwM2mValueConverterImpl implements LwM2mValueConverter { |
130 | 136 | return String.valueOf(value); |
131 | 137 | case TIME: |
132 | 138 | String DATE_FORMAT = "MMM d, yyyy HH:mm a"; |
133 | - Long timeValue = ((Date) value).getTime(); | |
139 | + Long timeValue; | |
140 | + try { | |
141 | + timeValue = ((Date) value).getTime(); | |
142 | + } | |
143 | + catch (Exception e){ | |
144 | + timeValue = new BigInteger((byte [])value).longValue(); | |
145 | + } | |
134 | 146 | DateFormat formatter = new SimpleDateFormat(DATE_FORMAT); |
135 | 147 | return formatter.format(new Date(timeValue)); |
136 | 148 | default: | ... | ... |
... | ... | @@ -15,9 +15,9 @@ |
15 | 15 | */ |
16 | 16 | package org.thingsboard.server.common.transport; |
17 | 17 | |
18 | -import org.thingsboard.server.common.data.id.TenantId; | |
19 | 18 | import org.thingsboard.server.common.data.Resource; |
20 | 19 | import org.thingsboard.server.common.data.ResourceType; |
20 | +import org.thingsboard.server.common.data.id.TenantId; | |
21 | 21 | |
22 | 22 | public interface TransportResourceCache { |
23 | 23 | ... | ... |
... | ... | @@ -18,10 +18,10 @@ package org.thingsboard.server.common.transport.lwm2m; |
18 | 18 | import lombok.Getter; |
19 | 19 | import lombok.Setter; |
20 | 20 | import lombok.extern.slf4j.Slf4j; |
21 | -import org.eclipse.leshan.core.model.ObjectLoader; | |
22 | 21 | import org.eclipse.leshan.core.model.ObjectModel; |
23 | 22 | import org.eclipse.leshan.core.model.ResourceModel; |
24 | 23 | import org.eclipse.leshan.core.node.LwM2mPath; |
24 | +import org.eclipse.leshan.server.model.LwM2mModelProvider; | |
25 | 25 | import org.eclipse.leshan.server.registration.Registration; |
26 | 26 | import org.springframework.beans.factory.annotation.Value; |
27 | 27 | import org.springframework.boot.autoconfigure.condition.ConditionalOnExpression; |
... | ... | @@ -38,16 +38,13 @@ import java.security.KeyStore; |
38 | 38 | import java.security.KeyStoreException; |
39 | 39 | import java.security.NoSuchAlgorithmException; |
40 | 40 | import java.security.cert.CertificateException; |
41 | -import java.util.Arrays; | |
42 | 41 | import java.util.List; |
43 | -import java.util.stream.Collectors; | |
44 | 42 | |
45 | 43 | @Slf4j |
46 | 44 | @Component |
47 | 45 | @ConditionalOnExpression("('${service.type:null}'=='tb-transport' && '${transport.lwm2m.enabled:false}'=='true') || '${service.type:null}'=='monolith' || '${service.type:null}'=='tb-core'") |
48 | 46 | public class LwM2MTransportConfigServer { |
49 | 47 | |
50 | - | |
51 | 48 | @Getter |
52 | 49 | private String MODEL_PATH_DEFAULT = "models"; |
53 | 50 | |
... | ... | @@ -84,7 +81,11 @@ public class LwM2MTransportConfigServer { |
84 | 81 | |
85 | 82 | @Getter |
86 | 83 | @Setter |
87 | - private List<ObjectModel> modelsValue; | |
84 | + private List<ObjectModel> modelsValueCommon; | |
85 | + | |
86 | + @Getter | |
87 | + @Setter | |
88 | + private LwM2mModelProvider modelProvider; | |
88 | 89 | |
89 | 90 | @Getter |
90 | 91 | @Value("${transport.lwm2m.timeout:}") |
... | ... | @@ -188,29 +189,9 @@ public class LwM2MTransportConfigServer { |
188 | 189 | |
189 | 190 | @PostConstruct |
190 | 191 | public void init() { |
191 | - modelsValue = ObjectLoader.loadDefault(); | |
192 | - File path = getPathModels(); | |
193 | - if (path.isDirectory()) { | |
194 | - try { | |
195 | - modelsValue.addAll(ObjectLoader.loadObjectsFromDir(path)); | |
196 | - log.info(" [{}] Models directory is a directory", path.getAbsoluteFile()); | |
197 | - } catch (Exception e) { | |
198 | - log.error(" [{}] Could not parse the resource definition file", e.toString()); | |
199 | - } | |
200 | - } else { | |
201 | - log.error(" [{}] Read Models", path.getAbsoluteFile()); | |
202 | - } | |
203 | 192 | this.getInKeyStore(); |
204 | 193 | } |
205 | 194 | |
206 | - private File getPathModels() { | |
207 | - Path pathModels = (modelPathFile != null && !modelPathFile.isEmpty()) ? Paths.get(modelPathFile) : | |
208 | - (new File(Paths.get(getBaseDirPath(), PATH_DATA, MODEL_PATH_DEFAULT).toUri()).isDirectory()) ? | |
209 | - Paths.get(getBaseDirPath(), PATH_DATA, MODEL_PATH_DEFAULT) : | |
210 | - Paths.get(getBaseDirPath(), APP_DIR, TRANSPORT_DIR, LWM2M_DIR, SRC_DIR, MAIN_DIR, RESOURCES_DIR, MODEL_PATH_DEFAULT); | |
211 | - return (pathModels != null) ? new File(pathModels.toUri()) : null; | |
212 | - } | |
213 | - | |
214 | 195 | private KeyStore getInKeyStore() { |
215 | 196 | try { |
216 | 197 | if (keyStoreValue != null && keyStoreValue.size() > 0) |
... | ... | @@ -253,12 +234,7 @@ public class LwM2MTransportConfigServer { |
253 | 234 | } |
254 | 235 | |
255 | 236 | public ResourceModel getResourceModel(Registration registration, LwM2mPath pathIds) { |
256 | - String pathLink = "/" + pathIds.getObjectId() + "/" + pathIds.getObjectInstanceId(); | |
257 | - return (Arrays.stream(registration.getObjectLinks()).filter(p-> p.getUrl().equals(pathLink)).findFirst().isPresent() && | |
258 | - this.modelsValue.stream().filter(v -> v.id == pathIds.getObjectId()).collect(Collectors.toList()).size() > 0) && | |
259 | - this.modelsValue.stream().filter(v -> v.id == pathIds.getObjectId()).collect(Collectors.toList()).get(0).resources.containsKey(pathIds.getResourceId()) ? | |
260 | - this.modelsValue.stream().filter(v -> v.id == pathIds.getObjectId()).collect(Collectors.toList()).get(0).resources.get(pathIds.getResourceId()) : | |
261 | - null; | |
237 | + return this.modelProvider.getObjectModel(registration).getResourceModel(pathIds.getObjectId(), pathIds.getResourceId()); | |
262 | 238 | } |
263 | 239 | |
264 | 240 | public ResourceModel.Type getResourceModelType(Registration registration, LwM2mPath pathIds) { |
... | ... | @@ -270,4 +246,5 @@ public class LwM2MTransportConfigServer { |
270 | 246 | ResourceModel resource = this.getResourceModel(registration, pathIds); |
271 | 247 | return (resource == null) ? ResourceModel.Operations.NONE : resource.operations; |
272 | 248 | } |
249 | + | |
273 | 250 | } | ... | ... |
... | ... | @@ -19,9 +19,9 @@ import lombok.Data; |
19 | 19 | import lombok.extern.slf4j.Slf4j; |
20 | 20 | import org.springframework.context.annotation.Lazy; |
21 | 21 | import org.springframework.stereotype.Component; |
22 | -import org.thingsboard.server.common.data.id.TenantId; | |
23 | 22 | import org.thingsboard.server.common.data.Resource; |
24 | 23 | import org.thingsboard.server.common.data.ResourceType; |
24 | +import org.thingsboard.server.common.data.id.TenantId; | |
25 | 25 | import org.thingsboard.server.common.transport.TransportResourceCache; |
26 | 26 | import org.thingsboard.server.common.transport.TransportService; |
27 | 27 | import org.thingsboard.server.common.transport.util.DataDecodingEncodingService; | ... | ... |
... | ... | @@ -31,13 +31,13 @@ import org.thingsboard.server.common.data.Device; |
31 | 31 | import org.thingsboard.server.common.data.DeviceProfile; |
32 | 32 | import org.thingsboard.server.common.data.DeviceTransportType; |
33 | 33 | import org.thingsboard.server.common.data.EntityType; |
34 | +import org.thingsboard.server.common.data.ResourceType; | |
34 | 35 | import org.thingsboard.server.common.data.Tenant; |
35 | 36 | import org.thingsboard.server.common.data.id.DeviceId; |
36 | 37 | import org.thingsboard.server.common.data.id.DeviceProfileId; |
37 | 38 | import org.thingsboard.server.common.data.id.RuleChainId; |
38 | 39 | import org.thingsboard.server.common.data.id.TenantId; |
39 | 40 | import org.thingsboard.server.common.data.id.TenantProfileId; |
40 | -import org.thingsboard.server.common.data.ResourceType; | |
41 | 41 | import org.thingsboard.server.common.msg.TbMsg; |
42 | 42 | import org.thingsboard.server.common.msg.TbMsgMetaData; |
43 | 43 | import org.thingsboard.server.common.msg.queue.ServiceQueue; |
... | ... | @@ -295,6 +295,7 @@ public class DefaultTransportService implements TransportService { |
295 | 295 | response -> callback.onSuccess(response.getValue().getValidateCredResponseMsg()), callback::onError, transportCallbackExecutor); |
296 | 296 | } |
297 | 297 | |
298 | + @Override | |
298 | 299 | public void process(DeviceTransportType transportType, TransportProtos.ValidateDeviceX509CertRequestMsg msg, TransportServiceCallback<ValidateDeviceCredentialsResponse> callback) { |
299 | 300 | log.trace("Processing msg: {}", msg); |
300 | 301 | TbProtoQueueMsg<TransportApiRequestMsg> protoMsg = new TbProtoQueueMsg<>(UUID.randomUUID(), TransportApiRequestMsg.newBuilder().setValidateX509CertRequestMsg(msg).build()); | ... | ... |
... | ... | @@ -16,9 +16,9 @@ |
16 | 16 | package org.thingsboard.server.dao.model.sql; |
17 | 17 | |
18 | 18 | import lombok.Data; |
19 | -import org.thingsboard.server.common.data.id.TenantId; | |
20 | 19 | import org.thingsboard.server.common.data.Resource; |
21 | 20 | import org.thingsboard.server.common.data.ResourceType; |
21 | +import org.thingsboard.server.common.data.id.TenantId; | |
22 | 22 | import org.thingsboard.server.dao.model.ToData; |
23 | 23 | |
24 | 24 | import javax.persistence.Column; | ... | ... |
... | ... | @@ -17,13 +17,15 @@ package org.thingsboard.server.dao.resource; |
17 | 17 | |
18 | 18 | import lombok.extern.slf4j.Slf4j; |
19 | 19 | import org.springframework.stereotype.Service; |
20 | +import org.thingsboard.server.common.data.Resource; | |
21 | +import org.thingsboard.server.common.data.ResourceType; | |
20 | 22 | import org.thingsboard.server.common.data.id.TenantId; |
21 | 23 | import org.thingsboard.server.common.data.page.PageData; |
22 | 24 | import org.thingsboard.server.common.data.page.PageLink; |
23 | -import org.thingsboard.server.common.data.Resource; | |
24 | -import org.thingsboard.server.common.data.ResourceType; | |
25 | 25 | import org.thingsboard.server.dao.exception.DataValidationException; |
26 | 26 | |
27 | +import java.util.List; | |
28 | + | |
27 | 29 | import static org.thingsboard.server.dao.device.DeviceServiceImpl.INCORRECT_TENANT_ID; |
28 | 30 | import static org.thingsboard.server.dao.service.Validator.validateId; |
29 | 31 | |
... | ... | @@ -65,6 +67,14 @@ public class BaseResourceService implements ResourceService { |
65 | 67 | return resourceDao.findAllByTenantId(tenantId, pageLink); |
66 | 68 | } |
67 | 69 | |
70 | + | |
71 | + @Override | |
72 | + public List<Resource> findResourcesByTenantIdResourceType(TenantId tenantId, ResourceType resourceType) { | |
73 | + log.trace("Executing findByTenantId [{}]", tenantId); | |
74 | + validateId(tenantId, INCORRECT_TENANT_ID + tenantId); | |
75 | + return resourceDao.findAllByTenantIdResourceType(tenantId, resourceType); | |
76 | + } | |
77 | + | |
68 | 78 | @Override |
69 | 79 | public void deleteResourcesByTenantId(TenantId tenantId) { |
70 | 80 | log.trace("Executing deleteDevicesByTenantId, tenantId [{}]", tenantId); | ... | ... |
... | ... | @@ -15,11 +15,13 @@ |
15 | 15 | */ |
16 | 16 | package org.thingsboard.server.dao.resource; |
17 | 17 | |
18 | +import org.thingsboard.server.common.data.Resource; | |
19 | +import org.thingsboard.server.common.data.ResourceType; | |
18 | 20 | import org.thingsboard.server.common.data.id.TenantId; |
19 | 21 | import org.thingsboard.server.common.data.page.PageData; |
20 | 22 | import org.thingsboard.server.common.data.page.PageLink; |
21 | -import org.thingsboard.server.common.data.Resource; | |
22 | -import org.thingsboard.server.common.data.ResourceType; | |
23 | + | |
24 | +import java.util.List; | |
23 | 25 | |
24 | 26 | public interface ResourceDao { |
25 | 27 | |
... | ... | @@ -31,5 +33,8 @@ public interface ResourceDao { |
31 | 33 | |
32 | 34 | PageData<Resource> findAllByTenantId(TenantId tenantId, PageLink pageLink); |
33 | 35 | |
36 | + | |
37 | + List<Resource> findAllByTenantIdResourceType(TenantId tenantId, ResourceType resourceType); | |
38 | + | |
34 | 39 | void removeAllByTenantId(TenantId tenantId); |
35 | 40 | } | ... | ... |
... | ... | @@ -18,16 +18,18 @@ package org.thingsboard.server.dao.sql.resource; |
18 | 18 | import lombok.extern.slf4j.Slf4j; |
19 | 19 | import org.springframework.stereotype.Component; |
20 | 20 | import org.springframework.transaction.annotation.Transactional; |
21 | +import org.thingsboard.server.common.data.Resource; | |
22 | +import org.thingsboard.server.common.data.ResourceType; | |
21 | 23 | import org.thingsboard.server.common.data.id.TenantId; |
22 | 24 | import org.thingsboard.server.common.data.page.PageData; |
23 | 25 | import org.thingsboard.server.common.data.page.PageLink; |
24 | -import org.thingsboard.server.common.data.Resource; | |
25 | -import org.thingsboard.server.common.data.ResourceType; | |
26 | 26 | import org.thingsboard.server.dao.DaoUtil; |
27 | 27 | import org.thingsboard.server.dao.model.sql.ResourceCompositeKey; |
28 | 28 | import org.thingsboard.server.dao.model.sql.ResourceEntity; |
29 | 29 | import org.thingsboard.server.dao.resource.ResourceDao; |
30 | 30 | |
31 | +import java.util.List; | |
32 | + | |
31 | 33 | @Slf4j |
32 | 34 | @Component |
33 | 35 | public class ResourceDaoImpl implements ResourceDao { |
... | ... | @@ -71,6 +73,11 @@ public class ResourceDaoImpl implements ResourceDao { |
71 | 73 | } |
72 | 74 | |
73 | 75 | @Override |
76 | + public List<Resource> findAllByTenantIdResourceType(TenantId tenantId, ResourceType resourceType) { | |
77 | + return DaoUtil.convertDataList(resourceRepository.findAllByTenantIdAndResourceType(tenantId.getId(), resourceType.name())); | |
78 | + } | |
79 | + | |
80 | + @Override | |
74 | 81 | public void removeAllByTenantId(TenantId tenantId) { |
75 | 82 | resourceRepository.removeAllByTenantId(tenantId.getId()); |
76 | 83 | } | ... | ... |
... | ... | @@ -21,11 +21,15 @@ import org.springframework.data.repository.CrudRepository; |
21 | 21 | import org.thingsboard.server.dao.model.sql.ResourceCompositeKey; |
22 | 22 | import org.thingsboard.server.dao.model.sql.ResourceEntity; |
23 | 23 | |
24 | +import java.util.List; | |
24 | 25 | import java.util.UUID; |
25 | 26 | |
26 | 27 | public interface ResourceRepository extends CrudRepository<ResourceEntity, ResourceCompositeKey> { |
27 | 28 | |
28 | 29 | Page<ResourceEntity> findAllByTenantId(UUID tenantId, Pageable pageable); |
29 | 30 | |
31 | + | |
32 | + List<ResourceEntity> findAllByTenantIdAndResourceType(UUID tenantId, String resourceType); | |
33 | + | |
30 | 34 | void removeAllByTenantId(UUID tenantId); |
31 | 35 | } | ... | ... |
... | ... | @@ -66,9 +66,9 @@ |
66 | 66 | <jackson-core.version>2.12.1</jackson-core.version> |
67 | 67 | <json-schema-validator.version>2.2.6</json-schema-validator.version> |
68 | 68 | <californium.version>2.6.1</californium.version> |
69 | - <leshan-server.version>1.3.0</leshan-server.version> | |
70 | - <leshan-core.version>1.3.0</leshan-core.version> | |
71 | - <leshan-client.version>1.3.0</leshan-client.version> | |
69 | + <leshan-server.version>1.3.1</leshan-server.version> | |
70 | + <leshan-core.version>1.3.1</leshan-core.version> | |
71 | + <leshan-client.version>1.3.1</leshan-client.version> | |
72 | 72 | <gson.version>2.6.2</gson.version> |
73 | 73 | <freemarker.version>2.3.30</freemarker.version> |
74 | 74 | <mail.version>1.6.2</mail.version> | ... | ... |