matterbridge 2.1.0-dev.1 → 2.1.0-dev.10
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +8 -6
- package/dist/frontend.js +89 -74
- package/dist/index.js +1 -0
- package/dist/matter/behaviors.js +1 -0
- package/dist/matter/clusters.js +1 -0
- package/dist/matter/devices.js +1 -0
- package/dist/matter/endpoints.js +1 -0
- package/dist/matter/export.js +1 -4
- package/dist/matter/types.js +2 -0
- package/dist/matterbridge.js +1 -14
- package/dist/matterbridgeBehaviors.js +5 -0
- package/dist/matterbridgeEndpoint.js +53 -398
- package/dist/matterbridgeEndpointHelpers.js +513 -0
- package/dist/matterbridgePlatform.js +3 -3
- package/dist/matterbridgeTypes.js +0 -3
- package/npm-shrinkwrap.json +47 -54
- package/package.json +22 -2
|
@@ -1,18 +1,14 @@
|
|
|
1
|
-
import { createHash } from 'crypto';
|
|
2
1
|
import { AnsiLogger, BLUE, CYAN, YELLOW, db, debugStringify, er, hk, or, zb } from './logger/export.js';
|
|
3
2
|
import { bridgedNode } from './matterbridgeDeviceTypes.js';
|
|
4
|
-
import {
|
|
5
|
-
import { MatterbridgeBehavior, MatterbridgeBehaviorDevice, MatterbridgeIdentifyServer, MatterbridgeOnOffServer, MatterbridgeLevelControlServer, MatterbridgeColorControlServer, MatterbridgeWindowCoveringServer, MatterbridgeThermostatServer, MatterbridgeFanControlServer, MatterbridgeDoorLockServer, MatterbridgeModeSelectServer, MatterbridgeValveConfigurationAndControlServer, MatterbridgeSmokeCoAlarmServer, MatterbridgeBooleanStateConfigurationServer, } from './matterbridgeBehaviors.js';
|
|
3
|
+
import { isValidNumber, isValidObject } from './utils/utils.js';
|
|
4
|
+
import { MatterbridgeBehavior, MatterbridgeBehaviorDevice, MatterbridgeIdentifyServer, MatterbridgeOnOffServer, MatterbridgeLevelControlServer, MatterbridgeColorControlServer, MatterbridgeWindowCoveringServer, MatterbridgeThermostatServer, MatterbridgeFanControlServer, MatterbridgeDoorLockServer, MatterbridgeModeSelectServer, MatterbridgeValveConfigurationAndControlServer, MatterbridgeSmokeCoAlarmServer, MatterbridgeBooleanStateConfigurationServer, MatterbridgeSwitchServer, } from './matterbridgeBehaviors.js';
|
|
5
|
+
import { addClusterServers, addFixedLabel, addOptionalClusterServers, addRequiredClusterServers, addUserLabel, capitalizeFirstLetter, createUniqueId, getBehavior, getBehaviourTypesFromClusterClientIds, getBehaviourTypesFromClusterServerIds, getDefaultFlowMeasurementClusterServer, getDefaultIlluminanceMeasurementClusterServer, getDefaultPressureMeasurementClusterServer, getDefaultRelativeHumidityMeasurementClusterServer, getDefaultTemperatureMeasurementClusterServer, getDefaultOccupancySensingClusterServer, lowercaseFirstLetter, updateAttribute, getClusterId, getAttributeId, setAttribute, getAttribute, } from './matterbridgeEndpointHelpers.js';
|
|
6
6
|
import { Endpoint, Lifecycle, MutableEndpoint, NamedHandler, SupportedBehaviors, VendorId } from '@matter/main';
|
|
7
7
|
import { getClusterNameById, MeasurementType } from '@matter/main/types';
|
|
8
8
|
import { Descriptor } from '@matter/main/clusters/descriptor';
|
|
9
9
|
import { PowerSource } from '@matter/main/clusters/power-source';
|
|
10
|
-
import { UserLabel } from '@matter/main/clusters/user-label';
|
|
11
|
-
import { FixedLabel } from '@matter/main/clusters/fixed-label';
|
|
12
|
-
import { BasicInformation } from '@matter/main/clusters/basic-information';
|
|
13
10
|
import { BridgedDeviceBasicInformation } from '@matter/main/clusters/bridged-device-basic-information';
|
|
14
11
|
import { Identify } from '@matter/main/clusters/identify';
|
|
15
|
-
import { Groups } from '@matter/main/clusters/groups';
|
|
16
12
|
import { OnOff } from '@matter/main/clusters/on-off';
|
|
17
13
|
import { LevelControl } from '@matter/main/clusters/level-control';
|
|
18
14
|
import { ColorControl } from '@matter/main/clusters/color-control';
|
|
@@ -20,39 +16,18 @@ import { WindowCovering } from '@matter/main/clusters/window-covering';
|
|
|
20
16
|
import { Thermostat } from '@matter/main/clusters/thermostat';
|
|
21
17
|
import { FanControl } from '@matter/main/clusters/fan-control';
|
|
22
18
|
import { DoorLock } from '@matter/main/clusters/door-lock';
|
|
23
|
-
import { ModeSelect } from '@matter/main/clusters/mode-select';
|
|
24
19
|
import { ValveConfigurationAndControl } from '@matter/main/clusters/valve-configuration-and-control';
|
|
25
20
|
import { PumpConfigurationAndControl } from '@matter/main/clusters/pump-configuration-and-control';
|
|
26
21
|
import { SmokeCoAlarm } from '@matter/main/clusters/smoke-co-alarm';
|
|
27
22
|
import { Switch } from '@matter/main/clusters/switch';
|
|
28
|
-
import { BooleanState } from '@matter/main/clusters/boolean-state';
|
|
29
23
|
import { BooleanStateConfiguration } from '@matter/main/clusters/boolean-state-configuration';
|
|
30
24
|
import { PowerTopology } from '@matter/main/clusters/power-topology';
|
|
31
25
|
import { ElectricalPowerMeasurement } from '@matter/main/clusters/electrical-power-measurement';
|
|
32
26
|
import { ElectricalEnergyMeasurement } from '@matter/main/clusters/electrical-energy-measurement';
|
|
33
|
-
import { TemperatureMeasurement } from '@matter/main/clusters/temperature-measurement';
|
|
34
|
-
import { RelativeHumidityMeasurement } from '@matter/main/clusters/relative-humidity-measurement';
|
|
35
|
-
import { PressureMeasurement } from '@matter/main/clusters/pressure-measurement';
|
|
36
|
-
import { FlowMeasurement } from '@matter/main/clusters/flow-measurement';
|
|
37
|
-
import { IlluminanceMeasurement } from '@matter/main/clusters/illuminance-measurement';
|
|
38
|
-
import { OccupancySensing } from '@matter/main/clusters/occupancy-sensing';
|
|
39
27
|
import { AirQuality } from '@matter/main/clusters/air-quality';
|
|
40
|
-
import { CarbonMonoxideConcentrationMeasurement } from '@matter/main/clusters/carbon-monoxide-concentration-measurement';
|
|
41
|
-
import { CarbonDioxideConcentrationMeasurement } from '@matter/main/clusters/carbon-dioxide-concentration-measurement';
|
|
42
|
-
import { NitrogenDioxideConcentrationMeasurement } from '@matter/main/clusters/nitrogen-dioxide-concentration-measurement';
|
|
43
|
-
import { OzoneConcentrationMeasurement } from '@matter/main/clusters/ozone-concentration-measurement';
|
|
44
|
-
import { FormaldehydeConcentrationMeasurement } from '@matter/main/clusters/formaldehyde-concentration-measurement';
|
|
45
|
-
import { Pm1ConcentrationMeasurement } from '@matter/main/clusters/pm1-concentration-measurement';
|
|
46
|
-
import { Pm25ConcentrationMeasurement } from '@matter/main/clusters/pm25-concentration-measurement';
|
|
47
|
-
import { Pm10ConcentrationMeasurement } from '@matter/main/clusters/pm10-concentration-measurement';
|
|
48
|
-
import { RadonConcentrationMeasurement } from '@matter/main/clusters/radon-concentration-measurement';
|
|
49
|
-
import { TotalVolatileOrganicCompoundsConcentrationMeasurement } from '@matter/main/clusters/total-volatile-organic-compounds-concentration-measurement';
|
|
50
28
|
import { ConcentrationMeasurement } from '@matter/main/clusters/concentration-measurement';
|
|
51
29
|
import { DescriptorServer } from '@matter/main/behaviors/descriptor';
|
|
52
30
|
import { PowerSourceServer } from '@matter/main/behaviors/power-source';
|
|
53
|
-
import { UserLabelServer } from '@matter/main/behaviors/user-label';
|
|
54
|
-
import { FixedLabelServer } from '@matter/main/behaviors/fixed-label';
|
|
55
|
-
import { BasicInformationServer } from '@matter/main/behaviors/basic-information';
|
|
56
31
|
import { BridgedDeviceBasicInformationServer } from '@matter/main/behaviors/bridged-device-basic-information';
|
|
57
32
|
import { GroupsServer } from '@matter/main/behaviors/groups';
|
|
58
33
|
import { ScenesManagementServer } from '@matter/main/behaviors/scenes-management';
|
|
@@ -79,242 +54,6 @@ import { Pm25ConcentrationMeasurementServer } from '@matter/main/behaviors/pm25-
|
|
|
79
54
|
import { Pm10ConcentrationMeasurementServer } from '@matter/main/behaviors/pm10-concentration-measurement';
|
|
80
55
|
import { RadonConcentrationMeasurementServer } from '@matter/main/behaviors/radon-concentration-measurement';
|
|
81
56
|
import { TotalVolatileOrganicCompoundsConcentrationMeasurementServer } from '@matter/main/behaviors/total-volatile-organic-compounds-concentration-measurement';
|
|
82
|
-
function capitalizeFirstLetter(name) {
|
|
83
|
-
if (!name)
|
|
84
|
-
return name;
|
|
85
|
-
return name.charAt(0).toUpperCase() + name.slice(1);
|
|
86
|
-
}
|
|
87
|
-
function lowercaseFirstLetter(name) {
|
|
88
|
-
if (!name)
|
|
89
|
-
return name;
|
|
90
|
-
return name.charAt(0).toLowerCase() + name.slice(1);
|
|
91
|
-
}
|
|
92
|
-
function createUniqueId(param1, param2, param3, param4) {
|
|
93
|
-
const hash = createHash('md5');
|
|
94
|
-
hash.update(param1 + param2 + param3 + param4);
|
|
95
|
-
return hash.digest('hex');
|
|
96
|
-
}
|
|
97
|
-
function getBehaviourTypesFromClusterServerIds(clusterServerList) {
|
|
98
|
-
const behaviorTypes = [];
|
|
99
|
-
clusterServerList.forEach((clusterId) => {
|
|
100
|
-
behaviorTypes.push(getBehaviourTypeFromClusterServerId(clusterId));
|
|
101
|
-
});
|
|
102
|
-
return behaviorTypes;
|
|
103
|
-
}
|
|
104
|
-
function getBehaviourTypesFromClusterClientIds(clusterClientList) {
|
|
105
|
-
const behaviorTypes = [];
|
|
106
|
-
clusterClientList.forEach((clusterId) => {
|
|
107
|
-
});
|
|
108
|
-
return behaviorTypes;
|
|
109
|
-
}
|
|
110
|
-
function getBehaviourTypeFromClusterServerId(clusterId) {
|
|
111
|
-
if (clusterId === PowerSource.Cluster.id)
|
|
112
|
-
return PowerSourceServer.with(PowerSource.Feature.Wired);
|
|
113
|
-
if (clusterId === UserLabel.Cluster.id)
|
|
114
|
-
return UserLabelServer;
|
|
115
|
-
if (clusterId === FixedLabel.Cluster.id)
|
|
116
|
-
return FixedLabelServer;
|
|
117
|
-
if (clusterId === BasicInformation.Cluster.id)
|
|
118
|
-
return BasicInformationServer;
|
|
119
|
-
if (clusterId === BridgedDeviceBasicInformation.Cluster.id)
|
|
120
|
-
return BridgedDeviceBasicInformationServer;
|
|
121
|
-
if (clusterId === Identify.Cluster.id)
|
|
122
|
-
return MatterbridgeIdentifyServer;
|
|
123
|
-
if (clusterId === Groups.Cluster.id)
|
|
124
|
-
return GroupsServer;
|
|
125
|
-
if (clusterId === OnOff.Cluster.id)
|
|
126
|
-
return MatterbridgeOnOffServer.with('Lighting');
|
|
127
|
-
if (clusterId === LevelControl.Cluster.id)
|
|
128
|
-
return MatterbridgeLevelControlServer.with('OnOff', 'Lighting');
|
|
129
|
-
if (clusterId === ColorControl.Cluster.id)
|
|
130
|
-
return MatterbridgeColorControlServer;
|
|
131
|
-
if (clusterId === WindowCovering.Cluster.id)
|
|
132
|
-
return MatterbridgeWindowCoveringServer.with('Lift', 'PositionAwareLift');
|
|
133
|
-
if (clusterId === Thermostat.Cluster.id)
|
|
134
|
-
return MatterbridgeThermostatServer.with('AutoMode', 'Heating', 'Cooling');
|
|
135
|
-
if (clusterId === FanControl.Cluster.id)
|
|
136
|
-
return MatterbridgeFanControlServer;
|
|
137
|
-
if (clusterId === DoorLock.Cluster.id)
|
|
138
|
-
return MatterbridgeDoorLockServer;
|
|
139
|
-
if (clusterId === ModeSelect.Cluster.id)
|
|
140
|
-
return MatterbridgeModeSelectServer;
|
|
141
|
-
if (clusterId === ValveConfigurationAndControl.Cluster.id)
|
|
142
|
-
return MatterbridgeValveConfigurationAndControlServer.with('Level');
|
|
143
|
-
if (clusterId === PumpConfigurationAndControl.Cluster.id)
|
|
144
|
-
return PumpConfigurationAndControlServer.with('ConstantSpeed');
|
|
145
|
-
if (clusterId === SmokeCoAlarm.Cluster.id)
|
|
146
|
-
return MatterbridgeSmokeCoAlarmServer.with('SmokeAlarm', 'CoAlarm');
|
|
147
|
-
if (clusterId === Switch.Cluster.id)
|
|
148
|
-
return SwitchServer.with('MomentarySwitch', 'MomentarySwitchRelease', 'MomentarySwitchLongPress', 'MomentarySwitchMultiPress');
|
|
149
|
-
if (clusterId === BooleanState.Cluster.id)
|
|
150
|
-
return BooleanStateServer.enable({ events: { stateChange: true } });
|
|
151
|
-
if (clusterId === BooleanStateConfiguration.Cluster.id)
|
|
152
|
-
return MatterbridgeBooleanStateConfigurationServer;
|
|
153
|
-
if (clusterId === PowerTopology.Cluster.id)
|
|
154
|
-
return PowerTopologyServer.with('TreeTopology');
|
|
155
|
-
if (clusterId === ElectricalPowerMeasurement.Cluster.id)
|
|
156
|
-
return ElectricalPowerMeasurementServer.with('AlternatingCurrent');
|
|
157
|
-
if (clusterId === ElectricalEnergyMeasurement.Cluster.id)
|
|
158
|
-
return ElectricalEnergyMeasurementServer.with('ImportedEnergy', 'ExportedEnergy', 'CumulativeEnergy');
|
|
159
|
-
if (clusterId === TemperatureMeasurement.Cluster.id)
|
|
160
|
-
return TemperatureMeasurementServer;
|
|
161
|
-
if (clusterId === RelativeHumidityMeasurement.Cluster.id)
|
|
162
|
-
return RelativeHumidityMeasurementServer;
|
|
163
|
-
if (clusterId === PressureMeasurement.Cluster.id)
|
|
164
|
-
return PressureMeasurementServer;
|
|
165
|
-
if (clusterId === FlowMeasurement.Cluster.id)
|
|
166
|
-
return FlowMeasurementServer;
|
|
167
|
-
if (clusterId === IlluminanceMeasurement.Cluster.id)
|
|
168
|
-
return IlluminanceMeasurementServer;
|
|
169
|
-
if (clusterId === OccupancySensing.Cluster.id)
|
|
170
|
-
return OccupancySensingServer;
|
|
171
|
-
if (clusterId === AirQuality.Cluster.id)
|
|
172
|
-
return AirQualityServer.with('Fair', 'Moderate', 'VeryPoor', 'ExtremelyPoor');
|
|
173
|
-
if (clusterId === CarbonMonoxideConcentrationMeasurement.Cluster.id)
|
|
174
|
-
return CarbonMonoxideConcentrationMeasurementServer.with('NumericMeasurement');
|
|
175
|
-
if (clusterId === CarbonDioxideConcentrationMeasurement.Cluster.id)
|
|
176
|
-
return CarbonDioxideConcentrationMeasurementServer.with('NumericMeasurement');
|
|
177
|
-
if (clusterId === NitrogenDioxideConcentrationMeasurement.Cluster.id)
|
|
178
|
-
return NitrogenDioxideConcentrationMeasurementServer.with('NumericMeasurement');
|
|
179
|
-
if (clusterId === OzoneConcentrationMeasurement.Cluster.id)
|
|
180
|
-
return OzoneConcentrationMeasurementServer.with('NumericMeasurement');
|
|
181
|
-
if (clusterId === FormaldehydeConcentrationMeasurement.Cluster.id)
|
|
182
|
-
return FormaldehydeConcentrationMeasurementServer.with('NumericMeasurement');
|
|
183
|
-
if (clusterId === Pm1ConcentrationMeasurement.Cluster.id)
|
|
184
|
-
return Pm1ConcentrationMeasurementServer.with('NumericMeasurement');
|
|
185
|
-
if (clusterId === Pm25ConcentrationMeasurement.Cluster.id)
|
|
186
|
-
return Pm25ConcentrationMeasurementServer.with('NumericMeasurement');
|
|
187
|
-
if (clusterId === Pm10ConcentrationMeasurement.Cluster.id)
|
|
188
|
-
return Pm10ConcentrationMeasurementServer.with('NumericMeasurement');
|
|
189
|
-
if (clusterId === RadonConcentrationMeasurement.Cluster.id)
|
|
190
|
-
return RadonConcentrationMeasurementServer.with('NumericMeasurement');
|
|
191
|
-
if (clusterId === TotalVolatileOrganicCompoundsConcentrationMeasurement.Cluster.id)
|
|
192
|
-
return TotalVolatileOrganicCompoundsConcentrationMeasurementServer.with('NumericMeasurement');
|
|
193
|
-
return MatterbridgeIdentifyServer;
|
|
194
|
-
}
|
|
195
|
-
function getBehaviourTypeFromClusterClientId(clusterId) {
|
|
196
|
-
}
|
|
197
|
-
function getBehavior(endpoint, cluster) {
|
|
198
|
-
let behavior;
|
|
199
|
-
if (typeof cluster === 'string') {
|
|
200
|
-
behavior = endpoint.behaviors.supported[lowercaseFirstLetter(cluster)];
|
|
201
|
-
}
|
|
202
|
-
else if (typeof cluster === 'number') {
|
|
203
|
-
behavior = endpoint.behaviors.supported[lowercaseFirstLetter(getClusterNameById(cluster))];
|
|
204
|
-
}
|
|
205
|
-
else if (typeof cluster === 'object') {
|
|
206
|
-
behavior = endpoint.behaviors.supported[lowercaseFirstLetter(cluster.name)];
|
|
207
|
-
}
|
|
208
|
-
else if (typeof cluster === 'function') {
|
|
209
|
-
behavior = cluster;
|
|
210
|
-
}
|
|
211
|
-
return behavior;
|
|
212
|
-
}
|
|
213
|
-
function addRequiredClusterServers(endpoint) {
|
|
214
|
-
const requiredServerList = [];
|
|
215
|
-
endpoint.log.debug(`addRequiredClusterServers for ${CYAN}${endpoint.maybeId}${db}`);
|
|
216
|
-
endpoint.deviceTypes.values().forEach((deviceType) => {
|
|
217
|
-
endpoint.log.debug(`- for deviceType: ${zb}${'0x' + deviceType.code.toString(16).padStart(4, '0')}${db}-${zb}${deviceType.name}${db}`);
|
|
218
|
-
deviceType.requiredServerClusters.forEach((clusterId) => {
|
|
219
|
-
if (!requiredServerList.includes(clusterId) && !endpoint.hasClusterServer(clusterId)) {
|
|
220
|
-
requiredServerList.push(clusterId);
|
|
221
|
-
endpoint.log.debug(`- cluster: ${hk}${'0x' + clusterId.toString(16).padStart(4, '0')}${db}-${hk}${getClusterNameById(clusterId)}${db}`);
|
|
222
|
-
}
|
|
223
|
-
});
|
|
224
|
-
});
|
|
225
|
-
addClusterServers(endpoint, requiredServerList);
|
|
226
|
-
}
|
|
227
|
-
function addOptionalClusterServers(endpoint) {
|
|
228
|
-
const optionalServerList = [];
|
|
229
|
-
endpoint.log.debug(`addOptionalClusterServers for ${CYAN}${endpoint.maybeId}${db}`);
|
|
230
|
-
endpoint.deviceTypes.values().forEach((deviceType) => {
|
|
231
|
-
endpoint.log.debug(`- for deviceType: ${zb}${'0x' + deviceType.code.toString(16).padStart(4, '0')}${db}-${zb}${deviceType.name}${db}`);
|
|
232
|
-
deviceType.optionalServerClusters.forEach((clusterId) => {
|
|
233
|
-
if (!optionalServerList.includes(clusterId) && !endpoint.hasClusterServer(clusterId)) {
|
|
234
|
-
optionalServerList.push(clusterId);
|
|
235
|
-
endpoint.log.debug(`- cluster: ${hk}${'0x' + clusterId.toString(16).padStart(4, '0')}${db}-${hk}${getClusterNameById(clusterId)}${db}`);
|
|
236
|
-
}
|
|
237
|
-
});
|
|
238
|
-
});
|
|
239
|
-
addClusterServers(endpoint, optionalServerList);
|
|
240
|
-
}
|
|
241
|
-
function addClusterServers(endpoint, serverList) {
|
|
242
|
-
if (serverList.includes(PowerSource.Cluster.id))
|
|
243
|
-
endpoint.createDefaultPowerSourceWiredClusterServer();
|
|
244
|
-
if (serverList.includes(Identify.Cluster.id))
|
|
245
|
-
endpoint.createDefaultIdentifyClusterServer();
|
|
246
|
-
if (serverList.includes(Groups.Cluster.id))
|
|
247
|
-
endpoint.createDefaultGroupsClusterServer();
|
|
248
|
-
if (serverList.includes(OnOff.Cluster.id))
|
|
249
|
-
endpoint.createDefaultOnOffClusterServer();
|
|
250
|
-
if (serverList.includes(LevelControl.Cluster.id))
|
|
251
|
-
endpoint.createDefaultLevelControlClusterServer();
|
|
252
|
-
if (serverList.includes(ColorControl.Cluster.id))
|
|
253
|
-
endpoint.createDefaultColorControlClusterServer();
|
|
254
|
-
if (serverList.includes(WindowCovering.Cluster.id))
|
|
255
|
-
endpoint.createDefaultWindowCoveringClusterServer();
|
|
256
|
-
if (serverList.includes(Thermostat.Cluster.id))
|
|
257
|
-
endpoint.createDefaultThermostatClusterServer();
|
|
258
|
-
if (serverList.includes(FanControl.Cluster.id))
|
|
259
|
-
endpoint.createDefaultFanControlClusterServer();
|
|
260
|
-
if (serverList.includes(DoorLock.Cluster.id))
|
|
261
|
-
endpoint.createDefaultDoorLockClusterServer();
|
|
262
|
-
if (serverList.includes(ValveConfigurationAndControl.Cluster.id))
|
|
263
|
-
endpoint.createDefaultValveConfigurationAndControlClusterServer();
|
|
264
|
-
if (serverList.includes(PumpConfigurationAndControl.Cluster.id))
|
|
265
|
-
endpoint.createDefaultPumpConfigurationAndControlClusterServer();
|
|
266
|
-
if (serverList.includes(SmokeCoAlarm.Cluster.id))
|
|
267
|
-
endpoint.createDefaultSmokeCOAlarmClusterServer();
|
|
268
|
-
if (serverList.includes(Switch.Cluster.id))
|
|
269
|
-
endpoint.createDefaultSwitchClusterServer();
|
|
270
|
-
if (serverList.includes(BooleanState.Cluster.id))
|
|
271
|
-
endpoint.createDefaultBooleanStateClusterServer();
|
|
272
|
-
if (serverList.includes(BooleanStateConfiguration.Cluster.id))
|
|
273
|
-
endpoint.createDefaultBooleanStateConfigurationClusterServer();
|
|
274
|
-
if (serverList.includes(PowerTopology.Cluster.id))
|
|
275
|
-
endpoint.createDefaultPowerTopologyClusterServer();
|
|
276
|
-
if (serverList.includes(ElectricalPowerMeasurement.Cluster.id))
|
|
277
|
-
endpoint.createDefaultElectricalPowerMeasurementClusterServer();
|
|
278
|
-
if (serverList.includes(ElectricalEnergyMeasurement.Cluster.id))
|
|
279
|
-
endpoint.createDefaultElectricalEnergyMeasurementClusterServer();
|
|
280
|
-
if (serverList.includes(TemperatureMeasurement.Cluster.id))
|
|
281
|
-
endpoint.createDefaultTemperatureMeasurementClusterServer();
|
|
282
|
-
if (serverList.includes(RelativeHumidityMeasurement.Cluster.id))
|
|
283
|
-
endpoint.createDefaultRelativeHumidityMeasurementClusterServer();
|
|
284
|
-
if (serverList.includes(PressureMeasurement.Cluster.id))
|
|
285
|
-
endpoint.createDefaultPressureMeasurementClusterServer();
|
|
286
|
-
if (serverList.includes(FlowMeasurement.Cluster.id))
|
|
287
|
-
endpoint.createDefaultFlowMeasurementClusterServer();
|
|
288
|
-
if (serverList.includes(IlluminanceMeasurement.Cluster.id))
|
|
289
|
-
endpoint.createDefaultIlluminanceMeasurementClusterServer();
|
|
290
|
-
if (serverList.includes(OccupancySensing.Cluster.id))
|
|
291
|
-
endpoint.createDefaultOccupancySensingClusterServer();
|
|
292
|
-
if (serverList.includes(AirQuality.Cluster.id))
|
|
293
|
-
endpoint.createDefaultAirQualityClusterServer();
|
|
294
|
-
if (serverList.includes(CarbonMonoxideConcentrationMeasurement.Cluster.id))
|
|
295
|
-
endpoint.createDefaultCarbonMonoxideConcentrationMeasurementClusterServer();
|
|
296
|
-
if (serverList.includes(CarbonDioxideConcentrationMeasurement.Cluster.id))
|
|
297
|
-
endpoint.createDefaultCarbonDioxideConcentrationMeasurementClusterServer();
|
|
298
|
-
if (serverList.includes(NitrogenDioxideConcentrationMeasurement.Cluster.id))
|
|
299
|
-
endpoint.createDefaultNitrogenDioxideConcentrationMeasurementClusterServer();
|
|
300
|
-
if (serverList.includes(OzoneConcentrationMeasurement.Cluster.id))
|
|
301
|
-
endpoint.createDefaultOzoneConcentrationMeasurementClusterServer();
|
|
302
|
-
if (serverList.includes(FormaldehydeConcentrationMeasurement.Cluster.id))
|
|
303
|
-
endpoint.createDefaultFormaldehydeConcentrationMeasurementClusterServer();
|
|
304
|
-
if (serverList.includes(Pm1ConcentrationMeasurement.Cluster.id))
|
|
305
|
-
endpoint.createDefaultPm1ConcentrationMeasurementClusterServer();
|
|
306
|
-
if (serverList.includes(Pm25ConcentrationMeasurement.Cluster.id))
|
|
307
|
-
endpoint.createDefaultPm25ConcentrationMeasurementClusterServer();
|
|
308
|
-
if (serverList.includes(Pm10ConcentrationMeasurement.Cluster.id))
|
|
309
|
-
endpoint.createDefaultPm10ConcentrationMeasurementClusterServer();
|
|
310
|
-
if (serverList.includes(RadonConcentrationMeasurement.Cluster.id))
|
|
311
|
-
endpoint.createDefaultRadonConcentrationMeasurementClusterServer();
|
|
312
|
-
if (serverList.includes(TotalVolatileOrganicCompoundsConcentrationMeasurement.Cluster.id))
|
|
313
|
-
endpoint.createDefaultTvocMeasurementClusterServer();
|
|
314
|
-
}
|
|
315
|
-
export function optionsFor(type, options) {
|
|
316
|
-
return options;
|
|
317
|
-
}
|
|
318
57
|
export class MatterbridgeEndpoint extends Endpoint {
|
|
319
58
|
static bridgeMode = '';
|
|
320
59
|
static logLevel = "info";
|
|
@@ -337,7 +76,6 @@ export class MatterbridgeEndpoint extends Endpoint {
|
|
|
337
76
|
deviceType;
|
|
338
77
|
uniqueStorageKey = undefined;
|
|
339
78
|
tagList = undefined;
|
|
340
|
-
subType = '';
|
|
341
79
|
deviceTypes = new Map();
|
|
342
80
|
commandHandler = new NamedHandler();
|
|
343
81
|
constructor(definition, options = {}, debug = false) {
|
|
@@ -412,7 +150,8 @@ export class MatterbridgeEndpoint extends Endpoint {
|
|
|
412
150
|
if (!behavior || !this.behaviors.supported[behavior.id])
|
|
413
151
|
return false;
|
|
414
152
|
const options = this.behaviors.optionsFor(behavior);
|
|
415
|
-
|
|
153
|
+
const defaults = this.behaviors.defaultsFor(behavior);
|
|
154
|
+
return lowercaseFirstLetter(attribute) in options || lowercaseFirstLetter(attribute) in defaults;
|
|
416
155
|
}
|
|
417
156
|
getClusterServerOptions(cluster) {
|
|
418
157
|
const behavior = getBehavior(this, cluster);
|
|
@@ -420,50 +159,14 @@ export class MatterbridgeEndpoint extends Endpoint {
|
|
|
420
159
|
return undefined;
|
|
421
160
|
return this.behaviors.optionsFor(behavior);
|
|
422
161
|
}
|
|
423
|
-
getAttribute(
|
|
424
|
-
|
|
425
|
-
if (this.construction.status !== Lifecycle.Status.Active) {
|
|
426
|
-
this.log.error(`getAttribute ${hk}${clusterName}.${attribute}${er} error: Endpoint ${or}${this.maybeId}${er}:${or}${this.maybeNumber}${er} is in the ${BLUE}${this.construction.status}${er} state`);
|
|
427
|
-
return undefined;
|
|
428
|
-
}
|
|
429
|
-
const state = this.state;
|
|
430
|
-
if (!(clusterName in state)) {
|
|
431
|
-
this.log.error(`getAttribute error: Cluster ${'0x' + clusterId.toString(16).padStart(4, '0')}:${clusterName} not found on endpoint ${or}${this.id}${er}:${or}${this.number}${er}`);
|
|
432
|
-
return undefined;
|
|
433
|
-
}
|
|
434
|
-
attribute = lowercaseFirstLetter(attribute);
|
|
435
|
-
if (!(attribute in state[clusterName])) {
|
|
436
|
-
this.log.error(`getAttribute error: Attribute ${hk}${attribute}${er} not found on Cluster ${'0x' + clusterId.toString(16).padStart(4, '0')}:${clusterName} on endpoint ${or}${this.id}${er}:${or}${this.number}${er}`);
|
|
437
|
-
return undefined;
|
|
438
|
-
}
|
|
439
|
-
const value = state[clusterName][attribute];
|
|
440
|
-
log?.info(`${db}Get endpoint ${or}${this.id}${db}:${or}${this.number}${db} attribute ${hk}${capitalizeFirstLetter(clusterName)}${db}.${hk}${attribute}${db} value ${YELLOW}${value !== null && typeof value === 'object' ? debugStringify(value) : value}${db}`);
|
|
441
|
-
return value;
|
|
162
|
+
getAttribute(cluster, attribute, log) {
|
|
163
|
+
return getAttribute(this, cluster, attribute, log);
|
|
442
164
|
}
|
|
443
165
|
async setAttribute(clusterId, attribute, value, log) {
|
|
444
|
-
|
|
445
|
-
|
|
446
|
-
|
|
447
|
-
|
|
448
|
-
}
|
|
449
|
-
const state = this.state;
|
|
450
|
-
if (!(clusterName in state)) {
|
|
451
|
-
this.log.error(`setAttribute ${hk}${attribute}${er} error: Cluster ${'0x' + clusterId.toString(16).padStart(4, '0')}:${clusterName} not found on endpoint ${or}${this.id}${er}:${or}${this.number}${er}`);
|
|
452
|
-
return false;
|
|
453
|
-
}
|
|
454
|
-
attribute = lowercaseFirstLetter(attribute);
|
|
455
|
-
if (!(attribute in state[clusterName])) {
|
|
456
|
-
this.log.error(`setAttribute error: Attribute ${hk}${attribute}${er} not found on Cluster ${'0x' + clusterId.toString(16).padStart(4, '0')}:${clusterName} on endpoint ${or}${this.id}${er}:${or}${this.number}${er}`);
|
|
457
|
-
return false;
|
|
458
|
-
}
|
|
459
|
-
let oldValue = state[clusterName][attribute];
|
|
460
|
-
if (typeof oldValue === 'object')
|
|
461
|
-
oldValue = deepCopy(oldValue);
|
|
462
|
-
await this.setStateOf(this.behaviors.supported[clusterName], { [attribute]: value });
|
|
463
|
-
log?.info(`${db}Set endpoint ${or}${this.id}${db}:${or}${this.number}${db} attribute ${hk}${capitalizeFirstLetter(clusterName)}${db}.${hk}${attribute}${db} ` +
|
|
464
|
-
`from ${YELLOW}${oldValue !== null && typeof oldValue === 'object' ? debugStringify(oldValue) : oldValue}${db} ` +
|
|
465
|
-
`to ${YELLOW}${value !== null && typeof value === 'object' ? debugStringify(value) : value}${db}`);
|
|
466
|
-
return true;
|
|
166
|
+
return await setAttribute(this, clusterId, attribute, value, log);
|
|
167
|
+
}
|
|
168
|
+
async updateAttribute(cluster, attribute, value, log) {
|
|
169
|
+
return await updateAttribute(this, cluster, attribute, value, log);
|
|
467
170
|
}
|
|
468
171
|
async subscribeAttribute(clusterId, attribute, listener, log) {
|
|
469
172
|
const clusterName = lowercaseFirstLetter(getClusterNameById(clusterId));
|
|
@@ -484,52 +187,30 @@ export class MatterbridgeEndpoint extends Endpoint {
|
|
|
484
187
|
log?.info(`${db}Subscribed endpoint ${or}${this.id}${db}:${or}${this.number}${db} attribute ${hk}${capitalizeFirstLetter(clusterName)}${db}.${hk}${attribute}${db}`);
|
|
485
188
|
return true;
|
|
486
189
|
}
|
|
487
|
-
async triggerEvent(clusterId, event, payload, log
|
|
488
|
-
if (!endpoint)
|
|
489
|
-
endpoint = this;
|
|
190
|
+
async triggerEvent(clusterId, event, payload, log) {
|
|
490
191
|
const clusterName = lowercaseFirstLetter(getClusterNameById(clusterId));
|
|
491
|
-
if (
|
|
492
|
-
this.log.error(`triggerEvent ${hk}${clusterName}.${event}${er} error: Endpoint ${or}${
|
|
192
|
+
if (this.construction.status !== Lifecycle.Status.Active) {
|
|
193
|
+
this.log.error(`triggerEvent ${hk}${clusterName}.${event}${er} error: Endpoint ${or}${this.maybeId}${er}:${or}${this.maybeNumber}${er} is in the ${BLUE}${this.construction.status}${er} state`);
|
|
493
194
|
return false;
|
|
494
195
|
}
|
|
495
|
-
const events =
|
|
196
|
+
const events = this.events;
|
|
496
197
|
if (!(clusterName in events) || !(event in events[clusterName])) {
|
|
497
|
-
this.log.error(`triggerEvent ${hk}${event}${er} error: Cluster ${'0x' + clusterId.toString(16).padStart(4, '0')}:${clusterName} not found on endpoint ${or}${
|
|
198
|
+
this.log.error(`triggerEvent ${hk}${event}${er} error: Cluster ${'0x' + clusterId.toString(16).padStart(4, '0')}:${clusterName} not found on endpoint ${or}${this.id}${er}:${or}${this.number}${er}`);
|
|
498
199
|
return false;
|
|
499
200
|
}
|
|
500
|
-
await
|
|
501
|
-
log?.info(`${db}Trigger event ${hk}${capitalizeFirstLetter(clusterName)}${db}.${hk}${event}${db} with ${debugStringify(payload)}${db} on endpoint ${or}${
|
|
201
|
+
await this.act((agent) => agent[clusterName].events[event].emit(payload, agent.context));
|
|
202
|
+
log?.info(`${db}Trigger event ${hk}${capitalizeFirstLetter(clusterName)}${db}.${hk}${event}${db} with ${debugStringify(payload)}${db} on endpoint ${or}${this.id}${db}:${or}${this.number}${db} `);
|
|
502
203
|
return true;
|
|
503
204
|
}
|
|
504
205
|
addClusterServers(serverList) {
|
|
505
206
|
addClusterServers(this, serverList);
|
|
506
207
|
}
|
|
507
208
|
async addFixedLabel(label, value) {
|
|
508
|
-
|
|
509
|
-
this.log.debug(`addFixedLabel: add cluster ${hk}FixedLabel${db}:${hk}fixedLabel${db} with label ${CYAN}${label}${db} value ${CYAN}${value}${db}`);
|
|
510
|
-
this.behaviors.require(FixedLabelServer, {
|
|
511
|
-
labelList: [{ label, value }],
|
|
512
|
-
});
|
|
513
|
-
return this;
|
|
514
|
-
}
|
|
515
|
-
this.log.debug(`addFixedLabel: add label ${CYAN}${label}${db} value ${CYAN}${value}${db}`);
|
|
516
|
-
const labelList = (this.getAttribute(FixedLabel.Cluster.id, 'labelList', this.log) ?? []).filter((entryLabel) => entryLabel.label !== label);
|
|
517
|
-
labelList.push({ label, value });
|
|
518
|
-
await this.setAttribute(FixedLabel.Cluster.id, 'labelList', labelList, this.log);
|
|
209
|
+
await addFixedLabel(this, label, value);
|
|
519
210
|
return this;
|
|
520
211
|
}
|
|
521
212
|
async addUserLabel(label, value) {
|
|
522
|
-
|
|
523
|
-
this.log.debug(`addUserLabel: add cluster ${hk}UserLabel${db}:${hk}userLabel${db} with label ${CYAN}${label}${db} value ${CYAN}${value}${db}`);
|
|
524
|
-
this.behaviors.require(UserLabelServer, {
|
|
525
|
-
labelList: [{ label, value }],
|
|
526
|
-
});
|
|
527
|
-
return this;
|
|
528
|
-
}
|
|
529
|
-
this.log.debug(`addUserLabel: add label ${CYAN}${label}${db} value ${CYAN}${value}${db}`);
|
|
530
|
-
const labelList = (this.getAttribute(UserLabel.Cluster.id, 'labelList', this.log) ?? []).filter((entryLabel) => entryLabel.label !== label);
|
|
531
|
-
labelList.push({ label, value });
|
|
532
|
-
await this.setAttribute(UserLabel.Cluster.id, 'labelList', labelList, this.log);
|
|
213
|
+
await addUserLabel(this, label, value);
|
|
533
214
|
return this;
|
|
534
215
|
}
|
|
535
216
|
addCommandHandler(command, handler) {
|
|
@@ -547,6 +228,27 @@ export class MatterbridgeEndpoint extends Endpoint {
|
|
|
547
228
|
addOptionalClusterServers(this);
|
|
548
229
|
return this;
|
|
549
230
|
}
|
|
231
|
+
getAllClusterServers() {
|
|
232
|
+
return Object.values(this.behaviors.supported);
|
|
233
|
+
}
|
|
234
|
+
getAllClusterServerNames() {
|
|
235
|
+
return Object.keys(this.behaviors.supported);
|
|
236
|
+
}
|
|
237
|
+
forEachAttribute(callback) {
|
|
238
|
+
for (const [clusterName, clusterAttributes] of Object.entries(this.state)) {
|
|
239
|
+
for (const [attributeName, attributeValue] of Object.entries(clusterAttributes)) {
|
|
240
|
+
const clusterId = getClusterId(this, clusterName);
|
|
241
|
+
if (clusterId === undefined) {
|
|
242
|
+
continue;
|
|
243
|
+
}
|
|
244
|
+
const attributeId = getAttributeId(this, clusterName, attributeName);
|
|
245
|
+
if (attributeId === undefined) {
|
|
246
|
+
continue;
|
|
247
|
+
}
|
|
248
|
+
callback(clusterName, clusterId, attributeName, attributeId, attributeValue);
|
|
249
|
+
}
|
|
250
|
+
}
|
|
251
|
+
}
|
|
550
252
|
addChildDeviceType(endpointName, definition, options = {}, debug = false) {
|
|
551
253
|
this.log.debug(`addChildDeviceType: ${CYAN}${endpointName}${db}`);
|
|
552
254
|
let alreadyAdded = false;
|
|
@@ -937,7 +639,6 @@ export class MatterbridgeEndpoint extends Endpoint {
|
|
|
937
639
|
await this.setAttribute(ColorControl.Cluster.id, 'colorMode', colorMode, this.log);
|
|
938
640
|
await this.setAttribute(ColorControl.Cluster.id, 'enhancedColorMode', colorMode, this.log);
|
|
939
641
|
}
|
|
940
|
-
return this;
|
|
941
642
|
}
|
|
942
643
|
createDefaultWindowCoveringClusterServer(positionPercent100ths) {
|
|
943
644
|
this.behaviors.require(MatterbridgeWindowCoveringServer.with(WindowCovering.Feature.Lift, WindowCovering.Feature.PositionAwareLift), {
|
|
@@ -961,7 +662,7 @@ export class MatterbridgeEndpoint extends Endpoint {
|
|
|
961
662
|
}
|
|
962
663
|
async setWindowCoveringTargetAsCurrentAndStopped() {
|
|
963
664
|
const position = this.getAttribute(WindowCovering.Cluster.id, 'currentPositionLiftPercent100ths', this.log);
|
|
964
|
-
if (position
|
|
665
|
+
if (isValidNumber(position, 0, 10000)) {
|
|
965
666
|
await this.setAttribute(WindowCovering.Cluster.id, 'targetPositionLiftPercent100ths', position, this.log);
|
|
966
667
|
await this.setAttribute(WindowCovering.Cluster.id, 'operationalStatus', {
|
|
967
668
|
global: WindowCovering.MovementStatus.Stopped,
|
|
@@ -991,8 +692,10 @@ export class MatterbridgeEndpoint extends Endpoint {
|
|
|
991
692
|
}
|
|
992
693
|
getWindowCoveringStatus() {
|
|
993
694
|
const status = this.getAttribute(WindowCovering.Cluster.id, 'operationalStatus', this.log);
|
|
994
|
-
|
|
995
|
-
|
|
695
|
+
if (isValidObject(status, 3) && 'global' in status && typeof status.global === 'number') {
|
|
696
|
+
this.log.debug(`Get WindowCovering operationalStatus: ${status.global}`);
|
|
697
|
+
return status.global;
|
|
698
|
+
}
|
|
996
699
|
}
|
|
997
700
|
async setWindowCoveringTargetAndCurrentPosition(position) {
|
|
998
701
|
await this.setAttribute(WindowCovering.Cluster.id, 'currentPositionLiftPercent100ths', position, this.log);
|
|
@@ -1121,7 +824,7 @@ export class MatterbridgeEndpoint extends Endpoint {
|
|
|
1121
824
|
return this;
|
|
1122
825
|
}
|
|
1123
826
|
createDefaultSwitchClusterServer() {
|
|
1124
|
-
this.behaviors.require(
|
|
827
|
+
this.behaviors.require(MatterbridgeSwitchServer.with(Switch.Feature.MomentarySwitch, Switch.Feature.MomentarySwitchRelease, Switch.Feature.MomentarySwitchLongPress, Switch.Feature.MomentarySwitchMultiPress).enable({
|
|
1125
828
|
events: { initialPress: true, longPress: true, shortRelease: true, longRelease: true, multiPressOngoing: true, multiPressComplete: true },
|
|
1126
829
|
}), {
|
|
1127
830
|
numberOfPositions: 2,
|
|
@@ -1280,76 +983,28 @@ export class MatterbridgeEndpoint extends Endpoint {
|
|
|
1280
983
|
});
|
|
1281
984
|
return this;
|
|
1282
985
|
}
|
|
1283
|
-
getDefaultTemperatureMeasurementClusterServer(measuredValue = 0) {
|
|
1284
|
-
return optionsFor(TemperatureMeasurementServer, {
|
|
1285
|
-
measuredValue,
|
|
1286
|
-
minMeasuredValue: null,
|
|
1287
|
-
maxMeasuredValue: null,
|
|
1288
|
-
tolerance: 0,
|
|
1289
|
-
});
|
|
1290
|
-
}
|
|
1291
986
|
createDefaultTemperatureMeasurementClusterServer(measuredValue = 0) {
|
|
1292
|
-
this.behaviors.require(TemperatureMeasurementServer,
|
|
987
|
+
this.behaviors.require(TemperatureMeasurementServer, getDefaultTemperatureMeasurementClusterServer(measuredValue));
|
|
1293
988
|
return this;
|
|
1294
989
|
}
|
|
1295
|
-
getDefaultRelativeHumidityMeasurementClusterServer(measuredValue = 0) {
|
|
1296
|
-
return optionsFor(RelativeHumidityMeasurementServer, {
|
|
1297
|
-
measuredValue,
|
|
1298
|
-
minMeasuredValue: null,
|
|
1299
|
-
maxMeasuredValue: null,
|
|
1300
|
-
tolerance: 0,
|
|
1301
|
-
});
|
|
1302
|
-
}
|
|
1303
990
|
createDefaultRelativeHumidityMeasurementClusterServer(measuredValue = 0) {
|
|
1304
|
-
this.behaviors.require(RelativeHumidityMeasurementServer,
|
|
991
|
+
this.behaviors.require(RelativeHumidityMeasurementServer, getDefaultRelativeHumidityMeasurementClusterServer(measuredValue));
|
|
1305
992
|
return this;
|
|
1306
993
|
}
|
|
1307
|
-
getDefaultPressureMeasurementClusterServer(measuredValue = 1000) {
|
|
1308
|
-
return optionsFor(PressureMeasurementServer, {
|
|
1309
|
-
measuredValue,
|
|
1310
|
-
minMeasuredValue: null,
|
|
1311
|
-
maxMeasuredValue: null,
|
|
1312
|
-
tolerance: 0,
|
|
1313
|
-
});
|
|
1314
|
-
}
|
|
1315
994
|
createDefaultPressureMeasurementClusterServer(measuredValue = 1000) {
|
|
1316
|
-
this.behaviors.require(PressureMeasurementServer,
|
|
995
|
+
this.behaviors.require(PressureMeasurementServer, getDefaultPressureMeasurementClusterServer(measuredValue));
|
|
1317
996
|
return this;
|
|
1318
997
|
}
|
|
1319
|
-
getDefaultIlluminanceMeasurementClusterServer(measuredValue = 0) {
|
|
1320
|
-
return optionsFor(IlluminanceMeasurementServer, {
|
|
1321
|
-
measuredValue,
|
|
1322
|
-
minMeasuredValue: null,
|
|
1323
|
-
maxMeasuredValue: null,
|
|
1324
|
-
tolerance: 0,
|
|
1325
|
-
});
|
|
1326
|
-
}
|
|
1327
998
|
createDefaultIlluminanceMeasurementClusterServer(measuredValue = 0) {
|
|
1328
|
-
this.behaviors.require(IlluminanceMeasurementServer,
|
|
999
|
+
this.behaviors.require(IlluminanceMeasurementServer, getDefaultIlluminanceMeasurementClusterServer(measuredValue));
|
|
1329
1000
|
return this;
|
|
1330
1001
|
}
|
|
1331
|
-
getDefaultFlowMeasurementClusterServer(measuredValue = 0) {
|
|
1332
|
-
return optionsFor(FlowMeasurementServer, {
|
|
1333
|
-
measuredValue,
|
|
1334
|
-
minMeasuredValue: null,
|
|
1335
|
-
maxMeasuredValue: null,
|
|
1336
|
-
tolerance: 0,
|
|
1337
|
-
});
|
|
1338
|
-
}
|
|
1339
1002
|
createDefaultFlowMeasurementClusterServer(measuredValue = 0) {
|
|
1340
|
-
this.behaviors.require(FlowMeasurementServer,
|
|
1003
|
+
this.behaviors.require(FlowMeasurementServer, getDefaultFlowMeasurementClusterServer(measuredValue));
|
|
1341
1004
|
return this;
|
|
1342
1005
|
}
|
|
1343
|
-
getDefaultOccupancySensingClusterServer(occupied = false) {
|
|
1344
|
-
return optionsFor(OccupancySensingServer, {
|
|
1345
|
-
occupancy: { occupied },
|
|
1346
|
-
occupancySensorType: OccupancySensing.OccupancySensorType.Pir,
|
|
1347
|
-
occupancySensorTypeBitmap: { pir: true, ultrasonic: false, physicalContact: false },
|
|
1348
|
-
pirOccupiedToUnoccupiedDelay: 30,
|
|
1349
|
-
});
|
|
1350
|
-
}
|
|
1351
1006
|
createDefaultOccupancySensingClusterServer(occupied = false) {
|
|
1352
|
-
this.behaviors.require(OccupancySensingServer,
|
|
1007
|
+
this.behaviors.require(OccupancySensingServer, getDefaultOccupancySensingClusterServer(occupied));
|
|
1353
1008
|
return this;
|
|
1354
1009
|
}
|
|
1355
1010
|
createDefaultAirQualityClusterServer(airQuality = AirQuality.AirQualityEnum.Unknown) {
|