@matterbridge/core 3.10.9-dev-20260906-2a9dc0e → 3.10.9-dev-20260907-5fcc59a
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/dist/chipTests.js +47 -5
- package/dist/demoDevices.js +14 -0
- package/dist/devices/evse.d.ts +28 -5
- package/dist/devices/evse.js +145 -30
- package/dist/matterbridgeEndpointCommandHandler.d.ts +8 -0
- package/package.json +5 -5
package/dist/chipTests.js
CHANGED
|
@@ -4,7 +4,7 @@ import { Seconds, Time } from '@matter/general';
|
|
|
4
4
|
import { BasicInformationServer } from '@matter/node/behaviors/basic-information';
|
|
5
5
|
import { BridgedDeviceBasicInformationServer } from '@matter/node/behaviors/bridged-device-basic-information';
|
|
6
6
|
import { GeneralDiagnosticsServer } from '@matter/node/behaviors/general-diagnostics';
|
|
7
|
-
import { Status, StatusResponseError } from '@matter/types';
|
|
7
|
+
import { MATTER_EPOCH_OFFSET_S, Status, StatusResponseError } from '@matter/types';
|
|
8
8
|
import { BooleanStateConfiguration } from '@matter/types/clusters/boolean-state-configuration';
|
|
9
9
|
import { ClosureControl } from '@matter/types/clusters/closure-control';
|
|
10
10
|
import { CommodityMetering } from '@matter/types/clusters/commodity-metering';
|
|
@@ -70,6 +70,11 @@ const energyEvseOverTemperatureFaultTrigger = 0x0099000000000011n;
|
|
|
70
70
|
const energyEvseFaultClearTrigger = 0x0099000000000012n;
|
|
71
71
|
const energyEvseDiagnosticsCompleteTrigger = 0x0099000000000020n;
|
|
72
72
|
const energyEvseTimeOfUseModeClearTrigger = 0x0099000000000021n;
|
|
73
|
+
const energyEvseSetSocLowTrigger = 0x0099000000000030n;
|
|
74
|
+
const energyEvseSetSocHighTrigger = 0x0099000000000031n;
|
|
75
|
+
const energyEvseSetSocClearTrigger = 0x0099000000000032n;
|
|
76
|
+
const energyEvseSetVehicleIdTrigger = 0x0099000000000040n;
|
|
77
|
+
const energyEvseRfidTrigger = 0x0099000000000050n;
|
|
73
78
|
const meterIdentificationAttributesValueSetTrigger = 0x0b06000000000000n;
|
|
74
79
|
const meterIdentificationTestEventClearTrigger = 0x0b06000000000001n;
|
|
75
80
|
const commodityMeteringAttributesValueSetTrigger = 0x0b07000000000000n;
|
|
@@ -296,6 +301,11 @@ async function handleEnergyEvseTestEventTrigger(eventTrigger) {
|
|
|
296
301
|
normalizeTestEventTrigger(energyEvseFaultClearTrigger),
|
|
297
302
|
normalizeTestEventTrigger(energyEvseDiagnosticsCompleteTrigger),
|
|
298
303
|
normalizeTestEventTrigger(energyEvseTimeOfUseModeClearTrigger),
|
|
304
|
+
normalizeTestEventTrigger(energyEvseSetSocLowTrigger),
|
|
305
|
+
normalizeTestEventTrigger(energyEvseSetSocHighTrigger),
|
|
306
|
+
normalizeTestEventTrigger(energyEvseSetSocClearTrigger),
|
|
307
|
+
normalizeTestEventTrigger(energyEvseSetVehicleIdTrigger),
|
|
308
|
+
normalizeTestEventTrigger(energyEvseRfidTrigger),
|
|
299
309
|
];
|
|
300
310
|
if (!supportedTriggers.includes(eventTrigger) || !chipTestMatterbridge || chipTestActiveEndpointId === undefined)
|
|
301
311
|
return false;
|
|
@@ -316,6 +326,9 @@ async function handleEnergyEvseTestEventTrigger(eventTrigger) {
|
|
|
316
326
|
minimumChargeCurrent: 6_000,
|
|
317
327
|
maximumChargeCurrent: 32_000,
|
|
318
328
|
userMaximumChargeCurrent: 32_000,
|
|
329
|
+
chargingEnabledUntil: MATTER_EPOCH_OFFSET_S,
|
|
330
|
+
...(endpoint.hasAttributeServer(EnergyEvse.id, 'dischargingEnabledUntil') ? { dischargingEnabledUntil: MATTER_EPOCH_OFFSET_S } : {}),
|
|
331
|
+
...(endpoint.hasAttributeServer(EnergyEvse.id, 'maximumDischargeCurrent') ? { maximumDischargeCurrent: 0 } : {}),
|
|
319
332
|
}, log);
|
|
320
333
|
return true;
|
|
321
334
|
case normalizeTestEventTrigger(energyEvseBasicClearTrigger):
|
|
@@ -323,7 +336,13 @@ async function handleEnergyEvseTestEventTrigger(eventTrigger) {
|
|
|
323
336
|
case normalizeTestEventTrigger(energyEvsePluggedInTrigger): {
|
|
324
337
|
const nextSessionId = sessionId + 1;
|
|
325
338
|
energyEvseSessionStartedAt.set(chipTestActiveEndpointId, Time.nowMs);
|
|
326
|
-
await endpoint.setCluster(EnergyEvse, {
|
|
339
|
+
await endpoint.setCluster(EnergyEvse, {
|
|
340
|
+
state: EnergyEvse.State.PluggedInNoDemand,
|
|
341
|
+
sessionId: nextSessionId,
|
|
342
|
+
sessionDuration: 0,
|
|
343
|
+
sessionEnergyCharged: 0,
|
|
344
|
+
...(endpoint.hasAttributeServer(EnergyEvse.id, 'sessionEnergyDischarged') ? { sessionEnergyDischarged: 0 } : {}),
|
|
345
|
+
}, log);
|
|
327
346
|
await endpoint.triggerEvent(EnergyEvse, 'evConnected', { sessionId: nextSessionId }, log);
|
|
328
347
|
return true;
|
|
329
348
|
}
|
|
@@ -331,18 +350,26 @@ async function handleEnergyEvseTestEventTrigger(eventTrigger) {
|
|
|
331
350
|
const sessionStartedAt = energyEvseSessionStartedAt.get(chipTestActiveEndpointId);
|
|
332
351
|
const sessionDuration = sessionStartedAt === undefined ? 0 : Math.floor((Time.nowMs - sessionStartedAt) / 1_000);
|
|
333
352
|
await endpoint.triggerEvent(EnergyEvse, 'evNotDetected', { sessionId, state: EnergyEvse.State.PluggedInNoDemand, sessionDuration, sessionEnergyCharged: 1 }, log);
|
|
334
|
-
await endpoint.setCluster(EnergyEvse, {
|
|
353
|
+
await endpoint.setCluster(EnergyEvse, {
|
|
354
|
+
state: EnergyEvse.State.NotPluggedIn,
|
|
355
|
+
sessionDuration,
|
|
356
|
+
sessionEnergyCharged: 1,
|
|
357
|
+
...(endpoint.hasAttributeServer(EnergyEvse.id, 'sessionEnergyDischarged') ? { sessionEnergyDischarged: 1 } : {}),
|
|
358
|
+
}, log);
|
|
335
359
|
energyEvseSessionStartedAt.delete(chipTestActiveEndpointId);
|
|
336
360
|
return true;
|
|
337
361
|
}
|
|
338
362
|
case normalizeTestEventTrigger(energyEvseChargeDemandTrigger): {
|
|
339
|
-
const
|
|
363
|
+
const supplyState = endpoint.getAttribute(EnergyEvse.id, 'supplyState');
|
|
364
|
+
const charging = supplyState === EnergyEvse.SupplyState.ChargingEnabled || supplyState === EnergyEvse.SupplyState.Enabled;
|
|
340
365
|
const nextState = charging ? EnergyEvse.State.PluggedInCharging : EnergyEvse.State.PluggedInDemand;
|
|
341
366
|
await endpoint.setCluster(EnergyEvse, { state: nextState }, log);
|
|
342
367
|
if (charging) {
|
|
343
368
|
const maximumChargeCurrentAttribute = endpoint.getAttribute(EnergyEvse.id, 'maximumChargeCurrent');
|
|
344
369
|
const maximumCurrent = typeof maximumChargeCurrentAttribute === 'number' || typeof maximumChargeCurrentAttribute === 'bigint' ? maximumChargeCurrentAttribute : 0;
|
|
345
|
-
|
|
370
|
+
const maximumDischargeCurrentAttribute = endpoint.getAttribute(EnergyEvse.id, 'maximumDischargeCurrent');
|
|
371
|
+
const maximumDischargeCurrent = typeof maximumDischargeCurrentAttribute === 'number' || typeof maximumDischargeCurrentAttribute === 'bigint' ? maximumDischargeCurrentAttribute : undefined;
|
|
372
|
+
await endpoint.triggerEvent(EnergyEvse, 'energyTransferStarted', { sessionId, state: nextState, maximumCurrent, maximumDischargeCurrent }, log);
|
|
346
373
|
}
|
|
347
374
|
return true;
|
|
348
375
|
}
|
|
@@ -372,6 +399,21 @@ async function handleEnergyEvseTestEventTrigger(eventTrigger) {
|
|
|
372
399
|
case normalizeTestEventTrigger(energyEvseDiagnosticsCompleteTrigger):
|
|
373
400
|
await endpoint.setCluster(EnergyEvse, { state: EnergyEvse.State.NotPluggedIn, supplyState: EnergyEvse.SupplyState.Disabled }, log);
|
|
374
401
|
return true;
|
|
402
|
+
case normalizeTestEventTrigger(energyEvseSetSocLowTrigger):
|
|
403
|
+
await endpoint.setCluster(EnergyEvse, { stateOfCharge: 20, batteryCapacity: 70_000_000 }, log);
|
|
404
|
+
return true;
|
|
405
|
+
case normalizeTestEventTrigger(energyEvseSetSocHighTrigger):
|
|
406
|
+
await endpoint.setCluster(EnergyEvse, { stateOfCharge: 95, batteryCapacity: 70_000_000 }, log);
|
|
407
|
+
return true;
|
|
408
|
+
case normalizeTestEventTrigger(energyEvseSetSocClearTrigger):
|
|
409
|
+
await endpoint.setCluster(EnergyEvse, { stateOfCharge: null, batteryCapacity: null }, log);
|
|
410
|
+
return true;
|
|
411
|
+
case normalizeTestEventTrigger(energyEvseSetVehicleIdTrigger):
|
|
412
|
+
await endpoint.setAttribute(EnergyEvse.id, 'vehicleId', 'Matterbridge EVSE', log);
|
|
413
|
+
return true;
|
|
414
|
+
case normalizeTestEventTrigger(energyEvseRfidTrigger):
|
|
415
|
+
await endpoint.triggerEvent(EnergyEvse, 'rfid', { uid: Uint8Array.of(0x4d, 0x42, 0x45, 0x56, 0x53, 0x45) }, log);
|
|
416
|
+
return true;
|
|
375
417
|
default:
|
|
376
418
|
return false;
|
|
377
419
|
}
|
package/dist/demoDevices.js
CHANGED
|
@@ -740,6 +740,20 @@ export async function createDemoDevices(matterbridge) {
|
|
|
740
740
|
tagList: [getSemtag(CommonNumberTag.One)],
|
|
741
741
|
});
|
|
742
742
|
await registerDevice(ep, 'EVSE', 'ENERGY-14-01');
|
|
743
|
+
ep = new Evse('EVSE Complete', 'ENERGY-14-01-1', {
|
|
744
|
+
id: 'EvseComplete',
|
|
745
|
+
number: EndpointNumber(14_01_1),
|
|
746
|
+
tagList: [getSemtag(CommonNumberTag.Two)],
|
|
747
|
+
stateOfCharge: 80,
|
|
748
|
+
batteryCapacity: 70_000_000,
|
|
749
|
+
vehicleId: null,
|
|
750
|
+
rfid: true,
|
|
751
|
+
v2x: true,
|
|
752
|
+
esaCanGenerate: true,
|
|
753
|
+
absMinPower: -7_400_000,
|
|
754
|
+
absMaxPower: 7_400_000,
|
|
755
|
+
});
|
|
756
|
+
await registerDevice(ep, 'EVSE Complete', 'ENERGY-14-01-1');
|
|
743
757
|
ep = new WaterHeater('Water Heater', 'ENERGY-14-02', {
|
|
744
758
|
id: 'WaterHeater',
|
|
745
759
|
number: EndpointNumber(14_02),
|
package/dist/devices/evse.d.ts
CHANGED
|
@@ -6,7 +6,9 @@ import { EnergyEvse } from '@matter/types/clusters/energy-evse';
|
|
|
6
6
|
import { EnergyEvseMode } from '@matter/types/clusters/energy-evse-mode';
|
|
7
7
|
import { ModeBase } from '@matter/types/clusters/mode-base';
|
|
8
8
|
import type { Semtag } from '@matter/types/globals';
|
|
9
|
+
import { type AnsiLogger } from 'node-ansi-logger';
|
|
9
10
|
import { MatterbridgeEndpoint } from '../matterbridgeEndpoint.js';
|
|
11
|
+
import type { ClusterAttributeValues } from '../matterbridgeEndpointCommandHandler.js';
|
|
10
12
|
export interface EvseOptions {
|
|
11
13
|
mode?: 'server' | 'matter';
|
|
12
14
|
id?: string;
|
|
@@ -23,12 +25,19 @@ export interface EvseOptions {
|
|
|
23
25
|
energy?: number | bigint | null;
|
|
24
26
|
absMinPower?: number;
|
|
25
27
|
absMaxPower?: number;
|
|
28
|
+
esaCanGenerate?: boolean;
|
|
29
|
+
stateOfCharge?: number | null;
|
|
30
|
+
batteryCapacity?: number | bigint | null;
|
|
31
|
+
vehicleId?: string | null;
|
|
32
|
+
rfid?: boolean;
|
|
33
|
+
v2x?: boolean;
|
|
26
34
|
}
|
|
27
35
|
export declare class Evse extends MatterbridgeEndpoint {
|
|
28
36
|
constructor(name: string, serial: string, options?: EvseOptions);
|
|
29
37
|
constructor(name: string, serial: string, currentMode?: number, supportedModes?: EnergyEvseMode.ModeOption[], state?: EnergyEvse.State, supplyState?: EnergyEvse.SupplyState, faultState?: EnergyEvse.FaultState, voltage?: number | bigint | null, current?: number | bigint | null, power?: number | bigint | null, energy?: number | bigint | null, absMinPower?: number, absMaxPower?: number);
|
|
30
|
-
createDefaultEnergyEvseClusterServer(state?: EnergyEvse.State, supplyState?: EnergyEvse.SupplyState, faultState?: EnergyEvse.FaultState): this;
|
|
31
|
-
createDefaultEnergyEvseModeClusterServer(currentMode?: number, supportedModes?: EnergyEvseMode.ModeOption[]): this;
|
|
38
|
+
createDefaultEnergyEvseClusterServer(state?: EnergyEvse.State, supplyState?: EnergyEvse.SupplyState, faultState?: EnergyEvse.FaultState, stateOfCharge?: number | null, batteryCapacity?: number | bigint | null, vehicleId?: string | null, rfid?: boolean, v2x?: boolean): this;
|
|
39
|
+
createDefaultEnergyEvseModeClusterServer(currentMode?: number, supportedModes?: EnergyEvseMode.ModeOption[], v2x?: boolean): this;
|
|
40
|
+
triggerRfidEvent(uid: Uint8Array, log?: AnsiLogger): Promise<boolean>;
|
|
32
41
|
}
|
|
33
42
|
declare const MatterbridgeEnergyEvseServer_base: import("@matter/node").ClusterBehavior.Type<typeof EnergyEvseServer, import("@matter/types").ClusterType.WithSupportedFeatures<EnergyEvse, {
|
|
34
43
|
chargingPreferences: true;
|
|
@@ -40,21 +49,35 @@ declare const MatterbridgeEnergyEvseServer_base: import("@matter/node").ClusterB
|
|
|
40
49
|
export declare class MatterbridgeEnergyEvseServer extends MatterbridgeEnergyEvseServer_base {
|
|
41
50
|
#private;
|
|
42
51
|
protected internal: MatterbridgeEnergyEvseServer.Internal;
|
|
52
|
+
state: ClusterAttributeValues<(typeof EnergyEvse)['attributes']> & MatterbridgeEnergyEvseServer.State;
|
|
43
53
|
initialize(): Promise<void>;
|
|
44
54
|
disable(): Promise<void>;
|
|
45
55
|
enableCharging(request: EnergyEvse.EnableChargingRequest): Promise<void>;
|
|
56
|
+
enableDischarging(request: EnergyEvse.EnableDischargingRequest): Promise<void>;
|
|
46
57
|
startDiagnostics(): Promise<void>;
|
|
47
58
|
setTargets(request: EnergyEvse.SetTargetsRequest): Promise<void>;
|
|
48
59
|
getTargets(): Promise<EnergyEvse.GetTargetsResponse>;
|
|
49
60
|
clearTargets(): Promise<void>;
|
|
50
61
|
}
|
|
51
62
|
export declare namespace MatterbridgeEnergyEvseServer {
|
|
52
|
-
class Internal {
|
|
63
|
+
export class Internal {
|
|
53
64
|
chargingExpiryTimer: Timer | undefined;
|
|
54
|
-
|
|
65
|
+
dischargingExpiryTimer: Timer | undefined;
|
|
55
66
|
maximumChargeCurrentUpdateTimer: Timer | undefined;
|
|
56
|
-
requestedMaximumChargeCurrent: number;
|
|
57
67
|
}
|
|
68
|
+
const State_base: new () => import("@matter/node").ClusterState.Type<import("@matter/types").ClusterType.WithSupportedFeatures<EnergyEvse, {
|
|
69
|
+
chargingPreferences: true;
|
|
70
|
+
plugAndCharge: false;
|
|
71
|
+
rfid: false;
|
|
72
|
+
soCReporting: false;
|
|
73
|
+
v2X: false;
|
|
74
|
+
}>, typeof EnergyEvseServer>;
|
|
75
|
+
export class State extends State_base {
|
|
76
|
+
chargingTargetSchedules: EnergyEvse.ChargingTargetSchedule[];
|
|
77
|
+
requestedMaximumChargeCurrent: number | undefined;
|
|
78
|
+
requestedMaximumDischargeCurrent: number | undefined;
|
|
79
|
+
}
|
|
80
|
+
export {};
|
|
58
81
|
}
|
|
59
82
|
export declare class MatterbridgeEnergyEvseModeServer extends EnergyEvseModeServer {
|
|
60
83
|
changeToMode(request: ModeBase.ChangeToModeRequest): Promise<ModeBase.ChangeToModeResponse>;
|
package/dist/devices/evse.js
CHANGED
|
@@ -20,8 +20,8 @@ export class Evse extends MatterbridgeEndpoint {
|
|
|
20
20
|
super([evse], { id: options.id ?? `${name.replaceAll(' ', '')}-${serial.replaceAll(' ', '')}`, number: options.number, tagList: options.tagList, mode: options.mode });
|
|
21
21
|
this.createDefaultIdentifyClusterServer()
|
|
22
22
|
.createDefaultBasicInformationClusterServer(name, serial, 0xfff1, 'Matterbridge', 0x8000, 'Matterbridge Evse')
|
|
23
|
-
.createDefaultEnergyEvseClusterServer(options.state, options.supplyState, options.faultState)
|
|
24
|
-
.createDefaultEnergyEvseModeClusterServer(options.currentMode, options.supportedModes)
|
|
23
|
+
.createDefaultEnergyEvseClusterServer(options.state, options.supplyState, options.faultState, options.stateOfCharge, options.batteryCapacity, options.vehicleId, options.rfid, options.v2x)
|
|
24
|
+
.createDefaultEnergyEvseModeClusterServer(options.currentMode, options.supportedModes, options.v2x)
|
|
25
25
|
.createDefaultTemperatureMeasurementClusterServer(24_00)
|
|
26
26
|
.addRequiredClusterServers();
|
|
27
27
|
fireAndForget(this.addFixedLabel('composed', 'EVSE'), this.log, 'Error adding composed label to EVSE');
|
|
@@ -32,12 +32,13 @@ export class Evse extends MatterbridgeEndpoint {
|
|
|
32
32
|
.createDefaultElectricalEnergyMeasurementClusterServer(options.energy ?? null, 0)
|
|
33
33
|
.addRequiredClusterServers();
|
|
34
34
|
this.addChildDeviceType('DeviceEnergyManagement', deviceEnergyManagement)
|
|
35
|
-
.createDefaultDeviceEnergyManagementClusterServer(DeviceEnergyManagement.EsaType.Evse, false, DeviceEnergyManagement.EsaState.Online, options.absMinPower, options.absMaxPower)
|
|
35
|
+
.createDefaultDeviceEnergyManagementClusterServer(DeviceEnergyManagement.EsaType.Evse, options.esaCanGenerate ?? false, DeviceEnergyManagement.EsaState.Online, options.absMinPower, options.absMaxPower)
|
|
36
36
|
.createDefaultDeviceEnergyManagementModeClusterServer()
|
|
37
37
|
.addRequiredClusterServers();
|
|
38
38
|
}
|
|
39
|
-
createDefaultEnergyEvseClusterServer(state, supplyState, faultState) {
|
|
40
|
-
|
|
39
|
+
createDefaultEnergyEvseClusterServer(state, supplyState, faultState, stateOfCharge, batteryCapacity, vehicleId, rfid, v2x) {
|
|
40
|
+
const evseServer = MatterbridgeEnergyEvseServer.with(EnergyEvse.Feature.ChargingPreferences, ...(stateOfCharge !== undefined ? [EnergyEvse.Feature.SoCReporting] : []), ...(vehicleId !== undefined ? [EnergyEvse.Feature.PlugAndCharge] : []), ...(rfid ? [EnergyEvse.Feature.Rfid] : []), ...(v2x ? [EnergyEvse.Feature.V2X] : []));
|
|
41
|
+
this.behaviors.require(rfid ? evseServer.enable({ events: { rfid: true } }) : evseServer, {
|
|
41
42
|
state: state !== undefined ? state : EnergyEvse.State.NotPluggedIn,
|
|
42
43
|
supplyState: supplyState !== undefined ? supplyState : EnergyEvse.SupplyState.ChargingEnabled,
|
|
43
44
|
faultState: faultState !== undefined ? faultState : EnergyEvse.FaultState.NoError,
|
|
@@ -49,26 +50,44 @@ export class Evse extends MatterbridgeEndpoint {
|
|
|
49
50
|
sessionId: null,
|
|
50
51
|
sessionDuration: null,
|
|
51
52
|
sessionEnergyCharged: null,
|
|
53
|
+
...(stateOfCharge !== undefined ? { stateOfCharge, batteryCapacity: batteryCapacity ?? null } : {}),
|
|
54
|
+
...(vehicleId !== undefined ? { vehicleId } : {}),
|
|
55
|
+
...(v2x ? { dischargingEnabledUntil: null, maximumDischargeCurrent: 0, sessionEnergyDischarged: null } : {}),
|
|
52
56
|
});
|
|
53
57
|
return this;
|
|
54
58
|
}
|
|
55
|
-
createDefaultEnergyEvseModeClusterServer(currentMode, supportedModes) {
|
|
59
|
+
createDefaultEnergyEvseModeClusterServer(currentMode, supportedModes, v2x) {
|
|
56
60
|
this.behaviors.require(MatterbridgeEnergyEvseModeServer, {
|
|
57
61
|
supportedModes: supportedModes ?? [
|
|
58
62
|
{ label: 'On demand', mode: 1, modeTags: [{ value: EnergyEvseMode.ModeTag.Manual }] },
|
|
59
63
|
{ label: 'Scheduled', mode: 2, modeTags: [{ value: EnergyEvseMode.ModeTag.TimeOfUse }] },
|
|
60
64
|
{ label: 'Solar charging', mode: 3, modeTags: [{ value: EnergyEvseMode.ModeTag.SolarCharging }] },
|
|
65
|
+
...(v2x ? [{ label: 'Home to vehicle and Vehicle to home', mode: 4, modeTags: [{ value: EnergyEvseMode.ModeTag.V2X }] }] : []),
|
|
61
66
|
],
|
|
62
67
|
currentMode: currentMode ?? 1,
|
|
63
68
|
});
|
|
64
69
|
return this;
|
|
65
70
|
}
|
|
71
|
+
async triggerRfidEvent(uid, log) {
|
|
72
|
+
if (![4, 7, 10].includes(uid.length)) {
|
|
73
|
+
(log ?? this.log).warn(`triggerRfidEvent: invalid RFID uid length ${uid.length} (expected 4, 7 or 10 bytes)`);
|
|
74
|
+
return false;
|
|
75
|
+
}
|
|
76
|
+
return this.triggerEvent(EnergyEvseServer.with(EnergyEvse.Feature.Rfid), 'rfid', { uid }, log);
|
|
77
|
+
}
|
|
66
78
|
}
|
|
67
79
|
export class MatterbridgeEnergyEvseServer extends EnergyEvseServer.with(EnergyEvse.Feature.ChargingPreferences) {
|
|
68
80
|
async initialize() {
|
|
69
81
|
await super.initialize();
|
|
70
|
-
this.
|
|
71
|
-
this.
|
|
82
|
+
this.state.requestedMaximumChargeCurrent ??= Number(this.state.maximumChargeCurrent);
|
|
83
|
+
this.state.requestedMaximumDischargeCurrent ??= this.features.v2X ? Number(this.state.maximumDischargeCurrent) : 0;
|
|
84
|
+
this.state.chargingTargetSchedules ??= [];
|
|
85
|
+
if (this.state.chargingEnabledUntil !== null) {
|
|
86
|
+
this.#scheduleChargingExpiry(this.state.chargingEnabledUntil);
|
|
87
|
+
}
|
|
88
|
+
if (this.features.v2X && this.state.dischargingEnabledUntil !== null) {
|
|
89
|
+
this.#scheduleDischargingExpiry(this.state.dischargingEnabledUntil);
|
|
90
|
+
}
|
|
72
91
|
const userMaximumChargeCurrentChanged = this.events.userMaximumChargeCurrent$Changed;
|
|
73
92
|
if (userMaximumChargeCurrentChanged) {
|
|
74
93
|
this.reactTo(userMaximumChargeCurrentChanged, this.#handleUserMaximumChargeCurrentChanged);
|
|
@@ -87,6 +106,10 @@ export class MatterbridgeEnergyEvseServer extends EnergyEvseServer.with(EnergyEv
|
|
|
87
106
|
device.log.debug(`MatterbridgeEnergyEvseServer: disable called (endpoint ${this.endpoint.maybeId}.${this.endpoint.maybeNumber})`);
|
|
88
107
|
this.state.chargingEnabledUntil = MATTER_EPOCH_OFFSET_S;
|
|
89
108
|
this.#stopCharging(EnergyEvse.EnergyTransferStoppedReason.EvseStopped);
|
|
109
|
+
if (this.features.v2X) {
|
|
110
|
+
this.state.dischargingEnabledUntil = MATTER_EPOCH_OFFSET_S;
|
|
111
|
+
this.#stopDischarging(EnergyEvse.EnergyTransferStoppedReason.EvseStopped);
|
|
112
|
+
}
|
|
90
113
|
}
|
|
91
114
|
async enableCharging(request) {
|
|
92
115
|
const device = this.endpoint.stateOf(MatterbridgeServer);
|
|
@@ -99,24 +122,56 @@ export class MatterbridgeEnergyEvseServer extends EnergyEvseServer.with(EnergyEv
|
|
|
99
122
|
endpoint: this.endpoint,
|
|
100
123
|
});
|
|
101
124
|
device.log.debug(`MatterbridgeEnergyEvseServer: enableCharging called (endpoint ${this.endpoint.maybeId}.${this.endpoint.maybeNumber})`);
|
|
102
|
-
if (this.state.supplyState === EnergyEvse.SupplyState.
|
|
103
|
-
|
|
125
|
+
if (this.state.supplyState === EnergyEvse.SupplyState.DisabledError ||
|
|
126
|
+
this.state.supplyState === EnergyEvse.SupplyState.DisabledDiagnostics ||
|
|
127
|
+
this.state.faultState !== EnergyEvse.FaultState.NoError) {
|
|
128
|
+
throw new StatusResponse.FailureError(`MatterbridgeEnergyEvseServer: cannot enable charging while an error or diagnostics are active (endpoint ${this.endpoint.maybeId}.${this.endpoint.maybeNumber})`);
|
|
104
129
|
}
|
|
105
130
|
this.internal.chargingExpiryTimer?.stop();
|
|
106
131
|
this.internal.chargingExpiryTimer = undefined;
|
|
107
|
-
this.state.supplyState = EnergyEvse.SupplyState.ChargingEnabled;
|
|
132
|
+
this.state.supplyState = this.#isDischargingActive() ? EnergyEvse.SupplyState.Enabled : EnergyEvse.SupplyState.ChargingEnabled;
|
|
108
133
|
this.state.chargingEnabledUntil = request.chargingEnabledUntil;
|
|
109
134
|
this.state.minimumChargeCurrent = request.minimumChargeCurrent;
|
|
110
|
-
this.
|
|
135
|
+
this.state.requestedMaximumChargeCurrent = Number(request.maximumChargeCurrent);
|
|
111
136
|
this.#updateMaximumChargeCurrent();
|
|
112
|
-
this.#updateNextChargeTarget();
|
|
113
137
|
if (this.state.state === EnergyEvse.State.PluggedInDemand) {
|
|
114
138
|
this.state.state = EnergyEvse.State.PluggedInCharging;
|
|
115
|
-
this.events.energyTransferStarted.emit({
|
|
139
|
+
this.events.energyTransferStarted.emit({
|
|
140
|
+
sessionId: this.state.sessionId ?? 0,
|
|
141
|
+
state: this.state.state,
|
|
142
|
+
maximumCurrent: this.state.maximumChargeCurrent,
|
|
143
|
+
...(this.features.v2X ? { maximumDischargeCurrent: this.state.maximumDischargeCurrent } : {}),
|
|
144
|
+
}, this.context);
|
|
116
145
|
}
|
|
146
|
+
this.#updateNextChargeTarget();
|
|
117
147
|
if (request.chargingEnabledUntil !== null) {
|
|
118
|
-
|
|
119
|
-
|
|
148
|
+
this.#scheduleChargingExpiry(request.chargingEnabledUntil);
|
|
149
|
+
}
|
|
150
|
+
}
|
|
151
|
+
async enableDischarging(request) {
|
|
152
|
+
const device = this.endpoint.stateOf(MatterbridgeServer);
|
|
153
|
+
device.log.info(`MatterbridgeEnergyEvseServer: enableDischarging (endpoint ${this.endpoint.maybeId}.${this.endpoint.maybeNumber})`);
|
|
154
|
+
await device.commandHandler.executeHandler('EnergyEvse.enableDischarging', {
|
|
155
|
+
command: 'enableDischarging',
|
|
156
|
+
request,
|
|
157
|
+
cluster: EnergyEvseServer.id,
|
|
158
|
+
attributes: this.state,
|
|
159
|
+
endpoint: this.endpoint,
|
|
160
|
+
});
|
|
161
|
+
device.log.debug(`MatterbridgeEnergyEvseServer: enableDischarging called (endpoint ${this.endpoint.maybeId}.${this.endpoint.maybeNumber})`);
|
|
162
|
+
if (this.state.supplyState === EnergyEvse.SupplyState.DisabledError ||
|
|
163
|
+
this.state.supplyState === EnergyEvse.SupplyState.DisabledDiagnostics ||
|
|
164
|
+
this.state.faultState !== EnergyEvse.FaultState.NoError) {
|
|
165
|
+
throw new StatusResponse.FailureError(`MatterbridgeEnergyEvseServer: cannot enable discharging while an error or diagnostics are active (endpoint ${this.endpoint.maybeId}.${this.endpoint.maybeNumber})`);
|
|
166
|
+
}
|
|
167
|
+
this.internal.dischargingExpiryTimer?.stop();
|
|
168
|
+
this.internal.dischargingExpiryTimer = undefined;
|
|
169
|
+
this.state.supplyState = this.#isChargingActive() ? EnergyEvse.SupplyState.Enabled : EnergyEvse.SupplyState.DischargingEnabled;
|
|
170
|
+
this.state.dischargingEnabledUntil = request.dischargingEnabledUntil;
|
|
171
|
+
this.state.requestedMaximumDischargeCurrent = Number(request.maximumDischargeCurrent);
|
|
172
|
+
this.#updateMaximumDischargeCurrent();
|
|
173
|
+
if (request.dischargingEnabledUntil !== null) {
|
|
174
|
+
this.#scheduleDischargingExpiry(request.dischargingEnabledUntil);
|
|
120
175
|
}
|
|
121
176
|
}
|
|
122
177
|
async startDiagnostics() {
|
|
@@ -138,25 +193,70 @@ export class MatterbridgeEnergyEvseServer extends EnergyEvseServer.with(EnergyEv
|
|
|
138
193
|
}
|
|
139
194
|
#expireCharging() {
|
|
140
195
|
this.internal.chargingExpiryTimer = undefined;
|
|
196
|
+
this.state.chargingEnabledUntil = MATTER_EPOCH_OFFSET_S;
|
|
141
197
|
this.#stopCharging(EnergyEvse.EnergyTransferStoppedReason.EvseStopped);
|
|
142
198
|
}
|
|
199
|
+
#expireDischarging() {
|
|
200
|
+
this.internal.dischargingExpiryTimer = undefined;
|
|
201
|
+
this.state.dischargingEnabledUntil = MATTER_EPOCH_OFFSET_S;
|
|
202
|
+
this.#stopDischarging(EnergyEvse.EnergyTransferStoppedReason.EvseStopped);
|
|
203
|
+
}
|
|
204
|
+
#scheduleChargingExpiry(chargingEnabledUntil) {
|
|
205
|
+
const remainingSeconds = Math.max(0, Math.ceil(chargingEnabledUntil - Time.nowMs / 1000));
|
|
206
|
+
this.internal.chargingExpiryTimer = Time.getTimer('EnergyEvse charging expiry', Seconds(remainingSeconds), this.callback(this.#expireCharging, { lock: true })).start();
|
|
207
|
+
}
|
|
208
|
+
#scheduleDischargingExpiry(dischargingEnabledUntil) {
|
|
209
|
+
const remainingSeconds = Math.max(0, Math.ceil(dischargingEnabledUntil - Time.nowMs / 1000));
|
|
210
|
+
this.internal.dischargingExpiryTimer = Time.getTimer('EnergyEvse discharging expiry', Seconds(remainingSeconds), this.callback(this.#expireDischarging, { lock: true })).start();
|
|
211
|
+
}
|
|
212
|
+
#isChargingActive() {
|
|
213
|
+
return this.state.supplyState === EnergyEvse.SupplyState.ChargingEnabled || this.state.supplyState === EnergyEvse.SupplyState.Enabled;
|
|
214
|
+
}
|
|
215
|
+
#isDischargingActive() {
|
|
216
|
+
return this.state.supplyState === EnergyEvse.SupplyState.DischargingEnabled || this.state.supplyState === EnergyEvse.SupplyState.Enabled;
|
|
217
|
+
}
|
|
143
218
|
#handleUserMaximumChargeCurrentChanged() {
|
|
144
219
|
this.internal.maximumChargeCurrentUpdateTimer?.stop();
|
|
145
220
|
this.internal.maximumChargeCurrentUpdateTimer = Time.getTimer('EnergyEvse maximum charge current update', Seconds(0), this.callback(this.#updateMaximumChargeCurrent, { lock: true })).start();
|
|
146
221
|
}
|
|
147
222
|
#updateMaximumChargeCurrent() {
|
|
148
|
-
this.state.maximumChargeCurrent = Math.min(Number(this.state.circuitCapacity), this.
|
|
223
|
+
this.state.maximumChargeCurrent = Math.min(Number(this.state.circuitCapacity), Number(this.state.requestedMaximumChargeCurrent), Number(this.state.userMaximumChargeCurrent));
|
|
224
|
+
}
|
|
225
|
+
#updateMaximumDischargeCurrent() {
|
|
226
|
+
this.state.maximumDischargeCurrent = Math.min(Number(this.state.circuitCapacity), Number(this.state.requestedMaximumDischargeCurrent));
|
|
149
227
|
}
|
|
150
228
|
#stopCharging(reason) {
|
|
151
229
|
this.internal.chargingExpiryTimer?.stop();
|
|
152
230
|
this.internal.chargingExpiryTimer = undefined;
|
|
153
231
|
if (this.state.state === EnergyEvse.State.PluggedInCharging) {
|
|
154
|
-
this.events.energyTransferStopped.emit({
|
|
232
|
+
this.events.energyTransferStopped.emit({
|
|
233
|
+
sessionId: this.state.sessionId ?? 0,
|
|
234
|
+
state: this.state.state,
|
|
235
|
+
reason,
|
|
236
|
+
energyTransferred: 0,
|
|
237
|
+
...(this.features.v2X ? { energyDischarged: 0 } : {}),
|
|
238
|
+
}, this.context);
|
|
155
239
|
this.state.state = EnergyEvse.State.PluggedInDemand;
|
|
156
240
|
}
|
|
157
|
-
this.state.supplyState =
|
|
241
|
+
this.state.supplyState =
|
|
242
|
+
this.features.v2X && this.#isPermissionActive(this.state.dischargingEnabledUntil) ? EnergyEvse.SupplyState.DischargingEnabled : EnergyEvse.SupplyState.Disabled;
|
|
243
|
+
this.state.minimumChargeCurrent = 0;
|
|
244
|
+
this.state.maximumChargeCurrent = 0;
|
|
158
245
|
this.#clearNextChargeTarget();
|
|
159
246
|
}
|
|
247
|
+
#stopDischarging(reason) {
|
|
248
|
+
this.internal.dischargingExpiryTimer?.stop();
|
|
249
|
+
this.internal.dischargingExpiryTimer = undefined;
|
|
250
|
+
if (this.state.state === EnergyEvse.State.PluggedInDischarging) {
|
|
251
|
+
this.events.energyTransferStopped.emit({ sessionId: this.state.sessionId ?? 0, state: this.state.state, reason, energyTransferred: 0, energyDischarged: 0 }, this.context);
|
|
252
|
+
this.state.state = EnergyEvse.State.PluggedInDemand;
|
|
253
|
+
}
|
|
254
|
+
this.state.supplyState = this.#isPermissionActive(this.state.chargingEnabledUntil) ? EnergyEvse.SupplyState.ChargingEnabled : EnergyEvse.SupplyState.Disabled;
|
|
255
|
+
this.state.maximumDischargeCurrent = 0;
|
|
256
|
+
}
|
|
257
|
+
#isPermissionActive(enabledUntil) {
|
|
258
|
+
return enabledUntil === null || enabledUntil > Time.nowMs / 1000;
|
|
259
|
+
}
|
|
160
260
|
async setTargets(request) {
|
|
161
261
|
const device = this.endpoint.stateOf(MatterbridgeServer);
|
|
162
262
|
device.log.info(`MatterbridgeEnergyEvseServer: setTargets request ${debugStringify(request.chargingTargetSchedules)} (endpoint ${this.endpoint.maybeId}.${this.endpoint.maybeNumber})`);
|
|
@@ -169,6 +269,9 @@ export class MatterbridgeEnergyEvseServer extends EnergyEvseServer.with(EnergyEv
|
|
|
169
269
|
});
|
|
170
270
|
let updatedDays = 0;
|
|
171
271
|
for (const schedule of request.chargingTargetSchedules) {
|
|
272
|
+
if (this.features.soCReporting && schedule.chargingTargets.some((target) => target.targetSoC === undefined || target.targetSoC === null)) {
|
|
273
|
+
throw new StatusResponse.InvalidCommandError(`MatterbridgeEnergyEvseServer: TargetSoC is required when SoC reporting is available (endpoint ${this.endpoint.maybeId}.${this.endpoint.maybeNumber})`);
|
|
274
|
+
}
|
|
172
275
|
const scheduleDays = this.#encodeTargetDays(schedule.dayOfWeekForSequence);
|
|
173
276
|
if ((updatedDays & scheduleDays) !== 0) {
|
|
174
277
|
throw new StatusResponse.ConstraintErrorError(`MatterbridgeEnergyEvseServer: each day may occur in only one ChargingTargetSchedule (endpoint ${this.endpoint.maybeId}.${this.endpoint.maybeNumber})`);
|
|
@@ -178,11 +281,11 @@ export class MatterbridgeEnergyEvseServer extends EnergyEvseServer.with(EnergyEv
|
|
|
178
281
|
}
|
|
179
282
|
updatedDays |= scheduleDays;
|
|
180
283
|
}
|
|
181
|
-
const unchangedSchedules = this.
|
|
284
|
+
const unchangedSchedules = this.state.chargingTargetSchedules.flatMap((schedule) => {
|
|
182
285
|
const remainingDays = this.#encodeTargetDays(schedule.dayOfWeekForSequence) & ~updatedDays;
|
|
183
286
|
return remainingDays === 0 ? [] : [{ ...schedule, dayOfWeekForSequence: new EnergyEvse.TargetDayOfWeek(remainingDays) }];
|
|
184
287
|
});
|
|
185
|
-
this.
|
|
288
|
+
this.state.chargingTargetSchedules = [...unchangedSchedules, ...structuredClone(request.chargingTargetSchedules)];
|
|
186
289
|
this.#updateNextChargeTarget();
|
|
187
290
|
}
|
|
188
291
|
async getTargets() {
|
|
@@ -195,7 +298,7 @@ export class MatterbridgeEnergyEvseServer extends EnergyEvseServer.with(EnergyEv
|
|
|
195
298
|
attributes: this.state,
|
|
196
299
|
endpoint: this.endpoint,
|
|
197
300
|
});
|
|
198
|
-
return { chargingTargetSchedules: structuredClone(this.
|
|
301
|
+
return { chargingTargetSchedules: structuredClone(this.state.chargingTargetSchedules) };
|
|
199
302
|
}
|
|
200
303
|
async clearTargets() {
|
|
201
304
|
const device = this.endpoint.stateOf(MatterbridgeServer);
|
|
@@ -207,7 +310,12 @@ export class MatterbridgeEnergyEvseServer extends EnergyEvseServer.with(EnergyEv
|
|
|
207
310
|
attributes: this.state,
|
|
208
311
|
endpoint: this.endpoint,
|
|
209
312
|
});
|
|
210
|
-
this.
|
|
313
|
+
this.state.chargingTargetSchedules = [];
|
|
314
|
+
const modeState = this.endpoint.stateOf(EnergyEvseModeServer);
|
|
315
|
+
const isAutomaticMode = modeState.supportedModes.some((mode) => mode.mode === modeState.currentMode && mode.modeTags.some((tag) => tag.value === EnergyEvseMode.ModeTag.TimeOfUse));
|
|
316
|
+
if (isAutomaticMode && this.state.state === EnergyEvse.State.PluggedInCharging) {
|
|
317
|
+
this.#stopCharging(EnergyEvse.EnergyTransferStoppedReason.EvseStopped);
|
|
318
|
+
}
|
|
211
319
|
this.#clearNextChargeTarget();
|
|
212
320
|
}
|
|
213
321
|
#encodeTargetDays(days) {
|
|
@@ -227,14 +335,14 @@ export class MatterbridgeEnergyEvseServer extends EnergyEvseServer.with(EnergyEv
|
|
|
227
335
|
}
|
|
228
336
|
#updateNextChargeTarget() {
|
|
229
337
|
this.#clearNextChargeTarget();
|
|
230
|
-
if (this
|
|
338
|
+
if (!this.#isChargingActive() || this.state.state === EnergyEvse.State.NotPluggedIn)
|
|
231
339
|
return;
|
|
232
340
|
const now = new Date(Time.nowMs);
|
|
233
341
|
for (let dayOffset = 0; dayOffset <= 7; dayOffset++) {
|
|
234
342
|
const targetDate = new Date(now);
|
|
235
343
|
targetDate.setDate(now.getDate() + dayOffset);
|
|
236
344
|
const dayBit = 1 << targetDate.getDay();
|
|
237
|
-
const schedule = this.
|
|
345
|
+
const schedule = this.state.chargingTargetSchedules.find((candidate) => (this.#encodeTargetDays(candidate.dayOfWeekForSequence) & dayBit) !== 0);
|
|
238
346
|
if (!schedule)
|
|
239
347
|
continue;
|
|
240
348
|
const targets = schedule.chargingTargets.toSorted((a, b) => a.targetTimeMinutesPastMidnight - b.targetTimeMinutesPastMidnight);
|
|
@@ -243,13 +351,15 @@ export class MatterbridgeEnergyEvseServer extends EnergyEvseServer.with(EnergyEv
|
|
|
243
351
|
if (targetDate.getTime() <= now.getTime())
|
|
244
352
|
continue;
|
|
245
353
|
const targetTime = Math.floor(targetDate.getTime() / 1000);
|
|
246
|
-
const
|
|
354
|
+
const useTargetSoC = target.targetSoC !== undefined && (target.addedEnergy === undefined || (this.features.soCReporting && this.state.stateOfCharge !== null));
|
|
355
|
+
const requiredEnergy = useTargetSoC || target.addedEnergy === undefined ? null : target.addedEnergy;
|
|
356
|
+
const targetSoCReached = useTargetSoC && this.state.stateOfCharge !== null && this.state.stateOfCharge >= Number(target.targetSoC);
|
|
247
357
|
this.state.nextChargeTargetTime = targetTime;
|
|
248
358
|
this.state.nextChargeRequiredEnergy = requiredEnergy;
|
|
249
|
-
this.state.nextChargeTargetSoC =
|
|
359
|
+
this.state.nextChargeTargetSoC = useTargetSoC ? Number(target.targetSoC) : null;
|
|
250
360
|
const maximumPowerMw = (230_000 * Number(this.state.maximumChargeCurrent)) / 1_000;
|
|
251
361
|
const chargingSeconds = requiredEnergy === null || maximumPowerMw <= 0 ? 1 : Math.max(1, Math.ceil((Number(requiredEnergy) * 3_600) / maximumPowerMw));
|
|
252
|
-
this.state.nextChargeStartTime = targetTime - chargingSeconds;
|
|
362
|
+
this.state.nextChargeStartTime = targetSoCReached ? null : targetTime - chargingSeconds;
|
|
253
363
|
return;
|
|
254
364
|
}
|
|
255
365
|
}
|
|
@@ -259,11 +369,16 @@ Supervision(MatterbridgeEnergyEvseServer.prototype.constructor, 'setTargets', 'c
|
|
|
259
369
|
(function (MatterbridgeEnergyEvseServer) {
|
|
260
370
|
class Internal {
|
|
261
371
|
chargingExpiryTimer;
|
|
262
|
-
|
|
372
|
+
dischargingExpiryTimer;
|
|
263
373
|
maximumChargeCurrentUpdateTimer;
|
|
264
|
-
requestedMaximumChargeCurrent = 0;
|
|
265
374
|
}
|
|
266
375
|
MatterbridgeEnergyEvseServer.Internal = Internal;
|
|
376
|
+
class State extends EnergyEvseServer.with(EnergyEvse.Feature.ChargingPreferences).State {
|
|
377
|
+
chargingTargetSchedules = [];
|
|
378
|
+
requestedMaximumChargeCurrent = undefined;
|
|
379
|
+
requestedMaximumDischargeCurrent = undefined;
|
|
380
|
+
}
|
|
381
|
+
MatterbridgeEnergyEvseServer.State = State;
|
|
267
382
|
})(MatterbridgeEnergyEvseServer || (MatterbridgeEnergyEvseServer = {}));
|
|
268
383
|
export class MatterbridgeEnergyEvseModeServer extends EnergyEvseModeServer {
|
|
269
384
|
async changeToMode(request) {
|
|
@@ -847,6 +847,7 @@ export type CommandHandlerDataMap = {
|
|
|
847
847
|
endpoint: MatterbridgeEndpoint;
|
|
848
848
|
};
|
|
849
849
|
'enableCharging': CommandHandlerData<'EnergyEvse.enableCharging'>;
|
|
850
|
+
'enableDischarging': CommandHandlerData<'EnergyEvse.enableDischarging'>;
|
|
850
851
|
'disable': CommandHandlerData<'EnergyEvse.disable'>;
|
|
851
852
|
'setTargets': CommandHandlerData<'EnergyEvse.setTargets'>;
|
|
852
853
|
'getTargets': CommandHandlerData<'EnergyEvse.getTargets'>;
|
|
@@ -858,6 +859,13 @@ export type CommandHandlerDataMap = {
|
|
|
858
859
|
attributes: ClusterAttributeValues<(typeof EnergyEvse)['attributes']>;
|
|
859
860
|
endpoint: MatterbridgeEndpoint;
|
|
860
861
|
};
|
|
862
|
+
'EnergyEvse.enableDischarging': {
|
|
863
|
+
command: 'enableDischarging';
|
|
864
|
+
request: EnergyEvse.EnableDischargingRequest;
|
|
865
|
+
cluster: 'energyEvse';
|
|
866
|
+
attributes: ClusterAttributeValues<(typeof EnergyEvse)['attributes']>;
|
|
867
|
+
endpoint: MatterbridgeEndpoint;
|
|
868
|
+
};
|
|
861
869
|
'EnergyEvse.disable': {
|
|
862
870
|
command: 'disable';
|
|
863
871
|
request: {};
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@matterbridge/core",
|
|
3
|
-
"version": "3.10.9-dev-
|
|
3
|
+
"version": "3.10.9-dev-20260907-5fcc59a",
|
|
4
4
|
"description": "Matterbridge core library",
|
|
5
5
|
"author": "https://github.com/Luligu",
|
|
6
6
|
"homepage": "https://matterbridge.io/",
|
|
@@ -132,10 +132,10 @@
|
|
|
132
132
|
},
|
|
133
133
|
"dependencies": {
|
|
134
134
|
"@matter/main": "0.17.9",
|
|
135
|
-
"@matterbridge/dgram": "3.10.9-dev-
|
|
136
|
-
"@matterbridge/thread": "3.10.9-dev-
|
|
137
|
-
"@matterbridge/types": "3.10.9-dev-
|
|
138
|
-
"@matterbridge/utils": "3.10.9-dev-
|
|
135
|
+
"@matterbridge/dgram": "3.10.9-dev-20260907-5fcc59a",
|
|
136
|
+
"@matterbridge/thread": "3.10.9-dev-20260907-5fcc59a",
|
|
137
|
+
"@matterbridge/types": "3.10.9-dev-20260907-5fcc59a",
|
|
138
|
+
"@matterbridge/utils": "3.10.9-dev-20260907-5fcc59a",
|
|
139
139
|
"escape-html": "1.0.3",
|
|
140
140
|
"express": "5.2.1",
|
|
141
141
|
"express-rate-limit": "8.7.0",
|