incyclist-devices 1.5.19 → 1.5.21

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.
@@ -97,7 +97,6 @@ class AntAdapter extends device_1.default {
97
97
  if (this.ivDataTimeout)
98
98
  return;
99
99
  this.ivDataTimeout = setInterval(() => {
100
- console.log('~~~ check', this.lastDataTS);
101
100
  if (!this.lastDataTS)
102
101
  return;
103
102
  if (this.lastDataTS + NO_DATA_TIMEOUT < Date.now()) {
@@ -110,6 +109,7 @@ class AntAdapter extends device_1.default {
110
109
  return;
111
110
  clearInterval(this.ivDataTimeout);
112
111
  this.ivDataTimeout = undefined;
112
+ this.lastDataTS = undefined;
113
113
  }
114
114
  start(props) {
115
115
  return __awaiter(this, void 0, void 0, function* () {
@@ -64,7 +64,7 @@ class AntInterface extends events_1.default {
64
64
  const device = new this.Binding(Object.assign(Object.assign({}, this.props), { logger: this.logger }));
65
65
  const opened = yield device.open();
66
66
  if (!opened) {
67
- this.logEvent({ message: 'could not connect' });
67
+ this.logEvent({ message: 'ANT+ not connected' });
68
68
  this.isConnecting = false;
69
69
  return false;
70
70
  }
package/lib/antv2/fe.d.ts CHANGED
@@ -8,7 +8,9 @@ export default class AntFEAdapter extends AntAdapter {
8
8
  protected logger: EventLogger;
9
9
  protected cyclingMode: CyclingMode;
10
10
  protected distanceInternal?: number;
11
+ protected startProps: any;
11
12
  protected msgCount: number;
13
+ protected isReconnecting: boolean;
12
14
  constructor(sensor: ISensor, protocol: AntProtocol);
13
15
  isBike(): boolean;
14
16
  isHrm(): boolean;
@@ -25,6 +27,7 @@ export default class AntFEAdapter extends AntAdapter {
25
27
  mapData(deviceData: any): IncyclistBikeData;
26
28
  transformData(bikeData: any): any;
27
29
  start(props?: any): Promise<any>;
28
- initTimeoutHandler(): void;
30
+ setFEDefaultTimeout(): void;
29
31
  stop(): Promise<boolean>;
32
+ reconnect(): Promise<boolean>;
30
33
  }
package/lib/antv2/fe.js CHANGED
@@ -18,9 +18,11 @@ const gd_eventlog_1 = require("gd-eventlog");
18
18
  const ant_fe_st_mode_1 = __importDefault(require("../ant/antfe/ant-fe-st-mode"));
19
19
  const ant_fe_erg_mode_1 = __importDefault(require("../ant/antfe/ant-fe-erg-mode"));
20
20
  const ant_fe_adv_st_mode_1 = __importDefault(require("../ant/antfe/ant-fe-adv-st-mode"));
21
+ const utils_2 = require("../utils");
21
22
  const DEFAULT_USER_WEIGHT = 75;
22
23
  const DEFAULT_BIKE_WEIGHT = 10;
23
24
  const DEFAULT_BIKE_WEIGHT_MOUNTAIN = 14.5;
25
+ const MAX_RETRIES = 3;
24
26
  class AntFEAdapter extends ant_device_1.default {
25
27
  constructor(sensor, protocol) {
26
28
  super(sensor, protocol);
@@ -30,6 +32,7 @@ class AntFEAdapter extends ant_device_1.default {
30
32
  };
31
33
  this.msgCount = 0;
32
34
  this.logger = new gd_eventlog_1.EventLogger('Ant+FE');
35
+ this.isReconnecting = false;
33
36
  }
34
37
  isBike() { return true; }
35
38
  isHrm() { return false; }
@@ -79,7 +82,7 @@ class AntFEAdapter extends ant_device_1.default {
79
82
  }
80
83
  sendUpdate(request) {
81
84
  return __awaiter(this, void 0, void 0, function* () {
82
- if (this.paused)
85
+ if (this.paused || this.isReconnecting)
83
86
  return;
84
87
  const update = this.getCyclingMode().sendBikeUpdate(request);
85
88
  this.logger.logEvent({ message: 'send bike update requested', update, request });
@@ -106,6 +109,9 @@ class AntFEAdapter extends ant_device_1.default {
106
109
  catch (err) {
107
110
  if (err.message && err.message.toLowerCase() === 'timeout') {
108
111
  this.emit('timeout');
112
+ if (this.startProps.automaticReconnect) {
113
+ yield this.reconnect();
114
+ }
109
115
  }
110
116
  this.logger.logEvent({ message: 'sendBikeUpdate() error', error: err.message });
111
117
  }
@@ -114,6 +120,7 @@ class AntFEAdapter extends ant_device_1.default {
114
120
  onDeviceData(deviceData) {
115
121
  if (!this.started || this.isStopped())
116
122
  return;
123
+ this.msgCount++;
117
124
  this.deviceData = deviceData;
118
125
  this.lastDataTS = Date.now();
119
126
  if (!this.ivDataTimeout)
@@ -189,73 +196,74 @@ class AntFEAdapter extends ant_device_1.default {
189
196
  });
190
197
  return __awaiter(this, void 0, void 0, function* () {
191
198
  _super.start.call(this, props);
199
+ this.startProps = props;
192
200
  this.logger.logEvent({ message: 'start', props });
193
201
  this.msgCount = 0;
194
202
  const opts = props || {};
195
203
  const { args = {}, user = {} } = opts;
196
204
  return new Promise((resolve, reject) => __awaiter(this, void 0, void 0, function* () {
197
205
  const { timeout = 20000 } = props || {};
198
- let start = Date.now();
199
- let startTimeout = start + timeout;
200
- const status = { userSent: false, slopeSent: false };
201
- let iv;
202
- const stopInterval = () => {
203
- if (iv)
204
- clearInterval(iv);
205
- iv = undefined;
206
+ let to;
207
+ const stopTimeoutCheck = () => {
208
+ if (to) {
209
+ clearTimeout(to);
210
+ to = null;
211
+ }
206
212
  };
207
- if (timeout) {
208
- iv = setInterval(() => __awaiter(this, void 0, void 0, function* () {
209
- if (Date.now() > startTimeout) {
210
- stopInterval();
211
- yield this.stop();
212
- reject(new Error(`could not start device, reason:timeout`));
213
- }
214
- if (this.started && this.msgCount > 1 && status.userSent) {
215
- this.logger.logEvent({ message: 'start success' });
216
- stopInterval();
213
+ to = setTimeout(() => __awaiter(this, void 0, void 0, function* () {
214
+ yield this.stop();
215
+ reject(new Error(`could not start device, reason:timeout`));
216
+ to = null;
217
+ }), timeout);
218
+ this.setFEDefaultTimeout();
219
+ let success = false;
220
+ let status;
221
+ let retry = 0;
222
+ while (!success && retry < MAX_RETRIES) {
223
+ retry++;
224
+ if (!this.started) {
225
+ this.started = yield this.ant.startSensor(this.sensor, this.onDeviceData.bind(this));
226
+ status = { userSent: false, slopeSent: false };
227
+ }
228
+ if (!this.started) {
229
+ yield (0, utils_2.sleep)(2000);
230
+ continue;
231
+ }
232
+ try {
233
+ const fe = this.sensor;
234
+ const mode = this.getCyclingMode();
235
+ const bikeType = mode ? mode.getSetting('bikeType').toLowerCase() : 'race';
236
+ const defaultBikeWeight = bikeType === 'mountain' ? DEFAULT_BIKE_WEIGHT_MOUNTAIN : DEFAULT_BIKE_WEIGHT;
237
+ const userWeight = args.userWeight || user.weight || DEFAULT_USER_WEIGHT;
238
+ const bikeWeight = args.bikeWeight || defaultBikeWeight;
239
+ status.userSent = status.userSent || (yield fe.sendUserConfiguration(userWeight, bikeWeight, args.wheelDiameter, args.gearRatio));
240
+ status.slopeSent = status.slopeSent || (yield fe.sendTrackResistance(0.0));
241
+ }
242
+ catch (error) {
243
+ try {
244
+ yield yield this.ant.stopSensor(this.sensor);
217
245
  }
218
- }), 100);
246
+ catch (_a) { }
247
+ this.started = false;
248
+ }
249
+ success = status.userSent && status.slopeSent;
219
250
  }
220
- this.started = yield this.ant.startSensor(this.sensor, this.onDeviceData.bind(this));
221
- if (!this.started) {
222
- stopInterval();
223
- this.stop();
224
- return reject(new Error(`could not start device`));
251
+ while (success && this.msgCount === 0) {
252
+ yield (0, utils_2.sleep)(500);
225
253
  }
226
- this.initTimeoutHandler();
227
- try {
228
- const fe = this.sensor;
229
- const mode = this.getCyclingMode();
230
- const bikeType = mode ? mode.getSetting('bikeType').toLowerCase() : 'race';
231
- const defaultBikeWeight = bikeType === 'mountain' ? DEFAULT_BIKE_WEIGHT_MOUNTAIN : DEFAULT_BIKE_WEIGHT;
232
- const userWeight = args.userWeight || user.weight || DEFAULT_USER_WEIGHT;
233
- const bikeWeight = args.bikeWeight || defaultBikeWeight;
234
- let i = 0;
235
- while (i < 3 && (!status.userSent || !status.slopeSent)) {
236
- if (!timeout || iv)
237
- status.userSent = status.userSent || (yield fe.sendUserConfiguration(userWeight, bikeWeight, args.wheelDiameter, args.gearRatio));
238
- if (!timeout || iv)
239
- status.slopeSent = status.slopeSent || (yield fe.sendTrackResistance(0.0));
240
- i++;
241
- }
242
- stopInterval();
243
- if (status.userSent) {
244
- this.logger.logEvent({ message: 'start success' });
245
- return resolve(true);
246
- }
247
- this.logger.logEvent({ message: 'start failure' });
248
- this.stop();
249
- return reject(new Error(`could not start device, reason: could not send commands`));
254
+ if (success) {
255
+ this.logger.logEvent({ message: 'start success' });
256
+ stopTimeoutCheck();
250
257
  }
251
- catch (error) {
252
- reject(new Error(`could not start device, reason:${error.message}`));
253
- return;
258
+ else {
259
+ this.logger.logEvent({ message: 'start failed' });
260
+ stopTimeoutCheck();
261
+ reject(new Error('could not start device, reason: could not send FE commands'));
254
262
  }
255
263
  }));
256
264
  });
257
265
  }
258
- initTimeoutHandler() {
266
+ setFEDefaultTimeout() {
259
267
  const fe = this.sensor;
260
268
  fe.setSendTimeout(5000);
261
269
  }
@@ -269,5 +277,24 @@ class AntFEAdapter extends ant_device_1.default {
269
277
  return stopped;
270
278
  });
271
279
  }
280
+ reconnect() {
281
+ return __awaiter(this, void 0, void 0, function* () {
282
+ this.logger.logEvent({ message: 'reconnect to device' });
283
+ this.isReconnecting = true;
284
+ try {
285
+ yield this.stop();
286
+ yield this.start(this.startProps);
287
+ this.started = true;
288
+ this.isReconnecting = false;
289
+ this.logger.logEvent({ message: 'reconnect success' });
290
+ return true;
291
+ }
292
+ catch (err) {
293
+ this.logger.logEvent({ message: 'reconnect failed' });
294
+ this.isReconnecting = false;
295
+ return false;
296
+ }
297
+ });
298
+ }
272
299
  }
273
300
  exports.default = AntFEAdapter;
@@ -672,7 +672,7 @@ class BleInterface extends ble_1.BleInterfaceClass {
672
672
  if (!this.getBinding())
673
673
  throw new Error('no binding defined');
674
674
  this.getBinding().removeAllListeners('discover');
675
- const ongoing = this.peripheralCache.filter(i => i.state.isLoading);
675
+ const ongoing = this.peripheralCache.filter(i => i.state && i.state.isLoading);
676
676
  if (ongoing)
677
677
  ongoing.forEach(i => { i.isInterrupted = true; });
678
678
  yield this.getBinding().stopScanning();
@@ -4,6 +4,7 @@ export default class DaumClassicAdapter extends DaumAdapter {
4
4
  static NAME: string;
5
5
  name: string;
6
6
  id: string;
7
+ udid: number;
7
8
  constructor(protocol: any, bike: any);
8
9
  setID(id: any): void;
9
10
  getID(): string;
@@ -28,6 +28,8 @@ class DaumClassicAdapter extends DaumAdapter_1.default {
28
28
  this.paused = undefined;
29
29
  this.iv = undefined;
30
30
  this.distanceInternal = undefined;
31
+ this.udid = Date.now();
32
+ this.logger.logEvent({ message: 'Device created', udid: this.udid, port: this.getPort() });
31
33
  this.initData();
32
34
  }
33
35
  setID(id) {
@@ -101,13 +103,13 @@ class DaumClassicAdapter extends DaumAdapter_1.default {
101
103
  }
102
104
  startRide(props) {
103
105
  return __awaiter(this, void 0, void 0, function* () {
104
- this.logger.logEvent({ message: 'relaunch of device' });
106
+ this.logger.logEvent({ message: 'relaunch of device', udid: this.udid });
105
107
  return yield this.launch(props, true);
106
108
  });
107
109
  }
108
110
  start(props) {
109
111
  return __awaiter(this, void 0, void 0, function* () {
110
- this.logger.logEvent({ message: 'initial start of device' });
112
+ this.logger.logEvent({ message: 'initial start of device', udid: this.udid });
111
113
  return yield this.launch(props, false);
112
114
  });
113
115
  }
@@ -122,7 +124,7 @@ class DaumClassicAdapter extends DaumAdapter_1.default {
122
124
  try {
123
125
  const version = yield this.bike.getVersion();
124
126
  const { serialNo, cockpit } = version || {};
125
- this.logEvent({ message: 'device info', deviceInfo: { serialNo, cockpit } });
127
+ this.logEvent({ message: 'device info', deviceInfo: { serialNo, cockpit }, udid: this.udid });
126
128
  }
127
129
  catch (_a) { }
128
130
  }
@@ -132,7 +134,7 @@ class DaumClassicAdapter extends DaumAdapter_1.default {
132
134
  return true;
133
135
  }
134
136
  catch (err) {
135
- this.logger.logEvent({ message: 'start result: error', error: err.message });
137
+ this.logger.logEvent({ message: 'start result: error', error: err.message, udid: this.udid });
136
138
  throw new Error(`could not start device, reason:${err.message}`);
137
139
  }
138
140
  });
package/package.json CHANGED
@@ -1,12 +1,12 @@
1
1
  {
2
2
  "name": "incyclist-devices",
3
- "version": "1.5.19",
3
+ "version": "1.5.21",
4
4
  "dependencies": {
5
5
  "@serialport/parser-byte-length": "^9.0.1",
6
6
  "@serialport/parser-delimiter": "^9.0.1",
7
7
  "@types/serialport": "^8.0.1",
8
8
  "gd-ant-plus": "^0.0.33",
9
- "incyclist-ant-plus": "^0.1.10",
9
+ "incyclist-ant-plus": "^0.1.13",
10
10
  "win32filetime": "^1.0.2"
11
11
  },
12
12
  "peerDependencies": {