@switchbot/homebridge-switchbot 3.5.1-beta.2 → 3.5.1-beta.3

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 (187) hide show
  1. package/dist/device/blindtilt.d.ts +15 -6
  2. package/dist/device/blindtilt.d.ts.map +1 -1
  3. package/dist/device/blindtilt.js +203 -255
  4. package/dist/device/blindtilt.js.map +1 -1
  5. package/dist/device/bot.d.ts +9 -4
  6. package/dist/device/bot.d.ts.map +1 -1
  7. package/dist/device/bot.js +196 -218
  8. package/dist/device/bot.js.map +1 -1
  9. package/dist/device/ceilinglight.d.ts +9 -4
  10. package/dist/device/ceilinglight.d.ts.map +1 -1
  11. package/dist/device/ceilinglight.js +202 -247
  12. package/dist/device/ceilinglight.js.map +1 -1
  13. package/dist/device/colorbulb.d.ts +10 -5
  14. package/dist/device/colorbulb.d.ts.map +1 -1
  15. package/dist/device/colorbulb.js +329 -378
  16. package/dist/device/colorbulb.js.map +1 -1
  17. package/dist/device/contact.d.ts +9 -4
  18. package/dist/device/contact.d.ts.map +1 -1
  19. package/dist/device/contact.js +99 -142
  20. package/dist/device/contact.js.map +1 -1
  21. package/dist/device/curtain.d.ts +19 -7
  22. package/dist/device/curtain.d.ts.map +1 -1
  23. package/dist/device/curtain.js +203 -264
  24. package/dist/device/curtain.js.map +1 -1
  25. package/dist/device/device.d.ts +28 -32
  26. package/dist/device/device.d.ts.map +1 -1
  27. package/dist/device/device.js +186 -225
  28. package/dist/device/device.js.map +1 -1
  29. package/dist/device/fan.d.ts +9 -4
  30. package/dist/device/fan.d.ts.map +1 -1
  31. package/dist/device/fan.js +198 -227
  32. package/dist/device/fan.js.map +1 -1
  33. package/dist/device/hub.d.ts +9 -5
  34. package/dist/device/hub.d.ts.map +1 -1
  35. package/dist/device/hub.js +106 -231
  36. package/dist/device/hub.js.map +1 -1
  37. package/dist/device/humidifier.d.ts +12 -4
  38. package/dist/device/humidifier.d.ts.map +1 -1
  39. package/dist/device/humidifier.js +192 -232
  40. package/dist/device/humidifier.js.map +1 -1
  41. package/dist/device/iosensor.d.ts +9 -4
  42. package/dist/device/iosensor.d.ts.map +1 -1
  43. package/dist/device/iosensor.js +91 -157
  44. package/dist/device/iosensor.js.map +1 -1
  45. package/dist/device/lightstrip.d.ts +10 -5
  46. package/dist/device/lightstrip.d.ts.map +1 -1
  47. package/dist/device/lightstrip.js +287 -367
  48. package/dist/device/lightstrip.js.map +1 -1
  49. package/dist/device/lock.d.ts +10 -5
  50. package/dist/device/lock.d.ts.map +1 -1
  51. package/dist/device/lock.js +171 -216
  52. package/dist/device/lock.js.map +1 -1
  53. package/dist/device/meter.d.ts +9 -4
  54. package/dist/device/meter.d.ts.map +1 -1
  55. package/dist/device/meter.js +93 -158
  56. package/dist/device/meter.js.map +1 -1
  57. package/dist/device/meterplus.d.ts +9 -4
  58. package/dist/device/meterplus.d.ts.map +1 -1
  59. package/dist/device/meterplus.js +94 -155
  60. package/dist/device/meterplus.js.map +1 -1
  61. package/dist/device/motion.d.ts +9 -4
  62. package/dist/device/motion.d.ts.map +1 -1
  63. package/dist/device/motion.js +84 -142
  64. package/dist/device/motion.js.map +1 -1
  65. package/dist/device/plug.d.ts +9 -4
  66. package/dist/device/plug.d.ts.map +1 -1
  67. package/dist/device/plug.js +99 -124
  68. package/dist/device/plug.js.map +1 -1
  69. package/dist/device/robotvacuumcleaner.d.ts +9 -6
  70. package/dist/device/robotvacuumcleaner.d.ts.map +1 -1
  71. package/dist/device/robotvacuumcleaner.js +170 -253
  72. package/dist/device/robotvacuumcleaner.js.map +1 -1
  73. package/dist/device/waterdetector.d.ts +12 -4
  74. package/dist/device/waterdetector.d.ts.map +1 -1
  75. package/dist/device/waterdetector.js +102 -128
  76. package/dist/device/waterdetector.js.map +1 -1
  77. package/dist/irdevice/airconditioner.d.ts +2 -1
  78. package/dist/irdevice/airconditioner.d.ts.map +1 -1
  79. package/dist/irdevice/airconditioner.js.map +1 -1
  80. package/dist/irdevice/airpurifier.d.ts +2 -1
  81. package/dist/irdevice/airpurifier.d.ts.map +1 -1
  82. package/dist/irdevice/airpurifier.js.map +1 -1
  83. package/dist/irdevice/camera.d.ts +2 -1
  84. package/dist/irdevice/camera.d.ts.map +1 -1
  85. package/dist/irdevice/camera.js.map +1 -1
  86. package/dist/irdevice/fan.d.ts +2 -1
  87. package/dist/irdevice/fan.d.ts.map +1 -1
  88. package/dist/irdevice/fan.js.map +1 -1
  89. package/dist/irdevice/irdevice.d.ts +2 -1
  90. package/dist/irdevice/irdevice.d.ts.map +1 -1
  91. package/dist/irdevice/irdevice.js +1 -1
  92. package/dist/irdevice/irdevice.js.map +1 -1
  93. package/dist/irdevice/light.d.ts +2 -1
  94. package/dist/irdevice/light.d.ts.map +1 -1
  95. package/dist/irdevice/light.js.map +1 -1
  96. package/dist/irdevice/other.d.ts +2 -1
  97. package/dist/irdevice/other.d.ts.map +1 -1
  98. package/dist/irdevice/other.js.map +1 -1
  99. package/dist/irdevice/tv.d.ts +2 -1
  100. package/dist/irdevice/tv.d.ts.map +1 -1
  101. package/dist/irdevice/tv.js.map +1 -1
  102. package/dist/irdevice/vacuumcleaner.d.ts +2 -1
  103. package/dist/irdevice/vacuumcleaner.d.ts.map +1 -1
  104. package/dist/irdevice/vacuumcleaner.js.map +1 -1
  105. package/dist/irdevice/waterheater.d.ts +2 -1
  106. package/dist/irdevice/waterheater.d.ts.map +1 -1
  107. package/dist/irdevice/waterheater.js.map +1 -1
  108. package/dist/platform.d.ts +5 -7
  109. package/dist/platform.d.ts.map +1 -1
  110. package/dist/platform.js +51 -34
  111. package/dist/platform.js.map +1 -1
  112. package/dist/settings.d.ts +49 -191
  113. package/dist/settings.d.ts.map +1 -1
  114. package/dist/settings.js +19 -0
  115. package/dist/settings.js.map +1 -1
  116. package/dist/types/bledevicestatus.d.ts +279 -0
  117. package/dist/types/bledevicestatus.d.ts.map +1 -0
  118. package/dist/types/bledevicestatus.js +2 -0
  119. package/dist/types/bledevicestatus.js.map +1 -0
  120. package/dist/types/devicelist.d.ts +89 -0
  121. package/dist/types/devicelist.d.ts.map +1 -0
  122. package/dist/types/devicelist.js +6 -0
  123. package/dist/types/devicelist.js.map +1 -0
  124. package/dist/types/deviceresponse.d.ts +13 -0
  125. package/dist/types/deviceresponse.d.ts.map +1 -0
  126. package/dist/types/deviceresponse.js +2 -0
  127. package/dist/types/deviceresponse.js.map +1 -0
  128. package/dist/types/devicestatus.d.ts +149 -0
  129. package/dist/types/devicestatus.d.ts.map +1 -0
  130. package/dist/types/devicestatus.js +3 -0
  131. package/dist/types/devicestatus.js.map +1 -0
  132. package/dist/types/devicewebhookstatus.d.ts +156 -0
  133. package/dist/types/devicewebhookstatus.d.ts.map +1 -0
  134. package/dist/types/devicewebhookstatus.js +2 -0
  135. package/dist/types/devicewebhookstatus.js.map +1 -0
  136. package/dist/types/irdevicelist.d.ts +10 -0
  137. package/dist/types/irdevicelist.d.ts.map +1 -0
  138. package/dist/types/irdevicelist.js +2 -0
  139. package/dist/types/irdevicelist.js.map +1 -0
  140. package/dist/types/pushbody.d.ts +6 -0
  141. package/dist/types/pushbody.d.ts.map +1 -0
  142. package/dist/types/pushbody.js +2 -0
  143. package/dist/types/pushbody.js.map +1 -0
  144. package/dist/utils.d.ts +25 -0
  145. package/dist/utils.d.ts.map +1 -1
  146. package/dist/utils.js +28 -0
  147. package/dist/utils.js.map +1 -1
  148. package/package.json +10 -10
  149. package/src/device/blindtilt.ts +223 -263
  150. package/src/device/bot.ts +208 -221
  151. package/src/device/ceilinglight.ts +210 -257
  152. package/src/device/colorbulb.ts +334 -397
  153. package/src/device/contact.ts +111 -146
  154. package/src/device/curtain.ts +220 -283
  155. package/src/device/device.ts +194 -245
  156. package/src/device/fan.ts +214 -230
  157. package/src/device/hub.ts +126 -246
  158. package/src/device/humidifier.ts +216 -243
  159. package/src/device/iosensor.ts +114 -166
  160. package/src/device/lightstrip.ts +302 -377
  161. package/src/device/lock.ts +187 -221
  162. package/src/device/meter.ts +116 -177
  163. package/src/device/meterplus.ts +117 -174
  164. package/src/device/motion.ts +99 -144
  165. package/src/device/plug.ts +110 -128
  166. package/src/device/robotvacuumcleaner.ts +189 -252
  167. package/src/device/waterdetector.ts +120 -138
  168. package/src/irdevice/airconditioner.ts +2 -1
  169. package/src/irdevice/airpurifier.ts +2 -1
  170. package/src/irdevice/camera.ts +2 -1
  171. package/src/irdevice/fan.ts +2 -1
  172. package/src/irdevice/irdevice.ts +3 -2
  173. package/src/irdevice/light.ts +2 -1
  174. package/src/irdevice/other.ts +2 -1
  175. package/src/irdevice/tv.ts +2 -1
  176. package/src/irdevice/vacuumcleaner.ts +2 -1
  177. package/src/irdevice/waterheater.ts +2 -1
  178. package/src/platform.ts +52 -34
  179. package/src/settings.ts +30 -239
  180. package/src/types/bledevicestatus.ts +305 -0
  181. package/src/types/devicelist.ts +124 -0
  182. package/src/types/deviceresponse.ts +15 -0
  183. package/src/types/devicestatus.ts +178 -0
  184. package/src/types/devicewebhookstatus.ts +196 -0
  185. package/src/types/irdevicelist.ts +15 -0
  186. package/src/types/pushbody.ts +9 -0
  187. package/src/utils.ts +33 -0
@@ -3,9 +3,9 @@
3
3
  * curtain.ts: @switchbot/homebridge-switchbot.
4
4
  */
5
5
  import { hostname } from 'os';
6
- import { interval, Subject } from 'rxjs';
7
6
  import { deviceBase } from './device.js';
8
- import { debounceTime, skipWhile, take, tap } from 'rxjs/operators';
7
+ import { SwitchBotBLEModel, SwitchBotBLEModelName } from 'node-switchbot';
8
+ import { Subject, debounceTime, interval, skipWhile, take, tap } from 'rxjs';
9
9
  export class Curtain extends deviceBase {
10
10
  platform;
11
11
  // Services
@@ -21,8 +21,6 @@ export class Curtain extends deviceBase {
21
21
  constructor(platform, accessory, device) {
22
22
  super(platform, accessory, device);
23
23
  this.platform = platform;
24
- // default placeholder
25
- this.history(device);
26
24
  // this is subject we use to track when we need to POST changes to the SwitchBot API
27
25
  this.doCurtainUpdate = new Subject();
28
26
  this.curtainUpdateInProgress = false;
@@ -108,7 +106,7 @@ export class Curtain extends deviceBase {
108
106
  // Initialize LightSensor Service
109
107
  if (device.curtain?.hide_lightsensor) {
110
108
  if (this.LightSensor?.Service) {
111
- this.debugLog(`${this.device.deviceType}: ${accessory.displayName} Removing Light Sensor Service`);
109
+ this.debugLog('Removing Light Sensor Service');
112
110
  this.LightSensor.Service = this.accessory.getService(this.hap.Service.LightSensor);
113
111
  accessory.removeService(this.LightSensor.Service);
114
112
  accessory.context.LightSensor = {};
@@ -135,14 +133,16 @@ export class Curtain extends deviceBase {
135
133
  this.refreshStatus();
136
134
  // Update Homekit
137
135
  this.updateHomeKitCharacteristics();
136
+ //regisiter webhook event handler
137
+ this.registerWebhook();
138
+ // History
139
+ this.history();
138
140
  // Start an update interval
139
141
  interval(this.deviceRefreshRate * 1000)
140
142
  .pipe(skipWhile(() => this.curtainUpdateInProgress))
141
143
  .subscribe(async () => {
142
144
  await this.refreshStatus();
143
145
  });
144
- //regisiter webhook event handler
145
- this.registerWebhook(accessory, device);
146
146
  // update slide progress
147
147
  interval(this.deviceUpdateRate * 1000)
148
148
  //.pipe(skipWhile(() => this.curtainUpdateInProgress))
@@ -150,8 +150,7 @@ export class Curtain extends deviceBase {
150
150
  if (this.WindowCovering.PositionState === this.hap.Characteristic.PositionState.STOPPED) {
151
151
  return;
152
152
  }
153
- this.debugLog(`${this.device.deviceType}: ${accessory.displayName} Refresh Status When Moving,`
154
- + ` PositionState: ${this.WindowCovering.PositionState}`);
153
+ await this.debugLog(`Refresh Status When Moving, PositionState: ${this.WindowCovering.PositionState}`);
155
154
  await this.refreshStatus();
156
155
  });
157
156
  // Watch for Curtain change events
@@ -165,17 +164,16 @@ export class Curtain extends deviceBase {
165
164
  await this.pushChanges();
166
165
  }
167
166
  catch (e) {
168
- this.apiError(e);
169
- this.errorLog(`${this.device.deviceType}: ${this.accessory.displayName} failed pushChanges with ${this.device.connectionType} Connection,`
170
- + ` Error Message: ${JSON.stringify(e.message)}`);
167
+ await this.apiError(e);
168
+ await this.errorLog(`failed pushChanges with ${device.connectionType} Connection, Error Message: ${JSON.stringify(e.message)}`);
171
169
  }
172
170
  this.curtainUpdateInProgress = false;
173
171
  });
174
172
  // Setup EVE history features
175
- this.setupHistoryService(accessory, device);
173
+ this.setupHistoryService();
176
174
  }
177
- history(device) {
178
- if (device.history === true) {
175
+ async history() {
176
+ if (this.device.history === true) {
179
177
  // initialize when this accessory is newly created.
180
178
  this.accessory.context.lastActivation = this.accessory.context.lastActivation ?? 0;
181
179
  }
@@ -187,8 +185,8 @@ export class Curtain extends deviceBase {
187
185
  /*
188
186
  * Setup EVE history features for curtain devices.
189
187
  */
190
- async setupHistoryService(accessory, device) {
191
- if (device.history !== true) {
188
+ async setupHistoryService() {
189
+ if (this.device.history !== true) {
192
190
  return;
193
191
  }
194
192
  const mac = this.device
@@ -230,189 +228,91 @@ export class Curtain extends deviceBase {
230
228
  time: Math.round(new Date().valueOf() / 1000),
231
229
  motion: motion,
232
230
  });
233
- setTimeout(() => {
234
- this.updateHistory();
231
+ setTimeout(async () => {
232
+ await this.updateHistory();
235
233
  }, 10 * 60 * 1000);
236
234
  }
237
235
  async BLEparseStatus(serviceData) {
238
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName} BLEparseStatus`);
239
- this.debugSuccessLog(`${this.device.deviceType}: ${this.accessory.displayName} ${JSON.stringify(serviceData)}`);
236
+ await this.debugLog('BLEparseStatus');
240
237
  // CurrentPosition
241
- this.WindowCovering.CurrentPosition = 100 - Number(serviceData.position);
242
- await this.setMinMax();
243
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName} CurrentPosition ${this.WindowCovering.CurrentPosition}`);
244
- if (this.setNewTarget) {
245
- this.infoLog(`${this.device.deviceType}: ${this.accessory.displayName} Checking Status ...`);
246
- await this.setMinMax();
247
- if (Number(this.WindowCovering.TargetPosition) > this.WindowCovering.CurrentPosition) {
248
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName} Closing, CurrentPosition: ${this.WindowCovering.CurrentPosition}`);
249
- this.WindowCovering.PositionState = this.hap.Characteristic.PositionState.INCREASING;
250
- this.WindowCovering.Service.getCharacteristic(this.hap.Characteristic.PositionState).updateValue(this.WindowCovering.PositionState);
251
- this.debugLog(`${this.device.deviceType}: ${this.WindowCovering.CurrentPosition} INCREASING`
252
- + ` PositionState: ${this.WindowCovering.PositionState}`);
253
- }
254
- else if (Number(this.WindowCovering.TargetPosition) < this.WindowCovering.CurrentPosition) {
255
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName} Opening, CurrentPosition: ${this.WindowCovering.CurrentPosition}`);
256
- this.WindowCovering.PositionState = this.hap.Characteristic.PositionState.DECREASING;
257
- this.WindowCovering.Service.getCharacteristic(this.hap.Characteristic.PositionState).updateValue(this.WindowCovering.PositionState);
258
- this.debugLog(`${this.device.deviceType}: ${this.WindowCovering.CurrentPosition} DECREASING`
259
- + ` PositionState: ${this.WindowCovering.PositionState}`);
260
- }
261
- else {
262
- this.debugLog(`${this.device.deviceType}: ${this.WindowCovering.CurrentPosition} Standby,`
263
- + ` CurrentPosition: ${this.WindowCovering.CurrentPosition}`);
264
- this.WindowCovering.PositionState = this.hap.Characteristic.PositionState.STOPPED;
265
- this.WindowCovering.Service.getCharacteristic(this.hap.Characteristic.PositionState).updateValue(this.WindowCovering.PositionState);
266
- this.debugLog(`${this.device.deviceType}: ${this.WindowCovering.CurrentPosition} STOPPED`
267
- + ` PositionState: ${this.WindowCovering.PositionState}`);
268
- }
269
- }
270
- else {
271
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName} Standby, CurrentPosition: ${this.WindowCovering.CurrentPosition}`);
272
- this.WindowCovering.TargetPosition = this.WindowCovering.CurrentPosition;
273
- this.WindowCovering.PositionState = this.hap.Characteristic.PositionState.STOPPED;
274
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName} Stopped`);
275
- }
276
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName} CurrentPosition: ${this.WindowCovering.CurrentPosition},`
277
- + ` TargetPosition: ${this.WindowCovering.TargetPosition}, PositionState: ${this.WindowCovering.PositionState},`);
278
- if (!this.device.curtain?.hide_lightsensor) {
238
+ this.WindowCovering.CurrentPosition = 100 - serviceData.position;
239
+ await this.getCurrentPostion();
240
+ // CurrentAmbientLightLevel
241
+ if (!this.device.curtain?.hide_lightsensor && this.LightSensor?.Service) {
279
242
  const set_minLux = this.device.curtain?.set_minLux ?? 1;
280
243
  const set_maxLux = this.device.curtain?.set_maxLux ?? 6001;
281
- const spaceBetweenLevels = 9;
282
- // Brightness
283
- switch (serviceData.lightLevel) {
284
- case 1:
285
- this.LightSensor.CurrentAmbientLightLevel = set_minLux;
286
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName} LightLevel: ${serviceData.lightLevel}`);
287
- break;
288
- case 2:
289
- this.LightSensor.CurrentAmbientLightLevel = (set_maxLux - set_minLux) / spaceBetweenLevels;
290
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName} LightLevel: ${serviceData.lightLevel},`
291
- + ` Calculation: ${(set_maxLux - set_minLux) / spaceBetweenLevels}`);
292
- break;
293
- case 3:
294
- this.LightSensor.CurrentAmbientLightLevel = ((set_maxLux - set_minLux) / spaceBetweenLevels) * 2;
295
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName} LightLevel: ${serviceData.lightLevel}`);
296
- break;
297
- case 4:
298
- this.LightSensor.CurrentAmbientLightLevel = ((set_maxLux - set_minLux) / spaceBetweenLevels) * 3;
299
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName} LightLevel: ${serviceData.lightLevel}`);
300
- break;
301
- case 5:
302
- this.LightSensor.CurrentAmbientLightLevel = ((set_maxLux - set_minLux) / spaceBetweenLevels) * 4;
303
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName} LightLevel: ${serviceData.lightLevel}`);
304
- break;
305
- case 6:
306
- this.LightSensor.CurrentAmbientLightLevel = ((set_maxLux - set_minLux) / spaceBetweenLevels) * 5;
307
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName} LightLevel: ${serviceData.lightLevel}`);
308
- break;
309
- case 7:
310
- this.LightSensor.CurrentAmbientLightLevel = ((set_maxLux - set_minLux) / spaceBetweenLevels) * 6;
311
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName} LightLevel: ${serviceData.lightLevel}`);
312
- break;
313
- case 8:
314
- this.LightSensor.CurrentAmbientLightLevel = ((set_maxLux - set_minLux) / spaceBetweenLevels) * 7;
315
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName} LightLevel: ${serviceData.lightLevel}`);
316
- break;
317
- case 9:
318
- this.LightSensor.CurrentAmbientLightLevel = ((set_maxLux - set_minLux) / spaceBetweenLevels) * 8;
319
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName} LightLevel: ${serviceData.lightLevel}`);
320
- break;
321
- case 10:
322
- default:
323
- this.LightSensor.CurrentAmbientLightLevel = set_maxLux;
324
- this.debugLog();
325
- }
326
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName} LightLevel: ${serviceData.lightLevel},`
244
+ const lightLevel = Number(serviceData.lightLevel);
245
+ this.LightSensor.CurrentAmbientLightLevel = await this.getLightLevel(lightLevel, set_minLux, set_maxLux, 19);
246
+ this.debugLog(`LightLevel: ${serviceData.lightLevel},`
327
247
  + ` CurrentAmbientLightLevel: ${this.LightSensor.CurrentAmbientLightLevel}`);
328
248
  }
329
- // Battery
249
+ // BatteryLevel
330
250
  this.Battery.BatteryLevel = Number(serviceData.battery);
331
- if (this.Battery.BatteryLevel < 10) {
332
- this.Battery.StatusLowBattery = this.hap.Characteristic.StatusLowBattery.BATTERY_LEVEL_LOW;
333
- }
334
- else {
335
- this.Battery.StatusLowBattery = this.hap.Characteristic.StatusLowBattery.BATTERY_LEVEL_NORMAL;
336
- }
337
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName} BatteryLevel: ${this.Battery.BatteryLevel},`
338
- + ` StatusLowBattery: ${this.Battery.StatusLowBattery}`);
251
+ await this.debugLog(`BatteryLevel: ${this.Battery.BatteryLevel}`);
252
+ // StatusLowBattery
253
+ this.Battery.StatusLowBattery = this.Battery.BatteryLevel < 10
254
+ ? this.hap.Characteristic.StatusLowBattery.BATTERY_LEVEL_LOW : this.hap.Characteristic.StatusLowBattery.BATTERY_LEVEL_NORMAL;
255
+ await this.debugLog(`StatusLowBattery: ${this.Battery.StatusLowBattery}`);
339
256
  }
340
257
  async openAPIparseStatus(deviceStatus) {
341
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName} openAPIparseStatus`);
258
+ await this.debugLog('openAPIparseStatus');
342
259
  // CurrentPosition
343
- this.WindowCovering.CurrentPosition = 100 - Number(deviceStatus.body.slidePosition);
260
+ this.WindowCovering.CurrentPosition = 100 - deviceStatus.slidePosition;
344
261
  await this.setMinMax();
345
- this.debugLog(`Curtain ${this.accessory.displayName} CurrentPosition: ${this.WindowCovering.CurrentPosition}`);
262
+ await this.debugLog(`Curtain ${this.accessory.displayName} CurrentPosition: ${this.WindowCovering.CurrentPosition}`);
346
263
  if (this.setNewTarget) {
347
- this.infoLog(`${this.device.deviceType}: ${this.accessory.displayName} Checking Status ...`);
264
+ await this.infoLog('Checking Status ...');
348
265
  }
349
- if (this.setNewTarget && deviceStatus.body.moving) {
266
+ if (this.setNewTarget && deviceStatus.moving) {
350
267
  await this.setMinMax();
351
268
  if (Number(this.WindowCovering.TargetPosition) > this.WindowCovering.CurrentPosition) {
352
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName} Closing, CurrentPosition: ${this.WindowCovering.CurrentPosition} `);
269
+ await this.debugLog(`Closing, CurrentPosition: ${this.WindowCovering.CurrentPosition}`);
353
270
  this.WindowCovering.PositionState = this.hap.Characteristic.PositionState.INCREASING;
354
271
  this.WindowCovering.Service.getCharacteristic(this.hap.Characteristic.PositionState).updateValue(this.WindowCovering.PositionState);
355
- this.debugLog(`${this.device.deviceType}: ${this.WindowCovering.CurrentPosition} INCREASING`
356
- + ` PositionState: ${this.WindowCovering.PositionState}`);
272
+ await this.debugLog(`Increasing, PositionState: ${this.WindowCovering.PositionState}`);
357
273
  }
358
274
  else if (Number(this.WindowCovering.TargetPosition) < this.WindowCovering.CurrentPosition) {
359
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName} Opening, CurrentPosition: ${this.WindowCovering.CurrentPosition} `);
275
+ await this.debugLog(`Opening, CurrentPosition: ${this.WindowCovering.CurrentPosition}`);
360
276
  this.WindowCovering.PositionState = this.hap.Characteristic.PositionState.DECREASING;
361
277
  this.WindowCovering.Service.getCharacteristic(this.hap.Characteristic.PositionState).updateValue(this.WindowCovering.PositionState);
362
- this.debugLog(`${this.device.deviceType}: ${this.WindowCovering.CurrentPosition} DECREASING`
363
- + ` PositionState: ${this.WindowCovering.PositionState}`);
278
+ await this.debugLog(`Decreasing, PositionState: ${this.WindowCovering.PositionState}`);
364
279
  }
365
280
  else {
366
- this.debugLog(`${this.device.deviceType}: ${this.WindowCovering.CurrentPosition} Standby,`
367
- + ` CurrentPosition: ${this.WindowCovering.CurrentPosition}`);
281
+ await this.debugLog(`Standby, CurrentPosition: ${this.WindowCovering.CurrentPosition}`);
368
282
  this.WindowCovering.PositionState = this.hap.Characteristic.PositionState.STOPPED;
369
283
  this.WindowCovering.Service.getCharacteristic(this.hap.Characteristic.PositionState).updateValue(this.WindowCovering.PositionState);
370
- this.debugLog(`${this.device.deviceType}: ${this.WindowCovering.CurrentPosition} STOPPED`
371
- + ` PositionState: ${this.WindowCovering.PositionState}`);
284
+ await this.debugLog(`Stopped, PositionState: ${this.WindowCovering.PositionState}`);
372
285
  }
373
286
  }
374
287
  else {
375
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName} Standby, CurrentPosition: ${this.WindowCovering.CurrentPosition}`);
288
+ await this.debugLog(`Standby, CurrentPosition: ${this.WindowCovering.CurrentPosition}`);
376
289
  this.WindowCovering.TargetPosition = this.WindowCovering.CurrentPosition;
377
290
  this.WindowCovering.PositionState = this.hap.Characteristic.PositionState.STOPPED;
378
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName} Stopped`);
291
+ await this.debugLog(`Stopped, PositionState: ${this.WindowCovering.PositionState}`);
379
292
  }
380
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName} CurrentPosition: ${this.WindowCovering.CurrentPosition},`
381
- + ` TargetPosition: ${this.WindowCovering.TargetPosition}, PositionState: ${this.WindowCovering.PositionState},`);
293
+ await this.debugLog(`CurrentPosition: ${this.WindowCovering.CurrentPosition}, TargetPosition: ${this.WindowCovering.TargetPosition},`
294
+ + ` PositionState: ${this.WindowCovering.PositionState},`);
382
295
  // Brightness
383
- if (!this.device.curtain?.hide_lightsensor) {
296
+ if (!this.device.curtain?.hide_lightsensor && this.LightSensor?.Service) {
384
297
  const set_minLux = this.device.curtain?.set_minLux ?? 1;
385
298
  const set_maxLux = this.device.curtain?.set_maxLux ?? 6001;
386
- switch (deviceStatus.body.brightness) {
387
- case 'bright':
388
- this.LightSensor.CurrentAmbientLightLevel = set_maxLux;
389
- this.Battery.ChargingState = this.hap.Characteristic.ChargingState.CHARGING;
390
- break;
391
- case 'dim':
392
- default:
393
- this.LightSensor.CurrentAmbientLightLevel = set_minLux;
394
- }
395
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName}`
299
+ const lightLevel = deviceStatus.lightLevel === 'bright' ? set_maxLux : set_minLux;
300
+ this.LightSensor.CurrentAmbientLightLevel = await this.getLightLevel(lightLevel, set_minLux, set_maxLux, 2);
301
+ await this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName}`
396
302
  + ` CurrentAmbientLightLevel: ${this.LightSensor.CurrentAmbientLightLevel}`);
397
303
  }
398
304
  // BatteryLevel
399
- this.Battery.BatteryLevel = Number(deviceStatus.body.battery);
400
- if (this.Battery.BatteryLevel < 10) {
401
- this.Battery.StatusLowBattery = this.hap.Characteristic.StatusLowBattery.BATTERY_LEVEL_LOW;
402
- }
403
- else {
404
- this.Battery.StatusLowBattery = this.hap.Characteristic.StatusLowBattery.BATTERY_LEVEL_NORMAL;
405
- }
406
- if (Number.isNaN(this.Battery.BatteryLevel)) {
407
- this.Battery.BatteryLevel = 100;
408
- }
409
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName} BatteryLevel: ${this.Battery.BatteryLevel},`
410
- + ` StatusLowBattery: ${this.Battery.StatusLowBattery}`);
305
+ this.Battery.BatteryLevel = Number(deviceStatus.battery);
306
+ await this.debugLog(`BatteryLevel: ${this.Battery.BatteryLevel}`);
307
+ // StatusLowBattery
308
+ this.Battery.StatusLowBattery = this.Battery.BatteryLevel < 10
309
+ ? this.hap.Characteristic.StatusLowBattery.BATTERY_LEVEL_LOW : this.hap.Characteristic.StatusLowBattery.BATTERY_LEVEL_NORMAL;
310
+ await this.debugLog(`StatusLowBattery: ${this.Battery.StatusLowBattery}`);
411
311
  // Firmware Version
412
- const version = deviceStatus.body.version?.toString();
413
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName} Firmware Version: ${version?.replace(/^V|-.*$/g, '')}`);
414
- if (deviceStatus.body.version) {
415
- const deviceVersion = version?.replace(/^V|-.*$/g, '') ?? '0.0.0';
312
+ if (deviceStatus.version) {
313
+ const version = deviceStatus.version.toString();
314
+ await this.debugLog(`Firmware Version: ${version.replace(/^V|-.*$/g, '')}`);
315
+ const deviceVersion = version.replace(/^V|-.*$/g, '') ?? '0.0.0';
416
316
  this.accessory
417
317
  .getService(this.hap.Service.AccessoryInformation)
418
318
  .setCharacteristic(this.hap.Characteristic.HardwareRevision, deviceVersion)
@@ -420,12 +320,30 @@ export class Curtain extends deviceBase {
420
320
  .getCharacteristic(this.hap.Characteristic.FirmwareRevision)
421
321
  .updateValue(deviceVersion);
422
322
  this.accessory.context.deviceVersion = deviceVersion;
423
- this.debugSuccessLog(`${this.device.deviceType}: ${this.accessory.displayName} deviceVersion: ${this.accessory.context.deviceVersion}`);
323
+ await this.debugSuccessLog(`deviceVersion: ${this.accessory.context.deviceVersion}`);
424
324
  }
425
325
  }
326
+ async parseStatusWebhook(context) {
327
+ await this.debugLog('parseStatusWebhook');
328
+ await this.debugLog(`(slidePosition, battery) = Webhook:(${context.slidePosition}, ${context.battery}),`
329
+ + ` current:(${this.WindowCovering.CurrentPosition}, ${this.Battery.BatteryLevel})`);
330
+ // CurrentPosition
331
+ this.WindowCovering.CurrentPosition = 100 - context.slidePosition;
332
+ await this.getCurrentPostion();
333
+ // BatteryLevel
334
+ this.Battery.BatteryLevel = context.battery;
335
+ await this.debugLog(`BatteryLevel: ${this.Battery.BatteryLevel}`);
336
+ // StatusLowBattery
337
+ this.Battery.StatusLowBattery = this.Battery.BatteryLevel < 10
338
+ ? this.hap.Characteristic.StatusLowBattery.BATTERY_LEVEL_LOW : this.hap.Characteristic.StatusLowBattery.BATTERY_LEVEL_NORMAL;
339
+ await this.debugLog(`StatusLowBattery: ${this.Battery.StatusLowBattery}`);
340
+ }
341
+ /**
342
+ * Asks the SwitchBot API for the latest device information
343
+ */
426
344
  async refreshStatus() {
427
345
  if (!this.device.enableCloudService && this.OpenAPI) {
428
- this.errorLog(`${this.device.deviceType}: ${this.accessory.displayName} refreshStatus enableCloudService: ${this.device.enableCloudService}`);
346
+ await this.errorLog(`refreshStatus enableCloudService: ${this.device.enableCloudService}`);
429
347
  }
430
348
  else if (this.BLE) {
431
349
  await this.BLERefreshStatus();
@@ -435,12 +353,11 @@ export class Curtain extends deviceBase {
435
353
  }
436
354
  else {
437
355
  await this.offlineOff();
438
- this.debugWarnLog(`${this.device.deviceType}: ${this.accessory.displayName} Connection Type:`
439
- + ` ${this.device.connectionType}, refreshStatus will not happen.`);
356
+ await this.debugWarnLog(`Connection Type: ${this.device.connectionType}, refreshStatus will not happen.`);
440
357
  }
441
358
  }
442
359
  async BLERefreshStatus() {
443
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName} BLERefreshStatus`);
360
+ await this.debugLog('BLERefreshStatus');
444
361
  const switchbot = await this.switchbotBLE();
445
362
  if (switchbot === undefined) {
446
363
  await this.BLERefreshConnection(switchbot);
@@ -451,62 +368,64 @@ export class Curtain extends deviceBase {
451
368
  // Start to monitor advertisement packets
452
369
  const serviceData = await this.monitorAdvertisementPackets(switchbot);
453
370
  // Update HomeKit
454
- if (serviceData.model !== '' && serviceData.modelName !== '') {
371
+ if ((serviceData.model === SwitchBotBLEModel.Curtain || SwitchBotBLEModel.Curtain3)
372
+ && (serviceData.modelName === SwitchBotBLEModelName.Curtain || SwitchBotBLEModelName.Curtain3)) {
455
373
  await this.BLEparseStatus(serviceData);
456
374
  await this.updateHomeKitCharacteristics();
457
375
  }
458
376
  else {
459
- this.errorLog(`${this.device.deviceType}: ${this.accessory.displayName} failed to get serviceData, serviceData: ${serviceData}`);
377
+ await this.errorLog(`failed to get serviceData, serviceData: ${serviceData}`);
460
378
  await this.BLERefreshConnection(switchbot);
461
379
  }
462
380
  })();
463
381
  }
464
382
  }
465
383
  async openAPIRefreshStatus() {
466
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName} openAPIRefreshStatus`);
384
+ await this.debugLog('openAPIRefreshStatus');
467
385
  try {
468
386
  const { body, statusCode } = await this.deviceRefreshStatus();
469
387
  const deviceStatus = await body.json();
470
- await this.refreshStatusCodes(statusCode, deviceStatus);
471
- if ((statusCode === 200 || statusCode === 100) && (deviceStatus.statusCode === 200 || deviceStatus.statusCode === 100)) {
472
- await this.successfulRefreshStatus(statusCode, deviceStatus);
473
- await this.openAPIparseStatus(deviceStatus);
388
+ await this.debugLog(`statusCode: ${statusCode}, deviceStatus: ${JSON.stringify(deviceStatus)}`);
389
+ ;
390
+ if (await this.successfulStatusCodes(statusCode, deviceStatus)) {
391
+ await this.debugSuccessLog(`statusCode: ${statusCode}, deviceStatus: ${JSON.stringify(deviceStatus)}`);
392
+ await this.openAPIparseStatus(deviceStatus.body);
474
393
  await this.updateHomeKitCharacteristics();
475
394
  }
476
395
  else {
477
- await this.statusCodes(statusCode, deviceStatus);
396
+ await this.debugWarnLog(`statusCode: ${statusCode}, deviceStatus: ${JSON.stringify(deviceStatus)}`);
397
+ await this.debugWarnLog(statusCode, deviceStatus);
478
398
  }
479
399
  }
480
400
  catch (e) {
481
401
  await this.apiError(e);
482
- await this.openAPIRefreshError(e);
402
+ await this.errorLog(`failed openAPIRefreshStatus with ${this.device.connectionType} Connection, Error Message: ${JSON.stringify(e.message)}`);
483
403
  }
484
404
  }
485
- async registerWebhook(accessory, device) {
486
- if (device.webhook) {
487
- this.debugLog(`${device.deviceType}: ${accessory.displayName} is listening webhook.`);
488
- this.platform.webhookEventHandler[device.deviceId] = async (context) => {
405
+ async registerWebhook() {
406
+ if (this.device.webhook) {
407
+ await this.debugLog('is listening webhook.');
408
+ this.platform.webhookEventHandler[this.device.deviceId] = async (context) => {
489
409
  try {
490
- this.debugLog(`${device.deviceType}: ${accessory.displayName} received Webhook: ${JSON.stringify(context)}`);
491
- const { slidePosition, battery } = context;
492
- this.debugLog(`${device.deviceType}: ${accessory.displayName} ` +
493
- '(slidePosition, battery) = ' +
494
- `Webhook:(${slidePosition}, ${battery}), `
495
- + `current:(${this.WindowCovering.CurrentPosition}, ${this.Battery.BatteryLevel})`);
496
- this.WindowCovering.CurrentPosition = slidePosition;
497
- this.Battery.BatteryLevel = battery;
498
- this.updateHomeKitCharacteristics();
410
+ await this.debugLog(`received Webhook: ${JSON.stringify(context)}`);
411
+ await this.parseStatusWebhook(context);
412
+ await this.updateHomeKitCharacteristics();
499
413
  }
500
414
  catch (e) {
501
- this.errorLog(`${device.deviceType}: ${accessory.displayName} `
502
- + `failed to handle webhook. Received: ${JSON.stringify(context)} Error: ${e}`);
415
+ await this.errorLog(`failed to handle webhook. Received: ${JSON.stringify(context)} Error: ${e}`);
503
416
  }
504
417
  };
505
418
  }
419
+ else {
420
+ await this.debugLog('is not listening webhook.');
421
+ }
506
422
  }
423
+ /**
424
+ * Pushes the requested changes to the SwitchBot API
425
+ */
507
426
  async pushChanges() {
508
427
  if (!this.device.enableCloudService && this.OpenAPI) {
509
- this.errorLog(`${this.device.deviceType}: ${this.accessory.displayName} pushChanges enableCloudService: ${this.device.enableCloudService}`);
428
+ await this.errorLog(`pushChanges enableCloudService: ${this.device.enableCloudService}`);
510
429
  }
511
430
  else if (this.BLE) {
512
431
  await this.BLEpushChanges();
@@ -516,7 +435,7 @@ export class Curtain extends deviceBase {
516
435
  }
517
436
  else {
518
437
  await this.offlineOff();
519
- await this.pushChangeDisabled();
438
+ await this.debugWarnLog(`Connection Type: ${this.device.connectionType}, pushChanges will not happen.`);
520
439
  }
521
440
  // Refresh the status from the API
522
441
  interval(15000)
@@ -527,108 +446,100 @@ export class Curtain extends deviceBase {
527
446
  });
528
447
  }
529
448
  async BLEpushChanges() {
530
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName} BLEpushChanges`);
449
+ await this.debugLog('BLEpushChanges');
531
450
  if (this.WindowCovering.TargetPosition !== this.WindowCovering.CurrentPosition) {
532
- const switchbot = await this.platform.connectBLE();
533
- // Convert to BLE Address
451
+ const switchbot = await this.platform.connectBLE(this.accessory, this.device);
534
452
  await this.convertBLEAddress();
535
453
  const { setPositionMode, Mode } = await this.setPerformance();
536
454
  const adjustedMode = setPositionMode === 1 ? 0x01 : 0xff;
537
- this.debugLog(`${this.accessory.displayName} Mode: ${Mode}`);
455
+ await this.debugLog(`Mode: ${Mode}, setPositionMode: ${setPositionMode}`);
538
456
  if (switchbot !== false) {
539
- try {
540
- const device_list = await switchbot.discover({ model: this.device.bleModel, quick: true, id: this.device.bleMac });
541
- this.infoLog(`${this.accessory.displayName} Target Position: ${this.WindowCovering.TargetPosition}`);
542
- await this.retryBLE({
457
+ switchbot
458
+ .discover({ model: this.device.bleModel, quick: true, id: this.device.bleMac })
459
+ .then(async (device_list) => {
460
+ return await this.retryBLE({
543
461
  max: await this.maxRetryBLE(),
544
462
  fn: async () => {
545
- await device_list[0].runToPos(100 - Number(this.WindowCovering.TargetPosition), adjustedMode);
463
+ return await device_list[0].runToPos(100 - Number(this.WindowCovering.TargetPosition), adjustedMode);
546
464
  },
547
465
  });
548
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName} Done.`);
549
- this.successLog(`${this.device.deviceType}: ${this.accessory.displayName} `
550
- + `TargetPosition: ${this.WindowCovering.TargetPosition} sent over BLE, sent successfully`);
551
- }
552
- catch (e) {
553
- this.apiError(e);
554
- this.errorLog(`${this.device.deviceType}: ${this.accessory.displayName} failed BLEpushChanges with ${this.device.connectionType}`
555
- + ` Connection, Error Message: ${JSON.stringify(e.message)}`);
466
+ })
467
+ .then(async () => {
468
+ await this.successLog(`TargetPostion: ${this.WindowCovering.TargetPosition} sent over SwitchBot BLE, sent successfully`);
469
+ await this.updateHomeKitCharacteristics();
470
+ })
471
+ .catch(async (e) => {
472
+ await this.apiError(e);
473
+ await this.errorLog(`failed BLEpushChanges with ${this.device.connectionType} Connection, Error Message: ${JSON.stringify(e.message)}`);
556
474
  await this.BLEPushConnection();
557
- throw new Error('Connection error');
558
- }
475
+ });
559
476
  }
560
477
  else {
561
- this.errorLog(`${this.device.deviceType}: ${this.accessory.displayName} wasn't able to establish BLE Connection`);
478
+ await this.errorLog(`wasn't able to establish BLE Connection, node-switchbot: ${switchbot}`);
562
479
  await this.BLEPushConnection();
563
480
  }
564
481
  }
565
482
  else {
566
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName} No BLEpushChanges, CurrentPosition & TargetPosition Are the Same.`
567
- + ` CurrentPosition: ${this.WindowCovering.CurrentPosition}, TargetPosition ${this.WindowCovering.TargetPosition}`);
483
+ await this.debugLog(`No changes (BLEpushChanges), TargetPosition: ${this.WindowCovering.TargetPosition},`
484
+ + ` CurrentPosition: ${this.WindowCovering.CurrentPosition}`);
568
485
  }
569
486
  }
570
487
  async openAPIpushChanges() {
571
- let command;
572
- let parameter;
573
- let commandType;
574
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName} openAPIpushChanges`);
488
+ await this.debugLog('openAPIpushChanges');
575
489
  if (this.WindowCovering.TargetPosition !== this.WindowCovering.CurrentPosition || this.device.disableCaching) {
576
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName} Pushing ${this.WindowCovering.TargetPosition}`);
490
+ await this.debugLog(`Pushing ${this.WindowCovering.TargetPosition}`);
577
491
  const adjustedTargetPosition = 100 - Number(this.WindowCovering.TargetPosition);
578
492
  const { setPositionMode, Mode } = await this.setPerformance();
579
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName} Mode: ${Mode}`);
493
+ await this.debugLog(`Mode: ${Mode}, setPositionMode: ${setPositionMode}`);
580
494
  const adjustedMode = setPositionMode || 'ff';
495
+ let bodyChange;
581
496
  if (this.WindowCovering.HoldPosition) {
582
- command = 'pause';
583
- parameter = 'default';
584
- commandType = 'command';
497
+ bodyChange = JSON.stringify({
498
+ command: 'pause',
499
+ parameter: 'default',
500
+ commandType: 'command',
501
+ });
585
502
  }
586
503
  else {
587
- command = 'setPosition';
588
- parameter = `0,${adjustedMode},${adjustedTargetPosition}`;
589
- commandType = 'command';
504
+ bodyChange = JSON.stringify({
505
+ command: 'setPosition',
506
+ parameter: `0,${adjustedMode},${adjustedTargetPosition}`,
507
+ commandType: 'command',
508
+ });
590
509
  }
591
- const bodyChange = JSON.stringify({
592
- command: command,
593
- parameter: parameter,
594
- commandType: commandType,
595
- });
596
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName} Sending request to SwitchBot API, body: ${bodyChange},`);
510
+ await this.debugLog(`SwitchBot OpenAPI bodyChange: ${JSON.stringify(bodyChange)}`);
597
511
  try {
598
512
  const { body, statusCode } = await this.pushChangeRequest(bodyChange);
599
513
  const deviceStatus = await body.json();
600
- await this.pushStatusCodes(statusCode, deviceStatus);
601
- if ((statusCode === 200 || statusCode === 100) && (deviceStatus.statusCode === 200 || deviceStatus.statusCode === 100)) {
602
- this.debugErrorLog(`${this.device.deviceType}: ${this.accessory.displayName} `
603
- + `statusCode: ${statusCode} & deviceStatus StatusCode: ${deviceStatus.statusCode}`);
604
- this.successLog(`${this.device.deviceType}: ${this.accessory.displayName} `
605
- + `request to SwitchBot API, body: ${JSON.stringify(JSON.parse(bodyChange))} sent successfully`);
514
+ await this.debugLog(`statusCode: ${statusCode}, deviceStatus: ${JSON.stringify(deviceStatus)}`);
515
+ if (await this.successfulStatusCodes(statusCode, deviceStatus)) {
516
+ await this.debugSuccessLog(`statusCode: ${statusCode}, deviceStatus: ${JSON.stringify(deviceStatus)}`);
517
+ await this.updateHomeKitCharacteristics();
606
518
  }
607
519
  else {
608
- this.statusCode(statusCode);
609
- this.statusCode(deviceStatus.statusCode);
520
+ await this.statusCode(statusCode);
521
+ await this.statusCode(deviceStatus.statusCode);
610
522
  }
611
523
  }
612
524
  catch (e) {
613
- this.apiError(e);
614
- this.errorLog(`${this.device.deviceType}: ${this.accessory.displayName} failed openAPIpushChanges with ${this.device.connectionType}`
615
- + ` Connection, Error Message: ${JSON.stringify(e.message)}`);
525
+ await this.apiError(e);
526
+ await this.errorLog(`failed openAPIpushChanges with ${this.device.connectionType} Connection, Error Message: ${JSON.stringify(e.message)}`);
616
527
  }
617
528
  }
618
529
  else {
619
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName} No OpenAPI Changes, CurrentPosition & TargetPosition Are the Same.`
620
- + ` CurrentPosition: ${this.WindowCovering.CurrentPosition}, TargetPosition ${this.WindowCovering.TargetPosition}`);
530
+ await this.debugLog(`No changes (openAPIpushChanges), CurrentPosition: ${this.WindowCovering.CurrentPosition},`
531
+ + ` TargetPosition: ${this.WindowCovering.TargetPosition}`);
621
532
  }
622
533
  }
623
534
  /**
624
535
  * Handle requests to set the value of the "Target Position" characteristic
625
536
  */
626
537
  async TargetPositionSet(value) {
627
- if (this.WindowCovering.TargetPosition === this.accessory.context.TargetPosition) {
628
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName} No Changes, Set TargetPosition: ${value}`);
538
+ if (this.WindowCovering.TargetPosition !== this.accessory.context.TargetPosition) {
539
+ await this.infoLog(`Set TargetPosition: ${value}`);
629
540
  }
630
541
  else {
631
- this.infoLog(`${this.device.deviceType}: ${this.accessory.displayName} Set TargetPosition: ${value}`);
542
+ await this.debugLog(`No Changes, TargetPosition: ${value}`);
632
543
  }
633
544
  // Set HoldPosition to false when TargetPosition is changed
634
545
  this.WindowCovering.HoldPosition = false;
@@ -643,20 +554,17 @@ export class Curtain extends deviceBase {
643
554
  if (this.WindowCovering.TargetPosition > this.WindowCovering.CurrentPosition) {
644
555
  this.WindowCovering.PositionState = this.hap.Characteristic.PositionState.INCREASING;
645
556
  this.setNewTarget = true;
646
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName} value: ${this.WindowCovering.TargetPosition},`
647
- + ` CurrentPosition: ${this.WindowCovering.CurrentPosition}`);
557
+ await this.debugLog(`value: ${this.WindowCovering.TargetPosition}, CurrentPosition: ${this.WindowCovering.CurrentPosition}`);
648
558
  }
649
559
  else if (this.WindowCovering.TargetPosition < this.WindowCovering.CurrentPosition) {
650
560
  this.WindowCovering.PositionState = this.hap.Characteristic.PositionState.DECREASING;
651
561
  this.setNewTarget = true;
652
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName} value: ${this.WindowCovering.TargetPosition},`
653
- + ` CurrentPosition: ${this.WindowCovering.CurrentPosition}`);
562
+ await this.debugLog(`value: ${this.WindowCovering.TargetPosition}, CurrentPosition: ${this.WindowCovering.CurrentPosition}`);
654
563
  }
655
564
  else {
656
565
  this.WindowCovering.PositionState = this.hap.Characteristic.PositionState.STOPPED;
657
566
  this.setNewTarget = false;
658
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName} value: ${this.WindowCovering.TargetPosition},`
659
- + ` CurrentPosition: ${this.WindowCovering.CurrentPosition}`);
567
+ await this.debugLog(`value: ${this.WindowCovering.TargetPosition}, CurrentPosition: ${this.WindowCovering.CurrentPosition}`);
660
568
  }
661
569
  this.WindowCovering.Service.setCharacteristic(this.hap.Characteristic.PositionState, this.WindowCovering.PositionState);
662
570
  this.WindowCovering.Service.getCharacteristic(this.hap.Characteristic.PositionState).updateValue(this.WindowCovering.PositionState);
@@ -665,10 +573,10 @@ export class Curtain extends deviceBase {
665
573
  * The minimum time depends on the network control latency.
666
574
  */
667
575
  clearTimeout(this.setNewTargetTimer);
668
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName} updateRate: ${this.deviceUpdateRate}`);
576
+ await this.debugLog(`deviceUpdateRate: ${this.deviceUpdateRate}`);
669
577
  if (this.setNewTarget) {
670
- this.setNewTargetTimer = setTimeout(() => {
671
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName} setNewTarget ${this.setNewTarget} timeout`);
578
+ this.setNewTargetTimer = setTimeout(async () => {
579
+ await this.debugLog(`setNewTarget ${this.setNewTarget} timeout`);
672
580
  this.setNewTarget = false;
673
581
  }, this.deviceUpdateRate * 1000);
674
582
  }
@@ -678,7 +586,7 @@ export class Curtain extends deviceBase {
678
586
  * Handle requests to set the value of the "Target Position" characteristic
679
587
  */
680
588
  async HoldPositionSet(value) {
681
- this.debugLog(`${this.device.deviceType}: ${this.accessory.displayName} HoldPosition: ${value}`);
589
+ this.debugLog(`HoldPosition: ${value}`);
682
590
  this.WindowCovering.HoldPosition = value;
683
591
  this.doCurtainUpdate.next();
684
592
  }
@@ -706,17 +614,14 @@ export class Curtain extends deviceBase {
706
614
  }
707
615
  async BLEPushConnection() {
708
616
  if (this.platform.config.credentials?.token && this.device.connectionType === 'BLE/OpenAPI') {
709
- this.warnLog(`${this.device.deviceType}: ${this.accessory.displayName} Using OpenAPI Connection to Push Changes`);
617
+ await this.warnLog('Using OpenAPI Connection to Push Changes');
710
618
  await this.openAPIpushChanges();
711
619
  }
712
620
  }
713
621
  async BLERefreshConnection(switchbot) {
714
- if (switchbot !== undefined) {
715
- this.errorLog(`${this.device.deviceType}: ${this.accessory.displayName} wasn't able to establish BLE Connection, node-switchbot:`
716
- + ` ${JSON.stringify(switchbot)}`);
717
- }
622
+ await this.errorLog(`wasn't able to establish BLE Connection, node-switchbot: ${JSON.stringify(switchbot)}`);
718
623
  if (this.platform.config.credentials?.token && this.device.connectionType === 'BLE/OpenAPI') {
719
- this.warnLog(`${this.device.deviceType}: ${this.accessory.displayName} Using OpenAPI Connection to Refresh Status`);
624
+ await this.warnLog('Using OpenAPI Connection to Refresh Status');
720
625
  await this.openAPIRefreshStatus();
721
626
  }
722
627
  }
@@ -753,6 +658,40 @@ export class Curtain extends deviceBase {
753
658
  }
754
659
  return { setPositionMode, Mode };
755
660
  }
661
+ async getCurrentPostion() {
662
+ await this.setMinMax();
663
+ await this.debugLog(`CurrentPosition ${this.WindowCovering.CurrentPosition}`);
664
+ if (this.setNewTarget) {
665
+ this.infoLog('Checking Status ...');
666
+ await this.setMinMax();
667
+ if (this.WindowCovering.TargetPosition > this.WindowCovering.CurrentPosition) {
668
+ await this.debugLog(`Closing, CurrentPosition: ${this.WindowCovering.CurrentPosition}`);
669
+ this.WindowCovering.PositionState = this.hap.Characteristic.PositionState.INCREASING;
670
+ this.WindowCovering.Service.getCharacteristic(this.hap.Characteristic.PositionState).updateValue(this.WindowCovering.PositionState);
671
+ await this.debugLog(`Increasing, PositionState: ${this.WindowCovering.PositionState}`);
672
+ }
673
+ else if (this.WindowCovering.TargetPosition < this.WindowCovering.CurrentPosition) {
674
+ await this.debugLog(`Opening, CurrentPosition: ${this.WindowCovering.CurrentPosition}`);
675
+ this.WindowCovering.PositionState = this.hap.Characteristic.PositionState.DECREASING;
676
+ this.WindowCovering.Service.getCharacteristic(this.hap.Characteristic.PositionState).updateValue(this.WindowCovering.PositionState);
677
+ await this.debugLog(`Decreasing, PositionState: ${this.WindowCovering.PositionState}`);
678
+ }
679
+ else {
680
+ await this.debugLog(`Standby, CurrentPosition: ${this.WindowCovering.CurrentPosition}`);
681
+ this.WindowCovering.PositionState = this.hap.Characteristic.PositionState.STOPPED;
682
+ this.WindowCovering.Service.getCharacteristic(this.hap.Characteristic.PositionState).updateValue(this.WindowCovering.PositionState);
683
+ await this.debugLog(`Stopped, PositionState: ${this.WindowCovering.PositionState}`);
684
+ }
685
+ }
686
+ else {
687
+ await this.debugLog(`Standby, CurrentPosition: ${this.WindowCovering.CurrentPosition}`);
688
+ this.WindowCovering.TargetPosition = this.WindowCovering.CurrentPosition;
689
+ this.WindowCovering.PositionState = this.hap.Characteristic.PositionState.STOPPED;
690
+ await this.debugLog(`Stopped, PositionState: ${this.WindowCovering.PositionState}`);
691
+ }
692
+ await this.debugLog(`CurrentPosition: ${this.WindowCovering.CurrentPosition}, TargetPosition: ${this.WindowCovering.TargetPosition},`
693
+ + ` PositionState: ${this.WindowCovering.PositionState},`);
694
+ }
756
695
  async setMinMax() {
757
696
  if (this.device.curtain?.set_min) {
758
697
  if (Number(this.WindowCovering.CurrentPosition) <= this.device.curtain?.set_min) {
@@ -784,7 +723,7 @@ export class Curtain extends deviceBase {
784
723
  this.Battery.Service.updateCharacteristic(this.hap.Characteristic.BatteryLevel, e);
785
724
  this.Battery.Service.updateCharacteristic(this.hap.Characteristic.StatusLowBattery, e);
786
725
  this.Battery.Service.updateCharacteristic(this.hap.Characteristic.ChargingState, e);
787
- if (!this.device.curtain?.hide_lightsensor) {
726
+ if (!this.device.curtain?.hide_lightsensor && this.LightSensor?.Service) {
788
727
  this.LightSensor.Service.updateCharacteristic(this.hap.Characteristic.CurrentAmbientLightLevel, e);
789
728
  this.LightSensor.Service.updateCharacteristic(this.hap.Characteristic.StatusActive, e);
790
729
  }