tsvesync 1.0.11 → 1.0.13

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 (40) hide show
  1. package/dist/index.d.ts +7 -0
  2. package/dist/index.js +25 -0
  3. package/dist/lib/helpers.d.ts +52 -51
  4. package/dist/lib/helpers.js +135 -112
  5. package/dist/lib/logger.d.ts +23 -0
  6. package/dist/lib/logger.js +54 -0
  7. package/dist/lib/vesync.d.ts +57 -15
  8. package/dist/lib/vesync.js +341 -217
  9. package/dist/lib/vesyncBaseDevice.d.ts +25 -50
  10. package/dist/lib/vesyncBaseDevice.js +63 -90
  11. package/dist/lib/vesyncBulb.d.ts +88 -0
  12. package/dist/lib/vesyncBulb.js +295 -1
  13. package/dist/lib/vesyncBulbImpl.d.ts +38 -0
  14. package/dist/lib/vesyncBulbImpl.js +230 -0
  15. package/dist/lib/vesyncFan.d.ts +55 -67
  16. package/dist/lib/vesyncFan.js +366 -213
  17. package/dist/lib/vesyncFanImpl.d.ts +173 -0
  18. package/dist/lib/vesyncFanImpl.js +909 -0
  19. package/dist/lib/vesyncOutlet.d.ts +70 -0
  20. package/dist/lib/vesyncOutlet.js +213 -1
  21. package/dist/lib/vesyncOutletImpl.d.ts +70 -0
  22. package/dist/lib/vesyncOutletImpl.js +245 -0
  23. package/dist/lib/vesyncSwitch.d.ts +45 -0
  24. package/dist/lib/vesyncSwitch.js +77 -1
  25. package/dist/lib/vesyncSwitchImpl.d.ts +82 -0
  26. package/dist/lib/vesyncSwitchImpl.js +344 -0
  27. package/package.json +1 -1
  28. package/src/index.ts +14 -0
  29. package/src/lib/helpers.ts +3 -2
  30. package/src/lib/logger.ts +60 -0
  31. package/src/lib/vesync.ts +42 -43
  32. package/src/lib/vesyncBaseDevice.ts +8 -7
  33. package/src/lib/vesyncBulb.ts +138 -30
  34. package/src/lib/vesyncBulbImpl.ts +113 -44
  35. package/src/lib/vesyncFan.ts +2 -4
  36. package/src/lib/vesyncFanImpl.ts +314 -42
  37. package/src/lib/vesyncOutlet.ts +140 -13
  38. package/src/lib/vesyncOutletImpl.ts +41 -0
  39. package/src/lib/vesyncSwitch.ts +3 -454
  40. package/src/lib/vesyncSwitchImpl.ts +66 -16
@@ -1,104 +1,116 @@
1
1
  "use strict";
2
- var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
3
- if (k2 === undefined) k2 = k;
4
- var desc = Object.getOwnPropertyDescriptor(m, k);
5
- if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
6
- desc = { enumerable: true, get: function() { return m[k]; } };
7
- }
8
- Object.defineProperty(o, k2, desc);
9
- }) : (function(o, m, k, k2) {
10
- if (k2 === undefined) k2 = k;
11
- o[k2] = m[k];
12
- }));
13
- var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
14
- Object.defineProperty(o, "default", { enumerable: true, value: v });
15
- }) : function(o, v) {
16
- o["default"] = v;
17
- });
18
- var __importStar = (this && this.__importStar) || (function () {
19
- var ownKeys = function(o) {
20
- ownKeys = Object.getOwnPropertyNames || function (o) {
21
- var ar = [];
22
- for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
23
- return ar;
24
- };
25
- return ownKeys(o);
26
- };
27
- return function (mod) {
28
- if (mod && mod.__esModule) return mod;
29
- var result = {};
30
- if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
31
- __setModuleDefault(result, mod);
32
- return result;
33
- };
34
- })();
35
- var _a;
36
- Object.defineProperty(exports, "__esModule", { value: true });
37
- exports.VeSync = void 0;
38
2
  /**
39
3
  * VeSync API Device Library
40
4
  */
5
+ Object.defineProperty(exports, "__esModule", { value: true });
6
+ exports.VeSync = void 0;
41
7
  const helpers_1 = require("./helpers");
42
- const bulbMods = __importStar(require("./vesyncBulb"));
43
- const fanMods = __importStar(require("./vesyncFan"));
44
- const outletMods = __importStar(require("./vesyncOutlet"));
45
- const switchMods = __importStar(require("./vesyncSwitch"));
46
- const kitchenMods = __importStar(require("./vesyncKitchen"));
8
+ const vesyncFanImpl_1 = require("./vesyncFanImpl");
9
+ const vesyncOutletImpl_1 = require("./vesyncOutletImpl");
10
+ const vesyncSwitchImpl_1 = require("./vesyncSwitchImpl");
11
+ const vesyncBulbImpl_1 = require("./vesyncBulbImpl");
12
+ const logger_1 = require("./logger");
47
13
  const DEFAULT_ENERGY_UPDATE_INTERVAL = 21600;
48
- function objectFactory(devType, config, manager) {
49
- const fans = (devType, config, manager) => {
50
- const fanCls = fanMods.fanModules[devType];
51
- return ['fans', new fanCls(config, manager)];
52
- };
53
- const outlets = (devType, config, manager) => {
54
- const outletCls = outletMods.outletModules[devType];
55
- return ['outlets', new outletCls(config, manager)];
56
- };
57
- const switches = (devType, config, manager) => {
58
- const switchCls = switchMods.switchModules[devType];
59
- return ['switches', new switchCls(config, manager)];
60
- };
61
- const bulbs = (devType, config, manager) => {
62
- const bulbCls = bulbMods.bulbModules[devType];
63
- return ['bulbs', new bulbCls(config, manager)];
64
- };
65
- const kitchen = (devType, config, manager) => {
66
- const kitchenCls = kitchenMods.kitchenModules[devType];
67
- return ['kitchen', new kitchenCls(config, manager)];
14
+ /**
15
+ * Create device instance based on type
16
+ */
17
+ function objectFactory(details, manager) {
18
+ const deviceType = details.deviceType;
19
+ let DeviceClass = null;
20
+ let category = 'unknown';
21
+ // Map of device categories to their module dictionaries
22
+ const allModules = {
23
+ outlets: vesyncOutletImpl_1.outletModules,
24
+ fans: vesyncFanImpl_1.fanModules,
25
+ bulbs: vesyncBulbImpl_1.bulbModules,
26
+ switches: vesyncSwitchImpl_1.switchModules
68
27
  };
69
- if (devType in fanMods.fanModules) {
70
- return fans(devType, config, manager);
71
- }
72
- else if (devType in outletMods.outletModules) {
73
- return outlets(devType, config, manager);
74
- }
75
- else if (devType in switchMods.switchModules) {
76
- return switches(devType, config, manager);
28
+ // First try exact match in all modules
29
+ for (const [cat, modules] of Object.entries(allModules)) {
30
+ if (deviceType in modules) {
31
+ DeviceClass = modules[deviceType];
32
+ category = cat;
33
+ logger_1.logger.debug(`Found exact match for ${deviceType} in ${cat} modules`);
34
+ break;
35
+ }
77
36
  }
78
- else if (devType in bulbMods.bulbModules) {
79
- return bulbs(devType, config, manager);
37
+ // If no exact match, try to find a base class
38
+ if (!DeviceClass) {
39
+ // Device type prefix mapping
40
+ const prefixMap = {
41
+ // Fans
42
+ 'Core': 'fans',
43
+ 'LAP': 'fans',
44
+ 'LTF': 'fans',
45
+ 'Classic': 'fans',
46
+ 'Dual': 'fans',
47
+ 'LUH': 'fans',
48
+ 'LEH': 'fans',
49
+ 'LV-PUR': 'fans',
50
+ 'LV-RH': 'fans',
51
+ // Outlets
52
+ 'wifi-switch': 'outlets',
53
+ 'ESW03': 'outlets',
54
+ 'ESW01': 'outlets',
55
+ 'ESW15': 'outlets',
56
+ 'ESO': 'outlets',
57
+ // Switches
58
+ 'ESWL': 'switches',
59
+ 'ESWD': 'switches',
60
+ // Bulbs
61
+ 'ESL': 'bulbs',
62
+ 'XYD': 'bulbs'
63
+ };
64
+ // Find category based on device type prefix
65
+ for (const [prefix, cat] of Object.entries(prefixMap)) {
66
+ if (deviceType.startsWith(prefix)) {
67
+ category = cat;
68
+ logger_1.logger.debug(`Device type ${deviceType} matched prefix ${prefix} -> category ${cat}`);
69
+ // Try to find a base class in this category's modules
70
+ const modules = allModules[cat];
71
+ for (const [moduleType, ModuleClass] of Object.entries(modules)) {
72
+ const baseType = moduleType.split('-')[0]; // e.g., ESL100 from ESL100-USA
73
+ if (deviceType.startsWith(baseType)) {
74
+ DeviceClass = ModuleClass;
75
+ logger_1.logger.debug(`Found base type match: ${deviceType} -> ${baseType}`);
76
+ break;
77
+ }
78
+ }
79
+ break;
80
+ }
81
+ }
80
82
  }
81
- else if (devType in kitchenMods.kitchenModules) {
82
- return kitchen(devType, config, manager);
83
+ if (DeviceClass) {
84
+ try {
85
+ // Add category to device details
86
+ details.deviceCategory = category;
87
+ const device = new DeviceClass(details, manager);
88
+ return [category, device];
89
+ }
90
+ catch (error) {
91
+ logger_1.logger.error(`Error creating device instance for ${deviceType}:`, error);
92
+ return [category, null];
93
+ }
83
94
  }
84
95
  else {
85
- console.debug('Unknown device named %s model %s', config.deviceName || '', config.deviceType || '');
86
- return ['unknown', null];
96
+ logger_1.logger.warn(`No device class found for type: ${deviceType}`);
97
+ return [category, null];
87
98
  }
88
99
  }
100
+ /**
101
+ * VeSync Manager Class
102
+ */
89
103
  class VeSync {
104
+ /**
105
+ * Initialize VeSync Manager
106
+ */
90
107
  constructor(username, password, timeZone = helpers_1.DEFAULT_TZ, debug = false, redact = true) {
91
- this.body = helpers_1.Helpers.reqBody(this, 'devicelist');
92
- this[_a] = await helpers_1.Helpers.callApi('/cloud/v1/deviceManaged/devices', 'post', body, helpers_1.Helpers.reqHeaders(this));
93
108
  this._debug = debug;
94
- if (debug) {
95
- // Set debug logging levels
96
- console.debug('Debug logging enabled');
97
- }
98
109
  this._redact = redact;
99
- if (redact) {
100
- helpers_1.Helpers.redact = redact;
101
- }
110
+ this._energyUpdateInterval = DEFAULT_ENERGY_UPDATE_INTERVAL;
111
+ this._energyCheck = true;
112
+ this._lastUpdateTs = null;
113
+ this._inProcess = false;
102
114
  this.username = username;
103
115
  this.password = password;
104
116
  this.token = null;
@@ -107,29 +119,22 @@ class VeSync {
107
119
  this.devices = null;
108
120
  this.enabled = false;
109
121
  this.updateInterval = helpers_1.API_RATE_LIMIT;
110
- this.lastUpdateTs = null;
111
- this.inProcess = false;
112
- this._energyUpdateInterval = DEFAULT_ENERGY_UPDATE_INTERVAL;
113
- this._energyCheck = true;
114
122
  this.fans = [];
115
123
  this.outlets = [];
116
124
  this.switches = [];
117
125
  this.bulbs = [];
118
126
  this.scales = [];
119
- this.kitchen = [];
120
127
  this._devList = {
121
128
  fans: this.fans,
122
129
  outlets: this.outlets,
123
130
  switches: this.switches,
124
- bulbs: this.bulbs,
125
- kitchen: this.kitchen,
126
- unknown: []
131
+ bulbs: this.bulbs
127
132
  };
128
133
  if (typeof timeZone === 'string' && timeZone) {
129
134
  const regTest = /[^a-zA-Z/_]/;
130
135
  if (regTest.test(timeZone)) {
131
136
  this.timeZone = helpers_1.DEFAULT_TZ;
132
- console.debug('Invalid characters in time zone - %s', timeZone);
137
+ logger_1.logger.debug('Invalid characters in time zone - ', timeZone);
133
138
  }
134
139
  else {
135
140
  this.timeZone = timeZone;
@@ -137,41 +142,47 @@ class VeSync {
137
142
  }
138
143
  else {
139
144
  this.timeZone = helpers_1.DEFAULT_TZ;
140
- console.debug('Time zone is not a string');
145
+ logger_1.logger.debug('Time zone is not a string');
146
+ }
147
+ if (debug) {
148
+ this.debug = true;
149
+ }
150
+ if (redact) {
151
+ this.redact = true;
141
152
  }
142
153
  }
154
+ /**
155
+ * Get/Set debug mode
156
+ */
143
157
  get debug() {
144
158
  return this._debug;
145
159
  }
146
- set debug(newFlag) {
147
- this._debug = newFlag;
148
- // Set logging levels based on debug flag
149
- if (newFlag) {
150
- console.debug('Debug logging enabled');
151
- }
160
+ set debug(flag) {
161
+ this._debug = flag;
152
162
  }
163
+ /**
164
+ * Get/Set redact mode
165
+ */
153
166
  get redact() {
154
167
  return this._redact;
155
168
  }
156
- set redact(newFlag) {
157
- if (newFlag) {
158
- helpers_1.Helpers.redact = true;
159
- }
160
- else {
161
- helpers_1.Helpers.redact = false;
162
- }
163
- this._redact = newFlag;
169
+ set redact(flag) {
170
+ this._redact = flag;
171
+ helpers_1.Helpers.shouldRedact = flag;
164
172
  }
173
+ /**
174
+ * Get/Set energy update interval
175
+ */
165
176
  get energyUpdateInterval() {
166
177
  return this._energyUpdateInterval;
167
178
  }
168
- set energyUpdateInterval(newEnergyUpdate) {
169
- if (newEnergyUpdate > 0) {
170
- this._energyUpdateInterval = newEnergyUpdate;
179
+ set energyUpdateInterval(interval) {
180
+ if (interval > 0) {
181
+ this._energyUpdateInterval = interval;
171
182
  }
172
183
  }
173
184
  /**
174
- * Test if device should be removed - false = Remove
185
+ * Test if device should be removed
175
186
  */
176
187
  static removeDevTest(device, newList) {
177
188
  if (Array.isArray(newList) && device.cid) {
@@ -180,130 +191,243 @@ class VeSync {
180
191
  return true;
181
192
  }
182
193
  }
194
+ logger_1.logger.debug(`Device removed - ${device.deviceName} - ${device.deviceType}`);
195
+ return false;
183
196
  }
184
- return false;
197
+ return true;
185
198
  }
186
199
  /**
187
- * Login to VeSync server
200
+ * Test if new device should be added
188
201
  */
189
- async login() {
190
- const body = helpers_1.Helpers.reqBody(this, 'login');
191
- const [response] = await helpers_1.Helpers.callApi('/cloud/v1/user/login', 'post', body);
192
- if (!response || response.code !== 0 || !response.result) {
193
- console.error('Error logging in to VeSync');
194
- return false;
202
+ addDevTest(newDev) {
203
+ if ('cid' in newDev) {
204
+ for (const devices of Object.values(this._devList)) {
205
+ for (const dev of devices) {
206
+ if (dev.cid === newDev.cid) {
207
+ return false;
208
+ }
209
+ }
210
+ }
195
211
  }
196
- this.token = response.result.token;
197
- this.accountId = response.result.accountID;
198
- this.countryCode = response.result.countryCode;
199
- this.enabled = true;
200
212
  return true;
201
213
  }
202
214
  /**
203
- * Get list of VeSync devices
215
+ * Remove devices not found in device list return
204
216
  */
205
- async getDevices() {
206
- if (!this.enabled)
207
- : console.error('Not logged in');
208
- return false;
217
+ removeOldDevices(devices) {
218
+ for (const [key, deviceList] of Object.entries(this._devList)) {
219
+ const before = deviceList.length;
220
+ this._devList[key] = deviceList.filter(device => VeSync.removeDevTest(device, devices));
221
+ const after = this._devList[key].length;
222
+ if (before !== after) {
223
+ logger_1.logger.debug(`${before - after} ${key} removed`);
224
+ }
225
+ }
226
+ return true;
209
227
  }
210
- if(, response) { }
211
- }
212
- exports.VeSync = VeSync;
213
- _a = response;
214
- || response.code !== 0;
215
- {
216
- console.error('Error getting device list');
217
- return false;
218
- }
219
- this.devices = response.result.list || [];
220
- return true;
221
- /**
222
- * Process devices after getting list of devices
223
- */
224
- processDevices();
225
- void {
226
- : .devices
227
- };
228
- {
229
- console.error('Device list not fetched');
230
- return;
231
- }
232
- const deviceList = [...this.devices];
233
- const toRemove = [];
234
- // Build list of devices to remove
235
- for (const devList of Object.values(this._devList)) {
236
- for (const device of devList) {
237
- if (!VeSync.removeDevTest(device, deviceList)) {
238
- toRemove.push(device);
228
+ /**
229
+ * Correct devices without cid or uuid
230
+ */
231
+ static setDevId(devices) {
232
+ const devRem = [];
233
+ devices.forEach((dev, index) => {
234
+ if (!dev.cid) {
235
+ if (dev.macID) {
236
+ dev.cid = dev.macID;
237
+ }
238
+ else if (dev.uuid) {
239
+ dev.cid = dev.uuid;
240
+ }
241
+ else {
242
+ devRem.push(index);
243
+ logger_1.logger.warn(`Device with no ID - ${dev.deviceName || ''}`);
244
+ }
245
+ }
246
+ });
247
+ if (devRem.length > 0) {
248
+ return devices.filter((_, index) => !devRem.includes(index));
239
249
  }
250
+ return devices;
240
251
  }
241
- }
242
- // Remove devices not in device list
243
- for (const device of toRemove) {
244
- for (const [key, devList] of Object.entries(this._devList)) {
245
- const index = devList.indexOf(device);
246
- if (index > -1) {
247
- this._devList[key].splice(index, 1);
252
+ /**
253
+ * Process device list and instantiate device objects
254
+ */
255
+ processDevices(devList) {
256
+ // Ensure devices have proper IDs
257
+ const devices = VeSync.setDevId(devList);
258
+ // Count current devices
259
+ let numDevices = 0;
260
+ for (const deviceList of Object.values(this._devList)) {
261
+ numDevices += deviceList.length;
262
+ }
263
+ if (!devices || devices.length === 0) {
264
+ logger_1.logger.warn('No devices found in api return');
265
+ return false;
266
+ }
267
+ // Initialize new device list or remove old devices
268
+ if (numDevices === 0) {
269
+ logger_1.logger.debug('New device list initialized');
270
+ }
271
+ else {
272
+ this.removeOldDevices(devices);
248
273
  }
274
+ // Filter out devices that already exist
275
+ const newDevices = devices.filter(dev => this.addDevTest(dev));
276
+ // Required keys for device instantiation
277
+ const requiredKeys = ['deviceType', 'deviceName', 'deviceStatus', 'cid'];
278
+ // Process each new device
279
+ for (const dev of newDevices) {
280
+ // Verify required device properties
281
+ if (!requiredKeys.every(key => key in dev)) {
282
+ logger_1.logger.debug(`Error adding device - missing required properties: ${dev.deviceName || 'Unknown'}`);
283
+ continue;
284
+ }
285
+ const devType = dev.deviceType;
286
+ try {
287
+ // Create device instance using factory
288
+ const [category, deviceObj] = objectFactory(dev, this);
289
+ // Add device to appropriate category if valid
290
+ if (deviceObj && category in this._devList) {
291
+ this._devList[category].push(deviceObj);
292
+ logger_1.logger.debug(`Added ${devType} device to ${category} category`);
293
+ }
294
+ else if (category === 'unknown') {
295
+ logger_1.logger.debug(`Unknown device type: ${devType}`);
296
+ }
297
+ }
298
+ catch (err) {
299
+ logger_1.logger.error(`Error creating device ${devType}:`, err);
300
+ continue;
301
+ }
302
+ }
303
+ return true;
249
304
  }
250
- }
251
- // Add new devices
252
- for (const device of deviceList) {
253
- let foundDevice = false;
254
- // Look for existing devices
255
- for (const devList of Object.values(this._devList)) {
256
- if (devList.some(dev => dev.cid === device.cid)) {
257
- foundDevice = true;
258
- break;
305
+ /**
306
+ * Get list of VeSync devices
307
+ */
308
+ async getDevices() {
309
+ var _a, _b;
310
+ if (!this.enabled) {
311
+ logger_1.logger.error('Not logged in to VeSync');
312
+ return false;
313
+ }
314
+ this._inProcess = true;
315
+ let procReturn = false;
316
+ try {
317
+ const [response] = await helpers_1.Helpers.callApi('/cloud/v2/deviceManaged/devices', 'post', helpers_1.Helpers.reqBody(this, 'devicelist'), helpers_1.Helpers.reqHeaders(this));
318
+ if ((_a = response === null || response === void 0 ? void 0 : response.result) === null || _a === void 0 ? void 0 : _a.list) {
319
+ const deviceList = response.result.list;
320
+ procReturn = this.processDevices(deviceList);
321
+ // Update the main devices array with all devices
322
+ this.devices = Object.values(this._devList).flat();
323
+ // Log device discovery results
324
+ logger_1.logger.debug('\n=== Device Discovery Summary ===');
325
+ logger_1.logger.debug(`Total devices processed: ${deviceList.length}`);
326
+ // Log device types found
327
+ const deviceTypes = deviceList.map((d) => d.deviceType);
328
+ logger_1.logger.debug('\nDevice types found:', deviceTypes);
329
+ // Log devices by category with details
330
+ logger_1.logger.debug('\nDevices by Category:');
331
+ logger_1.logger.debug('---------------------');
332
+ for (const [category, devices] of Object.entries(this._devList)) {
333
+ if (devices.length > 0) {
334
+ logger_1.logger.debug(`\n${category.toUpperCase()} (${devices.length} devices):`);
335
+ devices.forEach((d) => {
336
+ logger_1.logger.debug(` • ${d.deviceName}`);
337
+ logger_1.logger.debug(` Type: ${d.deviceType}`);
338
+ logger_1.logger.debug(` Status: ${d.deviceStatus}`);
339
+ logger_1.logger.debug(` ID: ${d.cid}`);
340
+ });
341
+ }
342
+ }
343
+ // Log summary statistics
344
+ logger_1.logger.debug('\nSummary Statistics:');
345
+ logger_1.logger.debug('-------------------');
346
+ logger_1.logger.debug(`Total Devices: ${((_b = this.devices) === null || _b === void 0 ? void 0 : _b.length) || 0}`);
347
+ for (const [category, devices] of Object.entries(this._devList)) {
348
+ logger_1.logger.debug(`${category}: ${devices.length} devices`);
349
+ }
350
+ logger_1.logger.debug('\n=== End of Device Discovery ===\n');
351
+ }
352
+ else {
353
+ logger_1.logger.error('No devices found in response');
354
+ }
355
+ }
356
+ catch (error) {
357
+ logger_1.logger.error('Unable to get device list:', error);
259
358
  }
359
+ this._inProcess = false;
360
+ return procReturn;
260
361
  }
261
- // If device not found, add it
262
- if (!foundDevice) {
263
- const [deviceType, deviceObj] = objectFactory(device.deviceType, device, this);
264
- if (deviceObj) {
265
- this._devList[deviceType].push(deviceObj);
362
+ /**
363
+ * Login to VeSync server
364
+ */
365
+ async login() {
366
+ var _a;
367
+ const body = helpers_1.Helpers.reqBody(this, 'login');
368
+ logger_1.logger.debug('Login request:', {
369
+ url: `${process.env.VESYNC_API_URL}/cloud/v1/user/login`,
370
+ body
371
+ });
372
+ try {
373
+ const [response, status] = await helpers_1.Helpers.callApi('/cloud/v1/user/login', 'post', body);
374
+ logger_1.logger.debug('Login response:', { status, response });
375
+ if ((_a = response === null || response === void 0 ? void 0 : response.result) === null || _a === void 0 ? void 0 : _a.token) {
376
+ this.token = response.result.token;
377
+ this.accountId = response.result.accountID;
378
+ this.countryCode = response.result.countryCode;
379
+ this.enabled = true;
380
+ return true;
381
+ }
382
+ logger_1.logger.error('Unable to login with supplied credentials');
383
+ return false;
384
+ }
385
+ catch (error) {
386
+ logger_1.logger.error('Login error:', error);
387
+ return false;
266
388
  }
267
389
  }
268
- }
269
- /**
270
- * Update all devices
271
- */
272
- async;
273
- update();
274
- Promise < void > {
275
- : .enabled
276
- };
277
- {
278
- console.error('Not logged in');
279
- return;
280
- }
281
- if (this.inProcess) {
282
- console.debug('Update already in process');
283
- return;
284
- }
285
- const currentTime = Date.now();
286
- if (this.lastUpdateTs &&
287
- currentTime - this.lastUpdateTs < this.updateInterval * 1000) {
288
- console.debug('Update rate limit - waiting %d seconds', this.updateInterval - (currentTime - this.lastUpdateTs) / 1000);
289
- return;
290
- }
291
- this.inProcess = true;
292
- this.lastUpdateTs = currentTime;
293
- try {
294
- await this.getDevices();
295
- this.processDevices();
296
- const updatePromises = [];
297
- for (const deviceList of Object.values(this._devList)) {
298
- for (const device of deviceList) {
299
- if ('update' in device && typeof device.update === 'function') {
300
- updatePromises.push(device.update());
390
+ /**
391
+ * Test if update interval has been exceeded
392
+ */
393
+ deviceTimeCheck() {
394
+ return (this._lastUpdateTs === null ||
395
+ (Date.now() - this._lastUpdateTs) / 1000 > this.updateInterval);
396
+ }
397
+ /**
398
+ * Update device list and details
399
+ */
400
+ async update() {
401
+ if (this.deviceTimeCheck()) {
402
+ if (!this.enabled) {
403
+ logger_1.logger.error('Not logged in to VeSync');
404
+ return;
301
405
  }
406
+ await this.getDevices();
407
+ logger_1.logger.debug('Start updating the device details one by one');
408
+ for (const deviceList of Object.values(this._devList)) {
409
+ for (const device of deviceList) {
410
+ try {
411
+ await device.getDetails();
412
+ }
413
+ catch (error) {
414
+ logger_1.logger.error(`Error updating ${device.deviceName}:`, error);
415
+ }
416
+ }
417
+ }
418
+ this._lastUpdateTs = Date.now();
302
419
  }
303
420
  }
304
- await Promise.all(updatePromises);
305
- }
306
- finally {
307
- this.inProcess = false;
421
+ /**
422
+ * Create device instance from details
423
+ */
424
+ createDevice(details) {
425
+ const deviceType = details.deviceType;
426
+ const deviceClass = vesyncFanImpl_1.fanModules[deviceType];
427
+ if (deviceClass) {
428
+ return new deviceClass(details, this);
429
+ }
430
+ return null;
431
+ }
308
432
  }
309
- //# sourceMappingURL=vesync.js.map
433
+ exports.VeSync = VeSync;