unetjs 1.0.0 → 2.0.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.
package/dist/unetjs.js CHANGED
@@ -2,9 +2,9 @@
2
2
  typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports) :
3
3
  typeof define === 'function' && define.amd ? define(['exports'], factory) :
4
4
  (global = typeof globalThis !== 'undefined' ? globalThis : global || self, factory(global.unet = {}));
5
- }(this, (function (exports) { 'use strict';
5
+ })(this, (function (exports) { 'use strict';
6
6
 
7
- /* fjage.js v1.9.1-rc5 2021-07-07T04:07:53.061Z */
7
+ /* fjage.js v1.9.1-rc6 */
8
8
 
9
9
  /* global window self */
10
10
 
@@ -1275,6 +1275,8 @@
1275
1275
  'TRANSPORT': 'org.arl.unet.Services.TRANSPORT',
1276
1276
  'REMOTE': 'org.arl.unet.Services.REMOTE',
1277
1277
  'STATE_MANAGER': 'org.arl.unet.Services.STATE_MANAGER',
1278
+ 'DEVICE_INFO': 'org.arl.unet.Services.DEVICE_INFO',
1279
+ 'DOA': 'org.arl.unet.Services.DOA'
1278
1280
  };
1279
1281
 
1280
1282
  Object.assign(Services, UnetServices);
@@ -1303,100 +1305,361 @@
1303
1305
  */
1304
1306
  let UnetMessages = {
1305
1307
  // unet
1306
- 'TestReportNtf' : MessageClass('org.arl.unet.TestReportNtf'),
1307
- 'AbnormalTerminationNtf' : MessageClass('org.arl.unet.AbnormalTerminationNtf'),
1308
- 'CapabilityListRsp' : MessageClass('org.arl.unet.CapabilityListRsp'),
1309
- 'CapabilityReq' : MessageClass('org.arl.unet.CapabilityReq'),
1310
- 'ClearReq' : MessageClass('org.arl.unet.ClearReq'),
1311
- 'DatagramCancelReq' : MessageClass('org.arl.unet.DatagramCancelReq'),
1312
- 'DatagramDeliveryNtf' : MessageClass('org.arl.unet.DatagramDeliveryNtf'),
1313
- 'DatagramFailureNtf' : MessageClass('org.arl.unet.DatagramFailureNtf'),
1314
- 'DatagramNtf' : MessageClass('org.arl.unet.DatagramNtf'),
1315
- 'DatagramProgressNtf' : MessageClass('org.arl.unet.DatagramProgressNtf'),
1316
- 'DatagramReq' : MessageClass('org.arl.unet.DatagramReq'),
1317
- 'ParamChangeNtf' : MessageClass('org.arl.unet.ParamChangeNtf'),
1318
- 'RefuseRsp' : MessageClass('org.arl.unet.RefuseRsp'),
1319
- 'FailureNtf' : MessageClass('org.arl.unet.FailureNtf'),
1308
+ 'TestReportNtf' : MessageClass('org.arl.unet.TestReportNtf'),
1309
+ 'AbnormalTerminationNtf' : MessageClass('org.arl.unet.AbnormalTerminationNtf'),
1310
+ 'CapabilityListRsp' : MessageClass('org.arl.unet.CapabilityListRsp'),
1311
+ 'CapabilityReq' : MessageClass('org.arl.unet.CapabilityReq'),
1312
+ 'ClearReq' : MessageClass('org.arl.unet.ClearReq'),
1313
+ 'DatagramCancelReq' : MessageClass('org.arl.unet.DatagramCancelReq'),
1314
+ 'DatagramDeliveryNtf' : MessageClass('org.arl.unet.DatagramDeliveryNtf'),
1315
+ 'DatagramFailureNtf' : MessageClass('org.arl.unet.DatagramFailureNtf'),
1316
+ 'DatagramNtf' : MessageClass('org.arl.unet.DatagramNtf'),
1317
+ 'DatagramProgressNtf' : MessageClass('org.arl.unet.DatagramProgressNtf'),
1318
+ 'DatagramReq' : MessageClass('org.arl.unet.DatagramReq'),
1319
+ 'ParamChangeNtf' : MessageClass('org.arl.unet.ParamChangeNtf'),
1320
+ 'RefuseRsp' : MessageClass('org.arl.unet.RefuseRsp'),
1321
+ 'FailureNtf' : MessageClass('org.arl.unet.FailureNtf'),
1320
1322
 
1321
1323
  // net
1322
- 'DatagramTraceReq' : MessageClass('org.arl.unet.net.DatagramTraceReq'),
1323
- 'RouteDiscoveryReq' : MessageClass('org.arl.unet.net.RouteDiscoveryReq'),
1324
- 'RouteTraceReq' : MessageClass('org.arl.unet.net.RouteTraceReq'),
1325
- 'RouteDiscoveryNtf' : MessageClass('org.arl.unet.net.RouteDiscoveryNtf'),
1326
- 'RouteTraceNtf' : MessageClass('org.arl.unet.net.RouteTraceNtf'),
1324
+ 'DatagramTraceReq' : MessageClass('org.arl.unet.net.DatagramTraceReq'),
1325
+ 'RouteDiscoveryReq' : MessageClass('org.arl.unet.net.RouteDiscoveryReq'),
1326
+ 'RouteTraceReq' : MessageClass('org.arl.unet.net.RouteTraceReq'),
1327
+ 'RouteDiscoveryNtf' : MessageClass('org.arl.unet.net.RouteDiscoveryNtf'),
1328
+ 'RouteTraceNtf' : MessageClass('org.arl.unet.net.RouteTraceNtf'),
1327
1329
 
1328
1330
  // phy
1329
- 'FecDecodeReq' : MessageClass('org.arl.unet.phy.FecDecodeReq'),
1330
- 'RxJanusFrameNtf' : MessageClass('org.arl.unet.phy.RxJanusFrameNtf'),
1331
- 'TxJanusFrameReq' : MessageClass('org.arl.unet.phy.TxJanusFrameReq'),
1332
- 'BadFrameNtf' : MessageClass('org.arl.unet.phy.BadFrameNtf'),
1331
+ 'FecDecodeReq' : MessageClass('org.arl.unet.phy.FecDecodeReq'),
1332
+ 'RxJanusFrameNtf' : MessageClass('org.arl.unet.phy.RxJanusFrameNtf'),
1333
+ 'TxJanusFrameReq' : MessageClass('org.arl.unet.phy.TxJanusFrameReq'),
1334
+ 'BadFrameNtf' : MessageClass('org.arl.unet.phy.BadFrameNtf'),
1333
1335
  'BadRangeNtf' : MessageClass('org.arl.unet.phy.BadRangeNtf'),
1334
- 'ClearSyncReq' : MessageClass('org.arl.unet.phy.ClearSyncReq'),
1335
- 'CollisionNtf' : MessageClass('org.arl.unet.phy.CollisionNtf'),
1336
- 'RxFrameNtf' : MessageClass('org.arl.unet.phy.RxFrameNtf', DatagramNtf$1),
1337
- 'RxFrameStartNtf' : MessageClass('org.arl.unet.phy.RxFrameStartNtf'),
1338
- 'SyncInfoReq' : MessageClass('org.arl.unet.phy.SyncInfoReq'),
1339
- 'SyncInfoRsp' : MessageClass('org.arl.unet.phy.SyncInfoRsp'),
1340
- 'TxFrameNtf' : MessageClass('org.arl.unet.phy.TxFrameNtf'),
1341
- 'TxFrameReq' : MessageClass('org.arl.unet.phy.TxFrameReq', DatagramReq$1),
1342
- 'TxFrameStartNtf' : MessageClass('org.arl.unet.phy.TxFrameStartNtf'),
1343
- 'TxRawFrameReq' : MessageClass('org.arl.unet.phy.TxRawFrameReq'),
1336
+ 'ClearSyncReq' : MessageClass('org.arl.unet.phy.ClearSyncReq'),
1337
+ 'CollisionNtf' : MessageClass('org.arl.unet.phy.CollisionNtf'),
1338
+ 'RxFrameNtf' : MessageClass('org.arl.unet.phy.RxFrameNtf', DatagramNtf$1),
1339
+ 'RxFrameStartNtf' : MessageClass('org.arl.unet.phy.RxFrameStartNtf'),
1340
+ 'SyncInfoReq' : MessageClass('org.arl.unet.phy.SyncInfoReq'),
1341
+ 'SyncInfoRsp' : MessageClass('org.arl.unet.phy.SyncInfoRsp'),
1342
+ 'TxFrameNtf' : MessageClass('org.arl.unet.phy.TxFrameNtf'),
1343
+ 'TxFrameReq' : MessageClass('org.arl.unet.phy.TxFrameReq', DatagramReq$1),
1344
+ 'TxFrameStartNtf' : MessageClass('org.arl.unet.phy.TxFrameStartNtf'),
1345
+ 'TxRawFrameReq' : MessageClass('org.arl.unet.phy.TxRawFrameReq'),
1344
1346
 
1345
1347
  // addr
1346
- 'AddressAllocReq' : MessageClass('org.arl.unet.addr.AddressAllocReq'),
1347
- 'AddressAllocRsp' : MessageClass('org.arl.unet.addr.AddressAllocRsp'),
1348
- 'AddressResolutionReq' : MessageClass('org.arl.unet.addr.AddressResolutionReq'),
1349
- 'AddressResolutionRsp' : MessageClass('org.arl.unet.addr.AddressResolutionRsp'),
1348
+ 'AddressAllocReq' : MessageClass('org.arl.unet.addr.AddressAllocReq'),
1349
+ 'AddressAllocRsp' : MessageClass('org.arl.unet.addr.AddressAllocRsp'),
1350
+ 'AddressResolutionReq' : MessageClass('org.arl.unet.addr.AddressResolutionReq'),
1351
+ 'AddressResolutionRsp' : MessageClass('org.arl.unet.addr.AddressResolutionRsp'),
1350
1352
 
1351
1353
  // bb
1352
- 'BasebandSignal' : MessageClass('org.arl.unet.bb.BasebandSignal'),
1353
- 'RecordBasebandSignalReq' : MessageClass('org.arl.unet.bb.RecordBasebandSignalReq'),
1354
- 'RxBasebandSignalNtf' : MessageClass('org.arl.unet.bb.RxBasebandSignalNtf', BasebandSignal),
1355
- 'TxBasebandSignalReq' : MessageClass('org.arl.unet.bb.TxBasebandSignalReq', BasebandSignal),
1354
+ 'BasebandSignal' : MessageClass('org.arl.unet.bb.BasebandSignal'),
1355
+ 'RecordBasebandSignalReq' : MessageClass('org.arl.unet.bb.RecordBasebandSignalReq'),
1356
+ 'RxBasebandSignalNtf' : MessageClass('org.arl.unet.bb.RxBasebandSignalNtf', BasebandSignal),
1357
+ 'TxBasebandSignalReq' : MessageClass('org.arl.unet.bb.TxBasebandSignalReq', BasebandSignal),
1356
1358
 
1357
1359
  // link
1358
- 'LinkStatusNtf' : MessageClass('org.arl.unet.link.LinkStatusNtf'),
1360
+ 'LinkStatusNtf' : MessageClass('org.arl.unet.link.LinkStatusNtf'),
1359
1361
 
1360
1362
  // localization
1361
- 'RangeNtf' : MessageClass('org.arl.unet.localization.RangeNtf'),
1362
- 'RangeReq' : MessageClass('org.arl.unet.localization.RangeReq'),
1363
- 'BeaconReq' : MessageClass('org.arl.unet.localization.BeaconReq'),
1364
- 'RespondReq' : MessageClass('org.arl.unet.localization.RespondReq'),
1365
- 'InterrogationNtf' : MessageClass('org.arl.unet.localization.InterrogationNtf'),
1363
+ 'RangeNtf' : MessageClass('org.arl.unet.localization.RangeNtf'),
1364
+ 'RangeReq' : MessageClass('org.arl.unet.localization.RangeReq'),
1365
+ 'BeaconReq' : MessageClass('org.arl.unet.localization.BeaconReq'),
1366
+ 'RespondReq' : MessageClass('org.arl.unet.localization.RespondReq'),
1367
+ 'InterrogationNtf' : MessageClass('org.arl.unet.localization.InterrogationNtf'),
1366
1368
 
1367
1369
 
1368
1370
  // mac
1369
- 'ReservationAcceptReq' : MessageClass('org.arl.unet.mac.ReservationAcceptReq'),
1370
- 'ReservationCancelReq' : MessageClass('org.arl.unet.mac.ReservationCancelReq'),
1371
- 'ReservationReq' : MessageClass('org.arl.unet.mac.ReservationReq'),
1372
- 'ReservationRsp' : MessageClass('org.arl.unet.mac.ReservationRsp'),
1373
- 'ReservationStatusNtf' : MessageClass('org.arl.unet.mac.ReservationStatusNtf'),
1374
- 'RxAckNtf' : MessageClass('org.arl.unet.mac.RxAckNtf'),
1375
- 'TxAckReq' : MessageClass('org.arl.unet.mac.TxAckReq'),
1371
+ 'ReservationAcceptReq' : MessageClass('org.arl.unet.mac.ReservationAcceptReq'),
1372
+ 'ReservationCancelReq' : MessageClass('org.arl.unet.mac.ReservationCancelReq'),
1373
+ 'ReservationReq' : MessageClass('org.arl.unet.mac.ReservationReq'),
1374
+ 'ReservationRsp' : MessageClass('org.arl.unet.mac.ReservationRsp'),
1375
+ 'ReservationStatusNtf' : MessageClass('org.arl.unet.mac.ReservationStatusNtf'),
1376
+ 'RxAckNtf' : MessageClass('org.arl.unet.mac.RxAckNtf'),
1377
+ 'TxAckReq' : MessageClass('org.arl.unet.mac.TxAckReq'),
1376
1378
 
1377
1379
 
1378
1380
  // remote
1379
- 'RemoteExecReq' : MessageClass('org.arl.unet.remote.RemoteExecReq'),
1380
- 'RemoteFailureNtf' : MessageClass('org.arl.unet.remote.RemoteFailureNtf'),
1381
- 'RemoteFileGetReq' : MessageClass('org.arl.unet.remote.RemoteFileGetReq'),
1382
- 'RemoteFileNtf' : MessageClass('org.arl.unet.remote.RemoteFileNtf'),
1383
- 'RemoteFilePutReq' : MessageClass('org.arl.unet.remote.RemoteFilePutReq'),
1384
- 'RemoteSuccessNtf' : MessageClass('org.arl.unet.remote.RemoteSuccessNtf'),
1385
- 'RemoteTextNtf' : MessageClass('org.arl.unet.remote.RemoteTextNtf'),
1386
- 'RemoteTextReq' : MessageClass('org.arl.unet.remote.RemoteTextReq'),
1381
+ 'RemoteExecReq' : MessageClass('org.arl.unet.remote.RemoteExecReq'),
1382
+ 'RemoteFailureNtf' : MessageClass('org.arl.unet.remote.RemoteFailureNtf'),
1383
+ 'RemoteFileGetReq' : MessageClass('org.arl.unet.remote.RemoteFileGetReq'),
1384
+ 'RemoteFileNtf' : MessageClass('org.arl.unet.remote.RemoteFileNtf'),
1385
+ 'RemoteFilePutReq' : MessageClass('org.arl.unet.remote.RemoteFilePutReq'),
1386
+ 'RemoteSuccessNtf' : MessageClass('org.arl.unet.remote.RemoteSuccessNtf'),
1387
+ 'RemoteTextNtf' : MessageClass('org.arl.unet.remote.RemoteTextNtf'),
1388
+ 'RemoteTextReq' : MessageClass('org.arl.unet.remote.RemoteTextReq'),
1387
1389
 
1388
1390
  // scheduler
1389
- 'AddScheduledSleepReq' : MessageClass('org.arl.unet.scheduler.AddScheduledSleepReq'),
1390
- 'GetSleepScheduleReq' : MessageClass('org.arl.unet.scheduler.GetSleepScheduleReq'),
1391
- 'RemoveScheduledSleepReq' : MessageClass('org.arl.unet.scheduler.RemoveScheduledSleepReq'),
1392
- 'SleepScheduleRsp' : MessageClass('org.arl.unet.scheduler.SleepScheduleRsp'),
1393
- 'WakeFromSleepNtf' : MessageClass('org.arl.unet.scheduler.WakeFromSleepNtf'),
1391
+ 'AddScheduledSleepReq' : MessageClass('org.arl.unet.scheduler.AddScheduledSleepReq'),
1392
+ 'GetSleepScheduleReq' : MessageClass('org.arl.unet.scheduler.GetSleepScheduleReq'),
1393
+ 'RemoveScheduledSleepReq' : MessageClass('org.arl.unet.scheduler.RemoveScheduledSleepReq'),
1394
+ 'SleepScheduleRsp' : MessageClass('org.arl.unet.scheduler.SleepScheduleRsp'),
1395
+ 'WakeFromSleepNtf' : MessageClass('org.arl.unet.scheduler.WakeFromSleepNtf'),
1394
1396
 
1395
1397
  // state
1396
- 'ClearStateReq' : MessageClass('org.arl.unet.state.ClearStateReq'),
1398
+ 'ClearStateReq' : MessageClass('org.arl.unet.state.ClearStateReq'),
1397
1399
  'SaveStateReq' : MessageClass('org.arl.unet.state.SaveStateReq')
1398
1400
  };
1399
1401
 
1402
+ /**
1403
+ * Convert coordinates from a local coordinates to GPS coordinate
1404
+ * @param {Array} origin - Local coordinate system's origin as `[latitude, longitude]`
1405
+ * @param {Number} x - X coordinate of the local coordinate to be converted
1406
+ * @param {Number} y - Y coordinate of the local coordinate to be converted
1407
+ * @returns {Array} - GPS coordinates (in decimal degrees) as `[latitude, longitude]`
1408
+ */
1409
+
1410
+ function toGps(origin, x, y) {
1411
+ let coords = [] ;
1412
+ let [xScale,yScale] = _initConv(origin[0]);
1413
+ coords[1] = x/xScale + origin[1];
1414
+ coords[0] = y/yScale + origin[0];
1415
+ return coords;
1416
+ }
1417
+
1418
+ /**
1419
+ * Convert coordinates from a GPS coordinates to local coordinate
1420
+ * @param {Array} origin - Local coordinate system's origin as `[latitude, longitude]`
1421
+ * @param {Number} lat - Latitude of the GPS coordinate to be converted
1422
+ * @param {Number} lon - Longitude of the GPS coordinate to be converted
1423
+ * @returns {Array} - GPS coordinates (in decimal degrees) as `[latitude, longitude]`
1424
+ */
1425
+ function toLocal(origin, lat, lon) {
1426
+ let pos = [];
1427
+ let [xScale,yScale] = _initConv(origin[0]);
1428
+ pos[0] = (lon-origin[1]) * xScale;
1429
+ pos[1] = (lat-origin[0]) * yScale;
1430
+ return pos;
1431
+ }
1432
+
1433
+ function _initConv(lat){
1434
+ let rlat = lat * Math.PI/180;
1435
+ let yScale = 111132.92 - 559.82*Math.cos(2*rlat) + 1.175*Math.cos(4*rlat) - 0.0023*Math.cos(6*rlat);
1436
+ let xScale = 111412.84*Math.cos(rlat) - 93.5*Math.cos(3*rlat) + 0.118*Math.cos(5*rlat);
1437
+ return [xScale, yScale];
1438
+ }
1439
+
1440
+ /**
1441
+ * A message which requests the transmission of the datagram from the Unet
1442
+ *
1443
+ * @typedef {Message} DatagramReq
1444
+ * @property {number[]} data - data as an Array of bytes
1445
+ * @property {number} from - from/source node address
1446
+ * @property {number} to - to/destination node address
1447
+ * @property {number} protocol - protocol number to be used to send this Datagram
1448
+ * @property {boolean} reliability - true if Datagram should be reliable, false if unreliable
1449
+ * @property {number} ttl - time-to-live for the datagram. Time-to-live is advisory, and an agent may choose it ignore it
1450
+ */
1451
+
1452
+ /**
1453
+ * Notification of received datagram message received by the Unet node.
1454
+ *
1455
+ * @typedef {Message} DatagramNtf
1456
+ * @property {number[]} data - data as an Array of bytes
1457
+ * @property {number} from - from/source node address
1458
+ * @property {number} to - to/destination node address
1459
+ * @property {number} protocol - protocol number to be used to send this Datagram
1460
+ * @property {number} ttl - time-to-live for the datagram. Time-to-live is advisory, and an agent may choose it ignore it
1461
+ */
1462
+
1463
+ /**
1464
+ * An identifier for an agent or a topic.
1465
+ * @external AgentID
1466
+ * @see {@link https://org-arl.github.io/fjage/jsdoc/|fjåge.js Documentation}
1467
+ */
1468
+
1469
+ /**
1470
+ * Services supported by fjage agents.
1471
+ * @external Services
1472
+ * @see {@link https://org-arl.github.io/fjage/jsdoc/|fjåge.js Documentation}
1473
+ */
1474
+
1475
+ /**
1476
+ * An action represented by a message.
1477
+ * @external Performative
1478
+ * @see {@link https://org-arl.github.io/fjage/jsdoc/|fjåge.js Documentation}
1479
+ */
1480
+
1481
+ /**
1482
+ * Function to creates a unqualified message class based on a fully qualified name.
1483
+ * @external MessageClass
1484
+ * @see {@link https://org-arl.github.io/fjage/jsdoc/|fjåge.js Documentation}
1485
+ */
1486
+
1487
+ /**
1488
+ * A caching CachingAgentID which caches Agent parameters locally.
1489
+ *
1490
+ * @class
1491
+ * @extends AgentID
1492
+ * @param {string | AgentID} name - name of the agent or an AgentID to copy
1493
+ * @param {boolean} topic - name of topic
1494
+ * @param {Gateway} owner - Gateway owner for this AgentID
1495
+ * @param {Boolean} [greedy=true] - greedily fetches and caches all parameters if this Agent
1496
+ *
1497
+ */
1498
+ class CachingAgentID extends AgentID {
1499
+
1500
+ constructor(name, topic, owner, greedy=true) {
1501
+ if (name instanceof AgentID) {
1502
+ super(name.getName(), name.topic, name.owner);
1503
+ } else {
1504
+ super(name, topic, owner);
1505
+ }
1506
+ this.greedy = greedy;
1507
+ this.cache = {};
1508
+ }
1509
+
1510
+ /**
1511
+ * Sets parameter(s) on the Agent referred to by this AgentID, and caches the parameter(s).
1512
+ *
1513
+ * @param {(string|string[])} params - parameters name(s) to be set
1514
+ * @param {(Object|Object[])} values - parameters value(s) to be set
1515
+ * @param {number} [index=-1] - index of parameter(s) to be set
1516
+ * @param {number} [timeout=5000] - timeout for the response
1517
+ * @returns {Promise<(Object|Object[])>} - a promise which returns the new value(s) of the parameters
1518
+ */
1519
+ async set(params, values, index=-1, timeout=5000) {
1520
+ let s = await super.set(params, values, index, timeout);
1521
+ this._updateCache(params, s, index);
1522
+ }
1523
+
1524
+ /**
1525
+ * Gets parameter(s) on the Agent referred to by this AgentID, getting them from the cache if possible.
1526
+ *
1527
+ * @param {(string|string[])} params - parameters name(s) to be fetched
1528
+ * @param {number} [index=-1] - index of parameter(s) to be fetched
1529
+ * @param {number} [timeout=5000] - timeout for the response
1530
+ * @param {number} [maxage=5000] - maximum age of the cached result to retreive
1531
+ * @returns {Promise<(Object|Object[])>} - a promise which returns the value(s) of the parameters
1532
+ */
1533
+ async get(params, index=-1, timeout=5000, maxage=5000) {
1534
+ if (this._isCached(params, index, maxage)) return this._getCache(params, index);
1535
+ if (this.greedy && !(Array.isArray(params) && params.includes('name')) && params != 'name') {
1536
+ let rsp = await super.get(null, index, timeout);
1537
+ this._updateCache(null, rsp, index);
1538
+ if (Array.isArray(params)) {
1539
+ return params.map(p => {
1540
+ let f = Object.keys(rsp).find(rv => this._toNamed(rv) === p);
1541
+ return f ? rsp[f] : null;
1542
+ });
1543
+ } else {
1544
+ let f = Object.keys(rsp).find(rv => this._toNamed(rv) === params);
1545
+ return f ? rsp[f] : null;
1546
+ }
1547
+ } else {
1548
+ let r = await super.get(params, index, timeout);
1549
+ this._updateCache(params, r, index);
1550
+ return r;
1551
+ }
1552
+ }
1553
+
1554
+ _updateCache(params, vals, index) {
1555
+ if (vals == null || Array.isArray(vals) && vals.every(v => v == null)) return;
1556
+ if (params == null) {
1557
+ params = Object.keys(vals);
1558
+ vals = Object.values(vals);
1559
+ } else if (!Array.isArray(params)) params = [params];
1560
+ if (!Array.isArray(vals)) vals = [vals];
1561
+ params = params.map(this._toNamed);
1562
+ if (this.cache[index.toString()] === undefined) this.cache[index.toString()] = {};
1563
+ let c = this.cache[index.toString()];
1564
+ for (let i = 0; i < params.length; i++) {
1565
+ if (c[params[i]] === undefined) c[params[i]] = {};
1566
+ c[params[i]].value = vals[i];
1567
+ c[params[i]].ctime = Date.now();
1568
+ }
1569
+ }
1570
+
1571
+ _isCached(params, index, maxage) {
1572
+ if (maxage <= 0) return false;
1573
+ if (params == null) return false;
1574
+ let c = this.cache[index.toString()];
1575
+ if (!c) {
1576
+ return false;
1577
+ }
1578
+ if (!Array.isArray(params)) params = [params];
1579
+ const rv = params.every(p => {
1580
+ p = this._toNamed(p);
1581
+ return (p in c) && (Date.now() - c[p].ctime <= maxage);
1582
+ });
1583
+ return rv;
1584
+ }
1585
+
1586
+ _getCache(params, index) {
1587
+ let c = this.cache[index.toString()];
1588
+ if (!c) return null;
1589
+ if (!Array.isArray(params)){
1590
+ if (params in c) return c[params].value;
1591
+ return null;
1592
+ }else {
1593
+ return params.map(p => p in c ? c[p].value : null);
1594
+ }
1595
+ }
1596
+
1597
+ _toNamed(param) {
1598
+ const idx = param.lastIndexOf('.');
1599
+ if (idx < 0) return param;
1600
+ else return param.slice(idx+1);
1601
+ }
1602
+
1603
+ }
1604
+
1605
+
1606
+ class CachingGateway extends Gateway{
1607
+
1608
+ /**
1609
+ * Get an AgentID for a given agent name.
1610
+ *
1611
+ * @param {string} name - name of agent
1612
+ * @param {Boolean} [caching=true] - if the AgentID should cache parameters
1613
+ * @param {Boolean} [greedy=true] - greedily fetches and caches all parameters if this Agent
1614
+ * @returns {AgentID|CachingAgentID} - AgentID for the given name
1615
+ */
1616
+ agent(name, caching=true, greedy=true) {
1617
+ const aid = super.agent(name);
1618
+ return caching ? new CachingAgentID(aid, null, null, greedy) : aid;
1619
+ }
1620
+
1621
+ /**
1622
+ * Returns an object representing the named topic.
1623
+ *
1624
+ * @param {string|AgentID} topic - name of the topic or AgentID
1625
+ * @param {string} topic2 - name of the topic if the topic param is an AgentID
1626
+ * @param {Boolean} [caching=true] - if the AgentID should cache parameters
1627
+ * @param {Boolean} [greedy=true] - greedily fetches and caches all parameters if this Agent
1628
+ * @returns {AgentID|CachingAgentID} - object representing the topic
1629
+ */
1630
+ topic(topic, topic2, caching=true, greedy=true) {
1631
+ const aid = super.topic(topic, topic2);
1632
+ return caching ? new CachingAgentID(aid, null, null, greedy) : aid;
1633
+ }
1634
+
1635
+ /**
1636
+ * Finds an agent that provides a named service. If multiple agents are registered
1637
+ * to provide a given service, any of the agents' id may be returned.
1638
+ *
1639
+ * @param {string} service - the named service of interest
1640
+ * @param {Boolean} [caching=true] - if the AgentID should cache parameters
1641
+ * @param {Boolean} [greedy=true] - greedily fetches and caches all parameters if this Agent
1642
+ * @returns {Promise<?AgentID|CachingAgentID>} - a promise which returns an agent id for an agent that provides the service when resolved
1643
+ */
1644
+ async agentForService(service, caching=true, greedy=true) {
1645
+ const aid = await super.agentForService(service);
1646
+ return caching ? new CachingAgentID(aid, null, null, greedy) : aid;
1647
+ }
1648
+
1649
+ /**
1650
+ * Finds all agents that provides a named service.
1651
+ *
1652
+ * @param {string} service - the named service of interest
1653
+ * @param {Boolean} [caching=true] - if the AgentID should cache parameters
1654
+ * @param {Boolean} [greedy=true] - greedily fetches and caches all parameters if this Agent
1655
+ * @returns {Promise<?AgentID|CachingAgentID[]>} - a promise which returns an array of all agent ids that provides the service when resolved
1656
+ */
1657
+ async agentsForService(service, caching=true, greedy=true) {
1658
+ const aids = await super.agentsForService(service);
1659
+ return caching ? aids.map(a => new CachingAgentID(a, null, null, greedy)) : aids;
1660
+ }
1661
+ }
1662
+
1400
1663
  const REQUEST_TIMEOUT = 1000;
1401
1664
 
1402
1665
  const AddressResolutionReq = UnetMessages.AddressResolutionReq;
@@ -1405,26 +1668,26 @@
1405
1668
  const RxFrameNtf = UnetMessages.RxFrameNtf;
1406
1669
 
1407
1670
  /**
1408
- * Creates a new UnetSocket to connect to a running Unet instance. This constructor returns a
1409
- * {@link Promise} instead of the constructed UnetSocket object. Use `await` or `.then()` to get
1410
- * a reference to the UnetSocket object. Based on if this is run in a Browser or Node.js,
1671
+ * Creates a new UnetSocket to connect to a running Unet instance. This constructor returns a
1672
+ * {@link Promise} instead of the constructed UnetSocket object. Use `await` or `.then()` to get
1673
+ * a reference to the UnetSocket object. Based on if this is run in a Browser or Node.js,
1411
1674
  * it will internally connect over WebSockets or TCP respectively.
1412
1675
  *
1413
- *
1676
+ *
1414
1677
  * @class UnetSocket
1415
1678
  * @param {string} [hostname] - hostname/ip address of the master container to connect to
1416
1679
  * @param {number} [port] - port number of the master container to connect to
1417
1680
  * @param {string} [path=''] - path of the master container to connect to (for WebSockets)
1418
1681
  * @returns {Promise<UnetSocket>} - Promise which resolves to the UnetSocket object being constructed
1419
- *
1682
+ *
1420
1683
  * @example
1421
1684
  * let socket = await new UnetSocket('localhost', 8081, '/ws/');
1422
1685
  */
1423
1686
  class UnetSocket {
1424
1687
 
1425
- constructor(hostname, port, path='') {
1688
+ constructor(hostname, port, path='') {
1426
1689
  return (async () => {
1427
- this.gw = new Gateway({
1690
+ this.gw = new CachingGateway({
1428
1691
  hostname : hostname,
1429
1692
  port : port,
1430
1693
  path : path
@@ -1453,13 +1716,13 @@
1453
1716
  * Checks if a socket is closed.
1454
1717
  * @returns {boolean} - true if closed, false if open
1455
1718
  */
1456
- isClosed() {
1719
+ isClosed() {
1457
1720
  return this.gw == null;
1458
1721
  }
1459
1722
 
1460
1723
  /**
1461
1724
  * Binds a socket to listen to a specific protocol datagrams.
1462
- * Protocol numbers between Protocol.DATA+1 to Protocol.USER-1 are reserved protocols
1725
+ * Protocol numbers between Protocol.DATA+1 to Protocol.USER-1 are reserved protocols
1463
1726
  * and cannot be bound. Unbound sockets listen to all unreserved
1464
1727
  * @param {Protocol} protocol - protocol number to listen for
1465
1728
  * @returns {boolean} - true on success, false on failure
@@ -1471,9 +1734,9 @@
1471
1734
  }
1472
1735
  return false;
1473
1736
  }
1474
-
1737
+
1475
1738
  /**
1476
- * Unbinds a socket so that it listens to all unreserved protocols.
1739
+ * Unbinds a socket so that it listens to all unreserved protocols.
1477
1740
  * Protocol numbers between Protocol.DATA+1 to Protocol.USER-1 are considered reserved.
1478
1741
  * @returns {void}
1479
1742
  */
@@ -1486,13 +1749,13 @@
1486
1749
  isBound() { return this.localProtocol >= 0;}
1487
1750
 
1488
1751
  /**
1489
- * Sets the default destination address and destination protocol number for datagrams sent
1490
- * using this socket. The defaults can be overridden for specific send() calls.
1491
- * The default protcol number when a socket is opened is Protcol.DATA.
1492
- * The default node address is undefined.
1493
- * Protocol numbers between Protocol.DATA+1 to Protocol.USER-1 are considered reserved,
1752
+ * Sets the default destination address and destination protocol number for datagrams sent
1753
+ * using this socket. The defaults can be overridden for specific send() calls.
1754
+ * The default protcol number when a socket is opened is Protcol.DATA.
1755
+ * The default node address is undefined.
1756
+ * Protocol numbers between Protocol.DATA+1 to Protocol.USER-1 are considered reserved,
1494
1757
  * and cannot be used for sending datagrams using the socket.
1495
- *
1758
+ *
1496
1759
  * @param {number} to - default destination node address
1497
1760
  * @param {Protocol} protocol - default protocol number
1498
1761
  * @returns {boolean} - true on success, false on failure
@@ -1507,11 +1770,11 @@
1507
1770
  }
1508
1771
 
1509
1772
  /**
1510
- * Resets the default destination address to undefined, and the default protocol number
1773
+ * Resets the default destination address to undefined, and the default protocol number
1511
1774
  * to Protocol.DATA.
1512
1775
  * @returns {void}
1513
1776
  */
1514
- disconnect() {
1777
+ disconnect() {
1515
1778
  this.remoteAddress = -1;
1516
1779
  this.remoteProtocol = 0;
1517
1780
  }
@@ -1526,7 +1789,7 @@
1526
1789
  * Gets the local node address of the Unet node connected to.
1527
1790
  * @returns {Promise<int>} - local node address, or -1 on error
1528
1791
  */
1529
- async getLocalAddress() {
1792
+ async getLocalAddress() {
1530
1793
  if (this.gw == null) return -1;
1531
1794
  const nodeinfo = await this.gw.agentForService(Services.NODE_INFO);
1532
1795
  if (nodeinfo == null) return -1;
@@ -1553,14 +1816,14 @@
1553
1816
  getRemoteProtocol() { return this.remoteProtocol; }
1554
1817
 
1555
1818
  /**
1556
- * Sets the timeout for datagram reception. A timeout of 0 means the
1557
- * {@link UnetSocket#receive|receive method} will check any appropriate
1819
+ * Sets the timeout for datagram reception. A timeout of 0 means the
1820
+ * {@link UnetSocket#receive|receive method} will check any appropriate
1558
1821
  * Datagram has already been received (and is cached) else return immediately.
1559
- *
1822
+ *
1560
1823
  * @param {number} ms - timeout in milliseconds
1561
1824
  * @returns {void}
1562
1825
  */
1563
- setTimeout(ms) {
1826
+ setTimeout(ms) {
1564
1827
  if (ms < 0) ms = 0;
1565
1828
  this.timeout = ms;
1566
1829
  }
@@ -1609,12 +1872,12 @@
1609
1872
  }
1610
1873
 
1611
1874
  /**
1612
- * Receives a datagram sent to the local node and the bound protocol number. If the socket is unbound,
1875
+ * Receives a datagram sent to the local node and the bound protocol number. If the socket is unbound,
1613
1876
  * then datagrams with all unreserved protocols are received. Any broadcast datagrams are also received.
1614
- *
1877
+ *
1615
1878
  * @returns {Promise<?DatagramNtf>} - datagram received by the socket
1616
1879
  */
1617
- async receive() {
1880
+ async receive() {
1618
1881
  if (this.gw == null) return null;
1619
1882
  return await this.gw.receive(msg => {
1620
1883
  if (msg.__clazz__ != DatagramNtf.__clazz__ && msg.__clazz__ != RxFrameNtf.__clazz__ ) return false;
@@ -1635,31 +1898,34 @@
1635
1898
  /**
1636
1899
  * Gets an AgentID providing a specified service for low-level access to UnetStack
1637
1900
  * @param {string} svc - the named service of interest
1901
+ * @param {Boolean} caching - if the AgentID should cache parameters
1638
1902
  * @returns {Promise<?AgentID>} - a promise which returns an {@link AgentID} that provides the service when resolved
1639
1903
  */
1640
- async agentForService(svc) {
1904
+ async agentForService(svc, caching=true) {
1641
1905
  if (this.gw == null) return null;
1642
- return await this.gw.agentForService(svc);
1906
+ return await this.gw.agentForService(svc, caching);
1643
1907
  }
1644
1908
 
1645
1909
  /**
1646
- *
1910
+ *
1647
1911
  * @param {string} svc - the named service of interest
1912
+ * @param {Boolean} caching - if the AgentID should cache parameters
1648
1913
  * @returns {Promise<AgentID[]>} - a promise which returns an array of {@link AgentID|AgentIDs} that provides the service when resolved
1649
1914
  */
1650
- async agentsForService(svc) {
1915
+ async agentsForService(svc, caching=true) {
1651
1916
  if (this.gw == null) return null;
1652
- return await this.gw.agentsForService(svc);
1917
+ return await this.gw.agentsForService(svc, caching``);
1653
1918
  }
1654
1919
 
1655
1920
  /**
1656
1921
  * Gets a named AgentID for low-level access to UnetStack.
1657
1922
  * @param {string} name - name of agent
1923
+ * @param {Boolean} caching - if the AgentID should cache parameters
1658
1924
  * @returns {AgentID} - AgentID for the given name
1659
1925
  */
1660
- agent(name) {
1926
+ agent(name, caching=true) {
1661
1927
  if (this.gw == null) return null;
1662
- return this.gw.agent(name);
1928
+ return this.gw.agent(name, caching);
1663
1929
  }
1664
1930
 
1665
1931
  /**
@@ -1667,7 +1933,7 @@
1667
1933
  * @param {string} nodeName - name of the node to resolve
1668
1934
  * @returns {Promise<?number>} - address of the node, or null if unable to resolve
1669
1935
  */
1670
- async host(nodeName) {
1936
+ async host(nodeName) {
1671
1937
  const arp = await this.agentForService(Services.ADDRESS_RESOLUTION);
1672
1938
  if (arp == null) return null;
1673
1939
  const req = new AddressResolutionReq(nodeName);
@@ -1680,7 +1946,8 @@
1680
1946
  }
1681
1947
 
1682
1948
  exports.AgentID = AgentID;
1683
- exports.Gateway = Gateway;
1949
+ exports.CachingAgentID = CachingAgentID;
1950
+ exports.Gateway = CachingGateway;
1684
1951
  exports.Message = Message;
1685
1952
  exports.MessageClass = MessageClass;
1686
1953
  exports.Performative = Performative;
@@ -1688,6 +1955,8 @@
1688
1955
  exports.Services = Services;
1689
1956
  exports.UnetMessages = UnetMessages;
1690
1957
  exports.UnetSocket = UnetSocket;
1958
+ exports.toGps = toGps;
1959
+ exports.toLocal = toLocal;
1691
1960
 
1692
- })));
1961
+ }));
1693
1962
  //# sourceMappingURL=unetjs.js.map