homey-api 3.4.33 → 3.4.35

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.
@@ -176,6 +176,36 @@
176
176
  }
177
177
  }
178
178
  },
179
+ "searchMatterDriver": {
180
+ "path": "/app/search-matter-driver",
181
+ "method": "post",
182
+ "parameters": {
183
+ "language": {
184
+ "in": "query",
185
+ "type": "string"
186
+ },
187
+ "homeyVersion": {
188
+ "type": "string",
189
+ "in": "body"
190
+ },
191
+ "homeyPlatform": {
192
+ "type": "string",
193
+ "in": "body"
194
+ },
195
+ "homeyMinimumSdkVersion": {
196
+ "type": "number",
197
+ "in": "body"
198
+ },
199
+ "productId": {
200
+ "type": "number",
201
+ "in": "body"
202
+ },
203
+ "vendorId": {
204
+ "type": "number",
205
+ "in": "body"
206
+ }
207
+ }
208
+ },
179
209
  "browseApps": {
180
210
  "path": "/app/browse",
181
211
  "method": "get",
@@ -1225,6 +1225,9 @@
1225
1225
  },
1226
1226
  "color": {
1227
1227
  "type": "string"
1228
+ },
1229
+ "note": {
1230
+ "type": "string"
1228
1231
  }
1229
1232
  },
1230
1233
  "x-realtime-bindings": {
@@ -2041,6 +2044,9 @@
2041
2044
  },
2042
2045
  "color": {
2043
2046
  "type": "string"
2047
+ },
2048
+ "note": {
2049
+ "type": "string"
2044
2050
  }
2045
2051
  }
2046
2052
  }
@@ -2633,7 +2639,7 @@
2633
2639
  "uriObj": {
2634
2640
  "type": "object"
2635
2641
  },
2636
- "broken": {
2642
+ "advanced": {
2637
2643
  "type": "boolean"
2638
2644
  },
2639
2645
  "title": {
@@ -2714,7 +2720,7 @@
2714
2720
  "uriObj": {
2715
2721
  "type": "object"
2716
2722
  },
2717
- "broken": {
2723
+ "advanced": {
2718
2724
  "type": "boolean"
2719
2725
  },
2720
2726
  "title": {
@@ -2762,7 +2768,7 @@
2762
2768
  "uriObj": {
2763
2769
  "type": "object"
2764
2770
  },
2765
- "broken": {
2771
+ "advanced": {
2766
2772
  "type": "boolean"
2767
2773
  },
2768
2774
  "title": {
@@ -3316,7 +3322,7 @@
3316
3322
  "path": "/flowcardaction/:uri/:id/run",
3317
3323
  "private": false,
3318
3324
  "scopes": [
3319
- "homey.flow.start"
3325
+ "homey.flow"
3320
3326
  ],
3321
3327
  "parameters": {
3322
3328
  "id": {
@@ -3333,6 +3339,10 @@
3333
3339
  "in": "body",
3334
3340
  "type": "number"
3335
3341
  },
3342
+ "state": {
3343
+ "in": "body",
3344
+ "type": "object"
3345
+ },
3336
3346
  "tokens": {
3337
3347
  "in": "body",
3338
3348
  "type": "object"
@@ -3389,7 +3399,7 @@
3389
3399
  "path": "/flowcardcondition/:uri/:id/run",
3390
3400
  "private": false,
3391
3401
  "scopes": [
3392
- "homey.flow.start"
3402
+ "homey.flow"
3393
3403
  ],
3394
3404
  "parameters": {
3395
3405
  "id": {
@@ -3402,6 +3412,10 @@
3402
3412
  "required": true,
3403
3413
  "type": "string"
3404
3414
  },
3415
+ "state": {
3416
+ "in": "body",
3417
+ "type": "object"
3418
+ },
3405
3419
  "tokens": {
3406
3420
  "in": "body",
3407
3421
  "type": "object"
@@ -3835,6 +3849,14 @@
3835
3849
  "x-homey-readonly": true,
3836
3850
  "type": "string"
3837
3851
  },
3852
+ "titleTrue": {
3853
+ "x-homey-readonly": true,
3854
+ "type": "string"
3855
+ },
3856
+ "titleFalse": {
3857
+ "x-homey-readonly": true,
3858
+ "type": "string"
3859
+ },
3838
3860
  "type": {
3839
3861
  "x-homey-readonly": true,
3840
3862
  "type": "string",
@@ -4287,22 +4309,42 @@
4287
4309
  "name": {
4288
4310
  "type": "string"
4289
4311
  },
4290
- "zone": {
4291
- "type": "string"
4312
+ "preset": {
4313
+ "type": [
4314
+ "string",
4315
+ "null"
4316
+ ]
4292
4317
  },
4293
- "icon": {
4318
+ "zone": {
4294
4319
  "type": "string"
4295
4320
  },
4296
4321
  "devices": {
4297
- "type": "array",
4298
- "items": {
4299
- "type": "object",
4300
- "properties": {
4301
- "id": {
4302
- "type": "string"
4303
- },
4304
- "state": {
4305
- "type": "object"
4322
+ "type": "object",
4323
+ "additionalProperties": false,
4324
+ "patternProperties": {
4325
+ "^[0-9a-f]{8}-[0-9a-f]{4}-[0-5][0-9a-f]{3}-[089ab][0-9a-f]{3}-[0-9a-f]{12}$": {
4326
+ "type": "object",
4327
+ "additionalProperties": false,
4328
+ "properties": {
4329
+ "state": {
4330
+ "type": "object",
4331
+ "additionalProperties": false,
4332
+ "patternProperties": {
4333
+ ".*": {
4334
+ "anyOf": [
4335
+ {
4336
+ "type": "string"
4337
+ },
4338
+ {
4339
+ "type": "boolean"
4340
+ },
4341
+ {
4342
+ "type": "number"
4343
+ }
4344
+ ]
4345
+ }
4346
+ }
4347
+ }
4306
4348
  }
4307
4349
  }
4308
4350
  }
@@ -4318,22 +4360,18 @@
4318
4360
  }
4319
4361
  },
4320
4362
  "operations": {
4321
- "triggerMood": {
4363
+ "setMood": {
4322
4364
  "method": "POST",
4323
- "path": "/mood/:id/trigger",
4365
+ "path": "/mood/:id/set",
4324
4366
  "private": false,
4325
4367
  "scopes": [
4326
- "homey.mood.start"
4368
+ "homey.mood.set"
4327
4369
  ],
4328
4370
  "parameters": {
4329
4371
  "id": {
4330
4372
  "in": "path",
4331
4373
  "required": true,
4332
4374
  "type": "string"
4333
- },
4334
- "state": {
4335
- "in": "body",
4336
- "root": true
4337
4375
  }
4338
4376
  }
4339
4377
  },
@@ -4443,76 +4481,37 @@
4443
4481
  "type": "id",
4444
4482
  "schema": {
4445
4483
  "type": "object",
4484
+ "additionalProperties": false,
4446
4485
  "properties": {
4447
4486
  "id": {
4448
4487
  "type": "string",
4449
- "format": "uuid",
4450
- "x-homey-updateable": false
4488
+ "format": "uuid"
4451
4489
  },
4452
4490
  "name": {
4453
4491
  "type": "string"
4454
4492
  },
4455
- "widgets": {
4456
- "type": "object",
4457
- "additionalProperties": false,
4458
- "patternProperties": {
4459
- "^[0-9a-f]{8}-[0-9a-f]{4}-[0-5][0-9a-f]{3}-[089ab][0-9a-f]{3}-[0-9a-f]{12}$": {
4460
- "type": "object",
4461
- "required": [
4462
- "type",
4463
- "x",
4464
- "y"
4465
- ],
4466
- "properties": {
4467
- "type": {
4468
- "type": "string"
4469
- },
4470
- "x": {
4471
- "type": "number"
4472
- },
4473
- "y": {
4474
- "type": "number"
4475
- },
4476
- "width": {
4477
- "type": "number"
4478
- },
4479
- "height": {
4480
- "type": "number"
4481
- },
4482
- "settings": {
4483
- "type": "object"
4484
- }
4485
- }
4486
- }
4487
- }
4488
- },
4489
- "lines": {
4490
- "type": "object",
4491
- "additionalProperties": false,
4492
- "patternProperties": {
4493
- "^[0-9a-f]{8}-[0-9a-f]{4}-[0-5][0-9a-f]{3}-[089ab][0-9a-f]{3}-[0-9a-f]{12}$": {
4494
- "type": "object",
4495
- "required": [
4496
- "x1",
4497
- "x2",
4498
- "y1",
4499
- "y2"
4500
- ],
4501
- "properties": {
4502
- "x1": {
4503
- "type": "number"
4504
- },
4505
- "x2": {
4506
- "type": "number"
4507
- },
4508
- "y1": {
4509
- "type": "number"
4510
- },
4511
- "y2": {
4512
- "type": "number"
4513
- },
4514
- "settings": {
4515
- "type": "object"
4493
+ "columns": {
4494
+ "type": "array",
4495
+ "items": {
4496
+ "type": "object",
4497
+ "properties": {
4498
+ "id": {
4499
+ "type": "string",
4500
+ "format": "uuid"
4501
+ },
4502
+ "widgets": {
4503
+ "type": "array",
4504
+ "items": {
4505
+ "type": "object",
4506
+ "required": [
4507
+ "id"
4508
+ ],
4509
+ "properties": {
4510
+ "id": {
4511
+ "type": "string",
4512
+ "format": "uuid"
4513
+ }
4514
+ }
4516
4515
  }
4517
4516
  }
4518
4517
  }
@@ -357,7 +357,7 @@ export namespace HomeyAPIV2.ManagerFlow {
357
357
 
358
358
  uriObj: object;
359
359
 
360
- broken: boolean;
360
+ advanced: boolean;
361
361
 
362
362
  title: string;
363
363
 
@@ -388,7 +388,7 @@ export namespace HomeyAPIV2.ManagerFlow {
388
388
 
389
389
  uriObj: object;
390
390
 
391
- broken: boolean;
391
+ advanced: boolean;
392
392
 
393
393
  title: string;
394
394
 
@@ -417,7 +417,7 @@ export namespace HomeyAPIV2.ManagerFlow {
417
417
 
418
418
  uriObj: object;
419
419
 
420
- broken: boolean;
420
+ advanced: boolean;
421
421
 
422
422
  title: string;
423
423
 
@@ -483,6 +483,10 @@ export namespace HomeyAPIV2.ManagerInsights {
483
483
 
484
484
  title: string;
485
485
 
486
+ titleTrue: string;
487
+
488
+ titleFalse: string;
489
+
486
490
  type: string;
487
491
 
488
492
  units: string;
@@ -136,6 +136,8 @@ export namespace HomeyAPIV2.ManagerDashboards {
136
136
 
137
137
  name: string;
138
138
 
139
+ columns: Array<any>;
140
+
139
141
  widgets: object;
140
142
 
141
143
  lines: object;
@@ -369,7 +371,7 @@ export namespace HomeyAPIV2.ManagerFlow {
369
371
 
370
372
  uriObj: object;
371
373
 
372
- broken: boolean;
374
+ advanced: boolean;
373
375
 
374
376
  title: string;
375
377
 
@@ -400,7 +402,7 @@ export namespace HomeyAPIV2.ManagerFlow {
400
402
 
401
403
  uriObj: object;
402
404
 
403
- broken: boolean;
405
+ advanced: boolean;
404
406
 
405
407
  title: string;
406
408
 
@@ -429,7 +431,7 @@ export namespace HomeyAPIV2.ManagerFlow {
429
431
 
430
432
  uriObj: object;
431
433
 
432
- broken: boolean;
434
+ advanced: boolean;
433
435
 
434
436
  title: string;
435
437
 
@@ -495,6 +497,10 @@ export namespace HomeyAPIV2.ManagerInsights {
495
497
 
496
498
  title: string;
497
499
 
500
+ titleTrue: string;
501
+
502
+ titleFalse: string;
503
+
498
504
  type: string;
499
505
 
500
506
  units: string;
@@ -525,11 +531,11 @@ export namespace HomeyAPIV2.ManagerMoods {
525
531
 
526
532
  name: string;
527
533
 
528
- zone: string;
534
+ preset: string | null;
529
535
 
530
- icon: string;
536
+ zone: string;
531
537
 
532
- devices: Array<any>;
538
+ devices: object;
533
539
  }
534
540
  }
535
541
 
@@ -1623,6 +1629,20 @@ export class AthomAppsAPI {
1623
1629
  manufacturerId?: number;
1624
1630
  }): Promise<any>;
1625
1631
 
1632
+ searchMatterDriver(opts: {
1633
+ language?: string;
1634
+
1635
+ homeyVersion?: string;
1636
+
1637
+ homeyPlatform?: string;
1638
+
1639
+ homeyMinimumSdkVersion?: number;
1640
+
1641
+ productId?: number;
1642
+
1643
+ vendorId?: number;
1644
+ }): Promise<any>;
1645
+
1626
1646
  browseApps(opts: {
1627
1647
  query?: string;
1628
1648
 
@@ -1913,6 +1933,20 @@ export class AthomAppsAPI {
1913
1933
  manufacturerId?: number;
1914
1934
  }): Promise<any>;
1915
1935
 
1936
+ searchMatterDriver(opts: {
1937
+ language?: string;
1938
+
1939
+ homeyVersion?: string;
1940
+
1941
+ homeyPlatform?: string;
1942
+
1943
+ homeyMinimumSdkVersion?: number;
1944
+
1945
+ productId?: number;
1946
+
1947
+ vendorId?: number;
1948
+ }): Promise<any>;
1949
+
1916
1950
  browseApps(opts: {
1917
1951
  query?: string;
1918
1952
 
@@ -4819,6 +4853,20 @@ export class AthomAppsAPI {
4819
4853
  manufacturerId?: number;
4820
4854
  }): Promise<any>;
4821
4855
 
4856
+ searchMatterDriver(opts: {
4857
+ language?: string;
4858
+
4859
+ homeyVersion?: string;
4860
+
4861
+ homeyPlatform?: string;
4862
+
4863
+ homeyMinimumSdkVersion?: number;
4864
+
4865
+ productId?: number;
4866
+
4867
+ vendorId?: number;
4868
+ }): Promise<any>;
4869
+
4822
4870
  browseApps(opts: {
4823
4871
  query?: string;
4824
4872
 
@@ -5109,6 +5157,20 @@ export class AthomAppsAPI {
5109
5157
  manufacturerId?: number;
5110
5158
  }): Promise<any>;
5111
5159
 
5160
+ searchMatterDriver(opts: {
5161
+ language?: string;
5162
+
5163
+ homeyVersion?: string;
5164
+
5165
+ homeyPlatform?: string;
5166
+
5167
+ homeyMinimumSdkVersion?: number;
5168
+
5169
+ productId?: number;
5170
+
5171
+ vendorId?: number;
5172
+ }): Promise<any>;
5173
+
5112
5174
  browseApps(opts: {
5113
5175
  query?: string;
5114
5176
 
package/index.browser.js CHANGED
@@ -1,6 +1,3 @@
1
- /* eslint-disable no-undef */
2
- /* eslint-disable global-require */
3
-
4
1
  'use strict';
5
2
 
6
3
  global.AthomAppsAPI = require('./lib/AthomAppsAPI');
package/index.js CHANGED
@@ -1,5 +1,3 @@
1
- /* eslint-disable global-require */
2
-
3
1
  'use strict';
4
2
 
5
3
  module.exports = {};
package/lib/API.js CHANGED
@@ -172,7 +172,6 @@ class API {
172
172
 
173
173
  __debug(...props) {
174
174
  if (!this.__debugEnabled) return;
175
- // eslint-disable-next-line no-console
176
175
  console.log('[homey-api]', `[${this.constructor.name}]`, ...props);
177
176
  }
178
177
 
@@ -1,5 +1,3 @@
1
- /* eslint-disable camelcase */
2
-
3
1
  'use strict';
4
2
 
5
3
  const APIError = require('./APIError');
@@ -1,5 +1,3 @@
1
- /* eslint-disable camelcase */
2
-
3
1
  'use strict';
4
2
 
5
3
  const APIError = require('./APIError');
@@ -17,7 +17,6 @@ class StorageAdapterBrowser extends StorageAdapter {
17
17
  */
18
18
  async get() {
19
19
  try {
20
- // eslint-disable-next-line no-undef
21
20
  return JSON.parse(window.localStorage.getItem(this.constructor.LOCAL_STORAGE_KEY) || '{}');
22
21
  } catch (err) {
23
22
  return {};
@@ -29,7 +28,6 @@ class StorageAdapterBrowser extends StorageAdapter {
29
28
  * @returns {Promise<void>}
30
29
  */
31
30
  async set(value) {
32
- // eslint-disable-next-line no-undef
33
31
  window.localStorage.setItem(this.constructor.LOCAL_STORAGE_KEY, JSON.stringify(value));
34
32
  }
35
33
 
@@ -1,5 +1,3 @@
1
- /* eslint-disable camelcase */
2
-
3
1
  'use strict';
4
2
 
5
3
  /**
@@ -476,11 +476,9 @@ for(const {@link HomeyAPIV2.ManagerDevices.Device device} of Object.values(devic
476
476
 
477
477
  // Remove ?code=... from URL
478
478
  if (Util.isBrowser() && removeCodeFromHistory) {
479
- // eslint-disable-next-line no-undef
480
479
  const url = new URL(window.location.href);
481
480
  url.searchParams.delete('code');
482
481
 
483
- // eslint-disable-next-line no-undef
484
482
  window.history.pushState(undefined, undefined, url.toString());
485
483
  }
486
484
 
@@ -1,5 +1,3 @@
1
- /* eslint-disable camelcase */
2
-
3
1
  'use strict';
4
2
 
5
3
  const APIError = require('../APIError');
@@ -1,5 +1,3 @@
1
- /* eslint-disable camelcase */
2
-
3
1
  'use strict';
4
2
 
5
3
  const HomeyAPIError = require('./HomeyAPIError');
@@ -11,8 +11,8 @@ const HomeyAPI = require('./HomeyAPI');
11
11
  */
12
12
  class HomeyAPIV1 extends HomeyAPI {
13
13
 
14
- constructor({ properties, ...props }) {
15
- super({ properties, ...props });
14
+ constructor({ properties, api, debug }) {
15
+ super({ properties, api, debug });
16
16
 
17
17
  // TODO: Bearer token
18
18
  const { token } = this.__properties;
@@ -1,5 +1,3 @@
1
- /* eslint-disable no-multi-assign */
2
-
3
1
  'use strict';
4
2
 
5
3
  const HomeyAPIV3Manager = require('../HomeyAPIV3/Manager');
@@ -1,12 +1,8 @@
1
- /* eslint-disable no-multi-assign */
2
-
3
1
  'use strict';
4
2
 
5
3
  const EventEmitter = require('../../EventEmitter');
6
4
  const Util = require('../../Util');
7
5
  const HomeyAPIError = require('../HomeyAPIError');
8
-
9
- // eslint-disable-next-line no-unused-vars
10
6
  const Item = require('./Item');
11
7
 
12
8
  /**
@@ -1,5 +1,3 @@
1
- /* eslint-disable no-unused-vars */
2
-
3
1
  'use strict';
4
2
 
5
3
  const Item = require('../Item');
@@ -56,6 +54,7 @@ class AdvancedFlow extends Item {
56
54
  if (typeof card.args === 'object') {
57
55
  for (const arg of Object.values(card.args)) {
58
56
  if (typeof arg !== 'string') continue;
57
+ // eslint-disable-next-line no-unused-vars
59
58
  for (const [tokenMatch, tokenId] of arg.matchAll(/\[\[(.*?)\]\]/g)) {
60
59
  await checkToken(tokenId);
61
60
  }
@@ -87,6 +86,7 @@ class AdvancedFlow extends Item {
87
86
  case 'condition': {
88
87
  try {
89
88
  await managerFlow.getFlowCardConditions(); // Fill the cache
89
+ // eslint-disable-next-line no-unused-vars
90
90
  const conditionCard = await this.manager.getFlowCardCondition({ id: card.id });
91
91
 
92
92
  // Add Error Token
@@ -1,4 +1,3 @@
1
- /* eslint-disable no-unused-vars */
2
1
 
3
2
  'use strict';
4
3
 
@@ -56,6 +55,7 @@ class Flow extends Item {
56
55
  if (typeof card.args === 'object') {
57
56
  for (const arg of Object.values(card.args)) {
58
57
  if (typeof arg !== 'string') continue;
58
+ // eslint-disable-next-line no-unused-vars
59
59
  for (const [tokenMatch, tokenId] of arg.matchAll(/\[\[(.*?)\]\]/g)) {
60
60
  await checkToken(tokenId);
61
61
  }
@@ -87,6 +87,7 @@ class Flow extends Item {
87
87
  for (const condition of Object.values(this.conditions)) {
88
88
  try {
89
89
  await managerFlow.getFlowCardConditions(); // Fill the cache
90
+ // eslint-disable-next-line no-unused-vars
90
91
  const conditionCard = await this.manager.getFlowCardCondition({ id: condition.id });
91
92
  await checkTokens(condition);
92
93
  } catch (err) {
@@ -101,6 +102,7 @@ class Flow extends Item {
101
102
  for (const action of Object.values(this.actions)) {
102
103
  try {
103
104
  await managerFlow.getFlowCardActions(); // Fill the cache
105
+ // eslint-disable-next-line no-unused-vars
104
106
  const actionCard = await this.manager.getFlowCardAction({ id: action.id });
105
107
  await checkTokens(action);
106
108
  } catch (err) {
@@ -12,8 +12,6 @@ const ManagerFlow = require('./HomeyAPIV3/ManagerFlow');
12
12
  const ManagerFlowToken = require('./HomeyAPIV3/ManagerFlowToken');
13
13
  const ManagerInsights = require('./HomeyAPIV3/ManagerInsights');
14
14
  const ManagerUsers = require('./HomeyAPIV3/ManagerUsers');
15
-
16
- // eslint-disable-next-line no-unused-vars
17
15
  const Manager = require('./HomeyAPIV3/Manager');
18
16
 
19
17
  /**
@@ -50,9 +48,10 @@ class HomeyAPIV3 extends HomeyAPI {
50
48
  token = null,
51
49
  session = null,
52
50
  reconnect = true,
53
- ...props
51
+ api,
52
+ debug,
54
53
  }) {
55
- super({ properties, ...props });
54
+ super({ properties, api, debug });
56
55
 
57
56
  this.__refreshMap = {};
58
57
 
@@ -128,7 +127,7 @@ class HomeyAPIV3 extends HomeyAPI {
128
127
  this.__baseUrlPromise = this.discoverBaseUrl().then(({ baseUrl }) => {
129
128
  return baseUrl;
130
129
  });
131
- this.__baseUrlPromise.catch(() => {});
130
+ this.__baseUrlPromise.catch(() => { });
132
131
  }
133
132
 
134
133
  return this.__baseUrlPromise;
@@ -145,7 +144,6 @@ class HomeyAPIV3 extends HomeyAPI {
145
144
  */
146
145
 
147
146
  getSpecification() {
148
- // eslint-disable-next-line global-require
149
147
  return require('../../assets/specifications/HomeyAPIV2.json');
150
148
  }
151
149
 
@@ -163,8 +161,8 @@ class HomeyAPIV3 extends HomeyAPI {
163
161
  const ManagerClass = this.constructor.MANAGERS[managerName]
164
162
  ? this.constructor.MANAGERS[managerName]
165
163
  : (() => {
166
- return class extends Manager {};
167
- })();
164
+ return class extends Manager { };
165
+ })();
168
166
 
169
167
  ManagerClass.ID = manager.id;
170
168
 
@@ -241,60 +239,68 @@ class HomeyAPIV3 extends HomeyAPI {
241
239
  // Create the returned Promise
242
240
  let resolve;
243
241
  let reject;
242
+
244
243
  const promise = new Promise((resolve_, reject_) => {
245
244
  resolve = resolve_;
246
245
  reject = reject_;
247
246
  });
247
+
248
248
  promise
249
249
  .then(({ baseUrl, strategyId }) => {
250
250
  this.__baseUrl = baseUrl;
251
251
  this.__strategyId = strategyId;
252
252
  })
253
- .catch(() => {});
253
+ .catch(() => { });
254
254
 
255
255
  // Ping method
256
256
  const ping = async (strategyId, timeout) => {
257
- let pingTimeout;
258
257
  const baseUrl = urls[strategyId];
259
- return Promise.race([
260
- Util.fetch(`${baseUrl}/api/manager/system/ping?id=${this.id}`, {
258
+
259
+ const response = await Util.fetch(
260
+ `${baseUrl}/api/manager/system/ping?id=${this.id}`,
261
+ {
261
262
  headers: {
262
263
  'X-Homey-ID': this.id,
263
264
  },
264
- }).then(async res => {
265
- const text = await res.text();
266
- if (!res.ok) throw new Error(text || res.statusText);
267
- if (text === 'false') throw new Error('Invalid Homey ID');
265
+ },
266
+ timeout
267
+ );
268
268
 
269
- const homeyId = res.headers.get('X-Homey-ID');
269
+ const text = await response.text();
270
270
 
271
- if (homeyId) {
272
- if (homeyId !== this.id) throw new Error('Invalid Homey ID'); // TODO: Add to Homey Connect
273
- }
271
+ if (!response.ok) {
272
+ throw new Error(text || response.statusText)
273
+ }
274
274
 
275
- // Set the version that Homey told us.
276
- // It's the absolute truth, because the Cloud API may be behind.
277
- const homeyVersion = res.headers.get('X-Homey-Version');
278
- if (homeyVersion !== this.version) {
279
- this.version = homeyVersion;
280
- }
275
+ if (text === 'false') {
276
+ throw new Error('Invalid Homey ID')
277
+ }
281
278
 
282
- return {
283
- baseUrl,
284
- strategyId,
285
- };
286
- }),
287
- new Promise((_, reject) => {
288
- pingTimeout = setTimeout(() => reject(new Error('PingTimeout')), timeout);
289
- }),
290
- ]).finally(() => clearTimeout(pingTimeout));
279
+ const homeyId = response.headers.get('X-Homey-ID');
280
+
281
+ if (homeyId && homeyId !== this.id) {
282
+ throw new Error('Invalid Homey ID'); // TODO: Add to Homey Connect
283
+ }
284
+
285
+ // Set the version that Homey told us.
286
+ // It's the absolute truth, because the Cloud API may be behind.
287
+ const homeyVersion = response.headers.get('X-Homey-Version');
288
+
289
+ if (homeyVersion !== this.version) {
290
+ this.version = homeyVersion;
291
+ }
292
+
293
+ return {
294
+ baseUrl,
295
+ strategyId,
296
+ };
291
297
  };
292
298
 
293
299
  const pings = {};
294
300
 
295
301
  // Ping localSecure (https://xxx-xxx-xxx-xx.homey.homeylocal.com)
296
302
  if (urls[HomeyAPI.DISCOVERY_STRATEGIES.LOCAL_SECURE]) {
297
- pings[HomeyAPI.DISCOVERY_STRATEGIES.LOCAL_SECURE] = ping(HomeyAPI.DISCOVERY_STRATEGIES.LOCAL_SECURE, 5000);
303
+ pings[HomeyAPI.DISCOVERY_STRATEGIES.LOCAL_SECURE] = ping(HomeyAPI.DISCOVERY_STRATEGIES.LOCAL_SECURE, 1200);
298
304
  pings[HomeyAPI.DISCOVERY_STRATEGIES.LOCAL_SECURE].catch(err => {
299
305
  this.__debug(`Ping ${HomeyAPI.DISCOVERY_STRATEGIES.LOCAL_SECURE} Error:`, err && err.message);
300
306
  this.__debug(urls[HomeyAPI.DISCOVERY_STRATEGIES.LOCAL_SECURE]);
@@ -444,6 +450,7 @@ class HomeyAPIV3 extends HomeyAPI {
444
450
  }
445
451
 
446
452
  this.__debug(method, `${baseUrl}${path}`);
453
+
447
454
  const res = await Util.fetch(
448
455
  `${baseUrl}${path}`,
449
456
  {
@@ -474,7 +481,7 @@ class HomeyAPIV3 extends HomeyAPI {
474
481
  try {
475
482
  resBodyJson = JSON.parse(resBodyText);
476
483
  // eslint-disable-next-line no-empty
477
- } catch (err) {}
484
+ } catch (err) { }
478
485
  }
479
486
 
480
487
  if (!res.ok) {
@@ -543,31 +550,7 @@ class HomeyAPIV3 extends HomeyAPI {
543
550
  return;
544
551
  }
545
552
 
546
- // Create a Session by generating a JWT token on AthomCloudAPI,
547
- // and then sending the JWT token to Homey.
548
- if (this.__api) {
549
- this.__debug('Retrieving token...');
550
- const jwtToken = await this.__api.createDelegationToken({ audience: 'homey' });
551
- const token = await this.users.login({
552
- $socket: false,
553
- token: jwtToken,
554
- shouldRetry: false,
555
- });
556
- this.__token = token;
557
-
558
- const session = await this.sessions.getSessionMe({
559
- $socket: false,
560
- shouldRetry: false,
561
- });
562
- this.__session = session;
563
-
564
- await this.__setStore({ token, session });
565
-
566
- this.__debug('Got token');
567
- return;
568
- }
569
-
570
- throw new Error('Cannot Sign In: Missing AthomCloudAPI');
553
+ await this.__refreshSession();
571
554
  });
572
555
 
573
556
  this.__loginPromise
@@ -585,6 +568,50 @@ class HomeyAPIV3 extends HomeyAPI {
585
568
  return this.__loginPromise;
586
569
  }
587
570
 
571
+ async __refreshSession() {
572
+ this.__debug('refreshSession');
573
+
574
+ if (this.__api) {
575
+ // Create a Session by generating a JWT token on AthomCloudAPI,
576
+ // and then sending the JWT token to Homey.
577
+ const jwtToken = await this.__api.createDelegationToken({ audience: 'homey' });
578
+ const token = await this.users.login({
579
+ $socket: false,
580
+ token: jwtToken,
581
+ shouldRetry: false,
582
+ });
583
+ this.__token = token;
584
+
585
+ const session = await this.sessions.getSessionMe({
586
+ $socket: false,
587
+ shouldRetry: false,
588
+ });
589
+ this.__session = session;
590
+
591
+ await this.__setStore({ session, token });
592
+
593
+ this.__debug('Got token');
594
+ return;
595
+ }
596
+
597
+ throw new Error('Cannot Sign In: Missing AthomCloudAPI');
598
+ }
599
+
600
+ async refreshSession() {
601
+ if (!this.__refreshSessionPromise) {
602
+ this.__refreshSessionPromise = this.__refreshSession();
603
+
604
+ this.__refreshSessionPromise
605
+ .catch(err => {
606
+ this.__debug('Error refreshing session:', err);
607
+ }).finally(() => {
608
+ this.__refreshSessionPromise = null;
609
+ });
610
+ }
611
+
612
+ return this.__refreshSessionPromise;
613
+ }
614
+
588
615
  async logout() {
589
616
  this.__token = null;
590
617
  this.__session = null;
@@ -614,12 +641,12 @@ class HomeyAPIV3 extends HomeyAPI {
614
641
  });
615
642
 
616
643
  this.__refreshMap[token]
617
- .then(() => {})
644
+ .then(() => { })
618
645
  .catch(err => {
619
646
  this.__debug('Error Refreshing Token:', err);
620
647
  })
621
648
  .finally(() => {
622
- // Delete after 30 seconds some requests might still be pending an they should be able
649
+ // Delete after 30 seconds some requests might still be pending and they should be able
623
650
  // to receive a rejected promise for this token.
624
651
  this.__refreshMap[token + 'timeout'] = setTimeout(() => {
625
652
  delete this.__refreshMap[token];
@@ -636,17 +663,17 @@ class HomeyAPIV3 extends HomeyAPI {
636
663
  * @returns {Boolean}
637
664
  */
638
665
  isConnected() {
639
- return this.__homeySocket && this.__homeySocket.connected;
666
+ return Boolean(this.__homeySocket && this.__homeySocket.connected);
640
667
  }
641
668
 
642
669
  async subscribe(
643
670
  uri,
644
671
  {
645
- onConnect = () => {},
646
- onReconnect = () => {},
647
- onReconnectError = () => {},
648
- onDisconnect = () => {},
649
- onEvent = () => {},
672
+ onConnect = () => { },
673
+ onReconnect = () => { },
674
+ onReconnectError = () => { },
675
+ onDisconnect = () => { },
676
+ onEvent = () => { },
650
677
  }
651
678
  ) {
652
679
  this.__debug('subscribe', uri);
@@ -51,7 +51,6 @@ class HomeyAPIV3Cloud extends HomeyAPIV3 {
51
51
  }
52
52
 
53
53
  getSpecification() {
54
- // eslint-disable-next-line global-require
55
54
  return require('../../assets/specifications/HomeyAPIV3Cloud.json');
56
55
  }
57
56
 
@@ -26,7 +26,6 @@ class HomeyAPIV3Local extends HomeyAPIV3 {
26
26
  }
27
27
 
28
28
  getSpecification() {
29
- // eslint-disable-next-line global-require
30
29
  return require('../../assets/specifications/HomeyAPIV3Local.json');
31
30
  }
32
31
 
package/lib/Util.js CHANGED
@@ -1,5 +1,3 @@
1
- /* eslint-disable no-undef */
2
-
3
1
  'use strict';
4
2
 
5
3
  const APIErrorTimeout = require('./APIErrorTimeout');
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "homey-api",
3
- "version": "3.4.33",
3
+ "version": "3.4.35",
4
4
  "description": "Homey API",
5
5
  "main": "index.js",
6
6
  "files": [
@@ -16,6 +16,7 @@
16
16
  "lint": "eslint .",
17
17
  "serve": "concurrently \"serve jsdoc/\" \"npm run jsdoc:watch\"",
18
18
  "build": "npm run build:specs && npm run build:jsdoc && npm run build:types && npm run build:webpack;",
19
+ "build:docs": "plantuml-cli -tsvg SOCKET.md",
19
20
  "build:webpack": "npm run webpack",
20
21
  "build:webpack:watch": "npm run webpack:watch",
21
22
  "build:types": "npm run generate-types;",
@@ -75,6 +76,7 @@
75
76
  "jsdoc-ts-utils": "^4.0.0",
76
77
  "jsdoc-tsimport-plugin": "^1.0.5",
77
78
  "keypather": "^3.1.0",
79
+ "plantuml-cli": "^1.2024.4",
78
80
  "prettier": "^3.2.5",
79
81
  "serve": "^14.0.1",
80
82
  "socket.io": "^4.7.4",