zk-agent-cli 0.1.0-rc.1 → 0.1.0-rc.2

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 (3) hide show
  1. package/README.md +99 -93
  2. package/dist/index.js +201 -17
  3. package/package.json +5 -1
package/README.md CHANGED
@@ -3,7 +3,41 @@
3
3
  `zk-agent-cli` is the packaged terminal CLI for the zk-agent operator path on
4
4
  zkSync Era and zkSync Sepolia.
5
5
 
6
- This file is the canonical operator manual for CLI users.
6
+ This is the canonical CLI operator manual.
7
+
8
+ Use:
9
+
10
+ - [`skills/QUICKSTART.md`](../../skills/QUICKSTART.md) for the shortest
11
+ verified path
12
+ - [`docs/15-codex-plugin-onboarding.md`](../../docs/15-codex-plugin-onboarding.md)
13
+ for the native Codex plugin/local marketplace path
14
+
15
+ ## One-minute path
16
+
17
+ Use this path unless the task explicitly needs a lower-level command:
18
+
19
+ ```bash
20
+ zk-agent setup
21
+ zk-agent next
22
+ zk-agent wallet create --await-local
23
+ zk-agent next
24
+ zk-agent workflow pay --wallet main --to <address> --amount <amount>
25
+ zk-agent suite
26
+ ```
27
+
28
+ What each step is doing:
29
+
30
+ - `setup` writes local defaults
31
+ - `next` gives the shortest valid follow-up step
32
+ - `wallet create --await-local` is the preferred local approval path
33
+ - `workflow pay` is the flagship zkSync-native AA native-send path
34
+ - `suite` is the packaged surface
35
+
36
+ If readiness is unclear before you choose a fix, use:
37
+
38
+ ```bash
39
+ zk-agent doctor
40
+ ```
7
41
 
8
42
  ## Install
9
43
 
@@ -26,7 +60,10 @@ The package also ships the alias:
26
60
  zksync-agent --help
27
61
  ```
28
62
 
29
- ## Defaults and prerequisites
63
+ The `npx skills add ...` path belongs to the repo skill bundle, not the
64
+ packaged CLI install surface.
65
+
66
+ ## Defaults
30
67
 
31
68
  - Node.js `>=24`
32
69
  - the default chain is `zksync-sepolia`
@@ -46,32 +83,7 @@ ZK_AGENT_TOKEN_DIRECTORY_ROOT=
46
83
  ZK_AGENT_STORAGE_DIR=
47
84
  ```
48
85
 
49
- ## Fastest verified path
50
-
51
- Use this path unless the task explicitly needs a lower-level command:
52
-
53
- ```bash
54
- zk-agent setup
55
- zk-agent next
56
- zk-agent wallet create --await-local
57
- zk-agent next
58
- zk-agent workflow pay --wallet main --to <address> --amount <amount>
59
- ```
60
-
61
- Interpretation:
62
-
63
- - `setup` writes local defaults
64
- - `next` gives the shortest valid follow-up step
65
- - `wallet create --await-local` is the preferred local approval path
66
- - `workflow pay` is the flagship zkSync-native AA native-send path
67
-
68
- If readiness is unclear before you choose a fix, use:
69
-
70
- ```bash
71
- zk-agent doctor
72
- ```
73
-
74
- ## Existing wallet recovery
86
+ ## Repair Paths
75
87
 
76
88
  If the wallet already exists and approval is missing or expired:
77
89
 
@@ -112,6 +124,15 @@ zk-agent wallet reapprove --name main --relay-url <relay-url> --wait-relay --pro
112
124
  zk-agent next
113
125
  ```
114
126
 
127
+ Current supportable product shape on this path:
128
+
129
+ - one externally reachable public origin
130
+ - one relay host with same-host file persistence
131
+ - one same-origin share-link + approval UI surface
132
+
133
+ Do not assume multi-host or load-balanced durability on the current relay
134
+ surface.
135
+
115
136
  If the relay is self-hosted through the built-in server:
116
137
 
117
138
  ```bash
@@ -125,16 +146,9 @@ path.
125
146
  For the supported hosted operating contract, use
126
147
  [`docs/16-hosted-approval-operated-baseline.md`](../../docs/16-hosted-approval-operated-baseline.md).
127
148
 
128
- ## Funding and execution
129
-
130
- Only fund when the CLI tells you funding is required:
131
-
132
- ```bash
133
- zk-agent workflow fund --wallet main
134
- zk-agent workflow fund --wallet main --amount <amount> --execute
135
- ```
149
+ ## After Wallet Ready
136
150
 
137
- Flagship pay path:
151
+ Default flagship write path:
138
152
 
139
153
  ```bash
140
154
  zk-agent workflow pay --wallet main --to <address> --amount <amount>
@@ -144,32 +158,34 @@ zk-agent workflow pay --wallet main --to <address> --amount <amount> --broadcast
144
158
  Keep `sed-lite` as the default AA baseline. Use `daily-spend-limit` only when
145
159
  you intentionally need that narrower policy profile.
146
160
 
147
- ## Operator suite
148
-
149
- Use:
161
+ Default packaged surface:
150
162
 
151
163
  ```bash
152
164
  zk-agent suite
153
165
  ```
154
166
 
155
- when you want the flagship path plus the current post-flagship surfaces in one
156
- place.
167
+ Use `suite` when the wallet is already ready and you want one packaged surface
168
+ for flagship pay, discovery/defaults, funding readiness, and approval-based
169
+ paymaster readiness.
170
+
171
+ Use `--wallet <name>` or `--chain <chain>` when the returned suite commands
172
+ should stay on a non-default wallet or chain.
173
+
174
+ Only fund when the CLI tells you funding is required:
175
+
176
+ ```bash
177
+ zk-agent workflow fund --wallet main
178
+ zk-agent workflow fund --wallet main --amount <amount> --execute
179
+ ```
157
180
 
158
- Current suite shape:
181
+ Do not guess the route. Use the exact funding command suggested by `next`,
182
+ `doctor`, `wallet status`, a blocked workflow, or `suite`.
159
183
 
160
- - flagship pay:
161
- `zk-agent workflow pay --wallet main --to <address> --amount <amount>`
162
- - discovery/defaults:
163
- `zk-agent assets --wallet main`
164
- `zk-agent defaults`
165
- `zk-agent resolve-token --chain zksync-sepolia --symbol USDC`
166
- - funding readiness:
167
- `zk-agent workflow fund --wallet main`
168
- - paymaster readiness:
169
- `zk-agent workflow pay --wallet main --to <address> --amount <amount> --paymaster-mode approval-based`
170
- `zk-agent tokens --chain zksync-sepolia --role paymaster-fee-token`
184
+ ## Direct Paths
171
185
 
172
- ## Discovery and direct commands
186
+ Prefer `suite` first when you want the packaged discovery/defaults/funding/
187
+ paymaster surface. Use the commands below only when you intentionally want a
188
+ narrower path.
173
189
 
174
190
  Preferred discovery order:
175
191
 
@@ -178,8 +194,7 @@ Preferred discovery order:
178
194
  - `zk-agent defaults`
179
195
  - `zk-agent resolve-token --chain zksync-sepolia --symbol <symbol>`
180
196
 
181
- Use the direct commands when you intentionally want to bypass the workflow
182
- layer:
197
+ Bypass examples:
183
198
 
184
199
  - `zk-agent send-token --wallet main --symbol USDC --to <address> --amount <amount>`
185
200
  - `zk-agent swap --wallet main --token-in-symbol USDC --token-out-symbol ETH --amount-in <amount>`
@@ -187,24 +202,9 @@ layer:
187
202
  - `zk-agent deposit --wallet main --symbol USDC --amount <amount>`
188
203
  - `zk-agent withdraw --wallet main --symbol USDC --amount <amount>`
189
204
 
190
- ## Local storage
191
-
192
- By default the CLI stores local state under:
193
-
194
- ```text
195
- ~/.zk-agent/
196
- ```
197
-
198
- Common files:
199
-
200
- - `config.json`
201
- - `wallets/*.json`
202
- - `requests/*.json`
203
- - `workflows/*.json`
204
-
205
- ## Smart-account profiles
205
+ ## Smart-account Profiles
206
206
 
207
- The packaged CLI includes built-in profile artifacts for:
207
+ Built-in profiles:
208
208
 
209
209
  - `sed-lite`
210
210
  - `daily-spend-limit`
@@ -224,32 +224,38 @@ zk-agent wallet smart-account deploy --profile sed-lite
224
224
 
225
225
  ## Common failures
226
226
 
227
- Connector callback never arrives:
227
+ - connector callback never arrives:
228
+ verify the connector URL saved by `zk-agent setup`; if local callback is not
229
+ viable in the current environment, switch to the relay-backed path
230
+ - wallet is missing a writable session:
231
+ run `zk-agent doctor --wallet <wallet>`, then inspect
232
+ `zk-agent wallet status --name <wallet>`; reapprove when approval is missing,
233
+ attach the signer when approval is still present
234
+ - workflow stops on funding:
235
+ do not guess the route; run the exact `workflow fund` command suggested by
236
+ the CLI
237
+ - locked-down environment blocks local callback or relay binding:
238
+ rerun from a normal host shell or use the relay/manual approval path that
239
+ matches the environment
228
240
 
229
- - verify the connector URL saved by `zk-agent setup`
230
- - if local callback is impossible in the current environment, switch to the
231
- relay-backed path
241
+ ## Reference
232
242
 
233
- CLI says the wallet is missing a writable session:
243
+ Local storage:
234
244
 
235
- - run `zk-agent doctor --wallet <wallet>`
236
- - inspect `zk-agent wallet status --name <wallet>`
237
- - reapprove when approval is missing
238
- - attach the signer when approval is present but local write readiness is not
239
-
240
- Workflow stops on funding:
241
-
242
- - do not guess the route
243
- - run the exact `workflow fund` command suggested by the CLI
245
+ By default the CLI stores local state under:
244
246
 
245
- Locked-down environment blocks local callback or relay binding:
247
+ ```text
248
+ ~/.zk-agent/
249
+ ```
246
250
 
247
- - rerun from a normal host shell
248
- - or use a relay/manual approval path that matches the environment
251
+ Common files:
249
252
 
250
- ## Command help
253
+ - `config.json`
254
+ - `wallets/*.json`
255
+ - `requests/*.json`
256
+ - `workflows/*.json`
251
257
 
252
- Use:
258
+ Help surfaces:
253
259
 
254
260
  ```bash
255
261
  zk-agent --help
package/dist/index.js CHANGED
@@ -7654,7 +7654,10 @@ function isTTY() {
7654
7654
  return Boolean(process.stdout.isTTY);
7655
7655
  }
7656
7656
  function shouldJsonOutput() {
7657
- return !isTTY() || process.env.ZK_AGENT_OUTPUT === "json";
7657
+ const requestedOutput = process.env.ZK_AGENT_OUTPUT?.trim().toLowerCase();
7658
+ if (requestedOutput === "text") return false;
7659
+ if (requestedOutput === "json") return true;
7660
+ return !isTTY();
7658
7661
  }
7659
7662
  function jsonOut(value) {
7660
7663
  console.log(JSON.stringify(value, null, 2));
@@ -7820,6 +7823,16 @@ function appendPaymasterMode(command, paymasterMode) {
7820
7823
  function buildDefaultsRecommendedCommand() {
7821
7824
  return "zk-agent defaults";
7822
7825
  }
7826
+ function buildSuiteRecommendedCommand(walletName = "main", chain = "zksync-sepolia") {
7827
+ const flags = [];
7828
+ if (walletName !== "main") {
7829
+ flags.push(`--wallet ${walletName}`);
7830
+ }
7831
+ if (chain !== "zksync-sepolia") {
7832
+ flags.push(`--chain ${chain}`);
7833
+ }
7834
+ return flags.length > 0 ? `zk-agent suite ${flags.join(" ")}` : "zk-agent suite";
7835
+ }
7823
7836
  function buildTopLevelNextRecommendedCommand(requestId, paymasterMode) {
7824
7837
  const command = requestId ? `zk-agent next --request-id ${requestId}` : "zk-agent next";
7825
7838
  return appendPaymasterMode(command, paymasterMode);
@@ -10685,6 +10698,54 @@ function agentProfileLines(summary) {
10685
10698
  return lines;
10686
10699
  }
10687
10700
 
10701
+ // src/lib/suite-handoff.ts
10702
+ function buildSuiteHandoffSummary(input) {
10703
+ const command = buildSuiteRecommendedCommand(input.walletName, input.chain);
10704
+ const useWhen = "Use suite once wallet approval and local signer readiness are no longer the blocker and you want one packaged surface for flagship pay plus the current post-flagship discovery, paymaster, and funding slices.";
10705
+ switch (input.currentSurface) {
10706
+ case "next":
10707
+ return {
10708
+ currentSurface: input.currentSurface,
10709
+ recommendedNow: input.recommendedNow,
10710
+ command,
10711
+ useWhen,
10712
+ stayOnCurrentSurfaceWhen: "Stay on next when you still need the CLI to choose across setup, wallet readiness, and the shortest flagship workflow entry.",
10713
+ note: input.recommendedNow ? "Wallet readiness is no longer the blocker. The default shortest action can still be workflow pay, while suite is the broader packaged follow-up surface." : "Suite is not the current recommendation because next is still steering setup or wallet remediation."
10714
+ };
10715
+ case "wallet":
10716
+ return {
10717
+ currentSurface: input.currentSurface,
10718
+ recommendedNow: input.recommendedNow,
10719
+ command,
10720
+ useWhen,
10721
+ stayOnCurrentSurfaceWhen: "Stay on wallet status or wallet next when approval, signer attach, deployment sync, or wallet-specific remediation is still the blocker.",
10722
+ note: input.recommendedNow ? "Wallet readiness is no longer the blocker, so suite is available as the broader packaged surface." : "Suite is not the current recommendation because wallet-specific remediation is still the blocker."
10723
+ };
10724
+ case "workflow":
10725
+ return {
10726
+ currentSurface: input.currentSurface,
10727
+ recommendedNow: input.recommendedNow,
10728
+ command,
10729
+ useWhen,
10730
+ stayOnCurrentSurfaceWhen: "Stay on workflow when you already have an explicit workflow question, checkpoint, or execution state to inspect, continue, or resume.",
10731
+ note: "This workflow surface stays authoritative for the current workflow. Switch to suite only after the question is no longer workflow-specific."
10732
+ };
10733
+ default: {
10734
+ const exhaustive = input.currentSurface;
10735
+ throw new Error(`Unsupported suite handoff surface: ${String(exhaustive)}`);
10736
+ }
10737
+ }
10738
+ }
10739
+ function suiteHandoffLines(summary) {
10740
+ return [
10741
+ ["suite", summary.command],
10742
+ ["suite ready", summary.recommendedNow ? "yes" : "no"],
10743
+ ["suite when", summary.useWhen],
10744
+ [`stay on ${summary.currentSurface} when`, summary.stayOnCurrentSurfaceWhen],
10745
+ ["suite note", summary.note]
10746
+ ];
10747
+ }
10748
+
10688
10749
  // src/lib/wallet-next.ts
10689
10750
  function buildWalletNextRecommendedCommands(walletName, summary, paymasterMode) {
10690
10751
  return {
@@ -10696,6 +10757,7 @@ function buildWalletNextRecommendedCommands(walletName, summary, paymasterMode)
10696
10757
  } : {},
10697
10758
  discoverTokens: buildTokensRecommendedCommand(summary.chain),
10698
10759
  inspectToken: buildResolveTokenRecommendedCommand(summary.chain),
10760
+ suite: buildSuiteRecommendedCommand(walletName, summary.chain),
10699
10761
  walletStatus: buildWalletStatusRecommendedCommand(walletName),
10700
10762
  ...summary.recommendedCommand ? { nextAction: summary.recommendedCommand } : {}
10701
10763
  };
@@ -10777,6 +10839,7 @@ function buildTopLevelWorkflowRecommendedCommands(input) {
10777
10839
  resume: buildWorkflowResumeRecommendedCommand(input.requestId),
10778
10840
  delete: buildWorkflowDeleteRecommendedCommand(input.requestId),
10779
10841
  walletStatus: buildWalletStatusRecommendedCommand(input.walletName),
10842
+ suite: buildSuiteRecommendedCommand(input.walletName, input.chain),
10780
10843
  ...input.nextAction ? { nextAction: input.nextAction } : {},
10781
10844
  ...workflowIntentSupportsTokenDiscovery2(input.intent) ? {
10782
10845
  discoverAssets: buildAssetsRecommendedCommand(input.walletName),
@@ -10857,6 +10920,9 @@ function buildNextHelpText() {
10857
10920
  " Stay on the wallet layer only when you need wallet-specific remediation:",
10858
10921
  " zk-agent wallet next --name main",
10859
10922
  "",
10923
+ " When the wallet is already ready and you want the packaged surface:",
10924
+ " zk-agent suite",
10925
+ "",
10860
10926
  " Switch to the hosted remote-approval path only when the browser is not colocated:",
10861
10927
  " zk-agent relay inspect --relay-url <url>",
10862
10928
  " zk-agent wallet create|reapprove --relay-url <url> --wait-relay --prompt-code",
@@ -10922,6 +10988,12 @@ function createNextCommand(deps) {
10922
10988
  paymasterMode: extractCheckpointPaymasterMode(updatedCheckpoint),
10923
10989
  recommendedCommands: recommendedCommands2
10924
10990
  });
10991
+ const suiteHandoffSummary2 = buildSuiteHandoffSummary({
10992
+ currentSurface: "workflow",
10993
+ recommendedNow: false,
10994
+ walletName: wallet2.walletName,
10995
+ chain: result.plan.chain
10996
+ });
10925
10997
  const workflowAgentProfile = await loadAgentIdentitySummary(wallet2.walletName);
10926
10998
  const agentFollowup2 = buildAgentFollowup(workflowAgentProfile, {
10927
10999
  walletName: wallet2.walletName,
@@ -10937,6 +11009,7 @@ function createNextCommand(deps) {
10937
11009
  ...agentProfileLines(workflowAgentProfile),
10938
11010
  ...agentFollowupLines(agentFollowup2),
10939
11011
  ...nextCommand2 ? [["next", nextCommand2]] : [],
11012
+ ...suiteHandoffLines(suiteHandoffSummary2),
10940
11013
  ["inspect defaults", recommendedCommands2.inspectDefaults],
10941
11014
  ...result.blockingActionIds.map((actionId) => ["blocking action", actionId]),
10942
11015
  ...result.fundingProgress ? [
@@ -10958,6 +11031,7 @@ function createNextCommand(deps) {
10958
11031
  result,
10959
11032
  checkpoint: updatedCheckpoint,
10960
11033
  tokenDiscoverySummary: tokenDiscoverySummary2,
11034
+ suiteHandoffSummary: suiteHandoffSummary2,
10961
11035
  recommendedCommands: recommendedCommands2
10962
11036
  }
10963
11037
  );
@@ -11124,6 +11198,7 @@ function createNextCommand(deps) {
11124
11198
  const recommendedCommands = {
11125
11199
  walletNext: buildWalletNextRecommendedCommand(wallet.walletName),
11126
11200
  walletStatus: buildWalletStatusRecommendedCommand(wallet.walletName),
11201
+ suite: buildSuiteRecommendedCommand(wallet.walletName, wallet.chain),
11127
11202
  discoverAssets: buildAssetsRecommendedCommand(wallet.walletName),
11128
11203
  discoverOwnedTokens: buildOwnedTokensRecommendedCommand(wallet.walletName),
11129
11204
  ...paymasterMode === "approval-based" ? {
@@ -11163,6 +11238,12 @@ function createNextCommand(deps) {
11163
11238
  paymasterMode,
11164
11239
  recommendedCommands: mergedRecommendedCommands
11165
11240
  });
11241
+ const suiteHandoffSummary = buildSuiteHandoffSummary({
11242
+ currentSurface: "next",
11243
+ recommendedNow: summary.status === "ready",
11244
+ walletName: wallet.walletName,
11245
+ chain: wallet.chain
11246
+ });
11166
11247
  printResult(
11167
11248
  topLevelNextLines("wallet", [
11168
11249
  ...walletNextLines(summary),
@@ -11174,6 +11255,7 @@ function createNextCommand(deps) {
11174
11255
  ...mergedRecommendedCommands.attachSigner ? [["attach signer", mergedRecommendedCommands.attachSigner]] : [],
11175
11256
  ...mergedRecommendedCommands.relayInspect ? [["relay inspect", mergedRecommendedCommands.relayInspect]] : [],
11176
11257
  ...mergedRecommendedCommands.reapproveRemote ? [["remote fallback", mergedRecommendedCommands.reapproveRemote]] : [],
11258
+ ...suiteHandoffLines(suiteHandoffSummary),
11177
11259
  ["discover assets", mergedRecommendedCommands.discoverAssets],
11178
11260
  ["discover owned tokens", mergedRecommendedCommands.discoverOwnedTokens],
11179
11261
  ...mergedRecommendedCommands.discoverPaymasterTokens ? [["discover paymaster tokens", mergedRecommendedCommands.discoverPaymasterTokens]] : [],
@@ -11194,6 +11276,7 @@ function createNextCommand(deps) {
11194
11276
  summary,
11195
11277
  nextCommand,
11196
11278
  tokenDiscoverySummary,
11279
+ suiteHandoffSummary,
11197
11280
  recommendedCommands: mergedRecommendedCommands
11198
11281
  }
11199
11282
  );
@@ -12722,12 +12805,9 @@ function buildOperatorSuitePayload(options = {}) {
12722
12805
  id: "flagship-pay",
12723
12806
  title: "Flagship Pay",
12724
12807
  goal: "Run the default zkSync-native native-send path through the workflow layer.",
12808
+ useWhen: "Start here when the wallet is already ready and the next real goal is a native send.",
12725
12809
  primaryCommand: flagshipCommand,
12726
- supportingCommands: [
12727
- "zk-agent next",
12728
- "zk-agent wallet status --name main",
12729
- inspectDefaults
12730
- ],
12810
+ supportingCommands: ["zk-agent next", buildWalletStatusRecommendedCommand(walletName), inspectDefaults],
12731
12811
  skillPath: "skills/zk-aa/SKILL.md"
12732
12812
  };
12733
12813
  const slices = [
@@ -12735,6 +12815,7 @@ function buildOperatorSuitePayload(options = {}) {
12735
12815
  id: "discovery-defaults",
12736
12816
  title: "Discovery / Defaults",
12737
12817
  goal: "Discover owned assets, tracked defaults, and symbol-first token resolution before acting.",
12818
+ useWhen: "Use this before tokenized actions or whenever asset/default context is unclear.",
12738
12819
  primaryCommand: discoveryCommand,
12739
12820
  supportingCommands: [
12740
12821
  inspectDefaults,
@@ -12748,6 +12829,7 @@ function buildOperatorSuitePayload(options = {}) {
12748
12829
  id: "paymaster-readiness",
12749
12830
  title: "Paymaster Readiness",
12750
12831
  goal: "Stay on the approval-based flagship path and recover the exact fee-token/default metadata when needed.",
12832
+ useWhen: "Use this when approval-based pay or another sponsored write needs fee-token/default recovery.",
12751
12833
  primaryCommand: paymasterCommand,
12752
12834
  supportingCommands: [
12753
12835
  inspectDefaults,
@@ -12761,6 +12843,7 @@ function buildOperatorSuitePayload(options = {}) {
12761
12843
  id: "funding-readiness",
12762
12844
  title: "Funding Readiness",
12763
12845
  goal: "Ask the workflow layer for the exact funding route before executing bridge/deposit follow-up.",
12846
+ useWhen: "Use this when the workflow path is blocked on gas or the CLI says funding is required.",
12764
12847
  primaryCommand: fundingCommand,
12765
12848
  supportingCommands: [
12766
12849
  buildWorkflowFundRunRecommendedCommand(walletName),
@@ -12777,14 +12860,17 @@ function buildOperatorSuitePayload(options = {}) {
12777
12860
  suiteId: "zk-agent-operator-suite",
12778
12861
  walletName,
12779
12862
  chain,
12863
+ stage: "wallet-ready-post-flagship",
12864
+ useWhen: "Use suite after wallet readiness when you want one packaged surface for flagship pay plus the current post-flagship discovery, paymaster, and funding slices.",
12780
12865
  flagshipId: flagship.id,
12781
12866
  postFlagshipSliceIds: slices.map((entry) => entry.id),
12867
+ recommendedOrder: [flagship.id, ...slices.map((entry) => entry.id)],
12782
12868
  nextAction: flagship.primaryCommand
12783
12869
  },
12784
12870
  flagship,
12785
12871
  slices,
12786
12872
  recommendedCommands: {
12787
- suite: "zk-agent suite",
12873
+ suite: buildSuiteRecommendedCommand(walletName, chain),
12788
12874
  flagship: flagshipCommand,
12789
12875
  discovery: discoveryCommand,
12790
12876
  paymaster: paymasterCommand,
@@ -12795,15 +12881,21 @@ function buildOperatorSuitePayload(options = {}) {
12795
12881
  }
12796
12882
  function operatorSuiteLines(payload) {
12797
12883
  const sliceLines = payload.slices.flatMap((entry) => [
12798
- [entry.id, formatRecommendedPath([entry.primaryCommand, ...entry.supportingCommands])],
12799
- [`${entry.id} skill`, entry.skillPath],
12800
- ...entry.smokeCommand ? [[`${entry.id} smoke`, entry.smokeCommand]] : []
12884
+ [entry.title.toLowerCase(), formatRecommendedPath([entry.primaryCommand, ...entry.supportingCommands])],
12885
+ [`${entry.title.toLowerCase()} when`, entry.useWhen],
12886
+ [`${entry.title.toLowerCase()} skill`, entry.skillPath],
12887
+ ...entry.smokeCommand ? [[`${entry.title.toLowerCase()} smoke`, entry.smokeCommand]] : []
12801
12888
  ]);
12802
12889
  return [
12803
12890
  ["suite", payload.summary.suiteId],
12804
12891
  ["wallet", payload.summary.walletName],
12805
12892
  ["chain", payload.summary.chain],
12806
- ["flagship", formatRecommendedPath([payload.flagship.primaryCommand, "zk-agent next"])],
12893
+ ["stage", payload.summary.stage],
12894
+ ["use when", payload.summary.useWhen],
12895
+ ["recommended order", payload.summary.recommendedOrder.join(" -> ")],
12896
+ [payload.flagship.title.toLowerCase(), formatRecommendedPath([payload.flagship.primaryCommand, "zk-agent next"])],
12897
+ [`${payload.flagship.title.toLowerCase()} when`, payload.flagship.useWhen],
12898
+ [`${payload.flagship.title.toLowerCase()} skill`, payload.flagship.skillPath],
12807
12899
  ...sliceLines,
12808
12900
  ["next action", payload.summary.nextAction]
12809
12901
  ];
@@ -12815,14 +12907,19 @@ function createSuiteCommand() {
12815
12907
  "after",
12816
12908
  [
12817
12909
  "",
12818
- " Current operator suite:",
12910
+ " Use `suite` after wallet readiness when you want one packaged surface",
12911
+ " for flagship pay plus the current post-flagship slices.",
12912
+ "",
12913
+ " Recommended order inside the suite:",
12819
12914
  " zk-agent workflow pay --wallet main --to <address> --amount <amount>",
12820
12915
  " zk-agent assets --wallet main",
12821
- " zk-agent workflow fund --wallet main",
12822
12916
  " zk-agent workflow pay --wallet main --to <address> --amount <amount> --paymaster-mode approval-based",
12917
+ " zk-agent workflow fund --wallet main",
12918
+ "",
12919
+ " Pass `--wallet` or `--chain` to retarget the entire suite contract.",
12823
12920
  "",
12824
- " Use `suite` when you want the flagship path plus the current",
12825
- " post-flagship discovery/defaults, funding, and paymaster surfaces in one place."
12921
+ " In JSON mode, `summary.useWhen`, `summary.recommendedOrder`, and each",
12922
+ " entry `useWhen` field explain when to stay on one slice instead of guessing."
12826
12923
  ].join("\n")
12827
12924
  ).action((options) => {
12828
12925
  const payload = buildOperatorSuitePayload({
@@ -14034,7 +14131,9 @@ function buildRelayInspectPayload(relayUrl, rawHealth) {
14034
14131
  };
14035
14132
  }
14036
14133
  function createRelayCommand() {
14037
- const relay = new Command10("relay").description("Run the local connector relay prototype server");
14134
+ const relay = new Command10("relay").description(
14135
+ "Serve and inspect the single-host connector relay baseline for hosted approval"
14136
+ );
14038
14137
  relay.addHelpText(
14039
14138
  "after",
14040
14139
  [
@@ -14045,6 +14144,12 @@ function createRelayCommand() {
14045
14144
  " zk-agent wallet create --relay-url <url> --wait-relay --prompt-code",
14046
14145
  " zk-agent wallet reapprove --name main --relay-url <url> --wait-relay --prompt-code",
14047
14146
  "",
14147
+ " Supported product claim today:",
14148
+ " one externally reachable public origin",
14149
+ " one relay host with same-host file persistence",
14150
+ " one same-origin share-link + approval UI surface",
14151
+ " Do not assume multi-host or load-balanced durability.",
14152
+ "",
14048
14153
  " Keep `wallet create|reapprove --await-local` as the default baseline when",
14049
14154
  " the browser and terminal are colocated.",
14050
14155
  "",
@@ -17006,6 +17111,9 @@ function createWalletCommand(deps) {
17006
17111
  " zk-agent wallet status --name main",
17007
17112
  " zk-agent wallet next --name main",
17008
17113
  "",
17114
+ " When wallet readiness is no longer the blocker and you want the packaged surface:",
17115
+ " zk-agent suite",
17116
+ "",
17009
17117
  " Hosted remote approval path:",
17010
17118
  " zk-agent relay inspect --relay-url <url>",
17011
17119
  " zk-agent wallet create --relay-url <url> --wait-relay --prompt-code",
@@ -17601,9 +17709,16 @@ function createWalletCommand(deps) {
17601
17709
  paymasterMode: resolveEffectivePaymasterSelection(walletRecord)?.mode,
17602
17710
  recommendedCommands
17603
17711
  });
17712
+ const suiteHandoffSummary = buildSuiteHandoffSummary({
17713
+ currentSurface: "wallet",
17714
+ recommendedNow: summary.status === "ready",
17715
+ walletName: walletRecord.walletName,
17716
+ chain: summary.chain
17717
+ });
17604
17718
  printResult(
17605
17719
  [
17606
17720
  ...walletStatusLines(inspection, summary),
17721
+ ...suiteHandoffLines(suiteHandoffSummary),
17607
17722
  ["discover assets", recommendedCommands.discoverAssets],
17608
17723
  ["discover owned tokens", recommendedCommands.discoverOwnedTokens],
17609
17724
  ...recommendedCommands.discoverPaymasterTokens ? [["discover paymaster tokens", recommendedCommands.discoverPaymasterTokens]] : [],
@@ -17617,6 +17732,7 @@ function createWalletCommand(deps) {
17617
17732
  inspection,
17618
17733
  summary,
17619
17734
  tokenDiscoverySummary,
17735
+ suiteHandoffSummary,
17620
17736
  recommendedCommands
17621
17737
  }
17622
17738
  );
@@ -17636,9 +17752,16 @@ function createWalletCommand(deps) {
17636
17752
  paymasterMode: resolveEffectivePaymasterSelection(walletRecord)?.mode,
17637
17753
  recommendedCommands
17638
17754
  });
17755
+ const suiteHandoffSummary = buildSuiteHandoffSummary({
17756
+ currentSurface: "wallet",
17757
+ recommendedNow: summary.status === "ready",
17758
+ walletName: walletRecord.walletName,
17759
+ chain: summary.chain
17760
+ });
17639
17761
  printResult(
17640
17762
  [
17641
17763
  ...walletNextLines(summary),
17764
+ ...suiteHandoffLines(suiteHandoffSummary),
17642
17765
  ["discover assets", recommendedCommands.discoverAssets],
17643
17766
  ["discover owned tokens", recommendedCommands.discoverOwnedTokens],
17644
17767
  ...recommendedCommands.discoverPaymasterTokens ? [["discover paymaster tokens", recommendedCommands.discoverPaymasterTokens]] : [],
@@ -17652,6 +17775,7 @@ function createWalletCommand(deps) {
17652
17775
  inspection,
17653
17776
  summary,
17654
17777
  tokenDiscoverySummary,
17778
+ suiteHandoffSummary,
17655
17779
  recommendedCommands
17656
17780
  }
17657
17781
  );
@@ -20338,6 +20462,10 @@ async function printWorkflowRunCommandResult(execution, command) {
20338
20462
  result: execution.result,
20339
20463
  nextCommand: execution.result.nextCommand
20340
20464
  });
20465
+ const suiteHandoffSummary2 = buildWorkflowSuiteHandoff({
20466
+ walletName: execution.result.walletName,
20467
+ chain: execution.result.plan.chain
20468
+ });
20341
20469
  const workflowEntrySummary2 = buildWorkflowEntrySummary({
20342
20470
  command,
20343
20471
  source: execution.requestId ? "checkpoint" : "input",
@@ -20355,6 +20483,7 @@ async function printWorkflowRunCommandResult(execution, command) {
20355
20483
  [
20356
20484
  ...workflowRunLines(execution.result),
20357
20485
  ...workflowWalletApprovalLines(execution.walletApproval),
20486
+ ...suiteHandoffLines(suiteHandoffSummary2),
20358
20487
  ...workflowFollowupLines(recommendedCommands2)
20359
20488
  ],
20360
20489
  agentProfile2,
@@ -20371,6 +20500,7 @@ async function printWorkflowRunCommandResult(execution, command) {
20371
20500
  result: execution.result,
20372
20501
  ...serializeWorkflowWalletApprovalOutput(execution.walletApproval),
20373
20502
  tokenDiscoverySummary: tokenDiscoverySummary2,
20503
+ suiteHandoffSummary: suiteHandoffSummary2,
20374
20504
  recommendedCommands: recommendedCommands2
20375
20505
  }
20376
20506
  );
@@ -20405,6 +20535,10 @@ async function printWorkflowRunCommandResult(execution, command) {
20405
20535
  status,
20406
20536
  nextCommand: status.recommendedCommand
20407
20537
  });
20538
+ const suiteHandoffSummary = buildWorkflowSuiteHandoff({
20539
+ walletName: status.walletName,
20540
+ chain: status.plan.chain
20541
+ });
20408
20542
  const workflowEntrySummary = buildWorkflowEntrySummary({
20409
20543
  command,
20410
20544
  source: execution.requestId ? "checkpoint" : "input",
@@ -20421,6 +20555,7 @@ async function printWorkflowRunCommandResult(execution, command) {
20421
20555
  [
20422
20556
  ...workflowStatusLines(status),
20423
20557
  ...workflowWalletApprovalLines(execution.walletApproval),
20558
+ ...suiteHandoffLines(suiteHandoffSummary),
20424
20559
  ...workflowFollowupLines(recommendedCommands)
20425
20560
  ],
20426
20561
  agentProfile,
@@ -20438,6 +20573,7 @@ async function printWorkflowRunCommandResult(execution, command) {
20438
20573
  checkpoint: execution.checkpoint,
20439
20574
  ...serializeWorkflowWalletApprovalOutput(execution.walletApproval),
20440
20575
  tokenDiscoverySummary,
20576
+ suiteHandoffSummary,
20441
20577
  recommendedCommands
20442
20578
  }
20443
20579
  );
@@ -20718,6 +20854,10 @@ async function printWorkflowAutoCommandResult(execution, command) {
20718
20854
  result: execution.result,
20719
20855
  nextCommand: nextAction
20720
20856
  });
20857
+ const suiteHandoffSummary = buildWorkflowSuiteHandoff({
20858
+ walletName: execution.status.walletName,
20859
+ chain: execution.status.plan.chain
20860
+ });
20721
20861
  const workflowEntrySummary = buildWorkflowEntrySummary({
20722
20862
  command,
20723
20863
  source: execution.source,
@@ -20742,6 +20882,7 @@ async function printWorkflowAutoCommandResult(execution, command) {
20742
20882
  ...summaryLines,
20743
20883
  ...detailLines,
20744
20884
  ...workflowWalletApprovalLines(execution.walletApproval),
20885
+ ...suiteHandoffLines(suiteHandoffSummary),
20745
20886
  ...workflowFollowupLines(recommendedCommands)
20746
20887
  ],
20747
20888
  agentProfile,
@@ -20763,6 +20904,7 @@ async function printWorkflowAutoCommandResult(execution, command) {
20763
20904
  checkpoint: execution.checkpoint,
20764
20905
  ...serializeWorkflowWalletApprovalOutput(execution.walletApproval),
20765
20906
  tokenDiscoverySummary,
20907
+ suiteHandoffSummary,
20766
20908
  recommendedCommands
20767
20909
  }
20768
20910
  );
@@ -20800,6 +20942,14 @@ function extractPaymasterModeFromCommand(command) {
20800
20942
  const match = command.match(/--paymaster-mode (none|sponsored|approval-based)\b/);
20801
20943
  return match?.[1];
20802
20944
  }
20945
+ function buildWorkflowSuiteHandoff(input) {
20946
+ return buildSuiteHandoffSummary({
20947
+ currentSurface: "workflow",
20948
+ recommendedNow: false,
20949
+ walletName: input.walletName,
20950
+ chain: input.chain
20951
+ });
20952
+ }
20803
20953
  function buildWorkflowRuntimeRecommendedCommands(input) {
20804
20954
  const paymasterMode = extractPaymasterModeFromCommand(input.nextAction) ?? input.paymasterMode;
20805
20955
  return {
@@ -21300,6 +21450,9 @@ function buildWorkflowHelpText() {
21300
21450
  " zk-agent workflow next --request-id <id>",
21301
21451
  " zk-agent workflow resume --request-id <id> [--broadcast]",
21302
21452
  "",
21453
+ " When the explicit workflow is no longer the real question and you want the broader packaged surface:",
21454
+ " zk-agent suite",
21455
+ "",
21303
21456
  " Funding-only step:",
21304
21457
  " zk-agent workflow fund --wallet main --amount <amount> --execute",
21305
21458
  "",
@@ -21636,6 +21789,10 @@ function createWorkflowCommand(deps) {
21636
21789
  status: inspection.result,
21637
21790
  nextCommand: inspection.result.recommendedCommand
21638
21791
  });
21792
+ const suiteHandoffSummary = buildWorkflowSuiteHandoff({
21793
+ walletName: inspection.result.walletName,
21794
+ chain: inspection.result.plan.chain
21795
+ });
21639
21796
  const workflowEntrySummary = buildWorkflowEntrySummary({
21640
21797
  command: "status",
21641
21798
  source: options.requestId?.trim() ? "checkpoint" : "input",
@@ -21652,6 +21809,7 @@ function createWorkflowCommand(deps) {
21652
21809
  [
21653
21810
  ...workflowStatusLines(inspection.result),
21654
21811
  ...workflowWalletApprovalLines(inspection.walletApproval),
21812
+ ...suiteHandoffLines(suiteHandoffSummary),
21655
21813
  ...workflowFollowupLines(recommendedCommands)
21656
21814
  ],
21657
21815
  agentProfile,
@@ -21669,6 +21827,7 @@ function createWorkflowCommand(deps) {
21669
21827
  checkpoint: inspection.checkpoint,
21670
21828
  ...serializeWorkflowWalletApprovalOutput(inspection.walletApproval),
21671
21829
  tokenDiscoverySummary,
21830
+ suiteHandoffSummary,
21672
21831
  recommendedCommands
21673
21832
  }
21674
21833
  );
@@ -21708,6 +21867,10 @@ function createWorkflowCommand(deps) {
21708
21867
  status: inspection.result,
21709
21868
  nextCommand
21710
21869
  });
21870
+ const suiteHandoffSummary = buildWorkflowSuiteHandoff({
21871
+ walletName: inspection.result.walletName,
21872
+ chain: inspection.result.plan.chain
21873
+ });
21711
21874
  const workflowEntrySummary = buildWorkflowEntrySummary({
21712
21875
  command: "next",
21713
21876
  source: options.requestId?.trim() ? "checkpoint" : "input",
@@ -21724,6 +21887,7 @@ function createWorkflowCommand(deps) {
21724
21887
  [
21725
21888
  ...workflowNextLines(inspection.result),
21726
21889
  ...workflowWalletApprovalLines(inspection.walletApproval),
21890
+ ...suiteHandoffLines(suiteHandoffSummary),
21727
21891
  ...workflowFollowupLines(recommendedCommands)
21728
21892
  ],
21729
21893
  agentProfile,
@@ -21741,6 +21905,7 @@ function createWorkflowCommand(deps) {
21741
21905
  checkpoint: inspection.checkpoint,
21742
21906
  ...serializeWorkflowWalletApprovalOutput(inspection.walletApproval),
21743
21907
  tokenDiscoverySummary,
21908
+ suiteHandoffSummary,
21744
21909
  recommendedCommands
21745
21910
  }
21746
21911
  );
@@ -21781,6 +21946,10 @@ function createWorkflowCommand(deps) {
21781
21946
  status: inspection.result,
21782
21947
  nextCommand: inspection.result.recommendedCommand
21783
21948
  });
21949
+ const suiteHandoffSummary2 = buildWorkflowSuiteHandoff({
21950
+ walletName: inspection.result.walletName,
21951
+ chain: inspection.result.plan.chain
21952
+ });
21784
21953
  const workflowEntrySummary2 = buildWorkflowEntrySummary({
21785
21954
  command: "resume",
21786
21955
  source: options.requestId?.trim() ? "checkpoint" : "input",
@@ -21797,6 +21966,7 @@ function createWorkflowCommand(deps) {
21797
21966
  [
21798
21967
  ...workflowStatusLines(inspection.result),
21799
21968
  ...workflowWalletApprovalLines(inspection.walletApproval),
21969
+ ...suiteHandoffLines(suiteHandoffSummary2),
21800
21970
  ...workflowFollowupLines(recommendedCommands2)
21801
21971
  ],
21802
21972
  agentProfile2,
@@ -21814,6 +21984,7 @@ function createWorkflowCommand(deps) {
21814
21984
  checkpoint: inspection.checkpoint,
21815
21985
  ...serializeWorkflowWalletApprovalOutput(inspection.walletApproval),
21816
21986
  tokenDiscoverySummary: tokenDiscoverySummary2,
21987
+ suiteHandoffSummary: suiteHandoffSummary2,
21817
21988
  recommendedCommands: recommendedCommands2
21818
21989
  }
21819
21990
  );
@@ -21857,6 +22028,10 @@ function createWorkflowCommand(deps) {
21857
22028
  status: status2,
21858
22029
  nextCommand: status2.recommendedCommand
21859
22030
  });
22031
+ const suiteHandoffSummary2 = buildWorkflowSuiteHandoff({
22032
+ walletName: status2.walletName,
22033
+ chain: status2.plan.chain
22034
+ });
21860
22035
  const workflowEntrySummary2 = buildWorkflowEntrySummary({
21861
22036
  command: "resume",
21862
22037
  source: options.requestId?.trim() ? "checkpoint" : "input",
@@ -21873,6 +22048,7 @@ function createWorkflowCommand(deps) {
21873
22048
  [
21874
22049
  ...workflowStatusLines(status2),
21875
22050
  ...workflowWalletApprovalLines(execution.walletApproval),
22051
+ ...suiteHandoffLines(suiteHandoffSummary2),
21876
22052
  ...workflowFollowupLines(recommendedCommands2)
21877
22053
  ],
21878
22054
  agentProfile2,
@@ -21890,6 +22066,7 @@ function createWorkflowCommand(deps) {
21890
22066
  checkpoint: execution.checkpoint,
21891
22067
  ...serializeWorkflowWalletApprovalOutput(execution.walletApproval),
21892
22068
  tokenDiscoverySummary: tokenDiscoverySummary2,
22069
+ suiteHandoffSummary: suiteHandoffSummary2,
21893
22070
  recommendedCommands: recommendedCommands2
21894
22071
  }
21895
22072
  );
@@ -21921,6 +22098,10 @@ function createWorkflowCommand(deps) {
21921
22098
  result: execution.result,
21922
22099
  nextCommand: execution.result.nextCommand ?? inspection.result.recommendedCommand
21923
22100
  });
22101
+ const suiteHandoffSummary = buildWorkflowSuiteHandoff({
22102
+ walletName: execution.result.walletName,
22103
+ chain: execution.result.plan.chain
22104
+ });
21924
22105
  const workflowEntrySummary = buildWorkflowEntrySummary({
21925
22106
  command: "resume",
21926
22107
  source: options.requestId?.trim() ? "checkpoint" : "input",
@@ -21938,6 +22119,7 @@ function createWorkflowCommand(deps) {
21938
22119
  [
21939
22120
  ...workflowRunLines(execution.result),
21940
22121
  ...workflowWalletApprovalLines(inspection.walletApproval),
22122
+ ...suiteHandoffLines(suiteHandoffSummary),
21941
22123
  ...workflowFollowupLines(recommendedCommands)
21942
22124
  ],
21943
22125
  agentProfile,
@@ -21955,6 +22137,7 @@ function createWorkflowCommand(deps) {
21955
22137
  result: execution.result,
21956
22138
  ...serializeWorkflowWalletApprovalOutput(inspection.walletApproval),
21957
22139
  tokenDiscoverySummary,
22140
+ suiteHandoffSummary,
21958
22141
  recommendedCommands
21959
22142
  }
21960
22143
  );
@@ -22017,6 +22200,7 @@ function buildDefaultOperatorPathHelpText() {
22017
22200
  "",
22018
22201
  "Use `zk-agent next --request-id <id>` to continue a stored workflow checkpoint.",
22019
22202
  "Use `zk-agent relay inspect --relay-url <url>` plus `zk-agent wallet create|reapprove --relay-url <url> --wait-relay --prompt-code` when the browser is not colocated.",
22203
+ "Current hosted approval claim: one public origin, one relay host, and one same-origin share-link + approval UI surface.",
22020
22204
  "Use `zk-agent wallet --help` for wallet recovery details and `zk-agent workflow --help` when the intent is broader than the flagship native-send path."
22021
22205
  ].join("\n");
22022
22206
  }
@@ -22061,7 +22245,7 @@ function applyRootHelpCommandOrder(program) {
22061
22245
  }
22062
22246
  function createProgram() {
22063
22247
  const program = new Command13().name("zk-agent").description(
22064
- "Local-first zkSync Era CLI for wallet approval, workflow execution, and hosted relay recovery"
22248
+ "Local-first zkSync-native CLI for wallet approval, workflow execution, and single-host hosted relay recovery"
22065
22249
  ).showHelpAfterError().option("--json", "Force JSON output for agent harnesses", false).hook("preAction", (thisCommand) => {
22066
22250
  if (thisCommand.optsWithGlobals().json) process.env.ZK_AGENT_OUTPUT = "json";
22067
22251
  });
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "zk-agent-cli",
3
- "version": "0.1.0-rc.1",
3
+ "version": "0.1.0-rc.2",
4
4
  "description": "Local-first zkSync Era and ZK Stack agent CLI with wallet session recovery, workflow orchestration, relay-backed approval, and SED smart-account support.",
5
5
  "license": "MIT",
6
6
  "type": "module",
@@ -46,6 +46,10 @@
46
46
  "smoke:hosted-operated-baseline": "node --import tsx ./src/smoke-hosted-operated-baseline.ts",
47
47
  "smoke:remote-approval": "node --import tsx ./src/smoke-remote-approval.ts",
48
48
  "typecheck": "tsc --noEmit",
49
+ "test:onboarding": "pnpm --filter @zk-agent/agent-core build && pnpm run build && node --import ../../scripts/ensure-test-storage-isolation.mjs --import tsx --test ./tests/setup-cli.test.mjs",
50
+ "test:suite": "pnpm --filter @zk-agent/agent-core build && pnpm run build && node --import ../../scripts/ensure-test-storage-isolation.mjs --import tsx --test ./tests/suite-cli.test.mjs",
51
+ "test:wallet-status": "pnpm --filter @zk-agent/agent-core build && node --import ../../scripts/ensure-test-storage-isolation.mjs --import tsx --test ./tests/wallet-status-cli.test.mjs",
52
+ "test:product-surface": "pnpm --filter @zk-agent/agent-core build && pnpm run build && node --import ../../scripts/ensure-test-storage-isolation.mjs --import tsx --test ./tests/setup-cli.test.mjs ./tests/suite-cli.test.mjs ./tests/wallet-status-cli.test.mjs",
49
53
  "test": "pnpm --filter @zk-agent/agent-core build && pnpm run build && node --import ../../scripts/ensure-test-storage-isolation.mjs --import tsx --test ./tests/*.test.mjs ./tests/*.test.ts"
50
54
  },
51
55
  "engines": {