tsvesync 1.0.70 → 1.0.72

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.
@@ -0,0 +1,150 @@
1
+ import { VeSyncFan } from '../vesyncFan';
2
+ import { VeSync } from '../vesync';
3
+ /**
4
+ * VeSync Superior 6000S Humidifier Class
5
+ * Implementation based on PyVeSync's VeSyncSuperior6000S class
6
+ */
7
+ export declare class VeSyncSuperior6000S extends VeSyncFan {
8
+ protected readonly modes: readonly ["auto", "manual", "sleep", "humidity"];
9
+ protected readonly mistLevels: number[];
10
+ protected readonly humidityRange: {
11
+ min: number;
12
+ max: number;
13
+ };
14
+ protected readonly _apiModes: string[];
15
+ details: {
16
+ mode: string;
17
+ speed?: number;
18
+ filter_life?: number;
19
+ screen_status?: 'on' | 'off';
20
+ child_lock?: boolean;
21
+ humidity: number;
22
+ target_humidity: number;
23
+ mist_level: number;
24
+ mist_virtual_level: number;
25
+ water_lacks: boolean;
26
+ water_tank_lifted: boolean;
27
+ display: boolean;
28
+ filter_life_percentage: number;
29
+ temperature: number;
30
+ drying_mode: {
31
+ autoDryingSwitch?: number;
32
+ dryingState?: number;
33
+ dryingLevel?: number;
34
+ dryingRemain?: number;
35
+ };
36
+ configuration: Record<string, any>;
37
+ connection_status: string | null;
38
+ };
39
+ constructor(details: Record<string, any>, manager: VeSync);
40
+ /**
41
+ * Build API dictionary for humidifier
42
+ */
43
+ protected buildApiDict(method: string): [Record<string, any>, Record<string, any>];
44
+ /**
45
+ * Get device details
46
+ */
47
+ getDetails(): Promise<Boolean>;
48
+ /**
49
+ * Turn device on
50
+ */
51
+ turnOn(): Promise<boolean>;
52
+ /**
53
+ * Turn device off
54
+ */
55
+ turnOff(): Promise<boolean>;
56
+ /**
57
+ * Toggle device power
58
+ */
59
+ toggleSwitch(enabled: boolean): Promise<boolean>;
60
+ /**
61
+ * Set mist level
62
+ */
63
+ setMistLevel(level: number): Promise<boolean>;
64
+ /**
65
+ * Change fan speed - Implemented to satisfy interface but redirects to setMistLevel
66
+ */
67
+ changeFanSpeed(speed: number): Promise<boolean>;
68
+ /**
69
+ * Set device mode
70
+ */
71
+ setMode(mode: string): Promise<boolean>;
72
+ /**
73
+ * Set target humidity
74
+ */
75
+ setHumidity(humidity: number): Promise<boolean>;
76
+ /**
77
+ * Set display status
78
+ */
79
+ setDisplay(enabled: boolean): Promise<boolean>;
80
+ /**
81
+ * Set drying mode enabled
82
+ */
83
+ setDryingModeEnabled(enabled: boolean): Promise<boolean>;
84
+ /**
85
+ * Turn on display
86
+ */
87
+ turnOnDisplay(): Promise<boolean>;
88
+ /**
89
+ * Turn off display
90
+ */
91
+ turnOffDisplay(): Promise<boolean>;
92
+ /**
93
+ * Set auto mode
94
+ */
95
+ setAutoMode(): Promise<boolean>;
96
+ /**
97
+ * Set manual mode
98
+ */
99
+ setManualMode(): Promise<boolean>;
100
+ /**
101
+ * Get current humidity
102
+ * Provides access to the current humidity reading
103
+ */
104
+ get currentHumidity(): number;
105
+ /**
106
+ * Get target humidity
107
+ * Provides access to the target humidity setting
108
+ */
109
+ get targetHumidity(): number;
110
+ /**
111
+ * Get current temperature
112
+ * Provides access to the current temperature reading
113
+ */
114
+ get temperature(): number;
115
+ /**
116
+ * Check if water tank is empty
117
+ * Returns true if water tank is empty and needs to be refilled
118
+ */
119
+ get waterLacks(): boolean;
120
+ /**
121
+ * Check if water tank is lifted
122
+ * Returns true if water tank is lifted/removed from the device
123
+ */
124
+ get waterTankLifted(): boolean;
125
+ /**
126
+ * Get filter life percentage
127
+ * Returns the percentage of filter life remaining
128
+ */
129
+ get filterLifePercentage(): number;
130
+ /**
131
+ * Check if drying mode is enabled
132
+ * Returns true if drying mode is enabled
133
+ */
134
+ get dryingModeEnabled(): boolean;
135
+ /**
136
+ * Get drying mode state
137
+ * Returns 'on' if drying mode is active, 'off' if inactive, null if unknown
138
+ */
139
+ get dryingModeState(): string | null;
140
+ /**
141
+ * Get drying mode level
142
+ * Returns 'low' if level is 1, 'high' if level is 2, null if unknown
143
+ */
144
+ get dryingModeLevel(): string | null;
145
+ /**
146
+ * Get drying mode seconds remaining
147
+ * Returns the number of seconds remaining in drying mode
148
+ */
149
+ get dryingModeSecondsRemaining(): number;
150
+ }
@@ -0,0 +1,360 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.VeSyncSuperior6000S = void 0;
4
+ const vesyncFan_1 = require("../vesyncFan");
5
+ const helpers_1 = require("../helpers");
6
+ const logger_1 = require("../logger");
7
+ /**
8
+ * VeSync Superior 6000S Humidifier Class
9
+ * Implementation based on PyVeSync's VeSyncSuperior6000S class
10
+ */
11
+ class VeSyncSuperior6000S extends vesyncFan_1.VeSyncFan {
12
+ constructor(details, manager) {
13
+ super(details, manager);
14
+ this.modes = ['auto', 'manual', 'sleep', 'humidity'];
15
+ this.mistLevels = [1, 2, 3, 4, 5, 6, 7, 8, 9];
16
+ this.humidityRange = { min: 30, max: 80 };
17
+ this._apiModes = [
18
+ 'getHumidifierStatus',
19
+ 'setSwitch',
20
+ 'setVirtualLevel',
21
+ 'setTargetHumidity',
22
+ 'setHumidityMode',
23
+ 'setDisplay',
24
+ 'setDryingMode',
25
+ ];
26
+ // Initialize details object
27
+ this.details = {
28
+ mode: '',
29
+ speed: 0,
30
+ filter_life: 0,
31
+ screen_status: 'off',
32
+ child_lock: false,
33
+ humidity: 0,
34
+ target_humidity: 0,
35
+ mist_level: 0,
36
+ mist_virtual_level: 0,
37
+ water_lacks: false,
38
+ water_tank_lifted: false,
39
+ display: false,
40
+ filter_life_percentage: 0,
41
+ temperature: 0,
42
+ drying_mode: {},
43
+ configuration: {},
44
+ connection_status: null
45
+ };
46
+ // Update config for Superior 6000S
47
+ this.config = {
48
+ module: 'VeSyncAirBypass', // This doesn't matter as we're implementing directly
49
+ features: ['display', 'humidity', 'mist', 'timer', 'auto_mode', 'drying'],
50
+ levels: this.mistLevels
51
+ };
52
+ logger_1.logger.debug(`Initialized VeSyncSuperior6000S device: ${this.deviceName}`);
53
+ }
54
+ /**
55
+ * Build API dictionary for humidifier
56
+ */
57
+ buildApiDict(method) {
58
+ if (!this._apiModes.includes(method)) {
59
+ logger_1.logger.debug(`Invalid mode - ${method}`);
60
+ throw new Error(`Invalid mode - ${method}`);
61
+ }
62
+ const head = helpers_1.Helpers.reqHeaderBypass();
63
+ const body = {
64
+ ...helpers_1.Helpers.reqBody(this.manager, 'bypassV2'),
65
+ cid: this.cid,
66
+ configModule: this.configModule,
67
+ payload: {
68
+ method: method,
69
+ source: 'APP',
70
+ data: {}
71
+ }
72
+ };
73
+ return [head, body];
74
+ }
75
+ /**
76
+ * Get device details
77
+ */
78
+ async getDetails() {
79
+ var _a;
80
+ logger_1.logger.debug(`Getting details for device: ${this.deviceName}`);
81
+ const [head, body] = this.buildApiDict('getHumidifierStatus');
82
+ const [response, status] = await this.callApi('/cloud/v2/deviceManaged/bypassV2', 'post', body, head);
83
+ const success = this.checkResponse([response, status], 'getDetails');
84
+ if (success && ((_a = response === null || response === void 0 ? void 0 : response.result) === null || _a === void 0 ? void 0 : _a.result)) {
85
+ const result = response.result.result;
86
+ // Update device status based on powerSwitch field
87
+ this.deviceStatus = result.powerSwitch === 1 ? 'on' : 'off';
88
+ // Build details object with Superior 6000S specific fields
89
+ this.details = {
90
+ mode: result.workMode === 'autoPro' ? 'auto' : result.workMode || '',
91
+ humidity: result.humidity || 0,
92
+ target_humidity: result.targetHumidity || 0,
93
+ mist_level: result.mistLevel || 0,
94
+ mist_virtual_level: result.virtualLevel || 0,
95
+ water_lacks: result.waterLacksState || false,
96
+ water_tank_lifted: result.waterTankLifted || false,
97
+ display: result.screenSwitch === 1,
98
+ filter_life_percentage: result.filterLifePercent || 0,
99
+ temperature: result.temperature || 0,
100
+ drying_mode: result.dryingMode || {},
101
+ configuration: result.configuration || {},
102
+ connection_status: result.connectionStatus || null
103
+ };
104
+ logger_1.logger.debug(`Successfully got details for device: ${this.deviceName}`);
105
+ }
106
+ return success;
107
+ }
108
+ /**
109
+ * Turn device on
110
+ */
111
+ async turnOn() {
112
+ return this.toggleSwitch(true);
113
+ }
114
+ /**
115
+ * Turn device off
116
+ */
117
+ async turnOff() {
118
+ return this.toggleSwitch(false);
119
+ }
120
+ /**
121
+ * Toggle device power
122
+ */
123
+ async toggleSwitch(enabled) {
124
+ logger_1.logger.info(`Setting device power to ${enabled ? 'on' : 'off'}: ${this.deviceName}`);
125
+ const [head, body] = this.buildApiDict('setSwitch');
126
+ body.payload.data = {
127
+ powerSwitch: enabled ? 1 : 0,
128
+ switchIdx: 0
129
+ };
130
+ const [response, status] = await this.callApi('/cloud/v2/deviceManaged/bypassV2', 'post', body, head);
131
+ const success = this.checkResponse([response, status], 'toggleSwitch');
132
+ if (success) {
133
+ this.deviceStatus = enabled ? 'on' : 'off';
134
+ return true;
135
+ }
136
+ logger_1.logger.error(`Failed to set device power to ${enabled ? 'on' : 'off'} for device: ${this.deviceName}`);
137
+ return false;
138
+ }
139
+ /**
140
+ * Set mist level
141
+ */
142
+ async setMistLevel(level) {
143
+ if (!this.mistLevels.includes(level)) {
144
+ const error = `Invalid mist level: ${level}. Must be one of: ${this.mistLevels.join(', ')}`;
145
+ logger_1.logger.error(`${error} for device: ${this.deviceName}`);
146
+ throw new Error(error);
147
+ }
148
+ logger_1.logger.info(`Setting mist level to ${level} for device: ${this.deviceName}`);
149
+ const [head, body] = this.buildApiDict('setVirtualLevel');
150
+ body.payload.data = {
151
+ levelIdx: 0,
152
+ virtualLevel: level,
153
+ levelType: 'mist'
154
+ };
155
+ const [response, status] = await this.callApi('/cloud/v2/deviceManaged/bypassV2', 'post', body, head);
156
+ const success = this.checkResponse([response, status], 'setMistLevel');
157
+ if (!success) {
158
+ logger_1.logger.error(`Failed to set mist level to ${level} for device: ${this.deviceName}`);
159
+ }
160
+ return success;
161
+ }
162
+ /**
163
+ * Change fan speed - Implemented to satisfy interface but redirects to setMistLevel
164
+ */
165
+ async changeFanSpeed(speed) {
166
+ logger_1.logger.debug(`Redirecting fan speed change to mist level for device: ${this.deviceName}`);
167
+ return this.setMistLevel(speed);
168
+ }
169
+ /**
170
+ * Set device mode
171
+ */
172
+ async setMode(mode) {
173
+ if (!this.modes.includes(mode)) {
174
+ const error = `Invalid mode: ${mode}. Must be one of: ${this.modes.join(', ')}`;
175
+ logger_1.logger.error(`${error} for device: ${this.deviceName}`);
176
+ throw new Error(error);
177
+ }
178
+ logger_1.logger.debug(`Setting mode to ${mode} for device: ${this.deviceName}`);
179
+ const [head, body] = this.buildApiDict('setHumidityMode');
180
+ body.payload.data = {
181
+ workMode: mode === 'auto' ? 'autoPro' : mode
182
+ };
183
+ const [response, status] = await this.callApi('/cloud/v2/deviceManaged/bypassV2', 'post', body, head);
184
+ const success = this.checkResponse([response, status], 'setMode');
185
+ if (success) {
186
+ this.details.mode = mode;
187
+ }
188
+ else {
189
+ logger_1.logger.error(`Failed to set mode to ${mode} for device: ${this.deviceName}`);
190
+ }
191
+ return success;
192
+ }
193
+ /**
194
+ * Set target humidity
195
+ */
196
+ async setHumidity(humidity) {
197
+ if (humidity < this.humidityRange.min || humidity > this.humidityRange.max) {
198
+ const error = `Invalid humidity: ${humidity}. Must be between ${this.humidityRange.min} and ${this.humidityRange.max}`;
199
+ logger_1.logger.error(`${error} for device: ${this.deviceName}`);
200
+ throw new Error(error);
201
+ }
202
+ logger_1.logger.debug(`Setting target humidity to ${humidity}% for device: ${this.deviceName}`);
203
+ const [head, body] = this.buildApiDict('setTargetHumidity');
204
+ body.payload.data = {
205
+ targetHumidity: humidity
206
+ };
207
+ const [response, status] = await this.callApi('/cloud/v2/deviceManaged/bypassV2', 'post', body, head);
208
+ const success = this.checkResponse([response, status], 'setHumidity');
209
+ if (!success) {
210
+ logger_1.logger.error(`Failed to set target humidity to ${humidity}% for device: ${this.deviceName}`);
211
+ }
212
+ return success;
213
+ }
214
+ /**
215
+ * Set display status
216
+ */
217
+ async setDisplay(enabled) {
218
+ logger_1.logger.debug(`Setting display to ${enabled ? 'on' : 'off'} for device: ${this.deviceName}`);
219
+ const [head, body] = this.buildApiDict('setDisplay');
220
+ body.payload.data = {
221
+ screenSwitch: enabled ? 1 : 0
222
+ };
223
+ const [response, status] = await this.callApi('/cloud/v2/deviceManaged/bypassV2', 'post', body, head);
224
+ const success = this.checkResponse([response, status], 'setDisplay');
225
+ if (!success) {
226
+ logger_1.logger.error(`Failed to set display to ${enabled ? 'on' : 'off'} for device: ${this.deviceName}`);
227
+ }
228
+ return success;
229
+ }
230
+ /**
231
+ * Set drying mode enabled
232
+ */
233
+ async setDryingModeEnabled(enabled) {
234
+ logger_1.logger.debug(`Setting drying mode to ${enabled ? 'enabled' : 'disabled'} for device: ${this.deviceName}`);
235
+ const [head, body] = this.buildApiDict('setDryingMode');
236
+ body.payload.data = {
237
+ autoDryingSwitch: enabled ? 1 : 0
238
+ };
239
+ const [response, status] = await this.callApi('/cloud/v2/deviceManaged/bypassV2', 'post', body, head);
240
+ const success = this.checkResponse([response, status], 'setDryingModeEnabled');
241
+ if (!success) {
242
+ logger_1.logger.error(`Failed to set drying mode to ${enabled ? 'enabled' : 'disabled'} for device: ${this.deviceName}`);
243
+ }
244
+ return success;
245
+ }
246
+ /**
247
+ * Turn on display
248
+ */
249
+ async turnOnDisplay() {
250
+ logger_1.logger.debug(`Turning on display for device: ${this.deviceName}`);
251
+ return this.setDisplay(true);
252
+ }
253
+ /**
254
+ * Turn off display
255
+ */
256
+ async turnOffDisplay() {
257
+ logger_1.logger.debug(`Turning off display for device: ${this.deviceName}`);
258
+ return this.setDisplay(false);
259
+ }
260
+ /**
261
+ * Set auto mode
262
+ */
263
+ async setAutoMode() {
264
+ logger_1.logger.debug(`Setting auto mode for device: ${this.deviceName}`);
265
+ return this.setMode('auto');
266
+ }
267
+ /**
268
+ * Set manual mode
269
+ */
270
+ async setManualMode() {
271
+ logger_1.logger.debug(`Setting manual mode for device: ${this.deviceName}`);
272
+ return this.setMode('manual');
273
+ }
274
+ /**
275
+ * Get current humidity
276
+ * Provides access to the current humidity reading
277
+ */
278
+ get currentHumidity() {
279
+ return this.details.humidity || 0;
280
+ }
281
+ /**
282
+ * Get target humidity
283
+ * Provides access to the target humidity setting
284
+ */
285
+ get targetHumidity() {
286
+ return this.details.target_humidity || 0;
287
+ }
288
+ /**
289
+ * Get current temperature
290
+ * Provides access to the current temperature reading
291
+ */
292
+ get temperature() {
293
+ return this.details.temperature || 0;
294
+ }
295
+ /**
296
+ * Check if water tank is empty
297
+ * Returns true if water tank is empty and needs to be refilled
298
+ */
299
+ get waterLacks() {
300
+ return this.details.water_lacks || false;
301
+ }
302
+ /**
303
+ * Check if water tank is lifted
304
+ * Returns true if water tank is lifted/removed from the device
305
+ */
306
+ get waterTankLifted() {
307
+ return this.details.water_tank_lifted || false;
308
+ }
309
+ /**
310
+ * Get filter life percentage
311
+ * Returns the percentage of filter life remaining
312
+ */
313
+ get filterLifePercentage() {
314
+ return this.details.filter_life_percentage || 0;
315
+ }
316
+ /**
317
+ * Check if drying mode is enabled
318
+ * Returns true if drying mode is enabled
319
+ */
320
+ get dryingModeEnabled() {
321
+ var _a;
322
+ const enabled = (_a = this.details.drying_mode) === null || _a === void 0 ? void 0 : _a.autoDryingSwitch;
323
+ return enabled === 1;
324
+ }
325
+ /**
326
+ * Get drying mode state
327
+ * Returns 'on' if drying mode is active, 'off' if inactive, null if unknown
328
+ */
329
+ get dryingModeState() {
330
+ var _a;
331
+ const state = (_a = this.details.drying_mode) === null || _a === void 0 ? void 0 : _a.dryingState;
332
+ if (state === 1)
333
+ return 'on';
334
+ if (state === 2)
335
+ return 'off';
336
+ return null;
337
+ }
338
+ /**
339
+ * Get drying mode level
340
+ * Returns 'low' if level is 1, 'high' if level is 2, null if unknown
341
+ */
342
+ get dryingModeLevel() {
343
+ var _a;
344
+ const level = (_a = this.details.drying_mode) === null || _a === void 0 ? void 0 : _a.dryingLevel;
345
+ if (level === 1)
346
+ return 'low';
347
+ if (level === 2)
348
+ return 'high';
349
+ return null;
350
+ }
351
+ /**
352
+ * Get drying mode seconds remaining
353
+ * Returns the number of seconds remaining in drying mode
354
+ */
355
+ get dryingModeSecondsRemaining() {
356
+ var _a;
357
+ return ((_a = this.details.drying_mode) === null || _a === void 0 ? void 0 : _a.dryingRemain) || 0;
358
+ }
359
+ }
360
+ exports.VeSyncSuperior6000S = VeSyncSuperior6000S;
@@ -5,7 +5,7 @@ import { VeSyncBaseDevice } from './vesyncBaseDevice';
5
5
  import { VeSync } from './vesync';
6
6
  interface FanConfig {
7
7
  [key: string]: {
8
- module: 'VeSyncAirBypass' | 'VeSyncHumidifier' | 'VeSyncWarmHumidifier' | 'VeSyncTowerFan' | 'VeSyncAirBaseV2';
8
+ module: 'VeSyncAirBypass' | 'VeSyncHumidifier' | 'VeSyncWarmHumidifier' | 'VeSyncTowerFan' | 'VeSyncAirBaseV2' | 'VeSyncSuperior6000S' | 'VeSyncHumid1000S' | 'VeSyncHumid200S';
9
9
  features: string[];
10
10
  levels?: number[];
11
11
  };
@@ -35,7 +35,7 @@ export declare abstract class VeSyncFan extends VeSyncBaseDevice {
35
35
  action: string;
36
36
  } | null;
37
37
  protected config: {
38
- module: 'VeSyncAirBypass' | 'VeSyncHumidifier' | 'VeSyncWarmHumidifier' | 'VeSyncTowerFan' | 'VeSyncAirBaseV2';
38
+ module: 'VeSyncAirBypass' | 'VeSyncHumidifier' | 'VeSyncWarmHumidifier' | 'VeSyncTowerFan' | 'VeSyncAirBaseV2' | 'VeSyncSuperior6000S' | 'VeSyncHumid1000S' | 'VeSyncHumid200S';
39
39
  features: string[];
40
40
  levels?: number[];
41
41
  };
@@ -192,8 +192,9 @@ exports.fanConfig = {
192
192
  features: ['display', 'humidity', 'mist', 'timer', 'auto_mode']
193
193
  },
194
194
  'Classic200S': {
195
- module: 'VeSyncHumidifier',
196
- features: ['display', 'humidity', 'mist', 'timer', 'auto_mode']
195
+ module: 'VeSyncHumid200S',
196
+ features: ['display', 'humidity', 'mist', 'timer', 'auto_mode'],
197
+ levels: [1, 2, 3]
197
198
  },
198
199
  // Dual Series
199
200
  'Dual200S': {
@@ -266,21 +267,25 @@ exports.fanConfig = {
266
267
  features: ['display', 'humidity', 'mist', 'warm', 'timer', 'auto_mode']
267
268
  },
268
269
  'LUH-M101S-WUS': {
269
- module: 'VeSyncWarmHumidifier',
270
- features: ['display', 'humidity', 'mist', 'warm', 'timer', 'auto_mode']
270
+ module: 'VeSyncHumid1000S',
271
+ features: ['display', 'humidity', 'mist', 'timer', 'auto_mode', 'night_light'],
272
+ levels: [1, 2, 3, 4, 5, 6, 7, 8, 9]
271
273
  },
272
274
  'LUH-M101S-WEUR': {
273
- module: 'VeSyncWarmHumidifier',
274
- features: ['display', 'humidity', 'mist', 'warm', 'timer', 'auto_mode']
275
+ module: 'VeSyncHumid1000S',
276
+ features: ['display', 'humidity', 'mist', 'timer', 'auto_mode', 'night_light'],
277
+ levels: [1, 2, 3, 4, 5, 6, 7, 8, 9]
275
278
  },
276
- // LEH Series
279
+ // LEH Series - Superior 6000S
277
280
  'LEH-S601S-WUS': {
278
- module: 'VeSyncWarmHumidifier',
279
- features: ['display', 'humidity', 'mist', 'warm', 'timer', 'auto_mode', 'drying']
281
+ module: 'VeSyncSuperior6000S',
282
+ features: ['display', 'humidity', 'mist', 'timer', 'auto_mode', 'drying', 'temperature'],
283
+ levels: [1, 2, 3, 4, 5, 6, 7, 8, 9]
280
284
  },
281
285
  'LEH-S601S-WUSR': {
282
- module: 'VeSyncWarmHumidifier',
283
- features: ['display', 'humidity', 'mist', 'warm', 'timer', 'auto_mode', 'drying']
286
+ module: 'VeSyncSuperior6000S',
287
+ features: ['display', 'humidity', 'mist', 'timer', 'auto_mode', 'drying', 'temperature'],
288
+ levels: [1, 2, 3, 4, 5, 6, 7, 8, 9]
284
289
  },
285
290
  // LV Series
286
291
  'LV-PUR131S': {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "tsvesync",
3
- "version": "1.0.70",
3
+ "version": "1.0.72",
4
4
  "description": "A TypeScript library for interacting with VeSync smart home devices",
5
5
  "main": "dist/index.js",
6
6
  "types": "dist/index.d.ts",