homebridge-midea-platform 0.2.1 → 0.3.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/.eslintignore +3 -0
- package/.husky/pre-commit +4 -0
- package/.prettierrc +18 -0
- package/README.md +5 -0
- package/config.schema.json +48 -0
- package/dist/accessory/AccessoryFactory.d.ts +2 -1
- package/dist/accessory/AccessoryFactory.d.ts.map +1 -1
- package/dist/accessory/AccessoryFactory.js +3 -0
- package/dist/accessory/AccessoryFactory.js.map +1 -1
- package/dist/accessory/AirConditionerAccessory.d.ts +23 -0
- package/dist/accessory/AirConditionerAccessory.d.ts.map +1 -1
- package/dist/accessory/AirConditionerAccessory.js +122 -36
- package/dist/accessory/AirConditionerAccessory.js.map +1 -1
- package/dist/accessory/BaseAccessory.d.ts.map +1 -1
- package/dist/accessory/BaseAccessory.js +2 -16
- package/dist/accessory/BaseAccessory.js.map +1 -1
- package/dist/accessory/DehumidifierAccessory.d.ts +41 -0
- package/dist/accessory/DehumidifierAccessory.d.ts.map +1 -0
- package/dist/accessory/DehumidifierAccessory.js +294 -0
- package/dist/accessory/DehumidifierAccessory.js.map +1 -0
- package/dist/core/MideaCloud.d.ts +11 -0
- package/dist/core/MideaCloud.d.ts.map +1 -1
- package/dist/core/MideaCloud.js +106 -65
- package/dist/core/MideaCloud.js.map +1 -1
- package/dist/core/MideaConstants.d.ts +2 -1
- package/dist/core/MideaConstants.d.ts.map +1 -1
- package/dist/core/MideaConstants.js +12 -16
- package/dist/core/MideaConstants.js.map +1 -1
- package/dist/core/MideaDevice.d.ts +26 -8
- package/dist/core/MideaDevice.d.ts.map +1 -1
- package/dist/core/MideaDevice.js +130 -28
- package/dist/core/MideaDevice.js.map +1 -1
- package/dist/core/MideaDiscover.d.ts +21 -1
- package/dist/core/MideaDiscover.d.ts.map +1 -1
- package/dist/core/MideaDiscover.js +98 -20
- package/dist/core/MideaDiscover.js.map +1 -1
- package/dist/core/MideaMessage.d.ts.map +1 -1
- package/dist/core/MideaMessage.js +28 -11
- package/dist/core/MideaMessage.js.map +1 -1
- package/dist/core/MideaPacketBuilder.d.ts.map +1 -1
- package/dist/core/MideaPacketBuilder.js +15 -5
- package/dist/core/MideaPacketBuilder.js.map +1 -1
- package/dist/core/MideaSecurity.d.ts +3 -1
- package/dist/core/MideaSecurity.d.ts.map +1 -1
- package/dist/core/MideaSecurity.js +41 -16
- package/dist/core/MideaSecurity.js.map +1 -1
- package/dist/core/MideaUtils.d.ts +21 -6
- package/dist/core/MideaUtils.d.ts.map +1 -1
- package/dist/core/MideaUtils.js +81 -83
- package/dist/core/MideaUtils.js.map +1 -1
- package/dist/devices/DeviceFactory.d.ts +3 -2
- package/dist/devices/DeviceFactory.d.ts.map +1 -1
- package/dist/devices/DeviceFactory.js +5 -2
- package/dist/devices/DeviceFactory.js.map +1 -1
- package/dist/devices/a1/MideaA1Device.d.ts +77 -0
- package/dist/devices/a1/MideaA1Device.d.ts.map +1 -0
- package/dist/devices/a1/MideaA1Device.js +144 -0
- package/dist/devices/a1/MideaA1Device.js.map +1 -0
- package/dist/devices/a1/MideaA1Message.d.ts +41 -0
- package/dist/devices/a1/MideaA1Message.d.ts.map +1 -0
- package/dist/devices/a1/MideaA1Message.js +206 -0
- package/dist/devices/a1/MideaA1Message.js.map +1 -0
- package/dist/devices/ac/MideaACDevice.d.ts +21 -7
- package/dist/devices/ac/MideaACDevice.d.ts.map +1 -1
- package/dist/devices/ac/MideaACDevice.js +82 -30
- package/dist/devices/ac/MideaACDevice.js.map +1 -1
- package/dist/devices/ac/MideaACMessage.d.ts.map +1 -1
- package/dist/devices/ac/MideaACMessage.js +158 -82
- package/dist/devices/ac/MideaACMessage.js.map +1 -1
- package/dist/platform.d.ts +29 -5
- package/dist/platform.d.ts.map +1 -1
- package/dist/platform.js +151 -52
- package/dist/platform.js.map +1 -1
- package/dist/platformUtils.d.ts +6 -1
- package/dist/platformUtils.d.ts.map +1 -1
- package/dist/platformUtils.js.map +1 -1
- package/package.json +12 -5
|
@@ -0,0 +1,294 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
3
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
4
|
+
};
|
|
5
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
|
+
const BaseAccessory_1 = __importDefault(require("./BaseAccessory"));
|
|
7
|
+
const settings_1 = require("../settings");
|
|
8
|
+
class DehumidifierAccessory extends BaseAccessory_1.default {
|
|
9
|
+
/*********************************************************************
|
|
10
|
+
* Constructor registers all the service types with Homebridge, registers
|
|
11
|
+
* a callback function with the MideaDevice class, and requests device status.
|
|
12
|
+
*/
|
|
13
|
+
constructor(platform, accessory, device, configDev) {
|
|
14
|
+
super(platform, accessory, device, configDev);
|
|
15
|
+
this.device = device;
|
|
16
|
+
this.configDev = configDev;
|
|
17
|
+
this.service =
|
|
18
|
+
this.accessory.getService(this.platform.Service.HumidifierDehumidifier) ||
|
|
19
|
+
this.accessory.addService(this.platform.Service.HumidifierDehumidifier);
|
|
20
|
+
this.service.setCharacteristic(this.platform.Characteristic.Name, this.device.name);
|
|
21
|
+
this.accessories = this.platform.accessories.filter((acc) => acc.context.id === this.accessory.UUID && acc !== this.accessory);
|
|
22
|
+
this.service
|
|
23
|
+
.getCharacteristic(this.platform.Characteristic.Active)
|
|
24
|
+
.onGet(this.getActive.bind(this))
|
|
25
|
+
.onSet(this.setActive.bind(this));
|
|
26
|
+
this.service
|
|
27
|
+
.getCharacteristic(this.platform.Characteristic.CurrentHumidifierDehumidifierState)
|
|
28
|
+
.onGet(this.getCurrentHumidifierDehumidifierState.bind(this));
|
|
29
|
+
this.service
|
|
30
|
+
.getCharacteristic(this.platform.Characteristic.TargetHumidifierDehumidifierState)
|
|
31
|
+
.onGet(this.getTargetHumidifierDehumidifierState.bind(this))
|
|
32
|
+
.onSet(this.setTargetHumidifierDehumidifierState.bind(this))
|
|
33
|
+
.setProps({
|
|
34
|
+
validValues: [
|
|
35
|
+
this.platform.Characteristic.TargetHumidifierDehumidifierState
|
|
36
|
+
.HUMIDIFIER_OR_DEHUMIDIFIER,
|
|
37
|
+
this.platform.Characteristic.TargetHumidifierDehumidifierState
|
|
38
|
+
.HUMIDIFIER,
|
|
39
|
+
this.platform.Characteristic.TargetHumidifierDehumidifierState
|
|
40
|
+
.DEHUMIDIFIER,
|
|
41
|
+
],
|
|
42
|
+
});
|
|
43
|
+
this.service
|
|
44
|
+
.getCharacteristic(this.platform.Characteristic.CurrentRelativeHumidity)
|
|
45
|
+
.onGet(this.getCurrentRelativeHumidity.bind(this))
|
|
46
|
+
.setProps({
|
|
47
|
+
minValue: 0,
|
|
48
|
+
maxValue: 100,
|
|
49
|
+
minStep: 1,
|
|
50
|
+
});
|
|
51
|
+
this.service
|
|
52
|
+
.getCharacteristic(this.platform.Characteristic.RelativeHumidityDehumidifierThreshold)
|
|
53
|
+
.onGet(this.getRelativeHumidityDehumidifierThreshold.bind(this))
|
|
54
|
+
.onSet(this.setRelativeHumidityDehumidifierThreshold.bind(this))
|
|
55
|
+
.setProps({
|
|
56
|
+
minValue: 0,
|
|
57
|
+
maxValue: 100,
|
|
58
|
+
minStep: 5,
|
|
59
|
+
});
|
|
60
|
+
this.service
|
|
61
|
+
.getCharacteristic(this.platform.Characteristic.RotationSpeed)
|
|
62
|
+
.onGet(this.getRotationSpeed.bind(this))
|
|
63
|
+
.onSet(this.setRotationSpeed.bind(this));
|
|
64
|
+
this.service
|
|
65
|
+
.getCharacteristic(this.platform.Characteristic.SwingMode)
|
|
66
|
+
.onGet(this.getSwingMode.bind(this))
|
|
67
|
+
.onSet(this.setSwingMode.bind(this));
|
|
68
|
+
this.service
|
|
69
|
+
.getCharacteristic(this.platform.Characteristic.LockPhysicalControls)
|
|
70
|
+
.onGet(this.getChildLockMode.bind(this))
|
|
71
|
+
.onSet(this.setChildLockMode.bind(this));
|
|
72
|
+
this.service
|
|
73
|
+
.getCharacteristic(this.platform.Characteristic.WaterLevel)
|
|
74
|
+
.onGet(this.getWaterLevel.bind(this));
|
|
75
|
+
// Register a callback function with MideaDevice and then refresh device status. The callback
|
|
76
|
+
// is called whenever there is a change in any attribute value from the device.
|
|
77
|
+
this.device.on('update', this.updateCharacteristics.bind(this));
|
|
78
|
+
this.device.refresh_status();
|
|
79
|
+
// Remove unused accessories
|
|
80
|
+
this.platform.api.unregisterPlatformAccessories(settings_1.PLUGIN_NAME, settings_1.PLATFORM_NAME, this.accessories);
|
|
81
|
+
}
|
|
82
|
+
/*********************************************************************
|
|
83
|
+
* Callback function called by MideaDevice whenever there is a change to
|
|
84
|
+
* any attribute value.
|
|
85
|
+
*/
|
|
86
|
+
async updateCharacteristics(attributes) {
|
|
87
|
+
for (const [k, v] of Object.entries(attributes)) {
|
|
88
|
+
this.platform.log.debug(`[${this.device.name}] Set attribute ${k} to: ${v}`);
|
|
89
|
+
let updateState = false;
|
|
90
|
+
switch (k.toLowerCase()) {
|
|
91
|
+
case 'power':
|
|
92
|
+
this.service.updateCharacteristic(this.platform.Characteristic.Active, v
|
|
93
|
+
? this.platform.Characteristic.Active.ACTIVE
|
|
94
|
+
: this.platform.Characteristic.Active.INACTIVE);
|
|
95
|
+
updateState = true;
|
|
96
|
+
break;
|
|
97
|
+
case 'target_humidity':
|
|
98
|
+
this.service.updateCharacteristic(this.platform.Characteristic.RelativeHumidityDehumidifierThreshold, v);
|
|
99
|
+
updateState = true;
|
|
100
|
+
break;
|
|
101
|
+
case 'fan_speed':
|
|
102
|
+
this.service.updateCharacteristic(this.platform.Characteristic.RotationSpeed, v);
|
|
103
|
+
break;
|
|
104
|
+
case 'current_humidity':
|
|
105
|
+
this.service.updateCharacteristic(this.platform.Characteristic.CurrentRelativeHumidity, v);
|
|
106
|
+
updateState = true;
|
|
107
|
+
break;
|
|
108
|
+
case 'mode':
|
|
109
|
+
updateState = true;
|
|
110
|
+
break;
|
|
111
|
+
case 'swing':
|
|
112
|
+
this.service.updateCharacteristic(this.platform.Characteristic.SwingMode, v
|
|
113
|
+
? this.platform.Characteristic.SwingMode.SWING_ENABLED
|
|
114
|
+
: this.platform.Characteristic.SwingMode.SWING_DISABLED);
|
|
115
|
+
break;
|
|
116
|
+
case 'current_temperature':
|
|
117
|
+
// Not currently supported
|
|
118
|
+
break;
|
|
119
|
+
case 'tank_level':
|
|
120
|
+
this.service.updateCharacteristic(this.platform.Characteristic.WaterLevel, v);
|
|
121
|
+
break;
|
|
122
|
+
case 'tank_full':
|
|
123
|
+
// No HomeKit characteristic
|
|
124
|
+
break;
|
|
125
|
+
case 'water_level_set':
|
|
126
|
+
// No HomeKit characteristic
|
|
127
|
+
break;
|
|
128
|
+
case 'child_lock':
|
|
129
|
+
this.service.updateCharacteristic(this.platform.Characteristic.LockPhysicalControls, v
|
|
130
|
+
? this.platform.Characteristic.LockPhysicalControls
|
|
131
|
+
.CONTROL_LOCK_ENABLED
|
|
132
|
+
: this.platform.Characteristic.LockPhysicalControls
|
|
133
|
+
.CONTROL_LOCK_DISABLED);
|
|
134
|
+
break;
|
|
135
|
+
default:
|
|
136
|
+
this.platform.log.warn(`[${this.device.name}] Attempt to set unsupported attribute ${k} to ${v}`);
|
|
137
|
+
}
|
|
138
|
+
if (updateState) {
|
|
139
|
+
this.service.updateCharacteristic(this.platform.Characteristic.TargetHumidifierDehumidifierState, this.platform.Characteristic.TargetHumidifierDehumidifierState
|
|
140
|
+
.DEHUMIDIFIER);
|
|
141
|
+
this.service.updateCharacteristic(this.platform.Characteristic.CurrentHumidifierDehumidifierState, this.currentHumidifierDehumidifierState());
|
|
142
|
+
}
|
|
143
|
+
}
|
|
144
|
+
}
|
|
145
|
+
/*********************************************************************
|
|
146
|
+
* Callback functions for each Homebridge/HomeKit service
|
|
147
|
+
*
|
|
148
|
+
*/
|
|
149
|
+
async getActive() {
|
|
150
|
+
this.platform.log.debug(`[${this.device.name}] GET Active, value: ${this.device.attributes.POWER}`);
|
|
151
|
+
return this.device.attributes.POWER
|
|
152
|
+
? this.platform.Characteristic.Active.ACTIVE
|
|
153
|
+
: this.platform.Characteristic.Active.INACTIVE;
|
|
154
|
+
}
|
|
155
|
+
async setActive(value) {
|
|
156
|
+
this.platform.log.debug(`[${this.device.name}] SET Active to: ${value}`);
|
|
157
|
+
await this.device.set_attribute({ POWER: !!value });
|
|
158
|
+
}
|
|
159
|
+
// Handle requests to get the current value of the "HumidifierDehumidifierState" characteristic
|
|
160
|
+
async getCurrentHumidifierDehumidifierState() {
|
|
161
|
+
this.platform.log.debug(`[${this.device.name}] GET CurrentHumidifierDehumidifierState, value: ${this.device.attributes.POWER},${this.device.attributes.MODE}`);
|
|
162
|
+
return this.currentHumidifierDehumidifierState();
|
|
163
|
+
}
|
|
164
|
+
currentHumidifierDehumidifierState() {
|
|
165
|
+
if (!this.device.attributes.POWER) {
|
|
166
|
+
// Powered off, must be inactive
|
|
167
|
+
return this.platform.Characteristic.CurrentHumidifierDehumidifierState
|
|
168
|
+
.INACTIVE;
|
|
169
|
+
}
|
|
170
|
+
else {
|
|
171
|
+
// Powered on, check mode
|
|
172
|
+
if (this.device.attributes.MODE >= 2) {
|
|
173
|
+
// Dehumidifying
|
|
174
|
+
return this.platform.Characteristic.CurrentHumidifierDehumidifierState
|
|
175
|
+
.DEHUMIDIFYING;
|
|
176
|
+
}
|
|
177
|
+
else if (this.device.attributes.MODE === 1) {
|
|
178
|
+
// Whether deumidifying depends on whether we have reached target. This is not
|
|
179
|
+
// always accurate, but is best we can do to signal whether actively dehumidifing or not.
|
|
180
|
+
if (this.device.attributes.CURRENT_HUMIDITY <
|
|
181
|
+
this.device.attributes.TARGET_HUMIDITY) {
|
|
182
|
+
return this.platform.Characteristic.CurrentHumidifierDehumidifierState
|
|
183
|
+
.IDLE;
|
|
184
|
+
}
|
|
185
|
+
else {
|
|
186
|
+
return this.platform.Characteristic.CurrentHumidifierDehumidifierState
|
|
187
|
+
.DEHUMIDIFYING;
|
|
188
|
+
}
|
|
189
|
+
}
|
|
190
|
+
return this.platform.Characteristic.CurrentHumidifierDehumidifierState
|
|
191
|
+
.IDLE;
|
|
192
|
+
}
|
|
193
|
+
}
|
|
194
|
+
// Handle requests to get the target value of the "HumidifierDehumidifierState" characteristic
|
|
195
|
+
async getTargetHumidifierDehumidifierState() {
|
|
196
|
+
this.platform.log.debug(`[${this.device.name}] GET TargetHumidifierDehumidifierState, value:
|
|
197
|
+
${this.platform.Characteristic.TargetHumidifierDehumidifierState.DEHUMIDIFIER}`);
|
|
198
|
+
// Always return that we are a dehumidifier, other states not supported.
|
|
199
|
+
return this.platform.Characteristic.TargetHumidifierDehumidifierState
|
|
200
|
+
.DEHUMIDIFIER;
|
|
201
|
+
}
|
|
202
|
+
// Handle requests to set the target value of the "HumidifierDehumidifierState" characteristic
|
|
203
|
+
async setTargetHumidifierDehumidifierState(value) {
|
|
204
|
+
this.platform.log.debug(`[${this.device.name}] SET TargetHumidifierDehumidifierState to: ${value}`);
|
|
205
|
+
if (value !==
|
|
206
|
+
this.platform.Characteristic.TargetHumidifierDehumidifierState
|
|
207
|
+
.DEHUMIDIFIER) {
|
|
208
|
+
throw new Error(`Device ${this.device.name} (${this.device.id}) can only be a DeHumidifier, illegal value: ${value}`);
|
|
209
|
+
}
|
|
210
|
+
}
|
|
211
|
+
// Handle requests to get the current value of the "RelativeHumidity" characteristic
|
|
212
|
+
async getCurrentRelativeHumidity() {
|
|
213
|
+
this.platform.log.debug(`[${this.device.name}] GET CurrentRelativeHumidity, value: ${this.device.attributes.CURRENT_HUMIDITY}`);
|
|
214
|
+
return this.device.attributes.CURRENT_HUMIDITY;
|
|
215
|
+
}
|
|
216
|
+
// Handle requests to get the Relative value of the "HumidityDehumidifierThreshold" characteristic
|
|
217
|
+
async getRelativeHumidityDehumidifierThreshold() {
|
|
218
|
+
this.platform.log.debug(`[${this.device.name}] GET RelativeHumidityDehumidifierThreshold, value: ${this.device.attributes.TARGET_HUMIDITY}`);
|
|
219
|
+
return this.device.attributes.TARGET_HUMIDITY;
|
|
220
|
+
}
|
|
221
|
+
// Handle requests to set the Relative value of the "HumidityDehumidifierThreshold" characteristic
|
|
222
|
+
async setRelativeHumidityDehumidifierThreshold(value) {
|
|
223
|
+
let RequestedHumidity = value;
|
|
224
|
+
// valid humidity has to be between min and max values
|
|
225
|
+
RequestedHumidity =
|
|
226
|
+
RequestedHumidity < this.device.MIN_HUMIDITY
|
|
227
|
+
? this.device.MIN_HUMIDITY
|
|
228
|
+
: RequestedHumidity > this.device.MAX_HUMIDITY
|
|
229
|
+
? this.device.MAX_HUMIDITY
|
|
230
|
+
: RequestedHumidity;
|
|
231
|
+
this.platform.log.debug(`[${this.device.name}] SET RelativeHumidityDehumidifierThreshold to: ${RequestedHumidity} (${value})`);
|
|
232
|
+
await this.device.set_attribute({ TARGET_HUMIDITY: RequestedHumidity });
|
|
233
|
+
// Update HomeKit in case we adjusted the value outside of min and max values
|
|
234
|
+
if (RequestedHumidity !== value) {
|
|
235
|
+
// We had to adjust the requested value to within permitted range... Update homekit to actual value set.
|
|
236
|
+
// Calling updateCharacteristic within set handler seems to fail, new value is not accepted. Workaround is
|
|
237
|
+
// to request the update after short delay (say 50ms) to allow homebridge/homekit to complete the set handler.
|
|
238
|
+
setTimeout(() => {
|
|
239
|
+
this.service.updateCharacteristic(this.platform.Characteristic.RelativeHumidityDehumidifierThreshold, RequestedHumidity);
|
|
240
|
+
}, 50);
|
|
241
|
+
}
|
|
242
|
+
}
|
|
243
|
+
// Handle requests to get the current value of the "RotationSpeed" characteristic
|
|
244
|
+
async getRotationSpeed() {
|
|
245
|
+
this.platform.log.debug(`[${this.device.name}] GET RotationSpeed, value: ${this.device.attributes.FAN_SPEED}`);
|
|
246
|
+
return this.device.attributes.FAN_SPEED;
|
|
247
|
+
}
|
|
248
|
+
// Handle requests to set the "RotationSpeed" characteristic
|
|
249
|
+
async setRotationSpeed(value) {
|
|
250
|
+
let speed = value;
|
|
251
|
+
speed = speed <= 40 ? 40 : speed > 40 && speed <= 60 ? 60 : 80;
|
|
252
|
+
this.platform.log.debug(`[${this.device.name}] SET RotationSpeed to: ${speed} (${value})`);
|
|
253
|
+
await this.device.set_attribute({ FAN_SPEED: speed });
|
|
254
|
+
if (speed !== value) {
|
|
255
|
+
// We had to adjust the requested value to within permitted range... Update homekit to actual value set.
|
|
256
|
+
// Calling updateCharacteristic within set handler seems to fail, new value is not accepted. Workaround is
|
|
257
|
+
// to request the update after short delay (say 50ms) to allow homebridge/homekit to complete the set handler.
|
|
258
|
+
setTimeout(() => {
|
|
259
|
+
this.service.updateCharacteristic(this.platform.Characteristic.RotationSpeed, speed);
|
|
260
|
+
}, 50);
|
|
261
|
+
}
|
|
262
|
+
}
|
|
263
|
+
// Handle requests to get the current value of the "WaterLevel" characteristic
|
|
264
|
+
async getWaterLevel() {
|
|
265
|
+
this.platform.log.debug(`[${this.device.name}] GET WaterLevel, value: ${this.device.attributes.TANK_LEVEL}`);
|
|
266
|
+
return this.device.attributes.TANK_LEVEL;
|
|
267
|
+
}
|
|
268
|
+
// Handle requests to get the current value of the "swingMode" characteristic
|
|
269
|
+
async getSwingMode() {
|
|
270
|
+
this.platform.log.debug(`[${this.device.name}] GET SwingMode, value: ${this.device.attributes.SWING}`);
|
|
271
|
+
return this.device.attributes.SWING
|
|
272
|
+
? this.platform.Characteristic.SwingMode.SWING_ENABLED
|
|
273
|
+
: this.platform.Characteristic.SwingMode.SWING_DISABLED;
|
|
274
|
+
}
|
|
275
|
+
// Handle requests to set the "swingMode" characteristic
|
|
276
|
+
async setSwingMode(value) {
|
|
277
|
+
this.platform.log.debug(`[${this.device.name}] SET SwingMode to: ${value}`);
|
|
278
|
+
await this.device.set_attribute({ SWING: !!value });
|
|
279
|
+
}
|
|
280
|
+
// Handle requests to get the current value of the "LockPhysicalControls" characteristic
|
|
281
|
+
async getChildLockMode() {
|
|
282
|
+
this.platform.log.debug(`[${this.device.name}] GET LockPhysicalControls, value: ${this.device.attributes.SWING}`);
|
|
283
|
+
return this.device.attributes.CHILD_LOCK
|
|
284
|
+
? this.platform.Characteristic.LockPhysicalControls.CONTROL_LOCK_ENABLED
|
|
285
|
+
: this.platform.Characteristic.LockPhysicalControls.CONTROL_LOCK_DISABLED;
|
|
286
|
+
}
|
|
287
|
+
// Handle requests to set the "LockPhysicalControls" characteristic
|
|
288
|
+
async setChildLockMode(value) {
|
|
289
|
+
this.platform.log.debug(`[${this.device.name}] SET LockPhysicalControls to: ${value}`);
|
|
290
|
+
await this.device.set_attribute({ CHILD_LOCK: !!value });
|
|
291
|
+
}
|
|
292
|
+
}
|
|
293
|
+
exports.default = DehumidifierAccessory;
|
|
294
|
+
//# sourceMappingURL=DehumidifierAccessory.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"DehumidifierAccessory.js","sourceRoot":"","sources":["../../src/accessory/DehumidifierAccessory.ts"],"names":[],"mappings":"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"}
|
|
@@ -1,4 +1,13 @@
|
|
|
1
1
|
/// <reference types="node" />
|
|
2
|
+
/***********************************************************************
|
|
3
|
+
* Midea Cloud access functions
|
|
4
|
+
*
|
|
5
|
+
* Copyright (c) 2023 Kovalovszky Patrik, https://github.com/kovapatrik
|
|
6
|
+
* Portions Copyright (c) 2023 David Kerr, https://github.com/dkerr64
|
|
7
|
+
*
|
|
8
|
+
* With thanks to https://github.com/georgezhao2010/midea_ac_lan
|
|
9
|
+
*
|
|
10
|
+
*/
|
|
2
11
|
import { Logger } from 'homebridge';
|
|
3
12
|
import { CloudSecurity } from './MideaSecurity';
|
|
4
13
|
import { Endianness } from './MideaConstants';
|
|
@@ -17,6 +26,8 @@ export declare abstract class CloudBase<T extends CloudSecurity> {
|
|
|
17
26
|
protected abstract API_URL: string;
|
|
18
27
|
protected access_token?: string;
|
|
19
28
|
protected key?: string;
|
|
29
|
+
private semaphore;
|
|
30
|
+
private loggedIn;
|
|
20
31
|
constructor(account: string, password: string, logger: Logger, security: T);
|
|
21
32
|
protected timestamp(): string;
|
|
22
33
|
apiRequest(endpoint: string, args?: {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"MideaCloud.d.ts","sourceRoot":"","sources":["../../src/core/MideaCloud.ts"],"names":[],"mappings":";AAAA,OAAO,EAAE,MAAM,EAAE,MAAM,YAAY,CAAC;AAKpC,OAAO,
|
|
1
|
+
{"version":3,"file":"MideaCloud.d.ts","sourceRoot":"","sources":["../../src/core/MideaCloud.ts"],"names":[],"mappings":";AAAA;;;;;;;;GAQG;AACH,OAAO,EAAE,MAAM,EAAE,MAAM,YAAY,CAAC;AAKpC,OAAO,EACL,aAAa,EAId,MAAM,iBAAiB,CAAC;AAEzB,OAAO,EAAE,UAAU,EAAE,MAAM,kBAAkB,CAAC;AAG9C,8BAAsB,SAAS,CAAC,CAAC,SAAS,aAAa;IAkBnD,SAAS,CAAC,QAAQ,CAAC,OAAO,EAAE,MAAM;IAClC,SAAS,CAAC,QAAQ,CAAC,QAAQ,EAAE,MAAM;IACnC,SAAS,CAAC,QAAQ,CAAC,MAAM,EAAE,MAAM;IACjC,SAAS,CAAC,QAAQ,CAAC,QAAQ,EAAE,CAAC;IApBhC,SAAS,CAAC,QAAQ,CAAC,WAAW,KAAK;IACnC,SAAS,CAAC,QAAQ,CAAC,MAAM,KAAK;IAC9B,SAAS,CAAC,QAAQ,CAAC,OAAO,cAAc;IAExC,SAAS,CAAC,QAAQ,CAAC,QAAQ,WAAW;IACtC,SAAS,CAAC,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAU;IAC3C,SAAS,CAAC,QAAQ,CAAC,GAAG,EAAE,MAAM,CAAU;IACxC,SAAS,CAAC,QAAQ,CAAC,SAAS,SAAkC;IAE9D,SAAS,CAAC,QAAQ,CAAC,OAAO,EAAE,MAAM,CAAC;IACnC,SAAS,CAAC,YAAY,CAAC,EAAE,MAAM,CAAC;IAChC,SAAS,CAAC,GAAG,CAAC,EAAE,MAAM,CAAC;IAEvB,OAAO,CAAC,SAAS,CAAY;IAC7B,OAAO,CAAC,QAAQ,CAAS;gBAGJ,OAAO,EAAE,MAAM,EACf,QAAQ,EAAE,MAAM,EAChB,MAAM,EAAE,MAAM,EACd,QAAQ,EAAE,CAAC;IAMhC,SAAS,CAAC,SAAS;IAIb,UAAU,CACd,QAAQ,EAAE,MAAM,EAEhB,IAAI,CAAC,EAAE;QAAE,CAAC,GAAG,EAAE,MAAM,GAAG,GAAG,CAAA;KAAE,EAE7B,IAAI,CAAC,EAAE;QAAE,CAAC,GAAG,EAAE,MAAM,GAAG,GAAG,CAAA;KAAE;IAmDzB,UAAU;IAaV,KAAK;IAgDL,QAAQ,CACZ,SAAS,EAAE,MAAM,EACjB,SAAS,EAAE,UAAU,GACpB,OAAO,CAAC,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;CAuB7B;AAmID,MAAM,CAAC,OAAO,OAAO,YAAY;IAC/B,MAAM,CAAC,WAAW,CAChB,OAAO,EAAE,MAAM,EACf,QAAQ,EAAE,MAAM,EAChB,MAAM,EAAE,MAAM,EACd,KAAK,EAAE,MAAM,GACZ,SAAS,CAAC,aAAa,CAAC;CAc5B"}
|
package/dist/core/MideaCloud.js
CHANGED
|
@@ -9,6 +9,7 @@ const luxon_1 = require("luxon");
|
|
|
9
9
|
const axios_1 = __importDefault(require("axios"));
|
|
10
10
|
const MideaSecurity_1 = require("./MideaSecurity");
|
|
11
11
|
const MideaUtils_1 = require("./MideaUtils");
|
|
12
|
+
const semaphore_promise_1 = require("semaphore-promise");
|
|
12
13
|
class CloudBase {
|
|
13
14
|
constructor(account, password, logger, security) {
|
|
14
15
|
this.account = account;
|
|
@@ -22,21 +23,27 @@ class CloudBase {
|
|
|
22
23
|
this.APP_ID = '1010';
|
|
23
24
|
this.SRC = '1010';
|
|
24
25
|
this.DEVICE_ID = (0, crypto_1.randomBytes)(8).toString('hex');
|
|
26
|
+
this.loggedIn = false;
|
|
27
|
+
// Required to serialize access to some cloud functions.
|
|
28
|
+
this.semaphore = new semaphore_promise_1.Semaphore();
|
|
25
29
|
}
|
|
26
30
|
timestamp() {
|
|
27
|
-
return luxon_1.DateTime.
|
|
31
|
+
return luxon_1.DateTime.now().toFormat('yyyyMMddHHmmss');
|
|
28
32
|
}
|
|
33
|
+
async apiRequest(endpoint,
|
|
29
34
|
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
30
|
-
|
|
35
|
+
args,
|
|
36
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
37
|
+
data) {
|
|
31
38
|
if (data === undefined) {
|
|
32
39
|
data = {
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
+
appId: this.APP_ID,
|
|
41
|
+
format: this.FORMAT,
|
|
42
|
+
clientType: this.CLIENT_TYPE,
|
|
43
|
+
language: this.LANGUAGE,
|
|
44
|
+
src: this.SRC,
|
|
45
|
+
stamp: this.timestamp(),
|
|
46
|
+
deviceId: this.DEVICE_ID,
|
|
40
47
|
};
|
|
41
48
|
}
|
|
42
49
|
data = { ...data, ...args };
|
|
@@ -48,10 +55,10 @@ class CloudBase {
|
|
|
48
55
|
const sign = this.security.sign(JSON.stringify(data), random);
|
|
49
56
|
const headers = {
|
|
50
57
|
'Content-Type': 'application/json',
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
58
|
+
secretVersion: '1',
|
|
59
|
+
sign: sign,
|
|
60
|
+
random: random,
|
|
61
|
+
accessToken: this.access_token,
|
|
55
62
|
};
|
|
56
63
|
for (let i = 0; i < 3; i++) {
|
|
57
64
|
try {
|
|
@@ -71,52 +78,74 @@ class CloudBase {
|
|
|
71
78
|
}
|
|
72
79
|
async getLoginId() {
|
|
73
80
|
const response = await this.apiRequest('/v1/user/login/id/get', {
|
|
74
|
-
|
|
81
|
+
loginAccount: this.account,
|
|
75
82
|
});
|
|
76
83
|
if (response) {
|
|
84
|
+
this.logger.info('Logged in to Midea Cloud.');
|
|
77
85
|
return response['loginId'];
|
|
78
86
|
}
|
|
79
87
|
throw new Error('Failed to get login ID.');
|
|
80
88
|
}
|
|
81
89
|
async login() {
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
}
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
90
|
+
// We need to protect against multiple attempts to login, so we only login if not already
|
|
91
|
+
// logged in. Protect this block with a semaphone.
|
|
92
|
+
const releaseSemaphore = await this.semaphore.acquire('Obtain login semaphore');
|
|
93
|
+
try {
|
|
94
|
+
if (this.loggedIn) {
|
|
95
|
+
return;
|
|
96
|
+
}
|
|
97
|
+
// Not logged in so proceed...
|
|
98
|
+
const login_id = await this.getLoginId();
|
|
99
|
+
const response = await this.apiRequest('/mj/user/login', {
|
|
100
|
+
data: {
|
|
101
|
+
appKey: this.APP_KEY,
|
|
102
|
+
platform: this.FORMAT,
|
|
103
|
+
deviceId: this.DEVICE_ID,
|
|
104
|
+
},
|
|
105
|
+
iotData: {
|
|
106
|
+
appId: this.APP_ID,
|
|
107
|
+
clientType: this.CLIENT_TYPE,
|
|
108
|
+
iampwd: this.security.encrpytIAMPassword(login_id, this.password),
|
|
109
|
+
loginAccount: this.account,
|
|
110
|
+
password: this.security.encrpytPassword(login_id, this.password),
|
|
111
|
+
pushToken: (0, crypto_1.randomBytes)(20).toString('base64url'),
|
|
112
|
+
reqId: (0, crypto_1.randomBytes)(16).toString('hex'),
|
|
113
|
+
src: this.SRC,
|
|
114
|
+
stamp: this.timestamp(),
|
|
115
|
+
},
|
|
116
|
+
});
|
|
117
|
+
if (response) {
|
|
118
|
+
this.access_token = response['mdata']['accessToken'];
|
|
119
|
+
if (response['key'] !== undefined) {
|
|
120
|
+
this.key = response['key'];
|
|
121
|
+
}
|
|
122
|
+
this.loggedIn = true;
|
|
123
|
+
}
|
|
124
|
+
else {
|
|
125
|
+
this.loggedIn = false;
|
|
126
|
+
throw new Error('Failed to login.');
|
|
105
127
|
}
|
|
106
128
|
}
|
|
107
|
-
|
|
108
|
-
|
|
129
|
+
catch (e) {
|
|
130
|
+
const msg = e instanceof Error ? e.stack : e;
|
|
131
|
+
throw new Error(`Error in Adding new accessory:\n${msg}`);
|
|
132
|
+
}
|
|
133
|
+
finally {
|
|
134
|
+
releaseSemaphore();
|
|
109
135
|
}
|
|
110
136
|
}
|
|
111
137
|
async getToken(device_id, endianess) {
|
|
112
138
|
const udpid = MideaSecurity_1.CloudSecurity.getUDPID((0, MideaUtils_1.numberToUint8Array)(device_id, 6, endianess));
|
|
113
139
|
const response = await this.apiRequest('/v1/iot/secure/getToken', {
|
|
114
|
-
|
|
140
|
+
udpid: udpid,
|
|
115
141
|
});
|
|
116
142
|
if (response) {
|
|
117
143
|
for (const token of response['tokenlist']) {
|
|
118
144
|
if (token['udpId'] === udpid) {
|
|
119
|
-
return [
|
|
145
|
+
return [
|
|
146
|
+
Buffer.from(token['token'], 'hex'),
|
|
147
|
+
Buffer.from(token['key'], 'hex'),
|
|
148
|
+
];
|
|
120
149
|
}
|
|
121
150
|
}
|
|
122
151
|
}
|
|
@@ -139,31 +168,24 @@ class MeijuCloud extends CloudBase {
|
|
|
139
168
|
this.API_URL = 'https://mp-prod.smartmidea.net/mas/v5/app/proxy?alias=';
|
|
140
169
|
}
|
|
141
170
|
}
|
|
142
|
-
class
|
|
143
|
-
constructor(account, password, logger) {
|
|
144
|
-
super(account, password, logger,
|
|
145
|
-
this.API_URL = 'https://mapp.appsmb.com';
|
|
146
|
-
this.APP_ID = '1017';
|
|
147
|
-
this.SRC = '1017';
|
|
148
|
-
}
|
|
149
|
-
}
|
|
150
|
-
class MideaAirCloud extends CloudBase {
|
|
151
|
-
constructor(account, password, logger) {
|
|
152
|
-
super(account, password, logger, new MideaSecurity_1.MideaAirSecurity('ff0cf6f5f0c3471de36341cab3f7a9af', undefined));
|
|
171
|
+
class UnProxiedCloudBase extends CloudBase {
|
|
172
|
+
constructor(account, password, logger, security) {
|
|
173
|
+
super(account, password, logger, security);
|
|
153
174
|
this.API_URL = 'https://mapp.appsmb.com';
|
|
154
|
-
this.APP_ID = '1117';
|
|
155
|
-
this.SRC = '17';
|
|
156
175
|
}
|
|
176
|
+
async apiRequest(endpoint,
|
|
157
177
|
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
158
|
-
|
|
178
|
+
args,
|
|
179
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
180
|
+
data) {
|
|
159
181
|
if (data === undefined) {
|
|
160
182
|
data = {
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
|
|
183
|
+
appId: this.APP_ID,
|
|
184
|
+
format: this.FORMAT,
|
|
185
|
+
clientType: this.CLIENT_TYPE,
|
|
186
|
+
language: this.LANGUAGE,
|
|
187
|
+
src: this.SRC,
|
|
188
|
+
stamp: this.timestamp(),
|
|
167
189
|
};
|
|
168
190
|
}
|
|
169
191
|
data = { ...data, ...args };
|
|
@@ -172,11 +194,16 @@ class MideaAirCloud extends CloudBase {
|
|
|
172
194
|
}
|
|
173
195
|
const url = `${this.API_URL}${endpoint}`;
|
|
174
196
|
const queryParams = new URLSearchParams(data);
|
|
197
|
+
queryParams.sort();
|
|
175
198
|
data['sign'] = this.security.sign(url, queryParams.toString());
|
|
199
|
+
const headers = {
|
|
200
|
+
'Content-Type': 'application/x-www-form-urlencoded',
|
|
201
|
+
};
|
|
176
202
|
for (let i = 0; i < 3; i++) {
|
|
177
203
|
try {
|
|
178
|
-
const response = await axios_1.default.post(url, data);
|
|
179
|
-
if (response.data['errorCode'] !== undefined &&
|
|
204
|
+
const response = await axios_1.default.post(url, data, { headers: headers });
|
|
205
|
+
if (response.data['errorCode'] !== undefined &&
|
|
206
|
+
Number.parseInt(response.data['errorCode']) === 0 &&
|
|
180
207
|
response.data['result'] !== undefined) {
|
|
181
208
|
return response.data['result'];
|
|
182
209
|
}
|
|
@@ -190,8 +217,8 @@ class MideaAirCloud extends CloudBase {
|
|
|
190
217
|
async login() {
|
|
191
218
|
const login_id = await this.getLoginId();
|
|
192
219
|
const response = await this.apiRequest('/v1/user/login', {
|
|
193
|
-
|
|
194
|
-
|
|
220
|
+
loginAccount: this.account,
|
|
221
|
+
password: this.security.encrpytPassword(login_id, this.password),
|
|
195
222
|
});
|
|
196
223
|
if (response) {
|
|
197
224
|
this.access_token = response['accessToken'];
|
|
@@ -202,6 +229,20 @@ class MideaAirCloud extends CloudBase {
|
|
|
202
229
|
}
|
|
203
230
|
}
|
|
204
231
|
}
|
|
232
|
+
class NetHomePlusCloud extends UnProxiedCloudBase {
|
|
233
|
+
constructor(account, password, logger) {
|
|
234
|
+
super(account, password, logger, new MideaSecurity_1.NetHomePlusSecurity('3742e9e5842d4ad59c2db887e12449f9'));
|
|
235
|
+
this.APP_ID = '1017';
|
|
236
|
+
this.SRC = '1017';
|
|
237
|
+
}
|
|
238
|
+
}
|
|
239
|
+
class MideaAirCloud extends UnProxiedCloudBase {
|
|
240
|
+
constructor(account, password, logger) {
|
|
241
|
+
super(account, password, logger, new MideaSecurity_1.MideaAirSecurity('ff0cf6f5f0c3471de36341cab3f7a9af'));
|
|
242
|
+
this.APP_ID = '1117';
|
|
243
|
+
this.SRC = '17';
|
|
244
|
+
}
|
|
245
|
+
}
|
|
205
246
|
class CloudFactory {
|
|
206
247
|
static createCloud(account, password, logger, cloud) {
|
|
207
248
|
switch (cloud) {
|