@matter/nodejs-shell 0.16.0-alpha.0-20251216-71c21f901 → 0.16.0-alpha.0-20251220-0bb8d9f89

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.
@@ -3,7 +3,13 @@
3
3
  * Copyright 2022-2025 Matter.js Authors
4
4
  * SPDX-License-Identifier: Apache-2.0
5
5
  */
6
- import { Environment, Logger, StorageService } from "#general";
6
+ import {
7
+ Environment,
8
+ Logger,
9
+ ObserverGroup,
10
+ StorageService
11
+ } from "#general";
12
+ import { SoftwareUpdateManager } from "#node";
7
13
  import { DclCertificateService, DclOtaUpdateService, DclVendorInfoService } from "#protocol";
8
14
  import { NodeId } from "#types";
9
15
  import { CommissioningController } from "@project-chip/matter.js";
@@ -19,6 +25,7 @@ class MatterNode {
19
25
  #netInterface;
20
26
  #dclFetchTestCertificates = false;
21
27
  #services;
28
+ #observers;
22
29
  constructor(nodeNum, netInterface) {
23
30
  this.#environment = Environment.default;
24
31
  this.#environment.runtime.add(this);
@@ -73,7 +80,8 @@ class MatterNode {
73
80
  id
74
81
  },
75
82
  autoConnect: false,
76
- adminFabricLabel: "matter.js Shell"
83
+ adminFabricLabel: "matter.js Shell",
84
+ enableOtaProvider: true
77
85
  });
78
86
  const storageService = this.commissioningController.env.get(StorageService);
79
87
  const baseLocation = storageService.location;
@@ -101,6 +109,7 @@ class MatterNode {
101
109
  async close() {
102
110
  await this.commissioningController?.close();
103
111
  await this.#services?.close();
112
+ this.#observers?.close();
104
113
  }
105
114
  async start() {
106
115
  if (this.#started) {
@@ -117,6 +126,14 @@ class MatterNode {
117
126
  } else {
118
127
  throw new Error("No controller initialized");
119
128
  }
129
+ this.#observers = this.#observers ?? new ObserverGroup(this.#environment.runtime);
130
+ const updateManagerEvents = this.commissioningController.otaProvider.eventsOf(SoftwareUpdateManager);
131
+ this.#observers.on(updateManagerEvents.updateAvailable, (peer, details) => {
132
+ logger.info(`Update available for peer `, peer, `:`, details);
133
+ });
134
+ this.#observers.on(updateManagerEvents.updateDone, (peer) => {
135
+ logger.info(`Update done for peer `, peer);
136
+ });
120
137
  this.#started = true;
121
138
  }
122
139
  async connectAndGetNodes(nodeIdStr, connectOptions) {
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "version": 3,
3
3
  "sources": ["../../src/MatterNode.ts"],
4
- "mappings": "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",
4
+ "mappings": "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",
5
5
  "names": []
6
6
  }
@@ -4,7 +4,9 @@
4
4
  * SPDX-License-Identifier: Apache-2.0
5
5
  */
6
6
  import { capitalize, decamelize, Diagnostic } from "#general";
7
- import { NodeId } from "#types";
7
+ import { SoftwareUpdateManager } from "#node";
8
+ import { PeerAddress } from "#protocol";
9
+ import { FabricIndex, NodeId } from "#types";
8
10
  import { NodeStateInformation } from "@project-chip/matter.js/device";
9
11
  function createDiagnosticCallbacks() {
10
12
  return {
@@ -198,10 +200,14 @@ function commands(theNode) {
198
200
  throw new Error(`Node ${nodeIdStr} not commissioned`);
199
201
  }
200
202
  }
203
+ const nodeDetails = theNode.commissioningController.getCommissionedNodesDetails();
201
204
  for (const nodeIdToProcess of nodeIds) {
202
205
  const node = theNode.commissioningController.getPairedNode(nodeIdToProcess);
203
206
  if (node === void 0) {
204
- console.log(`Node ${nodeIdToProcess}: Not initialized`);
207
+ const details = nodeDetails.find((nd) => nd.nodeId === nodeIdToProcess);
208
+ console.log(
209
+ `Node ${nodeIdToProcess}: Not initialized${details?.deviceData?.basicInformation !== void 0 ? ` (${details.deviceData.basicInformation.vendorName} ${details.deviceData.basicInformation.productName})` : ""}`
210
+ );
205
211
  } else {
206
212
  const basicInfo = node.basicInformation;
207
213
  console.log(
@@ -210,10 +216,91 @@ function commands(theNode) {
210
216
  }
211
217
  }
212
218
  }
219
+ ).command(
220
+ "add [node-id]",
221
+ "Adds a node without commissioning and connects to it (means need to exist in the fabric and commissioned otherwise)",
222
+ (yargs2) => {
223
+ return yargs2.positional("node-id", {
224
+ describe: "node id to connect.",
225
+ default: "all",
226
+ type: "string",
227
+ demandOption: true
228
+ }).positional("min-subscription-interval", {
229
+ describe: "Minimum subscription interval in seconds. If set then the node is subscribed to all attributes and events.",
230
+ type: "number"
231
+ }).positional("max-subscription-interval", {
232
+ describe: "Maximum subscription interval in seconds. If minimum interval is set and this not it will be determined automatically.",
233
+ type: "number"
234
+ });
235
+ },
236
+ async (argv) => {
237
+ const { nodeId: nodeIdStr, maxSubscriptionInterval, minSubscriptionInterval } = argv;
238
+ await theNode.start();
239
+ if (theNode.commissioningController === void 0) {
240
+ throw new Error("CommissioningController not initialized");
241
+ }
242
+ let nodeIds = theNode.commissioningController.getCommissionedNodes();
243
+ const cmdNodeId = NodeId(BigInt(nodeIdStr));
244
+ nodeIds = nodeIds.filter((nodeId) => nodeId === cmdNodeId);
245
+ if (nodeIds.length) {
246
+ throw new Error(`Node ${nodeIdStr} already known`);
247
+ }
248
+ await theNode.commissioningController.node.peers.forAddress(
249
+ theNode.commissioningController.fabric.addressOf(cmdNodeId)
250
+ );
251
+ const autoSubscribe = minSubscriptionInterval !== void 0;
252
+ const node = await theNode.commissioningController.getNode(cmdNodeId);
253
+ node.connect({
254
+ autoSubscribe,
255
+ subscribeMinIntervalFloorSeconds: autoSubscribe ? minSubscriptionInterval : void 0,
256
+ subscribeMaxIntervalCeilingSeconds: autoSubscribe ? maxSubscriptionInterval : void 0,
257
+ ...createDiagnosticCallbacks()
258
+ });
259
+ }
213
260
  ).command(
214
261
  "ota",
215
262
  "OTA update operations for nodes",
216
263
  (yargs2) => yargs2.command(
264
+ "known [node-id]",
265
+ "List which OTA updates are known to be available for commissioned nodes. A first query by the provider must have happened for this to be filled.",
266
+ (yargs3) => {
267
+ return yargs3.positional("node-id", {
268
+ describe: "Node ID to check for updates",
269
+ type: "string",
270
+ default: void 0
271
+ }).option("local", {
272
+ describe: "include local update files",
273
+ type: "boolean",
274
+ default: false
275
+ });
276
+ },
277
+ async (argv) => {
278
+ const { nodeId: nodeIdStr, local } = argv;
279
+ await theNode.start();
280
+ if (theNode.commissioningController === void 0) {
281
+ throw new Error("CommissioningController not initialized");
282
+ }
283
+ let peerToCheck = void 0;
284
+ if (nodeIdStr !== void 0) {
285
+ const nodeId = NodeId(BigInt(nodeIdStr));
286
+ peerToCheck = (await theNode.commissioningController.getNode(nodeId))?.node;
287
+ }
288
+ const updatesAvailable = await theNode.commissioningController.otaProvider.act(
289
+ (agent) => agent.get(SoftwareUpdateManager).queryUpdates({ peerToCheck, includeStoredUpdates: local })
290
+ );
291
+ if (updatesAvailable.length) {
292
+ console.log(`OTA updates available for ${updatesAvailable.length} nodes:`);
293
+ for (const { peerAddress, info } of updatesAvailable) {
294
+ console.log(
295
+ peerAddress,
296
+ `: new Version: ${info.softwareVersion} (${info.softwareVersionString})`
297
+ );
298
+ }
299
+ } else {
300
+ console.log("No OTA updates available.");
301
+ }
302
+ }
303
+ ).command(
217
304
  "check <node-id>",
218
305
  "Check for OTA updates for a commissioned node",
219
306
  (yargs3) => {
@@ -226,10 +313,14 @@ function commands(theNode) {
226
313
  type: "string",
227
314
  choices: ["prod", "test"],
228
315
  default: "prod"
316
+ }).option("local", {
317
+ describe: "include local update files",
318
+ type: "boolean",
319
+ default: false
229
320
  });
230
321
  },
231
322
  async (argv) => {
232
- const { nodeId: nodeIdStr, mode } = argv;
323
+ const { nodeId: nodeIdStr, mode, local } = argv;
233
324
  const isProduction = mode === "prod";
234
325
  await theNode.start();
235
326
  if (theNode.commissioningController === void 0) {
@@ -258,12 +349,13 @@ function commands(theNode) {
258
349
  );
259
350
  console.log(` DCL Mode: ${isProduction ? "production" : "test"}
260
351
  `);
261
- const updateInfo = await theNode.otaService.checkForUpdate(
262
- basicInfo.vendorId,
263
- basicInfo.productId,
264
- basicInfo.softwareVersion,
352
+ const updateInfo = await theNode.otaService.checkForUpdate({
353
+ vendorId: basicInfo.vendorId,
354
+ productId: basicInfo.productId,
355
+ currentSoftwareVersion: basicInfo.softwareVersion,
356
+ includeStoredUpdates: local,
265
357
  isProduction
266
- );
358
+ });
267
359
  if (updateInfo) {
268
360
  console.log("\u2713 Update available!");
269
361
  console.log(
@@ -302,10 +394,14 @@ Run "nodes ota download ${nodeIdStr}${mode === "test" ? " --mode test" : ""}" to
302
394
  describe: "Force download even if update is already stored locally",
303
395
  type: "boolean",
304
396
  default: false
397
+ }).option("local", {
398
+ describe: "include local update files",
399
+ type: "boolean",
400
+ default: false
305
401
  });
306
402
  },
307
403
  async (argv) => {
308
- const { nodeId: nodeIdStr, mode, force } = argv;
404
+ const { nodeId: nodeIdStr, mode, force, local } = argv;
309
405
  const isProduction = mode === "prod";
310
406
  const forceDownload = force === true;
311
407
  await theNode.start();
@@ -335,12 +431,13 @@ Run "nodes ota download ${nodeIdStr}${mode === "test" ? " --mode test" : ""}" to
335
431
  );
336
432
  console.log(` DCL Mode: ${isProduction ? "production" : "test"}
337
433
  `);
338
- const updateInfo = await theNode.otaService.checkForUpdate(
339
- basicInfo.vendorId,
340
- basicInfo.productId,
341
- basicInfo.softwareVersion,
434
+ const updateInfo = await theNode.otaService.checkForUpdate({
435
+ vendorId: basicInfo.vendorId,
436
+ productId: basicInfo.productId,
437
+ currentSoftwareVersion: basicInfo.softwareVersion,
438
+ includeStoredUpdates: local,
342
439
  isProduction
343
- );
440
+ });
344
441
  if (!updateInfo) {
345
442
  console.log("No updates available. Device is up to date.");
346
443
  return;
@@ -366,6 +463,119 @@ Run "nodes ota download ${nodeIdStr}${mode === "test" ? " --mode test" : ""}" to
366
463
  You can now apply this update to the device using your device's OTA mechanism.`
367
464
  );
368
465
  }
466
+ ).command(
467
+ "apply <node-id>",
468
+ "Apply OTA update for a commissioned node",
469
+ (yargs3) => {
470
+ return yargs3.positional("node-id", {
471
+ describe: "Node ID to download update for",
472
+ type: "string",
473
+ demandOption: true
474
+ }).option("mode", {
475
+ describe: "DCL mode (prod or test)",
476
+ type: "string",
477
+ choices: ["prod", "test"],
478
+ default: "prod"
479
+ }).option("force", {
480
+ describe: "Force download even if update is already stored locally",
481
+ type: "boolean",
482
+ default: false
483
+ }).option("local", {
484
+ describe: "Apply update from local file",
485
+ type: "boolean",
486
+ default: false
487
+ });
488
+ },
489
+ async (argv) => {
490
+ const { nodeId: nodeIdStr, mode, force, local } = argv;
491
+ const isProduction = mode === "prod";
492
+ const forceDownload = force === true;
493
+ await theNode.start();
494
+ if (theNode.commissioningController === void 0) {
495
+ throw new Error("CommissioningController not initialized");
496
+ }
497
+ const nodeId = NodeId(BigInt(nodeIdStr));
498
+ const nodeDetails = theNode.commissioningController.getCommissionedNodesDetails().find((nd) => nd.nodeId === nodeId);
499
+ const basicInfo = nodeDetails?.deviceData?.basicInformation;
500
+ if (!basicInfo) {
501
+ throw new Error(`Node ${nodeIdStr} has no basic information available`);
502
+ }
503
+ if (basicInfo.vendorId === void 0 || basicInfo.productId === void 0 || basicInfo.softwareVersion === void 0) {
504
+ throw new Error(
505
+ `Node ${nodeIdStr} is missing required basic information for OTA check`
506
+ );
507
+ }
508
+ console.log(`Checking for OTA updates for node ${nodeIdStr}...`);
509
+ console.log(
510
+ ` Vendor ID: ${Diagnostic.hex(basicInfo.vendorId, 4).toUpperCase()}`
511
+ );
512
+ console.log(
513
+ ` Product ID: ${Diagnostic.hex(basicInfo.productId, 4).toUpperCase()}`
514
+ );
515
+ console.log(
516
+ ` Current Software Version: ${basicInfo.softwareVersion} (${basicInfo.softwareVersionString})`
517
+ );
518
+ console.log(` DCL Mode: ${isProduction ? "production" : "test"}
519
+ `);
520
+ const localUpdates = await theNode.otaService.find({
521
+ vendorId: basicInfo.vendorId,
522
+ productId: basicInfo.productId,
523
+ currentVersion: basicInfo.softwareVersion
524
+ });
525
+ if (local && !localUpdates.length) {
526
+ console.log("No applicable updates available in local storage.");
527
+ return;
528
+ }
529
+ const updateInfo = await theNode.otaService.checkForUpdate({
530
+ vendorId: basicInfo.vendorId,
531
+ productId: basicInfo.productId,
532
+ currentSoftwareVersion: basicInfo.softwareVersion,
533
+ includeStoredUpdates: local,
534
+ isProduction
535
+ });
536
+ let updateVersion;
537
+ if (!updateInfo && !local) {
538
+ console.log("No updates available in DCL. Device is up to date.");
539
+ return;
540
+ } else if (updateInfo) {
541
+ console.log("Update found:");
542
+ console.log(
543
+ ` New Version: ${updateInfo.softwareVersion} (${updateInfo.softwareVersionString})`
544
+ );
545
+ console.log(` OTA URL: ${updateInfo.otaUrl}`);
546
+ if (updateInfo.otaFileSize) {
547
+ const sizeKB = Number(updateInfo.otaFileSize) / 1024;
548
+ console.log(` File Size: ${sizeKB.toFixed(2)} KB`);
549
+ }
550
+ console.log("\nDownloading update...");
551
+ const fd = await theNode.otaService.downloadUpdate(
552
+ updateInfo,
553
+ isProduction,
554
+ forceDownload
555
+ );
556
+ updateVersion = updateInfo.softwareVersion;
557
+ console.log(
558
+ `\u2713 Update to version ${updateVersion} (${updateInfo.softwareVersionString}) downloaded and stored successfully: ${fd.text}`
559
+ );
560
+ } else {
561
+ updateVersion = localUpdates[0].softwareVersion;
562
+ console.log(
563
+ `Update to version ${updateVersion} (${localUpdates[0].softwareVersionString}) found in local storage: ${localUpdates[0].filename}`
564
+ );
565
+ }
566
+ const node = theNode.commissioningController.getPairedNode(nodeId);
567
+ if (node === void 0) {
568
+ throw new Error(`Node ${nodeIdStr} not connected`);
569
+ }
570
+ await theNode.commissioningController.otaProvider.act((agent) => {
571
+ return agent.get(SoftwareUpdateManager).forceUpdate(
572
+ PeerAddress({ nodeId, fabricIndex: FabricIndex(1) }),
573
+ basicInfo.vendorId,
574
+ basicInfo.productId,
575
+ updateVersion
576
+ );
577
+ });
578
+ }
369
579
  ).demandCommand(1, "Please specify an OTA subcommand"),
370
580
  async (argv) => {
371
581
  argv.unhandled = true;
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "version": 3,
3
3
  "sources": ["../../../src/shell/cmd_nodes.ts"],
4
- "mappings": "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",
4
+ "mappings": "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",
5
5
  "names": ["yargs"]
6
6
  }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@matter/nodejs-shell",
3
- "version": "0.16.0-alpha.0-20251216-71c21f901",
3
+ "version": "0.16.0-alpha.0-20251220-0bb8d9f89",
4
4
  "description": "Shell app for Matter controller",
5
5
  "keywords": [
6
6
  "iot",
@@ -43,15 +43,15 @@
43
43
  "#types": "@matter/types"
44
44
  },
45
45
  "dependencies": {
46
- "@matter/general": "0.16.0-alpha.0-20251216-71c21f901",
47
- "@matter/model": "0.16.0-alpha.0-20251216-71c21f901",
48
- "@matter/node": "0.16.0-alpha.0-20251216-71c21f901",
49
- "@matter/nodejs": "0.16.0-alpha.0-20251216-71c21f901",
50
- "@matter/nodejs-ble": "0.16.0-alpha.0-20251216-71c21f901",
51
- "@matter/protocol": "0.16.0-alpha.0-20251216-71c21f901",
52
- "@matter/tools": "0.16.0-alpha.0-20251216-71c21f901",
53
- "@matter/types": "0.16.0-alpha.0-20251216-71c21f901",
54
- "@project-chip/matter.js": "0.16.0-alpha.0-20251216-71c21f901",
46
+ "@matter/general": "0.16.0-alpha.0-20251220-0bb8d9f89",
47
+ "@matter/model": "0.16.0-alpha.0-20251220-0bb8d9f89",
48
+ "@matter/node": "0.16.0-alpha.0-20251220-0bb8d9f89",
49
+ "@matter/nodejs": "0.16.0-alpha.0-20251220-0bb8d9f89",
50
+ "@matter/nodejs-ble": "0.16.0-alpha.0-20251220-0bb8d9f89",
51
+ "@matter/protocol": "0.16.0-alpha.0-20251220-0bb8d9f89",
52
+ "@matter/tools": "0.16.0-alpha.0-20251220-0bb8d9f89",
53
+ "@matter/types": "0.16.0-alpha.0-20251220-0bb8d9f89",
54
+ "@project-chip/matter.js": "0.16.0-alpha.0-20251220-0bb8d9f89",
55
55
  "ws": "^8.18.3",
56
56
  "yargs": "^18.0.0"
57
57
  },
package/src/MatterNode.ts CHANGED
@@ -5,7 +5,15 @@
5
5
  */
6
6
 
7
7
  // Include this first to auto-register Crypto, Network and Time Node.js implementations
8
- import { Environment, Logger, SharedEnvironmentServices, StorageContext, StorageService } from "#general";
8
+ import {
9
+ Environment,
10
+ Logger,
11
+ ObserverGroup,
12
+ SharedEnvironmentServices,
13
+ StorageContext,
14
+ StorageService,
15
+ } from "#general";
16
+ import { ServerNode, SoftwareUpdateManager } from "#node";
9
17
  import { DclCertificateService, DclOtaUpdateService, DclVendorInfoService } from "#protocol";
10
18
  import { NodeId } from "#types";
11
19
  import { CommissioningController } from "@project-chip/matter.js";
@@ -24,6 +32,7 @@ export class MatterNode {
24
32
  readonly #netInterface?: string;
25
33
  #dclFetchTestCertificates = false;
26
34
  #services?: SharedEnvironmentServices;
35
+ #observers?: ObserverGroup;
27
36
 
28
37
  constructor(nodeNum: number, netInterface?: string) {
29
38
  this.#environment = Environment.default;
@@ -47,7 +56,7 @@ export class MatterNode {
47
56
  return this.#services;
48
57
  }
49
58
 
50
- get node() {
59
+ get node(): ServerNode {
51
60
  if (this.commissioningController === undefined) {
52
61
  throw new Error("CommissioningController not initialized. Start first");
53
62
  }
@@ -79,7 +88,7 @@ export class MatterNode {
79
88
  /**
80
89
  * Initialize the storage system.
81
90
  *
82
- * The storage manager is then also used by the Matter server, so this code block in general is required,
91
+ * The Matter server then also uses the storage manager, so this code block in general is required,
83
92
  * but you can choose a different storage backend as long as it implements the required API.
84
93
  */
85
94
 
@@ -87,6 +96,7 @@ export class MatterNode {
87
96
  if (this.#netInterface !== undefined) {
88
97
  this.#environment.vars.set("mdns.networkinterface", this.#netInterface);
89
98
  }
99
+
90
100
  // Build up the "Not-so-legacy" Controller
91
101
  const id = `shell-${this.#nodeNum.toString()}`;
92
102
  this.commissioningController = new CommissioningController({
@@ -96,6 +106,7 @@ export class MatterNode {
96
106
  },
97
107
  autoConnect: false,
98
108
  adminFabricLabel: "matter.js Shell",
109
+ enableOtaProvider: true,
99
110
  });
100
111
 
101
112
  const storageService = this.commissioningController.env.get(StorageService);
@@ -129,6 +140,7 @@ export class MatterNode {
129
140
  async close() {
130
141
  await this.commissioningController?.close();
131
142
  await this.#services?.close();
143
+ this.#observers?.close();
132
144
  }
133
145
 
134
146
  async start() {
@@ -148,6 +160,16 @@ export class MatterNode {
148
160
  } else {
149
161
  throw new Error("No controller initialized");
150
162
  }
163
+
164
+ this.#observers = this.#observers ?? new ObserverGroup(this.#environment.runtime);
165
+ const updateManagerEvents = this.commissioningController.otaProvider.eventsOf(SoftwareUpdateManager);
166
+ this.#observers.on(updateManagerEvents.updateAvailable, (peer, details) => {
167
+ logger.info(`Update available for peer `, peer, `:`, details);
168
+ });
169
+ this.#observers.on(updateManagerEvents.updateDone, peer => {
170
+ logger.info(`Update done for peer `, peer);
171
+ });
172
+
151
173
  this.#started = true;
152
174
  }
153
175
 
@@ -5,7 +5,9 @@
5
5
  */
6
6
 
7
7
  import { capitalize, decamelize, Diagnostic } from "#general";
8
- import { NodeId, VendorId } from "#types";
8
+ import { ClientNode, SoftwareUpdateManager } from "#node";
9
+ import { PeerAddress } from "#protocol";
10
+ import { FabricIndex, NodeId, VendorId } from "#types";
9
11
  import { CommissioningControllerNodeOptions, NodeStateInformation } from "@project-chip/matter.js/device";
10
12
  import type { Argv } from "yargs";
11
13
  import { MatterNode } from "../MatterNode.js";
@@ -228,10 +230,15 @@ export default function commands(theNode: MatterNode) {
228
230
  }
229
231
  }
230
232
 
233
+ const nodeDetails = theNode.commissioningController.getCommissionedNodesDetails();
234
+
231
235
  for (const nodeIdToProcess of nodeIds) {
232
236
  const node = theNode.commissioningController.getPairedNode(nodeIdToProcess);
233
237
  if (node === undefined) {
234
- console.log(`Node ${nodeIdToProcess}: Not initialized`);
238
+ const details = nodeDetails.find(nd => nd.nodeId === nodeIdToProcess);
239
+ console.log(
240
+ `Node ${nodeIdToProcess}: Not initialized${details?.deviceData?.basicInformation !== undefined ? ` (${details.deviceData.basicInformation.vendorName} ${details.deviceData.basicInformation.productName})` : ""}`,
241
+ );
235
242
  } else {
236
243
  const basicInfo = node.basicInformation;
237
244
  console.log(
@@ -241,11 +248,112 @@ export default function commands(theNode: MatterNode) {
241
248
  }
242
249
  },
243
250
  )
251
+ .command(
252
+ "add [node-id]",
253
+ "Adds a node without commissioning and connects to it (means need to exist in the fabric and commissioned otherwise)",
254
+ yargs => {
255
+ return yargs
256
+ .positional("node-id", {
257
+ describe: "node id to connect.",
258
+ default: "all",
259
+ type: "string",
260
+ demandOption: true,
261
+ })
262
+ .positional("min-subscription-interval", {
263
+ describe:
264
+ "Minimum subscription interval in seconds. If set then the node is subscribed to all attributes and events.",
265
+ type: "number",
266
+ })
267
+ .positional("max-subscription-interval", {
268
+ describe:
269
+ "Maximum subscription interval in seconds. If minimum interval is set and this not it will be determined automatically.",
270
+ type: "number",
271
+ });
272
+ },
273
+ async argv => {
274
+ const { nodeId: nodeIdStr, maxSubscriptionInterval, minSubscriptionInterval } = argv;
275
+ await theNode.start();
276
+ if (theNode.commissioningController === undefined) {
277
+ throw new Error("CommissioningController not initialized");
278
+ }
279
+ let nodeIds = theNode.commissioningController.getCommissionedNodes();
280
+
281
+ const cmdNodeId = NodeId(BigInt(nodeIdStr));
282
+ nodeIds = nodeIds.filter(nodeId => nodeId === cmdNodeId);
283
+ if (nodeIds.length) {
284
+ throw new Error(`Node ${nodeIdStr} already known`);
285
+ }
286
+
287
+ await theNode.commissioningController.node.peers.forAddress(
288
+ theNode.commissioningController.fabric.addressOf(cmdNodeId),
289
+ );
290
+
291
+ const autoSubscribe = minSubscriptionInterval !== undefined;
292
+
293
+ const node = await theNode.commissioningController.getNode(cmdNodeId);
294
+ node.connect({
295
+ autoSubscribe,
296
+ subscribeMinIntervalFloorSeconds: autoSubscribe ? minSubscriptionInterval : undefined,
297
+ subscribeMaxIntervalCeilingSeconds: autoSubscribe ? maxSubscriptionInterval : undefined,
298
+ ...createDiagnosticCallbacks(),
299
+ });
300
+ },
301
+ )
244
302
  .command(
245
303
  "ota",
246
304
  "OTA update operations for nodes",
247
305
  yargs =>
248
306
  yargs
307
+ .command(
308
+ "known [node-id]",
309
+ "List which OTA updates are known to be available for commissioned nodes. A first query by the provider must have happened for this to be filled.",
310
+ yargs => {
311
+ return yargs
312
+ .positional("node-id", {
313
+ describe: "Node ID to check for updates",
314
+ type: "string",
315
+ default: undefined,
316
+ })
317
+ .option("local", {
318
+ describe: "include local update files",
319
+ type: "boolean",
320
+ default: false,
321
+ });
322
+ },
323
+ async argv => {
324
+ const { nodeId: nodeIdStr, local } = argv;
325
+
326
+ await theNode.start();
327
+ if (theNode.commissioningController === undefined) {
328
+ throw new Error("CommissioningController not initialized");
329
+ }
330
+
331
+ let peerToCheck: ClientNode | undefined = undefined;
332
+ if (nodeIdStr !== undefined) {
333
+ const nodeId = NodeId(BigInt(nodeIdStr));
334
+ peerToCheck = (await theNode.commissioningController.getNode(nodeId))?.node;
335
+ }
336
+
337
+ const updatesAvailable = await theNode.commissioningController.otaProvider.act(
338
+ agent =>
339
+ agent
340
+ .get(SoftwareUpdateManager)
341
+ .queryUpdates({ peerToCheck, includeStoredUpdates: local }),
342
+ );
343
+
344
+ if (updatesAvailable.length) {
345
+ console.log(`OTA updates available for ${updatesAvailable.length} nodes:`);
346
+ for (const { peerAddress, info } of updatesAvailable) {
347
+ console.log(
348
+ peerAddress,
349
+ `: new Version: ${info.softwareVersion} (${info.softwareVersionString})`,
350
+ );
351
+ }
352
+ } else {
353
+ console.log("No OTA updates available.");
354
+ }
355
+ },
356
+ )
249
357
  .command(
250
358
  "check <node-id>",
251
359
  "Check for OTA updates for a commissioned node",
@@ -261,10 +369,15 @@ export default function commands(theNode: MatterNode) {
261
369
  type: "string",
262
370
  choices: ["prod", "test"],
263
371
  default: "prod",
372
+ })
373
+ .option("local", {
374
+ describe: "include local update files",
375
+ type: "boolean",
376
+ default: false,
264
377
  });
265
378
  },
266
379
  async argv => {
267
- const { nodeId: nodeIdStr, mode } = argv;
380
+ const { nodeId: nodeIdStr, mode, local } = argv;
268
381
  const isProduction = mode === "prod";
269
382
 
270
383
  await theNode.start();
@@ -302,12 +415,13 @@ export default function commands(theNode: MatterNode) {
302
415
  );
303
416
  console.log(` DCL Mode: ${isProduction ? "production" : "test"}\n`);
304
417
 
305
- const updateInfo = await theNode.otaService.checkForUpdate(
306
- basicInfo.vendorId as VendorId,
307
- basicInfo.productId as number,
308
- basicInfo.softwareVersion as number,
418
+ const updateInfo = await theNode.otaService.checkForUpdate({
419
+ vendorId: basicInfo.vendorId as VendorId,
420
+ productId: basicInfo.productId as number,
421
+ currentSoftwareVersion: basicInfo.softwareVersion as number,
422
+ includeStoredUpdates: local,
309
423
  isProduction,
310
- );
424
+ });
311
425
 
312
426
  if (updateInfo) {
313
427
  console.log("✓ Update available!");
@@ -350,10 +464,15 @@ export default function commands(theNode: MatterNode) {
350
464
  describe: "Force download even if update is already stored locally",
351
465
  type: "boolean",
352
466
  default: false,
467
+ })
468
+ .option("local", {
469
+ describe: "include local update files",
470
+ type: "boolean",
471
+ default: false,
353
472
  });
354
473
  },
355
474
  async argv => {
356
- const { nodeId: nodeIdStr, mode, force } = argv;
475
+ const { nodeId: nodeIdStr, mode, force, local } = argv;
357
476
  const isProduction = mode === "prod";
358
477
  const forceDownload = force === true;
359
478
 
@@ -392,12 +511,13 @@ export default function commands(theNode: MatterNode) {
392
511
  );
393
512
  console.log(` DCL Mode: ${isProduction ? "production" : "test"}\n`);
394
513
 
395
- const updateInfo = await theNode.otaService.checkForUpdate(
396
- basicInfo.vendorId as VendorId,
397
- basicInfo.productId as number,
398
- basicInfo.softwareVersion as number,
514
+ const updateInfo = await theNode.otaService.checkForUpdate({
515
+ vendorId: basicInfo.vendorId as VendorId,
516
+ productId: basicInfo.productId as number,
517
+ currentSoftwareVersion: basicInfo.softwareVersion as number,
518
+ includeStoredUpdates: local,
399
519
  isProduction,
400
- );
520
+ });
401
521
 
402
522
  if (!updateInfo) {
403
523
  console.log("No updates available. Device is up to date.");
@@ -427,6 +547,144 @@ export default function commands(theNode: MatterNode) {
427
547
  );
428
548
  },
429
549
  )
550
+ .command(
551
+ "apply <node-id>",
552
+ "Apply OTA update for a commissioned node",
553
+ yargs => {
554
+ return yargs
555
+ .positional("node-id", {
556
+ describe: "Node ID to download update for",
557
+ type: "string",
558
+ demandOption: true,
559
+ })
560
+ .option("mode", {
561
+ describe: "DCL mode (prod or test)",
562
+ type: "string",
563
+ choices: ["prod", "test"],
564
+ default: "prod",
565
+ })
566
+ .option("force", {
567
+ describe: "Force download even if update is already stored locally",
568
+ type: "boolean",
569
+ default: false,
570
+ })
571
+ .option("local", {
572
+ describe: "Apply update from local file",
573
+ type: "boolean",
574
+ default: false,
575
+ });
576
+ },
577
+ async argv => {
578
+ const { nodeId: nodeIdStr, mode, force, local } = argv;
579
+ const isProduction = mode === "prod";
580
+ const forceDownload = force === true;
581
+
582
+ await theNode.start();
583
+
584
+ if (theNode.commissioningController === undefined) {
585
+ throw new Error("CommissioningController not initialized");
586
+ }
587
+
588
+ const nodeId = NodeId(BigInt(nodeIdStr));
589
+ const nodeDetails = theNode.commissioningController
590
+ .getCommissionedNodesDetails()
591
+ .find(nd => nd.nodeId === nodeId);
592
+ const basicInfo = nodeDetails?.deviceData?.basicInformation;
593
+ if (!basicInfo) {
594
+ throw new Error(`Node ${nodeIdStr} has no basic information available`);
595
+ }
596
+ if (
597
+ basicInfo.vendorId === undefined ||
598
+ basicInfo.productId === undefined ||
599
+ basicInfo.softwareVersion === undefined
600
+ ) {
601
+ throw new Error(
602
+ `Node ${nodeIdStr} is missing required basic information for OTA check`,
603
+ );
604
+ }
605
+
606
+ console.log(`Checking for OTA updates for node ${nodeIdStr}...`);
607
+ console.log(
608
+ ` Vendor ID: ${Diagnostic.hex(basicInfo.vendorId as VendorId, 4).toUpperCase()}`,
609
+ );
610
+ console.log(
611
+ ` Product ID: ${Diagnostic.hex(basicInfo.productId as number, 4).toUpperCase()}`,
612
+ );
613
+ console.log(
614
+ ` Current Software Version: ${basicInfo.softwareVersion} (${basicInfo.softwareVersionString})`,
615
+ );
616
+ console.log(` DCL Mode: ${isProduction ? "production" : "test"}\n`);
617
+
618
+ const localUpdates = await theNode.otaService.find({
619
+ vendorId: basicInfo.vendorId as VendorId,
620
+ productId: basicInfo.productId as number,
621
+ currentVersion: basicInfo.softwareVersion as number,
622
+ });
623
+
624
+ if (local && !localUpdates.length) {
625
+ console.log("No applicable updates available in local storage.");
626
+ return;
627
+ }
628
+
629
+ const updateInfo = await theNode.otaService.checkForUpdate({
630
+ vendorId: basicInfo.vendorId as VendorId,
631
+ productId: basicInfo.productId as number,
632
+ currentSoftwareVersion: basicInfo.softwareVersion as number,
633
+ includeStoredUpdates: local,
634
+ isProduction,
635
+ });
636
+
637
+ let updateVersion: number;
638
+ if (!updateInfo && !local) {
639
+ console.log("No updates available in DCL. Device is up to date.");
640
+ return;
641
+ } else if (updateInfo) {
642
+ console.log("Update found:");
643
+ console.log(
644
+ ` New Version: ${updateInfo.softwareVersion} (${updateInfo.softwareVersionString})`,
645
+ );
646
+ console.log(` OTA URL: ${updateInfo.otaUrl}`);
647
+ if (updateInfo.otaFileSize) {
648
+ const sizeKB = Number(updateInfo.otaFileSize) / 1024;
649
+ console.log(` File Size: ${sizeKB.toFixed(2)} KB`);
650
+ }
651
+
652
+ console.log("\nDownloading update...");
653
+ const fd = await theNode.otaService.downloadUpdate(
654
+ updateInfo,
655
+ isProduction,
656
+ forceDownload,
657
+ );
658
+
659
+ updateVersion = updateInfo.softwareVersion;
660
+
661
+ console.log(
662
+ `✓ Update to version ${updateVersion} (${updateInfo.softwareVersionString}) downloaded and stored successfully: ${fd.text}`,
663
+ );
664
+ } else {
665
+ updateVersion = localUpdates[0].softwareVersion;
666
+ console.log(
667
+ `Update to version ${updateVersion} (${localUpdates[0].softwareVersionString}) found in local storage: ${localUpdates[0].filename}`,
668
+ );
669
+ }
670
+
671
+ const node = theNode.commissioningController.getPairedNode(nodeId);
672
+ if (node === undefined) {
673
+ throw new Error(`Node ${nodeIdStr} not connected`);
674
+ }
675
+
676
+ await theNode.commissioningController.otaProvider.act(agent => {
677
+ return agent
678
+ .get(SoftwareUpdateManager)
679
+ .forceUpdate(
680
+ PeerAddress({ nodeId, fabricIndex: FabricIndex(1) }),
681
+ basicInfo.vendorId as VendorId,
682
+ basicInfo.productId as number,
683
+ updateVersion,
684
+ );
685
+ });
686
+ },
687
+ )
430
688
  .demandCommand(1, "Please specify an OTA subcommand"),
431
689
  async (argv: any) => {
432
690
  argv.unhandled = true;
@@ -1,12 +0,0 @@
1
- /**
2
- * @license
3
- * Copyright 2022-2025 Matter.js Authors
4
- * SPDX-License-Identifier: Apache-2.0
5
- */
6
- function camelize(str) {
7
- return str.charAt(0).toLowerCase() + str.slice(1);
8
- }
9
- export {
10
- camelize
11
- };
12
- //# sourceMappingURL=String.js.map
@@ -1,6 +0,0 @@
1
- {
2
- "version": 3,
3
- "sources": ["../../../src/util/String.ts"],
4
- "mappings": "AAAA;AAAA;AAAA;AAAA;AAAA;AAMO,SAAS,SAAS,KAAa;AAClC,SAAO,IAAI,OAAO,CAAC,EAAE,YAAY,IAAI,IAAI,MAAM,CAAC;AACpD;",
5
- "names": []
6
- }
@@ -1,9 +0,0 @@
1
- /**
2
- * @license
3
- * Copyright 2022-2025 Matter.js Authors
4
- * SPDX-License-Identifier: Apache-2.0
5
- */
6
-
7
- export function camelize(str: string) {
8
- return str.charAt(0).toLowerCase() + str.slice(1);
9
- }