iotagent-node-lib 2.18.0 → 2.21.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (141) hide show
  1. package/.github/workflows/ci.yml +1 -2
  2. package/.nyc_output/76bc24ff-5fac-4b5a-997d-de2799342eb0.json +1 -0
  3. package/.nyc_output/processinfo/76bc24ff-5fac-4b5a-997d-de2799342eb0.json +1 -0
  4. package/.nyc_output/processinfo/index.json +1 -0
  5. package/.readthedocs.yml +3 -1
  6. package/CHANGES_NEXT_RELEASE +1 -0
  7. package/README.md +5 -56
  8. package/doc/advanced-topics.md +121 -85
  9. package/doc/api.md +63 -54
  10. package/doc/development.md +8 -9
  11. package/doc/expressionLanguage.md +517 -316
  12. package/doc/installationguide.md +66 -64
  13. package/doc/northboundinteractions.md +40 -33
  14. package/doc/requirements.txt +4 -0
  15. package/{docs → doc}/roadmap.md +21 -6
  16. package/doc/usermanual.md +50 -18
  17. package/docker/Mosquitto/Dockerfile +28 -11
  18. package/docker/Mosquitto/README.md +8 -6
  19. package/docker/Mosquitto/startMosquitto.sh +14 -4
  20. package/lib/fiware-iotagent-lib.js +4 -2
  21. package/lib/jexlTranformsMap.js +11 -1
  22. package/lib/model/Device.js +4 -1
  23. package/lib/model/Group.js +19 -1
  24. package/lib/plugins/expressionParser.js +6 -4
  25. package/lib/plugins/expressionPlugin.js +63 -22
  26. package/lib/plugins/jexlParser.js +3 -1
  27. package/lib/plugins/multiEntity.js +2 -21
  28. package/lib/request-shim.js +111 -0
  29. package/lib/services/common/domain.js +6 -2
  30. package/lib/services/common/genericMiddleware.js +6 -2
  31. package/lib/services/common/iotManagerService.js +1 -1
  32. package/lib/services/common/securityServiceKeystone.js +1 -1
  33. package/lib/services/common/securityServiceOAuth2.js +3 -2
  34. package/lib/services/devices/deviceRegistryMemory.js +13 -2
  35. package/lib/services/devices/deviceRegistryMongoDB.js +16 -7
  36. package/lib/services/devices/deviceService.js +26 -2
  37. package/lib/services/devices/devices-NGSI-LD.js +1 -1
  38. package/lib/services/devices/devices-NGSI-v2.js +2 -6
  39. package/lib/services/devices/registrationUtils.js +0 -2
  40. package/lib/services/ngsi/entities-NGSI-LD.js +97 -11
  41. package/lib/services/ngsi/entities-NGSI-v2.js +95 -8
  42. package/lib/services/ngsi/ngsiService.js +5 -4
  43. package/lib/services/northBound/contextServer-NGSI-LD.js +3 -2
  44. package/lib/services/northBound/contextServer-NGSI-v2.js +32 -27
  45. package/lib/services/northBound/contextServerUtils.js +1 -1
  46. package/lib/services/northBound/deviceProvisioningServer.js +31 -6
  47. package/lib/services/northBound/northboundServer.js +2 -0
  48. package/lib/services/northBound/restUtils.js +1 -1
  49. package/lib/templates/createDevice.json +12 -0
  50. package/lib/templates/updateDevice.json +12 -0
  51. package/package.json +9 -15
  52. package/test/tools/utils.js +2 -0
  53. package/test/unit/expressions/jexlExpression-test.js +5 -5
  54. package/test/unit/general/contextBrokerKeystoneSecurityAccess-test.js +1 -1
  55. package/test/unit/general/deviceService-test.js +2 -5
  56. package/test/unit/general/loglevel-api_test.js +6 -11
  57. package/test/unit/general/startup-test.js +1 -0
  58. package/test/unit/memoryRegistry/deviceRegistryMemory_test.js +1 -0
  59. package/test/unit/mongodb/mongodb-group-registry-test.js +1 -1
  60. package/test/unit/mongodb/mongodb-registry-test.js +2 -1
  61. package/test/unit/ngsi-ld/examples/contextRequests/updateContextExpressionPlugin12a.json +7 -0
  62. package/test/unit/ngsi-ld/examples/contextRequests/updateContextExpressionPlugin13.json +13 -13
  63. package/test/unit/ngsi-ld/examples/contextRequests/updateContextExpressionPlugin1a.json +18 -0
  64. package/test/unit/ngsi-ld/examples/contextRequests/updateContextExpressionPlugin29.json +18 -0
  65. package/test/unit/ngsi-ld/examples/contextRequests/updateContextExpressionPlugin31.json +15 -0
  66. package/test/unit/ngsi-ld/examples/contextRequests/updateContextExpressionPlugin32.json +17 -0
  67. package/test/unit/ngsi-ld/examples/contextRequests/updateContextExpressionPlugin33.json +18 -0
  68. package/test/unit/ngsi-ld/examples/contextRequests/updateContextExpressionPlugin34.json +17 -0
  69. package/test/unit/ngsi-ld/examples/contextRequests/updateContextExpressionPlugin4a.json +36 -0
  70. package/test/unit/ngsi-ld/examples/contextRequests/updateContextExpressionPlugin7.json +16 -16
  71. package/test/unit/ngsi-ld/examples/contextRequests/updateContextExpressionPlugin8a.json +18 -0
  72. package/test/unit/ngsi-ld/examples/contextRequests/updateContextMultientityPlugin15.json +25 -0
  73. package/test/unit/ngsi-ld/expressions/jexlBasedTransformations-test.js +1018 -0
  74. package/test/unit/ngsi-ld/general/contextBrokerOAuthSecurityAccess-test.js +2 -2
  75. package/test/unit/ngsi-ld/general/deviceService-test.js +1 -1
  76. package/test/unit/ngsi-ld/general/https-support-test.js +2 -1
  77. package/test/unit/ngsi-ld/general/iotam-autoregistration-test.js +2 -1
  78. package/test/unit/ngsi-ld/general/startup-test.js +1 -0
  79. package/test/unit/ngsi-ld/lazyAndCommands/active-devices-attribute-update-test.js +3 -1
  80. package/test/unit/ngsi-ld/lazyAndCommands/command-test.js +2 -1
  81. package/test/unit/ngsi-ld/lazyAndCommands/lazy-devices-test.js +2 -6
  82. package/test/unit/ngsi-ld/lazyAndCommands/polling-commands-test.js +2 -1
  83. package/test/unit/ngsi-ld/ngsiService/active-devices-test.js +1 -0
  84. package/test/unit/ngsi-ld/ngsiService/autocast-test.js +1 -0
  85. package/test/unit/ngsi-ld/ngsiService/geoproperties-test.js +1 -0
  86. package/test/unit/ngsi-ld/ngsiService/subscriptions-test.js +4 -3
  87. package/test/unit/ngsi-ld/plugins/alias-plugin_test.js +1 -0
  88. package/test/unit/ngsi-ld/plugins/bidirectional-plugin_test.js +3 -2
  89. package/test/unit/ngsi-ld/plugins/multientity-plugin_test.js +61 -0
  90. package/test/unit/ngsi-ld/provisioning/device-provisioning-api_test.js +2 -1
  91. package/test/unit/ngsi-ld/provisioning/device-registration_test.js +3 -2
  92. package/test/unit/ngsi-ld/provisioning/device-update-registration_test.js +1 -0
  93. package/test/unit/ngsi-ld/provisioning/listProvisionedDevices-test.js +42 -54
  94. package/test/unit/ngsi-ld/provisioning/provisionDeviceMultientity-test.js +2 -1
  95. package/test/unit/ngsi-ld/provisioning/removeProvisionedDevice-test.js +4 -4
  96. package/test/unit/ngsi-ld/provisioning/singleConfigurationMode-test.js +3 -5
  97. package/test/unit/ngsi-ld/provisioning/updateProvisionedDevices-test.js +12 -18
  98. package/test/unit/ngsi-mixed/provisioning/ngsi-versioning-test.js +3 -1
  99. package/test/unit/ngsiv2/examples/contextRequests/updateContextExpressionPlugin17.json +1 -1
  100. package/test/unit/ngsiv2/examples/contextRequests/updateContextExpressionPlugin32.json +16 -0
  101. package/test/unit/ngsiv2/examples/contextRequests/updateContextExpressionPlugin33.json +22 -0
  102. package/test/unit/ngsiv2/examples/contextRequests/updateContextExpressionPlugin34.json +12 -0
  103. package/test/unit/ngsiv2/examples/contextRequests/updateContextExpressionPlugin35.json +2 -0
  104. package/test/unit/ngsiv2/examples/contextRequests/updateContextExpressionPlugin36.json +1 -0
  105. package/test/unit/ngsiv2/examples/contextRequests/updateContextMultientityPlugin15.json +25 -0
  106. package/test/unit/ngsiv2/examples/contextRequests/updateContextMultientityPlugin16.json +25 -0
  107. package/test/unit/ngsiv2/expressions/expressionBasedTransformations-test.js +4 -4
  108. package/test/unit/ngsiv2/expressions/jexlBasedTransformations-test.js +561 -0
  109. package/test/unit/ngsiv2/general/contextBrokerOAuthSecurityAccess-test.js +3 -2
  110. package/test/unit/ngsiv2/general/deviceService-test.js +9 -8
  111. package/test/unit/ngsiv2/general/https-support-test.js +2 -1
  112. package/test/unit/ngsiv2/general/iotam-autoregistration-test.js +2 -1
  113. package/test/unit/ngsiv2/general/startup-test.js +1 -0
  114. package/test/unit/ngsiv2/lazyAndCommands/active-devices-attribute-update-test.js +3 -1
  115. package/test/unit/ngsiv2/lazyAndCommands/command-test.js +2 -1
  116. package/test/unit/ngsiv2/lazyAndCommands/lazy-devices-test.js +14 -18
  117. package/test/unit/ngsiv2/lazyAndCommands/polling-commands-test.js +3 -1
  118. package/test/unit/ngsiv2/ngsiService/active-devices-test.js +1 -0
  119. package/test/unit/ngsiv2/ngsiService/queryDeviceInformationInCb-test.js +0 -1
  120. package/test/unit/ngsiv2/ngsiService/subscriptions-test.js +4 -3
  121. package/test/unit/ngsiv2/plugins/bidirectional-plugin_test.js +3 -2
  122. package/test/unit/ngsiv2/plugins/multientity-plugin_test.js +210 -0
  123. package/test/unit/ngsiv2/plugins/translation-inPlugins_test.js +1 -1
  124. package/test/unit/ngsiv2/provisioning/device-group-api-test.js +3 -2
  125. package/test/unit/ngsiv2/provisioning/device-group-utils-test.js +2 -1
  126. package/test/unit/ngsiv2/provisioning/device-provisioning-api_test.js +2 -1
  127. package/test/unit/ngsiv2/provisioning/device-registration_test.js +3 -2
  128. package/test/unit/ngsiv2/provisioning/device-update-registration_test.js +4 -3
  129. package/test/unit/ngsiv2/provisioning/listProvisionedDevices-test.js +42 -53
  130. package/test/unit/ngsiv2/provisioning/provisionDeviceMultientity-test.js +2 -1
  131. package/test/unit/ngsiv2/provisioning/removeProvisionedDevice-test.js +4 -4
  132. package/test/unit/ngsiv2/provisioning/singleConfigurationMode-test.js +3 -4
  133. package/test/unit/ngsiv2/provisioning/updateProvisionedDevices-test.js +13 -19
  134. package/test/unit/plugins/capture-configuration-inPlugins_test.js +3 -1
  135. package/test/unit/plugins/capture-provision-inPlugins_test.js +2 -1
  136. package/bin/agentConsole.js +0 -257
  137. package/bin/iotAgentTester.js +0 -44
  138. package/lib/command/commandLine.js +0 -918
  139. package/lib/command/migration.js +0 -176
  140. package/test/unit/general/migration-test.js +0 -256
  141. package/test/unit/ngsi-ld/examples/contextRequests/updateContextExpressionPlugin20.json +0 -25
@@ -30,6 +30,7 @@ const utils = require('../../../tools/utils');
30
30
  const should = require('should');
31
31
  const logger = require('logops');
32
32
  const nock = require('nock');
33
+ const timekeeper = require('timekeeper');
33
34
  let contextBrokerMock;
34
35
  const iotAgentConfig = {
35
36
  logLevel: 'FATAL',
@@ -216,6 +217,158 @@ const iotAgentConfig = {
216
217
  expression: 'updated|trim'
217
218
  }
218
219
  ]
220
+ },
221
+ GPS: {
222
+ commands: [],
223
+ type: 'GPS',
224
+ lazy: [],
225
+ active: [
226
+ {
227
+ name: 'location',
228
+ type: 'geo:json',
229
+ expression: "{coordinates: [lon,lat], type: 'Point'}"
230
+ },
231
+ {
232
+ name: 'TimeInstant',
233
+ type: 'DateTime',
234
+ expression: 'ts|toisodate'
235
+ }
236
+ ],
237
+ explicitAttrs: true
238
+ },
239
+ GPS2: {
240
+ commands: [],
241
+ type: 'GPS',
242
+ lazy: [],
243
+ active: [
244
+ {
245
+ name: 'location',
246
+ type: 'geo:json',
247
+ expression: "{coordinates: [lon,lat], type: 'Point'}"
248
+ }
249
+ ],
250
+ explicitAttrs: true
251
+ },
252
+ GPS3: {
253
+ commands: [],
254
+ type: 'GPS',
255
+ lazy: [],
256
+ static: [
257
+ {
258
+ name: 'color',
259
+ type: 'string',
260
+ value: 'blue'
261
+ }
262
+ ],
263
+ active: [
264
+ {
265
+ name: 'price',
266
+ type: 'number'
267
+ },
268
+ {
269
+ name: 'location',
270
+ type: 'geo:json',
271
+ expression: "{coordinates: [lon,lat], type: 'Point'}"
272
+ }
273
+ ],
274
+ explicitAttrs: '[ "location" ]'
275
+ },
276
+ GPS4: {
277
+ commands: [],
278
+ type: 'GPS',
279
+ lazy: [],
280
+ static: [
281
+ {
282
+ name: 'color',
283
+ type: 'string',
284
+ value: 'blue'
285
+ }
286
+ ],
287
+ active: [
288
+ {
289
+ name: 'price',
290
+ type: 'number'
291
+ },
292
+ {
293
+ name: 'location',
294
+ type: 'geo:json',
295
+ expression: "{coordinates: [lon,lat], type: 'Point'}"
296
+ }
297
+ ],
298
+ explicitAttrs: '[ "loca" + "tion" ]'
299
+ },
300
+ GPS5: {
301
+ commands: [],
302
+ type: 'GPS',
303
+ lazy: [],
304
+ static: [
305
+ {
306
+ name: 'color',
307
+ type: 'string',
308
+ value: 'blue'
309
+ }
310
+ ],
311
+ active: [
312
+ {
313
+ name: 'price',
314
+ type: 'number'
315
+ },
316
+ {
317
+ name: 'location',
318
+ type: 'geo:json',
319
+ expression: "{coordinates: [lon,lat], type: 'Point'}"
320
+ }
321
+ ],
322
+ explicitAttrs: "[ 'myattr' ]"
323
+ },
324
+ GPS6: {
325
+ commands: [],
326
+ type: 'GPS',
327
+ lazy: [],
328
+ static: [
329
+ {
330
+ name: 'lat',
331
+ type: 'Number',
332
+ value: 52
333
+ },
334
+ {
335
+ name: 'lon',
336
+ type: 'Number',
337
+ value: 13
338
+ }
339
+ ],
340
+ active: [
341
+ {
342
+ name: 'location',
343
+ type: 'geo:json',
344
+ expression: "{coordinates: [lon,lat], type: 'Point'}"
345
+ }
346
+ ],
347
+ explicitAttrs: true
348
+ },
349
+ GPS7: {
350
+ commands: [],
351
+ type: 'GPS',
352
+ lazy: [],
353
+ static: [
354
+ {
355
+ name: 'color',
356
+ type: 'string',
357
+ value: 'blue'
358
+ }
359
+ ],
360
+ active: [
361
+ {
362
+ name: 'price',
363
+ type: 'number'
364
+ },
365
+ {
366
+ name: 'location',
367
+ type: 'geo:json',
368
+ expression: "{coordinates: [lon,lat], type: 'Point'}"
369
+ }
370
+ ],
371
+ explicitAttrs: '[ ]'
219
372
  }
220
373
  },
221
374
  service: 'smartgondor',
@@ -225,6 +378,38 @@ const iotAgentConfig = {
225
378
  throttling: 'PT5S'
226
379
  };
227
380
 
381
+ const iotAgentConfigTS = {
382
+ logLevel: 'FATAL',
383
+ contextBroker: {
384
+ host: '192.168.1.1',
385
+ port: '1026',
386
+ ngsiVersion: 'v2'
387
+ },
388
+ defaultExpressionLanguage: 'jexl',
389
+ server: {
390
+ port: 4041
391
+ },
392
+ types: {
393
+ GPS: {
394
+ commands: [],
395
+ type: 'GPS',
396
+ lazy: [],
397
+ active: [
398
+ {
399
+ name: 'location',
400
+ type: 'geo:json',
401
+ expression: "{coordinates: [lon,lat], type: 'Point'}"
402
+ }
403
+ ],
404
+ explicitAttrs: true
405
+ }
406
+ },
407
+ timestamp: true,
408
+ service: 'smartgondor',
409
+ subservice: 'gardens',
410
+ providerUrl: 'http://smartgondor.com'
411
+ };
412
+
228
413
  describe('Java expression language (JEXL) based transformations plugin', function () {
229
414
  beforeEach(function (done) {
230
415
  logger.setLevel('FATAL');
@@ -804,4 +989,380 @@ describe('Java expression language (JEXL) based transformations plugin', functio
804
989
  });
805
990
  });
806
991
  });
992
+
993
+ describe('When there are additional attributes sent by the device to be calculated and removed', function () {
994
+ // Case: Expression which results is sent as a new attribute
995
+ const values = [
996
+ {
997
+ name: 'lat',
998
+ type: 'Number',
999
+ value: 52
1000
+ },
1001
+ {
1002
+ name: 'lon',
1003
+ type: 'Number',
1004
+ value: 13
1005
+ },
1006
+ {
1007
+ name: 'ts',
1008
+ type: 'Number',
1009
+ value: 1
1010
+ }
1011
+ ];
1012
+
1013
+ beforeEach(function () {
1014
+ nock.cleanAll();
1015
+
1016
+ contextBrokerMock = nock('http://192.168.1.1:1026')
1017
+ .matchHeader('fiware-service', 'smartgondor')
1018
+ .matchHeader('fiware-servicepath', 'gardens')
1019
+ .patch(
1020
+ '/v2/entities/gps1/attrs',
1021
+ utils.readExampleFile(
1022
+ './test/unit/ngsiv2/examples/contextRequests/updateContextExpressionPlugin32.json'
1023
+ )
1024
+ )
1025
+ .query({ type: 'GPS' })
1026
+ .reply(204);
1027
+ });
1028
+
1029
+ it('should calculate them and remove non-explicitAttrs from the payload', function (done) {
1030
+ iotAgentLib.update('gps1', 'GPS', '', values, function (error) {
1031
+ should.not.exist(error);
1032
+ contextBrokerMock.done();
1033
+ done();
1034
+ });
1035
+ });
1036
+ });
1037
+
1038
+ describe('When there is an extra TimeInstant sent by the device to be removed', function () {
1039
+ // Case: Expression which results is sent as a new attribute
1040
+ const values = [
1041
+ {
1042
+ name: 'lat',
1043
+ type: 'Number',
1044
+ value: 52
1045
+ },
1046
+ {
1047
+ name: 'lon',
1048
+ type: 'Number',
1049
+ value: 13
1050
+ },
1051
+ {
1052
+ name: 'TimeInstant',
1053
+ type: 'DateTime',
1054
+ value: '2015-08-05T07:35:01.468+00:00'
1055
+ }
1056
+ ];
1057
+
1058
+ beforeEach(function () {
1059
+ nock.cleanAll();
1060
+
1061
+ contextBrokerMock = nock('http://192.168.1.1:1026')
1062
+ .matchHeader('fiware-service', 'smartgondor')
1063
+ .matchHeader('fiware-servicepath', 'gardens')
1064
+ .patch(
1065
+ '/v2/entities/gps1/attrs',
1066
+ utils.readExampleFile(
1067
+ './test/unit/ngsiv2/examples/contextRequests/updateContextExpressionPlugin34.json'
1068
+ )
1069
+ )
1070
+ .query({ type: 'GPS' })
1071
+ .reply(204);
1072
+ });
1073
+
1074
+ it('should calculate them and remove non-explicitAttrs from the payload', function (done) {
1075
+ iotAgentLib.update('gps1', 'GPS2', '', values, function (error) {
1076
+ should.not.exist(error);
1077
+ contextBrokerMock.done();
1078
+ done();
1079
+ });
1080
+ });
1081
+ });
1082
+
1083
+ describe('When there is an extra TimeInstant sent by the device to be removed by string', function () {
1084
+ // Case: Expression which results is sent as a new attribute
1085
+ const values = [
1086
+ {
1087
+ name: 'lat',
1088
+ type: 'Number',
1089
+ value: 52
1090
+ },
1091
+ {
1092
+ name: 'lon',
1093
+ type: 'Number',
1094
+ value: 13
1095
+ },
1096
+ {
1097
+ name: 'TimeInstant',
1098
+ type: 'DateTime',
1099
+ value: '2015-08-05T07:35:01.468+00:00'
1100
+ }
1101
+ ];
1102
+
1103
+ beforeEach(function () {
1104
+ nock.cleanAll();
1105
+
1106
+ contextBrokerMock = nock('http://192.168.1.1:1026')
1107
+ .matchHeader('fiware-service', 'smartgondor')
1108
+ .matchHeader('fiware-servicepath', 'gardens')
1109
+ .patch(
1110
+ '/v2/entities/gps1/attrs',
1111
+ utils.readExampleFile(
1112
+ './test/unit/ngsiv2/examples/contextRequests/updateContextExpressionPlugin34.json'
1113
+ )
1114
+ )
1115
+ .query({ type: 'GPS' })
1116
+ .reply(204);
1117
+ });
1118
+
1119
+ it('should calculate them and remove non-explicitAttrs by string from the payload', function (done) {
1120
+ iotAgentLib.update('gps1', 'GPS3', '', values, function (error) {
1121
+ should.not.exist(error);
1122
+ contextBrokerMock.done();
1123
+ done();
1124
+ });
1125
+ });
1126
+ });
1127
+
1128
+ describe('When there is an extra TimeInstant sent by the device to be removed by jexl expression', function () {
1129
+ // Case: Expression which results is sent as a new attribute
1130
+ const values = [
1131
+ {
1132
+ name: 'lat',
1133
+ type: 'Number',
1134
+ value: 52
1135
+ },
1136
+ {
1137
+ name: 'lon',
1138
+ type: 'Number',
1139
+ value: 13
1140
+ },
1141
+ {
1142
+ name: 'TimeInstant',
1143
+ type: 'DateTime',
1144
+ value: '2015-08-05T07:35:01.468+00:00'
1145
+ }
1146
+ ];
1147
+
1148
+ beforeEach(function () {
1149
+ nock.cleanAll();
1150
+
1151
+ contextBrokerMock = nock('http://192.168.1.1:1026')
1152
+ .matchHeader('fiware-service', 'smartgondor')
1153
+ .matchHeader('fiware-servicepath', 'gardens')
1154
+ .patch(
1155
+ '/v2/entities/gps1/attrs',
1156
+ utils.readExampleFile(
1157
+ './test/unit/ngsiv2/examples/contextRequests/updateContextExpressionPlugin34.json'
1158
+ )
1159
+ )
1160
+ .query({ type: 'GPS' })
1161
+ .reply(204);
1162
+ });
1163
+
1164
+ it('should calculate them and remove non-explicitAttrs by jexl expression from the payload', function (done) {
1165
+ iotAgentLib.update('gps1', 'GPS4', '', values, function (error) {
1166
+ should.not.exist(error);
1167
+ contextBrokerMock.done();
1168
+ done();
1169
+ });
1170
+ });
1171
+ });
1172
+
1173
+ describe('When there is an extra TimeInstant sent by the device to be removed by jexl expression with context ', function () {
1174
+ // Case: Expression which results is sent as a new attribute
1175
+ const values = [
1176
+ {
1177
+ name: 'lat',
1178
+ type: 'Number',
1179
+ value: 52
1180
+ },
1181
+ {
1182
+ name: 'lon',
1183
+ type: 'Number',
1184
+ value: 13
1185
+ },
1186
+ {
1187
+ name: 'myattr',
1188
+ type: 'String',
1189
+ value: 'location'
1190
+ },
1191
+ {
1192
+ name: 'TimeInstant',
1193
+ type: 'DateTime',
1194
+ value: '2015-08-05T07:35:01.468+00:00'
1195
+ }
1196
+ ];
1197
+
1198
+ beforeEach(function () {
1199
+ nock.cleanAll();
1200
+
1201
+ contextBrokerMock = nock('http://192.168.1.1:1026')
1202
+ .matchHeader('fiware-service', 'smartgondor')
1203
+ .matchHeader('fiware-servicepath', 'gardens')
1204
+ .patch(
1205
+ '/v2/entities/gps1/attrs',
1206
+ utils.readExampleFile(
1207
+ './test/unit/ngsiv2/examples/contextRequests/updateContextExpressionPlugin36.json'
1208
+ )
1209
+ )
1210
+ .query({ type: 'GPS' })
1211
+ .reply(204);
1212
+ });
1213
+
1214
+ it('should calculate them and remove non-explicitAttrs by jexl expression with context from the payload ', function (done) {
1215
+ iotAgentLib.update('gps1', 'GPS5', '', values, function (error) {
1216
+ should.not.exist(error);
1217
+ contextBrokerMock.done();
1218
+ done();
1219
+ });
1220
+ });
1221
+ });
1222
+
1223
+ describe('When there is an extra TimeInstant sent by the device to be removedb jexl expression using static attrs', function () {
1224
+ // Case: Expression which results is sent as a new attribute
1225
+ const values = [
1226
+ {
1227
+ name: 'TimeInstant',
1228
+ type: 'DateTime',
1229
+ value: '2015-08-05T07:35:01.468+00:00'
1230
+ }
1231
+ ];
1232
+
1233
+ beforeEach(function () {
1234
+ nock.cleanAll();
1235
+
1236
+ contextBrokerMock = nock('http://192.168.1.1:1026')
1237
+ .matchHeader('fiware-service', 'smartgondor')
1238
+ .matchHeader('fiware-servicepath', 'gardens')
1239
+ .patch(
1240
+ '/v2/entities/gps1/attrs',
1241
+ utils.readExampleFile(
1242
+ './test/unit/ngsiv2/examples/contextRequests/updateContextExpressionPlugin34.json'
1243
+ )
1244
+ )
1245
+ .query({ type: 'GPS' })
1246
+ .reply(204);
1247
+ });
1248
+
1249
+ it('should calculate them and remove non-explicitAttrs from the payload', function (done) {
1250
+ iotAgentLib.update('gps1', 'GPS6', '', values, function (error) {
1251
+ should.not.exist(error);
1252
+ contextBrokerMock.done();
1253
+ done();
1254
+ });
1255
+ });
1256
+ });
1257
+
1258
+ describe('When there is an extra TimeInstant sent by the device to be removed by jexl expression with context but with empty explicitAttrs', function () {
1259
+ // Case: Expression which results is sent as a new attribute
1260
+ const values = [
1261
+ {
1262
+ name: 'lat',
1263
+ type: 'Number',
1264
+ value: 52
1265
+ },
1266
+ {
1267
+ name: 'lon',
1268
+ type: 'Number',
1269
+ value: 13
1270
+ },
1271
+ {
1272
+ name: 'myattr',
1273
+ type: 'String',
1274
+ value: 'location'
1275
+ },
1276
+ {
1277
+ name: 'TimeInstant',
1278
+ type: 'DateTime',
1279
+ value: '2015-08-05T07:35:01.468+00:00'
1280
+ }
1281
+ ];
1282
+
1283
+ beforeEach(function () {
1284
+ nock.cleanAll();
1285
+ });
1286
+
1287
+ it('should calculate them and remove non-explicitAttrs by jexl expression with context from the payload ', function (done) {
1288
+ iotAgentLib.update('gps1', 'GPS7', '', values, function (error) {
1289
+ should.not.exist(error);
1290
+ done();
1291
+ });
1292
+ });
1293
+ });
1294
+ });
1295
+
1296
+ describe('Java expression language (JEXL) based transformations plugin - Timestamps', function () {
1297
+ beforeEach(function (done) {
1298
+ logger.setLevel('FATAL');
1299
+
1300
+ iotAgentLib.activate(iotAgentConfigTS, function () {
1301
+ iotAgentLib.clearAll(function () {
1302
+ iotAgentLib.addUpdateMiddleware(iotAgentLib.dataPlugins.attributeAlias.update);
1303
+ iotAgentLib.addQueryMiddleware(iotAgentLib.dataPlugins.attributeAlias.query);
1304
+ iotAgentLib.addUpdateMiddleware(iotAgentLib.dataPlugins.expressionTransformation.update);
1305
+ done();
1306
+ });
1307
+ });
1308
+ });
1309
+
1310
+ afterEach(function (done) {
1311
+ iotAgentLib.clearAll(function () {
1312
+ iotAgentLib.deactivate(done);
1313
+ });
1314
+ });
1315
+
1316
+ describe('When timestamps are added but are not explicitly defined', function () {
1317
+ // Case: Expression which results is sent as a new attribute
1318
+ const values = [
1319
+ {
1320
+ name: 'lat',
1321
+ type: 'Number',
1322
+ value: 52
1323
+ },
1324
+ {
1325
+ name: 'lon',
1326
+ type: 'Number',
1327
+ value: 13
1328
+ },
1329
+ {
1330
+ name: 'ts',
1331
+ type: 'Number',
1332
+ value: 1
1333
+ }
1334
+ ];
1335
+
1336
+ beforeEach(function () {
1337
+ const time = new Date(1438760101468); // 2015-08-05T07:35:01.468+00:00
1338
+
1339
+ timekeeper.freeze(time);
1340
+ nock.cleanAll();
1341
+
1342
+ contextBrokerMock = nock('http://192.168.1.1:1026')
1343
+ .matchHeader('fiware-service', 'smartgondor')
1344
+ .matchHeader('fiware-servicepath', 'gardens')
1345
+ .patch(
1346
+ '/v2/entities/gps1/attrs',
1347
+ utils.readExampleFile(
1348
+ './test/unit/ngsiv2/examples/contextRequests/updateContextExpressionPlugin33.json'
1349
+ )
1350
+ )
1351
+ .query({ type: 'GPS' })
1352
+ .reply(204);
1353
+ });
1354
+
1355
+ afterEach(function (done) {
1356
+ timekeeper.reset();
1357
+ done();
1358
+ });
1359
+
1360
+ it('should calculate them and not remove the timestamp from the payload', function (done) {
1361
+ iotAgentLib.update('gps1', 'GPS', '', values, function (error) {
1362
+ should.not.exist(error);
1363
+ contextBrokerMock.done();
1364
+ done();
1365
+ });
1366
+ });
1367
+ });
807
1368
  });
@@ -27,10 +27,11 @@
27
27
 
28
28
  const iotAgentLib = require('../../../../lib/fiware-iotagent-lib');
29
29
  const utils = require('../../../tools/utils');
30
+ const request = utils.request;
30
31
  const should = require('should');
31
32
  const logger = require('logops');
32
33
  const nock = require('nock');
33
- const request = require('request');
34
+
34
35
  const timekeeper = require('timekeeper');
35
36
  let contextBrokerMock;
36
37
  let oauth2Mock;
@@ -338,7 +339,7 @@ describe('NGSI-v2 - Secured access to the Context Broker with OAuth2 provider',
338
339
  )
339
340
  .reply(201, utils.readExampleFile('./test/unit/examples/oauthResponses/tokenFromTrust.json'), {});
340
341
 
341
- contextBrokerMock.delete('/v2/subscriptions/51c0ac9ed714fb3b37d7d5a8').reply(204);
342
+ contextBrokerMock.delete('/v2/subscriptions/51c0ac9ed714fb3b37d7d5a8', '').reply(204);
342
343
 
343
344
  iotAgentLib.getDevice('Light1', 'smartgondor', 'electricity', function (error, device) {
344
345
  iotAgentLib.subscribe(device, ['dimming'], null, function (error) {
@@ -27,9 +27,10 @@
27
27
 
28
28
  const iotAgentLib = require('../../../../lib/fiware-iotagent-lib');
29
29
  const utils = require('../../../tools/utils');
30
+ const request = utils.request;
30
31
  const should = require('should');
31
32
  const nock = require('nock');
32
- const request = require('request');
33
+
33
34
  const logger = require('logops');
34
35
  const async = require('async');
35
36
  const iotAgentConfig = {
@@ -192,12 +193,12 @@ describe('NGSI-v2 - Device Service: utils', function () {
192
193
  .post('/v2/entities?options=upsert')
193
194
  .reply(204);
194
195
 
195
- async.series([request.bind(request, groupCreation), request.bind(request, deviceCreation)], function (
196
- error,
197
- results
198
- ) {
199
- done();
200
- });
196
+ async.series(
197
+ [utils.request.bind(utils.request, groupCreation), utils.request.bind(utils.request, deviceCreation)],
198
+ function (error, results) {
199
+ done();
200
+ }
201
+ );
201
202
  });
202
203
 
203
204
  it('should return the existing device', function (done) {
@@ -222,7 +223,7 @@ describe('NGSI-v2 - Device Service: utils', function () {
222
223
  .post('/v2/entities?options=upsert')
223
224
  .reply(204);
224
225
 
225
- async.series([request.bind(request, groupCreation)], function (error, results) {
226
+ async.series([utils.request.bind(utils.request, groupCreation)], function (error, results) {
226
227
  done();
227
228
  });
228
229
  });
@@ -27,9 +27,10 @@
27
27
  /* eslint-disable no-unused-vars */
28
28
 
29
29
  const iotAgentLib = require('../../../../lib/fiware-iotagent-lib');
30
- const request = require('request');
30
+
31
31
  const nock = require('nock');
32
32
  const utils = require('../../../tools/utils');
33
+ const request = utils.request;
33
34
  const groupRegistryMemory = require('../../../../lib/services/groups/groupRegistryMemory');
34
35
  const should = require('should');
35
36
  const iotAgentConfig = {
@@ -24,9 +24,10 @@
24
24
  /* eslint-disable no-unused-vars */
25
25
 
26
26
  const iotAgentLib = require('../../../../lib/fiware-iotagent-lib');
27
- const request = require('request');
27
+
28
28
  const nock = require('nock');
29
29
  const utils = require('../../../tools/utils');
30
+ const request = utils.request;
30
31
  const groupRegistryMemory = require('../../../../lib/services/groups/groupRegistryMemory');
31
32
  const should = require('should');
32
33
  const iotAgentConfig = {
@@ -30,6 +30,7 @@ const iotAgentLib = require('../../../../lib/fiware-iotagent-lib');
30
30
  const should = require('should');
31
31
  const nock = require('nock');
32
32
  const utils = require('../../../tools/utils');
33
+ const request = utils.request;
33
34
  const config = require('../../../../lib/commonConfig');
34
35
  const iotAgentConfig = {
35
36
  logLevel: 'FATAL',
@@ -26,11 +26,13 @@
26
26
  /* eslint-disable no-unused-vars */
27
27
 
28
28
  const iotAgentLib = require('../../../../lib/fiware-iotagent-lib');
29
+ const utils = require('../../../tools/utils');
30
+ const request = utils.request;
29
31
  const should = require('should');
30
32
  const logger = require('logops');
31
33
  const nock = require('nock');
32
34
  const mongoUtils = require('../../mongodb/mongoDBUtils');
33
- const request = require('request');
35
+
34
36
  let contextBrokerMock;
35
37
  const iotAgentConfig = {
36
38
  logLevel: 'FATAL',