kuzzle-device-manager 2.0.0-rc21 → 2.0.0-rc23
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.
- package/lib/DeviceManagerPlugin.js +7 -7
- package/lib/controllers/AssetController.d.ts +13 -6
- package/lib/controllers/AssetController.js +27 -12
- package/lib/controllers/{DecodersController.d.ts → DecoderController.d.ts} +1 -1
- package/lib/controllers/{DecodersController.js → DecoderController.js} +4 -4
- package/lib/controllers/DeviceController.d.ts +5 -3
- package/lib/controllers/DeviceController.js +21 -9
- package/lib/controllers/RelationalController.d.ts +7 -0
- package/lib/controllers/RelationalController.js +9 -0
- package/lib/controllers/index.d.ts +1 -1
- package/lib/controllers/index.js +1 -1
- package/lib/core-classes/AssetCategoryService.d.ts +7 -1
- package/lib/core-classes/AssetCategoryService.js +12 -0
- package/lib/core-classes/AssetService.d.ts +1 -1
- package/lib/core-classes/AssetService.js +3 -3
- package/lib/core-classes/Decoder.d.ts +23 -15
- package/lib/core-classes/Decoder.js +21 -16
- package/lib/core-classes/DeviceService.d.ts +0 -2
- package/lib/core-classes/DeviceService.js +8 -15
- package/lib/core-classes/MeasureService.d.ts +6 -5
- package/lib/core-classes/MeasureService.js +30 -19
- package/lib/core-classes/PayloadService.d.ts +7 -3
- package/lib/core-classes/PayloadService.js +15 -8
- package/lib/core-classes/registers/DecodersRegister.d.ts +7 -1
- package/lib/core-classes/registers/DecodersRegister.js +22 -4
- package/lib/measures/BatteryMeasure.d.ts +3 -5
- package/lib/measures/HumidityMeasure.d.ts +3 -5
- package/lib/measures/MovementMeasure.d.ts +3 -5
- package/lib/measures/PositionMeasure.d.ts +7 -9
- package/lib/measures/TemperatureMeasure.d.ts +4 -6
- package/lib/models/BaseAsset.js +4 -1
- package/lib/models/Device.d.ts +2 -0
- package/lib/models/Device.js +7 -0
- package/lib/types/DecodedPayload.d.ts +43 -30
- package/lib/types/DecodedPayload.js +70 -1
- package/lib/types/DecoderContent.d.ts +1 -1
- package/lib/types/index.d.ts +2 -0
- package/lib/types/index.js +2 -0
- package/lib/types/measures/MeasureContent.d.ts +9 -12
- package/lib/types/measures/MeasureContent.js +0 -9
- package/lib/types/measures/MeasureDefinition.d.ts +1 -1
- package/package.json +2 -2
|
@@ -20,10 +20,6 @@ class DeviceManagerPlugin extends kuzzle_1.Plugin {
|
|
|
20
20
|
super({
|
|
21
21
|
kuzzleVersion: '>=2.16.8 <3'
|
|
22
22
|
});
|
|
23
|
-
this.decodersRegister = new core_classes_1.DecodersRegister();
|
|
24
|
-
this.measuresRegister = new core_classes_1.MeasuresRegister();
|
|
25
|
-
this.devicesRegister = new core_classes_1.DevicesRegister(this.measuresRegister);
|
|
26
|
-
this.assetsRegister = new core_classes_1.AssetsRegister(this.measuresRegister);
|
|
27
23
|
this.api = {
|
|
28
24
|
'device-manager/payload': {
|
|
29
25
|
actions: {}
|
|
@@ -65,6 +61,10 @@ class DeviceManagerPlugin extends kuzzle_1.Plugin {
|
|
|
65
61
|
batchInterval: 10
|
|
66
62
|
};
|
|
67
63
|
/* eslint-enable sort-keys */
|
|
64
|
+
this.measuresRegister = new core_classes_1.MeasuresRegister();
|
|
65
|
+
this.decodersRegister = new core_classes_1.DecodersRegister(this.measuresRegister);
|
|
66
|
+
this.devicesRegister = new core_classes_1.DevicesRegister(this.measuresRegister);
|
|
67
|
+
this.assetsRegister = new core_classes_1.AssetsRegister(this.measuresRegister);
|
|
68
68
|
this.measures.register('temperature', measures_1.temperatureMeasure);
|
|
69
69
|
this.measures.register('position', measures_1.positionMeasure);
|
|
70
70
|
this.measures.register('movement', measures_1.movementMeasure);
|
|
@@ -159,19 +159,19 @@ class DeviceManagerPlugin extends kuzzle_1.Plugin {
|
|
|
159
159
|
this.assetService = new core_classes_1.AssetService(this, this.batchController);
|
|
160
160
|
this.deviceService = new core_classes_1.DeviceService(this, this.batchController, this.assetService, this.decodersRegister);
|
|
161
161
|
this.measuresService = new MeasureService_1.MeasureService(this, this.batchController, this.assetService, this.measuresRegister);
|
|
162
|
-
this.payloadService = new core_classes_1.PayloadService(this, this.batchController, this.
|
|
162
|
+
this.payloadService = new core_classes_1.PayloadService(this, this.batchController, this.measuresService);
|
|
163
163
|
this.deviceManagerEngine = new core_classes_1.DeviceManagerEngine(this, this.assetsRegister, this.devicesRegister, this.measuresRegister, this.adminConfigManager, this.engineConfigManager);
|
|
164
164
|
this.decodersRegister.init(this.context);
|
|
165
165
|
this.assetController = new controllers_1.AssetController(this, this.assetService, this.deviceService, this.assetCategoryService, this.measuresService);
|
|
166
166
|
this.deviceController = new controllers_1.DeviceController(this, this.deviceService);
|
|
167
|
-
this.decodersController = new controllers_1.
|
|
167
|
+
this.decodersController = new controllers_1.DecoderController(this, this.decodersRegister);
|
|
168
168
|
this.engineController = new kuzzle_plugin_commons_1.EngineController('device-manager', this, this.deviceManagerEngine);
|
|
169
169
|
this.assetCategoryController = new AssetCategoryController_1.AssetCategoryController(this, this.assetCategoryService);
|
|
170
170
|
this.metadataController = new MetadataController_1.MetadataController(this, this.assetCategoryService);
|
|
171
171
|
this.api['device-manager/payload'] = this.decodersRegister.getPayloadController(this.payloadService);
|
|
172
172
|
this.api['device-manager/asset'] = this.assetController.definition;
|
|
173
173
|
this.api['device-manager/device'] = this.deviceController.definition;
|
|
174
|
-
this.api['device-manager/
|
|
174
|
+
this.api['device-manager/decoder'] = this.decodersController.definition;
|
|
175
175
|
this.api['device-manager/assetCategory'] = this.assetCategoryController.definition;
|
|
176
176
|
this.api['device-manager/metadata'] = this.metadataController.definition;
|
|
177
177
|
this.api['device-manager/payload'].actions.generic = {
|
|
@@ -1,8 +1,9 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { KuzzleRequest, Plugin } from 'kuzzle';
|
|
2
2
|
import { BaseAsset } from '../models/BaseAsset';
|
|
3
3
|
import { AssetService, DeviceService } from '../core-classes';
|
|
4
4
|
import { AssetCategoryService } from '../core-classes/AssetCategoryService';
|
|
5
5
|
import { RelationalController } from './RelationalController';
|
|
6
|
+
import { BaseAssetContent } from '../types';
|
|
6
7
|
import { MeasureService } from 'lib/core-classes/MeasureService';
|
|
7
8
|
export declare class AssetController extends RelationalController {
|
|
8
9
|
private assetService;
|
|
@@ -21,9 +22,9 @@ export declare class AssetController extends RelationalController {
|
|
|
21
22
|
asset: BaseAsset;
|
|
22
23
|
}>;
|
|
23
24
|
getMeasures(request: KuzzleRequest): Promise<{
|
|
24
|
-
measures: import("kuzzle").KDocument<import("../types").MeasureContent
|
|
25
|
+
measures: import("kuzzle").KDocument<import("../types").MeasureContent<import("kuzzle").JSONObject>>[];
|
|
25
26
|
}>;
|
|
26
|
-
get(request: KuzzleRequest): Promise<
|
|
27
|
+
get(request: KuzzleRequest): Promise<BaseAssetContent>;
|
|
27
28
|
unlinkCategory(request: KuzzleRequest): Promise<import("kuzzle").KDocument<{
|
|
28
29
|
[x: string]: any;
|
|
29
30
|
}>>;
|
|
@@ -31,10 +32,10 @@ export declare class AssetController extends RelationalController {
|
|
|
31
32
|
[x: string]: any;
|
|
32
33
|
}>>;
|
|
33
34
|
pushMeasures(request: KuzzleRequest): Promise<{
|
|
34
|
-
asset: JSONObject | (() => JSONObject);
|
|
35
|
+
asset: import("kuzzle").JSONObject | (() => import("kuzzle").JSONObject);
|
|
35
36
|
engineId: string;
|
|
36
|
-
invalids: JSONObject[];
|
|
37
|
-
valids: any[] | import("../types").MeasureContent[];
|
|
37
|
+
invalids: import("kuzzle").JSONObject[];
|
|
38
|
+
valids: any[] | import("../types").MeasureContent<import("kuzzle").JSONObject>[];
|
|
38
39
|
}>;
|
|
39
40
|
update(request: KuzzleRequest): Promise<import("kuzzle").KDocument<{
|
|
40
41
|
[x: string]: any;
|
|
@@ -47,4 +48,10 @@ export declare class AssetController extends RelationalController {
|
|
|
47
48
|
successes: any[];
|
|
48
49
|
}>;
|
|
49
50
|
delete(request: KuzzleRequest): Promise<string>;
|
|
51
|
+
/**
|
|
52
|
+
* search assets or devices depending on the collection.
|
|
53
|
+
*
|
|
54
|
+
* @param request
|
|
55
|
+
*/
|
|
56
|
+
search(request: KuzzleRequest): Promise<import("kuzzle").SearchResult<import("kuzzle").KHit<BaseAssetContent>>>;
|
|
50
57
|
}
|
|
@@ -113,12 +113,8 @@ class AssetController extends RelationalController_1.RelationalController {
|
|
|
113
113
|
const engineId = request.getString('engineId');
|
|
114
114
|
const category = this.getFieldPath(request, 'category', null, 'asset-category');
|
|
115
115
|
const document = await this.genericGet(engineId, this.collection, id, [category]);
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
if (metadata) {
|
|
119
|
-
asset.metadata = await this.assetCategoryService.formatMetadataForGet(metadata);
|
|
120
|
-
}
|
|
121
|
-
return asset;
|
|
116
|
+
this.assetCategoryService.formatDocumentMetadata(document);
|
|
117
|
+
return document._source;
|
|
122
118
|
}
|
|
123
119
|
async unlinkCategory(request) {
|
|
124
120
|
const id = request.getId();
|
|
@@ -233,15 +229,34 @@ class AssetController extends RelationalController_1.RelationalController {
|
|
|
233
229
|
const assetId = request.getId();
|
|
234
230
|
const refresh = request.getRefresh();
|
|
235
231
|
const strict = request.getBoolean('strict');
|
|
236
|
-
const
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
await this.deviceService.unlinkAsset(deviceLink.deviceId, { refresh, strict });
|
|
241
|
-
}
|
|
232
|
+
const asset = await this.assetService.get(engineId, assetId);
|
|
233
|
+
for (const deviceLink of asset._source.deviceLinks) {
|
|
234
|
+
// TODO : Refacto to only get the asset one time
|
|
235
|
+
await this.deviceService.unlinkAsset(deviceLink.deviceId, { refresh, strict });
|
|
242
236
|
}
|
|
243
237
|
return super.delete(request);
|
|
244
238
|
}
|
|
239
|
+
/**
|
|
240
|
+
* search assets or devices depending on the collection.
|
|
241
|
+
*
|
|
242
|
+
* @param request
|
|
243
|
+
*/
|
|
244
|
+
async search(request) {
|
|
245
|
+
const engineId = request.getString('engineId');
|
|
246
|
+
const { searchBody, from, size, scrollTTL: scroll } = request.getSearchParams();
|
|
247
|
+
const category = this.getFieldPath(request, 'category', null, 'asset-category');
|
|
248
|
+
const res = await this.sdk.document.search(engineId, this.collection, searchBody, {
|
|
249
|
+
from,
|
|
250
|
+
lang: request.getLangParam(),
|
|
251
|
+
scroll,
|
|
252
|
+
size,
|
|
253
|
+
});
|
|
254
|
+
for (const hit of res.hits) {
|
|
255
|
+
const document = await this.esDocumentToFormatted(engineId, this.collection, hit, [category]);
|
|
256
|
+
this.assetCategoryService.formatDocumentMetadata(document);
|
|
257
|
+
}
|
|
258
|
+
return res;
|
|
259
|
+
}
|
|
245
260
|
}
|
|
246
261
|
exports.AssetController = AssetController;
|
|
247
262
|
//# sourceMappingURL=AssetController.js.map
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { ControllerDefinition } from 'kuzzle';
|
|
2
2
|
import { DeviceManagerPlugin } from '../DeviceManagerPlugin';
|
|
3
3
|
import { DecodersRegister } from '../core-classes';
|
|
4
|
-
export declare class
|
|
4
|
+
export declare class DecoderController {
|
|
5
5
|
private context;
|
|
6
6
|
private config;
|
|
7
7
|
private decodersRegister;
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
-
exports.
|
|
4
|
-
class
|
|
3
|
+
exports.DecoderController = void 0;
|
|
4
|
+
class DecoderController {
|
|
5
5
|
constructor(plugin, decodersRegister) {
|
|
6
6
|
this.context = plugin.context;
|
|
7
7
|
this.config = plugin.config;
|
|
@@ -23,5 +23,5 @@ class DecodersController {
|
|
|
23
23
|
return { decoders };
|
|
24
24
|
}
|
|
25
25
|
}
|
|
26
|
-
exports.
|
|
27
|
-
//# sourceMappingURL=
|
|
26
|
+
exports.DecoderController = DecoderController;
|
|
27
|
+
//# sourceMappingURL=DecoderController.js.map
|
|
@@ -12,9 +12,11 @@ export declare class DeviceController extends CRUDController {
|
|
|
12
12
|
* Create and provision a new device
|
|
13
13
|
*/
|
|
14
14
|
create(request: KuzzleRequest): Promise<Device>;
|
|
15
|
-
update(): Promise<
|
|
16
|
-
|
|
17
|
-
|
|
15
|
+
update(request: KuzzleRequest): Promise<import("kuzzle").KDocument<{
|
|
16
|
+
[x: string]: any;
|
|
17
|
+
}>>;
|
|
18
|
+
search(request: KuzzleRequest): Promise<any>;
|
|
19
|
+
delete(request: KuzzleRequest): Promise<string>;
|
|
18
20
|
/**
|
|
19
21
|
* Attach a device to a tenant
|
|
20
22
|
*/
|
|
@@ -61,6 +61,18 @@ class DeviceController extends kuzzle_plugin_commons_1.CRUDController {
|
|
|
61
61
|
handler: this.create.bind(this),
|
|
62
62
|
http: [{ path: 'device-manager/:engineId/devices', verb: 'post' }]
|
|
63
63
|
},
|
|
64
|
+
update: {
|
|
65
|
+
handler: this.update.bind(this),
|
|
66
|
+
http: [{ path: 'device-manager/:engineId/device/:deviceId', verb: 'post' }]
|
|
67
|
+
},
|
|
68
|
+
search: {
|
|
69
|
+
handler: this.search.bind(this),
|
|
70
|
+
http: [{ path: 'device-manager/:engineId/devices/_search', verb: 'post' }]
|
|
71
|
+
},
|
|
72
|
+
delete: {
|
|
73
|
+
handler: this.delete.bind(this),
|
|
74
|
+
http: [{ path: 'device-manager/:engineId/device/:deviceId', verb: 'delete' }]
|
|
75
|
+
},
|
|
64
76
|
}
|
|
65
77
|
};
|
|
66
78
|
/* eslint-enable sort-keys */
|
|
@@ -102,17 +114,17 @@ class DeviceController extends kuzzle_plugin_commons_1.CRUDController {
|
|
|
102
114
|
});
|
|
103
115
|
return device;
|
|
104
116
|
}
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
117
|
+
async update(request) {
|
|
118
|
+
request.input.args.index = request.getString('engineId');
|
|
119
|
+
return super.update(request);
|
|
108
120
|
}
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
121
|
+
async search(request) {
|
|
122
|
+
request.input.args.index = request.getString('engineId');
|
|
123
|
+
return super.search(request);
|
|
112
124
|
}
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
125
|
+
async delete(request) {
|
|
126
|
+
request.input.args.index = request.getString('engineId');
|
|
127
|
+
return super.delete(request);
|
|
116
128
|
}
|
|
117
129
|
/**
|
|
118
130
|
* Attach a device to a tenant
|
|
@@ -144,6 +144,13 @@ export declare abstract class RelationalController extends CRUDController {
|
|
|
144
144
|
* @param nestedFields : contain field name in the document to get, collection name and index name of documents that are linked
|
|
145
145
|
*/
|
|
146
146
|
protected genericGet<TKDocumentContent extends KDocumentContent>(index: string, collection: string, documentId: string, nestedFields?: FieldPath[]): Promise<KDocument<TKDocumentContent>>;
|
|
147
|
+
/**
|
|
148
|
+
* @param index
|
|
149
|
+
* @param collection
|
|
150
|
+
* @param documentId
|
|
151
|
+
* @param nestedFields : contain field name in the document to get, collection name and index name of documents that are linked
|
|
152
|
+
*/
|
|
153
|
+
protected esDocumentToFormatted<TKDocumentContent extends KDocumentContent>(index: string, collection: string, document: KDocument<TKDocumentContent>, nestedFields?: FieldPath[]): Promise<KDocument<TKDocumentContent>>;
|
|
147
154
|
/**
|
|
148
155
|
* Edit the document : replace content of field given by nestedField with content pointed
|
|
149
156
|
* @param document : document to edit
|
|
@@ -370,6 +370,15 @@ class RelationalController extends kuzzle_plugin_commons_1.CRUDController {
|
|
|
370
370
|
*/
|
|
371
371
|
async genericGet(index, collection, documentId, nestedFields = []) {
|
|
372
372
|
const document = await this.sdk.document.get(index, collection, documentId);
|
|
373
|
+
return this.esDocumentToFormatted(index, collection, document, nestedFields);
|
|
374
|
+
}
|
|
375
|
+
/**
|
|
376
|
+
* @param index
|
|
377
|
+
* @param collection
|
|
378
|
+
* @param documentId
|
|
379
|
+
* @param nestedFields : contain field name in the document to get, collection name and index name of documents that are linked
|
|
380
|
+
*/
|
|
381
|
+
async esDocumentToFormatted(index, collection, document, nestedFields = []) {
|
|
373
382
|
const promises = [];
|
|
374
383
|
for (const nestedField of nestedFields) {
|
|
375
384
|
promises.push(this.replaceNestedFieldByContent(document, nestedField));
|
package/lib/controllers/index.js
CHANGED
|
@@ -16,5 +16,5 @@ var __exportStar = (this && this.__exportStar) || function(m, exports) {
|
|
|
16
16
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
17
17
|
__exportStar(require("./AssetController"), exports);
|
|
18
18
|
__exportStar(require("./DeviceController"), exports);
|
|
19
|
-
__exportStar(require("./
|
|
19
|
+
__exportStar(require("./DecoderController"), exports);
|
|
20
20
|
//# sourceMappingURL=index.js.map
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
import { MetadataContent } from '../types/MetadataContent';
|
|
2
2
|
import { AssetCategoryContent, FormattedMetadata, FormattedValue } from '../types/AssetCategoryContent';
|
|
3
|
-
import { JSONObject, Plugin } from 'kuzzle';
|
|
3
|
+
import { JSONObject, KDocument, Plugin } from 'kuzzle';
|
|
4
|
+
import { BaseAssetContent } from '../types';
|
|
4
5
|
export declare class AssetCategoryService {
|
|
5
6
|
private config;
|
|
6
7
|
private context;
|
|
@@ -15,6 +16,11 @@ export declare class AssetCategoryService {
|
|
|
15
16
|
getMetadataValue(metadataValues: FormattedMetadata[], name: string): FormattedMetadata;
|
|
16
17
|
formatValue(value: any): FormattedValue;
|
|
17
18
|
formatMetadataForES(assetMetadata: JSONObject): FormattedMetadata[];
|
|
19
|
+
/**
|
|
20
|
+
* edit the document to format metadata
|
|
21
|
+
* @param document
|
|
22
|
+
*/
|
|
23
|
+
formatDocumentMetadata(document: KDocument<BaseAssetContent>): KDocument<BaseAssetContent>;
|
|
18
24
|
formatMetadataForGet(assetMetadata: FormattedMetadata[]): JSONObject;
|
|
19
25
|
getValue(value: FormattedValue, format?: boolean): string | number | boolean | JSONObject;
|
|
20
26
|
}
|
|
@@ -148,6 +148,18 @@ class AssetCategoryService {
|
|
|
148
148
|
}
|
|
149
149
|
return formattedMetadata;
|
|
150
150
|
}
|
|
151
|
+
/**
|
|
152
|
+
* edit the document to format metadata
|
|
153
|
+
* @param document
|
|
154
|
+
*/
|
|
155
|
+
formatDocumentMetadata(document) {
|
|
156
|
+
const metadata = document._source.metadata;
|
|
157
|
+
if (metadata) {
|
|
158
|
+
const asset = document._source;
|
|
159
|
+
asset.metadata = this.formatMetadataForGet(metadata);
|
|
160
|
+
}
|
|
161
|
+
return document;
|
|
162
|
+
}
|
|
151
163
|
formatMetadataForGet(assetMetadata) {
|
|
152
164
|
const formattedMetadata = {};
|
|
153
165
|
for (const metadata of assetMetadata) {
|
|
@@ -28,7 +28,7 @@ export declare class AssetService {
|
|
|
28
28
|
errors: any[];
|
|
29
29
|
successes: any[];
|
|
30
30
|
}>;
|
|
31
|
-
|
|
31
|
+
get(engineId: string, assetId: string): Promise<BaseAsset>;
|
|
32
32
|
removeMeasures(engineId: string, assetId: string, assetMeasureNames: string[], { strict }: {
|
|
33
33
|
strict?: boolean;
|
|
34
34
|
}): Promise<{
|
|
@@ -28,7 +28,7 @@ class AssetService {
|
|
|
28
28
|
* @param options.endAt Returns measures until this date (ISO8601)
|
|
29
29
|
*/
|
|
30
30
|
async measureHistory(engineId, assetId, { size = 25, startAt, endAt }) {
|
|
31
|
-
await this.
|
|
31
|
+
await this.get(engineId, assetId);
|
|
32
32
|
const query = {
|
|
33
33
|
range: {
|
|
34
34
|
measuredAt: {
|
|
@@ -68,12 +68,12 @@ class AssetService {
|
|
|
68
68
|
});
|
|
69
69
|
return results;
|
|
70
70
|
}
|
|
71
|
-
async
|
|
71
|
+
async get(engineId, assetId) {
|
|
72
72
|
const document = await this.sdk.document.get(engineId, InternalCollection_1.InternalCollection.ASSETS, assetId);
|
|
73
73
|
return new BaseAsset_1.BaseAsset(document._source, document._id);
|
|
74
74
|
}
|
|
75
75
|
async removeMeasures(engineId, assetId, assetMeasureNames, { strict }) {
|
|
76
|
-
const asset = await this.
|
|
76
|
+
const asset = await this.get(engineId, assetId);
|
|
77
77
|
const result = asset.removeMeasures(assetMeasureNames);
|
|
78
78
|
if (strict && result.notFound.length) {
|
|
79
79
|
throw new kuzzle_1.NotFoundError(`AssetMeasureNames "${result.notFound}" in asset "${assetId}" of engine "${engineId}"`);
|
|
@@ -1,11 +1,13 @@
|
|
|
1
1
|
import { HttpRoute, JSONObject, KuzzleRequest } from 'kuzzle';
|
|
2
2
|
import { DecodedPayload } from '../types/DecodedPayload';
|
|
3
3
|
import { DecoderContent } from '../types';
|
|
4
|
-
import { MeasuresRegister } from './registers/MeasuresRegister';
|
|
5
4
|
/**
|
|
6
|
-
*
|
|
5
|
+
* Array of measures declaration
|
|
7
6
|
*/
|
|
8
|
-
export declare type DecoderMeasures =
|
|
7
|
+
export declare type DecoderMeasures<T = string> = ReadonlyArray<{
|
|
8
|
+
name: T;
|
|
9
|
+
type: string;
|
|
10
|
+
}>;
|
|
9
11
|
/**
|
|
10
12
|
* Base class to implement a decoder for a device model.
|
|
11
13
|
* The device model must be passed to the parent constructor.
|
|
@@ -14,13 +16,24 @@ export declare type DecoderMeasures = Record<string, string>;
|
|
|
14
16
|
export declare abstract class Decoder {
|
|
15
17
|
private _http?;
|
|
16
18
|
/**
|
|
17
|
-
* Device model name
|
|
19
|
+
* Device model name.
|
|
20
|
+
*
|
|
21
|
+
* Will be infered from the class name if not defined:
|
|
22
|
+
* `AbeewayGPSDecoder` => `AbeewayGPS`
|
|
18
23
|
*/
|
|
19
24
|
deviceModel: string;
|
|
20
25
|
/**
|
|
21
|
-
*
|
|
26
|
+
* Declaration of the measures decoded by this decoder.
|
|
27
|
+
* The name correspond of the measure name for the device.
|
|
28
|
+
* Measures types should be registered on the plugin beforehand.
|
|
29
|
+
*
|
|
30
|
+
* @example
|
|
31
|
+
*
|
|
32
|
+
* this.measures = [
|
|
33
|
+
* { type: 'temperature', name: 'temperatureExterior' },
|
|
34
|
+
* ];
|
|
22
35
|
*/
|
|
23
|
-
|
|
36
|
+
measures: DecoderMeasures;
|
|
24
37
|
/**
|
|
25
38
|
* Custom name for the associated API action in the "payload" controller
|
|
26
39
|
*/
|
|
@@ -31,6 +44,7 @@ export declare abstract class Decoder {
|
|
|
31
44
|
* the device model unique identifier field.
|
|
32
45
|
*
|
|
33
46
|
* @example
|
|
47
|
+
*
|
|
34
48
|
* this.payloadsMappings = {
|
|
35
49
|
* device_properties: {
|
|
36
50
|
* properties: {
|
|
@@ -47,14 +61,8 @@ export declare abstract class Decoder {
|
|
|
47
61
|
*/
|
|
48
62
|
set http(http: HttpRoute[]);
|
|
49
63
|
get http(): HttpRoute[];
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
* @param decoderMeasures Measures created by this decoder
|
|
53
|
-
*
|
|
54
|
-
* @example
|
|
55
|
-
* super('AbeewayGPS', ['position']);
|
|
56
|
-
*/
|
|
57
|
-
constructor(deviceModel: string, decoderMeasures: DecoderMeasures, measuresRegister: MeasuresRegister);
|
|
64
|
+
get measureNames(): string[];
|
|
65
|
+
get measureTypes(): string[];
|
|
58
66
|
/**
|
|
59
67
|
* Validate the payload format before processing.
|
|
60
68
|
*
|
|
@@ -79,7 +87,7 @@ export declare abstract class Decoder {
|
|
|
79
87
|
*
|
|
80
88
|
* @returns Map of `Measurements` by device reference.
|
|
81
89
|
*/
|
|
82
|
-
abstract decode(payload: JSONObject, request: KuzzleRequest): Promise<DecodedPayload
|
|
90
|
+
abstract decode(payload: JSONObject, request: KuzzleRequest): Promise<DecodedPayload<Decoder>>;
|
|
83
91
|
/**
|
|
84
92
|
* Checks if the provided properties are present in the payload
|
|
85
93
|
*
|
|
@@ -12,20 +12,26 @@ const lodash_1 = __importDefault(require("lodash"));
|
|
|
12
12
|
* The abstract "decode" method must be implemented.
|
|
13
13
|
*/
|
|
14
14
|
class Decoder {
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
15
|
+
constructor() {
|
|
16
|
+
/**
|
|
17
|
+
* Declaration of the measures decoded by this decoder.
|
|
18
|
+
* The name correspond of the measure name for the device.
|
|
19
|
+
* Measures types should be registered on the plugin beforehand.
|
|
20
|
+
*
|
|
21
|
+
* @example
|
|
22
|
+
*
|
|
23
|
+
* this.measures = [
|
|
24
|
+
* { type: 'temperature', name: 'temperatureExterior' },
|
|
25
|
+
* ];
|
|
26
|
+
*/
|
|
27
|
+
this.measures = [];
|
|
23
28
|
/**
|
|
24
29
|
* Custom mappings for the payload collection.
|
|
25
30
|
* It will be injected in the "payload" property and it should allows to index
|
|
26
31
|
* the device model unique identifier field.
|
|
27
32
|
*
|
|
28
33
|
* @example
|
|
34
|
+
*
|
|
29
35
|
* this.payloadsMappings = {
|
|
30
36
|
* device_properties: {
|
|
31
37
|
* properties: {
|
|
@@ -35,13 +41,6 @@ class Decoder {
|
|
|
35
41
|
* }
|
|
36
42
|
*/
|
|
37
43
|
this.payloadsMappings = {};
|
|
38
|
-
this.deviceModel = deviceModel;
|
|
39
|
-
for (const [measureName, measureType] of Object.entries(decoderMeasures)) {
|
|
40
|
-
if (!measuresRegister.has(measureType)) {
|
|
41
|
-
throw new kuzzle_1.PluginImplementationError(`Decoder "${this.constructor.name}" cannot register unknown measure type "${measureType}"`);
|
|
42
|
-
}
|
|
43
|
-
}
|
|
44
|
-
this.decoderMeasures = decoderMeasures;
|
|
45
44
|
}
|
|
46
45
|
/**
|
|
47
46
|
* Define custom HTTP routes
|
|
@@ -57,6 +56,12 @@ class Decoder {
|
|
|
57
56
|
}
|
|
58
57
|
return this._http;
|
|
59
58
|
}
|
|
59
|
+
get measureNames() {
|
|
60
|
+
return this.measures.map(({ name }) => name);
|
|
61
|
+
}
|
|
62
|
+
get measureTypes() {
|
|
63
|
+
return this.measures.map(({ type }) => type);
|
|
64
|
+
}
|
|
60
65
|
/**
|
|
61
66
|
* Validate the payload format before processing.
|
|
62
67
|
*
|
|
@@ -91,8 +96,8 @@ class Decoder {
|
|
|
91
96
|
}
|
|
92
97
|
serialize() {
|
|
93
98
|
return {
|
|
94
|
-
decoderMeasures: this.decoderMeasures,
|
|
95
99
|
deviceModel: this.deviceModel,
|
|
100
|
+
measures: this.measures,
|
|
96
101
|
};
|
|
97
102
|
}
|
|
98
103
|
}
|
|
@@ -71,10 +71,8 @@ export declare class DeviceService {
|
|
|
71
71
|
* isn't specified, it will be auto generated with the
|
|
72
72
|
* `deviceMeasureNames` of the associated decoder
|
|
73
73
|
*
|
|
74
|
-
* @param {object} linkRequest Link request between an asset by Id and a device
|
|
75
74
|
* @param linkRequest.assetId Asset id to link to
|
|
76
75
|
* @param linkRequest.deviceLink The link with the device
|
|
77
|
-
* @param {object} options
|
|
78
76
|
* @param options.refresh Wait for ES indexation
|
|
79
77
|
* @param options.strict If true, throw if an operation isn't possible
|
|
80
78
|
*/
|
|
@@ -45,7 +45,7 @@ class DeviceService {
|
|
|
45
45
|
let asset;
|
|
46
46
|
if (linkRequest) {
|
|
47
47
|
try {
|
|
48
|
-
asset = await this.assetService.
|
|
48
|
+
asset = await this.assetService.get(engineId, linkRequest.assetId);
|
|
49
49
|
device.linkToAsset(linkRequest);
|
|
50
50
|
asset.linkToDevice(linkRequest);
|
|
51
51
|
}
|
|
@@ -137,10 +137,8 @@ class DeviceService {
|
|
|
137
137
|
* isn't specified, it will be auto generated with the
|
|
138
138
|
* `deviceMeasureNames` of the associated decoder
|
|
139
139
|
*
|
|
140
|
-
* @param {object} linkRequest Link request between an asset by Id and a device
|
|
141
140
|
* @param linkRequest.assetId Asset id to link to
|
|
142
141
|
* @param linkRequest.deviceLink The link with the device
|
|
143
|
-
* @param {object} options
|
|
144
142
|
* @param options.refresh Wait for ES indexation
|
|
145
143
|
* @param options.strict If true, throw if an operation isn't possible
|
|
146
144
|
*/
|
|
@@ -157,21 +155,16 @@ class DeviceService {
|
|
|
157
155
|
if (device._source.assetId) {
|
|
158
156
|
throw new kuzzle_1.BadRequestError(`Device "${device._id}" is already linked to an asset.`);
|
|
159
157
|
}
|
|
160
|
-
const asset = await this.assetService.
|
|
158
|
+
const asset = await this.assetService.get(deviceEngineId, assetId);
|
|
161
159
|
if (!asset) {
|
|
162
160
|
throw new kuzzle_1.BadRequestError(`Asset "${asset._id}" does not exist.`);
|
|
163
161
|
}
|
|
164
162
|
if (!deviceLink.measureNamesLinks.length) {
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
return {
|
|
171
|
-
assetMeasureName: deviceMeasureName,
|
|
172
|
-
deviceMeasureName,
|
|
173
|
-
};
|
|
174
|
-
});
|
|
163
|
+
const decoder = this.decodersRegister.get(device._source.model);
|
|
164
|
+
deviceLink.measureNamesLinks = decoder.measureNames.map(name => ({
|
|
165
|
+
assetMeasureName: name,
|
|
166
|
+
deviceMeasureName: name,
|
|
167
|
+
}));
|
|
175
168
|
}
|
|
176
169
|
device.linkToAsset({ assetId, deviceLink, engineId });
|
|
177
170
|
asset.linkToDevice({ assetId, deviceLink, engineId });
|
|
@@ -205,7 +198,7 @@ class DeviceService {
|
|
|
205
198
|
if (!device._source.assetId) {
|
|
206
199
|
throw new kuzzle_1.BadRequestError(`Device "${device._id}" is not linked to an asset.`);
|
|
207
200
|
}
|
|
208
|
-
const asset = await this.assetService.
|
|
201
|
+
const asset = await this.assetService.get(engineId, device._source.assetId);
|
|
209
202
|
asset.unlinkDevice(device);
|
|
210
203
|
device.unlinkToAsset();
|
|
211
204
|
const response = await this.app.trigger(`${eventId}:before`, { asset, device });
|
|
@@ -22,15 +22,16 @@ export declare class MeasureService {
|
|
|
22
22
|
* @param deviceModel Model of the device
|
|
23
23
|
* @param decodedPayloads `decodedPayload`
|
|
24
24
|
* @param payloadUuids Payload Uuids that generated the measurements
|
|
25
|
-
* @param
|
|
26
|
-
* @param options.provisionDevice If true and a `decodedPayload`
|
|
27
|
-
* reference a nonexisting device, create this device
|
|
25
|
+
* @param options.provisionDevice If true and a `decodedPayload` reference a nonexisting device, create this device
|
|
28
26
|
* @param options.refresh Wait for ES indexation
|
|
29
27
|
*/
|
|
30
|
-
processDecodedPayload(deviceModel: string,
|
|
28
|
+
processDecodedPayload(deviceModel: string, decodedPayload: DecodedPayload, payloadUuids: string[], options: {
|
|
31
29
|
refresh?: string;
|
|
32
30
|
}): Promise<void>;
|
|
33
31
|
private buildMeasures;
|
|
32
|
+
/**
|
|
33
|
+
* Get devices or create missing ones (when auto-provisionning is enabled)
|
|
34
|
+
*/
|
|
34
35
|
private getDevices;
|
|
35
36
|
private provisionDevices;
|
|
36
37
|
/**
|
|
@@ -59,7 +60,7 @@ export declare class MeasureService {
|
|
|
59
60
|
asset: () => JSONObject;
|
|
60
61
|
engineId: string;
|
|
61
62
|
invalids: JSONObject[];
|
|
62
|
-
valids: MeasureContent[];
|
|
63
|
+
valids: MeasureContent<JSONObject>[];
|
|
63
64
|
}>;
|
|
64
65
|
/**
|
|
65
66
|
* Register new measures in the engine
|