diff --git a/CHANGES_NEXT_RELEASE b/CHANGES_NEXT_RELEASE index 65ada9a75..854a262e1 100644 --- a/CHANGES_NEXT_RELEASE +++ b/CHANGES_NEXT_RELEASE @@ -1,2 +1,3 @@ - Fix: service header to use uppercase in case of update and delete (#1528) - Fix: Allow to send to CB batch update for multimeasures for NGSI-LD (#1623) +- Add: new JEXL transformations for including into an array keys that have a certain value: valuePicker and valuePickerMulti diff --git a/doc/api.md b/doc/api.md index c928422d4..76ce85c90 100644 --- a/doc/api.md +++ b/doc/api.md @@ -663,6 +663,9 @@ Current common transformation set: | localestring: (d, timezone, options) | `new Date(d).toLocaleString(timezone, options)` | | now: () | `Date.now()` | | hextostring: (val) | `new TextDecoder().decode(new Uint8Array(val.match(/.{1,2}/g).map(byte => parseInt(byte, 16))))` | +| valuePicker: (val,pick) | valuePicker: (val,pick) => Object.entries(val).filter(([_, v]) => v === pick).map(([k, _]) => k) | +| valuePickerMulti: (val,pick) | valuePickerMulti: (val,pick) => Object.entries(val).filter(([_, v]) => pick.includes(v)).map(([k, _]) => k) | + You have available this [JEXL interactive playground][99] with all the transformations already loaded, in which you can test all the functions described above. diff --git a/lib/jexlTranformsMap.js b/lib/jexlTranformsMap.js index b6031c035..89bc2ecd0 100644 --- a/lib/jexlTranformsMap.js +++ b/lib/jexlTranformsMap.js @@ -80,7 +80,9 @@ const map = { localestring: (d, timezone, options) => new Date(d).toLocaleString(timezone, options), now: () => Date.now(), hextostring: (val) => - new TextDecoder().decode(new Uint8Array(val.match(/.{1,2}/g).map((byte) => parseInt(byte, 16)))) + new TextDecoder().decode(new Uint8Array(val.match(/.{1,2}/g).map((byte) => parseInt(byte, 16)))), + valuePicker: (val,pick) => Object.entries(val).filter(([, v]) => v === pick).map(([k,]) => k), + valuePickerMulti: (val,pick) => Object.entries(val).filter(([, v]) => pick.includes(v)).map(([k,]) => k) }; exports.map = map; diff --git a/test/functional/testCases.js b/test/functional/testCases.js index da4d42216..bb3f51bec 100644 --- a/test/functional/testCases.js +++ b/test/functional/testCases.js @@ -4561,6 +4561,78 @@ const testCases = [ } } ] + }, + // 0900 - JEXL FUNCTION TESTS + { + describeName: '0900 - JEXL function - valuePicker and valuePickerMulti', + provision: { + url: 'http://localhost:' + config.iota.server.port + '/iot/services', + method: 'POST', + json: { + services: [ + { + resource: '/iot/json', + apikey: globalEnv.apikey, + entity_type: globalEnv.entity_type, + explicitAttrs: true, + commands: [], + lazy: [], + attributes: [ + { + object_id: 'single', + name: 'single', + type: 'Number', + expression: '{alarm1:alarm1,alarm2:alarm2,alarm3:alarm3}|valuePicker(true)' + }, + { + object_id: 'multi', + name: 'multi', + type: 'Number', + expression: "a|valuePickerMulti([true,1,'on','nok'])" + } + ], + static_attributes: [] + } + ] + }, + headers: { + 'fiware-service': globalEnv.service, + 'fiware-servicepath': globalEnv.servicePath + } + }, + should: [ + { + shouldName: + 'A - WHEN sending a boolean value (true) through http IT should send to Context Broker the value 3 ', + type: 'single', + measure: { + url: 'http://localhost:' + config.http.port + '/iot/json', + method: 'POST', + qs: { + i: globalEnv.deviceId, + k: globalEnv.apikey + }, + json: { + a: { n1: true, n2: 1, n3: 'on', n4: 'nok', n5: 'ok', n6: true, n7: false, n8: 0 }, + alarm1: true, + alarm2: false, + alarm3: true + } + }, + expectation: { + id: globalEnv.entity_name, + type: globalEnv.entity_type, + single: { + value: ['alarm1', 'alarm3'], + type: 'Number' + }, + multi: { + value: ['n1', 'n2', 'n3', 'n4', 'n6'], + type: 'Number' + } + } + } + ] } ];