@smarthome.exchange/integrations 1.0.0 → 3.0.0

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 (529) hide show
  1. package/changelog.md +84 -0
  2. package/dist_ts/00_commitinfo_data.js +1 -1
  3. package/dist_ts/core/classes.configstore.d.ts +2 -0
  4. package/dist_ts/core/classes.configstore.js +84 -27
  5. package/dist_ts/core/classes.nativehomeadmission.d.ts +19 -0
  6. package/dist_ts/core/classes.nativehomeadmission.js +84 -0
  7. package/dist_ts/core/classes.nativeintegrationowner.d.ts +81 -0
  8. package/dist_ts/core/classes.nativeintegrationowner.js +273 -0
  9. package/dist_ts/core/classes.runtimemanager.d.ts +2 -0
  10. package/dist_ts/core/classes.runtimemanager.js +11 -3
  11. package/dist_ts/core/index.d.ts +2 -0
  12. package/dist_ts/core/index.js +3 -1
  13. package/dist_ts/core/types.d.ts +16 -0
  14. package/dist_ts/integrations/braviatv/braviatv.classes.client.d.ts +23 -72
  15. package/dist_ts/integrations/braviatv/braviatv.classes.client.js +265 -625
  16. package/dist_ts/integrations/braviatv/braviatv.classes.configflow.d.ts +7 -7
  17. package/dist_ts/integrations/braviatv/braviatv.classes.configflow.js +51 -68
  18. package/dist_ts/integrations/braviatv/braviatv.classes.integration.d.ts +8 -11
  19. package/dist_ts/integrations/braviatv/braviatv.classes.integration.js +186 -135
  20. package/dist_ts/integrations/braviatv/braviatv.discovery.js +12 -11
  21. package/dist_ts/integrations/braviatv/braviatv.mapper.d.ts +6 -14
  22. package/dist_ts/integrations/braviatv/braviatv.mapper.js +37 -131
  23. package/dist_ts/integrations/braviatv/braviatv.types.d.ts +55 -133
  24. package/dist_ts/integrations/braviatv/braviatv.validation.d.ts +7 -0
  25. package/dist_ts/integrations/braviatv/braviatv.validation.js +72 -0
  26. package/dist_ts/integrations/broadlink/broadlink.actions.d.ts +2 -0
  27. package/dist_ts/integrations/broadlink/broadlink.actions.js +36 -0
  28. package/dist_ts/integrations/broadlink/broadlink.classes.client.d.ts +21 -19
  29. package/dist_ts/integrations/broadlink/broadlink.classes.client.js +185 -124
  30. package/dist_ts/integrations/broadlink/broadlink.classes.configflow.d.ts +5 -4
  31. package/dist_ts/integrations/broadlink/broadlink.classes.configflow.js +64 -83
  32. package/dist_ts/integrations/broadlink/broadlink.classes.integration.d.ts +16 -19
  33. package/dist_ts/integrations/broadlink/broadlink.classes.integration.js +114 -59
  34. package/dist_ts/integrations/broadlink/broadlink.mapper.d.ts +3 -2
  35. package/dist_ts/integrations/broadlink/broadlink.mapper.js +2 -1
  36. package/dist_ts/integrations/broadlink/broadlink.selected.mapper.d.ts +10 -0
  37. package/dist_ts/integrations/broadlink/broadlink.selected.mapper.js +41 -0
  38. package/dist_ts/integrations/broadlink/broadlink.types.d.ts +43 -7
  39. package/dist_ts/integrations/broadlink/broadlink.validation.d.ts +7 -0
  40. package/dist_ts/integrations/broadlink/broadlink.validation.js +63 -0
  41. package/dist_ts/integrations/daikin/daikin.classes.client.d.ts +10 -52
  42. package/dist_ts/integrations/daikin/daikin.classes.client.js +55 -614
  43. package/dist_ts/integrations/daikin/daikin.classes.configflow.d.ts +8 -12
  44. package/dist_ts/integrations/daikin/daikin.classes.configflow.js +77 -138
  45. package/dist_ts/integrations/daikin/daikin.classes.integration.d.ts +7 -24
  46. package/dist_ts/integrations/daikin/daikin.classes.integration.js +175 -67
  47. package/dist_ts/integrations/daikin/daikin.discovery.d.ts +11 -24
  48. package/dist_ts/integrations/daikin/daikin.discovery.js +98 -305
  49. package/dist_ts/integrations/daikin/daikin.mapper.d.ts +6 -7
  50. package/dist_ts/integrations/daikin/daikin.mapper.js +95 -155
  51. package/dist_ts/integrations/daikin/daikin.types.d.ts +24 -44
  52. package/dist_ts/integrations/daikin/daikin.types.js +1 -1
  53. package/dist_ts/integrations/daikin/daikin.validation.d.ts +5 -0
  54. package/dist_ts/integrations/daikin/daikin.validation.js +53 -0
  55. package/dist_ts/integrations/deconz/deconz.classes.client.d.ts +37 -29
  56. package/dist_ts/integrations/deconz/deconz.classes.client.js +521 -294
  57. package/dist_ts/integrations/deconz/deconz.classes.configflow.d.ts +6 -1
  58. package/dist_ts/integrations/deconz/deconz.classes.configflow.js +63 -33
  59. package/dist_ts/integrations/deconz/deconz.classes.integration.d.ts +4 -3
  60. package/dist_ts/integrations/deconz/deconz.classes.integration.js +85 -40
  61. package/dist_ts/integrations/deconz/deconz.mapper.d.ts +1 -0
  62. package/dist_ts/integrations/deconz/deconz.mapper.js +24 -6
  63. package/dist_ts/integrations/deconz/deconz.types.d.ts +43 -6
  64. package/dist_ts/integrations/deconz/deconz.validation.d.ts +7 -1
  65. package/dist_ts/integrations/deconz/deconz.validation.js +215 -4
  66. package/dist_ts/integrations/denonavr/denonavr.classes.client.d.ts +31 -40
  67. package/dist_ts/integrations/denonavr/denonavr.classes.client.js +149 -404
  68. package/dist_ts/integrations/denonavr/denonavr.classes.configflow.d.ts +7 -2
  69. package/dist_ts/integrations/denonavr/denonavr.classes.configflow.js +44 -36
  70. package/dist_ts/integrations/denonavr/denonavr.classes.integration.d.ts +6 -11
  71. package/dist_ts/integrations/denonavr/denonavr.classes.integration.js +192 -113
  72. package/dist_ts/integrations/denonavr/denonavr.discovery.d.ts +10 -18
  73. package/dist_ts/integrations/denonavr/denonavr.discovery.js +71 -193
  74. package/dist_ts/integrations/denonavr/denonavr.mapper.d.ts +5 -13
  75. package/dist_ts/integrations/denonavr/denonavr.mapper.js +35 -159
  76. package/dist_ts/integrations/denonavr/denonavr.types.d.ts +55 -90
  77. package/dist_ts/integrations/denonavr/denonavr.validation.d.ts +10 -0
  78. package/dist_ts/integrations/denonavr/denonavr.validation.js +86 -0
  79. package/dist_ts/integrations/esphome/esphome.classes.client.d.ts +19 -7
  80. package/dist_ts/integrations/esphome/esphome.classes.client.js +183 -89
  81. package/dist_ts/integrations/esphome/esphome.classes.configflow.d.ts +5 -2
  82. package/dist_ts/integrations/esphome/esphome.classes.configflow.js +43 -33
  83. package/dist_ts/integrations/esphome/esphome.classes.integration.d.ts +8 -6
  84. package/dist_ts/integrations/esphome/esphome.classes.integration.js +71 -43
  85. package/dist_ts/integrations/esphome/esphome.discovery.js +4 -12
  86. package/dist_ts/integrations/esphome/esphome.mapper.d.ts +2 -2
  87. package/dist_ts/integrations/esphome/esphome.mapper.js +6 -4
  88. package/dist_ts/integrations/esphome/esphome.types.d.ts +31 -6
  89. package/dist_ts/integrations/esphome/esphome.types.js +1 -1
  90. package/dist_ts/integrations/esphome/esphome.validation.d.ts +7 -0
  91. package/dist_ts/integrations/esphome/esphome.validation.js +66 -0
  92. package/dist_ts/integrations/homeassistant/homeassistant.classes.client.d.ts +32 -4
  93. package/dist_ts/integrations/homeassistant/homeassistant.classes.client.js +345 -116
  94. package/dist_ts/integrations/homeassistant/homeassistant.classes.integration.d.ts +8 -5
  95. package/dist_ts/integrations/homeassistant/homeassistant.classes.integration.js +34 -8
  96. package/dist_ts/integrations/homeassistant/homeassistant.classes.runtime.d.ts +7 -4
  97. package/dist_ts/integrations/homeassistant/homeassistant.classes.runtime.js +44 -56
  98. package/dist_ts/integrations/homeassistant/homeassistant.types.d.ts +12 -1
  99. package/dist_ts/integrations/hue/hue.classes.client.d.ts +6 -1
  100. package/dist_ts/integrations/hue/hue.classes.client.js +120 -45
  101. package/dist_ts/integrations/hue/hue.classes.configflow.js +16 -7
  102. package/dist_ts/integrations/hue/hue.classes.integration.d.ts +2 -0
  103. package/dist_ts/integrations/hue/hue.classes.integration.js +103 -30
  104. package/dist_ts/integrations/hue/hue.validation.d.ts +1 -0
  105. package/dist_ts/integrations/hue/hue.validation.js +14 -4
  106. package/dist_ts/integrations/kodi/kodi.classes.client.d.ts +11 -45
  107. package/dist_ts/integrations/kodi/kodi.classes.client.js +84 -310
  108. package/dist_ts/integrations/kodi/kodi.classes.configflow.d.ts +9 -8
  109. package/dist_ts/integrations/kodi/kodi.classes.configflow.js +53 -48
  110. package/dist_ts/integrations/kodi/kodi.classes.integration.d.ts +11 -11
  111. package/dist_ts/integrations/kodi/kodi.classes.integration.js +114 -171
  112. package/dist_ts/integrations/kodi/kodi.discovery.js +53 -29
  113. package/dist_ts/integrations/kodi/kodi.mapper.d.ts +7 -2
  114. package/dist_ts/integrations/kodi/kodi.mapper.js +48 -10
  115. package/dist_ts/integrations/kodi/kodi.types.d.ts +32 -28
  116. package/dist_ts/integrations/kodi/kodi.validation.d.ts +9 -0
  117. package/dist_ts/integrations/kodi/kodi.validation.js +62 -0
  118. package/dist_ts/integrations/modbus/modbus.classes.client.d.ts +15 -61
  119. package/dist_ts/integrations/modbus/modbus.classes.client.js +117 -776
  120. package/dist_ts/integrations/modbus/modbus.classes.configflow.d.ts +9 -5
  121. package/dist_ts/integrations/modbus/modbus.classes.configflow.js +70 -38
  122. package/dist_ts/integrations/modbus/modbus.classes.integration.d.ts +6 -17
  123. package/dist_ts/integrations/modbus/modbus.classes.integration.js +133 -57
  124. package/dist_ts/integrations/modbus/modbus.discovery.d.ts +5 -8
  125. package/dist_ts/integrations/modbus/modbus.discovery.js +38 -93
  126. package/dist_ts/integrations/modbus/modbus.mapper.d.ts +8 -32
  127. package/dist_ts/integrations/modbus/modbus.mapper.js +71 -431
  128. package/dist_ts/integrations/modbus/modbus.types.d.ts +82 -332
  129. package/dist_ts/integrations/modbus/modbus.validation.d.ts +10 -0
  130. package/dist_ts/integrations/modbus/modbus.validation.js +128 -0
  131. package/dist_ts/integrations/mqtt/mqtt.classes.client.d.ts +15 -2
  132. package/dist_ts/integrations/mqtt/mqtt.classes.client.js +173 -23
  133. package/dist_ts/integrations/mqtt/mqtt.classes.configflow.d.ts +5 -1
  134. package/dist_ts/integrations/mqtt/mqtt.classes.configflow.js +53 -33
  135. package/dist_ts/integrations/mqtt/mqtt.classes.integration.d.ts +4 -1
  136. package/dist_ts/integrations/mqtt/mqtt.classes.integration.js +127 -56
  137. package/dist_ts/integrations/mqtt/mqtt.classes.session.d.ts +13 -0
  138. package/dist_ts/integrations/mqtt/mqtt.classes.session.js +130 -0
  139. package/dist_ts/integrations/mqtt/mqtt.mapper.d.ts +3 -0
  140. package/dist_ts/integrations/mqtt/mqtt.mapper.js +44 -1
  141. package/dist_ts/integrations/mqtt/mqtt.types.d.ts +46 -0
  142. package/dist_ts/integrations/mqtt/mqtt.validation.d.ts +7 -0
  143. package/dist_ts/integrations/mqtt/mqtt.validation.js +180 -0
  144. package/dist_ts/integrations/nanoleaf/nanoleaf.classes.client.d.ts +12 -34
  145. package/dist_ts/integrations/nanoleaf/nanoleaf.classes.client.js +143 -231
  146. package/dist_ts/integrations/nanoleaf/nanoleaf.classes.configflow.d.ts +6 -1
  147. package/dist_ts/integrations/nanoleaf/nanoleaf.classes.configflow.js +105 -18
  148. package/dist_ts/integrations/nanoleaf/nanoleaf.classes.integration.d.ts +8 -8
  149. package/dist_ts/integrations/nanoleaf/nanoleaf.classes.integration.js +141 -155
  150. package/dist_ts/integrations/nanoleaf/nanoleaf.credentials.d.ts +9 -0
  151. package/dist_ts/integrations/nanoleaf/nanoleaf.credentials.js +35 -0
  152. package/dist_ts/integrations/nanoleaf/nanoleaf.mapper.d.ts +6 -18
  153. package/dist_ts/integrations/nanoleaf/nanoleaf.mapper.js +45 -220
  154. package/dist_ts/integrations/nanoleaf/nanoleaf.types.d.ts +33 -147
  155. package/dist_ts/integrations/nanoleaf/nanoleaf.validation.d.ts +6 -0
  156. package/dist_ts/integrations/nanoleaf/nanoleaf.validation.js +82 -0
  157. package/dist_ts/integrations/onkyo/onkyo.classes.client.d.ts +15 -20
  158. package/dist_ts/integrations/onkyo/onkyo.classes.client.js +161 -404
  159. package/dist_ts/integrations/onkyo/onkyo.classes.configflow.d.ts +9 -4
  160. package/dist_ts/integrations/onkyo/onkyo.classes.configflow.js +51 -6
  161. package/dist_ts/integrations/onkyo/onkyo.classes.integration.d.ts +22 -6
  162. package/dist_ts/integrations/onkyo/onkyo.classes.integration.js +144 -11
  163. package/dist_ts/integrations/onkyo/onkyo.discovery.d.ts +6 -1
  164. package/dist_ts/integrations/onkyo/onkyo.discovery.js +40 -4
  165. package/dist_ts/integrations/onkyo/onkyo.mapper.d.ts +7 -8
  166. package/dist_ts/integrations/onkyo/onkyo.mapper.js +45 -12
  167. package/dist_ts/integrations/onkyo/onkyo.types.d.ts +58 -8
  168. package/dist_ts/integrations/onkyo/onkyo.types.js +13 -102
  169. package/dist_ts/integrations/onkyo/onkyo.validation.d.ts +16 -0
  170. package/dist_ts/integrations/onkyo/onkyo.validation.js +77 -0
  171. package/dist_ts/integrations/panasonic_viera/panasonic_viera.classes.client.d.ts +25 -25
  172. package/dist_ts/integrations/panasonic_viera/panasonic_viera.classes.client.js +116 -360
  173. package/dist_ts/integrations/panasonic_viera/panasonic_viera.classes.configflow.d.ts +11 -3
  174. package/dist_ts/integrations/panasonic_viera/panasonic_viera.classes.configflow.js +76 -6
  175. package/dist_ts/integrations/panasonic_viera/panasonic_viera.classes.integration.d.ts +26 -4
  176. package/dist_ts/integrations/panasonic_viera/panasonic_viera.classes.integration.js +142 -9
  177. package/dist_ts/integrations/panasonic_viera/panasonic_viera.discovery.d.ts +2 -1
  178. package/dist_ts/integrations/panasonic_viera/panasonic_viera.discovery.js +31 -4
  179. package/dist_ts/integrations/panasonic_viera/panasonic_viera.mapper.d.ts +9 -9
  180. package/dist_ts/integrations/panasonic_viera/panasonic_viera.mapper.js +31 -149
  181. package/dist_ts/integrations/panasonic_viera/panasonic_viera.types.d.ts +51 -11
  182. package/dist_ts/integrations/panasonic_viera/panasonic_viera.types.js +22 -87
  183. package/dist_ts/integrations/panasonic_viera/panasonic_viera.validation.d.ts +6 -0
  184. package/dist_ts/integrations/panasonic_viera/panasonic_viera.validation.js +56 -0
  185. package/dist_ts/integrations/pioneer/pioneer.classes.client.d.ts +31 -16
  186. package/dist_ts/integrations/pioneer/pioneer.classes.client.js +167 -409
  187. package/dist_ts/integrations/pioneer/pioneer.classes.configflow.d.ts +10 -3
  188. package/dist_ts/integrations/pioneer/pioneer.classes.configflow.js +66 -6
  189. package/dist_ts/integrations/pioneer/pioneer.classes.integration.d.ts +13 -5
  190. package/dist_ts/integrations/pioneer/pioneer.classes.integration.js +239 -11
  191. package/dist_ts/integrations/pioneer/pioneer.discovery.d.ts +14 -1
  192. package/dist_ts/integrations/pioneer/pioneer.discovery.js +51 -4
  193. package/dist_ts/integrations/pioneer/pioneer.mapper.d.ts +14 -8
  194. package/dist_ts/integrations/pioneer/pioneer.mapper.js +54 -12
  195. package/dist_ts/integrations/pioneer/pioneer.types.d.ts +79 -12
  196. package/dist_ts/integrations/pioneer/pioneer.types.js +12 -76
  197. package/dist_ts/integrations/pioneer/pioneer.validation.d.ts +10 -0
  198. package/dist_ts/integrations/pioneer/pioneer.validation.js +85 -0
  199. package/dist_ts/integrations/samsungtv/samsungtv.classes.client.d.ts +4 -2
  200. package/dist_ts/integrations/samsungtv/samsungtv.classes.client.js +41 -16
  201. package/dist_ts/integrations/samsungtv/samsungtv.classes.configflow.d.ts +5 -0
  202. package/dist_ts/integrations/samsungtv/samsungtv.classes.configflow.js +20 -7
  203. package/dist_ts/integrations/samsungtv/samsungtv.classes.integration.d.ts +1 -0
  204. package/dist_ts/integrations/samsungtv/samsungtv.classes.integration.js +53 -50
  205. package/dist_ts/integrations/samsungtv/samsungtv.types.d.ts +4 -1
  206. package/dist_ts/integrations/shelly/shelly.classes.client.d.ts +26 -30
  207. package/dist_ts/integrations/shelly/shelly.classes.client.js +504 -276
  208. package/dist_ts/integrations/shelly/shelly.classes.configflow.d.ts +8 -3
  209. package/dist_ts/integrations/shelly/shelly.classes.configflow.js +43 -38
  210. package/dist_ts/integrations/shelly/shelly.classes.integration.d.ts +6 -6
  211. package/dist_ts/integrations/shelly/shelly.classes.integration.js +103 -101
  212. package/dist_ts/integrations/shelly/shelly.classes.subscription.d.ts +4 -0
  213. package/dist_ts/integrations/shelly/shelly.classes.subscription.js +24 -2
  214. package/dist_ts/integrations/shelly/shelly.mapper.d.ts +1 -2
  215. package/dist_ts/integrations/shelly/shelly.mapper.js +21 -20
  216. package/dist_ts/integrations/shelly/shelly.rpc.js +4 -1
  217. package/dist_ts/integrations/shelly/shelly.types.d.ts +42 -2
  218. package/dist_ts/integrations/shelly/shelly.types.js +11 -2
  219. package/dist_ts/integrations/shelly/shelly.validation.d.ts +7 -0
  220. package/dist_ts/integrations/shelly/shelly.validation.js +79 -0
  221. package/dist_ts/integrations/sonos/sonos.classes.client.d.ts +79 -22
  222. package/dist_ts/integrations/sonos/sonos.classes.client.js +427 -139
  223. package/dist_ts/integrations/sonos/sonos.classes.configflow.d.ts +9 -2
  224. package/dist_ts/integrations/sonos/sonos.classes.configflow.js +26 -28
  225. package/dist_ts/integrations/sonos/sonos.classes.integration.d.ts +7 -6
  226. package/dist_ts/integrations/sonos/sonos.classes.integration.js +289 -224
  227. package/dist_ts/integrations/sonos/sonos.config.d.ts +6 -1
  228. package/dist_ts/integrations/sonos/sonos.config.js +23 -2
  229. package/dist_ts/integrations/sonos/sonos.mapper.d.ts +1 -1
  230. package/dist_ts/integrations/sonos/sonos.mapper.js +14 -9
  231. package/dist_ts/integrations/sonos/sonos.matchers.js +3 -3
  232. package/dist_ts/integrations/sonos/sonos.types.d.ts +26 -1
  233. package/dist_ts/integrations/soundtouch/soundtouch.classes.client.d.ts +13 -36
  234. package/dist_ts/integrations/soundtouch/soundtouch.classes.client.js +179 -502
  235. package/dist_ts/integrations/soundtouch/soundtouch.classes.configflow.d.ts +6 -1
  236. package/dist_ts/integrations/soundtouch/soundtouch.classes.configflow.js +50 -40
  237. package/dist_ts/integrations/soundtouch/soundtouch.classes.integration.d.ts +14 -15
  238. package/dist_ts/integrations/soundtouch/soundtouch.classes.integration.js +108 -128
  239. package/dist_ts/integrations/soundtouch/soundtouch.discovery.d.ts +2 -20
  240. package/dist_ts/integrations/soundtouch/soundtouch.discovery.js +23 -113
  241. package/dist_ts/integrations/soundtouch/soundtouch.mapper.d.ts +3 -12
  242. package/dist_ts/integrations/soundtouch/soundtouch.mapper.js +35 -189
  243. package/dist_ts/integrations/soundtouch/soundtouch.types.d.ts +57 -142
  244. package/dist_ts/integrations/soundtouch/soundtouch.types.js +18 -3
  245. package/dist_ts/integrations/soundtouch/soundtouch.validation.d.ts +22 -0
  246. package/dist_ts/integrations/soundtouch/soundtouch.validation.js +65 -0
  247. package/dist_ts/integrations/tasmota/tasmota.classes.integration.d.ts +5 -0
  248. package/dist_ts/integrations/tasmota/tasmota.classes.integration.js +23 -7
  249. package/dist_ts/integrations/tasmota/tasmota.classes.runtime.d.ts +19 -5
  250. package/dist_ts/integrations/tasmota/tasmota.classes.runtime.js +115 -41
  251. package/dist_ts/integrations/tasmota/tasmota.config.js +23 -1
  252. package/dist_ts/integrations/tasmota/tasmota.credentials.d.ts +11 -0
  253. package/dist_ts/integrations/tasmota/tasmota.credentials.js +97 -0
  254. package/dist_ts/integrations/tasmota/tasmota.discovery.d.ts +7 -1
  255. package/dist_ts/integrations/tasmota/tasmota.discovery.js +108 -30
  256. package/dist_ts/integrations/tasmota/tasmota.mapper.d.ts +2 -2
  257. package/dist_ts/integrations/tasmota/tasmota.mapper.js +7 -7
  258. package/dist_ts/integrations/tasmota/tasmota.types.d.ts +41 -2
  259. package/dist_ts/integrations/tuya/tuya.classes.integration.d.ts +4 -1
  260. package/dist_ts/integrations/tuya/tuya.classes.integration.js +79 -110
  261. package/dist_ts/integrations/tuya/tuya.classes.runtime.d.ts +5 -2
  262. package/dist_ts/integrations/tuya/tuya.classes.runtime.js +73 -26
  263. package/dist_ts/integrations/tuya/tuya.mapper.js +2 -2
  264. package/dist_ts/integrations/tuya/tuya.types.d.ts +3 -0
  265. package/dist_ts/integrations/tuya/tuya.validation.d.ts +2 -2
  266. package/dist_ts/integrations/tuya/tuya.validation.js +6 -11
  267. package/dist_ts/integrations/webostv/webostv.classes.client.d.ts +6 -5
  268. package/dist_ts/integrations/webostv/webostv.classes.client.js +147 -76
  269. package/dist_ts/integrations/webostv/webostv.classes.configflow.d.ts +7 -2
  270. package/dist_ts/integrations/webostv/webostv.classes.configflow.js +36 -20
  271. package/dist_ts/integrations/webostv/webostv.classes.integration.d.ts +4 -4
  272. package/dist_ts/integrations/webostv/webostv.classes.integration.js +46 -54
  273. package/dist_ts/integrations/webostv/webostv.mapper.js +5 -5
  274. package/dist_ts/integrations/webostv/webostv.types.d.ts +16 -3
  275. package/dist_ts/integrations/webostv/webostv.types.js +1 -1
  276. package/dist_ts/integrations/webostv/webostv.validation.d.ts +3 -1
  277. package/dist_ts/integrations/webostv/webostv.validation.js +23 -1
  278. package/dist_ts/integrations/wiz/index.d.ts +1 -0
  279. package/dist_ts/integrations/wiz/index.js +2 -1
  280. package/dist_ts/integrations/wiz/wiz.classes.client.d.ts +14 -28
  281. package/dist_ts/integrations/wiz/wiz.classes.client.js +93 -229
  282. package/dist_ts/integrations/wiz/wiz.classes.configflow.d.ts +6 -4
  283. package/dist_ts/integrations/wiz/wiz.classes.configflow.js +38 -67
  284. package/dist_ts/integrations/wiz/wiz.classes.integration.d.ts +10 -21
  285. package/dist_ts/integrations/wiz/wiz.classes.integration.js +204 -44
  286. package/dist_ts/integrations/wiz/wiz.discovery.d.ts +10 -31
  287. package/dist_ts/integrations/wiz/wiz.discovery.js +48 -249
  288. package/dist_ts/integrations/wiz/wiz.mapper.d.ts +7 -51
  289. package/dist_ts/integrations/wiz/wiz.mapper.js +82 -668
  290. package/dist_ts/integrations/wiz/wiz.types.d.ts +34 -208
  291. package/dist_ts/integrations/wiz/wiz.validation.d.ts +8 -0
  292. package/dist_ts/integrations/wiz/wiz.validation.js +72 -0
  293. package/dist_ts/integrations/yamaha/index.d.ts +1 -0
  294. package/dist_ts/integrations/yamaha/index.js +2 -1
  295. package/dist_ts/integrations/yamaha/yamaha.classes.client.d.ts +30 -4
  296. package/dist_ts/integrations/yamaha/yamaha.classes.client.js +162 -6
  297. package/dist_ts/integrations/yamaha/yamaha.classes.configflow.d.ts +10 -3
  298. package/dist_ts/integrations/yamaha/yamaha.classes.configflow.js +106 -6
  299. package/dist_ts/integrations/yamaha/yamaha.classes.integration.d.ts +22 -4
  300. package/dist_ts/integrations/yamaha/yamaha.classes.integration.js +243 -8
  301. package/dist_ts/integrations/yamaha/yamaha.discovery.d.ts +13 -1
  302. package/dist_ts/integrations/yamaha/yamaha.discovery.js +57 -4
  303. package/dist_ts/integrations/yamaha/yamaha.mapper.d.ts +16 -8
  304. package/dist_ts/integrations/yamaha/yamaha.mapper.js +58 -12
  305. package/dist_ts/integrations/yamaha/yamaha.types.d.ts +73 -6
  306. package/dist_ts/integrations/yamaha/yamaha.types.js +8 -94
  307. package/dist_ts/integrations/yamaha/yamaha.validation.d.ts +12 -0
  308. package/dist_ts/integrations/yamaha/yamaha.validation.js +89 -0
  309. package/dist_ts/integrations/zigbee2mqtt/zigbee2mqtt.classes.configflow.d.ts +6 -1
  310. package/dist_ts/integrations/zigbee2mqtt/zigbee2mqtt.classes.configflow.js +18 -8
  311. package/dist_ts/integrations/zigbee2mqtt/zigbee2mqtt.classes.integration.d.ts +4 -1
  312. package/dist_ts/integrations/zigbee2mqtt/zigbee2mqtt.classes.integration.js +54 -6
  313. package/dist_ts/integrations/zigbee2mqtt/zigbee2mqtt.classes.runtime.d.ts +12 -6
  314. package/dist_ts/integrations/zigbee2mqtt/zigbee2mqtt.classes.runtime.js +73 -59
  315. package/dist_ts/integrations/zigbee2mqtt/zigbee2mqtt.mapper.d.ts +3 -2
  316. package/dist_ts/integrations/zigbee2mqtt/zigbee2mqtt.mapper.js +17 -12
  317. package/dist_ts/integrations/zigbee2mqtt/zigbee2mqtt.types.d.ts +31 -2
  318. package/dist_ts/integrations/zigbee2mqtt/zigbee2mqtt.validation.d.ts +9 -1
  319. package/dist_ts/integrations/zigbee2mqtt/zigbee2mqtt.validation.js +57 -7
  320. package/dist_ts/integrations/zwave_js/zwave_js.classes.client.d.ts +10 -4
  321. package/dist_ts/integrations/zwave_js/zwave_js.classes.client.js +167 -31
  322. package/dist_ts/integrations/zwave_js/zwave_js.classes.configflow.d.ts +6 -1
  323. package/dist_ts/integrations/zwave_js/zwave_js.classes.configflow.js +57 -35
  324. package/dist_ts/integrations/zwave_js/zwave_js.classes.integration.d.ts +3 -1
  325. package/dist_ts/integrations/zwave_js/zwave_js.classes.integration.js +59 -37
  326. package/dist_ts/integrations/zwave_js/zwave_js.discovery.js +3 -3
  327. package/dist_ts/integrations/zwave_js/zwave_js.mapper.js +41 -24
  328. package/dist_ts/integrations/zwave_js/zwave_js.types.d.ts +25 -3
  329. package/dist_ts/integrations/zwave_js/zwave_js.validation.d.ts +6 -2
  330. package/dist_ts/integrations/zwave_js/zwave_js.validation.js +52 -17
  331. package/dist_ts/plugins.d.ts +2 -1
  332. package/dist_ts/plugins.js +3 -2
  333. package/package.json +9 -9
  334. package/readme.md +539 -8
  335. package/ts/00_commitinfo_data.ts +1 -1
  336. package/ts/core/classes.configstore.ts +84 -27
  337. package/ts/core/classes.nativehomeadmission.ts +96 -0
  338. package/ts/core/classes.nativeintegrationowner.ts +302 -0
  339. package/ts/core/classes.runtimemanager.ts +11 -2
  340. package/ts/core/index.ts +2 -0
  341. package/ts/core/types.ts +18 -0
  342. package/ts/integrations/braviatv/braviatv.classes.client.ts +245 -709
  343. package/ts/integrations/braviatv/braviatv.classes.configflow.ts +47 -76
  344. package/ts/integrations/braviatv/braviatv.classes.integration.ts +167 -147
  345. package/ts/integrations/braviatv/braviatv.discovery.ts +11 -10
  346. package/ts/integrations/braviatv/braviatv.mapper.ts +39 -142
  347. package/ts/integrations/braviatv/braviatv.types.ts +53 -173
  348. package/ts/integrations/braviatv/braviatv.validation.ts +68 -0
  349. package/ts/integrations/broadlink/broadlink.actions.ts +31 -0
  350. package/ts/integrations/broadlink/broadlink.classes.client.ts +170 -144
  351. package/ts/integrations/broadlink/broadlink.classes.configflow.ts +59 -89
  352. package/ts/integrations/broadlink/broadlink.classes.integration.ts +110 -64
  353. package/ts/integrations/broadlink/broadlink.mapper.ts +5 -4
  354. package/ts/integrations/broadlink/broadlink.selected.mapper.ts +46 -0
  355. package/ts/integrations/broadlink/broadlink.types.ts +48 -8
  356. package/ts/integrations/broadlink/broadlink.validation.ts +66 -0
  357. package/ts/integrations/daikin/daikin.classes.client.ts +52 -661
  358. package/ts/integrations/daikin/daikin.classes.configflow.ts +72 -152
  359. package/ts/integrations/daikin/daikin.classes.integration.ts +166 -71
  360. package/ts/integrations/daikin/daikin.discovery.ts +94 -346
  361. package/ts/integrations/daikin/daikin.mapper.ts +83 -166
  362. package/ts/integrations/daikin/daikin.types.ts +27 -48
  363. package/ts/integrations/daikin/daikin.validation.ts +51 -0
  364. package/ts/integrations/daikin/readme.md +83 -0
  365. package/ts/integrations/deconz/deconz.classes.client.ts +348 -252
  366. package/ts/integrations/deconz/deconz.classes.configflow.ts +57 -29
  367. package/ts/integrations/deconz/deconz.classes.integration.ts +69 -37
  368. package/ts/integrations/deconz/deconz.mapper.ts +22 -5
  369. package/ts/integrations/deconz/deconz.types.ts +49 -6
  370. package/ts/integrations/deconz/deconz.validation.ts +177 -4
  371. package/ts/integrations/deconz/readme.md +15 -1
  372. package/ts/integrations/denonavr/denonavr.classes.client.ts +132 -421
  373. package/ts/integrations/denonavr/denonavr.classes.configflow.ts +44 -37
  374. package/ts/integrations/denonavr/denonavr.classes.integration.ts +171 -117
  375. package/ts/integrations/denonavr/denonavr.discovery.ts +67 -220
  376. package/ts/integrations/denonavr/denonavr.mapper.ts +36 -182
  377. package/ts/integrations/denonavr/denonavr.types.ts +48 -111
  378. package/ts/integrations/denonavr/denonavr.validation.ts +87 -0
  379. package/ts/integrations/esphome/esphome.classes.client.ts +179 -94
  380. package/ts/integrations/esphome/esphome.classes.configflow.ts +40 -33
  381. package/ts/integrations/esphome/esphome.classes.integration.ts +63 -36
  382. package/ts/integrations/esphome/esphome.discovery.ts +3 -12
  383. package/ts/integrations/esphome/esphome.mapper.ts +9 -7
  384. package/ts/integrations/esphome/esphome.types.ts +35 -6
  385. package/ts/integrations/esphome/esphome.validation.ts +66 -0
  386. package/ts/integrations/esphome/readme.md +20 -6
  387. package/ts/integrations/homeassistant/homeassistant.classes.client.ts +353 -125
  388. package/ts/integrations/homeassistant/homeassistant.classes.integration.ts +35 -18
  389. package/ts/integrations/homeassistant/homeassistant.classes.runtime.ts +50 -63
  390. package/ts/integrations/homeassistant/homeassistant.types.ts +17 -1
  391. package/ts/integrations/homeassistant/readme.md +22 -6
  392. package/ts/integrations/hue/hue.classes.client.ts +110 -41
  393. package/ts/integrations/hue/hue.classes.configflow.ts +12 -6
  394. package/ts/integrations/hue/hue.classes.integration.ts +92 -26
  395. package/ts/integrations/hue/hue.validation.ts +13 -3
  396. package/ts/integrations/hue/readme.md +3 -3
  397. package/ts/integrations/kodi/kodi.classes.client.ts +72 -352
  398. package/ts/integrations/kodi/kodi.classes.configflow.ts +52 -55
  399. package/ts/integrations/kodi/kodi.classes.integration.ts +97 -178
  400. package/ts/integrations/kodi/kodi.discovery.ts +49 -28
  401. package/ts/integrations/kodi/kodi.mapper.ts +52 -10
  402. package/ts/integrations/kodi/kodi.types.ts +33 -58
  403. package/ts/integrations/kodi/kodi.validation.ts +60 -0
  404. package/ts/integrations/modbus/modbus.classes.client.ts +100 -842
  405. package/ts/integrations/modbus/modbus.classes.configflow.ts +70 -41
  406. package/ts/integrations/modbus/modbus.classes.integration.ts +115 -60
  407. package/ts/integrations/modbus/modbus.discovery.ts +38 -106
  408. package/ts/integrations/modbus/modbus.mapper.ts +64 -467
  409. package/ts/integrations/modbus/modbus.types.ts +64 -381
  410. package/ts/integrations/modbus/modbus.validation.ts +119 -0
  411. package/ts/integrations/mqtt/mqtt.classes.client.ts +136 -19
  412. package/ts/integrations/mqtt/mqtt.classes.configflow.ts +45 -32
  413. package/ts/integrations/mqtt/mqtt.classes.integration.ts +99 -38
  414. package/ts/integrations/mqtt/mqtt.classes.session.ts +118 -0
  415. package/ts/integrations/mqtt/mqtt.mapper.ts +43 -1
  416. package/ts/integrations/mqtt/mqtt.types.ts +52 -0
  417. package/ts/integrations/mqtt/mqtt.validation.ts +157 -0
  418. package/ts/integrations/mqtt/readme.md +12 -3
  419. package/ts/integrations/nanoleaf/nanoleaf.classes.client.ts +115 -249
  420. package/ts/integrations/nanoleaf/nanoleaf.classes.configflow.ts +90 -19
  421. package/ts/integrations/nanoleaf/nanoleaf.classes.integration.ts +130 -181
  422. package/ts/integrations/nanoleaf/nanoleaf.credentials.ts +39 -0
  423. package/ts/integrations/nanoleaf/nanoleaf.mapper.ts +47 -260
  424. package/ts/integrations/nanoleaf/nanoleaf.types.ts +29 -147
  425. package/ts/integrations/nanoleaf/nanoleaf.validation.ts +77 -0
  426. package/ts/integrations/onkyo/onkyo.classes.client.ts +148 -457
  427. package/ts/integrations/onkyo/onkyo.classes.configflow.ts +52 -6
  428. package/ts/integrations/onkyo/onkyo.classes.integration.ts +121 -12
  429. package/ts/integrations/onkyo/onkyo.discovery.ts +41 -3
  430. package/ts/integrations/onkyo/onkyo.mapper.ts +46 -19
  431. package/ts/integrations/onkyo/onkyo.types.ts +55 -110
  432. package/ts/integrations/onkyo/onkyo.validation.ts +85 -0
  433. package/ts/integrations/onkyo/readme.md +126 -0
  434. package/ts/integrations/panasonic_viera/panasonic_viera.classes.client.ts +101 -398
  435. package/ts/integrations/panasonic_viera/panasonic_viera.classes.configflow.ts +69 -5
  436. package/ts/integrations/panasonic_viera/panasonic_viera.classes.integration.ts +141 -9
  437. package/ts/integrations/panasonic_viera/panasonic_viera.discovery.ts +32 -3
  438. package/ts/integrations/panasonic_viera/panasonic_viera.mapper.ts +34 -161
  439. package/ts/integrations/panasonic_viera/panasonic_viera.types.ts +52 -96
  440. package/ts/integrations/panasonic_viera/panasonic_viera.validation.ts +56 -0
  441. package/ts/integrations/pioneer/pioneer.classes.client.ts +132 -428
  442. package/ts/integrations/pioneer/pioneer.classes.configflow.ts +67 -5
  443. package/ts/integrations/pioneer/pioneer.classes.integration.ts +225 -11
  444. package/ts/integrations/pioneer/pioneer.discovery.ts +45 -3
  445. package/ts/integrations/pioneer/pioneer.mapper.ts +57 -13
  446. package/ts/integrations/pioneer/pioneer.types.ts +87 -85
  447. package/ts/integrations/pioneer/pioneer.validation.ts +84 -0
  448. package/ts/integrations/samsungtv/readme.md +11 -5
  449. package/ts/integrations/samsungtv/samsungtv.classes.client.ts +40 -15
  450. package/ts/integrations/samsungtv/samsungtv.classes.configflow.ts +21 -6
  451. package/ts/integrations/samsungtv/samsungtv.classes.integration.ts +53 -38
  452. package/ts/integrations/samsungtv/samsungtv.types.ts +4 -1
  453. package/ts/integrations/shelly/readme.md +22 -7
  454. package/ts/integrations/shelly/shelly.classes.client.ts +386 -269
  455. package/ts/integrations/shelly/shelly.classes.configflow.ts +43 -38
  456. package/ts/integrations/shelly/shelly.classes.integration.ts +92 -111
  457. package/ts/integrations/shelly/shelly.classes.subscription.ts +24 -1
  458. package/ts/integrations/shelly/shelly.mapper.ts +19 -20
  459. package/ts/integrations/shelly/shelly.rpc.ts +2 -0
  460. package/ts/integrations/shelly/shelly.types.ts +50 -2
  461. package/ts/integrations/shelly/shelly.validation.ts +76 -0
  462. package/ts/integrations/sonos/readme.md +117 -38
  463. package/ts/integrations/sonos/sonos.classes.client.ts +392 -123
  464. package/ts/integrations/sonos/sonos.classes.configflow.ts +25 -28
  465. package/ts/integrations/sonos/sonos.classes.integration.ts +211 -186
  466. package/ts/integrations/sonos/sonos.config.ts +24 -2
  467. package/ts/integrations/sonos/sonos.mapper.ts +13 -8
  468. package/ts/integrations/sonos/sonos.matchers.ts +2 -2
  469. package/ts/integrations/sonos/sonos.types.ts +30 -1
  470. package/ts/integrations/soundtouch/soundtouch.classes.client.ts +152 -571
  471. package/ts/integrations/soundtouch/soundtouch.classes.configflow.ts +47 -42
  472. package/ts/integrations/soundtouch/soundtouch.classes.integration.ts +95 -150
  473. package/ts/integrations/soundtouch/soundtouch.discovery.ts +21 -133
  474. package/ts/integrations/soundtouch/soundtouch.mapper.ts +36 -207
  475. package/ts/integrations/soundtouch/soundtouch.types.ts +50 -195
  476. package/ts/integrations/soundtouch/soundtouch.validation.ts +60 -0
  477. package/ts/integrations/tasmota/readme.md +16 -5
  478. package/ts/integrations/tasmota/tasmota.classes.integration.ts +24 -6
  479. package/ts/integrations/tasmota/tasmota.classes.runtime.ts +112 -43
  480. package/ts/integrations/tasmota/tasmota.config.ts +17 -0
  481. package/ts/integrations/tasmota/tasmota.credentials.ts +92 -0
  482. package/ts/integrations/tasmota/tasmota.discovery.ts +87 -24
  483. package/ts/integrations/tasmota/tasmota.mapper.ts +6 -6
  484. package/ts/integrations/tasmota/tasmota.types.ts +43 -2
  485. package/ts/integrations/tuya/readme.md +52 -10
  486. package/ts/integrations/tuya/tuya.classes.integration.ts +69 -98
  487. package/ts/integrations/tuya/tuya.classes.runtime.ts +70 -24
  488. package/ts/integrations/tuya/tuya.mapper.ts +1 -1
  489. package/ts/integrations/tuya/tuya.types.ts +4 -0
  490. package/ts/integrations/tuya/tuya.validation.ts +5 -8
  491. package/ts/integrations/webostv/readme.md +115 -22
  492. package/ts/integrations/webostv/webostv.classes.client.ts +123 -50
  493. package/ts/integrations/webostv/webostv.classes.configflow.ts +35 -15
  494. package/ts/integrations/webostv/webostv.classes.integration.ts +44 -37
  495. package/ts/integrations/webostv/webostv.mapper.ts +4 -4
  496. package/ts/integrations/webostv/webostv.types.ts +18 -3
  497. package/ts/integrations/webostv/webostv.validation.ts +22 -1
  498. package/ts/integrations/wiz/index.ts +1 -0
  499. package/ts/integrations/wiz/wiz.classes.client.ts +84 -254
  500. package/ts/integrations/wiz/wiz.classes.configflow.ts +39 -70
  501. package/ts/integrations/wiz/wiz.classes.integration.ts +189 -45
  502. package/ts/integrations/wiz/wiz.discovery.ts +48 -291
  503. package/ts/integrations/wiz/wiz.mapper.ts +81 -754
  504. package/ts/integrations/wiz/wiz.types.ts +24 -224
  505. package/ts/integrations/wiz/wiz.validation.ts +73 -0
  506. package/ts/integrations/yamaha/index.ts +1 -0
  507. package/ts/integrations/yamaha/yamaha.classes.client.ts +150 -6
  508. package/ts/integrations/yamaha/yamaha.classes.configflow.ts +100 -5
  509. package/ts/integrations/yamaha/yamaha.classes.integration.ts +236 -8
  510. package/ts/integrations/yamaha/yamaha.discovery.ts +52 -3
  511. package/ts/integrations/yamaha/yamaha.mapper.ts +65 -13
  512. package/ts/integrations/yamaha/yamaha.types.ts +77 -97
  513. package/ts/integrations/yamaha/yamaha.validation.ts +86 -0
  514. package/ts/integrations/zigbee2mqtt/readme.md +22 -27
  515. package/ts/integrations/zigbee2mqtt/zigbee2mqtt.classes.configflow.ts +16 -7
  516. package/ts/integrations/zigbee2mqtt/zigbee2mqtt.classes.integration.ts +53 -6
  517. package/ts/integrations/zigbee2mqtt/zigbee2mqtt.classes.runtime.ts +62 -49
  518. package/ts/integrations/zigbee2mqtt/zigbee2mqtt.mapper.ts +17 -11
  519. package/ts/integrations/zigbee2mqtt/zigbee2mqtt.types.ts +35 -2
  520. package/ts/integrations/zigbee2mqtt/zigbee2mqtt.validation.ts +53 -7
  521. package/ts/integrations/zwave_js/readme.md +42 -9
  522. package/ts/integrations/zwave_js/zwave_js.classes.client.ts +155 -31
  523. package/ts/integrations/zwave_js/zwave_js.classes.configflow.ts +55 -31
  524. package/ts/integrations/zwave_js/zwave_js.classes.integration.ts +57 -35
  525. package/ts/integrations/zwave_js/zwave_js.discovery.ts +2 -2
  526. package/ts/integrations/zwave_js/zwave_js.mapper.ts +37 -23
  527. package/ts/integrations/zwave_js/zwave_js.types.ts +26 -3
  528. package/ts/integrations/zwave_js/zwave_js.validation.ts +52 -18
  529. package/ts/plugins.ts +2 -1
@@ -1,683 +1,74 @@
1
+ import * as plugins from '../../plugins.js';
2
+ import { NativeHomeAdmission } from '../../core/classes.nativehomeadmission.js';
3
+ import type { INativeIntegrationSetupContext } from '../../core/types.js';
1
4
  import { DaikinMapper } from './daikin.mapper.js';
2
- import type {
3
- IDaikinCommandRequest,
4
- IDaikinConfig,
5
- IDaikinControlSettings,
6
- IDaikinRawData,
7
- IDaikinRefreshResult,
8
- IDaikinSnapshot,
9
- IDaikinValueMap,
10
- TDaikinApiVariant,
11
- } from './daikin.types.js';
12
- import { daikinDefaultHttpPort, daikinDefaultHttpsPort, daikinDefaultTimeoutMs, daikinSkyFiPort } from './daikin.types.js';
13
-
14
- export class DaikinApiError extends Error {}
15
- export class DaikinApiConnectionError extends DaikinApiError {}
16
- export class DaikinApiAuthorizationError extends DaikinApiError {}
17
- export class DaikinUnsupportedCommandError extends DaikinApiError {}
18
-
19
- const legacyResources = [
20
- 'common/basic_info',
21
- 'aircon/get_sensor_info',
22
- 'aircon/get_model_info',
23
- 'aircon/get_control_info',
24
- 'aircon/get_target',
25
- 'common/get_holiday',
26
- 'common/get_notify',
27
- 'aircon/get_day_power_ex',
28
- 'aircon/get_week_power',
29
- 'aircon/get_year_power',
30
- ];
31
-
32
- const airbaseResources = [
33
- 'skyfi/common/basic_info',
34
- 'skyfi/aircon/get_control_info',
35
- 'skyfi/aircon/get_model_info',
36
- 'skyfi/aircon/get_sensor_info',
37
- 'skyfi/aircon/get_zone_setting',
38
- ];
39
-
40
- const resourceKeyMap: Record<string, keyof IDaikinRawData> = {
41
- 'common/basic_info': 'basicInfo',
42
- 'skyfi/common/basic_info': 'basicInfo',
43
- 'aircon/get_control_info': 'controlInfo',
44
- 'skyfi/aircon/get_control_info': 'controlInfo',
45
- 'aircon/get_sensor_info': 'sensorInfo',
46
- 'skyfi/aircon/get_sensor_info': 'sensorInfo',
47
- 'aircon/get_model_info': 'modelInfo',
48
- 'skyfi/aircon/get_model_info': 'modelInfo',
49
- 'common/get_holiday': 'holiday',
50
- 'common/get_notify': 'notify',
51
- 'aircon/get_day_power_ex': 'dayPowerEx',
52
- 'aircon/get_week_power': 'weekPower',
53
- 'aircon/get_year_power': 'yearPower',
54
- 'skyfi/aircon/get_zone_setting': 'zoneSetting',
55
- };
56
-
57
- const brp084ModeMap: Record<string, string> = {
58
- '0300': 'auto',
59
- '0200': 'cool',
60
- '0100': 'heat',
61
- '0000': 'fan',
62
- '0500': 'dry',
63
- };
64
-
65
- const brp084FanModeMap: Record<string, string> = {
66
- '0A00': 'auto',
67
- '0B00': 'quiet',
68
- '0300': '1',
69
- '0400': '2',
70
- '0500': '3',
71
- '0600': '4',
72
- '0700': '5',
73
- };
74
-
75
- const brp084Paths = {
76
- power: ['/dsiot/edge/adr_0100.dgc_status', 'dgc_status', 'e_1002', 'e_A002', 'p_01'],
77
- mode: ['/dsiot/edge/adr_0100.dgc_status', 'dgc_status', 'e_1002', 'e_3001', 'p_01'],
78
- indoorTemp: ['/dsiot/edge/adr_0100.dgc_status', 'dgc_status', 'e_1002', 'e_A00B', 'p_01'],
79
- indoorHumidity: ['/dsiot/edge/adr_0100.dgc_status', 'dgc_status', 'e_1002', 'e_A00B', 'p_02'],
80
- outdoorTemp: ['/dsiot/edge/adr_0200.dgc_status', 'dgc_status', 'e_1003', 'e_A00D', 'p_01'],
81
- mac: ['/dsiot/edge.adp_i', 'adp_i', 'mac'],
82
- coolTemp: ['/dsiot/edge/adr_0100.dgc_status', 'dgc_status', 'e_1002', 'e_3001', 'p_02'],
83
- heatTemp: ['/dsiot/edge/adr_0100.dgc_status', 'dgc_status', 'e_1002', 'e_3001', 'p_03'],
84
- autoTemp: ['/dsiot/edge/adr_0100.dgc_status', 'dgc_status', 'e_1002', 'e_3001', 'p_1D'],
85
- coolFan: ['/dsiot/edge/adr_0100.dgc_status', 'dgc_status', 'e_1002', 'e_3001', 'p_09'],
86
- heatFan: ['/dsiot/edge/adr_0100.dgc_status', 'dgc_status', 'e_1002', 'e_3001', 'p_0A'],
87
- autoFan: ['/dsiot/edge/adr_0100.dgc_status', 'dgc_status', 'e_1002', 'e_3001', 'p_26'],
88
- fanFan: ['/dsiot/edge/adr_0100.dgc_status', 'dgc_status', 'e_1002', 'e_3001', 'p_28'],
89
- todayRuntime: ['/dsiot/edge/adr_0100.i_power.week_power', 'week_power', 'today_runtime'],
90
- weeklyData: ['/dsiot/edge/adr_0100.i_power.week_power', 'week_power', 'datas'],
91
- };
5
+ import type { IDaikinNativeConfig, IDaikinSnapshot } from './daikin.types.js';
6
+ import { normalizeDaikinConfig } from './daikin.validation.js';
92
7
 
8
+ /** Selected BRP069 facade. The public protocol owns validation, preflight, HTTP, queueing and drain. */
93
9
  export class DaikinClient {
94
- private currentSnapshot?: IDaikinSnapshot;
95
-
96
- constructor(private readonly config: IDaikinConfig) {}
97
-
98
- public async getSnapshot(forceRefreshArg = false): Promise<IDaikinSnapshot> {
99
- if (!forceRefreshArg && this.currentSnapshot) {
100
- return this.cloneSnapshot(this.currentSnapshot);
101
- }
102
-
103
- if (!forceRefreshArg && this.config.snapshot) {
104
- this.currentSnapshot = DaikinMapper.toSnapshot({ config: this.config, source: 'snapshot', online: this.config.snapshot.online });
105
- return this.cloneSnapshot(this.currentSnapshot);
106
- }
107
-
108
- if (this.config.client) {
109
- try {
110
- this.currentSnapshot = await this.snapshotFromClient();
111
- } catch (errorArg) {
112
- this.currentSnapshot = this.offlineSnapshot(this.errorMessage(errorArg));
113
- }
114
- return this.cloneSnapshot(this.currentSnapshot);
115
- }
116
-
117
- if (!forceRefreshArg && this.hasManualData()) {
118
- this.currentSnapshot = DaikinMapper.toSnapshot({ config: this.config, online: this.config.online ?? true, source: 'manual' });
119
- return this.cloneSnapshot(this.currentSnapshot);
120
- }
121
-
122
- if (this.config.host || this.config.url) {
123
- try {
124
- this.currentSnapshot = await this.fetchSnapshot();
125
- } catch (errorArg) {
126
- this.currentSnapshot = this.offlineSnapshot(this.errorMessage(errorArg));
127
- }
128
- return this.cloneSnapshot(this.currentSnapshot);
129
- }
130
-
131
- this.currentSnapshot = this.offlineSnapshot('No Daikin local HTTP endpoint, client, snapshot, or manual data is configured.');
132
- return this.cloneSnapshot(this.currentSnapshot);
133
- }
134
-
135
- public async refresh(): Promise<IDaikinRefreshResult> {
136
- try {
137
- this.currentSnapshot = undefined;
138
- const snapshot = await this.getSnapshot(Boolean(this.config.host || this.config.url || this.config.client));
139
- const success = snapshot.online && !snapshot.error;
140
- return { success, snapshot, error: success ? undefined : snapshot.error, data: { source: snapshot.source } };
141
- } catch (errorArg) {
142
- const error = this.errorMessage(errorArg);
143
- const snapshot = this.offlineSnapshot(error);
144
- this.currentSnapshot = snapshot;
145
- return { success: false, snapshot: this.cloneSnapshot(snapshot), error };
146
- }
147
- }
148
-
149
- public async fetchSnapshot(): Promise<IDaikinSnapshot> {
150
- const variant = this.config.apiVariant || 'auto';
151
- if (variant === 'skyfi' || this.config.password) {
152
- return this.snapshotFromRawData(await this.fetchSkyFiRawData(), 'http');
153
- }
154
- if (variant === 'airbase') {
155
- return this.snapshotFromRawData(await this.fetchLegacyRawData('airbase'), 'http');
156
- }
157
- if (variant === 'brp084') {
158
- return this.snapshotFromRawData(await this.fetchBrp084RawData(), 'http');
159
- }
160
- if (variant === 'brp072c' || this.config.apiKey) {
161
- return this.snapshotFromRawData(await this.fetchLegacyRawData('brp072c'), 'http');
162
- }
163
-
164
- const legacy = await this.fetchLegacyRawData('brp069');
165
- const legacyValues = DaikinMapper.valuesFromRawData(legacy);
166
- if (legacyValues.mode || legacyValues.pow || legacyValues.htemp || legacyValues.mac) {
167
- return this.snapshotFromRawData(legacy, 'http');
168
- }
169
-
170
- return this.snapshotFromRawData(await this.fetchLegacyRawData('airbase'), 'http');
171
- }
172
-
173
- public async execute(commandArg: IDaikinCommandRequest): Promise<unknown> {
174
- if (this.config.commandExecutor) {
175
- return this.config.commandExecutor.execute(commandArg);
176
- }
177
- if (this.config.client?.execute) {
178
- return this.config.client.execute(commandArg);
179
- }
180
- if (commandArg.action === 'refresh') {
181
- return (await this.refresh()).snapshot;
182
- }
183
- if (!this.config.host && !this.config.url) {
184
- throw new DaikinApiConnectionError('Daikin commands require config.host/config.url, an injected client.execute, or commandExecutor. Static snapshots/manual data are read-only.');
185
- }
186
- if (commandArg.path && commandArg.method) {
187
- return this.requestKeyValue(commandArg.path, commandArg.query, this.requestVariant(commandArg.protocol), true);
188
- }
189
-
190
- switch (commandArg.action) {
191
- case 'set_control':
192
- return this.setControl(commandArg.settings || {}, this.requestVariant(commandArg.protocol));
193
- case 'set_holiday':
194
- return this.setHoliday(Boolean(commandArg.enabled), this.requestVariant(commandArg.protocol));
195
- case 'set_advanced_mode':
196
- return this.setAdvancedMode(commandArg.mode || 'powerful', Boolean(commandArg.enabled), this.requestVariant(commandArg.protocol));
197
- case 'set_streamer':
198
- return this.setStreamer(Boolean(commandArg.enabled), this.requestVariant(commandArg.protocol));
199
- case 'set_zone':
200
- return this.setZone(commandArg.zoneId, commandArg.zoneKey || 'zone_onoff', commandArg.zoneValue ?? (commandArg.enabled ? '1' : '0'), this.requestVariant(commandArg.protocol));
201
- default:
202
- throw new DaikinUnsupportedCommandError(`Unsupported Daikin command: ${commandArg.action}`);
203
- }
204
- }
205
-
206
- public async destroy(): Promise<void> {
207
- await this.config.client?.destroy?.();
208
- }
209
-
210
- private async snapshotFromClient(): Promise<IDaikinSnapshot> {
211
- const client = this.config.client;
212
- if (!client) {
213
- throw new DaikinApiConnectionError('No Daikin client configured.');
214
- }
215
- if (client.getSnapshot) {
216
- const result = await client.getSnapshot();
217
- if (this.isSnapshot(result)) {
218
- return DaikinMapper.toSnapshot({ config: { ...this.config, snapshot: result }, source: 'client', online: result.online });
219
- }
220
- return DaikinMapper.toSnapshot({ config: this.config, rawData: result, online: true, source: 'client' });
221
- }
222
- if (client.getRawData) {
223
- return DaikinMapper.toSnapshot({ config: this.config, rawData: await client.getRawData(), online: true, source: 'client' });
224
- }
225
- throw new DaikinApiConnectionError('Daikin client must expose getSnapshot() or getRawData().');
226
- }
227
-
228
- private snapshotFromRawData(rawDataArg: Partial<IDaikinRawData>, sourceArg: 'http' | 'manual' | 'client'): IDaikinSnapshot {
229
- return DaikinMapper.toSnapshot({ config: this.config, rawData: rawDataArg, online: true, source: sourceArg });
230
- }
231
-
232
- private async fetchLegacyRawData(variantArg: TDaikinApiVariant): Promise<Partial<IDaikinRawData>> {
233
- const resources = variantArg === 'airbase' ? airbaseResources : legacyResources;
234
- if (variantArg === 'brp072c' && this.config.apiKey) {
235
- await this.requestKeyValue('common/register_terminal', { key: this.config.apiKey }, variantArg, true);
236
- }
237
-
238
- const rawData: Partial<IDaikinRawData> = { variant: variantArg, resources: {}, fetchedAt: new Date().toISOString() };
239
- for (const resource of resources) {
240
- const data = await this.requestKeyValue(resource, undefined, variantArg, true).catch((errorArg) => {
241
- if (resource === resources[0]) {
242
- throw errorArg;
243
- }
244
- return {};
245
- });
246
- rawData.resources![resource] = data;
247
- const key = resourceKeyMap[resource];
248
- if (key) {
249
- (rawData as Record<string, unknown>)[key] = data;
250
- }
251
- }
252
- return rawData;
253
- }
254
-
255
- private async fetchSkyFiRawData(): Promise<Partial<IDaikinRawData>> {
256
- const ac = await this.requestSkyFi('ac.cgi');
257
- const zones = await this.requestSkyFi('zones.cgi').catch(() => ({}));
258
- return {
259
- variant: 'skyfi',
260
- skyfiAc: ac,
261
- skyfiZones: zones,
262
- values: { ...ac, ...zones },
263
- fetchedAt: new Date().toISOString(),
264
- };
265
- }
266
-
267
- private async fetchBrp084RawData(): Promise<Partial<IDaikinRawData>> {
268
- const payload = {
269
- requests: [
270
- { op: 2, to: '/dsiot/edge/adr_0100.dgc_status?filter=pv,pt,md' },
271
- { op: 2, to: '/dsiot/edge/adr_0200.dgc_status?filter=pv,pt,md' },
272
- { op: 2, to: '/dsiot/edge/adr_0100.i_power.week_power?filter=pv,pt,md' },
273
- { op: 2, to: '/dsiot/edge.adp_i' },
274
- ],
275
- };
276
- const response = await this.requestJson<Record<string, unknown>>('/dsiot/multireq', payload, 'brp084');
277
- const modeValue = this.findBrp084Value(response, brp084Paths.mode);
278
- const mode = brp084ModeMap[modeValue] || modeValue;
279
- const isOff = this.findBrp084Value(response, brp084Paths.power) === '00';
280
- const tempPath = mode === 'cool' ? brp084Paths.coolTemp : mode === 'heat' ? brp084Paths.heatTemp : brp084Paths.autoTemp;
281
- const fanPath = mode === 'cool' ? brp084Paths.coolFan : mode === 'heat' ? brp084Paths.heatFan : mode === 'fan' ? brp084Paths.fanFan : brp084Paths.autoFan;
282
- const values: IDaikinValueMap = {
283
- mac: this.findBrp084Value(response, brp084Paths.mac),
284
- pow: isOff ? '0' : '1',
285
- mode: isOff ? 'off' : mode,
286
- otemp: this.hexTemp(this.findBrp084Value(response, brp084Paths.outdoorTemp)),
287
- htemp: this.hexTemp(this.findBrp084Value(response, brp084Paths.indoorTemp), 1),
288
- hhum: this.hexInt(this.findBrp084Value(response, brp084Paths.indoorHumidity)),
289
- stemp: this.hexTemp(this.findBrp084Value(response, tempPath)),
290
- f_rate: brp084FanModeMap[this.findBrp084Value(response, fanPath)] || 'auto',
291
- datas: this.brp084WeeklyData(response),
292
- };
293
- return { variant: 'brp084', brp084: response, values, fetchedAt: new Date().toISOString() };
294
- }
295
-
296
- private async setControl(settingsArg: Partial<IDaikinControlSettings>, variantArg: TDaikinApiVariant): Promise<unknown> {
297
- if (variantArg === 'skyfi') {
298
- return this.setSkyFiControl(settingsArg);
299
- }
300
- if (variantArg === 'brp084') {
301
- throw new DaikinUnsupportedCommandError('Daikin BRP084 dsiot control writes are not implemented by this native port. Provide commandExecutor for BRP084 controls.');
302
- }
303
- return this.setLegacyControl(settingsArg, variantArg === 'airbase' ? 'airbase' : 'brp069');
304
- }
305
-
306
- private async setLegacyControl(settingsArg: Partial<IDaikinControlSettings>, variantArg: 'brp069' | 'airbase'): Promise<unknown> {
307
- const prefix = variantArg === 'airbase' ? 'skyfi/' : '';
308
- const current = await this.requestKeyValue(`${prefix}aircon/get_control_info`, undefined, variantArg, true);
309
- const values: IDaikinValueMap = { ...current };
310
- this.applyControlSettings(values, settingsArg, variantArg);
311
-
312
- if (settingsArg.mode === 'off') {
313
- values.pow = '0';
314
- values.mode = current.mode || values.mode;
315
- } else if ('mode' in settingsArg || Object.keys(settingsArg).length === 0) {
316
- values.pow = '1';
317
- }
318
-
319
- this.fillModeDefaults(values, current);
320
- const query = variantArg === 'airbase'
321
- ? {
322
- f_airside: values.f_airside || 0,
323
- f_auto: values.f_auto || '0',
324
- f_dir: values.f_dir || '0',
325
- f_rate: (values.f_rate || 'A')[0],
326
- lpw: '',
327
- mode: values.mode || current.mode || '0',
328
- pow: values.pow || current.pow || '1',
329
- shum: values.shum || current.shum || '--',
330
- stemp: values.stemp || current.stemp || '--',
331
- }
332
- : this.cleanQuery({
333
- mode: values.mode || current.mode || '0',
334
- pow: values.pow || current.pow || '1',
335
- shum: values.shum || current.shum || '--',
336
- stemp: values.stemp || current.stemp || '--',
337
- f_rate: values.f_rate !== undefined || current.f_rate !== undefined ? values.f_rate || current.f_rate : undefined,
338
- f_dir: values.f_dir !== undefined || current.f_dir !== undefined ? values.f_dir || current.f_dir : undefined,
339
- f_dir_ud: current.f_dir_ud !== undefined ? this.swingAxis(values.f_dir, 'ud') : undefined,
340
- f_dir_lr: current.f_dir_lr !== undefined ? this.swingAxis(values.f_dir, 'lr') : undefined,
341
- });
342
- return this.requestKeyValue(`${prefix}aircon/set_control_info`, query, variantArg, true);
343
- }
344
-
345
- private async setSkyFiControl(settingsArg: Partial<IDaikinControlSettings>): Promise<unknown> {
346
- const current = await this.requestSkyFi('ac.cgi');
347
- const values: IDaikinValueMap = { ...current };
348
- this.applyControlSettings(values, settingsArg, 'skyfi');
349
- if (settingsArg.mode === 'off') {
350
- return this.requestSkyFi('set.cgi', { p: '0' });
351
- }
352
- if ('mode' in settingsArg || Object.keys(settingsArg).length === 0) {
353
- values.opmode = '1';
354
- values.pow = '1';
355
- }
356
- return this.requestSkyFi('set.cgi', {
357
- p: values.opmode || values.pow || '1',
358
- t: values.settemp || values.stemp || current.settemp || current.stemp,
359
- f: values.fanspeed || values.f_rate || current.fanspeed || current.f_rate,
360
- m: values.acmode || values.mode || current.acmode || current.mode,
10
+ readonly #config: Readonly<IDaikinNativeConfig>;
11
+ readonly #protocol: plugins.ecobridgeDeviceManager.DaikinProtocol;
12
+ readonly #lifetime = new AbortController();
13
+ #healthy = false;
14
+ #destroy?: Promise<void>;
15
+ #removeAbort: () => void = () => undefined;
16
+
17
+ constructor(configArg: IDaikinNativeConfig, contextArg: INativeIntegrationSetupContext) {
18
+ const config = normalizeDaikinConfig(configArg);
19
+ const context = new NativeHomeAdmission('daikin').admit(contextArg, config.homeId);
20
+ const signalArg = context.abortSignal;
21
+ this.#config = Object.freeze({ ...config, homeId: context.homeId });
22
+ this.#protocol = new plugins.ecobridgeDeviceManager.DaikinProtocol({
23
+ address: this.#config.host, expectedMac: this.#config.expectedMac, port: this.#config.port,
24
+ timeoutMs: this.#config.timeoutMs, maxResponseBytes: this.#config.maxResponseBytes,
25
+ maxPendingOperations: this.#config.maxPendingOperations,
361
26
  });
362
- }
363
-
364
- private async setHoliday(enabledArg: boolean, variantArg: TDaikinApiVariant): Promise<unknown> {
365
- if (variantArg === 'skyfi' || variantArg === 'airbase' || variantArg === 'brp084') {
366
- throw new DaikinUnsupportedCommandError(`Daikin ${variantArg} holiday mode is not represented by a supported local request in this port.`);
367
- }
368
- return this.requestKeyValue('common/set_holiday', { en_hol: enabledArg ? '1' : '0' }, variantArg, true);
369
- }
370
-
371
- private async setAdvancedMode(modeArg: string, enabledArg: boolean, variantArg: TDaikinApiVariant): Promise<unknown> {
372
- if (variantArg === 'skyfi' || variantArg === 'brp084') {
373
- throw new DaikinUnsupportedCommandError(`Daikin ${variantArg} advanced modes are not represented by a supported local request in this port.`);
27
+ if (signalArg) {
28
+ // Preserve cleanup failure in destroy() while an event listener has no promise consumer.
29
+ const aborted = (): void => { void this.destroy().catch(() => undefined); };
30
+ signalArg.addEventListener('abort', aborted, { once: true });
31
+ this.#removeAbort = () => signalArg.removeEventListener('abort', aborted);
32
+ if (signalArg.aborted) aborted();
374
33
  }
375
- const mode = DaikinMapper.humanToDaikin('spmode_kind', modeArg, variantArg) || modeArg;
376
- return this.requestKeyValue(`${variantArg === 'airbase' ? 'skyfi/' : ''}aircon/set_special_mode`, { spmode_kind: mode, set_spmode: enabledArg ? '1' : '0' }, variantArg, true);
377
34
  }
378
35
 
379
- private async setStreamer(enabledArg: boolean, variantArg: TDaikinApiVariant): Promise<unknown> {
380
- if (variantArg === 'skyfi' || variantArg === 'brp084') {
381
- throw new DaikinUnsupportedCommandError(`Daikin ${variantArg} streamer mode is not represented by a supported local request in this port.`);
382
- }
383
- return this.requestKeyValue(`${variantArg === 'airbase' ? 'skyfi/' : ''}aircon/set_special_mode`, { en_streamer: enabledArg ? '1' : '0' }, variantArg, true);
384
- }
36
+ public get config(): Readonly<IDaikinNativeConfig> { return this.#config; }
37
+ public isHealthy(): boolean { return this.#healthy && !this.#lifetime.signal.aborted; }
385
38
 
386
- private async setZone(zoneIdArg: number | undefined, keyArg: string, valueArg: string, variantArg: TDaikinApiVariant): Promise<unknown> {
387
- if (zoneIdArg === undefined || !Number.isInteger(zoneIdArg) || zoneIdArg < 0) {
388
- throw new DaikinUnsupportedCommandError('Daikin zone commands require a non-negative zoneId.');
389
- }
390
- if (variantArg === 'skyfi') {
391
- if (keyArg !== 'zone_onoff') {
392
- throw new DaikinUnsupportedCommandError('Daikin SkyFi only supports zone_onoff through setzone.cgi.');
393
- }
394
- return this.requestSkyFi('setzone.cgi', { z: zoneIdArg + 1, s: valueArg });
395
- }
396
- if (variantArg !== 'airbase') {
397
- throw new DaikinUnsupportedCommandError(`Daikin ${variantArg} zone commands are not represented by a supported local request in this port.`);
398
- }
399
-
400
- const current = await this.requestKeyValue('skyfi/aircon/get_zone_setting', undefined, variantArg, true);
401
- if (!current[keyArg]) {
402
- throw new DaikinUnsupportedCommandError(`Daikin AirBase zone setting ${keyArg} is not available on this device.`);
403
- }
404
- const group = this.listValue(current[keyArg]);
405
- if (zoneIdArg >= group.length) {
406
- throw new DaikinUnsupportedCommandError(`Daikin AirBase zone ${zoneIdArg} is outside the available range 0-${Math.max(0, group.length - 1)}.`);
407
- }
408
- group[zoneIdArg] = valueArg;
409
- const values = { ...current, [keyArg]: encodeURIComponent(group.join(';')).toLowerCase() };
410
- const query = [`zone_name=${values.zone_name || ''}`, `zone_onoff=${values.zone_onoff || ''}`];
411
- if (values.lztemp_c !== undefined && values.lztemp_h !== undefined) {
412
- query.push(`lztemp_c=${values.lztemp_c}`, `lztemp_h=${values.lztemp_h}`);
413
- }
414
- return this.requestKeyValue(`skyfi/aircon/set_zone_setting?${query.join('&')}`, undefined, variantArg, true);
415
- }
416
-
417
- private applyControlSettings(valuesArg: IDaikinValueMap, settingsArg: Partial<IDaikinControlSettings>, variantArg: TDaikinApiVariant): void {
418
- for (const [key, value] of Object.entries(settingsArg)) {
419
- if (value === undefined) {
420
- continue;
421
- }
422
- if (key === 'stemp') {
423
- valuesArg.stemp = DaikinMapper.formatTargetTemperature(Number(value));
424
- valuesArg.settemp = valuesArg.stemp;
425
- } else if (key === 'shum') {
426
- valuesArg.shum = String(value);
427
- } else if (key === 'mode') {
428
- const daikinMode = DaikinMapper.humanToDaikin('mode', String(value), variantArg);
429
- valuesArg.mode = daikinMode;
430
- valuesArg.acmode = daikinMode;
431
- } else if (key === 'f_rate') {
432
- const fanRate = DaikinMapper.humanToDaikin('f_rate', String(value), variantArg);
433
- valuesArg.f_rate = fanRate;
434
- valuesArg.fanspeed = fanRate;
435
- } else if (key === 'f_dir') {
436
- valuesArg.f_dir = DaikinMapper.humanToDaikin('f_dir', String(value), variantArg);
437
- } else {
438
- valuesArg[key] = String(value);
439
- }
440
- }
441
- }
442
-
443
- private fillModeDefaults(valuesArg: IDaikinValueMap, currentArg: IDaikinValueMap): void {
444
- const mode = valuesArg.mode || currentArg.mode;
445
- if (!mode) {
446
- return;
447
- }
448
- const defaults: Record<string, string> = { stemp: `dt${mode}`, shum: `dh${mode}`, f_rate: `dfr${mode}` };
449
- for (const [target, source] of Object.entries(defaults)) {
450
- if (valuesArg[target] === undefined && currentArg[source] !== undefined) {
451
- valuesArg[target] = currentArg[source];
452
- }
453
- }
454
- }
455
-
456
- private async requestSkyFi(pathArg: string, queryArg: Record<string, string | number | boolean | undefined> = {}): Promise<IDaikinValueMap> {
457
- const query = { pass: this.config.password || '', ...queryArg };
458
- const response = await this.fetchText(pathArg, query, 'skyfi', true);
459
- return DaikinMapper.parseSkyFiResponse(response);
460
- }
461
-
462
- private async requestKeyValue(pathArg: string, queryArg: Record<string, string | number | boolean | undefined> | undefined, variantArg: TDaikinApiVariant, allowEmptyArg = false): Promise<IDaikinValueMap> {
463
- if (this.config.client?.getResource && !this.config.host && !this.config.url) {
464
- return this.config.client.getResource(pathArg, queryArg);
465
- }
466
- const text = await this.fetchText(pathArg, queryArg, variantArg, allowEmptyArg);
467
- if (!text.trim()) {
468
- return {};
469
- }
39
+ public async getSnapshot(signalArg?: AbortSignal): Promise<IDaikinSnapshot> {
470
40
  try {
471
- return DaikinMapper.parseKeyValueResponse(text);
472
- } catch (errorArg) {
473
- if (allowEmptyArg) {
474
- return {};
475
- }
476
- throw errorArg;
477
- }
41
+ const state = await this.#protocol.readState({ signal: this.#signal(signalArg) });
42
+ this.#healthy = true;
43
+ return DaikinMapper.fromState(this.#config, state);
44
+ } catch (errorArg) { this.#healthy = false; throw errorArg; }
478
45
  }
479
46
 
480
- private async requestJson<TValue>(pathArg: string, bodyArg: unknown, variantArg: TDaikinApiVariant): Promise<TValue> {
481
- const url = this.url(pathArg, undefined, variantArg);
482
- let response: Response;
47
+ public async setControl(controlArg: plugins.ecobridgeDeviceManager.IDaikinControl, signalArg?: AbortSignal): Promise<plugins.ecobridgeDeviceManager.IDaikinControlResult> {
483
48
  try {
484
- response = await globalThis.fetch(url, {
485
- method: 'POST',
486
- headers: this.headers(variantArg, { 'content-type': 'application/json', accept: 'application/json' }),
487
- body: JSON.stringify(bodyArg),
488
- signal: AbortSignal.timeout(this.config.timeoutMs || daikinDefaultTimeoutMs),
489
- });
49
+ const result = await this.#protocol.setControl(controlArg, { signal: this.#signal(signalArg) });
50
+ this.#healthy = true;
51
+ return result;
490
52
  } catch (errorArg) {
491
- throw new DaikinApiConnectionError(`Connection to ${url} failed: ${this.errorMessage(errorArg)}`);
53
+ if (!(errorArg instanceof plugins.ecobridgeDeviceManager.DaikinProtocolError) || !['unsupported', 'invalid-options', 'device-error', 'capacity'].includes(errorArg.code)) this.#healthy = false;
54
+ throw errorArg;
492
55
  }
493
- await this.assertOk(response, url, false);
494
- return await response.json() as TValue;
495
56
  }
496
57
 
497
- private async fetchText(pathArg: string, queryArg: Record<string, string | number | boolean | undefined> | undefined, variantArg: TDaikinApiVariant, allowEmptyArg: boolean): Promise<string> {
498
- const url = this.url(pathArg, queryArg, variantArg);
499
- let response: Response;
500
- try {
501
- response = await globalThis.fetch(url, {
502
- method: 'GET',
503
- headers: this.headers(variantArg),
504
- signal: AbortSignal.timeout(this.config.timeoutMs || daikinDefaultTimeoutMs),
58
+ public destroy(): Promise<void> {
59
+ if (!this.#destroy) {
60
+ this.#healthy = false;
61
+ this.#destroy = Promise.resolve().then(async () => {
62
+ this.#removeAbort();
63
+ this.#lifetime.abort(new Error('Daikin client is destroyed.'));
64
+ await this.#protocol.close();
505
65
  });
506
- } catch (errorArg) {
507
- throw new DaikinApiConnectionError(`Connection to ${url} failed: ${this.errorMessage(errorArg)}`);
508
- }
509
- if (response.status === 404 && allowEmptyArg) {
510
- await response.arrayBuffer().catch(() => undefined);
511
- return '';
512
- }
513
- await this.assertOk(response, url, allowEmptyArg);
514
- return await response.text();
515
- }
516
-
517
- private async assertOk(responseArg: Response, urlArg: string, allowEmptyArg: boolean): Promise<void> {
518
- if (responseArg.status === 403 || responseArg.status === 401) {
519
- throw new DaikinApiAuthorizationError('Daikin authentication failed. Check API key, UUID, or SkyFi password.');
520
- }
521
- if (!responseArg.ok) {
522
- const text = await responseArg.text().catch(() => '');
523
- if (allowEmptyArg && responseArg.status === 404) {
524
- return;
525
- }
526
- throw new DaikinApiConnectionError(`Daikin endpoint ${urlArg} failed with HTTP ${responseArg.status}${text ? `: ${text}` : ''}`);
527
- }
528
- }
529
-
530
- private url(pathArg: string, queryArg: Record<string, string | number | boolean | undefined> | undefined, variantArg: TDaikinApiVariant): string {
531
- if (/^https?:\/\//i.test(pathArg)) {
532
- return pathArg;
533
- }
534
- const base = this.baseUrl(variantArg);
535
- const url = new URL(pathArg.startsWith('/') ? pathArg : `/${pathArg}`, base.endsWith('/') ? base : `${base}/`);
536
- for (const [key, value] of Object.entries(queryArg || {})) {
537
- if (value !== undefined) {
538
- url.searchParams.set(key, String(value));
539
- }
540
- }
541
- return url.toString();
542
- }
543
-
544
- private baseUrl(variantArg: TDaikinApiVariant): string {
545
- const configured = this.config.url || this.config.host || 'localhost';
546
- if (/^https?:\/\//i.test(configured)) {
547
- const url = new URL(configured);
548
- return `${url.protocol}//${url.host}`;
549
- }
550
- const ssl = this.config.ssl ?? this.config.tls ?? variantArg === 'brp072c';
551
- const protocol = ssl ? 'https' : 'http';
552
- const defaultPort = variantArg === 'skyfi' ? daikinSkyFiPort : ssl ? daikinDefaultHttpsPort : daikinDefaultHttpPort;
553
- const port = this.config.port && this.config.port !== defaultPort ? `:${this.config.port}` : '';
554
- return `${protocol}://${this.hostForUrl(configured)}${port}`;
555
- }
556
-
557
- private headers(variantArg: TDaikinApiVariant, extraArg: Record<string, string> = {}): Record<string, string> {
558
- const headers = { ...extraArg };
559
- if (variantArg === 'brp072c' && this.config.uuid) {
560
- headers['x-daikin-uuid'] = this.config.uuid.replace(/-/g, '');
561
66
  }
562
- return headers;
563
- }
564
-
565
- private requestVariant(valueArg: IDaikinCommandRequest['protocol']): TDaikinApiVariant {
566
- if (valueArg && valueArg !== 'legacy' && valueArg !== 'auto') {
567
- return valueArg;
568
- }
569
- if (this.config.apiVariant && this.config.apiVariant !== 'auto') {
570
- return this.config.apiVariant;
571
- }
572
- if (this.config.password) {
573
- return 'skyfi';
574
- }
575
- if (this.config.apiKey) {
576
- return 'brp072c';
577
- }
578
- return 'brp069';
579
- }
580
-
581
- private findBrp084Value(dataArg: Record<string, unknown>, pathArg: string[]): string {
582
- const responses = Array.isArray(dataArg.responses) ? dataArg.responses as Array<Record<string, unknown>> : [];
583
- const from = pathArg[0];
584
- let nodes = responses.filter((responseArg) => responseArg.fr === from || responseArg.to === from).map((responseArg) => responseArg.pc as Record<string, unknown>).filter(Boolean);
585
- for (const key of pathArg.slice(1)) {
586
- let found: Record<string, unknown> | undefined;
587
- for (const node of nodes) {
588
- if (node.pn === key) {
589
- found = node;
590
- break;
591
- }
592
- }
593
- if (!found) {
594
- throw new DaikinApiConnectionError(`Daikin BRP084 response missing key ${key}.`);
595
- }
596
- if (pathArg[pathArg.length - 1] === key) {
597
- return String(found.pv ?? '');
598
- }
599
- nodes = Array.isArray(found.pch) ? found.pch as Array<Record<string, unknown>> : [];
600
- }
601
- return '';
602
- }
603
-
604
- private brp084WeeklyData(dataArg: Record<string, unknown>): string | undefined {
605
- try {
606
- const value = this.findBrp084Value(dataArg, brp084Paths.weeklyData);
607
- return Array.isArray(value) ? value.join('/') : String(value);
608
- } catch {
609
- return undefined;
610
- }
611
- }
612
-
613
- private hexTemp(valueArg: string, divisorArg = 2): string | undefined {
614
- if (!valueArg) {
615
- return undefined;
616
- }
617
- const parsed = Number.parseInt(valueArg.slice(0, 2), 16);
618
- return Number.isFinite(parsed) ? String(parsed / divisorArg) : undefined;
619
- }
620
-
621
- private hexInt(valueArg: string): string | undefined {
622
- if (!valueArg) {
623
- return undefined;
624
- }
625
- const parsed = Number.parseInt(valueArg, 16);
626
- return Number.isFinite(parsed) ? String(parsed) : undefined;
627
- }
628
-
629
- private swingAxis(valueArg: string | undefined, axisArg: 'ud' | 'lr'): string {
630
- const value = valueArg || '0';
631
- if (axisArg === 'ud') {
632
- return value === '1' || value === '3' ? 'S' : '0';
633
- }
634
- return value === '2' || value === '3' ? 'S' : '0';
635
- }
636
-
637
- private listValue(valueArg?: string): string[] {
638
- if (!valueArg) {
639
- return [];
640
- }
641
- let decoded = valueArg;
642
- try {
643
- decoded = decodeURIComponent(valueArg.replace(/\+/g, '%20'));
644
- } catch {
645
- decoded = valueArg;
646
- }
647
- return decoded.includes(';') ? decoded.split(';') : decoded.split('');
648
- }
649
-
650
- private cleanQuery(queryArg: Record<string, string | number | boolean | undefined>): Record<string, string | number | boolean | undefined> {
651
- const cleaned: Record<string, string | number | boolean | undefined> = {};
652
- for (const [key, value] of Object.entries(queryArg)) {
653
- if (value !== undefined) {
654
- cleaned[key] = value;
655
- }
656
- }
657
- return cleaned;
658
- }
659
-
660
- private offlineSnapshot(errorArg: string): IDaikinSnapshot {
661
- return DaikinMapper.toSnapshot({ config: this.config, online: false, source: 'runtime', error: errorArg });
662
- }
663
-
664
- private hasManualData(): boolean {
665
- return Boolean(this.config.snapshot || this.config.rawData || this.config.values);
666
- }
667
-
668
- private isSnapshot(valueArg: unknown): valueArg is IDaikinSnapshot {
669
- return Boolean(valueArg && typeof valueArg === 'object' && 'device' in valueArg && 'climate' in valueArg);
670
- }
671
-
672
- private hostForUrl(hostArg: string): string {
673
- return hostArg.includes(':') && !hostArg.startsWith('[') ? `[${hostArg}]` : hostArg;
674
- }
675
-
676
- private errorMessage(errorArg: unknown): string {
677
- return errorArg instanceof Error ? errorArg.message : String(errorArg);
67
+ return this.#destroy;
678
68
  }
679
69
 
680
- private cloneSnapshot(snapshotArg: IDaikinSnapshot): IDaikinSnapshot {
681
- return JSON.parse(JSON.stringify(snapshotArg)) as IDaikinSnapshot;
70
+ #signal(signalArg?: AbortSignal): AbortSignal {
71
+ if (this.#destroy) throw new plugins.ecobridgeDeviceManager.DaikinProtocolError('Daikin client is destroyed.', 'closed');
72
+ return signalArg ? AbortSignal.any([signalArg, this.#lifetime.signal]) : this.#lifetime.signal;
682
73
  }
683
74
  }