@switchbot/homebridge-switchbot 1.10.2-beta.3 → 1.10.2-beta.7

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 (136) hide show
  1. package/CHANGELOG.md +6 -0
  2. package/README.md +10 -0
  3. package/dist/{devices/bots.d.ts → device/bot.d.ts} +3 -3
  4. package/dist/device/bot.d.ts.map +1 -0
  5. package/dist/{devices/bots.js → device/bot.js} +4 -1
  6. package/dist/device/bot.js.map +1 -0
  7. package/dist/{devices → device}/colorbulb.d.ts +7 -1
  8. package/dist/device/colorbulb.d.ts.map +1 -0
  9. package/dist/{devices → device}/colorbulb.js +9 -0
  10. package/dist/device/colorbulb.js.map +1 -0
  11. package/dist/{devices → device}/contact.d.ts +0 -0
  12. package/dist/device/contact.d.ts.map +1 -0
  13. package/dist/{devices → device}/contact.js +0 -0
  14. package/dist/device/contact.js.map +1 -0
  15. package/dist/{devices/curtains.d.ts → device/curtain.d.ts} +1 -1
  16. package/dist/device/curtain.d.ts.map +1 -0
  17. package/dist/{devices/curtains.js → device/curtain.js} +2 -2
  18. package/dist/device/curtain.js.map +1 -0
  19. package/dist/{devices/humidifiers.d.ts → device/humidifier.d.ts} +5 -5
  20. package/dist/device/humidifier.d.ts.map +1 -0
  21. package/dist/{devices/humidifiers.js → device/humidifier.js} +4 -4
  22. package/dist/device/humidifier.js.map +1 -0
  23. package/dist/{devices/plugs.d.ts → device/lock.d.ts} +14 -12
  24. package/dist/device/lock.d.ts.map +1 -0
  25. package/dist/device/lock.js +298 -0
  26. package/dist/device/lock.js.map +1 -0
  27. package/dist/{devices/meters.d.ts → device/meter.d.ts} +2 -1
  28. package/dist/device/meter.d.ts.map +1 -0
  29. package/dist/{devices/meters.js → device/meter.js} +15 -5
  30. package/dist/device/meter.js.map +1 -0
  31. package/dist/{devices → device}/motion.d.ts +2 -2
  32. package/dist/device/motion.d.ts.map +1 -0
  33. package/dist/{devices → device}/motion.js +3 -4
  34. package/dist/device/motion.js.map +1 -0
  35. package/dist/device/plug.d.ts +54 -0
  36. package/dist/device/plug.d.ts.map +1 -0
  37. package/dist/{devices/plugs.js → device/plug.js} +29 -12
  38. package/dist/device/plug.js.map +1 -0
  39. package/dist/{irdevices/airconditioners.d.ts → irdevice/airconditioner.d.ts} +1 -1
  40. package/dist/irdevice/airconditioner.d.ts.map +1 -0
  41. package/dist/{irdevices/airconditioners.js → irdevice/airconditioner.js} +1 -1
  42. package/dist/irdevice/airconditioner.js.map +1 -0
  43. package/dist/{irdevices/airpurifiers.d.ts → irdevice/airpurifier.d.ts} +1 -1
  44. package/dist/irdevice/airpurifier.d.ts.map +1 -0
  45. package/dist/{irdevices/airpurifiers.js → irdevice/airpurifier.js} +1 -1
  46. package/dist/irdevice/airpurifier.js.map +1 -0
  47. package/dist/{irdevices/cameras.d.ts → irdevice/camera.d.ts} +1 -1
  48. package/dist/irdevice/camera.d.ts.map +1 -0
  49. package/dist/{irdevices/cameras.js → irdevice/camera.js} +1 -1
  50. package/dist/irdevice/camera.js.map +1 -0
  51. package/dist/{irdevices/fans.d.ts → irdevice/fan.d.ts} +1 -1
  52. package/dist/irdevice/fan.d.ts.map +1 -0
  53. package/dist/{irdevices/fans.js → irdevice/fan.js} +1 -1
  54. package/dist/irdevice/fan.js.map +1 -0
  55. package/dist/{irdevices/lights.d.ts → irdevice/light.d.ts} +1 -1
  56. package/dist/irdevice/light.d.ts.map +1 -0
  57. package/dist/{irdevices/lights.js → irdevice/light.js} +1 -1
  58. package/dist/irdevice/light.js.map +1 -0
  59. package/dist/{irdevices/others.d.ts → irdevice/other.d.ts} +1 -1
  60. package/dist/irdevice/other.d.ts.map +1 -0
  61. package/dist/{irdevices/others.js → irdevice/other.js} +1 -1
  62. package/dist/irdevice/other.js.map +1 -0
  63. package/dist/{irdevices/tvs.d.ts → irdevice/tv.d.ts} +1 -1
  64. package/dist/irdevice/tv.d.ts.map +1 -0
  65. package/dist/{irdevices/tvs.js → irdevice/tv.js} +1 -1
  66. package/dist/irdevice/tv.js.map +1 -0
  67. package/dist/{irdevices/vacuumcleaners.d.ts → irdevice/vacuumcleaner.d.ts} +1 -1
  68. package/dist/irdevice/vacuumcleaner.d.ts.map +1 -0
  69. package/dist/{irdevices/vacuumcleaners.js → irdevice/vacuumcleaner.js} +1 -1
  70. package/dist/irdevice/vacuumcleaner.js.map +1 -0
  71. package/dist/{irdevices/waterheaters.d.ts → irdevice/waterheater.d.ts} +1 -1
  72. package/dist/irdevice/waterheater.d.ts.map +1 -0
  73. package/dist/{irdevices/waterheaters.js → irdevice/waterheater.js} +1 -1
  74. package/dist/irdevice/waterheater.js.map +1 -0
  75. package/dist/platform.d.ts +1 -0
  76. package/dist/platform.d.ts.map +1 -1
  77. package/dist/platform.js +106 -45
  78. package/dist/platform.js.map +1 -1
  79. package/dist/settings.d.ts +7 -0
  80. package/dist/settings.d.ts.map +1 -1
  81. package/dist/settings.js.map +1 -1
  82. package/package.json +1 -1
  83. package/src/{devices/bots.ts → device/bot.ts} +5 -2
  84. package/src/{devices → device}/colorbulb.ts +10 -1
  85. package/src/{devices → device}/contact.ts +0 -0
  86. package/src/{devices/curtains.ts → device/curtain.ts} +1 -1
  87. package/src/{devices/humidifiers.ts → device/humidifier.ts} +7 -10
  88. package/src/device/lock.ts +345 -0
  89. package/src/{devices/meters.ts → device/meter.ts} +13 -7
  90. package/src/{devices → device}/motion.ts +5 -9
  91. package/src/{devices/plugs.ts → device/plug.ts} +31 -16
  92. package/src/{irdevices/airconditioners.ts → irdevice/airconditioner.ts} +0 -0
  93. package/src/{irdevices/airpurifiers.ts → irdevice/airpurifier.ts} +0 -0
  94. package/src/{irdevices/cameras.ts → irdevice/camera.ts} +0 -0
  95. package/src/{irdevices/fans.ts → irdevice/fan.ts} +0 -0
  96. package/src/{irdevices/lights.ts → irdevice/light.ts} +0 -0
  97. package/src/{irdevices/others.ts → irdevice/other.ts} +0 -0
  98. package/src/{irdevices/tvs.ts → irdevice/tv.ts} +0 -0
  99. package/src/{irdevices/vacuumcleaners.ts → irdevice/vacuumcleaner.ts} +0 -0
  100. package/src/{irdevices/waterheaters.ts → irdevice/waterheater.ts} +0 -0
  101. package/src/platform.ts +82 -17
  102. package/src/settings.ts +24 -11
  103. package/dist/devices/bots.d.ts.map +0 -1
  104. package/dist/devices/bots.js.map +0 -1
  105. package/dist/devices/colorbulb.d.ts.map +0 -1
  106. package/dist/devices/colorbulb.js.map +0 -1
  107. package/dist/devices/contact.d.ts.map +0 -1
  108. package/dist/devices/contact.js.map +0 -1
  109. package/dist/devices/curtains.d.ts.map +0 -1
  110. package/dist/devices/curtains.js.map +0 -1
  111. package/dist/devices/humidifiers.d.ts.map +0 -1
  112. package/dist/devices/humidifiers.js.map +0 -1
  113. package/dist/devices/meters.d.ts.map +0 -1
  114. package/dist/devices/meters.js.map +0 -1
  115. package/dist/devices/motion.d.ts.map +0 -1
  116. package/dist/devices/motion.js.map +0 -1
  117. package/dist/devices/plugs.d.ts.map +0 -1
  118. package/dist/devices/plugs.js.map +0 -1
  119. package/dist/irdevices/airconditioners.d.ts.map +0 -1
  120. package/dist/irdevices/airconditioners.js.map +0 -1
  121. package/dist/irdevices/airpurifiers.d.ts.map +0 -1
  122. package/dist/irdevices/airpurifiers.js.map +0 -1
  123. package/dist/irdevices/cameras.d.ts.map +0 -1
  124. package/dist/irdevices/cameras.js.map +0 -1
  125. package/dist/irdevices/fans.d.ts.map +0 -1
  126. package/dist/irdevices/fans.js.map +0 -1
  127. package/dist/irdevices/lights.d.ts.map +0 -1
  128. package/dist/irdevices/lights.js.map +0 -1
  129. package/dist/irdevices/others.d.ts.map +0 -1
  130. package/dist/irdevices/others.js.map +0 -1
  131. package/dist/irdevices/tvs.d.ts.map +0 -1
  132. package/dist/irdevices/tvs.js.map +0 -1
  133. package/dist/irdevices/vacuumcleaners.d.ts.map +0 -1
  134. package/dist/irdevices/vacuumcleaners.js.map +0 -1
  135. package/dist/irdevices/waterheaters.d.ts.map +0 -1
  136. package/dist/irdevices/waterheaters.js.map +0 -1
@@ -0,0 +1,345 @@
1
+ import { AxiosResponse } from 'axios';
2
+ import { interval, Subject } from 'rxjs';
3
+ import { SwitchBotPlatform } from '../platform';
4
+ import { debounceTime, skipWhile, take, tap } from 'rxjs/operators';
5
+ import { Service, PlatformAccessory, CharacteristicValue } from 'homebridge';
6
+ import { DeviceURL, device, devicesConfig, deviceStatusResponse, payload, deviceStatus } from '../settings';
7
+
8
+ export class Lock {
9
+ // Services
10
+ private lockService: Service;
11
+ private doorService?: Service;
12
+
13
+ // Characteristic Values
14
+ LockCurrentState!: CharacteristicValue;
15
+ LockTargetState!: CharacteristicValue;
16
+ LockTargetStateCached!: CharacteristicValue;
17
+
18
+ // OpenAPI Others
19
+ doorState!: deviceStatus['doorState'];
20
+ lockState!: deviceStatus['lockState'];
21
+ deviceStatus!: deviceStatusResponse;
22
+
23
+ // Config
24
+ scanDuration!: number;
25
+ deviceLogging!: string;
26
+ deviceRefreshRate!: number;
27
+
28
+ // Updates
29
+ lockUpdateInProgress!: boolean;
30
+ doLockUpdate!: Subject<void>;
31
+
32
+ constructor(private readonly platform: SwitchBotPlatform, private accessory: PlatformAccessory, public device: device & devicesConfig) {
33
+ // default placeholders
34
+ this.logs(device);
35
+ this.scan(device);
36
+ this.refreshRate(device);
37
+ this.config(device);
38
+ if (this.LockTargetState === undefined) {
39
+ this.LockTargetState = false;
40
+ } else {
41
+ this.LockTargetState = this.accessory.context.On;
42
+ }
43
+
44
+ // this is subject we use to track when we need to POST changes to the SwitchBot API
45
+ this.doLockUpdate = new Subject();
46
+ this.lockUpdateInProgress = false;
47
+
48
+ // Retrieve initial values and updateHomekit
49
+ this.refreshStatus();
50
+
51
+ // set accessory information
52
+ accessory
53
+ .getService(this.platform.Service.AccessoryInformation)!
54
+ .setCharacteristic(this.platform.Characteristic.Manufacturer, 'SwitchBot')
55
+ .setCharacteristic(this.platform.Characteristic.Model, 'SWITCHBOT-LOCK-W1601700')
56
+ .setCharacteristic(this.platform.Characteristic.SerialNumber, device.deviceId!);
57
+
58
+ // get the WindowCovering service if it exists, otherwise create a new WindowCovering service
59
+ // you can create multiple services for each accessory
60
+ (this.lockService = accessory.getService(this.platform.Service.Outlet) || accessory.addService(this.platform.Service.Outlet)),
61
+ `${device.deviceName} ${device.deviceType}`;
62
+
63
+ // To avoid "Cannot add a Service with the same UUID another Service without also defining a unique 'subtype' property." error,
64
+ // when creating multiple services of the same type, you need to use the following syntax to specify a name and subtype id:
65
+ // accessory.getService('NAME') ?? accessory.addService(this.platform.Service.Lightbulb, 'NAME', 'USER_DEFINED_SUBTYPE');
66
+
67
+ // set the service name, this is what is displayed as the default name on the Home app
68
+ // in this example we are using the name we stored in the `accessory.context` in the `discoverDevices` method.
69
+ this.lockService.setCharacteristic(this.platform.Characteristic.Name, accessory.displayName);
70
+
71
+ // each service must implement at-minimum the "required characteristics" for the given service type
72
+ // see https://developers.homebridge.io/#/service/WindowCovering
73
+
74
+ // create handlers for required characteristics
75
+ this.lockService.getCharacteristic(this.platform.Characteristic.LockCurrentState).onSet(this.LockTargetStateSet.bind(this));
76
+
77
+ // Update Homekit
78
+ this.updateHomeKitCharacteristics();
79
+
80
+ // Start an update interval
81
+ interval(this.deviceRefreshRate * 1000)
82
+ .pipe(skipWhile(() => this.lockUpdateInProgress))
83
+ .subscribe(() => {
84
+ this.refreshStatus();
85
+ });
86
+
87
+ // Watch for Lock change events
88
+ // We put in a debounce of 100ms so we don't make duplicate calls
89
+ this.doLockUpdate
90
+ .pipe(
91
+ tap(() => {
92
+ this.lockUpdateInProgress = true;
93
+ }),
94
+ debounceTime(this.platform.config.options!.pushRate! * 1000),
95
+ )
96
+ .subscribe(async () => {
97
+ try {
98
+ await this.pushChanges();
99
+ } catch (e: any) {
100
+ this.errorLog(`Lock: ${this.accessory.displayName} failed pushChanges`);
101
+ if (this.deviceLogging === 'debug') {
102
+ this.errorLog(`Lock: ${this.accessory.displayName} failed pushChanges,` + ` Error Message: ${JSON.stringify(e.message)}`);
103
+ }
104
+ if (this.platform.debugMode) {
105
+ this.errorLog(`Lock: ${this.accessory.displayName} failed pushChanges,` + ` Error: ${JSON.stringify(e)}`);
106
+ }
107
+ this.apiError(e);
108
+ }
109
+ this.lockUpdateInProgress = false;
110
+ });
111
+ }
112
+
113
+ parseStatus() {
114
+ switch (this.lockState) {
115
+ case 'on':
116
+ this.LockCurrentState = this.platform.Characteristic.LockCurrentState.UNSECURED;
117
+ break;
118
+ default:
119
+ this.LockCurrentState = this.platform.Characteristic.LockCurrentState.SECURED;
120
+ }
121
+ this.debugLog(`Lock: ${this.accessory.displayName} On: ${this.LockTargetState}`);
122
+ }
123
+
124
+ private async refreshStatus() {
125
+ try {
126
+ this.deviceStatus = (await this.platform.axios.get(`${DeviceURL}/${this.device.deviceId}/status`)).data;
127
+ this.debugLog(`Lock: ${this.accessory.displayName} refreshStatus: ${JSON.stringify(this.deviceStatus)}`);
128
+ this.lockState = this.deviceStatus.body.lockState;
129
+ this.warnLog(`Lock: ${this.accessory.displayName} lockState: ${JSON.stringify(this.lockState)} (COPY THIS LOG)`);
130
+ this.doorState = this.deviceStatus.body.doorState;
131
+ this.debugLog(`Lock: ${this.accessory.displayName} doorState: ${JSON.stringify(this.doorState)} (COPY THIS LOG)`);
132
+ this.parseStatus();
133
+ this.updateHomeKitCharacteristics();
134
+ } catch (e: any) {
135
+ this.errorLog(`Lock: ${this.accessory.displayName} failed refreshStatus with OpenAPI Connection`);
136
+ if (this.deviceLogging === 'debug') {
137
+ this.errorLog(
138
+ `Lock: ${this.accessory.displayName} failed refreshStatus with OpenAPI Connection,` + ` Error Message: ${JSON.stringify(e.message)}`,
139
+ );
140
+ }
141
+ if (this.platform.debugMode) {
142
+ this.errorLog(`Lock: ${this.accessory.displayName} failed refreshStatus with OpenAPI Connection,` + ` Error: ${JSON.stringify(e)}`);
143
+ }
144
+ this.apiError(e);
145
+ }
146
+ }
147
+
148
+ /**
149
+ * Pushes the requested changes to the SwitchBot API
150
+ * deviceType commandType Command command parameter Description
151
+ * Lock - "command" "????" "????" = set to ???? state
152
+ * Lock - "command" "????" "????" = set to ???? state - LockCurrentState
153
+ */
154
+ async pushChanges() {
155
+ if (this.LockTargetState !== this.LockTargetStateCached) {
156
+ const payload = {
157
+ commandType: 'command',
158
+ parameter: 'default',
159
+ } as payload;
160
+
161
+ if (this.LockTargetState) {
162
+ payload.command = 'turnOn';
163
+ } else {
164
+ payload.command = 'turnOff';
165
+ }
166
+
167
+ this.infoLog(
168
+ `Lock: ${this.accessory.displayName} Sending request to SwitchBot API. command: ${payload.command},` +
169
+ ` parameter: ${payload.parameter}, commandType: ${payload.commandType}`,
170
+ );
171
+
172
+ // Make the API request
173
+ const push: any = await this.platform.axios.post(`${DeviceURL}/${this.device.deviceId}/commands`, payload);
174
+ this.debugLog(`Lock: ${this.accessory.displayName} pushchanges: ${JSON.stringify(push.data)}`);
175
+ this.statusCode(push);
176
+ this.LockTargetStateCached = this.LockTargetState;
177
+ this.accessory.context.On = this.LockTargetStateCached;
178
+ }
179
+ interval(5000)
180
+ .pipe(skipWhile(() => this.lockUpdateInProgress))
181
+ .pipe(take(1))
182
+ .subscribe(() => {
183
+ this.refreshStatus();
184
+ });
185
+ }
186
+
187
+ updateHomeKitCharacteristics() {
188
+ if (this.LockTargetState === undefined) {
189
+ this.debugLog(`Lock: ${this.accessory.displayName} LockTargetState: ${this.LockTargetState}`);
190
+ } else {
191
+ this.lockService.updateCharacteristic(this.platform.Characteristic.LockTargetState, this.LockTargetState);
192
+ this.debugLog(`Lock: ${this.accessory.displayName} updateCharacteristic LockTargetState: ${this.LockTargetState}`);
193
+ }
194
+ if (this.LockCurrentState === undefined) {
195
+ this.debugLog(`Lock: ${this.accessory.displayName} LockCurrentState: ${this.LockCurrentState}`);
196
+ } else {
197
+ this.lockService.updateCharacteristic(this.platform.Characteristic.LockCurrentState, this.LockCurrentState);
198
+ this.debugLog(`Lock: ${this.accessory.displayName} updateCharacteristic LockTargetState: ${this.LockCurrentState}`);
199
+ }
200
+ }
201
+
202
+ public apiError(e: any) {
203
+ this.lockService.updateCharacteristic(this.platform.Characteristic.LockTargetState, e);
204
+ this.lockService.updateCharacteristic(this.platform.Characteristic.LockCurrentState, e);
205
+ //throw new this.platform.api.hap.HapStatusError(HAPStatus.SERVICE_COMMUNICATION_FAILURE);
206
+ }
207
+
208
+ private statusCode(push: AxiosResponse<{ statusCode: number }>) {
209
+ switch (push.data.statusCode) {
210
+ case 151:
211
+ this.errorLog(`Lock: ${this.accessory.displayName} Command not supported by this device type.`);
212
+ break;
213
+ case 152:
214
+ this.errorLog(`Lock: ${this.accessory.displayName} Device not found.`);
215
+ break;
216
+ case 160:
217
+ this.errorLog(`Lock: ${this.accessory.displayName} Command is not supported.`);
218
+ break;
219
+ case 161:
220
+ this.errorLog(`Lock: ${this.accessory.displayName} Device is offline.`);
221
+ break;
222
+ case 171:
223
+ this.errorLog(`Lock: ${this.accessory.displayName} Hub Device is offline. Hub: ${this.device.hubDeviceId}`);
224
+ break;
225
+ case 190:
226
+ this.errorLog(
227
+ `Lock: ${this.accessory.displayName} Device internal error due to device states not synchronized with server,` +
228
+ ` Or command: ${JSON.stringify(push.data)} format is invalid`,
229
+ );
230
+ break;
231
+ case 100:
232
+ this.debugLog(`Lock: ${this.accessory.displayName} Command successfully sent.`);
233
+ break;
234
+ default:
235
+ this.debugLog(`Lock: ${this.accessory.displayName} Unknown statusCode.`);
236
+ }
237
+ }
238
+
239
+ /**
240
+ * Handle requests to set the value of the "On" characteristic
241
+ */
242
+ LockTargetStateSet(value: CharacteristicValue) {
243
+ this.debugLog(`Lock: ${this.accessory.displayName} Set LockTargetState: ${value}`);
244
+
245
+ this.LockTargetState = value;
246
+ this.doLockUpdate.next();
247
+ }
248
+
249
+ config(device: device & devicesConfig) {
250
+ let config = {};
251
+ if (device.lock) {
252
+ config = device.lock;
253
+ }
254
+ if (device.ble !== undefined) {
255
+ config['ble'] = device.ble;
256
+ }
257
+ if (device.logging !== undefined) {
258
+ config['logging'] = device.logging;
259
+ }
260
+ if (device.refreshRate !== undefined) {
261
+ config['refreshRate'] = device.refreshRate;
262
+ }
263
+ if (device.scanDuration !== undefined) {
264
+ config['scanDuration'] = device.scanDuration;
265
+ }
266
+ if (Object.entries(config).length !== 0) {
267
+ this.warnLog(`Lock: ${this.accessory.displayName} Config: ${JSON.stringify(config)}`);
268
+ }
269
+ }
270
+
271
+ refreshRate(device: device & devicesConfig) {
272
+ if (device.refreshRate) {
273
+ this.deviceRefreshRate = this.accessory.context.refreshRate = device.refreshRate;
274
+ this.debugLog(`Lock: ${this.accessory.displayName} Using Device Config refreshRate: ${this.deviceRefreshRate}`);
275
+ } else if (this.platform.config.options!.refreshRate) {
276
+ this.deviceRefreshRate = this.accessory.context.refreshRate = this.platform.config.options!.refreshRate;
277
+ this.debugLog(`Lock: ${this.accessory.displayName} Using Platform Config refreshRate: ${this.deviceRefreshRate}`);
278
+ }
279
+ }
280
+
281
+ scan(device: device & devicesConfig) {
282
+ if (device.scanDuration) {
283
+ this.scanDuration = this.accessory.context.scanDuration = device.scanDuration;
284
+ if (device.ble) {
285
+ this.debugLog(`Lock: ${this.accessory.displayName} Using Device Config scanDuration: ${this.scanDuration}`);
286
+ }
287
+ } else {
288
+ this.scanDuration = this.accessory.context.scanDuration = 1;
289
+ if (this.device.ble) {
290
+ this.debugLog(`Lock: ${this.accessory.displayName} Using Default scanDuration: ${this.scanDuration}`);
291
+ }
292
+ }
293
+ }
294
+
295
+ logs(device: device & devicesConfig) {
296
+ if (this.platform.debugMode) {
297
+ this.deviceLogging = this.accessory.context.logging = 'debugMode';
298
+ this.debugLog(`Lock: ${this.accessory.displayName} Using Debug Mode Logging: ${this.deviceLogging}`);
299
+ } else if (device.logging) {
300
+ this.deviceLogging = this.accessory.context.logging = device.logging;
301
+ this.debugLog(`Lock: ${this.accessory.displayName} Using Device Config Logging: ${this.deviceLogging}`);
302
+ } else if (this.platform.config.options?.logging) {
303
+ this.deviceLogging = this.accessory.context.logging = this.platform.config.options?.logging;
304
+ this.debugLog(`Lock: ${this.accessory.displayName} Using Platform Config Logging: ${this.deviceLogging}`);
305
+ } else {
306
+ this.deviceLogging = this.accessory.context.logging = 'standard';
307
+ this.debugLog(`Lock: ${this.accessory.displayName} Logging Not Set, Using: ${this.deviceLogging}`);
308
+ }
309
+ }
310
+
311
+ /**
312
+ * Logging for Device
313
+ */
314
+ infoLog(...log: any[]) {
315
+ if (this.enablingDeviceLogging()) {
316
+ this.platform.log.info(String(...log));
317
+ }
318
+ }
319
+
320
+ warnLog(...log: any[]) {
321
+ if (this.enablingDeviceLogging()) {
322
+ this.platform.log.warn(String(...log));
323
+ }
324
+ }
325
+
326
+ errorLog(...log: any[]) {
327
+ if (this.enablingDeviceLogging()) {
328
+ this.platform.log.error(String(...log));
329
+ }
330
+ }
331
+
332
+ debugLog(...log: any[]) {
333
+ if (this.enablingDeviceLogging()) {
334
+ if (this.deviceLogging === 'debug') {
335
+ this.platform.log.info('[DEBUG]', String(...log));
336
+ } else {
337
+ this.platform.log.debug(String(...log));
338
+ }
339
+ }
340
+ }
341
+
342
+ enablingDeviceLogging(): boolean {
343
+ return this.deviceLogging === 'debug' || this.deviceLogging === 'standard';
344
+ }
345
+ }
@@ -66,12 +66,6 @@ export class Meter {
66
66
  this.CurrentTemperature = this.accessory.context.CurrentTemperature;
67
67
  }
68
68
 
69
- // Meter Config
70
- this.debugLog(
71
- `Meter: ${this.accessory.displayName} Config: (ble: ${device.ble}, hide_temperature: ${device.meter?.hide_temperature},` +
72
- ` hide_humidity: ${device.meter?.hide_humidity})`,
73
- );
74
-
75
69
  // this is subject we use to track when we need to POST changes to the SwitchBot API
76
70
  this.doMeterUpdate = new Subject();
77
71
  this.meterUpdateInProgress = false;
@@ -83,7 +77,7 @@ export class Meter {
83
77
  accessory
84
78
  .getService(this.platform.Service.AccessoryInformation)!
85
79
  .setCharacteristic(this.platform.Characteristic.Manufacturer, 'SwitchBot')
86
- .setCharacteristic(this.platform.Characteristic.Model, 'SWITCHBOT-METERTH-S1')
80
+ .setCharacteristic(this.platform.Characteristic.Model, this.model(device))
87
81
  .setCharacteristic(this.platform.Characteristic.SerialNumber, device.deviceId!);
88
82
 
89
83
  // Temperature Sensor Service
@@ -393,6 +387,18 @@ export class Meter {
393
387
  //throw new this.platform.api.hap.HapStatusError(HAPStatus.SERVICE_COMMUNICATION_FAILURE);
394
388
  }
395
389
 
390
+ model(device: device & devicesConfig): CharacteristicValue {
391
+ let model: string;
392
+ if (device.deviceType === 'Meter Plus (US)') {
393
+ model = 'SWITCHBOT-METERTH-W2301500';
394
+ } else if (device.deviceType === 'Meter Plus (JP)') {
395
+ model = 'SWITCHBOT-METERTH-W2201500';
396
+ } else {
397
+ model = 'SWITCHBOT-METERTH-S1';
398
+ }
399
+ return model;
400
+ }
401
+
396
402
  config(device: device & devicesConfig) {
397
403
  let config = {};
398
404
  if (device.meter) {
@@ -54,13 +54,6 @@ export class Motion {
54
54
  this.config(device);
55
55
  this.MotionDetected = false;
56
56
 
57
- // Motion Config
58
- this.debugLog(
59
- `Motion Sensor: ${this.accessory.displayName} Config: (ble: ${device.ble}, offline: ${device.offline},` +
60
- ` hide_lightsensor: ${device.motion?.hide_lightsensor},` +
61
- ` set_minLux: ${this.device.motion?.set_minLux}, set_maxLux: ${this.device.motion?.set_maxLux})`,
62
- );
63
-
64
57
  // this is subject we use to track when we need to POST changes to the SwitchBot API
65
58
  this.doMotionUpdate = new Subject();
66
59
  this.motionUbpdateInProgress = false;
@@ -390,6 +383,9 @@ export class Motion {
390
383
  if (device.scanDuration !== undefined) {
391
384
  config['scanDuration'] = device.scanDuration;
392
385
  }
386
+ if (device.offline !== undefined) {
387
+ config['offline'] = device.offline;
388
+ }
393
389
  if (Object.entries(config).length !== 0) {
394
390
  this.warnLog(`Motion Sensor: ${this.accessory.displayName} Config: ${JSON.stringify(config)}`);
395
391
  }
@@ -435,7 +431,7 @@ export class Motion {
435
431
  }
436
432
  }
437
433
 
438
- private minLux(): number {
434
+ minLux(): number {
439
435
  if (this.device.motion?.set_minLux) {
440
436
  this.set_minLux = this.device.motion!.set_minLux!;
441
437
  } else {
@@ -444,7 +440,7 @@ export class Motion {
444
440
  return this.set_minLux;
445
441
  }
446
442
 
447
- private maxLux(): number {
443
+ maxLux(): number {
448
444
  if (this.device.motion?.set_maxLux) {
449
445
  this.set_maxLux = this.device.motion!.set_maxLux!;
450
446
  } else {
@@ -38,9 +38,6 @@ export class Plug {
38
38
  this.On = this.accessory.context.On;
39
39
  }
40
40
 
41
- // Plug Config
42
- this.debugLog(`Plug: ${this.accessory.displayName} Config: (offline: ${device.offline})`);
43
-
44
41
  // this is subject we use to track when we need to POST changes to the SwitchBot API
45
42
  this.doPlugUpdate = new Subject();
46
43
  this.plugUpdateInProgress = false;
@@ -52,7 +49,7 @@ export class Plug {
52
49
  accessory
53
50
  .getService(this.platform.Service.AccessoryInformation)!
54
51
  .setCharacteristic(this.platform.Characteristic.Manufacturer, 'SwitchBot')
55
- .setCharacteristic(this.platform.Characteristic.Model, 'SWITCHBOT-PLUG-SP11')
52
+ .setCharacteristic(this.platform.Characteristic.Model, this.model(device))
56
53
  .setCharacteristic(this.platform.Characteristic.SerialNumber, device.deviceId!);
57
54
 
58
55
  // get the WindowCovering service if it exists, otherwise create a new WindowCovering service
@@ -145,8 +142,11 @@ export class Plug {
145
142
  /**
146
143
  * Pushes the requested changes to the SwitchBot API
147
144
  * deviceType commandType Command command parameter Description
148
- * Plug - "command" "turnOff" "default" = set to OFF state
149
- * Plug - "command" "turnOn" "default" = set to ON state
145
+ * Plug - "command" "turnOff" "default" = set to OFF state
146
+ * Plug - "command" "turnOn" "default" = set to ON state
147
+ * Plug Mini (US/JP) - "command" turnOn default = set to ON state
148
+ * Plug Mini (US/JP) - "command" turnOff default = set to OFF state
149
+ * Plug Mini (US/JP) - "command" toggle default = toggle state
150
150
  */
151
151
  async pushChanges() {
152
152
  if (this.On !== this.OnCached) {
@@ -228,7 +228,7 @@ export class Plug {
228
228
  }
229
229
  }
230
230
 
231
- private offlineOff() {
231
+ async offlineOff(): Promise<void> {
232
232
  if (this.device.offline) {
233
233
  this.On = false;
234
234
  this.service.getCharacteristic(this.platform.Characteristic.On).updateValue(this.On);
@@ -238,14 +238,26 @@ export class Plug {
238
238
  /**
239
239
  * Handle requests to set the value of the "On" characteristic
240
240
  */
241
- OnSet(value: CharacteristicValue) {
241
+ async OnSet(value: CharacteristicValue): Promise<void> {
242
242
  this.debugLog(`Plug: ${this.accessory.displayName} - Set On: ${value}`);
243
243
 
244
244
  this.On = value;
245
245
  this.doPlugUpdate.next();
246
246
  }
247
247
 
248
- config(device: device & devicesConfig) {
248
+ model(device: device & devicesConfig): string {
249
+ let model: string;
250
+ if (device.deviceType === 'Plug Mini (US)') {
251
+ model = 'SWITCHBOT-PLUG-W1901400';
252
+ } else if (device.deviceType === 'Plug Mini (JP)') {
253
+ model = 'SWITCHBOT-PLUG-W2001400';
254
+ } else {
255
+ model = 'SWITCHBOT-PLUG-SP11';
256
+ }
257
+ return model;
258
+ }
259
+
260
+ async config(device: device & devicesConfig): Promise<void> {
249
261
  let config = {};
250
262
  if (device.plug) {
251
263
  config = device.plug;
@@ -262,12 +274,15 @@ export class Plug {
262
274
  if (device.scanDuration !== undefined) {
263
275
  config['scanDuration'] = device.scanDuration;
264
276
  }
277
+ if (device.offline !== undefined) {
278
+ config['offline'] = device.offline;
279
+ }
265
280
  if (Object.entries(config).length !== 0) {
266
281
  this.warnLog(`Plug: ${this.accessory.displayName} Config: ${JSON.stringify(config)}`);
267
282
  }
268
283
  }
269
284
 
270
- refreshRate(device: device & devicesConfig) {
285
+ async refreshRate(device: device & devicesConfig): Promise<void> {
271
286
  if (device.refreshRate) {
272
287
  this.deviceRefreshRate = this.accessory.context.refreshRate = device.refreshRate;
273
288
  this.debugLog(`Plug: ${this.accessory.displayName} Using Device Config refreshRate: ${this.deviceRefreshRate}`);
@@ -277,7 +292,7 @@ export class Plug {
277
292
  }
278
293
  }
279
294
 
280
- scan(device: device & devicesConfig) {
295
+ async scan(device: device & devicesConfig): Promise<void> {
281
296
  if (device.scanDuration) {
282
297
  this.scanDuration = this.accessory.context.scanDuration = device.scanDuration;
283
298
  if (device.ble) {
@@ -291,7 +306,7 @@ export class Plug {
291
306
  }
292
307
  }
293
308
 
294
- logs(device: device & devicesConfig) {
309
+ async logs(device: device & devicesConfig): Promise<void> {
295
310
  if (this.platform.debugMode) {
296
311
  this.deviceLogging = this.accessory.context.logging = 'debugMode';
297
312
  this.debugLog(`Plug: ${this.accessory.displayName} Using Debug Mode Logging: ${this.deviceLogging}`);
@@ -310,25 +325,25 @@ export class Plug {
310
325
  /**
311
326
  * Logging for Device
312
327
  */
313
- infoLog(...log: any[]) {
328
+ infoLog(...log: any[]): void {
314
329
  if (this.enablingDeviceLogging()) {
315
330
  this.platform.log.info(String(...log));
316
331
  }
317
332
  }
318
333
 
319
- warnLog(...log: any[]) {
334
+ warnLog(...log: any[]): void {
320
335
  if (this.enablingDeviceLogging()) {
321
336
  this.platform.log.warn(String(...log));
322
337
  }
323
338
  }
324
339
 
325
- errorLog(...log: any[]) {
340
+ errorLog(...log: any[]): void {
326
341
  if (this.enablingDeviceLogging()) {
327
342
  this.platform.log.error(String(...log));
328
343
  }
329
344
  }
330
345
 
331
- debugLog(...log: any[]) {
346
+ debugLog(...log: any[]): void {
332
347
  if (this.enablingDeviceLogging()) {
333
348
  if (this.deviceLogging === 'debug') {
334
349
  this.platform.log.info('[DEBUG]', String(...log));
File without changes
File without changes
File without changes
File without changes
File without changes