@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.
- package/changelog.md +84 -0
- package/dist_ts/00_commitinfo_data.js +1 -1
- package/dist_ts/core/classes.configstore.d.ts +2 -0
- package/dist_ts/core/classes.configstore.js +84 -27
- package/dist_ts/core/classes.nativehomeadmission.d.ts +19 -0
- package/dist_ts/core/classes.nativehomeadmission.js +84 -0
- package/dist_ts/core/classes.nativeintegrationowner.d.ts +81 -0
- package/dist_ts/core/classes.nativeintegrationowner.js +273 -0
- package/dist_ts/core/classes.runtimemanager.d.ts +2 -0
- package/dist_ts/core/classes.runtimemanager.js +11 -3
- package/dist_ts/core/index.d.ts +2 -0
- package/dist_ts/core/index.js +3 -1
- package/dist_ts/core/types.d.ts +16 -0
- package/dist_ts/integrations/braviatv/braviatv.classes.client.d.ts +23 -72
- package/dist_ts/integrations/braviatv/braviatv.classes.client.js +265 -625
- package/dist_ts/integrations/braviatv/braviatv.classes.configflow.d.ts +7 -7
- package/dist_ts/integrations/braviatv/braviatv.classes.configflow.js +51 -68
- package/dist_ts/integrations/braviatv/braviatv.classes.integration.d.ts +8 -11
- package/dist_ts/integrations/braviatv/braviatv.classes.integration.js +186 -135
- package/dist_ts/integrations/braviatv/braviatv.discovery.js +12 -11
- package/dist_ts/integrations/braviatv/braviatv.mapper.d.ts +6 -14
- package/dist_ts/integrations/braviatv/braviatv.mapper.js +37 -131
- package/dist_ts/integrations/braviatv/braviatv.types.d.ts +55 -133
- package/dist_ts/integrations/braviatv/braviatv.validation.d.ts +7 -0
- package/dist_ts/integrations/braviatv/braviatv.validation.js +72 -0
- package/dist_ts/integrations/broadlink/broadlink.actions.d.ts +2 -0
- package/dist_ts/integrations/broadlink/broadlink.actions.js +36 -0
- package/dist_ts/integrations/broadlink/broadlink.classes.client.d.ts +21 -19
- package/dist_ts/integrations/broadlink/broadlink.classes.client.js +185 -124
- package/dist_ts/integrations/broadlink/broadlink.classes.configflow.d.ts +5 -4
- package/dist_ts/integrations/broadlink/broadlink.classes.configflow.js +64 -83
- package/dist_ts/integrations/broadlink/broadlink.classes.integration.d.ts +16 -19
- package/dist_ts/integrations/broadlink/broadlink.classes.integration.js +114 -59
- package/dist_ts/integrations/broadlink/broadlink.mapper.d.ts +3 -2
- package/dist_ts/integrations/broadlink/broadlink.mapper.js +2 -1
- package/dist_ts/integrations/broadlink/broadlink.selected.mapper.d.ts +10 -0
- package/dist_ts/integrations/broadlink/broadlink.selected.mapper.js +41 -0
- package/dist_ts/integrations/broadlink/broadlink.types.d.ts +43 -7
- package/dist_ts/integrations/broadlink/broadlink.validation.d.ts +7 -0
- package/dist_ts/integrations/broadlink/broadlink.validation.js +63 -0
- package/dist_ts/integrations/daikin/daikin.classes.client.d.ts +10 -52
- package/dist_ts/integrations/daikin/daikin.classes.client.js +55 -614
- package/dist_ts/integrations/daikin/daikin.classes.configflow.d.ts +8 -12
- package/dist_ts/integrations/daikin/daikin.classes.configflow.js +77 -138
- package/dist_ts/integrations/daikin/daikin.classes.integration.d.ts +7 -24
- package/dist_ts/integrations/daikin/daikin.classes.integration.js +175 -67
- package/dist_ts/integrations/daikin/daikin.discovery.d.ts +11 -24
- package/dist_ts/integrations/daikin/daikin.discovery.js +98 -305
- package/dist_ts/integrations/daikin/daikin.mapper.d.ts +6 -7
- package/dist_ts/integrations/daikin/daikin.mapper.js +95 -155
- package/dist_ts/integrations/daikin/daikin.types.d.ts +24 -44
- package/dist_ts/integrations/daikin/daikin.types.js +1 -1
- package/dist_ts/integrations/daikin/daikin.validation.d.ts +5 -0
- package/dist_ts/integrations/daikin/daikin.validation.js +53 -0
- package/dist_ts/integrations/deconz/deconz.classes.client.d.ts +37 -29
- package/dist_ts/integrations/deconz/deconz.classes.client.js +521 -294
- package/dist_ts/integrations/deconz/deconz.classes.configflow.d.ts +6 -1
- package/dist_ts/integrations/deconz/deconz.classes.configflow.js +63 -33
- package/dist_ts/integrations/deconz/deconz.classes.integration.d.ts +4 -3
- package/dist_ts/integrations/deconz/deconz.classes.integration.js +85 -40
- package/dist_ts/integrations/deconz/deconz.mapper.d.ts +1 -0
- package/dist_ts/integrations/deconz/deconz.mapper.js +24 -6
- package/dist_ts/integrations/deconz/deconz.types.d.ts +43 -6
- package/dist_ts/integrations/deconz/deconz.validation.d.ts +7 -1
- package/dist_ts/integrations/deconz/deconz.validation.js +215 -4
- package/dist_ts/integrations/denonavr/denonavr.classes.client.d.ts +31 -40
- package/dist_ts/integrations/denonavr/denonavr.classes.client.js +149 -404
- package/dist_ts/integrations/denonavr/denonavr.classes.configflow.d.ts +7 -2
- package/dist_ts/integrations/denonavr/denonavr.classes.configflow.js +44 -36
- package/dist_ts/integrations/denonavr/denonavr.classes.integration.d.ts +6 -11
- package/dist_ts/integrations/denonavr/denonavr.classes.integration.js +192 -113
- package/dist_ts/integrations/denonavr/denonavr.discovery.d.ts +10 -18
- package/dist_ts/integrations/denonavr/denonavr.discovery.js +71 -193
- package/dist_ts/integrations/denonavr/denonavr.mapper.d.ts +5 -13
- package/dist_ts/integrations/denonavr/denonavr.mapper.js +35 -159
- package/dist_ts/integrations/denonavr/denonavr.types.d.ts +55 -90
- package/dist_ts/integrations/denonavr/denonavr.validation.d.ts +10 -0
- package/dist_ts/integrations/denonavr/denonavr.validation.js +86 -0
- package/dist_ts/integrations/esphome/esphome.classes.client.d.ts +19 -7
- package/dist_ts/integrations/esphome/esphome.classes.client.js +183 -89
- package/dist_ts/integrations/esphome/esphome.classes.configflow.d.ts +5 -2
- package/dist_ts/integrations/esphome/esphome.classes.configflow.js +43 -33
- package/dist_ts/integrations/esphome/esphome.classes.integration.d.ts +8 -6
- package/dist_ts/integrations/esphome/esphome.classes.integration.js +71 -43
- package/dist_ts/integrations/esphome/esphome.discovery.js +4 -12
- package/dist_ts/integrations/esphome/esphome.mapper.d.ts +2 -2
- package/dist_ts/integrations/esphome/esphome.mapper.js +6 -4
- package/dist_ts/integrations/esphome/esphome.types.d.ts +31 -6
- package/dist_ts/integrations/esphome/esphome.types.js +1 -1
- package/dist_ts/integrations/esphome/esphome.validation.d.ts +7 -0
- package/dist_ts/integrations/esphome/esphome.validation.js +66 -0
- package/dist_ts/integrations/homeassistant/homeassistant.classes.client.d.ts +32 -4
- package/dist_ts/integrations/homeassistant/homeassistant.classes.client.js +345 -116
- package/dist_ts/integrations/homeassistant/homeassistant.classes.integration.d.ts +8 -5
- package/dist_ts/integrations/homeassistant/homeassistant.classes.integration.js +34 -8
- package/dist_ts/integrations/homeassistant/homeassistant.classes.runtime.d.ts +7 -4
- package/dist_ts/integrations/homeassistant/homeassistant.classes.runtime.js +44 -56
- package/dist_ts/integrations/homeassistant/homeassistant.types.d.ts +12 -1
- package/dist_ts/integrations/hue/hue.classes.client.d.ts +6 -1
- package/dist_ts/integrations/hue/hue.classes.client.js +120 -45
- package/dist_ts/integrations/hue/hue.classes.configflow.js +16 -7
- package/dist_ts/integrations/hue/hue.classes.integration.d.ts +2 -0
- package/dist_ts/integrations/hue/hue.classes.integration.js +103 -30
- package/dist_ts/integrations/hue/hue.validation.d.ts +1 -0
- package/dist_ts/integrations/hue/hue.validation.js +14 -4
- package/dist_ts/integrations/kodi/kodi.classes.client.d.ts +11 -45
- package/dist_ts/integrations/kodi/kodi.classes.client.js +84 -310
- package/dist_ts/integrations/kodi/kodi.classes.configflow.d.ts +9 -8
- package/dist_ts/integrations/kodi/kodi.classes.configflow.js +53 -48
- package/dist_ts/integrations/kodi/kodi.classes.integration.d.ts +11 -11
- package/dist_ts/integrations/kodi/kodi.classes.integration.js +114 -171
- package/dist_ts/integrations/kodi/kodi.discovery.js +53 -29
- package/dist_ts/integrations/kodi/kodi.mapper.d.ts +7 -2
- package/dist_ts/integrations/kodi/kodi.mapper.js +48 -10
- package/dist_ts/integrations/kodi/kodi.types.d.ts +32 -28
- package/dist_ts/integrations/kodi/kodi.validation.d.ts +9 -0
- package/dist_ts/integrations/kodi/kodi.validation.js +62 -0
- package/dist_ts/integrations/modbus/modbus.classes.client.d.ts +15 -61
- package/dist_ts/integrations/modbus/modbus.classes.client.js +117 -776
- package/dist_ts/integrations/modbus/modbus.classes.configflow.d.ts +9 -5
- package/dist_ts/integrations/modbus/modbus.classes.configflow.js +70 -38
- package/dist_ts/integrations/modbus/modbus.classes.integration.d.ts +6 -17
- package/dist_ts/integrations/modbus/modbus.classes.integration.js +133 -57
- package/dist_ts/integrations/modbus/modbus.discovery.d.ts +5 -8
- package/dist_ts/integrations/modbus/modbus.discovery.js +38 -93
- package/dist_ts/integrations/modbus/modbus.mapper.d.ts +8 -32
- package/dist_ts/integrations/modbus/modbus.mapper.js +71 -431
- package/dist_ts/integrations/modbus/modbus.types.d.ts +82 -332
- package/dist_ts/integrations/modbus/modbus.validation.d.ts +10 -0
- package/dist_ts/integrations/modbus/modbus.validation.js +128 -0
- package/dist_ts/integrations/mqtt/mqtt.classes.client.d.ts +15 -2
- package/dist_ts/integrations/mqtt/mqtt.classes.client.js +173 -23
- package/dist_ts/integrations/mqtt/mqtt.classes.configflow.d.ts +5 -1
- package/dist_ts/integrations/mqtt/mqtt.classes.configflow.js +53 -33
- package/dist_ts/integrations/mqtt/mqtt.classes.integration.d.ts +4 -1
- package/dist_ts/integrations/mqtt/mqtt.classes.integration.js +127 -56
- package/dist_ts/integrations/mqtt/mqtt.classes.session.d.ts +13 -0
- package/dist_ts/integrations/mqtt/mqtt.classes.session.js +130 -0
- package/dist_ts/integrations/mqtt/mqtt.mapper.d.ts +3 -0
- package/dist_ts/integrations/mqtt/mqtt.mapper.js +44 -1
- package/dist_ts/integrations/mqtt/mqtt.types.d.ts +46 -0
- package/dist_ts/integrations/mqtt/mqtt.validation.d.ts +7 -0
- package/dist_ts/integrations/mqtt/mqtt.validation.js +180 -0
- package/dist_ts/integrations/nanoleaf/nanoleaf.classes.client.d.ts +12 -34
- package/dist_ts/integrations/nanoleaf/nanoleaf.classes.client.js +143 -231
- package/dist_ts/integrations/nanoleaf/nanoleaf.classes.configflow.d.ts +6 -1
- package/dist_ts/integrations/nanoleaf/nanoleaf.classes.configflow.js +105 -18
- package/dist_ts/integrations/nanoleaf/nanoleaf.classes.integration.d.ts +8 -8
- package/dist_ts/integrations/nanoleaf/nanoleaf.classes.integration.js +141 -155
- package/dist_ts/integrations/nanoleaf/nanoleaf.credentials.d.ts +9 -0
- package/dist_ts/integrations/nanoleaf/nanoleaf.credentials.js +35 -0
- package/dist_ts/integrations/nanoleaf/nanoleaf.mapper.d.ts +6 -18
- package/dist_ts/integrations/nanoleaf/nanoleaf.mapper.js +45 -220
- package/dist_ts/integrations/nanoleaf/nanoleaf.types.d.ts +33 -147
- package/dist_ts/integrations/nanoleaf/nanoleaf.validation.d.ts +6 -0
- package/dist_ts/integrations/nanoleaf/nanoleaf.validation.js +82 -0
- package/dist_ts/integrations/onkyo/onkyo.classes.client.d.ts +15 -20
- package/dist_ts/integrations/onkyo/onkyo.classes.client.js +161 -404
- package/dist_ts/integrations/onkyo/onkyo.classes.configflow.d.ts +9 -4
- package/dist_ts/integrations/onkyo/onkyo.classes.configflow.js +51 -6
- package/dist_ts/integrations/onkyo/onkyo.classes.integration.d.ts +22 -6
- package/dist_ts/integrations/onkyo/onkyo.classes.integration.js +144 -11
- package/dist_ts/integrations/onkyo/onkyo.discovery.d.ts +6 -1
- package/dist_ts/integrations/onkyo/onkyo.discovery.js +40 -4
- package/dist_ts/integrations/onkyo/onkyo.mapper.d.ts +7 -8
- package/dist_ts/integrations/onkyo/onkyo.mapper.js +45 -12
- package/dist_ts/integrations/onkyo/onkyo.types.d.ts +58 -8
- package/dist_ts/integrations/onkyo/onkyo.types.js +13 -102
- package/dist_ts/integrations/onkyo/onkyo.validation.d.ts +16 -0
- package/dist_ts/integrations/onkyo/onkyo.validation.js +77 -0
- package/dist_ts/integrations/panasonic_viera/panasonic_viera.classes.client.d.ts +25 -25
- package/dist_ts/integrations/panasonic_viera/panasonic_viera.classes.client.js +116 -360
- package/dist_ts/integrations/panasonic_viera/panasonic_viera.classes.configflow.d.ts +11 -3
- package/dist_ts/integrations/panasonic_viera/panasonic_viera.classes.configflow.js +76 -6
- package/dist_ts/integrations/panasonic_viera/panasonic_viera.classes.integration.d.ts +26 -4
- package/dist_ts/integrations/panasonic_viera/panasonic_viera.classes.integration.js +142 -9
- package/dist_ts/integrations/panasonic_viera/panasonic_viera.discovery.d.ts +2 -1
- package/dist_ts/integrations/panasonic_viera/panasonic_viera.discovery.js +31 -4
- package/dist_ts/integrations/panasonic_viera/panasonic_viera.mapper.d.ts +9 -9
- package/dist_ts/integrations/panasonic_viera/panasonic_viera.mapper.js +31 -149
- package/dist_ts/integrations/panasonic_viera/panasonic_viera.types.d.ts +51 -11
- package/dist_ts/integrations/panasonic_viera/panasonic_viera.types.js +22 -87
- package/dist_ts/integrations/panasonic_viera/panasonic_viera.validation.d.ts +6 -0
- package/dist_ts/integrations/panasonic_viera/panasonic_viera.validation.js +56 -0
- package/dist_ts/integrations/pioneer/pioneer.classes.client.d.ts +31 -16
- package/dist_ts/integrations/pioneer/pioneer.classes.client.js +167 -409
- package/dist_ts/integrations/pioneer/pioneer.classes.configflow.d.ts +10 -3
- package/dist_ts/integrations/pioneer/pioneer.classes.configflow.js +66 -6
- package/dist_ts/integrations/pioneer/pioneer.classes.integration.d.ts +13 -5
- package/dist_ts/integrations/pioneer/pioneer.classes.integration.js +239 -11
- package/dist_ts/integrations/pioneer/pioneer.discovery.d.ts +14 -1
- package/dist_ts/integrations/pioneer/pioneer.discovery.js +51 -4
- package/dist_ts/integrations/pioneer/pioneer.mapper.d.ts +14 -8
- package/dist_ts/integrations/pioneer/pioneer.mapper.js +54 -12
- package/dist_ts/integrations/pioneer/pioneer.types.d.ts +79 -12
- package/dist_ts/integrations/pioneer/pioneer.types.js +12 -76
- package/dist_ts/integrations/pioneer/pioneer.validation.d.ts +10 -0
- package/dist_ts/integrations/pioneer/pioneer.validation.js +85 -0
- package/dist_ts/integrations/samsungtv/samsungtv.classes.client.d.ts +4 -2
- package/dist_ts/integrations/samsungtv/samsungtv.classes.client.js +41 -16
- package/dist_ts/integrations/samsungtv/samsungtv.classes.configflow.d.ts +5 -0
- package/dist_ts/integrations/samsungtv/samsungtv.classes.configflow.js +20 -7
- package/dist_ts/integrations/samsungtv/samsungtv.classes.integration.d.ts +1 -0
- package/dist_ts/integrations/samsungtv/samsungtv.classes.integration.js +53 -50
- package/dist_ts/integrations/samsungtv/samsungtv.types.d.ts +4 -1
- package/dist_ts/integrations/shelly/shelly.classes.client.d.ts +26 -30
- package/dist_ts/integrations/shelly/shelly.classes.client.js +504 -276
- package/dist_ts/integrations/shelly/shelly.classes.configflow.d.ts +8 -3
- package/dist_ts/integrations/shelly/shelly.classes.configflow.js +43 -38
- package/dist_ts/integrations/shelly/shelly.classes.integration.d.ts +6 -6
- package/dist_ts/integrations/shelly/shelly.classes.integration.js +103 -101
- package/dist_ts/integrations/shelly/shelly.classes.subscription.d.ts +4 -0
- package/dist_ts/integrations/shelly/shelly.classes.subscription.js +24 -2
- package/dist_ts/integrations/shelly/shelly.mapper.d.ts +1 -2
- package/dist_ts/integrations/shelly/shelly.mapper.js +21 -20
- package/dist_ts/integrations/shelly/shelly.rpc.js +4 -1
- package/dist_ts/integrations/shelly/shelly.types.d.ts +42 -2
- package/dist_ts/integrations/shelly/shelly.types.js +11 -2
- package/dist_ts/integrations/shelly/shelly.validation.d.ts +7 -0
- package/dist_ts/integrations/shelly/shelly.validation.js +79 -0
- package/dist_ts/integrations/sonos/sonos.classes.client.d.ts +79 -22
- package/dist_ts/integrations/sonos/sonos.classes.client.js +427 -139
- package/dist_ts/integrations/sonos/sonos.classes.configflow.d.ts +9 -2
- package/dist_ts/integrations/sonos/sonos.classes.configflow.js +26 -28
- package/dist_ts/integrations/sonos/sonos.classes.integration.d.ts +7 -6
- package/dist_ts/integrations/sonos/sonos.classes.integration.js +289 -224
- package/dist_ts/integrations/sonos/sonos.config.d.ts +6 -1
- package/dist_ts/integrations/sonos/sonos.config.js +23 -2
- package/dist_ts/integrations/sonos/sonos.mapper.d.ts +1 -1
- package/dist_ts/integrations/sonos/sonos.mapper.js +14 -9
- package/dist_ts/integrations/sonos/sonos.matchers.js +3 -3
- package/dist_ts/integrations/sonos/sonos.types.d.ts +26 -1
- package/dist_ts/integrations/soundtouch/soundtouch.classes.client.d.ts +13 -36
- package/dist_ts/integrations/soundtouch/soundtouch.classes.client.js +179 -502
- package/dist_ts/integrations/soundtouch/soundtouch.classes.configflow.d.ts +6 -1
- package/dist_ts/integrations/soundtouch/soundtouch.classes.configflow.js +50 -40
- package/dist_ts/integrations/soundtouch/soundtouch.classes.integration.d.ts +14 -15
- package/dist_ts/integrations/soundtouch/soundtouch.classes.integration.js +108 -128
- package/dist_ts/integrations/soundtouch/soundtouch.discovery.d.ts +2 -20
- package/dist_ts/integrations/soundtouch/soundtouch.discovery.js +23 -113
- package/dist_ts/integrations/soundtouch/soundtouch.mapper.d.ts +3 -12
- package/dist_ts/integrations/soundtouch/soundtouch.mapper.js +35 -189
- package/dist_ts/integrations/soundtouch/soundtouch.types.d.ts +57 -142
- package/dist_ts/integrations/soundtouch/soundtouch.types.js +18 -3
- package/dist_ts/integrations/soundtouch/soundtouch.validation.d.ts +22 -0
- package/dist_ts/integrations/soundtouch/soundtouch.validation.js +65 -0
- package/dist_ts/integrations/tasmota/tasmota.classes.integration.d.ts +5 -0
- package/dist_ts/integrations/tasmota/tasmota.classes.integration.js +23 -7
- package/dist_ts/integrations/tasmota/tasmota.classes.runtime.d.ts +19 -5
- package/dist_ts/integrations/tasmota/tasmota.classes.runtime.js +115 -41
- package/dist_ts/integrations/tasmota/tasmota.config.js +23 -1
- package/dist_ts/integrations/tasmota/tasmota.credentials.d.ts +11 -0
- package/dist_ts/integrations/tasmota/tasmota.credentials.js +97 -0
- package/dist_ts/integrations/tasmota/tasmota.discovery.d.ts +7 -1
- package/dist_ts/integrations/tasmota/tasmota.discovery.js +108 -30
- package/dist_ts/integrations/tasmota/tasmota.mapper.d.ts +2 -2
- package/dist_ts/integrations/tasmota/tasmota.mapper.js +7 -7
- package/dist_ts/integrations/tasmota/tasmota.types.d.ts +41 -2
- package/dist_ts/integrations/tuya/tuya.classes.integration.d.ts +4 -1
- package/dist_ts/integrations/tuya/tuya.classes.integration.js +79 -110
- package/dist_ts/integrations/tuya/tuya.classes.runtime.d.ts +5 -2
- package/dist_ts/integrations/tuya/tuya.classes.runtime.js +73 -26
- package/dist_ts/integrations/tuya/tuya.mapper.js +2 -2
- package/dist_ts/integrations/tuya/tuya.types.d.ts +3 -0
- package/dist_ts/integrations/tuya/tuya.validation.d.ts +2 -2
- package/dist_ts/integrations/tuya/tuya.validation.js +6 -11
- package/dist_ts/integrations/webostv/webostv.classes.client.d.ts +6 -5
- package/dist_ts/integrations/webostv/webostv.classes.client.js +147 -76
- package/dist_ts/integrations/webostv/webostv.classes.configflow.d.ts +7 -2
- package/dist_ts/integrations/webostv/webostv.classes.configflow.js +36 -20
- package/dist_ts/integrations/webostv/webostv.classes.integration.d.ts +4 -4
- package/dist_ts/integrations/webostv/webostv.classes.integration.js +46 -54
- package/dist_ts/integrations/webostv/webostv.mapper.js +5 -5
- package/dist_ts/integrations/webostv/webostv.types.d.ts +16 -3
- package/dist_ts/integrations/webostv/webostv.types.js +1 -1
- package/dist_ts/integrations/webostv/webostv.validation.d.ts +3 -1
- package/dist_ts/integrations/webostv/webostv.validation.js +23 -1
- package/dist_ts/integrations/wiz/index.d.ts +1 -0
- package/dist_ts/integrations/wiz/index.js +2 -1
- package/dist_ts/integrations/wiz/wiz.classes.client.d.ts +14 -28
- package/dist_ts/integrations/wiz/wiz.classes.client.js +93 -229
- package/dist_ts/integrations/wiz/wiz.classes.configflow.d.ts +6 -4
- package/dist_ts/integrations/wiz/wiz.classes.configflow.js +38 -67
- package/dist_ts/integrations/wiz/wiz.classes.integration.d.ts +10 -21
- package/dist_ts/integrations/wiz/wiz.classes.integration.js +204 -44
- package/dist_ts/integrations/wiz/wiz.discovery.d.ts +10 -31
- package/dist_ts/integrations/wiz/wiz.discovery.js +48 -249
- package/dist_ts/integrations/wiz/wiz.mapper.d.ts +7 -51
- package/dist_ts/integrations/wiz/wiz.mapper.js +82 -668
- package/dist_ts/integrations/wiz/wiz.types.d.ts +34 -208
- package/dist_ts/integrations/wiz/wiz.validation.d.ts +8 -0
- package/dist_ts/integrations/wiz/wiz.validation.js +72 -0
- package/dist_ts/integrations/yamaha/index.d.ts +1 -0
- package/dist_ts/integrations/yamaha/index.js +2 -1
- package/dist_ts/integrations/yamaha/yamaha.classes.client.d.ts +30 -4
- package/dist_ts/integrations/yamaha/yamaha.classes.client.js +162 -6
- package/dist_ts/integrations/yamaha/yamaha.classes.configflow.d.ts +10 -3
- package/dist_ts/integrations/yamaha/yamaha.classes.configflow.js +106 -6
- package/dist_ts/integrations/yamaha/yamaha.classes.integration.d.ts +22 -4
- package/dist_ts/integrations/yamaha/yamaha.classes.integration.js +243 -8
- package/dist_ts/integrations/yamaha/yamaha.discovery.d.ts +13 -1
- package/dist_ts/integrations/yamaha/yamaha.discovery.js +57 -4
- package/dist_ts/integrations/yamaha/yamaha.mapper.d.ts +16 -8
- package/dist_ts/integrations/yamaha/yamaha.mapper.js +58 -12
- package/dist_ts/integrations/yamaha/yamaha.types.d.ts +73 -6
- package/dist_ts/integrations/yamaha/yamaha.types.js +8 -94
- package/dist_ts/integrations/yamaha/yamaha.validation.d.ts +12 -0
- package/dist_ts/integrations/yamaha/yamaha.validation.js +89 -0
- package/dist_ts/integrations/zigbee2mqtt/zigbee2mqtt.classes.configflow.d.ts +6 -1
- package/dist_ts/integrations/zigbee2mqtt/zigbee2mqtt.classes.configflow.js +18 -8
- package/dist_ts/integrations/zigbee2mqtt/zigbee2mqtt.classes.integration.d.ts +4 -1
- package/dist_ts/integrations/zigbee2mqtt/zigbee2mqtt.classes.integration.js +54 -6
- package/dist_ts/integrations/zigbee2mqtt/zigbee2mqtt.classes.runtime.d.ts +12 -6
- package/dist_ts/integrations/zigbee2mqtt/zigbee2mqtt.classes.runtime.js +73 -59
- package/dist_ts/integrations/zigbee2mqtt/zigbee2mqtt.mapper.d.ts +3 -2
- package/dist_ts/integrations/zigbee2mqtt/zigbee2mqtt.mapper.js +17 -12
- package/dist_ts/integrations/zigbee2mqtt/zigbee2mqtt.types.d.ts +31 -2
- package/dist_ts/integrations/zigbee2mqtt/zigbee2mqtt.validation.d.ts +9 -1
- package/dist_ts/integrations/zigbee2mqtt/zigbee2mqtt.validation.js +57 -7
- package/dist_ts/integrations/zwave_js/zwave_js.classes.client.d.ts +10 -4
- package/dist_ts/integrations/zwave_js/zwave_js.classes.client.js +167 -31
- package/dist_ts/integrations/zwave_js/zwave_js.classes.configflow.d.ts +6 -1
- package/dist_ts/integrations/zwave_js/zwave_js.classes.configflow.js +57 -35
- package/dist_ts/integrations/zwave_js/zwave_js.classes.integration.d.ts +3 -1
- package/dist_ts/integrations/zwave_js/zwave_js.classes.integration.js +59 -37
- package/dist_ts/integrations/zwave_js/zwave_js.discovery.js +3 -3
- package/dist_ts/integrations/zwave_js/zwave_js.mapper.js +41 -24
- package/dist_ts/integrations/zwave_js/zwave_js.types.d.ts +25 -3
- package/dist_ts/integrations/zwave_js/zwave_js.validation.d.ts +6 -2
- package/dist_ts/integrations/zwave_js/zwave_js.validation.js +52 -17
- package/dist_ts/plugins.d.ts +2 -1
- package/dist_ts/plugins.js +3 -2
- package/package.json +9 -9
- package/readme.md +539 -8
- package/ts/00_commitinfo_data.ts +1 -1
- package/ts/core/classes.configstore.ts +84 -27
- package/ts/core/classes.nativehomeadmission.ts +96 -0
- package/ts/core/classes.nativeintegrationowner.ts +302 -0
- package/ts/core/classes.runtimemanager.ts +11 -2
- package/ts/core/index.ts +2 -0
- package/ts/core/types.ts +18 -0
- package/ts/integrations/braviatv/braviatv.classes.client.ts +245 -709
- package/ts/integrations/braviatv/braviatv.classes.configflow.ts +47 -76
- package/ts/integrations/braviatv/braviatv.classes.integration.ts +167 -147
- package/ts/integrations/braviatv/braviatv.discovery.ts +11 -10
- package/ts/integrations/braviatv/braviatv.mapper.ts +39 -142
- package/ts/integrations/braviatv/braviatv.types.ts +53 -173
- package/ts/integrations/braviatv/braviatv.validation.ts +68 -0
- package/ts/integrations/broadlink/broadlink.actions.ts +31 -0
- package/ts/integrations/broadlink/broadlink.classes.client.ts +170 -144
- package/ts/integrations/broadlink/broadlink.classes.configflow.ts +59 -89
- package/ts/integrations/broadlink/broadlink.classes.integration.ts +110 -64
- package/ts/integrations/broadlink/broadlink.mapper.ts +5 -4
- package/ts/integrations/broadlink/broadlink.selected.mapper.ts +46 -0
- package/ts/integrations/broadlink/broadlink.types.ts +48 -8
- package/ts/integrations/broadlink/broadlink.validation.ts +66 -0
- package/ts/integrations/daikin/daikin.classes.client.ts +52 -661
- package/ts/integrations/daikin/daikin.classes.configflow.ts +72 -152
- package/ts/integrations/daikin/daikin.classes.integration.ts +166 -71
- package/ts/integrations/daikin/daikin.discovery.ts +94 -346
- package/ts/integrations/daikin/daikin.mapper.ts +83 -166
- package/ts/integrations/daikin/daikin.types.ts +27 -48
- package/ts/integrations/daikin/daikin.validation.ts +51 -0
- package/ts/integrations/daikin/readme.md +83 -0
- package/ts/integrations/deconz/deconz.classes.client.ts +348 -252
- package/ts/integrations/deconz/deconz.classes.configflow.ts +57 -29
- package/ts/integrations/deconz/deconz.classes.integration.ts +69 -37
- package/ts/integrations/deconz/deconz.mapper.ts +22 -5
- package/ts/integrations/deconz/deconz.types.ts +49 -6
- package/ts/integrations/deconz/deconz.validation.ts +177 -4
- package/ts/integrations/deconz/readme.md +15 -1
- package/ts/integrations/denonavr/denonavr.classes.client.ts +132 -421
- package/ts/integrations/denonavr/denonavr.classes.configflow.ts +44 -37
- package/ts/integrations/denonavr/denonavr.classes.integration.ts +171 -117
- package/ts/integrations/denonavr/denonavr.discovery.ts +67 -220
- package/ts/integrations/denonavr/denonavr.mapper.ts +36 -182
- package/ts/integrations/denonavr/denonavr.types.ts +48 -111
- package/ts/integrations/denonavr/denonavr.validation.ts +87 -0
- package/ts/integrations/esphome/esphome.classes.client.ts +179 -94
- package/ts/integrations/esphome/esphome.classes.configflow.ts +40 -33
- package/ts/integrations/esphome/esphome.classes.integration.ts +63 -36
- package/ts/integrations/esphome/esphome.discovery.ts +3 -12
- package/ts/integrations/esphome/esphome.mapper.ts +9 -7
- package/ts/integrations/esphome/esphome.types.ts +35 -6
- package/ts/integrations/esphome/esphome.validation.ts +66 -0
- package/ts/integrations/esphome/readme.md +20 -6
- package/ts/integrations/homeassistant/homeassistant.classes.client.ts +353 -125
- package/ts/integrations/homeassistant/homeassistant.classes.integration.ts +35 -18
- package/ts/integrations/homeassistant/homeassistant.classes.runtime.ts +50 -63
- package/ts/integrations/homeassistant/homeassistant.types.ts +17 -1
- package/ts/integrations/homeassistant/readme.md +22 -6
- package/ts/integrations/hue/hue.classes.client.ts +110 -41
- package/ts/integrations/hue/hue.classes.configflow.ts +12 -6
- package/ts/integrations/hue/hue.classes.integration.ts +92 -26
- package/ts/integrations/hue/hue.validation.ts +13 -3
- package/ts/integrations/hue/readme.md +3 -3
- package/ts/integrations/kodi/kodi.classes.client.ts +72 -352
- package/ts/integrations/kodi/kodi.classes.configflow.ts +52 -55
- package/ts/integrations/kodi/kodi.classes.integration.ts +97 -178
- package/ts/integrations/kodi/kodi.discovery.ts +49 -28
- package/ts/integrations/kodi/kodi.mapper.ts +52 -10
- package/ts/integrations/kodi/kodi.types.ts +33 -58
- package/ts/integrations/kodi/kodi.validation.ts +60 -0
- package/ts/integrations/modbus/modbus.classes.client.ts +100 -842
- package/ts/integrations/modbus/modbus.classes.configflow.ts +70 -41
- package/ts/integrations/modbus/modbus.classes.integration.ts +115 -60
- package/ts/integrations/modbus/modbus.discovery.ts +38 -106
- package/ts/integrations/modbus/modbus.mapper.ts +64 -467
- package/ts/integrations/modbus/modbus.types.ts +64 -381
- package/ts/integrations/modbus/modbus.validation.ts +119 -0
- package/ts/integrations/mqtt/mqtt.classes.client.ts +136 -19
- package/ts/integrations/mqtt/mqtt.classes.configflow.ts +45 -32
- package/ts/integrations/mqtt/mqtt.classes.integration.ts +99 -38
- package/ts/integrations/mqtt/mqtt.classes.session.ts +118 -0
- package/ts/integrations/mqtt/mqtt.mapper.ts +43 -1
- package/ts/integrations/mqtt/mqtt.types.ts +52 -0
- package/ts/integrations/mqtt/mqtt.validation.ts +157 -0
- package/ts/integrations/mqtt/readme.md +12 -3
- package/ts/integrations/nanoleaf/nanoleaf.classes.client.ts +115 -249
- package/ts/integrations/nanoleaf/nanoleaf.classes.configflow.ts +90 -19
- package/ts/integrations/nanoleaf/nanoleaf.classes.integration.ts +130 -181
- package/ts/integrations/nanoleaf/nanoleaf.credentials.ts +39 -0
- package/ts/integrations/nanoleaf/nanoleaf.mapper.ts +47 -260
- package/ts/integrations/nanoleaf/nanoleaf.types.ts +29 -147
- package/ts/integrations/nanoleaf/nanoleaf.validation.ts +77 -0
- package/ts/integrations/onkyo/onkyo.classes.client.ts +148 -457
- package/ts/integrations/onkyo/onkyo.classes.configflow.ts +52 -6
- package/ts/integrations/onkyo/onkyo.classes.integration.ts +121 -12
- package/ts/integrations/onkyo/onkyo.discovery.ts +41 -3
- package/ts/integrations/onkyo/onkyo.mapper.ts +46 -19
- package/ts/integrations/onkyo/onkyo.types.ts +55 -110
- package/ts/integrations/onkyo/onkyo.validation.ts +85 -0
- package/ts/integrations/onkyo/readme.md +126 -0
- package/ts/integrations/panasonic_viera/panasonic_viera.classes.client.ts +101 -398
- package/ts/integrations/panasonic_viera/panasonic_viera.classes.configflow.ts +69 -5
- package/ts/integrations/panasonic_viera/panasonic_viera.classes.integration.ts +141 -9
- package/ts/integrations/panasonic_viera/panasonic_viera.discovery.ts +32 -3
- package/ts/integrations/panasonic_viera/panasonic_viera.mapper.ts +34 -161
- package/ts/integrations/panasonic_viera/panasonic_viera.types.ts +52 -96
- package/ts/integrations/panasonic_viera/panasonic_viera.validation.ts +56 -0
- package/ts/integrations/pioneer/pioneer.classes.client.ts +132 -428
- package/ts/integrations/pioneer/pioneer.classes.configflow.ts +67 -5
- package/ts/integrations/pioneer/pioneer.classes.integration.ts +225 -11
- package/ts/integrations/pioneer/pioneer.discovery.ts +45 -3
- package/ts/integrations/pioneer/pioneer.mapper.ts +57 -13
- package/ts/integrations/pioneer/pioneer.types.ts +87 -85
- package/ts/integrations/pioneer/pioneer.validation.ts +84 -0
- package/ts/integrations/samsungtv/readme.md +11 -5
- package/ts/integrations/samsungtv/samsungtv.classes.client.ts +40 -15
- package/ts/integrations/samsungtv/samsungtv.classes.configflow.ts +21 -6
- package/ts/integrations/samsungtv/samsungtv.classes.integration.ts +53 -38
- package/ts/integrations/samsungtv/samsungtv.types.ts +4 -1
- package/ts/integrations/shelly/readme.md +22 -7
- package/ts/integrations/shelly/shelly.classes.client.ts +386 -269
- package/ts/integrations/shelly/shelly.classes.configflow.ts +43 -38
- package/ts/integrations/shelly/shelly.classes.integration.ts +92 -111
- package/ts/integrations/shelly/shelly.classes.subscription.ts +24 -1
- package/ts/integrations/shelly/shelly.mapper.ts +19 -20
- package/ts/integrations/shelly/shelly.rpc.ts +2 -0
- package/ts/integrations/shelly/shelly.types.ts +50 -2
- package/ts/integrations/shelly/shelly.validation.ts +76 -0
- package/ts/integrations/sonos/readme.md +117 -38
- package/ts/integrations/sonos/sonos.classes.client.ts +392 -123
- package/ts/integrations/sonos/sonos.classes.configflow.ts +25 -28
- package/ts/integrations/sonos/sonos.classes.integration.ts +211 -186
- package/ts/integrations/sonos/sonos.config.ts +24 -2
- package/ts/integrations/sonos/sonos.mapper.ts +13 -8
- package/ts/integrations/sonos/sonos.matchers.ts +2 -2
- package/ts/integrations/sonos/sonos.types.ts +30 -1
- package/ts/integrations/soundtouch/soundtouch.classes.client.ts +152 -571
- package/ts/integrations/soundtouch/soundtouch.classes.configflow.ts +47 -42
- package/ts/integrations/soundtouch/soundtouch.classes.integration.ts +95 -150
- package/ts/integrations/soundtouch/soundtouch.discovery.ts +21 -133
- package/ts/integrations/soundtouch/soundtouch.mapper.ts +36 -207
- package/ts/integrations/soundtouch/soundtouch.types.ts +50 -195
- package/ts/integrations/soundtouch/soundtouch.validation.ts +60 -0
- package/ts/integrations/tasmota/readme.md +16 -5
- package/ts/integrations/tasmota/tasmota.classes.integration.ts +24 -6
- package/ts/integrations/tasmota/tasmota.classes.runtime.ts +112 -43
- package/ts/integrations/tasmota/tasmota.config.ts +17 -0
- package/ts/integrations/tasmota/tasmota.credentials.ts +92 -0
- package/ts/integrations/tasmota/tasmota.discovery.ts +87 -24
- package/ts/integrations/tasmota/tasmota.mapper.ts +6 -6
- package/ts/integrations/tasmota/tasmota.types.ts +43 -2
- package/ts/integrations/tuya/readme.md +52 -10
- package/ts/integrations/tuya/tuya.classes.integration.ts +69 -98
- package/ts/integrations/tuya/tuya.classes.runtime.ts +70 -24
- package/ts/integrations/tuya/tuya.mapper.ts +1 -1
- package/ts/integrations/tuya/tuya.types.ts +4 -0
- package/ts/integrations/tuya/tuya.validation.ts +5 -8
- package/ts/integrations/webostv/readme.md +115 -22
- package/ts/integrations/webostv/webostv.classes.client.ts +123 -50
- package/ts/integrations/webostv/webostv.classes.configflow.ts +35 -15
- package/ts/integrations/webostv/webostv.classes.integration.ts +44 -37
- package/ts/integrations/webostv/webostv.mapper.ts +4 -4
- package/ts/integrations/webostv/webostv.types.ts +18 -3
- package/ts/integrations/webostv/webostv.validation.ts +22 -1
- package/ts/integrations/wiz/index.ts +1 -0
- package/ts/integrations/wiz/wiz.classes.client.ts +84 -254
- package/ts/integrations/wiz/wiz.classes.configflow.ts +39 -70
- package/ts/integrations/wiz/wiz.classes.integration.ts +189 -45
- package/ts/integrations/wiz/wiz.discovery.ts +48 -291
- package/ts/integrations/wiz/wiz.mapper.ts +81 -754
- package/ts/integrations/wiz/wiz.types.ts +24 -224
- package/ts/integrations/wiz/wiz.validation.ts +73 -0
- package/ts/integrations/yamaha/index.ts +1 -0
- package/ts/integrations/yamaha/yamaha.classes.client.ts +150 -6
- package/ts/integrations/yamaha/yamaha.classes.configflow.ts +100 -5
- package/ts/integrations/yamaha/yamaha.classes.integration.ts +236 -8
- package/ts/integrations/yamaha/yamaha.discovery.ts +52 -3
- package/ts/integrations/yamaha/yamaha.mapper.ts +65 -13
- package/ts/integrations/yamaha/yamaha.types.ts +77 -97
- package/ts/integrations/yamaha/yamaha.validation.ts +86 -0
- package/ts/integrations/zigbee2mqtt/readme.md +22 -27
- package/ts/integrations/zigbee2mqtt/zigbee2mqtt.classes.configflow.ts +16 -7
- package/ts/integrations/zigbee2mqtt/zigbee2mqtt.classes.integration.ts +53 -6
- package/ts/integrations/zigbee2mqtt/zigbee2mqtt.classes.runtime.ts +62 -49
- package/ts/integrations/zigbee2mqtt/zigbee2mqtt.mapper.ts +17 -11
- package/ts/integrations/zigbee2mqtt/zigbee2mqtt.types.ts +35 -2
- package/ts/integrations/zigbee2mqtt/zigbee2mqtt.validation.ts +53 -7
- package/ts/integrations/zwave_js/readme.md +42 -9
- package/ts/integrations/zwave_js/zwave_js.classes.client.ts +155 -31
- package/ts/integrations/zwave_js/zwave_js.classes.configflow.ts +55 -31
- package/ts/integrations/zwave_js/zwave_js.classes.integration.ts +57 -35
- package/ts/integrations/zwave_js/zwave_js.discovery.ts +2 -2
- package/ts/integrations/zwave_js/zwave_js.mapper.ts +37 -23
- package/ts/integrations/zwave_js/zwave_js.types.ts +26 -3
- package/ts/integrations/zwave_js/zwave_js.validation.ts +52 -18
- package/ts/plugins.ts +2 -1
|
@@ -1,168 +1,88 @@
|
|
|
1
|
-
import * as plugins from '../../plugins.js';
|
|
2
1
|
import type { IConfigFlow, IConfigFlowContext, IConfigFlowStep, IDiscoveryCandidate } from '../../core/types.js';
|
|
3
|
-
import
|
|
4
|
-
import {
|
|
2
|
+
import { NativeIntegrationOwner, type NativeIntegrationScope } from '../../core/classes.nativeintegrationowner.js';
|
|
3
|
+
import { DaikinClient } from './daikin.classes.client.js';
|
|
4
|
+
import type { IDaikinIntegrationOptions, IDaikinNativeConfig } from './daikin.types.js';
|
|
5
|
+
import { daikinKeys, daikinObject, normalizeDaikinConfig } from './daikin.validation.js';
|
|
5
6
|
|
|
6
|
-
export class DaikinConfigFlow implements IConfigFlow<
|
|
7
|
-
|
|
8
|
-
|
|
7
|
+
export class DaikinConfigFlow implements IConfigFlow<IDaikinNativeConfig> {
|
|
8
|
+
readonly #scope: NativeIntegrationScope;
|
|
9
|
+
|
|
10
|
+
constructor(optionsArg: IDaikinIntegrationOptions = {}, scopeArg?: NativeIntegrationScope) {
|
|
11
|
+
this.#scope = scopeArg ?? new NativeIntegrationOwner('daikin', optionsArg).createFlowScope();
|
|
12
|
+
}
|
|
13
|
+
|
|
14
|
+
public destroy(): Promise<void> { return this.#scope.close(); }
|
|
15
|
+
public retryCleanup(): Promise<void> { return this.#scope.retryCleanup(); }
|
|
16
|
+
|
|
17
|
+
public async start(candidateArg: IDiscoveryCandidate, contextArg: IConfigFlowContext): Promise<IConfigFlowStep<IDaikinNativeConfig>> {
|
|
18
|
+
const context = this.#scope.admit(contextArg);
|
|
19
|
+
const candidate = daikinObject(candidateArg, 'Daikin candidate');
|
|
20
|
+
const metadata = candidate.metadata === undefined ? {} : daikinObject(candidate.metadata, 'Daikin candidate metadata');
|
|
21
|
+
const host = typeof candidate.host === 'string' ? candidate.host : undefined;
|
|
22
|
+
const expectedMac = typeof candidate.macAddress === 'string' ? candidate.macAddress.replace(/:/g, '') : typeof metadata.expectedMac === 'string' ? metadata.expectedMac : undefined;
|
|
9
23
|
return {
|
|
10
|
-
kind: 'form',
|
|
11
|
-
|
|
12
|
-
description: 'Configure a local Daikin endpoint, or use snapshot/manual data from the discovery candidate. Use either API key or SkyFi password, not both.',
|
|
24
|
+
kind: 'form', title: 'Connect selected Daikin BRP069',
|
|
25
|
+
description: 'Select a private IPv4 address and exact 12-digit adapter MAC for the host-selected home. Setup verifies basic, model and current control observations. BRP069 LAN HTTP is unauthenticated. No credentials are accepted.',
|
|
13
26
|
fields: [
|
|
14
|
-
{ name: 'host', label: '
|
|
15
|
-
{ name: '
|
|
16
|
-
{ name: 'apiVariant', label: '
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
{ label: 'BRP072C HTTPS with API key', value: 'brp072c' },
|
|
20
|
-
{ label: 'AirBase / skyfi path prefix', value: 'airbase' },
|
|
21
|
-
{ label: 'SkyFi password API', value: 'skyfi' },
|
|
22
|
-
{ label: 'BRP084 dsiot read-only', value: 'brp084' },
|
|
23
|
-
] },
|
|
24
|
-
{ name: 'ssl', label: 'Use HTTPS', type: 'boolean' },
|
|
25
|
-
{ name: 'verifySsl', label: 'Verify TLS certificate', type: 'boolean' },
|
|
26
|
-
{ name: 'apiKey', label: 'API key', type: 'password' },
|
|
27
|
-
{ name: 'uuid', label: 'Terminal UUID', type: 'text' },
|
|
28
|
-
{ name: 'password', label: 'SkyFi password', type: 'password' },
|
|
27
|
+
{ name: 'host', label: 'Selected private IPv4', type: 'text', required: true },
|
|
28
|
+
{ name: 'expectedMac', label: 'Exact adapter MAC (12 hex digits)', type: 'text', required: true },
|
|
29
|
+
{ name: 'apiVariant', label: 'Controller family', type: 'select', required: true, options: [{ label: 'Selected BRP069', value: 'brp069' }] },
|
|
30
|
+
{ name: 'allowPlaintext', label: 'Allow unauthenticated plaintext LAN HTTP', type: 'boolean', required: true },
|
|
31
|
+
{ name: 'port', label: 'HTTP port (80)', type: 'number' },
|
|
29
32
|
{ name: 'name', label: 'Name', type: 'text' },
|
|
30
33
|
],
|
|
31
|
-
submit: async (valuesArg) =>
|
|
34
|
+
submit: async (valuesArg) => {
|
|
35
|
+
let config: Readonly<IDaikinNativeConfig>;
|
|
36
|
+
try {
|
|
37
|
+
const values = daikinObject(valuesArg, 'Daikin configuration form');
|
|
38
|
+
daikinKeys(values, ['homeId', 'host', 'expectedMac', 'apiVariant', 'allowPlaintext', 'port', 'name']);
|
|
39
|
+
if (values.homeId !== undefined && values.homeId !== context.homeId) throw new TypeError('Daikin submitted home must match the independently selected host home.');
|
|
40
|
+
config = normalizeDaikinConfig({
|
|
41
|
+
homeId: context.homeId,
|
|
42
|
+
host: formText(values.host, host),
|
|
43
|
+
expectedMac: formText(values.expectedMac, expectedMac),
|
|
44
|
+
apiVariant: selectedVariant(values.apiVariant), allowPlaintext: selectedPlaintext(values.allowPlaintext), port: formPort(values.port, candidate.port),
|
|
45
|
+
name: values.name === undefined ? undefined : formText(values.name),
|
|
46
|
+
});
|
|
47
|
+
this.#scope.admit(context, config.homeId);
|
|
48
|
+
} catch (errorArg) {
|
|
49
|
+
return { kind: 'error', title: 'Daikin verification failed', error: errorArg instanceof Error ? errorArg.message : 'Daikin configuration is invalid.' };
|
|
50
|
+
}
|
|
51
|
+
return this.#scope.run(context, config.homeId, async (leaseArg): Promise<IConfigFlowStep<IDaikinNativeConfig>> => {
|
|
52
|
+
const client = new DaikinClient(config, leaseArg.context);
|
|
53
|
+
leaseArg.own(() => client.destroy());
|
|
54
|
+
try {
|
|
55
|
+
await client.getSnapshot(leaseArg.signal);
|
|
56
|
+
leaseArg.assertOpen();
|
|
57
|
+
return { kind: 'done', title: 'Verified selected Daikin BRP069', config };
|
|
58
|
+
} catch (errorArg) {
|
|
59
|
+
return { kind: 'error', title: 'Daikin verification failed', error: errorArg instanceof Error ? errorArg.message : 'Daikin verification failed.' };
|
|
60
|
+
}
|
|
61
|
+
});
|
|
62
|
+
},
|
|
32
63
|
};
|
|
33
64
|
}
|
|
34
|
-
|
|
35
|
-
private async submit(candidateArg: IDiscoveryCandidate, valuesArg: Record<string, unknown>): Promise<IConfigFlowStep<IDaikinConfig>> {
|
|
36
|
-
const metadata = candidateArg.metadata || {};
|
|
37
|
-
const parsed = parseEndpoint(this.stringValue(valuesArg.host) || this.stringValue(metadata.url));
|
|
38
|
-
const snapshot = snapshotValue(metadata.snapshot);
|
|
39
|
-
const rawData = rawDataValue(metadata.rawData);
|
|
40
|
-
const apiKey = this.stringValue(valuesArg.apiKey) || this.stringMetadata(metadata, 'apiKey');
|
|
41
|
-
const password = this.stringValue(valuesArg.password) || this.stringMetadata(metadata, 'password');
|
|
42
|
-
const apiVariant = this.apiVariant(this.stringValue(valuesArg.apiVariant) || this.stringMetadata(metadata, 'apiVariant'), apiKey, password);
|
|
43
|
-
const host = parsed?.host || this.stringValue(valuesArg.host) || candidateArg.host || snapshot?.device.host;
|
|
44
|
-
const ssl = this.booleanValue(valuesArg.ssl) ?? this.booleanMetadata(metadata, 'ssl') ?? parsed?.ssl ?? snapshot?.device.ssl ?? apiVariant === 'brp072c';
|
|
45
|
-
const port = this.numberValue(valuesArg.port) || candidateArg.port || parsed?.port || snapshot?.device.port || this.defaultPort(apiVariant, ssl);
|
|
46
|
-
const hasManualData = Boolean(snapshot || rawData || metadata.values || metadata.client);
|
|
47
|
-
|
|
48
|
-
if (apiKey && password) {
|
|
49
|
-
return { kind: 'error', title: 'Daikin setup failed', error: 'Invalid authentication: use either API key or password, not both.' };
|
|
50
|
-
}
|
|
51
|
-
if (!host && !hasManualData) {
|
|
52
|
-
return { kind: 'error', title: 'Daikin setup failed', error: 'Daikin host, injected client, snapshot, or manual data is required.' };
|
|
53
|
-
}
|
|
54
|
-
if (!this.validPort(port)) {
|
|
55
|
-
return { kind: 'error', title: 'Daikin setup failed', error: 'Daikin port must be between 1 and 65535.' };
|
|
56
|
-
}
|
|
57
|
-
|
|
58
|
-
const config: IDaikinConfig = {
|
|
59
|
-
host,
|
|
60
|
-
port,
|
|
61
|
-
ssl,
|
|
62
|
-
verifySsl: this.booleanValue(valuesArg.verifySsl) ?? this.booleanMetadata(metadata, 'verifySsl') ?? false,
|
|
63
|
-
apiKey,
|
|
64
|
-
uuid: this.stringValue(valuesArg.uuid) || this.stringMetadata(metadata, 'uuid') || (apiKey ? plugins.crypto.randomUUID().replace(/-/g, '') : undefined),
|
|
65
|
-
password,
|
|
66
|
-
apiVariant,
|
|
67
|
-
timeoutMs: daikinDefaultTimeoutMs,
|
|
68
|
-
name: this.stringValue(valuesArg.name) || candidateArg.name || snapshot?.device.name || this.stringMetadata(metadata, 'name'),
|
|
69
|
-
manufacturer: candidateArg.manufacturer || snapshot?.device.manufacturer || 'Daikin',
|
|
70
|
-
model: candidateArg.model || snapshot?.device.model,
|
|
71
|
-
uniqueId: candidateArg.id || snapshot?.device.id || snapshot?.device.macAddress || (host ? `${host}:${port}` : undefined),
|
|
72
|
-
macAddress: candidateArg.macAddress || snapshot?.device.macAddress,
|
|
73
|
-
snapshot,
|
|
74
|
-
rawData,
|
|
75
|
-
values: valueMapValue(metadata.values),
|
|
76
|
-
client: metadata.client as IDaikinConfig['client'],
|
|
77
|
-
commandExecutor: metadata.commandExecutor as IDaikinConfig['commandExecutor'],
|
|
78
|
-
};
|
|
79
|
-
|
|
80
|
-
return { kind: 'done', title: 'Daikin configured', config };
|
|
81
|
-
}
|
|
82
|
-
|
|
83
|
-
private apiVariant(valueArg: string | undefined, apiKeyArg: string | undefined, passwordArg: string | undefined): TDaikinApiVariant {
|
|
84
|
-
if (passwordArg) {
|
|
85
|
-
return 'skyfi';
|
|
86
|
-
}
|
|
87
|
-
if (apiKeyArg) {
|
|
88
|
-
return 'brp072c';
|
|
89
|
-
}
|
|
90
|
-
const allowed: TDaikinApiVariant[] = ['auto', 'brp069', 'brp072c', 'airbase', 'skyfi', 'brp084'];
|
|
91
|
-
return allowed.includes(valueArg as TDaikinApiVariant) ? valueArg as TDaikinApiVariant : 'auto';
|
|
92
|
-
}
|
|
93
|
-
|
|
94
|
-
private defaultPort(apiVariantArg: TDaikinApiVariant, sslArg: boolean): number {
|
|
95
|
-
if (apiVariantArg === 'skyfi') {
|
|
96
|
-
return daikinSkyFiPort;
|
|
97
|
-
}
|
|
98
|
-
return sslArg ? daikinDefaultHttpsPort : daikinDefaultHttpPort;
|
|
99
|
-
}
|
|
100
|
-
|
|
101
|
-
private stringValue(valueArg: unknown): string | undefined {
|
|
102
|
-
return typeof valueArg === 'string' && valueArg.trim() ? valueArg.trim().replace(/\/$/, '') : undefined;
|
|
103
|
-
}
|
|
104
|
-
|
|
105
|
-
private numberValue(valueArg: unknown): number | undefined {
|
|
106
|
-
if (typeof valueArg === 'number' && Number.isFinite(valueArg)) {
|
|
107
|
-
return Math.round(valueArg);
|
|
108
|
-
}
|
|
109
|
-
if (typeof valueArg === 'string' && valueArg.trim()) {
|
|
110
|
-
const parsed = Number(valueArg);
|
|
111
|
-
return Number.isFinite(parsed) ? Math.round(parsed) : undefined;
|
|
112
|
-
}
|
|
113
|
-
return undefined;
|
|
114
|
-
}
|
|
115
|
-
|
|
116
|
-
private booleanValue(valueArg: unknown): boolean | undefined {
|
|
117
|
-
if (typeof valueArg === 'boolean') {
|
|
118
|
-
return valueArg;
|
|
119
|
-
}
|
|
120
|
-
if (typeof valueArg === 'string') {
|
|
121
|
-
const normalized = valueArg.trim().toLowerCase();
|
|
122
|
-
if (['true', 'yes', 'on', '1'].includes(normalized)) {
|
|
123
|
-
return true;
|
|
124
|
-
}
|
|
125
|
-
if (['false', 'no', 'off', '0'].includes(normalized)) {
|
|
126
|
-
return false;
|
|
127
|
-
}
|
|
128
|
-
}
|
|
129
|
-
return undefined;
|
|
130
|
-
}
|
|
131
|
-
|
|
132
|
-
private stringMetadata(metadataArg: Record<string, unknown>, keyArg: string): string | undefined {
|
|
133
|
-
return this.stringValue(metadataArg[keyArg]);
|
|
134
|
-
}
|
|
135
|
-
|
|
136
|
-
private booleanMetadata(metadataArg: Record<string, unknown>, keyArg: string): boolean | undefined {
|
|
137
|
-
const value = metadataArg[keyArg];
|
|
138
|
-
return typeof value === 'boolean' ? value : undefined;
|
|
139
|
-
}
|
|
140
|
-
|
|
141
|
-
private validPort(valueArg: number): boolean {
|
|
142
|
-
return Number.isInteger(valueArg) && valueArg > 0 && valueArg <= 65535;
|
|
143
|
-
}
|
|
144
65
|
}
|
|
145
66
|
|
|
146
|
-
const
|
|
147
|
-
if (
|
|
148
|
-
|
|
149
|
-
}
|
|
150
|
-
try {
|
|
151
|
-
const url = new URL(valueArg);
|
|
152
|
-
return { host: url.hostname, port: url.port ? Number(url.port) : undefined, ssl: url.protocol === 'https:' };
|
|
153
|
-
} catch {
|
|
154
|
-
return undefined;
|
|
155
|
-
}
|
|
67
|
+
const selectedVariant = (valueArg: unknown): 'brp069' => {
|
|
68
|
+
if (valueArg !== 'brp069') throw new TypeError('Select the BRP069 controller family explicitly.');
|
|
69
|
+
return valueArg;
|
|
156
70
|
};
|
|
157
|
-
|
|
158
|
-
const
|
|
159
|
-
|
|
71
|
+
const formPort = (valueArg: unknown, hintArg: unknown): number | undefined => {
|
|
72
|
+
const value = valueArg === undefined || valueArg === '' ? hintArg : valueArg;
|
|
73
|
+
if (value === undefined) return undefined;
|
|
74
|
+
if (typeof value === 'number') return value;
|
|
75
|
+
if (typeof value === 'string' && /^\d{1,5}$/.test(value)) return Number(value);
|
|
76
|
+
throw new TypeError('Daikin port must be an integer.');
|
|
160
77
|
};
|
|
161
78
|
|
|
162
|
-
const
|
|
163
|
-
|
|
79
|
+
const selectedPlaintext = (valueArg: unknown): true => {
|
|
80
|
+
if (valueArg !== true) throw new TypeError('Explicitly allow unauthenticated plaintext LAN HTTP.');
|
|
81
|
+
return valueArg;
|
|
164
82
|
};
|
|
165
83
|
|
|
166
|
-
const
|
|
167
|
-
|
|
84
|
+
const formText = (valueArg: unknown, hintArg?: string): string => {
|
|
85
|
+
if (valueArg === undefined) return hintArg ?? '';
|
|
86
|
+
if (typeof valueArg !== 'string') throw new TypeError('Daikin text fields must be strings.');
|
|
87
|
+
return valueArg;
|
|
168
88
|
};
|
|
@@ -1,107 +1,202 @@
|
|
|
1
|
-
import
|
|
1
|
+
import * as plugins from '../../plugins.js';
|
|
2
2
|
import { BaseIntegration } from '../../core/classes.baseintegration.js';
|
|
3
|
-
import
|
|
3
|
+
import { NativeIntegrationOwner, type INativeSetupLease } from '../../core/classes.nativeintegrationowner.js';
|
|
4
|
+
import type { IDeviceFeatureWriteRequest, IIntegrationEntity, IIntegrationEvent, IIntegrationRuntime, IIntegrationSetupContext, ILogger, IServiceCallRequest, IServiceCallResult } from '../../core/types.js';
|
|
4
5
|
import { DaikinClient } from './daikin.classes.client.js';
|
|
5
6
|
import { DaikinConfigFlow } from './daikin.classes.configflow.js';
|
|
6
7
|
import { createDaikinDiscoveryDescriptor } from './daikin.discovery.js';
|
|
7
8
|
import { DaikinMapper } from './daikin.mapper.js';
|
|
8
|
-
import type {
|
|
9
|
-
import {
|
|
9
|
+
import type { IDaikinIntegrationOptions, IDaikinNativeConfig, IDaikinSnapshot } from './daikin.types.js';
|
|
10
|
+
import { normalizeDaikinConfig } from './daikin.validation.js';
|
|
10
11
|
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
12
|
+
const failure = (errorArg: unknown): IServiceCallResult => ({
|
|
13
|
+
success: false, error: errorArg instanceof Error ? errorArg.message : 'Daikin operation failed.',
|
|
14
|
+
data: errorArg instanceof plugins.ecobridgeDeviceManager.DaikinProtocolError
|
|
15
|
+
? { code: errorArg.code, effectOutcome: errorArg.effectOutcome }
|
|
16
|
+
: { effectOutcome: 'not-sent' },
|
|
17
|
+
});
|
|
18
|
+
|
|
19
|
+
export class DaikinIntegration extends BaseIntegration<IDaikinNativeConfig> {
|
|
20
|
+
public readonly domain = 'daikin';
|
|
21
|
+
public readonly displayName = 'Daikin BRP069';
|
|
14
22
|
public readonly status = 'control-runtime' as const;
|
|
15
23
|
public readonly discoveryDescriptor = createDaikinDiscoveryDescriptor();
|
|
16
|
-
public readonly configFlow
|
|
24
|
+
public readonly configFlow: DaikinConfigFlow;
|
|
17
25
|
public readonly metadata = {
|
|
18
|
-
source: '
|
|
19
|
-
upstreamPath: 'homeassistant/components/daikin',
|
|
20
|
-
upstreamDomain: daikinDomain,
|
|
21
|
-
integrationType: 'device',
|
|
22
|
-
iotClass: 'local_polling',
|
|
23
|
-
requirements: ['pydaikin==2.17.2'],
|
|
24
|
-
dependencies: [] as string[],
|
|
25
|
-
afterDependencies: [] as string[],
|
|
26
|
-
codeowners: ['@fredrike'],
|
|
27
|
-
configFlow: true,
|
|
28
|
-
documentation: 'https://www.home-assistant.io/integrations/daikin',
|
|
29
|
-
zeroconf: ['_dkapi._tcp.local.'],
|
|
30
|
-
discovery: {
|
|
31
|
-
zeroconf: '_dkapi._tcp.local.',
|
|
32
|
-
udp: 'DAIKIN_UDP/common/basic_info broadcast on UDP 30050 from source port 30000.',
|
|
33
|
-
http: 'Manual HTTP candidates for /common/basic_info, /aircon/*, /skyfi/*, and /dsiot/* are recognized.',
|
|
34
|
-
manual: true,
|
|
35
|
-
},
|
|
36
|
-
runtime: {
|
|
37
|
-
type: 'control-runtime',
|
|
38
|
-
polling: 'local Daikin HTTP key/value APIs plus SkyFi and BRP084 dsiot read modeling',
|
|
39
|
-
services: ['snapshot', 'status', 'refresh', 'climate controls', 'power switch', 'zone switch', 'streamer', 'holiday/advanced modes when represented by local endpoints'],
|
|
40
|
-
controls: true,
|
|
41
|
-
},
|
|
26
|
+
source: '@ecobridge.xyz/devicemanager', upstreamDomain: 'daikin', integrationType: 'device', iotClass: 'local_polling',
|
|
42
27
|
localApi: {
|
|
43
|
-
implemented: [
|
|
44
|
-
|
|
45
|
-
'BRP072C register_terminal/API-key request modeling when HTTPS is usable by the runtime',
|
|
46
|
-
'AirBase skyfi-prefixed reads plus zone setting writes',
|
|
47
|
-
'SkyFi password API reads and set.cgi/setzone.cgi writes',
|
|
48
|
-
'BRP084 dsiot snapshot reads',
|
|
49
|
-
'snapshot/manual-data and injected client/executor operation',
|
|
50
|
-
],
|
|
51
|
-
explicitUnsupported: [
|
|
52
|
-
'BRP084 dsiot control writes without an injected commandExecutor',
|
|
53
|
-
'faking command success for snapshot/manual-only configurations',
|
|
54
|
-
'forcing TLS certificate bypass for BRP072C self-signed devices through Node fetch',
|
|
55
|
-
],
|
|
28
|
+
implemented: ['selected BRP069 fresh identity/model/control observations', 'explicit power', 'integer target in observed cool or heat mode', 'independent readback'],
|
|
29
|
+
explicitUnsupported: ['automatic family selection', 'mode/humidity/fan/direction changes', 'other controller-family effects', 'cloud', 'retries', 'optimistic state', 'injected effect executors'],
|
|
56
30
|
},
|
|
57
31
|
};
|
|
32
|
+
readonly #owner: NativeIntegrationOwner;
|
|
33
|
+
|
|
34
|
+
constructor(optionsArg: IDaikinIntegrationOptions = {}) {
|
|
35
|
+
super();
|
|
36
|
+
this.#owner = new NativeIntegrationOwner(this.domain, optionsArg);
|
|
37
|
+
this.configFlow = new DaikinConfigFlow({}, this.#owner.createFlowScope());
|
|
38
|
+
}
|
|
58
39
|
|
|
59
|
-
public async setup(configArg:
|
|
60
|
-
|
|
61
|
-
return
|
|
40
|
+
public async setup(configArg: IDaikinNativeConfig, contextArg: IIntegrationSetupContext): Promise<IIntegrationRuntime> {
|
|
41
|
+
const config = normalizeDaikinConfig(configArg);
|
|
42
|
+
return this.#owner.runSetup(contextArg, config.homeId, async (leaseArg) => {
|
|
43
|
+
const client = new DaikinClient(config, leaseArg.context);
|
|
44
|
+
let runtime: DaikinRuntime | undefined;
|
|
45
|
+
leaseArg.own(() => runtime ? runtime.cleanupOwnedResource() : client.destroy());
|
|
46
|
+
const identity = await client.getSnapshot(leaseArg.signal);
|
|
47
|
+
leaseArg.assertOpen();
|
|
48
|
+
runtime = new DaikinRuntime(client, identity, leaseArg, leaseArg.context.logger);
|
|
49
|
+
leaseArg.promoteToRuntime();
|
|
50
|
+
return runtime;
|
|
51
|
+
});
|
|
62
52
|
}
|
|
63
53
|
|
|
64
|
-
public
|
|
54
|
+
public destroy(): Promise<void> { return this.#owner.close(); }
|
|
55
|
+
public retryCleanup(): Promise<void> { return this.#owner.retryCleanup(); }
|
|
65
56
|
}
|
|
66
57
|
|
|
67
58
|
export class HomeAssistantDaikinIntegration extends DaikinIntegration {}
|
|
68
59
|
|
|
60
|
+
interface IDaikinSubscriber {
|
|
61
|
+
handler: (eventArg: IIntegrationEvent) => void;
|
|
62
|
+
cleanup: () => void;
|
|
63
|
+
}
|
|
64
|
+
|
|
69
65
|
class DaikinRuntime implements IIntegrationRuntime {
|
|
70
|
-
public domain =
|
|
66
|
+
public readonly domain = 'daikin';
|
|
67
|
+
readonly #identity: IDaikinSnapshot;
|
|
68
|
+
readonly #subscriptions = new Set<IDaikinSubscriber>();
|
|
69
|
+
#entities: IIntegrationEntity[];
|
|
70
|
+
#available = true;
|
|
71
|
+
#destroy?: Promise<void>;
|
|
72
|
+
#removeAbort: () => void = () => undefined;
|
|
71
73
|
|
|
72
|
-
constructor(private readonly client: DaikinClient
|
|
74
|
+
constructor(private readonly client: DaikinClient, identityArg: IDaikinSnapshot, private readonly lease: INativeSetupLease,
|
|
75
|
+
private readonly logger?: ILogger) {
|
|
76
|
+
this.#identity = structuredClone(identityArg);
|
|
77
|
+
this.#entities = DaikinMapper.toEntities(identityArg);
|
|
78
|
+
// The lease retains failed cleanup; destroy() and the owner expose its stable rejection.
|
|
79
|
+
const aborted = (): void => { void this.destroy().catch(() => undefined); };
|
|
80
|
+
lease.signal.addEventListener('abort', aborted, { once: true });
|
|
81
|
+
this.#removeAbort = () => lease.signal.removeEventListener('abort', aborted);
|
|
82
|
+
if (lease.signal.aborted) aborted();
|
|
83
|
+
}
|
|
73
84
|
|
|
74
|
-
public
|
|
75
|
-
|
|
85
|
+
public isHealthy(): boolean { return !this.#destroy && this.client.isHealthy(); }
|
|
86
|
+
public async devices(signalArg?: AbortSignal): Promise<plugins.shxInterfaces.data.IDeviceDefinition[]> {
|
|
87
|
+
return DaikinMapper.toDevices(await this.#snapshot(signalArg));
|
|
76
88
|
}
|
|
89
|
+
public async entities(): Promise<IIntegrationEntity[]> { return DaikinMapper.toEntities(await this.#snapshot()); }
|
|
77
90
|
|
|
78
|
-
public async
|
|
79
|
-
|
|
91
|
+
public async subscribe(handlerArg: (eventArg: IIntegrationEvent) => void, signalArg?: AbortSignal): Promise<() => Promise<void>> {
|
|
92
|
+
this.#assertOpen();
|
|
93
|
+
if (typeof handlerArg !== 'function') throw new TypeError('Daikin subscriber must be a function.');
|
|
94
|
+
if (signalArg !== undefined && !(signalArg instanceof AbortSignal)) throw new TypeError('Daikin subscriber signal must be an AbortSignal.');
|
|
95
|
+
signalArg?.throwIfAborted();
|
|
96
|
+
if (this.#subscriptions.size >= 128) throw new Error('Daikin subscriber capacity is exhausted.');
|
|
97
|
+
const subscriber: IDaikinSubscriber = { handler: handlerArg, cleanup: () => {
|
|
98
|
+
this.#subscriptions.delete(subscriber);
|
|
99
|
+
signalArg?.removeEventListener('abort', subscriber.cleanup);
|
|
100
|
+
} };
|
|
101
|
+
this.#subscriptions.add(subscriber);
|
|
102
|
+
signalArg?.addEventListener('abort', subscriber.cleanup, { once: true });
|
|
103
|
+
if (signalArg?.aborted) subscriber.cleanup();
|
|
104
|
+
return async () => subscriber.cleanup();
|
|
80
105
|
}
|
|
81
106
|
|
|
82
107
|
public async callService(requestArg: IServiceCallRequest): Promise<IServiceCallResult> {
|
|
83
108
|
try {
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
return { success:
|
|
109
|
+
this.#assertOpen();
|
|
110
|
+
const control = DaikinMapper.controlForService(this.#identity, requestArg);
|
|
111
|
+
if (control === 'snapshot') {
|
|
112
|
+
const snapshot = await this.client.getSnapshot();
|
|
113
|
+
this.#observe(snapshot);
|
|
114
|
+
return { success: true, data: snapshot };
|
|
90
115
|
}
|
|
116
|
+
return this.#result(await this.client.setControl(control));
|
|
117
|
+
} catch (errorArg) { this.#report(errorArg); return failure(errorArg); }
|
|
118
|
+
}
|
|
119
|
+
|
|
120
|
+
public async writeFeature(requestArg: IDeviceFeatureWriteRequest, signalArg?: AbortSignal): Promise<IServiceCallResult> {
|
|
121
|
+
try {
|
|
122
|
+
this.#assertOpen();
|
|
123
|
+
return this.#result(await this.client.setControl(DaikinMapper.controlForFeature(this.#identity, requestArg), signalArg));
|
|
124
|
+
} catch (errorArg) { this.#report(errorArg); return failure(errorArg); }
|
|
125
|
+
}
|
|
126
|
+
|
|
127
|
+
public destroy(): Promise<void> {
|
|
128
|
+
this.#destroy ??= Promise.resolve().then(() => this.lease.close());
|
|
129
|
+
return this.#destroy;
|
|
130
|
+
}
|
|
91
131
|
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
132
|
+
/** One adapter resource groups its client and subscriptions; every sibling must settle. */
|
|
133
|
+
public async cleanupOwnedResource(): Promise<void> {
|
|
134
|
+
const results = await Promise.allSettled([
|
|
135
|
+
Promise.resolve().then(() => this.#removeAbort()),
|
|
136
|
+
...[...this.#subscriptions].map((subscriberArg) => Promise.resolve().then(() => subscriberArg.cleanup())),
|
|
137
|
+
Promise.resolve().then(() => this.client.destroy()),
|
|
138
|
+
]);
|
|
139
|
+
const errors = results.filter((resultArg): resultArg is PromiseRejectedResult => resultArg.status === 'rejected').map((resultArg) => resultArg.reason as unknown);
|
|
140
|
+
if (errors.length) throw new AggregateError(errors, 'Daikin runtime resource cleanup failed.');
|
|
141
|
+
}
|
|
142
|
+
|
|
143
|
+
async #snapshot(signalArg?: AbortSignal): Promise<IDaikinSnapshot> {
|
|
144
|
+
this.#assertOpen();
|
|
145
|
+
try {
|
|
146
|
+
const snapshot = await this.client.getSnapshot(signalArg);
|
|
147
|
+
this.#observe(snapshot);
|
|
148
|
+
return snapshot;
|
|
149
|
+
} catch (errorArg) { this.#report(errorArg); throw errorArg; }
|
|
150
|
+
}
|
|
151
|
+
|
|
152
|
+
#result(dataArg: plugins.ecobridgeDeviceManager.IDaikinControlResult): IServiceCallResult {
|
|
153
|
+
this.#observe(DaikinMapper.fromState(this.client.config, dataArg.observed));
|
|
154
|
+
return { success: dataArg.effectOutcome === 'confirmed', data: dataArg,
|
|
155
|
+
error: dataArg.effectOutcome === 'confirmed' ? undefined : 'Daikin setter was accepted but requested state was not confirmed by observation.' };
|
|
156
|
+
}
|
|
157
|
+
|
|
158
|
+
#observe(snapshotArg: IDaikinSnapshot): void {
|
|
159
|
+
const entities = DaikinMapper.toEntities(snapshotArg);
|
|
160
|
+
if (!this.#available) this.#emit({ type: 'availability_changed', data: { available: true } });
|
|
161
|
+
this.#available = true;
|
|
162
|
+
for (const entity of entities) {
|
|
163
|
+
const previous = this.#entities.find((entryArg) => entryArg.id === entity.id);
|
|
164
|
+
if (!previous || JSON.stringify([previous.state, previous.attributes]) !== JSON.stringify([entity.state, entity.attributes])) {
|
|
165
|
+
this.#emit({ type: 'state_changed', entityId: entity.id, data: entity });
|
|
96
166
|
}
|
|
97
|
-
const data = await this.client.execute(command);
|
|
98
|
-
return { success: true, data: data ?? command };
|
|
99
|
-
} catch (errorArg) {
|
|
100
|
-
return { success: false, error: errorArg instanceof Error ? errorArg.message : String(errorArg) };
|
|
101
167
|
}
|
|
168
|
+
this.#entities = entities;
|
|
169
|
+
}
|
|
170
|
+
|
|
171
|
+
#report(errorArg: unknown): void {
|
|
172
|
+
if (!this.client.isHealthy() && this.#available) {
|
|
173
|
+
this.#available = false;
|
|
174
|
+
this.#emit({ type: 'availability_changed', data: { available: false } });
|
|
175
|
+
}
|
|
176
|
+
this.#emit({ type: 'error', data: failure(errorArg) });
|
|
177
|
+
}
|
|
178
|
+
|
|
179
|
+
#emit(eventArg: Pick<IIntegrationEvent, 'type' | 'data'> & { entityId?: string }): void {
|
|
180
|
+
if (this.#destroy) return;
|
|
181
|
+
const event: IIntegrationEvent = { ...eventArg, integrationDomain: this.domain,
|
|
182
|
+
deviceId: DaikinMapper.deviceId(this.#identity), timestamp: Date.now() };
|
|
183
|
+
for (const subscriber of [...this.#subscriptions]) {
|
|
184
|
+
if (!this.#subscriptions.has(subscriber)) continue;
|
|
185
|
+
try {
|
|
186
|
+
const returned: unknown = subscriber.handler(structuredClone(event));
|
|
187
|
+
if (returned instanceof Promise) void returned.catch(() => this.#subscriberFailed(subscriber));
|
|
188
|
+
} catch { this.#subscriberFailed(subscriber); }
|
|
189
|
+
}
|
|
190
|
+
}
|
|
191
|
+
|
|
192
|
+
#subscriberFailed(subscriberArg: IDaikinSubscriber): void {
|
|
193
|
+
subscriberArg.cleanup();
|
|
194
|
+
this.logger?.log('error', 'Daikin event subscriber failed.');
|
|
195
|
+
this.#emit({ type: 'error', data: { error: 'Daikin event subscriber failed.' } });
|
|
102
196
|
}
|
|
103
197
|
|
|
104
|
-
|
|
105
|
-
|
|
198
|
+
#assertOpen(): void {
|
|
199
|
+
if (this.#destroy) throw new Error('Daikin runtime is destroyed.');
|
|
200
|
+
this.lease.assertOpen();
|
|
106
201
|
}
|
|
107
202
|
}
|