@switchbot/homebridge-switchbot 5.1.0-beta.9 → 5.1.1

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 (143) hide show
  1. package/.github/copilot-instructions.md +0 -63
  2. package/.github/scripts/compute-version-override.cjs +51 -0
  3. package/.github/scripts/normalize-changelog-header.cjs +1 -1
  4. package/.github/scripts/npm-version-script-esm-auto.js +1 -1
  5. package/.github/scripts/resolve-version-bump-esm.js +1 -1
  6. package/CHANGELOG.md +32 -9
  7. package/MIGRATION.md +0 -5
  8. package/README.md +0 -25
  9. package/config.schema.json +0 -11
  10. package/dist/{Platform.HAP.d.ts → SwitchBotHAPPlatform.d.ts} +16 -2
  11. package/dist/SwitchBotHAPPlatform.d.ts.map +1 -0
  12. package/dist/{Platform.HAP.js → SwitchBotHAPPlatform.js} +111 -40
  13. package/dist/SwitchBotHAPPlatform.js.map +1 -0
  14. package/dist/{Platform.Matter.d.ts → SwitchBotMatterPlatform.d.ts} +2 -4
  15. package/dist/SwitchBotMatterPlatform.d.ts.map +1 -0
  16. package/dist/{Platform.Matter.js → SwitchBotMatterPlatform.js} +6 -62
  17. package/dist/SwitchBotMatterPlatform.js.map +1 -0
  18. package/dist/device-types.d.ts.map +1 -1
  19. package/dist/device-types.js +10 -0
  20. package/dist/device-types.js.map +1 -1
  21. package/dist/deviceFactory.d.ts.map +1 -1
  22. package/dist/deviceFactory.js +10 -16
  23. package/dist/deviceFactory.js.map +1 -1
  24. package/dist/devices/genericDevice.d.ts +63 -5
  25. package/dist/devices/genericDevice.d.ts.map +1 -1
  26. package/dist/devices/genericDevice.js +251 -11
  27. package/dist/devices/genericDevice.js.map +1 -1
  28. package/dist/homebridge-ui/device-types.js +10 -0
  29. package/dist/homebridge-ui/device-types.js.map +1 -1
  30. package/dist/homebridge-ui/endpoints/config.d.ts.map +1 -1
  31. package/dist/homebridge-ui/endpoints/config.js +2 -9
  32. package/dist/homebridge-ui/endpoints/config.js.map +1 -1
  33. package/dist/homebridge-ui/homebridge-ui/endpoints/config.js +2 -9
  34. package/dist/homebridge-ui/homebridge-ui/endpoints/config.js.map +1 -1
  35. package/dist/homebridge-ui/homebridge-ui/utils/config-parser.js +0 -8
  36. package/dist/homebridge-ui/homebridge-ui/utils/config-parser.js.map +1 -1
  37. package/dist/homebridge-ui/public/css/styles.css +1 -61
  38. package/dist/homebridge-ui/public/index.html +2 -61
  39. package/dist/homebridge-ui/public/js/advanced-settings.d.ts.map +1 -1
  40. package/dist/homebridge-ui/public/js/advanced-settings.js +3 -4
  41. package/dist/homebridge-ui/public/js/advanced-settings.js.map +1 -1
  42. package/dist/homebridge-ui/public/js/advanced-settings.ts +3 -4
  43. package/dist/homebridge-ui/public/js/api.d.ts +0 -16
  44. package/dist/homebridge-ui/public/js/api.d.ts.map +1 -1
  45. package/dist/homebridge-ui/public/js/api.js +0 -48
  46. package/dist/homebridge-ui/public/js/api.js.map +1 -1
  47. package/dist/homebridge-ui/public/js/api.ts +1 -61
  48. package/dist/homebridge-ui/public/js/app.js +135 -272
  49. package/dist/homebridge-ui/public/js/app.js.map +4 -4
  50. package/dist/homebridge-ui/public/js/app.ts +4 -47
  51. package/dist/homebridge-ui/public/js/credentials.d.ts.map +1 -1
  52. package/dist/homebridge-ui/public/js/credentials.js +5 -11
  53. package/dist/homebridge-ui/public/js/credentials.js.map +1 -1
  54. package/dist/homebridge-ui/public/js/credentials.ts +5 -11
  55. package/dist/homebridge-ui/public/js/devices.d.ts.map +1 -1
  56. package/dist/homebridge-ui/public/js/devices.js +0 -6
  57. package/dist/homebridge-ui/public/js/devices.js.map +1 -1
  58. package/dist/homebridge-ui/public/js/devices.ts +0 -6
  59. package/dist/homebridge-ui/public/js/modals.d.ts +0 -1
  60. package/dist/homebridge-ui/public/js/modals.d.ts.map +1 -1
  61. package/dist/homebridge-ui/public/js/modals.js +0 -53
  62. package/dist/homebridge-ui/public/js/modals.js.map +1 -1
  63. package/dist/homebridge-ui/public/js/modals.ts +0 -58
  64. package/dist/homebridge-ui/public/js/render.d.ts.map +1 -1
  65. package/dist/homebridge-ui/public/js/render.js +1 -2
  66. package/dist/homebridge-ui/public/js/render.js.map +1 -1
  67. package/dist/homebridge-ui/public/js/render.ts +1 -2
  68. package/dist/homebridge-ui/settings.js.map +1 -1
  69. package/dist/homebridge-ui/utils/config-parser.d.ts +0 -8
  70. package/dist/homebridge-ui/utils/config-parser.d.ts.map +1 -1
  71. package/dist/homebridge-ui/utils/config-parser.js +0 -8
  72. package/dist/homebridge-ui/utils/config-parser.js.map +1 -1
  73. package/dist/index.js +2 -2
  74. package/dist/index.js.map +1 -1
  75. package/dist/settings.d.ts +0 -11
  76. package/dist/settings.d.ts.map +1 -1
  77. package/dist/settings.js.map +1 -1
  78. package/dist/utils.d.ts +0 -5
  79. package/dist/utils.d.ts.map +1 -1
  80. package/dist/utils.js +0 -27
  81. package/dist/utils.js.map +1 -1
  82. package/docs/assets/highlight.css +16 -16
  83. package/docs/assets/main.js +1 -1
  84. package/docs/assets/style.css +18 -3
  85. package/docs/hierarchy.html +26 -1
  86. package/docs/index.html +70 -23
  87. package/docs/modules.html +33 -1
  88. package/docs/variables/default.html +46 -3
  89. package/package.json +22 -15
  90. package/scripts/build-ui.js +0 -30
  91. package/src/{Platform.HAP.ts → SwitchBotHAPPlatform.ts} +112 -39
  92. package/src/{Platform.Matter.ts → SwitchBotMatterPlatform.ts} +8 -63
  93. package/src/device-types.ts +11 -0
  94. package/src/deviceFactory.ts +10 -15
  95. package/src/devices/genericDevice.ts +271 -12
  96. package/src/homebridge-ui/endpoints/config.ts +2 -10
  97. package/src/homebridge-ui/public/css/styles.css +1 -61
  98. package/src/homebridge-ui/public/index.html +0 -59
  99. package/src/homebridge-ui/public/js/advanced-settings.ts +3 -4
  100. package/src/homebridge-ui/public/js/api.ts +1 -61
  101. package/src/homebridge-ui/public/js/app.ts +4 -47
  102. package/src/homebridge-ui/public/js/credentials.ts +5 -11
  103. package/src/homebridge-ui/public/js/devices.ts +0 -6
  104. package/src/homebridge-ui/public/js/modals.ts +0 -58
  105. package/src/homebridge-ui/public/js/render.ts +1 -2
  106. package/src/homebridge-ui/utils/config-parser.ts +0 -9
  107. package/src/index.ts +2 -2
  108. package/src/settings.ts +0 -12
  109. package/src/utils.ts +0 -31
  110. package/test/device/deviceFactory.spec.ts +9 -0
  111. package/test/device/getstate-cache.spec.ts +62 -0
  112. package/test/device/getstate-returns-status.spec.ts +89 -0
  113. package/test/device/model-identities.spec.ts +45 -0
  114. package/test/device/water-detector-battery.spec.ts +81 -0
  115. package/test/device/water-detector-leak.spec.ts +43 -0
  116. package/test/hap-push-updates.spec.ts +150 -0
  117. package/test/platform/accessory-restore.spec.ts +2 -2
  118. package/test/platform/matter-childbridge.spec.ts +1 -1
  119. package/test/platform/matter-integration.spec.ts +1 -51
  120. package/test/platform/platform-edge.spec.ts +2 -2
  121. package/test/platform/platform.integration.spec.ts +1 -1
  122. package/test/utils/utils.spec.ts +0 -15
  123. package/.github/npm-version-script-esm.js +0 -97
  124. package/dist/Platform.HAP.d.ts.map +0 -1
  125. package/dist/Platform.HAP.js.map +0 -1
  126. package/dist/Platform.Matter.d.ts.map +0 -1
  127. package/dist/Platform.Matter.js.map +0 -1
  128. package/dist/homebridge-ui/homebridge-ui/utils/v4-detection.js +0 -23
  129. package/dist/homebridge-ui/homebridge-ui/utils/v4-detection.js.map +0 -1
  130. package/dist/homebridge-ui/public/js/legacy-view.d.ts +0 -3
  131. package/dist/homebridge-ui/public/js/legacy-view.d.ts.map +0 -1
  132. package/dist/homebridge-ui/public/js/legacy-view.js +0 -45
  133. package/dist/homebridge-ui/public/js/legacy-view.js.map +0 -1
  134. package/dist/homebridge-ui/public/js/legacy-view.ts +0 -107
  135. package/dist/homebridge-ui/utils/v4-detection.d.ts +0 -12
  136. package/dist/homebridge-ui/utils/v4-detection.d.ts.map +0 -1
  137. package/dist/homebridge-ui/utils/v4-detection.js +0 -23
  138. package/dist/homebridge-ui/utils/v4-detection.js.map +0 -1
  139. package/src/device-types.js +0 -246
  140. package/src/homebridge-ui/public/js/legacy-view.js +0 -45
  141. package/src/homebridge-ui/public/js/legacy-view.ts +0 -107
  142. package/src/homebridge-ui/utils/v4-detection.ts +0 -23
  143. package/test/homebridge-ui/config-parser.spec.ts +0 -61
@@ -1,14 +1,123 @@
1
1
  var __defProp = Object.defineProperty;
2
2
  var __getOwnPropNames = Object.getOwnPropertyNames;
3
- var __esm = (fn, res) => function __init() {
4
- return fn && (res = (0, fn[__getOwnPropNames(fn)[0]])(fn = 0)), res;
3
+ var __esm = (fn, res, err) => function __init() {
4
+ if (err) throw err[0];
5
+ try {
6
+ return fn && (res = (0, fn[__getOwnPropNames(fn)[0]])(fn = 0)), res;
7
+ } catch (e) {
8
+ throw err = [e], e;
9
+ }
5
10
  };
6
11
  var __export = (target, all) => {
7
12
  for (var name in all)
8
13
  __defProp(target, name, { get: all[name], enumerable: true });
9
14
  };
10
15
 
11
- // src/device-types.js
16
+ // src/homebridge-ui/public/js/logger.ts
17
+ var PREFIX, uiLog;
18
+ var init_logger = __esm({
19
+ "src/homebridge-ui/public/js/logger.ts"() {
20
+ "use strict";
21
+ PREFIX = "[SwitchBot UI/html]";
22
+ uiLog = {
23
+ info: (message, ...parameters) => {
24
+ console.log(PREFIX, message, ...parameters);
25
+ },
26
+ warn: (message, ...parameters) => {
27
+ console.warn(PREFIX, message, ...parameters);
28
+ },
29
+ error: (message, ...parameters) => {
30
+ console.error(PREFIX, message, ...parameters);
31
+ },
32
+ debug: (message, ...parameters) => {
33
+ console.debug(PREFIX, message, ...parameters);
34
+ }
35
+ };
36
+ }
37
+ });
38
+
39
+ // src/homebridge-ui/public/js/types.ts
40
+ var init_types = __esm({
41
+ "src/homebridge-ui/public/js/types.ts"() {
42
+ "use strict";
43
+ }
44
+ });
45
+
46
+ // src/homebridge-ui/public/js/modal.ts
47
+ function callUiMethod(name, ...args) {
48
+ try {
49
+ if (typeof homebridge?.[name] === "function") {
50
+ uiLog.info(`[callUiMethod] Invoking homebridge.${String(name)}()`);
51
+ const fn = homebridge?.[name];
52
+ if (typeof fn === "function") {
53
+ uiLog.info(`[callUiMethod] Invoking homebridge.${String(name)}()`);
54
+ fn.apply(homebridge, args);
55
+ } else {
56
+ uiLog.warn(`[callUiMethod] homebridge[${String(name)}] is not a function.`);
57
+ }
58
+ } else {
59
+ uiLog.warn(`[callUiMethod] homebridge[${String(name)}] is not a function.`);
60
+ }
61
+ } catch (e) {
62
+ uiLog.warn(`Homebridge UI method ${String(name)} failed:`, e);
63
+ }
64
+ }
65
+ function showBusyUi() {
66
+ callUiMethod("disableSaveButton");
67
+ callUiMethod("showSpinner");
68
+ }
69
+ function hideBusyUi() {
70
+ callUiMethod("hideSpinner");
71
+ callUiMethod("enableSaveButton");
72
+ }
73
+ var init_modal = __esm({
74
+ "src/homebridge-ui/public/js/modal.ts"() {
75
+ "use strict";
76
+ init_types();
77
+ init_logger();
78
+ }
79
+ });
80
+
81
+ // src/homebridge-ui/public/js/toast.ts
82
+ function showToast(method, message, title = "SwitchBot") {
83
+ try {
84
+ const hb = typeof window !== "undefined" ? window.homebridge : void 0;
85
+ const toast = hb && typeof hb.toast === "object" ? hb.toast : void 0;
86
+ if (toast && typeof toast[method] === "function") {
87
+ try {
88
+ toast[method](message, title);
89
+ return;
90
+ } catch (err) {
91
+ uiLog.warn(`Toast ${method} threw:`, err);
92
+ }
93
+ }
94
+ uiLog.info(`[Toast:${method}] ${title} - ${message}`);
95
+ } catch (e) {
96
+ uiLog.warn(`Toast ${method} outer error:`, e);
97
+ uiLog.info(`[Toast:${method}] ${title} - ${message}`);
98
+ }
99
+ }
100
+ function toastSuccess(message, title) {
101
+ showToast("success", message, title);
102
+ }
103
+ function toastError(message, title) {
104
+ showToast("error", message, title);
105
+ }
106
+ function toastWarning(message, title) {
107
+ showToast("warning", message, title);
108
+ }
109
+ function toastInfo(message, title) {
110
+ showToast("info", message, title);
111
+ }
112
+ var init_toast = __esm({
113
+ "src/homebridge-ui/public/js/toast.ts"() {
114
+ "use strict";
115
+ init_types();
116
+ init_logger();
117
+ }
118
+ });
119
+
120
+ // src/device-types.ts
12
121
  function getValidDeviceTypes() {
13
122
  const validTypes = /* @__PURE__ */ new Set();
14
123
  for (const category of Object.values(DEVICE_TYPES)) {
@@ -43,7 +152,7 @@ function isValidDeviceType(deviceType) {
43
152
  }
44
153
  var DEVICE_TYPES, DEVICE_TYPE_NORMALIZATION_MAP;
45
154
  var init_device_types = __esm({
46
- "src/device-types.js"() {
155
+ "src/device-types.ts"() {
47
156
  "use strict";
48
157
  DEVICE_TYPES = {
49
158
  "Window Coverings": ["Blind Tilt", "Curtain", "Curtain3", "Roller Shade"],
@@ -232,7 +341,17 @@ var init_device_types = __esm({
232
341
  "lock touch": "Keypad Touch",
233
342
  // Invalid type
234
343
  // Additional normalization for new/unknown types from logs
235
- "woplugus": "Plug Mini (US)"
344
+ "woplugus": "Plug Mini (US)",
345
+ // Product-specific identities reported by node-switchbot 5 (pySwitchbot 3.0.0 parity)
346
+ "woplugjp": "Plug Mini (JP)",
347
+ "wocurtain3": "Curtain3",
348
+ "wometerplus": "Meter Plus",
349
+ "wothpc": "Meter Pro (CO2)",
350
+ "woceilingpro": "Ceiling Light Pro",
351
+ "wolinkmini": "Hub Mini",
352
+ "woiosensorth": "WoIOSensor",
353
+ "outdoor meter": "WoIOSensor",
354
+ "indoor/outdoor thermo-hygrometer": "WoIOSensor"
236
355
  // Removed duplicate keys below, only last occurrence kept
237
356
  // 'plug mini us': 'plug mini (us)', // duplicate, removed
238
357
  // 'plug us': 'plug mini (us)', // duplicate, removed
@@ -249,90 +368,6 @@ var init_device_types = __esm({
249
368
  }
250
369
  });
251
370
 
252
- // src/homebridge-ui/utils/v4-detection.ts
253
- function isV4Config(platform) {
254
- if (!platform || typeof platform !== "object") {
255
- return false;
256
- }
257
- const hasCredentials = platform.credentials !== void 0 && typeof platform.credentials === "object";
258
- const hasOptionsDevices = platform.options !== void 0 && typeof platform.options === "object" && Array.isArray(platform.options.devices);
259
- return hasCredentials || hasOptionsDevices;
260
- }
261
- var init_v4_detection = __esm({
262
- "src/homebridge-ui/utils/v4-detection.ts"() {
263
- "use strict";
264
- }
265
- });
266
-
267
- // src/homebridge-ui/public/js/types.ts
268
- var init_types = __esm({
269
- "src/homebridge-ui/public/js/types.ts"() {
270
- "use strict";
271
- }
272
- });
273
-
274
- // src/homebridge-ui/public/js/logger.ts
275
- var PREFIX, uiLog;
276
- var init_logger = __esm({
277
- "src/homebridge-ui/public/js/logger.ts"() {
278
- "use strict";
279
- PREFIX = "[SwitchBot UI/html]";
280
- uiLog = {
281
- info: (message, ...parameters) => {
282
- console.log(PREFIX, message, ...parameters);
283
- },
284
- warn: (message, ...parameters) => {
285
- console.warn(PREFIX, message, ...parameters);
286
- },
287
- error: (message, ...parameters) => {
288
- console.error(PREFIX, message, ...parameters);
289
- },
290
- debug: (message, ...parameters) => {
291
- console.debug(PREFIX, message, ...parameters);
292
- }
293
- };
294
- }
295
- });
296
-
297
- // src/homebridge-ui/public/js/toast.ts
298
- function showToast(method, message, title = "SwitchBot") {
299
- try {
300
- const hb = typeof window !== "undefined" ? window.homebridge : void 0;
301
- const toast = hb && typeof hb.toast === "object" ? hb.toast : void 0;
302
- if (toast && typeof toast[method] === "function") {
303
- try {
304
- toast[method](message, title);
305
- return;
306
- } catch (err) {
307
- uiLog.warn(`Toast ${method} threw:`, err);
308
- }
309
- }
310
- uiLog.info(`[Toast:${method}] ${title} - ${message}`);
311
- } catch (e) {
312
- uiLog.warn(`Toast ${method} outer error:`, e);
313
- uiLog.info(`[Toast:${method}] ${title} - ${message}`);
314
- }
315
- }
316
- function toastSuccess(message, title) {
317
- showToast("success", message, title);
318
- }
319
- function toastError(message, title) {
320
- showToast("error", message, title);
321
- }
322
- function toastWarning(message, title) {
323
- showToast("warning", message, title);
324
- }
325
- function toastInfo(message, title) {
326
- showToast("info", message, title);
327
- }
328
- var init_toast = __esm({
329
- "src/homebridge-ui/public/js/toast.ts"() {
330
- "use strict";
331
- init_types();
332
- init_logger();
333
- }
334
- });
335
-
336
371
  // src/homebridge-ui/public/js/api.ts
337
372
  var api_exports = {};
338
373
  __export(api_exports, {
@@ -340,13 +375,12 @@ __export(api_exports, {
340
375
  addDevicesInBulk: () => addDevicesInBulk,
341
376
  deleteAllDevices: () => deleteAllDevices,
342
377
  deleteDevice: () => deleteDevice,
343
- detectV4Config: () => detectV4Config,
344
378
  discoverDevices: () => discoverDevices,
345
379
  fetchBluetoothStatus: () => fetchBluetoothStatus,
346
380
  fetchCredentialStatus: () => fetchCredentialStatus,
347
381
  fetchDevices: () => fetchDevices,
348
382
  normalizeBulkAddDevicesResponse: () => normalizeBulkAddDevicesResponse,
349
- saveCredentials: () => saveCredentials,
383
+ saveCredentials: () => saveCredentials2,
350
384
  syncParentPluginConfigFromDisk: () => syncParentPluginConfigFromDisk,
351
385
  testDeviceConnection: () => testDeviceConnection,
352
386
  updateDevice: () => updateDevice,
@@ -369,25 +403,6 @@ async function fetchDevices() {
369
403
  return [];
370
404
  }
371
405
  }
372
- async function detectV4Config() {
373
- try {
374
- if (typeof homebridge.getPluginConfig !== "function") {
375
- return false;
376
- }
377
- const configArr = await homebridge.getPluginConfig();
378
- if (!Array.isArray(configArr)) {
379
- return false;
380
- }
381
- const config = configArr.find(isSwitchBotPlatformConfig);
382
- if (!config || typeof config !== "object") {
383
- return false;
384
- }
385
- return isV4Config(config);
386
- } catch (e) {
387
- uiLog.warn("Error detecting v4 config:", e);
388
- return false;
389
- }
390
- }
391
406
  function validateAndFixDeviceTypes(devices) {
392
407
  const errors = [];
393
408
  for (const d of devices) {
@@ -457,7 +472,7 @@ async function fetchCredentialStatus() {
457
472
  return null;
458
473
  }
459
474
  }
460
- async function saveCredentials(token, secret) {
475
+ async function saveCredentials2(token, secret) {
461
476
  uiLog.info("Saving credentials...");
462
477
  const resp = await homebridge.request("/credentials", { token, secret });
463
478
  uiLog.info("Save response:", resp);
@@ -532,24 +547,6 @@ async function addDevice(deviceId, name, type, options) {
532
547
  if (options?.keyId) {
533
548
  newDevice.keyId = options.keyId;
534
549
  }
535
- if (options?.connectionPreference) {
536
- newDevice.connectionPreference = options.connectionPreference;
537
- }
538
- if (options?.externalPublishProtocol) {
539
- newDevice.externalPublishProtocol = options.externalPublishProtocol;
540
- }
541
- if (options?.room) {
542
- newDevice.room = options.room;
543
- }
544
- if (typeof options?.refreshRate === "number" && Number.isFinite(options.refreshRate)) {
545
- newDevice.refreshRate = options.refreshRate;
546
- }
547
- if (typeof options?.blePollingEnabled === "boolean") {
548
- newDevice.blePollingEnabled = options.blePollingEnabled;
549
- }
550
- if (typeof options?.blePollIntervalMs === "number" && Number.isFinite(options.blePollIntervalMs)) {
551
- newDevice.blePollIntervalMs = options.blePollIntervalMs;
552
- }
553
550
  config.devices.push(newDevice);
554
551
  await homebridge.updatePluginConfig(configArr);
555
552
  if (typeof homebridge.savePluginConfig === "function") {
@@ -670,48 +667,12 @@ var init_api = __esm({
670
667
  "src/homebridge-ui/public/js/api.ts"() {
671
668
  "use strict";
672
669
  init_device_types();
673
- init_v4_detection();
674
670
  init_types();
675
671
  init_logger();
676
672
  init_toast();
677
673
  }
678
674
  });
679
675
 
680
- // src/homebridge-ui/public/js/modal.ts
681
- function callUiMethod(name, ...args) {
682
- try {
683
- if (typeof homebridge?.[name] === "function") {
684
- uiLog.info(`[callUiMethod] Invoking homebridge.${String(name)}()`);
685
- const fn = homebridge?.[name];
686
- if (typeof fn === "function") {
687
- uiLog.info(`[callUiMethod] Invoking homebridge.${String(name)}()`);
688
- fn.apply(homebridge, args);
689
- } else {
690
- uiLog.warn(`[callUiMethod] homebridge[${String(name)}] is not a function.`);
691
- }
692
- } else {
693
- uiLog.warn(`[callUiMethod] homebridge[${String(name)}] is not a function.`);
694
- }
695
- } catch (e) {
696
- uiLog.warn(`Homebridge UI method ${String(name)} failed:`, e);
697
- }
698
- }
699
- function showBusyUi() {
700
- callUiMethod("disableSaveButton");
701
- callUiMethod("showSpinner");
702
- }
703
- function hideBusyUi() {
704
- callUiMethod("hideSpinner");
705
- callUiMethod("enableSaveButton");
706
- }
707
- var init_modal = __esm({
708
- "src/homebridge-ui/public/js/modal.ts"() {
709
- "use strict";
710
- init_types();
711
- init_logger();
712
- }
713
- });
714
-
715
676
  // src/homebridge-ui/public/js/discovery.ts
716
677
  var discovery_exports = {};
717
678
  __export(discovery_exports, {
@@ -1923,27 +1884,6 @@ async function importDiscoveredDevice(device) {
1923
1884
  opt.selected = (device.connectionPreference || "auto") === val;
1924
1885
  connectionPrefSelect.appendChild(opt);
1925
1886
  });
1926
- const externalPublishLabel = document.createElement("label");
1927
- externalPublishLabel.textContent = "Publish as External Device";
1928
- externalPublishLabel.style.display = "block";
1929
- externalPublishLabel.style.marginBottom = "6px";
1930
- externalPublishLabel.style.fontWeight = "500";
1931
- externalPublishLabel.style.fontSize = "12px";
1932
- externalPublishLabel.style.color = "#6b7280";
1933
- const externalPublishSelect = document.createElement("select");
1934
- externalPublishSelect.style.width = "100%";
1935
- externalPublishSelect.style.marginBottom = "12px";
1936
- externalPublishSelect.style.padding = "8px 10px";
1937
- externalPublishSelect.style.borderRadius = "6px";
1938
- externalPublishSelect.style.fontSize = "14px";
1939
- externalPublishSelect.style.boxSizing = "border-box";
1940
- ["none", "hap", "matter"].forEach((val) => {
1941
- const opt = document.createElement("option");
1942
- opt.value = val;
1943
- opt.text = val === "none" ? "None" : val.toUpperCase();
1944
- opt.selected = (device.externalPublishProtocol || "none") === val;
1945
- externalPublishSelect.appendChild(opt);
1946
- });
1947
1887
  const roomLabel = document.createElement("label");
1948
1888
  roomLabel.textContent = "Room";
1949
1889
  roomLabel.style.display = "block";
@@ -2075,7 +2015,6 @@ async function importDiscoveredDevice(device) {
2075
2015
  configDeviceType: typeSelect.value || device.type,
2076
2016
  address: macInput.value || void 0,
2077
2017
  connectionPreference: connectionPrefSelect.value || void 0,
2078
- externalPublishProtocol: externalPublishSelect.value || "none",
2079
2018
  room: roomInput.value || void 0,
2080
2019
  encryptionKey: encryptionKeyInput.value || void 0,
2081
2020
  keyId: keyIdInput.value || void 0,
@@ -2097,8 +2036,6 @@ async function importDiscoveredDevice(device) {
2097
2036
  contentDiv.appendChild(typeSelect);
2098
2037
  contentDiv.appendChild(connectionPrefLabel);
2099
2038
  contentDiv.appendChild(connectionPrefSelect);
2100
- contentDiv.appendChild(externalPublishLabel);
2101
- contentDiv.appendChild(externalPublishSelect);
2102
2039
  contentDiv.appendChild(roomLabel);
2103
2040
  contentDiv.appendChild(roomInput);
2104
2041
  contentDiv.appendChild(macLabel);
@@ -2304,27 +2241,6 @@ async function editDevice(device) {
2304
2241
  opt.selected = (device.connectionPreference || "auto") === val;
2305
2242
  connectionPrefSelect.appendChild(opt);
2306
2243
  });
2307
- const externalPublishLabel = document.createElement("label");
2308
- externalPublishLabel.textContent = "Publish as External Device";
2309
- externalPublishLabel.style.display = "block";
2310
- externalPublishLabel.style.marginBottom = "6px";
2311
- externalPublishLabel.style.fontWeight = "500";
2312
- externalPublishLabel.style.fontSize = "12px";
2313
- externalPublishLabel.style.color = "#6b7280";
2314
- const externalPublishSelect = document.createElement("select");
2315
- externalPublishSelect.style.width = "100%";
2316
- externalPublishSelect.style.marginBottom = "12px";
2317
- externalPublishSelect.style.padding = "8px 10px";
2318
- externalPublishSelect.style.borderRadius = "6px";
2319
- externalPublishSelect.style.fontSize = "14px";
2320
- externalPublishSelect.style.boxSizing = "border-box";
2321
- ["none", "hap", "matter"].forEach((val) => {
2322
- const opt = document.createElement("option");
2323
- opt.value = val;
2324
- opt.text = val === "none" ? "None" : val.toUpperCase();
2325
- opt.selected = (device.externalPublishProtocol || "none") === val;
2326
- externalPublishSelect.appendChild(opt);
2327
- });
2328
2244
  const roomLabel = document.createElement("label");
2329
2245
  roomLabel.textContent = "Room";
2330
2246
  roomLabel.style.display = "block";
@@ -2413,7 +2329,6 @@ async function editDevice(device) {
2413
2329
  configDeviceName: nameInput.value || void 0,
2414
2330
  configDeviceType: typeSelect.value,
2415
2331
  connectionPreference: connectionPrefSelect.value,
2416
- externalPublishProtocol: externalPublishSelect.value,
2417
2332
  room: roomInput.value || void 0,
2418
2333
  encryptionKey: encryptionKeyInput.value || void 0,
2419
2334
  keyId: keyIdInput.value || void 0,
@@ -2428,9 +2343,6 @@ async function editDevice(device) {
2428
2343
  if (params.room !== void 0) {
2429
2344
  options.room = params.room;
2430
2345
  }
2431
- if (params.externalPublishProtocol !== void 0) {
2432
- options.externalPublishProtocol = params.externalPublishProtocol;
2433
- }
2434
2346
  if (params.encryptionKey !== void 0) {
2435
2347
  options.encryptionKey = params.encryptionKey;
2436
2348
  }
@@ -2475,8 +2387,6 @@ async function editDevice(device) {
2475
2387
  contentDiv.appendChild(typeSelect);
2476
2388
  contentDiv.appendChild(connectionPrefLabel);
2477
2389
  contentDiv.appendChild(connectionPrefSelect);
2478
- contentDiv.appendChild(externalPublishLabel);
2479
- contentDiv.appendChild(externalPublishSelect);
2480
2390
  contentDiv.appendChild(roomLabel);
2481
2391
  contentDiv.appendChild(roomInput);
2482
2392
  contentDiv.appendChild(encryptionKeyLabel);
@@ -3525,9 +3435,8 @@ function renderDeviceList(list) {
3525
3435
  const id = `ID: ${deviceIdentifier}`;
3526
3436
  const typeText = d.configDeviceType || d.type ? `Type: ${d.configDeviceType || d.type}` : "";
3527
3437
  const connText = d.connectionPreference ? `Conn: ${d.connectionPreference}` : "";
3528
- const extText = d.externalPublishProtocol && d.externalPublishProtocol !== "none" ? `external: ${d.externalPublishProtocol}` : "";
3529
3438
  const roomText = d.room ? `Room: ${d.room}` : "";
3530
- meta.textContent = [id, typeText, connText, extText, roomText].filter(Boolean).join(" | ");
3439
+ meta.textContent = [id, typeText, connText, roomText].filter(Boolean).join(" | ");
3531
3440
  info.appendChild(nameContainer);
3532
3441
  info.appendChild(meta);
3533
3442
  info.appendChild(expandedDetails);
@@ -3626,14 +3535,8 @@ async function addDeviceToConfig2(device, options = {}) {
3626
3535
  address: importValues.address,
3627
3536
  model: device.model,
3628
3537
  rssi: device.rssi,
3629
- connectionPreference: importValues.connectionPreference,
3630
- externalPublishProtocol: importValues.externalPublishProtocol,
3631
- room: importValues.room,
3632
3538
  encryptionKey: importValues.encryptionKey,
3633
- keyId: importValues.keyId,
3634
- refreshRate: importValues.refreshRate,
3635
- blePollingEnabled: importValues.blePollingEnabled,
3636
- blePollIntervalMs: importValues.blePollIntervalMs
3539
+ keyId: importValues.keyId
3637
3540
  });
3638
3541
  uiLog.info("Add device response:", resp);
3639
3542
  const alreadyExists = !!resp?.alreadyExists;
@@ -3704,9 +3607,6 @@ var init_devices = __esm({
3704
3607
  }
3705
3608
  });
3706
3609
 
3707
- // src/homebridge-ui/public/js/app.ts
3708
- init_api();
3709
-
3710
3610
  // src/homebridge-ui/public/js/credentials.ts
3711
3611
  init_logger();
3712
3612
  init_modal();
@@ -3744,7 +3644,7 @@ async function loadCredentialStatus() {
3744
3644
  uiLog.error("Error loading credentials:", e);
3745
3645
  }
3746
3646
  }
3747
- async function saveCredentials2() {
3647
+ async function saveCredentials() {
3748
3648
  const token = document.getElementById("token")?.value;
3749
3649
  const secret = document.getElementById("secret")?.value;
3750
3650
  const saveStatus = document.getElementById("saveStatus");
@@ -3766,19 +3666,14 @@ async function saveCredentials2() {
3766
3666
  if (typeof homebridge.getPluginConfig !== "function" || typeof homebridge.updatePluginConfig !== "function") {
3767
3667
  throw new TypeError("Homebridge UI API not available");
3768
3668
  }
3769
- let configArr = await homebridge.getPluginConfig();
3770
- if (!Array.isArray(configArr)) {
3771
- configArr = [];
3772
- }
3773
- let idx = configArr.findIndex((c) => (c.platform || c.name || "").toLowerCase() === "switchbot");
3774
- if (idx === -1) {
3775
- configArr.push({ platform: "SwitchBot" });
3776
- idx = configArr.length - 1;
3669
+ const configArr = await homebridge.getPluginConfig();
3670
+ if (!Array.isArray(configArr) || configArr.length === 0) {
3671
+ throw new Error("No plugin config found");
3777
3672
  }
3778
- const config = configArr[idx];
3673
+ const config = configArr[0];
3779
3674
  config.openApiToken = token;
3780
3675
  config.openApiSecret = secret;
3781
- await homebridge.updatePluginConfig(configArr);
3676
+ await homebridge.updatePluginConfig([config]);
3782
3677
  if (typeof homebridge.savePluginConfig === "function") {
3783
3678
  await homebridge.savePluginConfig();
3784
3679
  }
@@ -3808,42 +3703,10 @@ async function saveCredentials2() {
3808
3703
  // src/homebridge-ui/public/js/app.ts
3809
3704
  init_devices();
3810
3705
  init_discovery();
3811
- async function ensureSwitchBotConfigBlock() {
3812
- try {
3813
- if (typeof homebridge.getPluginConfig !== "function" || typeof homebridge.updatePluginConfig !== "function") {
3814
- return;
3815
- }
3816
- let configArr = await homebridge.getPluginConfig();
3817
- if (!Array.isArray(configArr)) {
3818
- configArr = [];
3819
- }
3820
- const idx = configArr.findIndex((c) => (c.platform || c.name || "").toLowerCase().includes("switchbot"));
3821
- if (idx === -1) {
3822
- configArr.push({ platform: "SwitchBot" });
3823
- await homebridge.updatePluginConfig(configArr);
3824
- if (typeof homebridge.savePluginConfig === "function") {
3825
- await homebridge.savePluginConfig();
3826
- }
3827
- }
3828
- } catch (_e) {
3829
- }
3830
- }
3831
3706
  window.loadCredentialStatus = loadCredentialStatus;
3832
- window.saveCredentials = saveCredentials2;
3707
+ window.saveCredentials = saveCredentials;
3833
3708
  window.discoverDevices = discoverDevices2;
3834
- async function checkV4Config() {
3835
- const banner = document.getElementById("v4ConfigWarning");
3836
- if (!banner) {
3837
- return;
3838
- }
3839
- const isV4 = await detectV4Config();
3840
- if (isV4) {
3841
- banner.style.display = "block";
3842
- }
3843
- }
3844
3709
  async function init() {
3845
- await ensureSwitchBotConfigBlock();
3846
- await checkV4Config();
3847
3710
  await loadCredentialStatus();
3848
3711
  await initializeDiscoverySettings();
3849
3712
  await loadConfiguredDevices();