homebridge-melcloud-control 4.3.5-beta.5 → 4.3.5-beta.7

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/index.js CHANGED
@@ -179,15 +179,15 @@ class MelCloudPlatform {
179
179
  let configuredDevice;
180
180
  switch (deviceType) {
181
181
  case 0: //ATA
182
- configuredDevice = new DeviceAta(api, account, device, devicesFile, defaultTempsFile, accountInfo, accountFile, devicesList.WebSocket, melcloud);
182
+ configuredDevice = new DeviceAta(api, account, device, devicesFile, defaultTempsFile, accountInfo, accountFile, melcloud);
183
183
  break;
184
184
  case 1: //ATW
185
- configuredDevice = new DeviceAtw(api, account, device, devicesFile, defaultTempsFile, accountInfo, accountFile, devicesList.WebSocket);
185
+ configuredDevice = new DeviceAtw(api, account, device, devicesFile, defaultTempsFile, accountInfo, accountFile, melcloud);
186
186
  break;
187
187
  case 2:
188
188
  break;
189
189
  case 3: //ERV
190
- configuredDevice = new DeviceErv(api, account, device, devicesFile, defaultTempsFile, accountInfo, accountFile, devicesList.WebSocket);
190
+ configuredDevice = new DeviceErv(api, account, device, devicesFile, defaultTempsFile, accountInfo, accountFile, melcloud);
191
191
  break;
192
192
  default:
193
193
  if (logLevel.warn) log.warn(`${accountName}, ${deviceTypeString}, ${deviceName}, unknown device: ${deviceType}.`);
@@ -205,9 +205,6 @@ class MelCloudPlatform {
205
205
  if (accessory) {
206
206
  api.publishExternalAccessories(PluginName, [accessory]);
207
207
  if (logLevel.success) log.success(`${accountName}, ${deviceTypeString}, ${deviceName}, Published as external accessory.`);
208
-
209
- //start impulse generators for device
210
- await configuredDevice.startStopImpulseGenerator(true, [{ name: 'checkState', sampling: deviceRefreshInterval }]);
211
208
  }
212
209
  }
213
210
 
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "displayName": "MELCloud Control",
3
3
  "name": "homebridge-melcloud-control",
4
- "version": "4.3.5-beta.5",
4
+ "version": "4.3.5-beta.7",
5
5
  "description": "Homebridge plugin to control Mitsubishi Air Conditioner, Heat Pump and Energy Recovery Ventilation.",
6
6
  "license": "MIT",
7
7
  "author": "grzegorz914",
package/src/deviceata.js CHANGED
@@ -7,7 +7,7 @@ import { TemperatureDisplayUnits, AirConditioner } from './constants.js';
7
7
  let Accessory, Characteristic, Service, Categories, AccessoryUUID;
8
8
 
9
9
  class DeviceAta extends EventEmitter {
10
- constructor(api, account, device, devicesFile, defaultTempsFile, accountInfo, accountFile, webSocket, melcloud) {
10
+ constructor(api, account, device, devicesFile, defaultTempsFile, accountInfo, accountFile, melcloud) {
11
11
  super();
12
12
 
13
13
  Accessory = api.platformAccessory;
@@ -18,7 +18,6 @@ class DeviceAta extends EventEmitter {
18
18
 
19
19
  //account config
20
20
  this.melcloud = melcloud;
21
- this.webSocket = webSocket;
22
21
  this.account = account;
23
22
  this.accountType = account.type;
24
23
  this.accountName = account.name;
@@ -109,16 +108,6 @@ class DeviceAta extends EventEmitter {
109
108
  this.accessory = {};
110
109
  };
111
110
 
112
- async startStopImpulseGenerator(state, timers = []) {
113
- try {
114
- //start impulse generator
115
- await this.melCloudAta.impulseGenerator.state(state, timers)
116
- return true;
117
- } catch (error) {
118
- throw new Error(`Impulse generator start error: ${error}`);
119
- }
120
- }
121
-
122
111
  async externalIntegrations() {
123
112
  //RESTFul server
124
113
  const restFulEnabled = this.restFul.enable || false;
@@ -1332,7 +1321,7 @@ class DeviceAta extends EventEmitter {
1332
1321
  async start() {
1333
1322
  try {
1334
1323
  //melcloud device
1335
- this.melCloudAta = new MelCloudAta(this.account, this.device, this.devicesFile, this.defaultTempsFile, this.accountFile, this.webSocket, this.melcloud )
1324
+ this.melCloudAta = new MelCloudAta(this.account, this.device, this.devicesFile, this.defaultTempsFile, this.accountFile, this.melcloud)
1336
1325
  .on('deviceInfo', (modelIndoor, modelOutdoor, serialNumber, firmwareAppVersion) => {
1337
1326
  if (this.logDeviceInfo && this.displayDeviceInfo) {
1338
1327
  this.emit('devInfo', `---- ${this.deviceTypeString}: ${this.deviceName} ----`);
package/src/deviceatw.js CHANGED
@@ -7,7 +7,7 @@ import { TemperatureDisplayUnits, HeatPump } from './constants.js';
7
7
  let Accessory, Characteristic, Service, Categories, AccessoryUUID;
8
8
 
9
9
  class DeviceAtw extends EventEmitter {
10
- constructor(api, account, device, devicesFile, defaultTempsFile, accountInfo, accountFile, webSocket) {
10
+ constructor(api, account, device, devicesFile, defaultTempsFile, accountInfo, accountFile, melcloud) {
11
11
  super();
12
12
 
13
13
  Accessory = api.platformAccessory;
@@ -17,7 +17,7 @@ class DeviceAtw extends EventEmitter {
17
17
  AccessoryUUID = api.hap.uuid;
18
18
 
19
19
  //account config
20
- this.webSocket = webSocket;
20
+ this.melcloud = melcloud;
21
21
  this.account = account;
22
22
  this.accountType = account.type;
23
23
  this.accountName = account.name;
@@ -112,17 +112,6 @@ class DeviceAtw extends EventEmitter {
112
112
  this.accessory = {};
113
113
  };
114
114
 
115
- async startStopImpulseGenerator(state, timers = []) {
116
- try {
117
- //start impulse generator
118
- await this.melCloudAtw.impulseGenerator.state(state, timers)
119
- return true;
120
- } catch (error) {
121
- throw new Error(`Impulse generator start error: ${error}`);
122
- }
123
- }
124
-
125
-
126
115
  async externalIntegrations() {
127
116
  //RESTFul server
128
117
  const restFulEnabled = this.restFul.enable || false;
@@ -1578,7 +1567,7 @@ class DeviceAtw extends EventEmitter {
1578
1567
  async start() {
1579
1568
  try {
1580
1569
  //melcloud device
1581
- this.melCloudAtw = new MelCloudAtw(this.account, this.device, this.devicesFile, this.defaultTempsFile, this.accountFile, this.webSocket)
1570
+ this.melCloudAtw = new MelCloudAtw(this.account, this.device, this.devicesFile, this.defaultTempsFile, this.accountFile, this.melcloud)
1582
1571
  .on('deviceInfo', (modelIndoor, modelOutdoor, serialNumber, firmwareAppVersion, supportsHotWaterTank, supportsZone2) => {
1583
1572
  if (this.logDeviceInfo && this.displayDeviceInfo) {
1584
1573
  this.emit('devInfo', `---- ${this.deviceTypeString}: ${this.deviceName} ----`);
package/src/deviceerv.js CHANGED
@@ -7,7 +7,7 @@ import { TemperatureDisplayUnits, Ventilation } from './constants.js';
7
7
  let Accessory, Characteristic, Service, Categories, AccessoryUUID;
8
8
 
9
9
  class DeviceErv extends EventEmitter {
10
- constructor(api, account, device, devicesFile, defaultTempsFile, accountInfo, accountFile, webSocket) {
10
+ constructor(api, account, device, devicesFile, defaultTempsFile, accountInfo, accountFile, melcloud) {
11
11
  super();
12
12
 
13
13
  Accessory = api.platformAccessory;
@@ -17,7 +17,7 @@ class DeviceErv extends EventEmitter {
17
17
  AccessoryUUID = api.hap.uuid;
18
18
 
19
19
  //account config
20
- this.webSocket = webSocket;
20
+ this.melcloud = melcloud;
21
21
  this.account = account;
22
22
  this.accountType = account.type;
23
23
  this.accountName = account.name;
@@ -104,16 +104,6 @@ class DeviceErv extends EventEmitter {
104
104
  this.accessory = {};
105
105
  };
106
106
 
107
- async startStopImpulseGenerator(state, timers = []) {
108
- try {
109
- //start impulse generator
110
- await this.melCloudErv.impulseGenerator.state(state, timers)
111
- return true;
112
- } catch (error) {
113
- throw new Error(`Impulse generator start error: ${error}`);
114
- }
115
- }
116
-
117
107
  async externalIntegrations() {
118
108
  //RESTFul server
119
109
  const restFulEnabled = this.restFul.enable || false;
@@ -1131,7 +1121,7 @@ class DeviceErv extends EventEmitter {
1131
1121
  async start() {
1132
1122
  try {
1133
1123
  //melcloud device
1134
- this.melCloudErv = new MelCloudErv(this.account, this.device, this.devicesFile, this.defaultTempsFile, this.accountFile, this.webSocket)
1124
+ this.melCloudErv = new MelCloudErv(this.account, this.device, this.devicesFile, this.defaultTempsFile, this.accountFile, this.melcloud)
1135
1125
  .on('deviceInfo', (modelIndoor, modelOutdoor, serialNumber, firmwareAppVersion) => {
1136
1126
  if (this.logDeviceInfo && this.displayDeviceInfo) {
1137
1127
  this.emit('devInfo', `---- ${this.deviceTypeString}: ${this.deviceName} ----`);
package/src/melcloud.js CHANGED
@@ -110,12 +110,11 @@ class MelCloud extends EventEmitter {
110
110
  devicesList.Info = `Found ${devicesCount} devices`;
111
111
  devicesList.Devices = devices;
112
112
  devicesList.Headers = this.headers;
113
+ this.emit('devicesList', devicesList);
113
114
 
114
115
  await this.functions.saveData(this.devicesFile, devicesList);
115
116
  if (this.logDebug) this.emit('debug', `${devicesCount} devices saved`);
116
117
 
117
- this.emit('devicesList', devicesList);
118
-
119
118
  return devicesList;
120
119
  } catch (error) {
121
120
  throw new Error(`Check devices list error: ${error.message}`);
@@ -1,11 +1,10 @@
1
1
  import axios from 'axios';
2
2
  import EventEmitter from 'events';
3
- import ImpulseGenerator from './impulsegenerator.js';
4
3
  import Functions from './functions.js';
5
4
  import { ApiUrls, ApiUrlsHome, AirConditioner } from './constants.js';
6
5
 
7
6
  class MelCloudAta extends EventEmitter {
8
- constructor(account, device, devicesFile, defaultTempsFile, accountFile, webSocket, melcloud) {
7
+ constructor(account, device, devicesFile, defaultTempsFile, accountFile, melcloud) {
9
8
  super();
10
9
  this.accountType = account.type;
11
10
  this.logSuccess = account.log?.success;
@@ -18,7 +17,6 @@ class MelCloudAta extends EventEmitter {
18
17
  this.devicesFile = devicesFile;
19
18
  this.defaultTempsFile = defaultTempsFile;
20
19
  this.accountFile = accountFile;
21
- this.webSocket = webSocket;
22
20
  this.functions = new Functions(this.logWarn, this.logError, this.logDebug)
23
21
  .on('warn', warn => this.emit('warn', warn))
24
22
  .on('error', error => this.emit('error', error))
@@ -27,7 +25,6 @@ class MelCloudAta extends EventEmitter {
27
25
  //set default values
28
26
  this.deviceData = {};
29
27
  this.headers = {};
30
- this.firstRun = true;
31
28
 
32
29
  let deviceData = null;
33
30
  melcloud.on('devicesList', async (devicesData) => {
@@ -43,7 +40,7 @@ class MelCloudAta extends EventEmitter {
43
40
  //web cocket message
44
41
  if (this.accountType === 'melcloudhome') {
45
42
  try {
46
- webSocket.on('message', async (message) => {
43
+ melcloud.webSocket.on('message', async (message) => {
47
44
  const parsedMessage = JSON.parse(message);
48
45
  const stringifyMessage = JSON.stringify(parsedMessage, null, 2);
49
46
  if (parsedMessage.message === 'Forbidden') return;
@@ -105,29 +102,6 @@ class MelCloudAta extends EventEmitter {
105
102
  if (this.logError) this.emit('error', `Socket connection failed: ${error}`);
106
103
  }
107
104
  }
108
-
109
- //lock flag
110
- this.locks = false;
111
- this.impulseGenerator = new ImpulseGenerator()
112
- .on('checkState', () => this.handleWithLock(async () => {
113
- //await this.checkState();
114
- }))
115
- .on('state', (state) => {
116
- this.emit(state ? 'success' : 'warn', `Impulse generator ${state ? 'started' : 'stopped'}`);
117
- });
118
- }
119
-
120
- async handleWithLock(fn) {
121
- if (this.locks) return;
122
-
123
- this.locks = true;
124
- try {
125
- await fn();
126
- } catch (error) {
127
- this.emit('error', `Inpulse generator error: ${error}`);
128
- } finally {
129
- this.locks = false;
130
- }
131
105
  }
132
106
 
133
107
  async updateState(deviceData) {
@@ -203,95 +177,6 @@ class MelCloudAta extends EventEmitter {
203
177
  };
204
178
  };
205
179
 
206
- async checkState() {
207
- try {
208
- //read device info from file
209
- const devicesData = await this.functions.readData(this.devicesFile, true);
210
- if (!devicesData) return;
211
-
212
- this.headers = devicesData.Headers;
213
- const deviceData = devicesData.Devices.find(device => device.DeviceID === this.deviceId);
214
- if (!deviceData) return;
215
- deviceData.Scenes = devicesData.Scenes ?? [];
216
-
217
- //web cocket message
218
- if (this.accountType === 'melcloudhome' && !this.firstRun) {
219
- this.firstRun = false;
220
-
221
- try {
222
- this.webSocket.on('message', async (message) => {
223
- const parsedMessage = JSON.parse(message);
224
- const stringifyMessage = JSON.stringify(parsedMessage, null, 2);
225
- if (parsedMessage.message === 'Forbidden') return;
226
-
227
- const messageData = parsedMessage?.[0]?.Data;
228
- if (!messageData) return;
229
-
230
- let updateState = false;
231
- const unitId = messageData?.id;
232
- switch (unitId) {
233
- case this.deviceId:
234
- if (!this.logDebug) this.emit('debug', `Incoming message: ${stringifyMessage}`);
235
- const messageType = parsedMessage[0].messageType;
236
- const settings = this.functions.parseArrayNameValue(messageData.settings);
237
- switch (messageType) {
238
- case 'unitStateChanged':
239
-
240
- //update values
241
- for (const [key, value] of Object.entries(settings)) {
242
- if (!this.functions.isValidValue(value)) continue;
243
-
244
- //update holiday mode
245
- if (key === 'HolidayMode') {
246
- deviceData.HolidayMode.Enabled = value;
247
- continue;
248
- }
249
-
250
- //update device settings
251
- if (key in deviceData.Device) {
252
- deviceData.Device[key] = value;
253
- }
254
- }
255
- updateState = true;
256
- break;
257
- case 'unitHolidayModeTriggered':
258
- deviceData.Device.Power = settings.Power;
259
- deviceData.HolidayMode.Enabled = settings.HolidayMode;
260
- deviceData.HolidayMode.Active = messageData.active;
261
- updateState = true;
262
- break;
263
- case 'unitWifiSignalChanged':
264
- deviceData.Rssi = messageData.rssi;
265
- updateState = true;
266
- break;
267
- default:
268
- if (this.logDebug) this.emit('debug', `Unit ${unitId}, received unknown message type: ${stringifyMessage}`);
269
- return;
270
- }
271
- break;
272
- default:
273
- if (this.logDebug) this.emit('debug', `Incoming unknown unit id: ${stringifyMessage}`);
274
- return;
275
- }
276
-
277
- //update state
278
- if (updateState) await this.updateState(deviceData);
279
- });
280
- } catch (error) {
281
- if (this.logError) this.emit('error', `Socket connection failed: ${error}`);
282
- this.cleanupSocket();
283
- }
284
- }
285
-
286
- //update state
287
- await this.updateState(deviceData);
288
-
289
- return true;
290
- } catch (error) {
291
- throw new Error(`Check state error: ${error.message}`);
292
- };
293
- };
294
-
295
180
  async send(accountType, displayType, deviceData, flag, flagData) {
296
181
  try {
297
182
  let method = null
@@ -343,7 +228,7 @@ class MelCloudAta extends EventEmitter {
343
228
  headers: headers,
344
229
  data: payload
345
230
  });
346
- this.updateData(deviceData, updateState);
231
+
347
232
  return true;
348
233
  case "melcloudhome":
349
234
  switch (flag) {
@@ -434,7 +319,6 @@ class MelCloudAta extends EventEmitter {
434
319
  data: payload
435
320
  });
436
321
 
437
- this.updateData(deviceData, updateState);
438
322
  return true;
439
323
  default:
440
324
  return;
@@ -444,14 +328,5 @@ class MelCloudAta extends EventEmitter {
444
328
  throw new Error(`Send data error: ${error.message}`);
445
329
  }
446
330
  }
447
-
448
- updateData(deviceData, updateState = true) {
449
- this.locks = true;
450
- if (updateState) this.emit('deviceState', deviceData);
451
-
452
- setTimeout(() => {
453
- this.locks = false
454
- }, 5000);
455
- }
456
331
  };
457
332
  export default MelCloudAta;
@@ -1,12 +1,10 @@
1
- import WebSocket from 'ws';
2
1
  import axios from 'axios';
3
2
  import EventEmitter from 'events';
4
- import ImpulseGenerator from './impulsegenerator.js';
5
3
  import Functions from './functions.js';
6
4
  import { ApiUrls, ApiUrlsHome, HeatPump } from './constants.js';
7
5
 
8
6
  class MelCloudAtw extends EventEmitter {
9
- constructor(account, device, devicesFile, defaultTempsFile, accountFile, webSocket) {
7
+ constructor(account, device, devicesFile, defaultTempsFile, accountFile, melcloud) {
10
8
  super();
11
9
  this.accountType = account.type;
12
10
  this.logSuccess = account.log?.success;
@@ -27,44 +25,68 @@ class MelCloudAtw extends EventEmitter {
27
25
  //set default values
28
26
  this.deviceData = {};
29
27
  this.headers = {};
30
- this.firstRun = true;
31
28
 
32
- //lock flag
33
- this.locks = false;
34
- this.impulseGenerator = new ImpulseGenerator()
35
- .on('checkState', () => this.handleWithLock(async () => {
36
- await this.checkState();
37
- }))
38
- .on('state', (state) => {
39
- this.emit(state ? 'success' : 'warn', `Impulse generator ${state ? 'started' : 'stopped'}`);
40
- });
41
- }
42
-
43
- async handleWithLock(fn) {
44
- if (this.locks) return;
45
-
46
- this.locks = true;
47
- try {
48
- await fn();
49
- } catch (error) {
50
- this.emit('error', `Inpulse generator error: ${error}`);
51
- } finally {
52
- this.locks = false;
53
- }
54
- }
29
+ let deviceData = null;
30
+ melcloud.on('devicesList', async (devicesData) => {
31
+ this.headers = devicesData.Headers;
32
+ deviceData = devicesData.Devices.find(device => device.DeviceID === this.deviceId);
33
+ if (!deviceData) return;
34
+ deviceData.Scenes = devicesData.Scenes ?? [];
55
35
 
56
- cleanupSocket() {
57
- if (this.heartbeat) {
58
- clearInterval(this.heartbeat);
59
- this.heartbeat = null;
60
- }
36
+ //update state
37
+ await this.updateState(deviceData);
38
+ });
39
+
40
+ ///web cocket message
41
+ if (this.accountType === 'melcloudhome') {
42
+ try {
43
+ melcloud.webSocket.on('message', async (message) => {
44
+ const parsedMessage = JSON.parse(message);
45
+ const stringifyMessage = JSON.stringify(parsedMessage, null, 2);
46
+ if (this.logDebug) this.emit('debug', `Incoming message: ${stringifyMessage}`);
47
+ if (parsedMessage.message === 'Forbidden') return;
48
+
49
+ const messageData = parsedMessage?.[0]?.Data;
50
+ if (!messageData || !deviceData) return;
51
+
52
+ let updateState = false;
53
+ const unitId = messageData?.id;
54
+ switch (unitId) {
55
+ case this.deviceId:
56
+ const messageType = parsedMessage[0].messageType;
57
+ switch (messageType) {
58
+ case 'unitStateChanged':
59
+ const settings = Object.fromEntries(
60
+ messageData.settings.map(({ name, value }) => {
61
+ let parsedValue = this.functions.convertValue(value);
62
+ return [name, parsedValue];
63
+ })
64
+ );
65
+ Object.assign(deviceData.Device, settings);
66
+ updateState = true;
67
+ break;
68
+ case 'unitWifiSignalChanged':
69
+ deviceData.Rssi = messageData.rssi;
70
+ updateState = true;
71
+ break;
72
+ default:
73
+ if (this.logDebug) this.emit('debug', `Unit ${unitId}, received unknown message type: ${stringifyMessage}`);
74
+ return;
75
+ }
76
+ break;
77
+ default:
78
+ if (this.logDebug) this.emit('debug', `Incoming unknown unit id: ${stringifyMessage}`);
79
+ return;
80
+ }
61
81
 
62
- if (this.socket) {
63
- try { this.socket.close(); } catch { }
64
- this.socket = null;
82
+ //update state
83
+ if (updateState) await this.updateState(deviceData);
84
+ });
85
+ } catch (error) {
86
+ if (this.logError) this.emit('error', `Socket connection failed: ${error}`);
87
+ this.cleanupSocket();
88
+ }
65
89
  }
66
-
67
- this.socketConnected = false;
68
90
  }
69
91
 
70
92
  async updateState(deviceData) {
@@ -134,79 +156,6 @@ class MelCloudAtw extends EventEmitter {
134
156
  };
135
157
  };
136
158
 
137
- async checkState() {
138
- try {
139
- //read device info from file
140
- const devicesData = await this.functions.readData(this.devicesFile, true);
141
- if (!devicesData) return;
142
-
143
- this.headers = devicesData.Headers;
144
- const deviceData = devicesData.Devices.find(device => device.DeviceID === this.deviceId);
145
- if (!deviceData) return;
146
- deviceData.Scenes = devicesData.Scenes ?? [];
147
-
148
- ///web cocket message
149
- if (this.accountType === 'melcloudhome' && !this.firstRun) {
150
- this.firstRun = false;
151
-
152
- try {
153
- this.webSocket.on('message', async (message) => {
154
- const parsedMessage = JSON.parse(message);
155
- const stringifyMessage = JSON.stringify(parsedMessage, null, 2);
156
- if (this.logDebug) this.emit('debug', `Incoming message: ${stringifyMessage}`);
157
- if (parsedMessage.message === 'Forbidden') return;
158
-
159
- const messageData = parsedMessage?.[0]?.Data;
160
- if (!messageData) return;
161
-
162
- let updateState = false;
163
- const unitId = messageData?.id;
164
- switch (unitId) {
165
- case this.deviceId:
166
- const messageType = parsedMessage[0].messageType;
167
- switch (messageType) {
168
- case 'unitStateChanged':
169
- const settings = Object.fromEntries(
170
- messageData.settings.map(({ name, value }) => {
171
- let parsedValue = this.functions.convertValue(value);
172
- return [name, parsedValue];
173
- })
174
- );
175
- Object.assign(deviceData.Device, settings);
176
- updateState = true;
177
- break;
178
- case 'unitWifiSignalChanged':
179
- deviceData.Rssi = messageData.rssi;
180
- updateState = true;
181
- break;
182
- default:
183
- if (this.logDebug) this.emit('debug', `Unit ${unitId}, received unknown message type: ${stringifyMessage}`);
184
- return;
185
- }
186
- break;
187
- default:
188
- if (this.logDebug) this.emit('debug', `Incoming unknown unit id: ${stringifyMessage}`);
189
- return;
190
- }
191
-
192
- //update state
193
- if (updateState) await this.updateState(deviceData);
194
- });
195
- } catch (error) {
196
- if (this.logError) this.emit('error', `Socket connection failed: ${error}`);
197
- this.cleanupSocket();
198
- }
199
- }
200
-
201
- //update state
202
- await this.updateState(deviceData);
203
-
204
- return true;
205
- } catch (error) {
206
- throw new Error(`Check state error: ${error.message}`);
207
- };
208
- };
209
-
210
159
  async send(accountType, displayType, deviceData, flag, flagData) {
211
160
  try {
212
161
 
@@ -273,7 +222,7 @@ class MelCloudAtw extends EventEmitter {
273
222
  headers: headers,
274
223
  data: payload
275
224
  });
276
- this.updateData(deviceData);
225
+
277
226
  return true;
278
227
  case "melcloudhome":
279
228
  switch (flag) {
@@ -333,7 +282,6 @@ class MelCloudAtw extends EventEmitter {
333
282
  data: payload
334
283
  });
335
284
 
336
- this.updateData(deviceData, updateState);
337
285
  return true;
338
286
  default:
339
287
  return;
@@ -343,14 +291,5 @@ class MelCloudAtw extends EventEmitter {
343
291
  throw new Error(`Send data error: ${error.message}`);
344
292
  }
345
293
  }
346
-
347
- updateData(deviceData, updateState = true) {
348
- this.locks = true;
349
- if (updateState) this.emit('deviceState', deviceData);
350
-
351
- setTimeout(() => {
352
- this.locks = false
353
- }, 5000);
354
- }
355
294
  };
356
295
  export default MelCloudAtw;
@@ -1,12 +1,10 @@
1
- import WebSocket from 'ws';
2
1
  import axios from 'axios';
3
2
  import EventEmitter from 'events';
4
- import ImpulseGenerator from './impulsegenerator.js';
5
3
  import Functions from './functions.js';
6
4
  import { ApiUrls, ApiUrlsHome, Ventilation } from './constants.js';
7
5
 
8
6
  class MelCloudErv extends EventEmitter {
9
- constructor(account, device, devicesFile, defaultTempsFile, accountFile, webSocket) {
7
+ constructor(account, device, devicesFile, defaultTempsFile, accountFile, melcloud) {
10
8
  super();
11
9
  this.accountType = account.type;
12
10
  this.logSuccess = account.log?.success;
@@ -27,41 +25,21 @@ class MelCloudErv extends EventEmitter {
27
25
  //set default values
28
26
  this.deviceData = {};
29
27
  this.headers = {};
30
- this.firstRun = true;
31
28
 
32
- //lock flags
33
- this.locks = false;
34
- this.impulseGenerator = new ImpulseGenerator()
35
- .on('checkState', () => this.handleWithLock(async () => {
36
- await this.checkState();
37
- }))
38
- .on('state', (state) => {
39
- this.emit(state ? 'success' : 'warn', `Impulse generator ${state ? 'started' : 'stopped'}`);
40
- });
41
- }
42
-
43
- async handleWithLock(fn) {
44
- if (this.locks) return;
29
+ let deviceData = null;
30
+ melcloud.on('devicesList', async (devicesData) => {
31
+ this.headers = devicesData.Headers;
32
+ deviceData = devicesData.Devices.find(device => device.DeviceID === this.deviceId);
33
+ if (!deviceData) return;
34
+ deviceData.Scenes = devicesData.Scenes ?? [];
45
35
 
46
- this.locks = true;
47
- try {
48
- await fn();
49
- } catch (error) {
50
- this.emit('error', `Inpulse generator error: ${error}`);
51
- } finally {
52
- this.locks = false;
53
- }
36
+ //update state
37
+ await this.updateState(deviceData);
38
+ }); this.firstRun = true;
54
39
  }
55
40
 
56
- async checkState() {
41
+ async updateState(deviceData) {
57
42
  try {
58
- //read device info from file
59
- const devicesData = await this.functions.readData(this.devicesFile, true);
60
- if (!devicesData) return;
61
-
62
- this.headers = devicesData.Headers;
63
- const deviceData = devicesData.Devices.find(device => device.DeviceID === this.deviceId);
64
- if (!deviceData) return;
65
43
  if (this.accountType === 'melcloudhome') {
66
44
  deviceData.Scenes = devicesData.Scenes ?? [];
67
45
 
@@ -195,7 +173,7 @@ class MelCloudErv extends EventEmitter {
195
173
  headers: headers,
196
174
  data: payload
197
175
  });
198
- this.updateData(deviceData);
176
+
199
177
  return true;
200
178
  case "melcloudhome":
201
179
  switch (flag) {
@@ -258,7 +236,7 @@ class MelCloudErv extends EventEmitter {
258
236
  headers: headers,
259
237
  data: payload
260
238
  });
261
- this.updateData(deviceData, updateState);
239
+
262
240
  return true;
263
241
  default:
264
242
  return;
@@ -268,14 +246,5 @@ class MelCloudErv extends EventEmitter {
268
246
  throw new Error(`Send data error: ${error.message}`);
269
247
  }
270
248
  }
271
-
272
- updateData(deviceData, updateState = true) {
273
- this.locks = true;
274
- if (updateState) this.emit('deviceState', deviceData);
275
-
276
- setTimeout(() => {
277
- this.locks = false
278
- }, 5000);
279
- }
280
249
  };
281
250
  export default MelCloudErv;
@@ -242,13 +242,18 @@ class MelCloudHome extends EventEmitter {
242
242
  // heartbeat
243
243
  this.heartbeat = setInterval(() => {
244
244
  if (this.socket.readyState === this.socket.OPEN) {
245
- if (!this.logDebug) this.emit('debug', `Socket send heartbeat`);
245
+ if (this.logDebug) this.emit('debug', `Socket send heartbeat`);
246
246
  this.socket.ping();
247
247
  }
248
248
  }, 30000);
249
249
  })
250
250
  .on('pong', () => {
251
- if (!this.logDebug) this.emit('debug', `Socket received heartbeat`);
251
+ if (this.logDebug) this.emit('debug', `Socket received heartbeat`);
252
+ })
253
+ .on('message', (message) => {
254
+ const parsedMessage = JSON.parse(message);
255
+ const stringifyMessage = JSON.stringify(parsedMessage, null, 2);
256
+ if (this.logDebug) this.emit('debug', `Incoming message: ${stringifyMessage}`);
252
257
  });
253
258
  } catch (error) {
254
259
  if (this.logError) this.emit('error', `Socket connection failed: ${error}`);
@@ -262,12 +267,11 @@ class MelCloudHome extends EventEmitter {
262
267
  devicesList.Scenes = scenes;
263
268
  devicesList.Headers = this.headers;
264
269
  devicesList.WebSocket = this.socket;
270
+ this.emit('devicesList', devicesList);
265
271
 
266
272
  await this.functions.saveData(this.devicesFile, devicesList);
267
273
  if (this.logDebug) this.emit('debug', `${devicesCount} devices saved`);
268
274
 
269
- this.emit('devicesList', devicesList);
270
-
271
275
  return devicesList;
272
276
  } catch (error) {
273
277
  throw new Error(`Check devices list error: ${error.message}`);