rovloom 0.5.0 → 0.6.1

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.
Files changed (64) hide show
  1. package/README.md +9 -1
  2. package/dist/src/admin/index.js +1 -1
  3. package/dist/src/{chunk-emcefrc1.js → chunk-0e9gg4sg.js} +3 -4
  4. package/dist/src/chunk-1xer1ent.js +102 -0
  5. package/dist/src/{chunk-863tk45b.js → chunk-41fny9qm.js} +5 -5
  6. package/dist/src/{chunk-zjzrcc59.js → chunk-59h200cr.js} +139 -7
  7. package/dist/src/chunk-5w5srj3b.js +93 -0
  8. package/dist/src/{chunk-d4ejrtjq.js → chunk-6n6b1xpy.js} +1 -1
  9. package/dist/src/{chunk-ympzv86c.js → chunk-6w4g9fw8.js} +16 -4
  10. package/dist/src/{chunk-smpevv7n.js → chunk-73aq2qkz.js} +9 -16
  11. package/dist/src/{chunk-0ake7e4r.js → chunk-8c9yc0ge.js} +9 -17
  12. package/dist/src/{chunk-57ayxqnb.js → chunk-8fy8w7ds.js} +2 -23
  13. package/dist/src/{chunk-64ftwe9b.js → chunk-8ykrqhxh.js} +8 -2
  14. package/dist/src/{chunk-2tn0r64b.js → chunk-9h9x79bx.js} +5 -5
  15. package/dist/src/{chunk-nyn75b8v.js → chunk-av31bx1e.js} +31 -2
  16. package/dist/src/{chunk-0xgpxdgc.js → chunk-bbdtsg4b.js} +7 -5
  17. package/dist/src/{chunk-q5pgbwb3.js → chunk-e7jgpxkf.js} +2 -2
  18. package/dist/src/{chunk-zj48jvfe.js → chunk-efty77sb.js} +3 -40
  19. package/dist/src/{chunk-abd4envz.js → chunk-enj7s8cv.js} +71 -78
  20. package/dist/src/{chunk-4etdq0cp.js → chunk-ftpy8xx3.js} +313 -28
  21. package/dist/src/{chunk-zdxww7ms.js → chunk-h3xyq7zk.js} +1 -1
  22. package/dist/src/{chunk-ttsrctxg.js → chunk-hxmq28pg.js} +9 -7
  23. package/dist/src/{chunk-r0nfthsf.js → chunk-j59ac0xs.js} +2 -2
  24. package/dist/src/{chunk-5s2emvww.js → chunk-j6svdqr8.js} +10 -302
  25. package/dist/src/{chunk-9y36gntb.js → chunk-jkzfck98.js} +10 -5
  26. package/dist/src/{chunk-sj24fpz3.js → chunk-m76cmkfy.js} +28 -30
  27. package/dist/src/{chunk-5n8csngz.js → chunk-m96mbzcw.js} +816 -305
  28. package/dist/src/{chunk-xhq21g24.js → chunk-m9c1pnv9.js} +3 -3
  29. package/dist/src/{chunk-fnakrk0a.js → chunk-n3z3jaxy.js} +39 -36
  30. package/dist/src/{chunk-e7x51y0t.js → chunk-ndj0ay2p.js} +19 -18
  31. package/dist/src/chunk-pgs9jp6t.js +320 -0
  32. package/dist/src/chunk-pksaqt9a.js +25 -0
  33. package/dist/src/{chunk-ebm3kvnq.js → chunk-pnep7yhj.js} +31 -100
  34. package/dist/src/chunk-qn5xae7g.js +66 -0
  35. package/dist/src/{chunk-0pewfj89.js → chunk-qp8tgms2.js} +1 -1
  36. package/dist/src/{chunk-7k9g0x5e.js → chunk-rmgw8h27.js} +10 -8
  37. package/dist/src/{chunk-gbsbwssz.js → chunk-sf4ztxba.js} +3 -3
  38. package/dist/src/{chunk-7q96e161.js → chunk-shez7hkc.js} +6 -12
  39. package/dist/src/chunk-sqz614bh.js +30 -0
  40. package/dist/src/{chunk-09f9q26d.js → chunk-vdwzb63d.js} +2 -2
  41. package/dist/src/chunk-xtvgm6kf.js +48 -0
  42. package/dist/src/chunk-y8zm75jt.js +157 -0
  43. package/dist/src/chunk-yasqw2vj.js +756 -0
  44. package/dist/src/{chunk-ybte82d3.js → chunk-z0qmfqvd.js} +4 -3
  45. package/dist/src/chunk-zm705snh.js +53 -0
  46. package/dist/src/cli/index.js +39 -30
  47. package/dist/src/cli/main.js +14 -9
  48. package/dist/src/connector/herdr/installation.js +4 -4
  49. package/dist/src/connector/herdr/provider.js +9 -9
  50. package/dist/src/connector/herdr/runtime.js +7 -7
  51. package/dist/src/connector/luvus/index.js +7 -6
  52. package/dist/src/mcp/index.js +16 -14
  53. package/dist/src/runtime/index.js +16 -15
  54. package/dist/src/service/index.js +3 -4
  55. package/dist/src/store.js +4 -4
  56. package/dist/src/transport/index.js +9 -9
  57. package/dist/src/webui/index.js +975 -834
  58. package/package.json +1 -1
  59. package/dist/src/chunk-5j0gj6w2.js +0 -7
  60. package/dist/src/chunk-9yg6x3gt.js +0 -24
  61. package/dist/src/chunk-erdq0rn8.js +0 -1300
  62. package/dist/src/chunk-n073xnr1.js +0 -1117
  63. package/dist/src/chunk-rwpynx2j.js +0 -51
  64. package/dist/src/chunk-vwcntax3.js +0 -228
@@ -27,7 +27,7 @@ import {
27
27
  ConnectorAttemptBook2,
28
28
  createConnectorAdmissionBackend2,
29
29
  connectorAdmissionAdapter
30
- } from "./chunk-d4ejrtjq.js";
30
+ } from "./chunk-6n6b1xpy.js";
31
31
  import {
32
32
  compileHerdrSchemas2
33
33
  } from "./chunk-5h82060k.js";
@@ -35,11 +35,11 @@ import {
35
35
  HerdrLocalError,
36
36
  inspectHerdrPath,
37
37
  pinHerdrConfig
38
- } from "./chunk-q5pgbwb3.js";
38
+ } from "./chunk-e7jgpxkf.js";
39
39
  import {
40
40
  HerdrInstallation2,
41
41
  createHerdrHostServices2
42
- } from "./chunk-863tk45b.js";
42
+ } from "./chunk-41fny9qm.js";
43
43
  import {
44
44
  createHerdrGatewaySourceOwner,
45
45
  persistentHerdrBackend2,
@@ -48,13 +48,13 @@ import {
48
48
  import {
49
49
  createHerdrWireAdapter,
50
50
  createHerdrRuntime2
51
- } from "./chunk-ttsrctxg.js";
51
+ } from "./chunk-hxmq28pg.js";
52
52
  import {
53
53
  describeHerdrContract2
54
54
  } from "./chunk-5svt6rwr.js";
55
55
  import {
56
56
  LuvusDispatchClaims2
57
- } from "./chunk-gbsbwssz.js";
57
+ } from "./chunk-sf4ztxba.js";
58
58
  import {
59
59
  privateFile,
60
60
  readPrivateBytes
@@ -23,7 +23,7 @@ import {
23
23
  import {
24
24
  lockContent,
25
25
  recoverStaleLock
26
- } from "./chunk-zdxww7ms.js";
26
+ } from "./chunk-h3xyq7zk.js";
27
27
  import {
28
28
  privatePath,
29
29
  privateFile,
@@ -1636,6 +1636,35 @@ class Store2 {
1636
1636
  revoke(machine) {
1637
1637
  this.devices.revoke(machine);
1638
1638
  }
1639
+ deleteDevice(machine, actor) {
1640
+ this.transaction((now) => {
1641
+ this.devices.applyRevoke(machine, now);
1642
+ for (const table of ["pairing_claims", "enrollments", "admin_pairings", "providers", "calls", "machines"]) {
1643
+ this.db.prepare(`DELETE FROM ${table} WHERE machine_id=?`).run(machine);
1644
+ }
1645
+ this.audit("machine_deleted", actor, now, undefined, { machine_id: machine });
1646
+ }, false);
1647
+ }
1648
+ listPairings(offset = 0) {
1649
+ return this.db.prepare(`SELECT p.pairing_id,p.machine_id,m.name,
1650
+ CASE WHEN p.status='pending' AND p.expires<=? THEN 'expired' ELSE p.status END AS status,p.expires
1651
+ FROM admin_pairings p JOIN machines m ON m.machine_id=p.machine_id ORDER BY p.expires DESC,p.pairing_id LIMIT 51 OFFSET ?`).all(this.clock(), offset);
1652
+ }
1653
+ deletePairing(pairing, actor) {
1654
+ return this.transaction((now) => {
1655
+ const application = this.devices.pairingApplication(pairing);
1656
+ if (!application) {
1657
+ throw new GatewayError2("pairing_not_found");
1658
+ }
1659
+ const unfinished = this.db.prepare("SELECT claim_id FROM pairing_claims WHERE pairing_id=? AND status IN ('approved','delivered')").get(pairing);
1660
+ if (unfinished) {
1661
+ this.devices.applyRevoke(application.machine_id, now);
1662
+ }
1663
+ this.db.prepare("DELETE FROM admin_pairings WHERE pairing_id=?").run(pairing);
1664
+ this.audit("pairing_deleted", actor, now, undefined, { pairing_id: pairing, machine_id: application.machine_id });
1665
+ return unfinished ? application.machine_id : null;
1666
+ }, false);
1667
+ }
1639
1668
  defineProvider(binding) {
1640
1669
  validateProvider2(binding);
1641
1670
  return this.transaction((now) => {
@@ -2275,4 +2304,4 @@ class Store2 {
2275
2304
 
2276
2305
  export { DEFAULT_RETENTION2, configuredSnapshotDirectory, SCHEMA_VERSION, assertBudget, assertUsage, GATEWAY_LOCK_FORMAT2, Store2 };
2277
2306
 
2278
- //# debugId=14A43F12EAAA7BD364756E2164756E21
2307
+ //# debugId=B8B3ABA270E159D964756E2164756E21
@@ -29,17 +29,19 @@ import {
29
29
  createLuvusWireAdapter2
30
30
  } from "./chunk-hz8pm6hz.js";
31
31
  import {
32
- LuvusAdapterError2,
33
- ConnectorCapacityError,
34
32
  readLinuxPeer,
35
33
  pinTerminalExecution,
36
34
  assertTerminalExecutionAllowed
37
- } from "./chunk-57ayxqnb.js";
35
+ } from "./chunk-8fy8w7ds.js";
38
36
  import {
39
37
  macosPeer,
40
38
  windowsInspectPath,
41
39
  windowsPipeServerPid
42
- } from "./chunk-09f9q26d.js";
40
+ } from "./chunk-vdwzb63d.js";
41
+ import {
42
+ LuvusAdapterError2,
43
+ ConnectorCapacityError
44
+ } from "./chunk-pksaqt9a.js";
43
45
  import {
44
46
  agentSearchPath
45
47
  } from "./chunk-3nnahj0j.js";
@@ -1191,4 +1193,4 @@ function readLuvusPeer2(socket, endpoint) {
1191
1193
  }
1192
1194
  export { createProviderResultAccess2, WINDOWS_PIPE, LUVUS_ENDPOINT_TRANSPORT, localLimits, withPrivateUmask, pinConfig, measureLuvusInstallation, verifyInstallation, childEnvironment, inspectEndpoint, recheckEndpoint, aborted, deadline, runFixedProcess, runSocket, parseRpcFrame, LuvusRpcAdapter2, createLuvusCatalog2, createLuvusResultAccess2, readLinuxLuvusPeer2, readWindowsLuvusPeer2, readMacosLuvusPeer2, readLuvusPeer2 };
1193
1195
 
1194
- //# debugId=457F5F627A972E6164756E2164756E21
1196
+ //# debugId=E452FD0D21C4480664756E2164756E21
@@ -12,11 +12,11 @@ import {
12
12
  windowsInspectPath,
13
13
  windowsPipeServerPid,
14
14
  windowsProcessFacts
15
- } from "./chunk-09f9q26d.js";
15
+ } from "./chunk-vdwzb63d.js";
16
16
  import {
17
17
  readLinuxPeer,
18
18
  pinTerminalExecution
19
- } from "./chunk-57ayxqnb.js";
19
+ } from "./chunk-8fy8w7ds.js";
20
20
  import {
21
21
  agentSearchPath
22
22
  } from "./chunk-3nnahj0j.js";
@@ -1,9 +1,5 @@
1
1
  // @bun
2
2
  import {
3
- GatewayError2
4
- } from "./chunk-d71r315c.js";
5
- import {
6
- createNativeValidator2,
7
3
  LUVUS_OPERATION_READ,
8
4
  LUVUS_OPERATION_WRITE,
9
5
  luvusMethod2
@@ -15,7 +11,7 @@ import {
15
11
  } from "./chunk-qt9m2kg2.js";
16
12
  import {
17
13
  LuvusAdapterError2
18
- } from "./chunk-57ayxqnb.js";
14
+ } from "./chunk-pksaqt9a.js";
19
15
 
20
16
  // src/runtime/luvus-operations.ts
21
17
  var conditional = new Set(["pane.list", "agent.prompt", "agent.send", "agent.wait", "agent.keys"]);
@@ -269,39 +265,6 @@ function validateLuvusOperationParams2(method, input) {
269
265
  }
270
266
  }
271
267
 
272
- // src/runtime/request-preflight.ts
273
- class NativeRequestPreflightError extends GatewayError2 {
274
- outcome = "not_dispatched";
275
- constructor() {
276
- super("native_request_invalid");
277
- }
278
- }
279
- function createLuvusRequestPreflight(contract) {
280
- const validator = createNativeValidator2(contract);
281
- return (request) => {
282
- const checked = validator.checkRequestShape(request);
283
- if (!checked.ok) {
284
- if (checked.error.code === "native_request_invalid") {
285
- throw new NativeRequestPreflightError;
286
- }
287
- throw new GatewayError2(checked.error.code);
288
- }
289
- };
290
- }
291
- function luvusValidation(kind, request, options) {
292
- if (kind !== "luvus" || !luvusOperationDescriptor2(request.method)) {
293
- return options;
294
- }
295
- const required = luvusOperationValidation2(request.method);
296
- if (options.validation === undefined) {
297
- return { ...options, validation: required };
298
- }
299
- if (options.validation !== required) {
300
- throw new NativeRequestPreflightError;
301
- }
302
- return options;
303
- }
304
-
305
- export { LUVUS_OPERATION_METHODS2, luvusOperationDescriptor2, luvusOperationValidation2, validateLuvusOperationParams2, NativeRequestPreflightError, createLuvusRequestPreflight, luvusValidation };
268
+ export { LUVUS_OPERATION_METHODS2, luvusOperationDescriptor2, luvusOperationValidation2, validateLuvusOperationParams2 };
306
269
 
307
- //# debugId=3118E44EB80F2C2464756E2164756E21
270
+ //# debugId=115949A0A756E47E64756E2164756E21
@@ -1,10 +1,14 @@
1
1
  // @bun
2
+ import {
3
+ cliMessages2,
4
+ formatMessage2
5
+ } from "./chunk-pgs9jp6t.js";
2
6
  import {
3
7
  readRuntimeConfig2
4
8
  } from "./chunk-bspzg8er.js";
5
9
  import {
6
10
  readOrCreateRoleConfig
7
- } from "./chunk-64ftwe9b.js";
11
+ } from "./chunk-8ykrqhxh.js";
8
12
  import {
9
13
  resolveRoleConfigPath2
10
14
  } from "./chunk-1bf0wmgk.js";
@@ -18,7 +22,7 @@ import {
18
22
  } from "./chunk-hpzr94hm.js";
19
23
  import {
20
24
  PRODUCT_VERSION2
21
- } from "./chunk-r0nfthsf.js";
25
+ } from "./chunk-j59ac0xs.js";
22
26
  import {
23
27
  isWildcardHostname
24
28
  } from "./chunk-6n9s7nfe.js";
@@ -62,44 +66,9 @@ function serviceDiagnostic(text) {
62
66
  }
63
67
 
64
68
  // src/cli/run.ts
65
- var WILDCARD_LISTEN_WARNING = `wildcard_listener
66
- MCP/management listen on all interfaces over plain HTTP; protect them with a firewall or a TLS reverse proxy.
67
- MCP/\u7BA1\u7406\u9875\u76D1\u542C\u6240\u6709\u7F51\u5361\u4E14\u4E3A\u660E\u6587 HTTP\uFF1B\u8BF7\u7528\u9632\u706B\u5899\u6216 TLS \u53CD\u5411\u4EE3\u7406\u6536\u53E3\u3002
68
- `;
69
- var HELP2 = `Rovloom ${PRODUCT_VERSION2}
70
-
71
- \u7528\u6CD5\uFF1A
72
- rovloom --help
73
- rovloom --version
74
- rovloom config template gateway|connector
75
- rovloom config init connector [--provider luvus|herdr|mixed] [--config /absolute/path/config.json]
76
- rovloom config init gateway [--container] [--config /absolute/path/config.json]
77
- rovloom config check [--role gateway|connector] [--config /absolute/path/config.json]
78
- rovloom config check-runtime [--role gateway|connector] [--config /absolute/path/config.json]
79
- rovloom gateway [--add-device | --repair-device] [--config /absolute/path/config.json] [--non-interactive]
80
- rovloom connector [--repair | --claim] [--config /absolute/path/config.json] [--non-interactive]
81
- rovloom service --help
82
- rovloom token --help
83
- rovloom doctor --help
84
- rovloom storage --help
85
- rovloom admin --help
86
-
87
- gateway / connector \u542F\u52A8\u5BF9\u5E94\u89D2\u8272\u3002\u9996\u6B21\u8FD0\u884C\u65F6\u5728\u771F\u5B9E\u672C\u5730\u7EC8\u7AEF\u5B8C\u6210\u4E00\u6B21\u6027\u914D\u5BF9\u4E0E\u539F\u751F\u5B89\u88C5\u6279\u51C6\uFF1B
88
- \u5728\u7EC8\u7AEF\u62D2\u7EDD\u914D\u5BF9\u63D0\u793A\u65F6\uFF0CGateway \u4FDD\u6301\u672A\u914D\u5BF9\u8FD0\u884C\uFF0C\u53EF\u5148\u8FD0\u884C rovloom admin create \u518D\u4ECE\u7BA1\u7406\u9875\u5B8C\u6210\u9996\u53F0\u914D\u5BF9\uFF1B
89
- --add-device \u5728\u5DF2\u5B8C\u6210\u7684\u5F15\u5BFC\u4E4B\u4E0A\u518D\u914D\u5BF9\u4E00\u53F0 Connector\uFF08\u6CBF\u7528\u540C\u4E00 MCP \u51ED\u636E\uFF0C\u6388\u6743\u968F\u4E4B\u6269\u5927\u5230\u65B0\u8BBE\u5907\uFF09\uFF1B
90
- --repair-device / --repair \u91CD\u65B0\u914D\u5BF9\u5DF2\u914D\u5BF9\u7684\u540C\u4E00\u8BBE\u5907\uFF08\u51ED\u636E\u4E22\u5931\u6216\u6CC4\u6F0F\uFF09\uFF0C\u4FDD\u7559\u539F\u751F\u8BBE\u7F6E\u4E0E MCP \u6388\u6743\u3002
91
- --claim \u8BA9\u672A\u914D\u5BF9\u7684 Connector \u5411\u8FD0\u884C\u4E2D\u7684 Gateway \u5728\u7EBF\u8BA4\u9886\u7BA1\u7406\u5458\u521B\u5EFA\u7684\u914D\u5BF9\u7533\u8BF7\uFF08\u7BA1\u7406\u9875\u6838\u5BF9\u7801\u6279\u51C6\uFF0CGateway \u4E0D\u505C\u673A\uFF09\u3002
92
- \u8FD9\u56DB\u4E2A\u9009\u9879\u9700\u8981\u771F\u5B9E\u672C\u5730\u7EC8\u7AEF\uFF0C\u4E0D\u53EF\u4E0E --non-interactive \u5408\u7528\u3002--non-interactive \u5173\u95ED\u672C\u5730\u4EA4\u4E92\u5F15\u5BFC\uFF08\u670D\u52A1\u4EE5\u6B64\u8FD0\u884C\uFF09\u3002
93
- token \u7BA1\u7406 MCP Bearer \u4EE4\u724C\uFF0Cadmin \u7BA1\u7406\u7BA1\u7406\u9875\u7BA1\u7406\u5458\uFF0Cservice \u7BA1\u7406\u5F00\u673A\u670D\u52A1\uFF1B\u8BE6\u89C1\u5404\u81EA\u7684 --help\u3002
94
- config check \u53EA\u8BFB\u68C0\u67E5\u914D\u7F6E\u6587\u4EF6\uFF1Bcheck-runtime \u53E6\u6838\u5BF9\u7A0B\u5E8F\u7BA1\u7406\u7684\u72B6\u6001\uFF0C\u4E0D\u8BFB\u53D6\u51ED\u636E\u3002
95
-
96
- \u7701\u7565 --config \u65F6\u8BFB\u53D6 ~/.config/rovloom/gateway.json \u6216 connector.json\uFF08Windows \u540C\u6837\u4F7F\u7528\u7528\u6237 home\uFF09\u3002
97
- \u6587\u4EF6\u7F3A\u5931\u65F6\u9996\u6B21\u8FD0\u884C\u4F1A\u751F\u6210\u9ED8\u8BA4\u914D\u7F6E\uFF0C\u5DF2\u6709\u6587\u4EF6\u4E0D\u4F1A\u88AB\u8986\u76D6\u6216\u91CD\u7F6E\u3002
98
- Gateway \u652F\u6301 Linux/macOS/Windows\uFF1BConnector \u652F\u6301 Linux x64\u3001Windows x64 \u4E0E macOS\uFF08x64 / arm64\uFF0C\u4EC5\u9644\u7740\u5DF2\u8FD0\u884C\u7684 Herdr / Luvus\uFF09\u3002
99
- \u9996\u6B21\u5F15\u5BFC\u6309 Connector \u7684 native.provider \u9009\u62E9 luvus\uFF08\u9ED8\u8BA4\uFF09\u3001herdr \u6216 mixed\u3002
100
- Agent \u4E0E\u6A21\u578B\u767B\u5F55\u9700\u72EC\u7ACB\u51C6\u5907\uFF1B\u539F\u751F ready \u4E0D\u4EE3\u8868\u6A21\u578B\u5DF2\u56DE\u590D\u3002
101
- \u9000\u51FA\u7801\uFF1A0 \u6210\u529F/\u6B63\u5E38\u5173\u95ED\uFF0C2 \u53C2\u6570\u6216\u914D\u7F6E\u9519\u8BEF\uFF0C3 \u540E\u7AEF\u4E0D\u53EF\u7528\uFF0C1 \u8FD0\u884C\u6216\u5173\u95ED\u5931\u8D25\u3002
102
- `;
69
+ function cliHelp2(language = "en") {
70
+ return formatMessage2(cliMessages2(language)["help.main"], { version: PRODUCT_VERSION2 });
71
+ }
103
72
  function parseCommand2(args, environment) {
104
73
  if (args.length === 0 || args.length === 1 && ["--help", "-h", "help"].includes(args[0])) {
105
74
  return { action: "help" };
@@ -144,26 +113,43 @@ function parseCommand2(args, environment) {
144
113
  throw new CliError2("invalid_arguments");
145
114
  }
146
115
  const withoutNonInteractive = nonInteractive ? serviceArgs.slice(0, -1) : serviceArgs;
147
- const flag = withoutNonInteractive[1];
148
- const repair = withoutNonInteractive[0] === "gateway" ? flag === "--repair-device" : flag === "--repair";
149
- const addDevice = withoutNonInteractive[0] === "gateway" && flag === "--add-device";
150
- const claim = withoutNonInteractive[0] === "connector" && flag === "--claim";
151
- if ((repair || addDevice || claim) && nonInteractive) {
116
+ const role = withoutNonInteractive[0];
117
+ if (role !== "gateway" && role !== "connector") {
152
118
  throw new CliError2("invalid_arguments");
153
119
  }
154
- const roleArgs = repair || addDevice || claim ? [withoutNonInteractive[0], ...withoutNonInteractive.slice(2)] : withoutNonInteractive;
155
- if ((roleArgs[0] === "gateway" || roleArgs[0] === "connector") && (roleArgs.length === 1 || roleArgs.length === 3 && roleArgs[1] === "--config")) {
156
- return {
157
- action: roleArgs[0],
158
- path: resolveRoleConfigPath2(roleArgs[0], roleArgs[2], environment),
159
- ...nonInteractive ? { nonInteractive: true } : {},
160
- ...serviceId ? { serviceId } : {},
161
- ...repair ? { repair: true } : {},
162
- ...addDevice ? { addDevice: true } : {},
163
- ...claim ? { claim: true } : {}
164
- };
120
+ let explicit;
121
+ let joinValue;
122
+ let issueCode = false;
123
+ let unpair = false;
124
+ for (let index = 1;index < withoutNonInteractive.length; index++) {
125
+ const option = withoutNonInteractive[index];
126
+ if (option === "--config" && explicit === undefined) {
127
+ explicit = withoutNonInteractive[++index];
128
+ if (explicit === undefined || explicit.startsWith("--")) {
129
+ throw new CliError2("invalid_arguments");
130
+ }
131
+ } else if (option === "--join" && role === "connector" && joinValue === undefined && !unpair) {
132
+ joinValue = withoutNonInteractive[++index];
133
+ if (joinValue === undefined || !/^wss?:\/\/[^#\s]+#[A-Za-z0-9_.-]+$/.test(joinValue)) {
134
+ throw new CliError2("invalid_arguments");
135
+ }
136
+ } else if (option === "--issue-code" && role === "gateway" && !issueCode) {
137
+ issueCode = true;
138
+ } else if (option === "--unpair" && role === "connector" && !unpair && joinValue === undefined) {
139
+ unpair = true;
140
+ } else {
141
+ throw new CliError2("invalid_arguments");
142
+ }
165
143
  }
166
- throw new CliError2("invalid_arguments");
144
+ return {
145
+ action: role,
146
+ path: resolveRoleConfigPath2(role, explicit, environment),
147
+ ...nonInteractive ? { nonInteractive: true } : {},
148
+ ...serviceId ? { serviceId } : {},
149
+ ...joinValue !== undefined ? { join: joinValue } : {},
150
+ ...issueCode ? { issueCode: true } : {},
151
+ ...unpair ? { unpair: true } : {}
152
+ };
167
153
  }
168
154
  async function untilStopped(running, signal) {
169
155
  let wake;
@@ -183,9 +169,9 @@ async function untilStopped(running, signal) {
183
169
  async function runCli2(args, io, runtime = {}, environment) {
184
170
  try {
185
171
  if (args[0] === "service") {
186
- const { SERVICE_HELP, handleServiceCommand } = await import("./chunk-emcefrc1.js");
172
+ const { handleServiceCommand } = await import("./chunk-0e9gg4sg.js");
187
173
  if (args.length === 2 && args[1] === "--help") {
188
- io.stderr.write(SERVICE_HELP);
174
+ io.stderr.write(cliMessages2(io.language)["help.service"]);
189
175
  return 0;
190
176
  }
191
177
  if (!runtime.service) {
@@ -194,6 +180,7 @@ async function runCli2(args, io, runtime = {}, environment) {
194
180
  const host = runtime.service;
195
181
  const code = await handleServiceCommand(args, {
196
182
  ...host,
183
+ language: io.language ?? "en",
197
184
  resolveDefaultConfig: host.resolveDefaultConfig ? (role, account) => {
198
185
  try {
199
186
  return host.resolveDefaultConfig(role, account);
@@ -212,19 +199,19 @@ async function runCli2(args, io, runtime = {}, environment) {
212
199
  throw new CliError2("invalid_arguments");
213
200
  }
214
201
  if (args[0] === "admin") {
215
- const { handleAdminCommand } = await import("./chunk-9yg6x3gt.js");
202
+ const { handleAdminCommand } = await import("./chunk-n3z3jaxy.js");
216
203
  return await handleAdminCommand(args, io, environment);
217
204
  }
218
205
  if (args[0] === "doctor" || args[0] === "storage") {
219
- const { handleStorageCommand } = await import("./chunk-0ake7e4r.js");
206
+ const { handleStorageCommand } = await import("./chunk-8c9yc0ge.js");
220
207
  return await handleStorageCommand(args, io, environment);
221
208
  }
222
209
  if (args[0] === "token") {
223
- const { handleTokenCommand } = await import("./chunk-sj24fpz3.js");
210
+ const { handleTokenCommand } = await import("./chunk-m76cmkfy.js");
224
211
  return await handleTokenCommand(args, io, environment);
225
212
  }
226
213
  if (args[0] === "config" && args[1] === "init") {
227
- const { initializeRoleConfig } = await import("./chunk-xhq21g24.js");
214
+ const { initializeRoleConfig } = await import("./chunk-m9c1pnv9.js");
228
215
  initializeRoleConfig(args, environment);
229
216
  io.stderr.write(`config_ready
230
217
  `);
@@ -232,7 +219,7 @@ async function runCli2(args, io, runtime = {}, environment) {
232
219
  }
233
220
  const command = parseCommand2(args, environment);
234
221
  if (command.action === "help") {
235
- io.stderr.write(HELP2);
222
+ io.stderr.write(cliHelp2(io.language));
236
223
  return 0;
237
224
  }
238
225
  if (command.action === "version") {
@@ -281,11 +268,14 @@ async function runCli2(args, io, runtime = {}, environment) {
281
268
  if (io.signal.aborted) {
282
269
  return 0;
283
270
  }
284
- if (!command.nonInteractive) {
271
+ if (command.unpair) {
272
+ const { handleConnectorUnpair } = await import("./chunk-sqz614bh.js");
273
+ return await handleConnectorUnpair(command.path, io);
274
+ }
275
+ if (!command.nonInteractive || command.join !== undefined || command.issueCode) {
285
276
  config = await runtime.prepare?.(config, command.path, io, {
286
- ...command.repair ? { repair: true } : {},
287
- ...command.addDevice ? { addDevice: true } : {},
288
- ...command.claim ? { claim: true } : {}
277
+ ...command.join !== undefined ? { join: command.join } : {},
278
+ ...command.issueCode ? { issueCode: true } : {}
289
279
  }) ?? config;
290
280
  }
291
281
  if (config.role !== command.action) {
@@ -306,15 +296,16 @@ async function runCli2(args, io, runtime = {}, environment) {
306
296
  }
307
297
  let reload = false;
308
298
  let warnedWildcard = false;
299
+ let shownDashboard = false;
309
300
  do {
310
301
  reload = false;
311
302
  const gateway = await runtime.gateway(config);
312
303
  if (!warnedWildcard && (isWildcardHostname(config.mcp_hostname) || config.management_enabled && isWildcardHostname(config.management_hostname))) {
313
304
  warnedWildcard = true;
314
- io.stderr.write(WILDCARD_LISTEN_WARNING);
305
+ io.stderr.write(cliMessages2(io.language)["run.wildcardListenWarning"]);
315
306
  }
316
307
  try {
317
- const { startHttpFacade } = await import("./chunk-ybte82d3.js");
308
+ const { startHttpFacade } = await import("./chunk-z0qmfqvd.js");
318
309
  const http = startHttpFacade({
319
310
  service: gateway.service,
320
311
  authentication: gateway.authentication,
@@ -322,17 +313,21 @@ async function runCli2(args, io, runtime = {}, environment) {
322
313
  port: config.mcp_port,
323
314
  ...config.mcp_public_url ? { publicUrl: config.mcp_public_url } : {},
324
315
  ...config.mcp_lan ? { lan: true } : {},
316
+ ...io.language ? { language: io.language } : {},
325
317
  diagnostic: (code) => io.stderr.write(code + `
326
318
  `)
327
319
  });
328
320
  try {
329
321
  await gateway.listening?.(http.url);
322
+ if (!shownDashboard && gateway.managementUrl) {
323
+ shownDashboard = true;
324
+ io.stderr.write("dashboard_listening " + new URL(gateway.managementUrl).href + `
325
+ `);
326
+ }
330
327
  if (gateway.setupRequired) {
331
328
  io.stderr.write("gateway_listening " + http.url + `
332
329
  pairing_required
333
- Gateway is running; complete local pairing and native setup before using an Agent.
334
- Gateway \u5DF2\u542F\u52A8\uFF1B\u4F7F\u7528 Agent \u524D\u4ECD\u9700\u5B8C\u6210\u672C\u5730\u914D\u5BF9\u548C\u539F\u751F\u521D\u59CB\u5316\u3002
335
- `);
330
+ ` + cliMessages2(io.language)["run.pairingRequiredHint"]);
336
331
  }
337
332
  await untilStopped({
338
333
  closed: Promise.race([
@@ -362,9 +357,7 @@ Gateway \u5DF2\u542F\u52A8\uFF1B\u4F7F\u7528 Agent \u524D\u4ECD\u9700\u5B8C\u621
362
357
  io.stderr.write(error.code + `
363
358
  `);
364
359
  if (error.code === "configuration_required") {
365
- io.stderr.write(`Setup requires a local terminal, a reachable Gateway, completed pairing and a compatible installed Luvus. Preserve uncertain setup state for owner review.
366
- \u521D\u59CB\u5316\u9700\u672C\u5730\u7EC8\u7AEF\u3001\u53EF\u8FBE Gateway\u3001\u5B8C\u6574\u914D\u5BF9\u53CA\u517C\u5BB9 Luvus \u5B89\u88C5\uFF1B\u7ED3\u679C\u4E0D\u786E\u5B9A\u65F6\u4FDD\u7559\u539F\u72B6\u6001\u5E76\u7531\u6240\u6709\u8005\u6838\u67E5\u3002
367
- `);
360
+ io.stderr.write(cliMessages2(io.language)["run.configurationRequiredHint"]);
368
361
  }
369
362
  return error.exitCode;
370
363
  }
@@ -374,6 +367,6 @@ Gateway \u5DF2\u542F\u52A8\uFF1B\u4F7F\u7528 Agent \u524D\u4ECD\u9700\u5B8C\u621
374
367
  }
375
368
  }
376
369
 
377
- export { HELP2, parseCommand2, runCli2 };
370
+ export { cliHelp2, parseCommand2, runCli2 };
378
371
 
379
- //# debugId=EDE27C0F1768E16864756E2164756E21
372
+ //# debugId=9F289B394757794864756E2164756E21