homebridge-lib 6.0.2 → 6.2.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/README.md +1 -1
- package/cli/hap.js +1 -1
- package/cli/json.js +1 -1
- package/cli/sysinfo.js +1 -1
- package/cli/upnp.js +1 -1
- package/index.js +1 -1
- package/lib/AccessoryDelegate.js +30 -27
- package/lib/AdaptiveLighting.js +1 -1
- package/lib/CharacteristicDelegate.js +22 -36
- package/lib/Colour.js +1 -1
- package/lib/CommandLineParser.js +1 -1
- package/lib/CommandLineTool.js +1 -1
- package/lib/CustomHomeKitTypes.js +1 -1
- package/lib/Delegate.js +31 -33
- package/lib/EveHomeKitTypes.js +62 -52
- package/lib/HttpClient.js +1 -1
- package/lib/JsonFormatter.js +1 -1
- package/lib/MyHomeKitTypes.js +88 -97
- package/lib/OptionParser.js +27 -2
- package/lib/Platform.js +12 -20
- package/lib/PropertyDelegate.js +8 -11
- package/lib/ServiceDelegate/AccessoryInformation.js +1 -1
- package/lib/ServiceDelegate/Battery.js +1 -1
- package/lib/ServiceDelegate/Dummy.js +1 -1
- package/lib/ServiceDelegate/History/Consumption.js +28 -49
- package/lib/ServiceDelegate/History/Light.js +15 -23
- package/lib/ServiceDelegate/History/On.js +29 -33
- package/lib/ServiceDelegate/History/Power.js +43 -52
- package/lib/ServiceDelegate/History/Sensor.js +215 -0
- package/lib/ServiceDelegate/History/Thermo.js +19 -33
- package/lib/ServiceDelegate/History/index.js +137 -186
- package/lib/ServiceDelegate/ServiceLabel.js +1 -1
- package/lib/ServiceDelegate/index.js +13 -11
- package/lib/SystemInfo.js +3 -2
- package/lib/UiServer.js +1 -1
- package/lib/UpnpClient.js +1 -1
- package/package.json +2 -2
- package/lib/ServiceDelegate/History/Contact.js +0 -96
- package/lib/ServiceDelegate/History/Motion.js +0 -155
- package/lib/ServiceDelegate/History/Room.js +0 -112
- package/lib/ServiceDelegate/History/Weather.js +0 -124
package/lib/OptionParser.js
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
// homebridge-lib/lib/OptionParser.js
|
|
2
2
|
//
|
|
3
3
|
// Library for Homebridge plugins.
|
|
4
|
-
// Copyright © 2018-
|
|
4
|
+
// Copyright © 2018-2023 Erik Baauw. All rights reserved.
|
|
5
5
|
|
|
6
6
|
'use strict'
|
|
7
7
|
|
|
@@ -769,6 +769,31 @@ class OptionParser extends events.EventEmitter {
|
|
|
769
769
|
return this
|
|
770
770
|
}
|
|
771
771
|
|
|
772
|
+
/** Defines a key that takes an number value,
|
|
773
|
+
* optionally clamped between min and max.
|
|
774
|
+
*
|
|
775
|
+
* @param {!string} key - The key.
|
|
776
|
+
* @param {?number} min - Minimum value returned.
|
|
777
|
+
* @param {?number} max - Maximum value returned.
|
|
778
|
+
* @return {OptionParser} this - For chaining.
|
|
779
|
+
* @throws {TypeError} When key is not a string.
|
|
780
|
+
* @throws {RangeError} When key is empty string.
|
|
781
|
+
* @throws {SyntaxError} On duplicate key.
|
|
782
|
+
*/
|
|
783
|
+
numberKey (key, min, max) {
|
|
784
|
+
key = this._toKey(key)
|
|
785
|
+
min = min == null ? -Infinity : OptionParser.toNumber('min', min)
|
|
786
|
+
max = max == null ? Infinity : OptionParser.toNumber('max', max)
|
|
787
|
+
if (max < min) {
|
|
788
|
+
throw newRangeError('max: smaller than min')
|
|
789
|
+
}
|
|
790
|
+
|
|
791
|
+
this._callbacks[key] = (value) => {
|
|
792
|
+
this._object[key] = OptionParser.toNumber(key, value, min, max, this._userInput)
|
|
793
|
+
}
|
|
794
|
+
return this
|
|
795
|
+
}
|
|
796
|
+
|
|
772
797
|
/** Defines a key that takes an object as value.
|
|
773
798
|
*
|
|
774
799
|
* @param {!string} key - The key.
|
|
@@ -832,7 +857,7 @@ class OptionParser extends events.EventEmitter {
|
|
|
832
857
|
* @throws {TypeError} When option has wrong type.
|
|
833
858
|
* @throws {RangeError} When option has wrong value.
|
|
834
859
|
* @throws {SyntaxError} Unknown option.
|
|
835
|
-
* @throws {
|
|
860
|
+
* @throws {UserInputError} On error, when value was input by user.
|
|
836
861
|
*/
|
|
837
862
|
parse (options) {
|
|
838
863
|
options = OptionParser.toObject('options', options)
|
package/lib/Platform.js
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
// homebridge-lib/lib/Platform.js
|
|
2
2
|
//
|
|
3
3
|
// Library for Homebridge plugins.
|
|
4
|
-
// Copyright © 2017-
|
|
4
|
+
// Copyright © 2017-2023 Erik Baauw. All rights reserved.
|
|
5
5
|
|
|
6
6
|
'use strict'
|
|
7
7
|
|
|
@@ -28,7 +28,9 @@ const context = {
|
|
|
28
28
|
recommendedHomebridgeVersion:
|
|
29
29
|
semver.minVersion(libPackageJson.engines.homebridge).toString(),
|
|
30
30
|
saveInterval: 3600,
|
|
31
|
-
checkInterval: 7 * 24 * 3600
|
|
31
|
+
checkInterval: 7 * 24 * 3600,
|
|
32
|
+
driftDebugThreshold: 250,
|
|
33
|
+
driftWarningThreshold: 2500
|
|
32
34
|
}
|
|
33
35
|
|
|
34
36
|
/** Homebridge dynamic platform plugin.
|
|
@@ -139,7 +141,7 @@ class Platform extends homebridgeLib.Delegate {
|
|
|
139
141
|
this._log = log
|
|
140
142
|
this._configJson = configJson
|
|
141
143
|
this._homebridge = homebridge
|
|
142
|
-
this._myContext = context[this.
|
|
144
|
+
this._myContext = context[this.constructor.name]
|
|
143
145
|
this._platformName = this._myContext.platformName
|
|
144
146
|
this._pluginName = this._myContext.packageJson.name
|
|
145
147
|
this._pluginVersion = this._myContext.packageJson.version
|
|
@@ -266,8 +268,12 @@ class Platform extends homebridgeLib.Delegate {
|
|
|
266
268
|
this.debug('last heartbeat %d, drift %d', beat, drift)
|
|
267
269
|
return
|
|
268
270
|
}
|
|
269
|
-
if (drift < -
|
|
270
|
-
|
|
271
|
+
if (drift < -context.driftDebugThreshold || drift > context.driftDebugThreshold) {
|
|
272
|
+
if (drift < -context.driftWarningThreshold || drift > context.driftWarningThreshold) {
|
|
273
|
+
this.warn('heartbeat %d, drift %d', beat, drift)
|
|
274
|
+
} else {
|
|
275
|
+
this.debug('heartbeat %d, drift %d', beat, drift)
|
|
276
|
+
}
|
|
271
277
|
}
|
|
272
278
|
setTimeout(() => {
|
|
273
279
|
this._beat(beat)
|
|
@@ -460,8 +466,7 @@ class Platform extends homebridgeLib.Delegate {
|
|
|
460
466
|
|
|
461
467
|
// Get or create accessory.
|
|
462
468
|
_getAccessory (delegate, params) {
|
|
463
|
-
const className = delegate.
|
|
464
|
-
const version = this._pluginVersion
|
|
469
|
+
const className = delegate.constructor.name
|
|
465
470
|
const id = params.id
|
|
466
471
|
const name = params.name
|
|
467
472
|
let accessory = this._accessories[id]
|
|
@@ -473,11 +478,6 @@ class Platform extends homebridgeLib.Delegate {
|
|
|
473
478
|
this._accessories[id] = accessory
|
|
474
479
|
accessory.displayName = name
|
|
475
480
|
accessory.context = {
|
|
476
|
-
className,
|
|
477
|
-
version,
|
|
478
|
-
id,
|
|
479
|
-
name,
|
|
480
|
-
logLevel: this.logLevel,
|
|
481
481
|
context: {}
|
|
482
482
|
}
|
|
483
483
|
delegate.once('initialised', () => {
|
|
@@ -507,14 +507,6 @@ class Platform extends homebridgeLib.Delegate {
|
|
|
507
507
|
delegate.emit('exposeError', error)
|
|
508
508
|
}
|
|
509
509
|
})
|
|
510
|
-
} else {
|
|
511
|
-
// Allow for plugin to change delegate class, version, and name.
|
|
512
|
-
accessory.context.className = className
|
|
513
|
-
accessory.context.version = version
|
|
514
|
-
accessory.context.name = name
|
|
515
|
-
if (accessory.context.logLevel == null) {
|
|
516
|
-
accessory.context.logLevel = this.logLevel
|
|
517
|
-
}
|
|
518
510
|
}
|
|
519
511
|
this._accessoryDelegates[id] = delegate
|
|
520
512
|
return accessory
|
package/lib/PropertyDelegate.js
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
// homebridge-lib/lib/PropertyDelegate.js
|
|
2
2
|
//
|
|
3
3
|
// Library for Homebridge plugins.
|
|
4
|
-
// Copyright © 2017-
|
|
4
|
+
// Copyright © 2017-2023 Erik Baauw. All rights reserved.
|
|
5
5
|
|
|
6
6
|
'use strict'
|
|
7
7
|
|
|
@@ -22,8 +22,7 @@ class PropertyDelegate extends homebridgeLib.Delegate {
|
|
|
22
22
|
/** Instantiate a property delegate.
|
|
23
23
|
*
|
|
24
24
|
* Note that instances are normally created by invoking
|
|
25
|
-
* {@link AccessoryDelegate#addPropertyDelegate addPropertyDelegate()}
|
|
26
|
-
* {@link ServiceDelegate#addPropertyDelegate addPropertyDelegate()}.
|
|
25
|
+
* {@link AccessoryDelegate#addPropertyDelegate addPropertyDelegate()}.
|
|
27
26
|
* @param {!AccessoryDelegate|ServiceDelegate} delegate - Reference to the
|
|
28
27
|
* delegate of the corresponding HomeKit accessory or service.
|
|
29
28
|
* @param {!object} params - Parameters of the property delegate.
|
|
@@ -41,10 +40,7 @@ class PropertyDelegate extends homebridgeLib.Delegate {
|
|
|
41
40
|
* optional parameter is not applicable.
|
|
42
41
|
*/
|
|
43
42
|
constructor (parent, params = {}) {
|
|
44
|
-
if (!(
|
|
45
|
-
parent instanceof homebridgeLib.AccessoryDelegate ||
|
|
46
|
-
parent instanceof homebridgeLib.ServiceDelegate
|
|
47
|
-
)) {
|
|
43
|
+
if (!(parent instanceof homebridgeLib.AccessoryDelegate)) {
|
|
48
44
|
throw new TypeError('parent: not an AccessoryDelegate')
|
|
49
45
|
}
|
|
50
46
|
super(parent.platform, parent.name + ': ' + params.key)
|
|
@@ -61,8 +57,6 @@ class PropertyDelegate extends homebridgeLib.Delegate {
|
|
|
61
57
|
if (this.value == null && params.value != null) {
|
|
62
58
|
this.value = params.value
|
|
63
59
|
}
|
|
64
|
-
|
|
65
|
-
this.vdebug('created')
|
|
66
60
|
}
|
|
67
61
|
|
|
68
62
|
/** Destroy the propery delegate.
|
|
@@ -92,6 +86,10 @@ class PropertyDelegate extends homebridgeLib.Delegate {
|
|
|
92
86
|
return this._parent.logLevel
|
|
93
87
|
}
|
|
94
88
|
|
|
89
|
+
get _namePrefix () {
|
|
90
|
+
return this._parent._namePrefix + this._key + ': '
|
|
91
|
+
}
|
|
92
|
+
|
|
95
93
|
validate (value) {
|
|
96
94
|
// Todo: check value against type.
|
|
97
95
|
return { value, s: '' }
|
|
@@ -116,8 +114,7 @@ class PropertyDelegate extends homebridgeLib.Delegate {
|
|
|
116
114
|
this._log('set to %j%s%s', value, this._unit, s)
|
|
117
115
|
} else {
|
|
118
116
|
this._log(
|
|
119
|
-
'set to %j%s%s (from %j%s)', value, this._unit, s,
|
|
120
|
-
this.value, this._unit
|
|
117
|
+
'set to %j%s%s (from %j%s)', value, this._unit, s, this.value, this._unit
|
|
121
118
|
)
|
|
122
119
|
}
|
|
123
120
|
|
|
@@ -1,20 +1,13 @@
|
|
|
1
1
|
// homebridge-lib/lib/ServiceDelegate/History/Consumption.js
|
|
2
2
|
//
|
|
3
3
|
// Library for Homebridge plugins.
|
|
4
|
-
// Copyright © 2017-
|
|
5
|
-
//
|
|
6
|
-
// The logic for handling Eve history was copied from Simone Tisa's
|
|
7
|
-
// fakagato-history repository, copyright © 2017 simont77.
|
|
8
|
-
// See https://github.com/simont77/fakegato-history.
|
|
4
|
+
// Copyright © 2017-2023 Erik Baauw. All rights reserved.
|
|
9
5
|
|
|
10
6
|
'use strict'
|
|
11
7
|
|
|
12
8
|
const homebridgeLib = require('../../../index')
|
|
13
|
-
const util = require('util')
|
|
14
9
|
|
|
15
|
-
const {
|
|
16
|
-
const { History } = ServiceDelegate
|
|
17
|
-
const { swap16, swap32, numToHex } = History
|
|
10
|
+
const { History } = homebridgeLib.ServiceDelegate
|
|
18
11
|
|
|
19
12
|
/** Class for an Eve Energy _History_ service delegate.
|
|
20
13
|
*
|
|
@@ -53,9 +46,9 @@ class Consumption extends History {
|
|
|
53
46
|
* @param {?CharacteristicDelegate} params.powerDelegate - A reference to the
|
|
54
47
|
* delegate of the associated `Characteristics.eve.CurrentConsumption`
|
|
55
48
|
* characteristic.
|
|
56
|
-
* @param {
|
|
49
|
+
* @param {?CharacteristicDelegate} params.onDelegate - A reference to the
|
|
57
50
|
* delegate of the associated `Characteristics.hap.On` characteristic.
|
|
58
|
-
* @param {
|
|
51
|
+
* @param {?CharacteristicDelegate} params.lastActivationDelegate - A
|
|
59
52
|
* reference to the delegate of the associated
|
|
60
53
|
* `Characteristics.eve.LastActivation` characteristic.
|
|
61
54
|
*/
|
|
@@ -85,66 +78,52 @@ class Consumption extends History {
|
|
|
85
78
|
this._consumptionDelegate = params.consumptionDelegate
|
|
86
79
|
this._powerDelegate = params.powerDelegate
|
|
87
80
|
|
|
88
|
-
this.
|
|
81
|
+
this.entry = { p: 0 }
|
|
89
82
|
if (params.onDelegate != null) {
|
|
90
|
-
this.
|
|
83
|
+
this.entry.o = params.onDelegate.value ? 1 : 0
|
|
91
84
|
params.onDelegate.on('didSet', (value) => {
|
|
92
|
-
const now =
|
|
85
|
+
const now = History.now()
|
|
93
86
|
if (params.lastActivationDelegate != null) {
|
|
94
|
-
params.lastActivationDelegate.value =
|
|
87
|
+
params.lastActivationDelegate.value = this.lastActivationValue(now)
|
|
95
88
|
}
|
|
96
|
-
this.
|
|
97
|
-
|
|
98
|
-
this._entry.power = null
|
|
99
|
-
super._addEntry(now)
|
|
100
|
-
this._entry.power = power
|
|
89
|
+
this.entry.o = value ? 1 : 0
|
|
90
|
+
super.addEntry({ time: now, o: this.entry.o })
|
|
101
91
|
})
|
|
102
92
|
}
|
|
103
93
|
}
|
|
104
94
|
|
|
105
|
-
|
|
106
|
-
const now = Math.round(new Date().valueOf() / 1000)
|
|
95
|
+
addEntry (entry) {
|
|
107
96
|
// Sensor deliveres totalConsumption, optionally compute currentConsumption
|
|
108
97
|
if (this._consumption != null && this._time != null) {
|
|
109
98
|
const delta = this._consumptionDelegate.value - this._consumption // kWh
|
|
110
|
-
const period =
|
|
99
|
+
const period = entry.time - this._time // s
|
|
111
100
|
const power = 1000 * 3600 * delta / period // W
|
|
112
101
|
if (this._powerDelegate != null) {
|
|
113
102
|
this._powerDelegate.value = Math.round(power) // W
|
|
114
103
|
}
|
|
115
|
-
|
|
116
|
-
super._addEntry(now)
|
|
104
|
+
entry.p = Math.round(power * 10) // 0.1 W * 10 min
|
|
117
105
|
}
|
|
106
|
+
super.addEntry(entry)
|
|
118
107
|
this._consumption = this._consumptionDelegate.value
|
|
119
|
-
this._time =
|
|
108
|
+
this._time = entry.time
|
|
120
109
|
}
|
|
121
110
|
|
|
122
|
-
get
|
|
111
|
+
get fingerPrint () { return '02 0702 0E01' }
|
|
123
112
|
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
)
|
|
113
|
+
entryToBuffer (entry) {
|
|
114
|
+
const buffer = Buffer.alloc(16)
|
|
115
|
+
let mask = 0
|
|
116
|
+
let o = 1
|
|
117
|
+
if (entry.p != null) {
|
|
118
|
+
mask |= 0x01
|
|
119
|
+
buffer.writeUInt16LE(entry.p, o); o += 2
|
|
132
120
|
}
|
|
133
|
-
if (entry.
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
numToHex(swap32(this._h.currentEntry), 8),
|
|
137
|
-
numToHex(swap32(entry.time - this._h.initialTime), 8),
|
|
138
|
-
numToHex(entry.on, 2)
|
|
139
|
-
)
|
|
121
|
+
if (entry.o != null) {
|
|
122
|
+
mask |= 0x02
|
|
123
|
+
buffer.writeUInt8(entry.o, o); o += 1
|
|
140
124
|
}
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
numToHex(swap32(this._h.currentEntry), 8),
|
|
144
|
-
numToHex(swap32(entry.time - this._h.initialTime), 8),
|
|
145
|
-
numToHex(swap16(entry.power), 4),
|
|
146
|
-
numToHex(entry.on, 2)
|
|
147
|
-
)
|
|
125
|
+
buffer.writeUInt8(mask, 0)
|
|
126
|
+
return buffer.slice(0, o)
|
|
148
127
|
}
|
|
149
128
|
}
|
|
150
129
|
|
|
@@ -1,18 +1,13 @@
|
|
|
1
1
|
// homebridge-lib/lib/ServiceDelegate/History/On.js
|
|
2
2
|
//
|
|
3
3
|
// Library for Homebridge plugins.
|
|
4
|
-
// Copyright © 2017-
|
|
5
|
-
//
|
|
6
|
-
// The logic for handling Eve history was copied from Simone Tisa's
|
|
7
|
-
// fakagato-history repository, copyright © 2017 simont77.
|
|
8
|
-
// See https://github.com/simont77/fakegato-history.
|
|
4
|
+
// Copyright © 2017-2023 Erik Baauw. All rights reserved.
|
|
9
5
|
|
|
10
6
|
'use strict'
|
|
11
7
|
|
|
12
8
|
const homebridgeLib = require('../../../index')
|
|
13
9
|
|
|
14
|
-
const {
|
|
15
|
-
const { History } = ServiceDelegate
|
|
10
|
+
const { History } = homebridgeLib.ServiceDelegate
|
|
16
11
|
|
|
17
12
|
/** Class for an Eve Light Strip _History_ service delegate.
|
|
18
13
|
*
|
|
@@ -28,7 +23,12 @@ const { History } = ServiceDelegate
|
|
|
28
23
|
* `historyEntries` | `Characteristics.eve.HistoryEntries`
|
|
29
24
|
*
|
|
30
25
|
* This delegate creates the history from the associated
|
|
31
|
-
* `Characteristics.hap.On` characteristic.
|
|
26
|
+
* `Characteristics.hap.On` characteristic. It updates the
|
|
27
|
+
* values of the associated `Characteristics.eve.LastActivation`
|
|
28
|
+
* characteristic.
|
|
29
|
+
* Note that the Eve Light Strip doesn't actually provide history entries;
|
|
30
|
+
* the _History_ service is used only to provide a reference time for
|
|
31
|
+
* last `LastActivation`.
|
|
32
32
|
* @extends ServiceDelegate.History
|
|
33
33
|
* @memberof ServiceDelegate.History
|
|
34
34
|
*/
|
|
@@ -54,28 +54,20 @@ class Light extends History {
|
|
|
54
54
|
if (!(params.lastActivationDelegate instanceof homebridgeLib.CharacteristicDelegate)) {
|
|
55
55
|
throw new TypeError('params.lastActivationDelegate: not a CharacteristicDelegate')
|
|
56
56
|
}
|
|
57
|
-
|
|
58
|
-
params.temperatureDelegate != null &&
|
|
59
|
-
!(params.temperatureDelegate instanceof homebridgeLib.CharacteristicDelegate)
|
|
60
|
-
) {
|
|
61
|
-
throw new TypeError('params.temperatureDelegate: not a CharacteristicDelegate')
|
|
62
|
-
}
|
|
63
|
-
this._entry = {
|
|
64
|
-
time: 0
|
|
65
|
-
}
|
|
57
|
+
this.entry = { }
|
|
66
58
|
params.onDelegate.on('didSet', (value) => {
|
|
67
|
-
const now =
|
|
59
|
+
const now = History.now()
|
|
68
60
|
if (params.lastActivationDelegate != null) {
|
|
69
|
-
params.lastActivationDelegate.value =
|
|
61
|
+
params.lastActivationDelegate.value = this.lastActivationValue(now)
|
|
70
62
|
}
|
|
71
|
-
this.
|
|
63
|
+
this.addEntry({ time: now })
|
|
72
64
|
})
|
|
73
65
|
}
|
|
74
66
|
|
|
75
|
-
get
|
|
67
|
+
get fingerPrint () { return '00' }
|
|
76
68
|
|
|
77
|
-
|
|
78
|
-
return
|
|
69
|
+
entryToBuffer (entry) {
|
|
70
|
+
return Buffer.alloc(0)
|
|
79
71
|
}
|
|
80
72
|
}
|
|
81
73
|
|
|
@@ -1,20 +1,13 @@
|
|
|
1
1
|
// homebridge-lib/lib/ServiceDelegate/History/On.js
|
|
2
2
|
//
|
|
3
3
|
// Library for Homebridge plugins.
|
|
4
|
-
// Copyright © 2017-
|
|
5
|
-
//
|
|
6
|
-
// The logic for handling Eve history was copied from Simone Tisa's
|
|
7
|
-
// fakagato-history repository, copyright © 2017 simont77.
|
|
8
|
-
// See https://github.com/simont77/fakegato-history.
|
|
4
|
+
// Copyright © 2017-2023 Erik Baauw. All rights reserved.
|
|
9
5
|
|
|
10
6
|
'use strict'
|
|
11
7
|
|
|
12
8
|
const homebridgeLib = require('../../../index')
|
|
13
|
-
const util = require('util')
|
|
14
9
|
|
|
15
|
-
const {
|
|
16
|
-
const { History } = ServiceDelegate
|
|
17
|
-
const { swap32, numToHex } = History
|
|
10
|
+
const { History } = homebridgeLib.ServiceDelegate
|
|
18
11
|
|
|
19
12
|
/** Class for a Raspberry Pi _History_ service delegate.
|
|
20
13
|
*
|
|
@@ -61,41 +54,44 @@ class On extends History {
|
|
|
61
54
|
) {
|
|
62
55
|
throw new TypeError('params.lastActivationDelegate: not a CharacteristicDelegate')
|
|
63
56
|
}
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
!(params.temperatureDelegate instanceof homebridgeLib.CharacteristicDelegate)
|
|
67
|
-
) {
|
|
68
|
-
throw new TypeError('params.temperatureDelegate: not a CharacteristicDelegate')
|
|
69
|
-
}
|
|
70
|
-
this._entry = {
|
|
71
|
-
time: 0,
|
|
72
|
-
on: params.onDelegate.value ? 1 : 0
|
|
73
|
-
}
|
|
57
|
+
|
|
58
|
+
this.entry = { o: params.onDelegate.value ? 1 : 0 }
|
|
74
59
|
params.onDelegate.on('didSet', (value) => {
|
|
75
|
-
const now =
|
|
60
|
+
const now = History.now()
|
|
76
61
|
if (params.lastActivationDelegate != null) {
|
|
77
|
-
params.lastActivationDelegate.value =
|
|
62
|
+
params.lastActivationDelegate.value = this.lastActivationValue(now)
|
|
78
63
|
}
|
|
79
|
-
this.
|
|
80
|
-
this.
|
|
64
|
+
this.entry.o = value ? 1 : 0
|
|
65
|
+
this.addEntry({ time: now, o: this.entry.o })
|
|
81
66
|
})
|
|
67
|
+
|
|
82
68
|
if (params.temperatureDelegate != null) {
|
|
83
|
-
|
|
69
|
+
if (!(params.temperatureDelegate instanceof homebridgeLib.CharacteristicDelegate)) {
|
|
70
|
+
throw new TypeError('params.temperatureDelegate: not a CharacteristicDelegate')
|
|
71
|
+
}
|
|
72
|
+
this.entry.t = params.temperatureDelegate.value * 100
|
|
84
73
|
params.temperatureDelegate.on('didSet', (value) => {
|
|
85
|
-
this.
|
|
74
|
+
this.entry.t = value * 100
|
|
86
75
|
})
|
|
87
76
|
}
|
|
88
77
|
}
|
|
89
78
|
|
|
90
|
-
get
|
|
79
|
+
get fingerPrint () { return '01 0E01 0102' }
|
|
91
80
|
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
81
|
+
entryToBuffer (entry) {
|
|
82
|
+
const buffer = Buffer.alloc(16)
|
|
83
|
+
let mask = 0
|
|
84
|
+
let o = 1
|
|
85
|
+
if (entry.o != null) {
|
|
86
|
+
mask |= 0x01
|
|
87
|
+
buffer.writeUInt8(entry.o, o); o += 1
|
|
88
|
+
}
|
|
89
|
+
if (entry.t != null) {
|
|
90
|
+
mask |= 0x02
|
|
91
|
+
buffer.writeUInt16LE(entry.t, o); o += 2
|
|
92
|
+
}
|
|
93
|
+
buffer.writeUInt8(mask, 0)
|
|
94
|
+
return buffer.slice(0, o)
|
|
99
95
|
}
|
|
100
96
|
}
|
|
101
97
|
|
|
@@ -1,20 +1,13 @@
|
|
|
1
1
|
// homebridge-lib/lib/ServiceDelegate/History/Power.js
|
|
2
2
|
//
|
|
3
3
|
// Library for Homebridge plugins.
|
|
4
|
-
// Copyright © 2017-
|
|
5
|
-
//
|
|
6
|
-
// The logic for handling Eve history was copied from Simone Tisa's
|
|
7
|
-
// fakagato-history repository, copyright © 2017 simont77.
|
|
8
|
-
// See https://github.com/simont77/fakegato-history.
|
|
4
|
+
// Copyright © 2017-2023 Erik Baauw. All rights reserved.
|
|
9
5
|
|
|
10
6
|
'use strict'
|
|
11
7
|
|
|
12
8
|
const homebridgeLib = require('../../../index')
|
|
13
|
-
const util = require('util')
|
|
14
9
|
|
|
15
|
-
const {
|
|
16
|
-
const { History } = ServiceDelegate
|
|
17
|
-
const { swap16, swap32, numToHex } = History
|
|
10
|
+
const { History } = homebridgeLib.ServiceDelegate
|
|
18
11
|
|
|
19
12
|
/** Class for an Eve Energy _History_ service delegate.
|
|
20
13
|
*
|
|
@@ -49,8 +42,11 @@ class Power extends History {
|
|
|
49
42
|
* @param {!CharacteristicDelegate} params.consumptionDelegate - A reference
|
|
50
43
|
* to the delegate of the associated `Characteristics.eve.TotalConsumption`
|
|
51
44
|
* characteristic.
|
|
52
|
-
* @param {
|
|
45
|
+
* @param {?CharacteristicDelegate} params.onDelegate - A reference to the
|
|
53
46
|
* delegate of the associated `Characteristics.hap.On` characteristic.
|
|
47
|
+
* @param {?CharacteristicDelegate} params.lastActivationDelegate - A
|
|
48
|
+
* reference to the delegate of the associated
|
|
49
|
+
* `Characteristics.eve.LastActivation` characteristic.
|
|
54
50
|
*/
|
|
55
51
|
constructor (accessoryDelegate, params) {
|
|
56
52
|
super(accessoryDelegate, params)
|
|
@@ -64,15 +60,24 @@ class Power extends History {
|
|
|
64
60
|
params.onDelegate != null &&
|
|
65
61
|
!(params.onDelegate instanceof homebridgeLib.CharacteristicDelegate)
|
|
66
62
|
) {
|
|
67
|
-
throw new TypeError('params.
|
|
63
|
+
throw new TypeError('params.onDelegate: not a CharacteristicDelegate')
|
|
64
|
+
}
|
|
65
|
+
if (
|
|
66
|
+
params.lastActivationDelegate != null &&
|
|
67
|
+
!(params.lastActivationDelegate instanceof homebridgeLib.CharacteristicDelegate)
|
|
68
|
+
) {
|
|
69
|
+
throw new TypeError('params.lastActivationDelegate: not a CharacteristicDelegate')
|
|
68
70
|
}
|
|
69
71
|
this._powerDelegate = params.powerDelegate
|
|
70
72
|
this._consumptionDelegate = params.consumptionDelegate
|
|
71
|
-
|
|
73
|
+
|
|
74
|
+
this.entry = { p: 0 }
|
|
72
75
|
this._runningConsumption = 0 // 10-min-interval running value
|
|
73
76
|
this._totalConsumption = params.consumptionDelegate.value // life-time value
|
|
77
|
+
this._power = params.powerDelegate.value // current power
|
|
78
|
+
this._time = History.now // start time of current power
|
|
74
79
|
params.powerDelegate.on('didSet', (value) => {
|
|
75
|
-
const now =
|
|
80
|
+
const now = History.now
|
|
76
81
|
if (this._time != null) {
|
|
77
82
|
const delta = this._power * (now - this._time) // Ws
|
|
78
83
|
this._runningConsumption += Math.round(delta / 60.0) // 0.1W * 10 min
|
|
@@ -81,6 +86,7 @@ class Power extends History {
|
|
|
81
86
|
this._power = value
|
|
82
87
|
this._time = now
|
|
83
88
|
})
|
|
89
|
+
|
|
84
90
|
this.addCharacteristicDelegate({
|
|
85
91
|
key: 'resetTotal',
|
|
86
92
|
Characteristic: this.Characteristics.eve.ResetTotal,
|
|
@@ -90,66 +96,51 @@ class Power extends History {
|
|
|
90
96
|
this._totalConsumption = 0
|
|
91
97
|
this._consumptionDelegate.value = this._totalConsumption
|
|
92
98
|
})
|
|
99
|
+
|
|
93
100
|
if (params.onDelegate != null) {
|
|
94
|
-
this.
|
|
101
|
+
this.entry.o = params.onDelegate.value ? 1 : 0
|
|
95
102
|
params.onDelegate.on('didSet', (value) => {
|
|
96
|
-
const now =
|
|
103
|
+
const now = History.now
|
|
97
104
|
if (params.lastActivationDelegate != null) {
|
|
98
|
-
params.lastActivationDelegate.value =
|
|
105
|
+
params.lastActivationDelegate.value = this.lastActivationValue(now)
|
|
99
106
|
}
|
|
100
|
-
this.
|
|
101
|
-
|
|
102
|
-
this._entry.power = null
|
|
103
|
-
super._addEntry(now)
|
|
104
|
-
this._entry.power = power
|
|
107
|
+
this.entry.o = value ? 1 : 0
|
|
108
|
+
super.addEntry({ time: now, o: this.entry.o })
|
|
105
109
|
})
|
|
106
110
|
}
|
|
107
111
|
}
|
|
108
112
|
|
|
109
|
-
|
|
110
|
-
const now = Math.round(new Date().valueOf() / 1000)
|
|
113
|
+
addEntry (entry) {
|
|
111
114
|
// Sensor delivers currentConsumption, compute totalConsumption
|
|
112
115
|
if (this._time != null) {
|
|
113
|
-
const delta = this._power * (
|
|
116
|
+
const delta = this._power * (entry.time - this._time) // Ws
|
|
114
117
|
this._runningConsumption += delta / 60.0 // 0.1 W * 10 min
|
|
115
118
|
this._totalConsumption += delta / 36000.0 // 0.01 kWh
|
|
116
119
|
this._consumptionDelegate.value = Math.round(this._totalConsumption) / 100.0 // kWh
|
|
117
|
-
|
|
118
|
-
super._addEntry(now)
|
|
119
|
-
} else if (this._entry.on != null) {
|
|
120
|
-
super._addEntry(now)
|
|
120
|
+
entry.p = Math.round(this._runningConsumption) // 0.1 W * 10 min
|
|
121
121
|
}
|
|
122
|
+
super.addEntry(entry)
|
|
122
123
|
this._power = this._powerDelegate.value
|
|
123
|
-
this._time =
|
|
124
|
+
this._time = entry.time
|
|
124
125
|
this._runningConsumption = 0
|
|
125
126
|
}
|
|
126
127
|
|
|
127
|
-
get
|
|
128
|
+
get fingerPrint () { return '02 0702 0E01' }
|
|
128
129
|
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
)
|
|
130
|
+
entryToBuffer (entry) {
|
|
131
|
+
const buffer = Buffer.alloc(16)
|
|
132
|
+
let mask = 0
|
|
133
|
+
let o = 1
|
|
134
|
+
if (entry.p != null) {
|
|
135
|
+
mask |= 0x01
|
|
136
|
+
buffer.writeUInt16LE(entry.p, o); o += 2
|
|
137
137
|
}
|
|
138
|
-
if (entry.
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
numToHex(swap32(this._h.currentEntry), 8),
|
|
142
|
-
numToHex(swap32(entry.time - this._h.initialTime), 8),
|
|
143
|
-
numToHex(entry.on, 2)
|
|
144
|
-
)
|
|
138
|
+
if (entry.o != null) {
|
|
139
|
+
mask |= 0x02
|
|
140
|
+
buffer.writeUInt8(entry.o, o); o += 1
|
|
145
141
|
}
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
numToHex(swap32(this._h.currentEntry), 8),
|
|
149
|
-
numToHex(swap32(entry.time - this._h.initialTime), 8),
|
|
150
|
-
numToHex(swap16(entry.power), 4),
|
|
151
|
-
numToHex(entry.on, 2)
|
|
152
|
-
)
|
|
142
|
+
buffer.writeUInt8(mask, 0)
|
|
143
|
+
return buffer.slice(0, o)
|
|
153
144
|
}
|
|
154
145
|
}
|
|
155
146
|
|