@sherwoodagent/cli 0.40.6 → 0.41.4

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 (42) hide show
  1. package/dist/{abis-TXCLIR2K.js → abis-RGCO5GHC.js} +2 -2
  2. package/dist/{addresses-J4NSZRGB.js → addresses-JBIU5U3T.js} +2 -2
  3. package/dist/{agent-XBYSALOA.js → agent-LBF6OZRW.js} +3 -3
  4. package/dist/{chat-EYCDCZUA.js → chat-3GE6474H.js} +6 -6
  5. package/dist/{chunk-KHTM4GB5.js → chunk-AGKCDHKI.js} +3 -3
  6. package/dist/{chunk-5OMMVOR6.js → chunk-ARHM3CYN.js} +3 -3
  7. package/dist/{chunk-FCM6SSL6.js → chunk-CECQNUS6.js} +3 -3
  8. package/dist/{chunk-W3GXAODE.js → chunk-D77JGXIV.js} +15 -1
  9. package/dist/chunk-D77JGXIV.js.map +1 -0
  10. package/dist/{chunk-ITNGXYLB.js → chunk-JGJAKTKK.js} +4 -12
  11. package/dist/chunk-JGJAKTKK.js.map +1 -0
  12. package/dist/{chunk-363E34JI.js → chunk-JJ4EF7ZE.js} +3 -3
  13. package/dist/{chunk-ZN6CUAX7.js → chunk-VMNB4ARO.js} +19 -5
  14. package/dist/chunk-VMNB4ARO.js.map +1 -0
  15. package/dist/{eas-MUKSLDIP.js → eas-27JA63VQ.js} +4 -4
  16. package/dist/{governor-WA74WFOS.js → governor-YLZJIQOB.js} +4 -4
  17. package/dist/index.js +784 -293
  18. package/dist/index.js.map +1 -1
  19. package/dist/{price-ELYQKRSN.js → price-5RAPTAYW.js} +3 -3
  20. package/dist/{research-HXOXZA4N.js → research-HDEPP2SL.js} +3 -3
  21. package/dist/{session-NL6KF2Q5.js → session-EST3O7W3.js} +6 -6
  22. package/dist/{trade-WMPWF6RT.js → trade-XTLUZJB6.js} +7 -7
  23. package/dist/{xmtp-7CZ5LB5O.js → xmtp-LPCRZRHX.js} +4 -4
  24. package/package.json +1 -1
  25. package/dist/chunk-ITNGXYLB.js.map +0 -1
  26. package/dist/chunk-W3GXAODE.js.map +0 -1
  27. package/dist/chunk-ZN6CUAX7.js.map +0 -1
  28. /package/dist/{abis-TXCLIR2K.js.map → abis-RGCO5GHC.js.map} +0 -0
  29. /package/dist/{addresses-J4NSZRGB.js.map → addresses-JBIU5U3T.js.map} +0 -0
  30. /package/dist/{agent-XBYSALOA.js.map → agent-LBF6OZRW.js.map} +0 -0
  31. /package/dist/{chat-EYCDCZUA.js.map → chat-3GE6474H.js.map} +0 -0
  32. /package/dist/{chunk-KHTM4GB5.js.map → chunk-AGKCDHKI.js.map} +0 -0
  33. /package/dist/{chunk-5OMMVOR6.js.map → chunk-ARHM3CYN.js.map} +0 -0
  34. /package/dist/{chunk-FCM6SSL6.js.map → chunk-CECQNUS6.js.map} +0 -0
  35. /package/dist/{chunk-363E34JI.js.map → chunk-JJ4EF7ZE.js.map} +0 -0
  36. /package/dist/{eas-MUKSLDIP.js.map → eas-27JA63VQ.js.map} +0 -0
  37. /package/dist/{governor-WA74WFOS.js.map → governor-YLZJIQOB.js.map} +0 -0
  38. /package/dist/{price-ELYQKRSN.js.map → price-5RAPTAYW.js.map} +0 -0
  39. /package/dist/{research-HXOXZA4N.js.map → research-HDEPP2SL.js.map} +0 -0
  40. /package/dist/{session-NL6KF2Q5.js.map → session-EST3O7W3.js.map} +0 -0
  41. /package/dist/{trade-WMPWF6RT.js.map → trade-XTLUZJB6.js.map} +0 -0
  42. /package/dist/{xmtp-7CZ5LB5O.js.map → xmtp-LPCRZRHX.js.map} +0 -0
package/dist/index.js CHANGED
@@ -9,7 +9,7 @@ import {
9
9
  getQuote,
10
10
  listModels,
11
11
  provisionApiKey
12
- } from "./chunk-ITNGXYLB.js";
12
+ } from "./chunk-JGJAKTKK.js";
13
13
  import {
14
14
  createApproval,
15
15
  createJoinRequest,
@@ -19,14 +19,14 @@ import {
19
19
  queryJoinRequests,
20
20
  revokeAttestation,
21
21
  stripReferrerPrefix
22
- } from "./chunk-FCM6SSL6.js";
22
+ } from "./chunk-CECQNUS6.js";
23
23
  import {
24
24
  createSyndicate,
25
25
  getActiveSyndicates,
26
26
  getSyndicate,
27
27
  subdomainExists,
28
28
  updateMetadata
29
- } from "./chunk-KHTM4GB5.js";
29
+ } from "./chunk-AGKCDHKI.js";
30
30
  import {
31
31
  approveDepositor,
32
32
  deposit,
@@ -49,7 +49,7 @@ import {
49
49
  resolveVaultSyndicate,
50
50
  setTextRecord,
51
51
  setVaultAddress
52
- } from "./chunk-363E34JI.js";
52
+ } from "./chunk-JJ4EF7ZE.js";
53
53
  import {
54
54
  PROPOSAL_STATE,
55
55
  PROPOSAL_STATES,
@@ -81,7 +81,7 @@ import {
81
81
  setVotingPeriod,
82
82
  settleProposal,
83
83
  vote
84
- } from "./chunk-5OMMVOR6.js";
84
+ } from "./chunk-ARHM3CYN.js";
85
85
  import {
86
86
  AERODROME,
87
87
  AGENT_REGISTRY,
@@ -94,11 +94,12 @@ import {
94
94
  TOKENS,
95
95
  UNISWAP,
96
96
  VENICE
97
- } from "./chunk-ZN6CUAX7.js";
97
+ } from "./chunk-VMNB4ARO.js";
98
98
  import {
99
99
  formatContractError,
100
100
  getAccount,
101
101
  getPublicClient,
102
+ getWalletClient,
102
103
  sendTxWithRetry,
103
104
  waitForReceipt,
104
105
  writeContractWithRetry
@@ -144,7 +145,7 @@ import {
144
145
  SWAP_ROUTER_EXACT_INPUT_SINGLE_ABI,
145
146
  SYNDICATE_VAULT_ABI,
146
147
  VENICE_STAKING_ABI
147
- } from "./chunk-W3GXAODE.js";
148
+ } from "./chunk-D77JGXIV.js";
148
149
  import {
149
150
  fetchMetadata,
150
151
  uploadMetadata
@@ -154,9 +155,9 @@ import {
154
155
  import { config as loadDotenv } from "dotenv";
155
156
  import { createRequire } from "module";
156
157
  import { Command, Option } from "commander";
157
- import { parseUnits as parseUnits4, formatUnits as formatUnits4, isAddress as isAddress5 } from "viem";
158
- import chalk8 from "chalk";
159
- import ora7 from "ora";
158
+ import { parseUnits as parseUnits6, formatUnits as formatUnits5, isAddress as isAddress6 } from "viem";
159
+ import chalk9 from "chalk";
160
+ import ora8 from "ora";
160
161
  import { input, confirm, select } from "@inquirer/prompts";
161
162
 
162
163
  // src/providers/moonwell.ts
@@ -1444,9 +1445,9 @@ function registerStrategyTemplateCommands(strategy2) {
1444
1445
  console.error(chalk.red("Missing --name, --performance-fee, or --duration. Use --write-calls to skip proposal submission."));
1445
1446
  process.exit(1);
1446
1447
  }
1447
- const { propose: propose2 } = await import("./governor-WA74WFOS.js");
1448
+ const { propose: propose2 } = await import("./governor-YLZJIQOB.js");
1448
1449
  const { pinJSON } = await import("./ipfs-IGXLLJCF.js");
1449
- const { parseDuration: parseDuration2 } = await import("./governor-WA74WFOS.js");
1450
+ const { parseDuration: parseDuration2 } = await import("./governor-YLZJIQOB.js");
1450
1451
  const performanceFeeBps = BigInt(opts.performanceFee);
1451
1452
  if (performanceFeeBps < 0n || performanceFeeBps > 10000n) {
1452
1453
  console.error(chalk.red("--performance-fee must be 0-10000 (basis points)"));
@@ -1553,7 +1554,7 @@ function registerStrategyTemplateCommands(strategy2) {
1553
1554
  let prices = [];
1554
1555
  let priceSource = null;
1555
1556
  try {
1556
- const { getTokenPricesInAsset } = await import("./price-ELYQKRSN.js");
1557
+ const { getTokenPricesInAsset } = await import("./price-5RAPTAYW.js");
1557
1558
  prices = await getTokenPricesInAsset({
1558
1559
  tokens: allocations.map((a, i) => ({
1559
1560
  token: a.token,
@@ -1946,10 +1947,11 @@ async function getActiveSyndicates2(creator) {
1946
1947
  }
1947
1948
 
1948
1949
  // src/commands/venice.ts
1949
- import { formatUnits as formatUnits2, isAddress as isAddress2 } from "viem";
1950
+ import { formatUnits as formatUnits2, isAddress as isAddress2, parseUnits as parseUnits2 } from "viem";
1950
1951
  import chalk2 from "chalk";
1951
1952
  import ora2 from "ora";
1952
1953
  import { readFileSync } from "fs";
1954
+ import { createInterface } from "readline/promises";
1953
1955
  function registerVeniceCommands(program2) {
1954
1956
  const venice = program2.command("venice").description("Venice private inference \u2014 provision API keys, run inference");
1955
1957
  venice.command("provision").description("Self-provision a Venice API key (requires sVVV in wallet)").action(async () => {
@@ -1982,7 +1984,7 @@ function registerVeniceCommands(program2) {
1982
1984
  console.log(chalk2.dim(` Key: ${apiKey.slice(0, 8)}...${apiKey.slice(-4)}`));
1983
1985
  console.log(chalk2.dim(" Saved to ~/.sherwood/config.json"));
1984
1986
  try {
1985
- const { createVeniceProvisionAttestation, getEasScanUrl: getEasScanUrl2 } = await import("./eas-MUKSLDIP.js");
1987
+ const { createVeniceProvisionAttestation, getEasScanUrl: getEasScanUrl2 } = await import("./eas-27JA63VQ.js");
1986
1988
  const { uid } = await createVeniceProvisionAttestation(account.address);
1987
1989
  if (uid !== "0x0000000000000000000000000000000000000000000000000000000000000000") {
1988
1990
  console.log(chalk2.dim(` Attested: ${getEasScanUrl2(uid)}`));
@@ -1995,6 +1997,203 @@ function registerVeniceCommands(program2) {
1995
1997
  process.exit(1);
1996
1998
  }
1997
1999
  });
2000
+ venice.command("stake").description("Stake VVV tokens to receive sVVV (required for API key provisioning)").requiredOption("--amount <n>", "Amount of VVV to stake (human-readable, e.g. 13)").action(async (opts) => {
2001
+ const account = getAccount();
2002
+ const client = getPublicClient();
2003
+ const chain = getChain();
2004
+ const veniceAddrs = VENICE();
2005
+ const amount = parseUnits2(opts.amount, 18);
2006
+ const balSpinner = ora2("Checking VVV balance...").start();
2007
+ try {
2008
+ const vvvBalance = await client.readContract({
2009
+ address: veniceAddrs.VVV,
2010
+ abi: ERC20_ABI,
2011
+ functionName: "balanceOf",
2012
+ args: [account.address]
2013
+ });
2014
+ if (vvvBalance < amount) {
2015
+ balSpinner.fail(`Insufficient VVV: have ${formatUnits2(vvvBalance, 18)}, need ${opts.amount}`);
2016
+ process.exit(1);
2017
+ }
2018
+ balSpinner.succeed(`VVV balance: ${formatUnits2(vvvBalance, 18)}`);
2019
+ } catch (err) {
2020
+ balSpinner.fail("Failed to check VVV balance");
2021
+ console.error(chalk2.red(formatContractError(err)));
2022
+ process.exit(1);
2023
+ }
2024
+ const approveSpinner = ora2("Approving VVV for staking contract...").start();
2025
+ try {
2026
+ const approveHash = await writeContractWithRetry({
2027
+ account,
2028
+ chain,
2029
+ address: veniceAddrs.VVV,
2030
+ abi: ERC20_ABI,
2031
+ functionName: "approve",
2032
+ args: [veniceAddrs.STAKING, amount]
2033
+ });
2034
+ await waitForReceipt(approveHash);
2035
+ approveSpinner.succeed("VVV approved");
2036
+ } catch (err) {
2037
+ approveSpinner.fail("Approve failed");
2038
+ console.error(chalk2.red(formatContractError(err)));
2039
+ process.exit(1);
2040
+ }
2041
+ const stakeSpinner = ora2(`Staking ${opts.amount} VVV...`).start();
2042
+ try {
2043
+ const stakeHash = await writeContractWithRetry({
2044
+ account,
2045
+ chain,
2046
+ address: veniceAddrs.STAKING,
2047
+ abi: VENICE_STAKING_ABI,
2048
+ functionName: "stake",
2049
+ args: [account.address, amount]
2050
+ });
2051
+ await waitForReceipt(stakeHash);
2052
+ const sVvvBalance = await client.readContract({
2053
+ address: veniceAddrs.STAKING,
2054
+ abi: VENICE_STAKING_ABI,
2055
+ functionName: "balanceOf",
2056
+ args: [account.address]
2057
+ });
2058
+ stakeSpinner.succeed(`Staked ${opts.amount} VVV \u2192 ${formatUnits2(sVvvBalance, 18)} sVVV`);
2059
+ console.log(chalk2.dim(" You can now run: sherwood venice provision"));
2060
+ } catch (err) {
2061
+ stakeSpinner.fail("Stake failed");
2062
+ console.error(chalk2.red(formatContractError(err)));
2063
+ process.exit(1);
2064
+ }
2065
+ });
2066
+ venice.command("mint-diem").description("Lock sVVV to mint DIEM (Venice inference credits; ~1d cooldown)").requiredOption("--amount <n>", "Amount of sVVV to lock (human-readable, 18 decimals)").option("--slippage <bps>", "Slippage tolerance in bps (default 500 = 5%)", "500").option("--yes", "Skip the cooldown confirmation prompt").action(async (opts) => {
2067
+ const account = getAccount();
2068
+ const client = getPublicClient();
2069
+ const chain = getChain();
2070
+ const { STAKING, DIEM } = VENICE();
2071
+ const amount = parseUnits2(opts.amount, 18);
2072
+ const slippageBps = BigInt(opts.slippage ?? "500");
2073
+ if (slippageBps < 0n || slippageBps > 10000n) {
2074
+ console.error(chalk2.red(`Invalid slippage bps: ${opts.slippage} (must be 0\u201310000)`));
2075
+ process.exit(1);
2076
+ }
2077
+ const balSpinner = ora2("Checking sVVV balance...").start();
2078
+ let sVvvBalance;
2079
+ try {
2080
+ sVvvBalance = await client.readContract({
2081
+ address: STAKING,
2082
+ abi: VENICE_STAKING_ABI,
2083
+ functionName: "balanceOf",
2084
+ args: [account.address]
2085
+ });
2086
+ } catch (err) {
2087
+ balSpinner.fail("Failed to read sVVV balance");
2088
+ console.error(chalk2.red(formatContractError(err)));
2089
+ process.exit(1);
2090
+ }
2091
+ if (sVvvBalance < amount) {
2092
+ balSpinner.fail(
2093
+ `Insufficient sVVV: have ${formatUnits2(sVvvBalance, 18)}, need ${opts.amount}`
2094
+ );
2095
+ console.log(chalk2.yellow(" Stake VVV first (see VeniceInferenceStrategy proposal flow)."));
2096
+ process.exit(1);
2097
+ }
2098
+ balSpinner.succeed(`sVVV balance: ${formatUnits2(sVvvBalance, 18)}`);
2099
+ const quoteSpinner = ora2("Quoting DIEM output...").start();
2100
+ let expected;
2101
+ try {
2102
+ expected = await client.readContract({
2103
+ address: STAKING,
2104
+ abi: VENICE_STAKING_ABI,
2105
+ functionName: "getDiemAmountOut",
2106
+ args: [amount]
2107
+ });
2108
+ } catch (err) {
2109
+ quoteSpinner.fail("Failed to quote DIEM output");
2110
+ console.error(chalk2.red(formatContractError(err)));
2111
+ process.exit(1);
2112
+ }
2113
+ if (expected === 0n) {
2114
+ quoteSpinner.fail("Quote returned 0 DIEM \u2014 refusing to mint");
2115
+ process.exit(1);
2116
+ }
2117
+ const minOut = expected * (10000n - slippageBps) / 10000n;
2118
+ quoteSpinner.succeed(
2119
+ `Expected: ${formatUnits2(expected, 18)} DIEM (minOut @ ${slippageBps}bps: ${formatUnits2(minOut, 18)})`
2120
+ );
2121
+ const MIN_SPENDABLE_DIEM = parseUnits2("0.1", 18);
2122
+ let currentDiem = 0n;
2123
+ try {
2124
+ currentDiem = await client.readContract({
2125
+ address: DIEM,
2126
+ abi: ERC20_ABI,
2127
+ functionName: "balanceOf",
2128
+ args: [account.address]
2129
+ });
2130
+ } catch {
2131
+ }
2132
+ const projectedDiem = currentDiem + expected;
2133
+ if (projectedDiem < MIN_SPENDABLE_DIEM) {
2134
+ const shortfall = MIN_SPENDABLE_DIEM - projectedDiem;
2135
+ const sVvvNeeded = (amount * shortfall + expected - 1n) / expected;
2136
+ console.log();
2137
+ console.log(chalk2.red(" \u26A0 Venice requires \u2265 0.1 DIEM minimum before ANY DIEM credit"));
2138
+ console.log(chalk2.red(" becomes spendable on inference calls."));
2139
+ console.log(chalk2.red(` Projected DIEM after mint: ${formatUnits2(projectedDiem, 18)} (short by ${formatUnits2(shortfall, 18)})`));
2140
+ console.log(chalk2.red(` Approx additional sVVV needed: ${formatUnits2(sVvvNeeded, 18)}`));
2141
+ console.log(chalk2.dim(" Below threshold, this DIEM sits idle \u2014 consider acquiring"));
2142
+ console.log(chalk2.dim(" more sVVV first, or use x402 USDC pay-per-request."));
2143
+ }
2144
+ console.log();
2145
+ console.log(chalk2.yellow(" \u26A0 Locked sVVV cannot be unstaked directly. To recover it you must"));
2146
+ console.log(chalk2.yellow(" first call `staking.burnDiem(amount)` (burns DIEM, unlocks sVVV"));
2147
+ console.log(chalk2.yellow(" at your average mint rate), then `initiateUnstake` + wait the"));
2148
+ console.log(chalk2.yellow(" 7-day staking cooldown, then `finalizeUnstake`."));
2149
+ console.log(chalk2.dim(" x402 alternative (pay-per-request in USDC, no DIEM lock):"));
2150
+ console.log(chalk2.dim(" https://docs.venice.ai/overview/guides/generating-api-key-agent#paying-for-inference"));
2151
+ console.log();
2152
+ if (!opts.yes) {
2153
+ const rl = createInterface({ input: process.stdin, output: process.stdout });
2154
+ try {
2155
+ const answer = (await rl.question(` Lock ${opts.amount} sVVV for DIEM credits? [y/N] `)).trim().toLowerCase();
2156
+ if (answer !== "y" && answer !== "yes") {
2157
+ console.log(chalk2.dim(" Aborted."));
2158
+ process.exit(0);
2159
+ }
2160
+ } finally {
2161
+ rl.close();
2162
+ }
2163
+ }
2164
+ const diemBefore = currentDiem;
2165
+ const mintSpinner = ora2(`Minting DIEM from ${opts.amount} sVVV...`).start();
2166
+ try {
2167
+ const hash = await writeContractWithRetry({
2168
+ account,
2169
+ chain,
2170
+ address: STAKING,
2171
+ abi: VENICE_STAKING_ABI,
2172
+ functionName: "mintDiem",
2173
+ args: [amount, minOut]
2174
+ });
2175
+ await waitForReceipt(hash);
2176
+ const diemAfter = await client.readContract({
2177
+ address: DIEM,
2178
+ abi: ERC20_ABI,
2179
+ functionName: "balanceOf",
2180
+ args: [account.address]
2181
+ });
2182
+ const delta = diemAfter - diemBefore;
2183
+ mintSpinner.succeed(
2184
+ `Minted ${formatUnits2(delta > 0n ? delta : diemAfter, 18)} DIEM` + (delta > 0n ? ` (balance: ${formatUnits2(diemAfter, 18)})` : "")
2185
+ );
2186
+ console.log(chalk2.dim(` Tx: ${hash}`));
2187
+ console.log(chalk2.yellow(" Note: Venice requires \u2265 0.1 DIEM to spend ANY DIEM credit, and"));
2188
+ console.log(chalk2.yellow(" refreshes daily allocation at 00:00 UTC. Below threshold,"));
2189
+ console.log(chalk2.yellow(" inference will continue to 402."));
2190
+ console.log(chalk2.dim(' Once over threshold: sherwood venice infer --model <id> --prompt "..."'));
2191
+ } catch (err) {
2192
+ mintSpinner.fail("mintDiem failed");
2193
+ console.error(chalk2.red(formatContractError(err)));
2194
+ process.exit(1);
2195
+ }
2196
+ });
1998
2197
  venice.command("status").description("Show Venice inference status: sVVV balances, DIEM, API key").requiredOption("--vault <address>", "Vault address").action(async (opts) => {
1999
2198
  const vaultAddress = opts.vault;
2000
2199
  if (!isAddress2(vaultAddress)) {
@@ -2032,7 +2231,7 @@ function registerVeniceCommands(program2) {
2032
2231
  return { agent, balance: bal };
2033
2232
  })
2034
2233
  );
2035
- const [mySvvv, myPending] = await Promise.all([
2234
+ const [mySvvv, myPending, myDiem] = await Promise.all([
2036
2235
  client.readContract({
2037
2236
  address: VENICE().STAKING,
2038
2237
  abi: VENICE_STAKING_ABI,
@@ -2044,6 +2243,12 @@ function registerVeniceCommands(program2) {
2044
2243
  abi: VENICE_STAKING_ABI,
2045
2244
  functionName: "pendingRewards",
2046
2245
  args: [account.address]
2246
+ }),
2247
+ client.readContract({
2248
+ address: VENICE().DIEM,
2249
+ abi: ERC20_ABI,
2250
+ functionName: "balanceOf",
2251
+ args: [account.address]
2047
2252
  })
2048
2253
  ]);
2049
2254
  const apiKeyValid = await checkApiKeyValid();
@@ -2065,6 +2270,8 @@ function registerVeniceCommands(program2) {
2065
2270
  console.log(chalk2.bold("\n Your Wallet"));
2066
2271
  console.log(` sVVV: ${formatUnits2(mySvvv, 18)}`);
2067
2272
  console.log(` Pending rewards: ${formatUnits2(myPending, 18)} VVV`);
2273
+ console.log(` DIEM (credits): ${formatUnits2(myDiem, 18)}`);
2274
+ console.log(chalk2.dim(" (mint via `sherwood venice mint-diem --amount <sVVV>`)"));
2068
2275
  console.log(chalk2.bold("\n Venice API"));
2069
2276
  console.log(` Key: ${apiKey ? `${apiKey.slice(0, 8)}...${apiKey.slice(-4)}` : chalk2.dim("not provisioned")}`);
2070
2277
  console.log(` Status: ${apiKeyValid ? chalk2.green("valid") : chalk2.red("invalid/missing")}`);
@@ -2133,7 +2340,7 @@ ${opts.prompt}`;
2133
2340
  console.log(chalk2.dim(`Model: ${result.model} | Tokens: ${result.usage.promptTokens} in, ${result.usage.completionTokens} out, ${result.usage.totalTokens} total`));
2134
2341
  }
2135
2342
  try {
2136
- const { createVeniceInferenceAttestation, getEasScanUrl: getEasScanUrl2 } = await import("./eas-MUKSLDIP.js");
2343
+ const { createVeniceInferenceAttestation, getEasScanUrl: getEasScanUrl2 } = await import("./eas-27JA63VQ.js");
2137
2344
  const { keccak256, toHex, isAddress: isAddr } = await import("viem");
2138
2345
  const { getChainContracts: getChainContracts2 } = await import("./config-LS7FKZL5.js");
2139
2346
  const { getChain: getActiveChain } = await import("./network-KSMKPKNL.js");
@@ -2160,14 +2367,14 @@ ${opts.prompt}`;
2160
2367
  }
2161
2368
 
2162
2369
  // src/commands/allowance.ts
2163
- import { parseUnits as parseUnits3, formatUnits as formatUnits3, isAddress as isAddress3 } from "viem";
2370
+ import { parseUnits as parseUnits4, formatUnits as formatUnits3, isAddress as isAddress3 } from "viem";
2164
2371
  import chalk3 from "chalk";
2165
2372
  import ora3 from "ora";
2166
2373
 
2167
2374
  // src/strategies/allowance-disburse.ts
2168
- import { encodeFunctionData as encodeFunctionData8, parseUnits as parseUnits2 } from "viem";
2375
+ import { encodeFunctionData as encodeFunctionData8, parseUnits as parseUnits3 } from "viem";
2169
2376
  function buildDisburseBatch(config, vaultAddress, agents, assetAddress, assetDecimals, minUsdc, swapPath) {
2170
- const assetAmount = parseUnits2(config.amount, assetDecimals);
2377
+ const assetAmount = parseUnits3(config.amount, assetDecimals);
2171
2378
  const isUsdc = assetAddress.toLowerCase() === TOKENS().USDC.toLowerCase();
2172
2379
  const isWeth = assetAddress.toLowerCase() === TOKENS().WETH.toLowerCase();
2173
2380
  const calls = [];
@@ -2280,7 +2487,7 @@ function registerAllowanceCommands(program2) {
2280
2487
  console.error(chalk3.red("No agents registered in vault. Register agents first."));
2281
2488
  process.exit(1);
2282
2489
  }
2283
- const requestedAmount = parseUnits3(opts.amount, assetDecimals);
2490
+ const requestedAmount = parseUnits4(opts.amount, assetDecimals);
2284
2491
  const profit = assetBalance > totalDeposited ? assetBalance - totalDeposited : 0n;
2285
2492
  const isUsdc = assetAddress.toLowerCase() === TOKENS().USDC.toLowerCase();
2286
2493
  const isWeth = assetAddress.toLowerCase() === TOKENS().WETH.toLowerCase();
@@ -2507,12 +2714,12 @@ function registerIdentityCommands(program2) {
2507
2714
  identity.command("load").description("Load an existing ERC-8004 agent identity into your config").requiredOption("--id <tokenId>", "Agent token ID to load").action(async (opts) => {
2508
2715
  const account = getAccount();
2509
2716
  const client = getPublicClient();
2510
- const registry = AGENT_REGISTRY().IDENTITY_REGISTRY;
2717
+ const registry2 = AGENT_REGISTRY().IDENTITY_REGISTRY;
2511
2718
  const tokenId = Number(opts.id);
2512
2719
  const spinner = ora4(`Verifying ownership of agent #${tokenId}...`).start();
2513
2720
  try {
2514
2721
  const owner = await client.readContract({
2515
- address: registry,
2722
+ address: registry2,
2516
2723
  abi: IDENTITY_REGISTRY_ABI,
2517
2724
  functionName: "ownerOf",
2518
2725
  args: [BigInt(tokenId)]
@@ -2533,12 +2740,12 @@ function registerIdentityCommands(program2) {
2533
2740
  });
2534
2741
  identity.command("status").description("Show your agent identity status").action(async () => {
2535
2742
  const account = getAccount();
2536
- const registry = AGENT_REGISTRY().IDENTITY_REGISTRY;
2743
+ const registry2 = AGENT_REGISTRY().IDENTITY_REGISTRY;
2537
2744
  const client = getPublicClient();
2538
2745
  const spinner = ora4("Checking identity...").start();
2539
2746
  try {
2540
2747
  const balance = await client.readContract({
2541
- address: registry,
2748
+ address: registry2,
2542
2749
  abi: IDENTITY_REGISTRY_ABI,
2543
2750
  functionName: "balanceOf",
2544
2751
  args: [account.address]
@@ -2549,12 +2756,12 @@ function registerIdentityCommands(program2) {
2549
2756
  console.log(chalk4.bold("Agent Identity (ERC-8004)"));
2550
2757
  console.log(chalk4.dim("\u2500".repeat(40)));
2551
2758
  console.log(` Wallet: ${account.address}`);
2552
- console.log(` Registry: ${registry}`);
2759
+ console.log(` Registry: ${registry2}`);
2553
2760
  console.log(` NFTs owned: ${balance.toString()}`);
2554
2761
  if (savedId) {
2555
2762
  try {
2556
2763
  const owner = await client.readContract({
2557
- address: registry,
2764
+ address: registry2,
2558
2765
  abi: IDENTITY_REGISTRY_ABI,
2559
2766
  functionName: "ownerOf",
2560
2767
  args: [BigInt(savedId)]
@@ -3265,7 +3472,7 @@ function printSimulationResult(result, callType) {
3265
3472
  }
3266
3473
  async function sendSimulationAlert(subdomain, proposalId, vault, execResult, settleResult) {
3267
3474
  try {
3268
- const xmtp = await import("./xmtp-7CZ5LB5O.js");
3475
+ const xmtp = await import("./xmtp-LPCRZRHX.js");
3269
3476
  const { getAccount: getAccount2 } = await import("./client-HKAG55PQ.js");
3270
3477
  const group = await xmtp.getGroup("", subdomain);
3271
3478
  const allRisks = [...execResult.risks, ...settleResult?.risks ?? []];
@@ -4074,6 +4281,289 @@ function registerGovernorCommands(program2) {
4074
4281
  });
4075
4282
  }
4076
4283
 
4284
+ // src/commands/guardian-delegate.ts
4285
+ import chalk8 from "chalk";
4286
+ import ora7 from "ora";
4287
+ import { formatUnits as formatUnits4, isAddress as isAddress5, parseUnits as parseUnits5 } from "viem";
4288
+ var G4 = chalk8.green;
4289
+ var W4 = chalk8.white;
4290
+ var DIM4 = chalk8.gray;
4291
+ var BOLD4 = chalk8.white.bold;
4292
+ var LABEL4 = chalk8.green.bold;
4293
+ var WARN = chalk8.yellow;
4294
+ var SEP4 = () => console.log(DIM4("\u2500".repeat(60)));
4295
+ var GUARDIAN_REGISTRY_ABI = [
4296
+ // Guardian stake
4297
+ { type: "function", name: "stakeAsGuardian", inputs: [{ type: "uint256" }, { type: "uint256" }], outputs: [], stateMutability: "nonpayable" },
4298
+ { type: "function", name: "requestUnstakeGuardian", inputs: [], outputs: [], stateMutability: "nonpayable" },
4299
+ { type: "function", name: "cancelUnstakeGuardian", inputs: [], outputs: [], stateMutability: "nonpayable" },
4300
+ { type: "function", name: "claimUnstakeGuardian", inputs: [], outputs: [], stateMutability: "nonpayable" },
4301
+ // Delegation
4302
+ { type: "function", name: "delegateStake", inputs: [{ type: "address" }, { type: "uint256" }], outputs: [], stateMutability: "nonpayable" },
4303
+ { type: "function", name: "requestUnstakeDelegation", inputs: [{ type: "address" }], outputs: [], stateMutability: "nonpayable" },
4304
+ { type: "function", name: "cancelUnstakeDelegation", inputs: [{ type: "address" }], outputs: [], stateMutability: "nonpayable" },
4305
+ { type: "function", name: "claimUnstakeDelegation", inputs: [{ type: "address" }], outputs: [], stateMutability: "nonpayable" },
4306
+ // Commission
4307
+ { type: "function", name: "setCommission", inputs: [{ type: "uint256" }], outputs: [], stateMutability: "nonpayable" },
4308
+ // Views
4309
+ { type: "function", name: "guardianStake", inputs: [{ type: "address" }], outputs: [{ type: "uint256" }], stateMutability: "view" },
4310
+ { type: "function", name: "isActiveGuardian", inputs: [{ type: "address" }], outputs: [{ type: "bool" }], stateMutability: "view" },
4311
+ { type: "function", name: "commissionOf", inputs: [{ type: "address" }], outputs: [{ type: "uint256" }], stateMutability: "view" },
4312
+ { type: "function", name: "delegationOf", inputs: [{ type: "address" }, { type: "address" }], outputs: [{ type: "uint256" }], stateMutability: "view" },
4313
+ { type: "function", name: "delegatedInbound", inputs: [{ type: "address" }], outputs: [{ type: "uint256" }], stateMutability: "view" },
4314
+ // Guardian-fee claim (vault asset)
4315
+ { type: "function", name: "claimProposalReward", inputs: [{ type: "uint256" }], outputs: [], stateMutability: "nonpayable" },
4316
+ { type: "function", name: "claimDelegatorProposalReward", inputs: [{ type: "address" }, { type: "uint256" }], outputs: [], stateMutability: "nonpayable" }
4317
+ ];
4318
+ var ERC20_ABI2 = [
4319
+ { type: "function", name: "approve", inputs: [{ type: "address" }, { type: "uint256" }], outputs: [{ type: "bool" }], stateMutability: "nonpayable" },
4320
+ { type: "function", name: "balanceOf", inputs: [{ type: "address" }], outputs: [{ type: "uint256" }], stateMutability: "view" },
4321
+ { type: "function", name: "decimals", inputs: [], outputs: [{ type: "uint8" }], stateMutability: "view" }
4322
+ ];
4323
+ function requireAddress(name, addr) {
4324
+ if (addr === "0x0000000000000000000000000000000000000000") {
4325
+ console.error(chalk8.red(`${name} is not deployed on ${getNetwork()}. Update cli/src/lib/addresses.ts after deploy.`));
4326
+ process.exit(1);
4327
+ }
4328
+ return addr;
4329
+ }
4330
+ function registry() {
4331
+ return requireAddress("GUARDIAN_REGISTRY", SHERWOOD().GUARDIAN_REGISTRY);
4332
+ }
4333
+ function wood() {
4334
+ return requireAddress("WOOD_TOKEN", SHERWOOD().WOOD_TOKEN);
4335
+ }
4336
+ async function ensureWoodAllowance(amount) {
4337
+ const wallet = getWalletClient();
4338
+ const pc = getPublicClient();
4339
+ const addr = wallet.account.address;
4340
+ const current = await pc.readContract({
4341
+ address: wood(),
4342
+ abi: [{ type: "function", name: "allowance", inputs: [{ type: "address" }, { type: "address" }], outputs: [{ type: "uint256" }], stateMutability: "view" }],
4343
+ functionName: "allowance",
4344
+ args: [addr, registry()]
4345
+ });
4346
+ if (current >= amount) return;
4347
+ const spinner = ora7("Approving WOOD...").start();
4348
+ try {
4349
+ const hash = await wallet.writeContract({
4350
+ address: wood(),
4351
+ abi: ERC20_ABI2,
4352
+ functionName: "approve",
4353
+ args: [registry(), 2n ** 256n - 1n],
4354
+ chain: null,
4355
+ account: wallet.account
4356
+ });
4357
+ await pc.waitForTransactionReceipt({ hash });
4358
+ spinner.succeed("WOOD approval granted");
4359
+ } catch (err) {
4360
+ spinner.fail("WOOD approval failed");
4361
+ throw err;
4362
+ }
4363
+ }
4364
+ function registerGuardianCommands(program2) {
4365
+ const guardian = program2.command("guardian").description("Guardian staking, delegation, and rewards (V1.5)");
4366
+ guardian.command("status [address]").description("Show guardian stake + commission + active status for an address (default: caller)").action(async (addressArg) => {
4367
+ const pc = getPublicClient();
4368
+ let target;
4369
+ if (addressArg) {
4370
+ if (!isAddress5(addressArg)) {
4371
+ console.error(chalk8.red("Invalid address"));
4372
+ process.exit(1);
4373
+ }
4374
+ target = addressArg;
4375
+ } else {
4376
+ const wallet = getWalletClient();
4377
+ target = wallet.account.address;
4378
+ }
4379
+ const spinner = ora7("Loading...").start();
4380
+ try {
4381
+ const [stake, active, commission] = await Promise.all([
4382
+ pc.readContract({ address: registry(), abi: GUARDIAN_REGISTRY_ABI, functionName: "guardianStake", args: [target] }),
4383
+ pc.readContract({ address: registry(), abi: GUARDIAN_REGISTRY_ABI, functionName: "isActiveGuardian", args: [target] }),
4384
+ pc.readContract({ address: registry(), abi: GUARDIAN_REGISTRY_ABI, functionName: "commissionOf", args: [target] })
4385
+ ]);
4386
+ const delegatedIn = await pc.readContract({
4387
+ address: registry(),
4388
+ abi: GUARDIAN_REGISTRY_ABI,
4389
+ functionName: "delegatedInbound",
4390
+ args: [target]
4391
+ });
4392
+ spinner.stop();
4393
+ console.log();
4394
+ console.log(LABEL4(" \u25C6 Guardian Status"));
4395
+ SEP4();
4396
+ console.log(W4(` Address: ${G4(target)}`));
4397
+ console.log(W4(` Active guardian: ${active ? G4("yes") : DIM4("no")}`));
4398
+ console.log(W4(` Own stake: ${BOLD4(formatUnits4(stake, 18))} WOOD`));
4399
+ console.log(W4(` Delegated inbound: ${BOLD4(formatUnits4(delegatedIn, 18))} WOOD`));
4400
+ console.log(W4(` Commission: ${BOLD4(`${Number(commission) / 100}%`)}`));
4401
+ SEP4();
4402
+ console.log();
4403
+ } catch (err) {
4404
+ spinner.fail("Failed to load");
4405
+ console.error(chalk8.red(formatContractError(err)));
4406
+ process.exit(1);
4407
+ }
4408
+ });
4409
+ guardian.command("stake <amount>").description("Stake as a guardian. Amount in WOOD (min = registry.minGuardianStake).").option("--agent-id <id>", "ERC-8004 agent ID to associate (first-stake only)", "0").action(async (amountStr, opts) => {
4410
+ const amount = parseUnits5(amountStr, 18);
4411
+ const agentId = BigInt(opts.agentId);
4412
+ await ensureWoodAllowance(amount);
4413
+ const wallet = getWalletClient();
4414
+ const pc = getPublicClient();
4415
+ const spinner = ora7(`Staking ${amountStr} WOOD...`).start();
4416
+ try {
4417
+ const hash = await wallet.writeContract({
4418
+ address: registry(),
4419
+ abi: GUARDIAN_REGISTRY_ABI,
4420
+ functionName: "stakeAsGuardian",
4421
+ args: [amount, agentId],
4422
+ chain: null,
4423
+ account: wallet.account
4424
+ });
4425
+ await pc.waitForTransactionReceipt({ hash });
4426
+ spinner.succeed(`Staked. Tx: ${hash}`);
4427
+ } catch (err) {
4428
+ spinner.fail("Stake failed");
4429
+ console.error(chalk8.red(formatContractError(err)));
4430
+ process.exit(1);
4431
+ }
4432
+ });
4433
+ guardian.command("unstake <action>").description("Unstake flow: 'request' | 'cancel' | 'claim' (7d cooldown)").action(async (action) => {
4434
+ const fn = { request: "requestUnstakeGuardian", cancel: "cancelUnstakeGuardian", claim: "claimUnstakeGuardian" }[action];
4435
+ if (!fn) {
4436
+ console.error(chalk8.red(`Unknown action '${action}'. Use request | cancel | claim.`));
4437
+ process.exit(1);
4438
+ }
4439
+ const wallet = getWalletClient();
4440
+ const pc = getPublicClient();
4441
+ const spinner = ora7(`${action}...`).start();
4442
+ try {
4443
+ const hash = await wallet.writeContract({ address: registry(), abi: GUARDIAN_REGISTRY_ABI, functionName: fn, args: [], chain: null, account: wallet.account });
4444
+ await pc.waitForTransactionReceipt({ hash });
4445
+ spinner.succeed(`${action} confirmed. Tx: ${hash}`);
4446
+ } catch (err) {
4447
+ spinner.fail(`${action} failed`);
4448
+ console.error(chalk8.red(formatContractError(err)));
4449
+ process.exit(1);
4450
+ }
4451
+ });
4452
+ guardian.command("delegate <delegate> <amount>").description("Delegate WOOD stake to a guardian. Amount in WOOD.").action(async (delegate, amountStr) => {
4453
+ if (!isAddress5(delegate)) {
4454
+ console.error(chalk8.red("Invalid delegate address"));
4455
+ process.exit(1);
4456
+ }
4457
+ const amount = parseUnits5(amountStr, 18);
4458
+ await ensureWoodAllowance(amount);
4459
+ const wallet = getWalletClient();
4460
+ const pc = getPublicClient();
4461
+ const spinner = ora7(`Delegating ${amountStr} WOOD to ${delegate}...`).start();
4462
+ try {
4463
+ const hash = await wallet.writeContract({ address: registry(), abi: GUARDIAN_REGISTRY_ABI, functionName: "delegateStake", args: [delegate, amount], chain: null, account: wallet.account });
4464
+ await pc.waitForTransactionReceipt({ hash });
4465
+ spinner.succeed(`Delegated. Tx: ${hash}`);
4466
+ } catch (err) {
4467
+ spinner.fail("Delegation failed");
4468
+ console.error(chalk8.red(formatContractError(err)));
4469
+ process.exit(1);
4470
+ }
4471
+ });
4472
+ guardian.command("undelegate <delegate> <action>").description("Unstake-delegation flow: 'request' | 'cancel' | 'claim'").action(async (delegate, action) => {
4473
+ if (!isAddress5(delegate)) {
4474
+ console.error(chalk8.red("Invalid delegate address"));
4475
+ process.exit(1);
4476
+ }
4477
+ const fn = { request: "requestUnstakeDelegation", cancel: "cancelUnstakeDelegation", claim: "claimUnstakeDelegation" }[action];
4478
+ if (!fn) {
4479
+ console.error(chalk8.red(`Unknown action '${action}'. Use request | cancel | claim.`));
4480
+ process.exit(1);
4481
+ }
4482
+ const wallet = getWalletClient();
4483
+ const pc = getPublicClient();
4484
+ const spinner = ora7(`${action}...`).start();
4485
+ try {
4486
+ const hash = await wallet.writeContract({ address: registry(), abi: GUARDIAN_REGISTRY_ABI, functionName: fn, args: [delegate], chain: null, account: wallet.account });
4487
+ await pc.waitForTransactionReceipt({ hash });
4488
+ spinner.succeed(`${action} confirmed. Tx: ${hash}`);
4489
+ } catch (err) {
4490
+ spinner.fail(`${action} failed`);
4491
+ console.error(chalk8.red(formatContractError(err)));
4492
+ process.exit(1);
4493
+ }
4494
+ });
4495
+ guardian.command("set-commission <bps>").description("Set your commission rate in bps (0-5000 = 0-50%). Raises capped cumulatively at 500 bps/epoch.").action(async (bpsStr) => {
4496
+ const bps = BigInt(bpsStr);
4497
+ if (bps > 5000n) {
4498
+ console.error(chalk8.red("Commission cannot exceed 5000 bps (50%)"));
4499
+ process.exit(1);
4500
+ }
4501
+ const wallet = getWalletClient();
4502
+ const pc = getPublicClient();
4503
+ const spinner = ora7(`Setting commission to ${Number(bps) / 100}%...`).start();
4504
+ try {
4505
+ const hash = await wallet.writeContract({ address: registry(), abi: GUARDIAN_REGISTRY_ABI, functionName: "setCommission", args: [bps], chain: null, account: wallet.account });
4506
+ await pc.waitForTransactionReceipt({ hash });
4507
+ spinner.succeed(`Commission set. Tx: ${hash}`);
4508
+ } catch (err) {
4509
+ spinner.fail("setCommission failed");
4510
+ console.error(chalk8.red(formatContractError(err)));
4511
+ process.exit(1);
4512
+ }
4513
+ });
4514
+ guardian.command("claim-proposal <proposalId>").description("Claim guardian-fee commission for a settled proposal you voted Approve on (vault asset).").action(async (pidStr) => {
4515
+ const pid = BigInt(pidStr);
4516
+ const wallet = getWalletClient();
4517
+ const pc = getPublicClient();
4518
+ const spinner = ora7("Claiming...").start();
4519
+ try {
4520
+ const hash = await wallet.writeContract({ address: registry(), abi: GUARDIAN_REGISTRY_ABI, functionName: "claimProposalReward", args: [pid], chain: null, account: wallet.account });
4521
+ await pc.waitForTransactionReceipt({ hash });
4522
+ spinner.succeed(`Claimed. Tx: ${hash}`);
4523
+ } catch (err) {
4524
+ spinner.fail("Claim failed");
4525
+ console.error(chalk8.red(formatContractError(err)));
4526
+ process.exit(1);
4527
+ }
4528
+ });
4529
+ guardian.command("claim-delegator <delegate> <proposalId>").description("Claim your delegator share of a delegate's guardian-fee pool for a specific proposal.").action(async (delegate, pidStr) => {
4530
+ if (!isAddress5(delegate)) {
4531
+ console.error(chalk8.red("Invalid delegate address"));
4532
+ process.exit(1);
4533
+ }
4534
+ const pid = BigInt(pidStr);
4535
+ const wallet = getWalletClient();
4536
+ const pc = getPublicClient();
4537
+ const spinner = ora7("Claiming delegator share...").start();
4538
+ try {
4539
+ const hash = await wallet.writeContract({ address: registry(), abi: GUARDIAN_REGISTRY_ABI, functionName: "claimDelegatorProposalReward", args: [delegate, pid], chain: null, account: wallet.account });
4540
+ await pc.waitForTransactionReceipt({ hash });
4541
+ spinner.succeed(`Claimed. Tx: ${hash}`);
4542
+ } catch (err) {
4543
+ spinner.fail("Claim failed");
4544
+ console.error(chalk8.red(formatContractError(err)));
4545
+ process.exit(1);
4546
+ }
4547
+ });
4548
+ guardian.command("claim-wood").description("Open merkl.xyz to claim WOOD epoch block-rewards (off-chain distribution).").action(async () => {
4549
+ const wallet = getWalletClient();
4550
+ const addr = wallet.account.address;
4551
+ const url = `https://merkl.angle.money/user/${addr}`;
4552
+ console.log();
4553
+ console.log(LABEL4(" \u25C6 Merkl Reward Claim"));
4554
+ SEP4();
4555
+ console.log(W4(" WOOD epoch block-rewards are distributed off-chain via Merkl."));
4556
+ console.log(W4(" Open this URL in your browser to view + claim pending rewards:"));
4557
+ console.log();
4558
+ console.log(G4(` ${url}`));
4559
+ console.log();
4560
+ console.log(WARN(" Note: guardian-fee rewards (vault assets) are claimed on-chain"));
4561
+ console.log(WARN(" via `sherwood guardian claim-proposal <pid>`."));
4562
+ SEP4();
4563
+ console.log();
4564
+ });
4565
+ }
4566
+
4077
4567
  // src/index.ts
4078
4568
  try {
4079
4569
  loadDotenv();
@@ -4082,20 +4572,20 @@ try {
4082
4572
  var require2 = createRequire(import.meta.url);
4083
4573
  var { version: CLI_VERSION } = require2("../package.json");
4084
4574
  async function loadXmtp() {
4085
- return import("./xmtp-7CZ5LB5O.js");
4575
+ return import("./xmtp-LPCRZRHX.js");
4086
4576
  }
4087
4577
  async function loadCron() {
4088
4578
  return import("./cron-EOULYO3R.js");
4089
4579
  }
4090
- var G4 = chalk8.green;
4091
- var W4 = chalk8.white;
4092
- var DIM4 = chalk8.gray;
4093
- var BOLD4 = chalk8.white.bold;
4094
- var LABEL4 = chalk8.green.bold;
4095
- var SEP4 = () => console.log(DIM4("\u2500".repeat(60)));
4580
+ var G5 = chalk9.green;
4581
+ var W5 = chalk9.white;
4582
+ var DIM5 = chalk9.gray;
4583
+ var BOLD5 = chalk9.white.bold;
4584
+ var LABEL5 = chalk9.green.bold;
4585
+ var SEP5 = () => console.log(DIM5("\u2500".repeat(60)));
4096
4586
  function validateAddress(value, name) {
4097
- if (!isAddress5(value)) {
4098
- console.error(chalk8.red(`Invalid ${name} address: ${value}`));
4587
+ if (!isAddress6(value)) {
4588
+ console.error(chalk9.red(`Invalid ${name} address: ${value}`));
4099
4589
  process.exit(1);
4100
4590
  }
4101
4591
  return value;
@@ -4115,7 +4605,7 @@ program.name("sherwood").description("CLI for agent-managed investment syndicate
4115
4605
  process.env.ENABLE_TESTNET = "true";
4116
4606
  if (network !== "base") {
4117
4607
  console.warn(
4118
- chalk8.yellow("[warn] --testnet ignored, --chain takes precedence")
4608
+ chalk9.yellow("[warn] --testnet ignored, --chain takes precedence")
4119
4609
  );
4120
4610
  } else {
4121
4611
  network = "base-sepolia";
@@ -4123,39 +4613,39 @@ program.name("sherwood").description("CLI for agent-managed investment syndicate
4123
4613
  }
4124
4614
  setNetwork(network);
4125
4615
  if (getNetwork() !== "base") {
4126
- console.log(chalk8.yellow(`[${getNetwork()}]`));
4616
+ console.log(chalk9.yellow(`[${getNetwork()}]`));
4127
4617
  }
4128
4618
  });
4129
4619
  var syndicate = program.command("syndicate");
4130
4620
  syndicate.command("create").description("Create a new syndicate via the factory (interactive)").option("--subdomain <name>", "ENS subdomain (skip prompt)").option("--name <name>", "Syndicate name (skip prompt)").option("--agent-id <id>", "ERC-8004 agent identity token ID (skip prompt)").option("--asset <symbol-or-address>", "Vault asset: USDC, WETH, or a token address").option("--description <text>", "Short description").option("--metadata-uri <uri>", "Override metadata URI (skip IPFS upload)").option("--open-deposits", "Allow anyone to deposit (no whitelist)").option("--public-chat", "Enable dashboard spectator mode", false).option("-y, --yes", "Skip confirmation prompt (non-interactive mode)", false).action(async (opts) => {
4131
4621
  try {
4132
4622
  console.log();
4133
- console.log(LABEL4(" \u25C6 Create Syndicate"));
4134
- SEP4();
4623
+ console.log(LABEL5(" \u25C6 Create Syndicate"));
4624
+ SEP5();
4135
4625
  const wallet = getAccount();
4136
- console.log(DIM4(` Wallet: ${wallet.address}`));
4137
- console.log(DIM4(` Network: ${getChain().name}`));
4138
- SEP4();
4626
+ console.log(DIM5(` Wallet: ${wallet.address}`));
4627
+ console.log(DIM5(` Network: ${getChain().name}`));
4628
+ SEP5();
4139
4629
  const savedAgentId = getAgentId();
4140
4630
  const nonInteractive = opts.yes;
4141
4631
  const name = opts.name || (nonInteractive ? (() => {
4142
4632
  throw new Error("--name is required in non-interactive mode (-y)");
4143
4633
  })() : await input({
4144
- message: G4("Syndicate name"),
4634
+ message: G5("Syndicate name"),
4145
4635
  validate: (v) => v.length > 0 || "Name is required"
4146
4636
  }));
4147
4637
  const subdomain = opts.subdomain || (nonInteractive ? name.toLowerCase().replace(/\s+/g, "-").replace(/[^a-z0-9-]/g, "") : await input({
4148
- message: G4("ENS subdomain"),
4638
+ message: G5("ENS subdomain"),
4149
4639
  default: name.toLowerCase().replace(/\s+/g, "-").replace(/[^a-z0-9-]/g, ""),
4150
4640
  validate: (v) => v.length >= 3 || "Must be at least 3 characters"
4151
4641
  }));
4152
4642
  const description = opts.description || (nonInteractive ? `${name} \u2014 a Sherwood syndicate` : await input({
4153
- message: G4("Description"),
4643
+ message: G5("Description"),
4154
4644
  default: `${name} \u2014 a Sherwood syndicate`
4155
4645
  }));
4156
- const agentIdStr = opts.agentId || (savedAgentId ? nonInteractive ? String(savedAgentId) : await input({ message: G4("Agent ID (ERC-8004)"), default: String(savedAgentId) }) : nonInteractive ? "0" : await input({ message: G4("Agent ID (ERC-8004)"), validate: (v) => /^\d+$/.test(v) || "Must be a number" }));
4646
+ const agentIdStr = opts.agentId || (savedAgentId ? nonInteractive ? String(savedAgentId) : await input({ message: G5("Agent ID (ERC-8004)"), default: String(savedAgentId) }) : nonInteractive ? "0" : await input({ message: G5("Agent ID (ERC-8004)"), validate: (v) => /^\d+$/.test(v) || "Must be a number" }));
4157
4647
  const openDeposits = opts.openDeposits !== void 0 ? opts.openDeposits : nonInteractive ? true : await confirm({
4158
- message: G4("Open deposits? (anyone can deposit)"),
4648
+ message: G5("Open deposits? (anyone can deposit)"),
4159
4649
  default: true
4160
4650
  });
4161
4651
  const ASSET_SYMBOLS = {
@@ -4171,14 +4661,14 @@ syndicate.command("create").description("Create a new syndicate via the factory
4171
4661
  asset = opts.asset;
4172
4662
  } else {
4173
4663
  const supported = Object.keys(ASSET_SYMBOLS).join(", ");
4174
- console.error(chalk8.red(` Unknown asset "${opts.asset}". Use a symbol (${supported}) or a 0x address.`));
4664
+ console.error(chalk9.red(` Unknown asset "${opts.asset}". Use a symbol (${supported}) or a 0x address.`));
4175
4665
  process.exit(1);
4176
4666
  }
4177
4667
  } else if (nonInteractive) {
4178
4668
  asset = TOKENS().USDC !== "0x0000000000000000000000000000000000000000" ? ASSET_SYMBOLS.USDC : ASSET_SYMBOLS.WETH;
4179
4669
  } else {
4180
4670
  const assetChoice = await select({
4181
- message: G4("Vault asset (what token do depositors provide?)"),
4671
+ message: G5("Vault asset (what token do depositors provide?)"),
4182
4672
  choices: [
4183
4673
  { name: "USDC", value: "USDC", description: "USD Coin (6 decimals)" },
4184
4674
  { name: "WETH", value: "WETH", description: "Wrapped Ether (18 decimals)" }
@@ -4193,26 +4683,26 @@ syndicate.command("create").description("Create a new syndicate via the factory
4193
4683
  ]);
4194
4684
  const symbol = `sw${assetSymbol}`;
4195
4685
  console.log();
4196
- console.log(LABEL4(" \u25C6 Review"));
4197
- SEP4();
4198
- console.log(W4(` Name: ${BOLD4(name)}`));
4199
- console.log(W4(` ENS: ${G4(`${subdomain}.sherwoodagent.eth`)}`));
4200
- console.log(W4(` Description: ${DIM4(description)}`));
4201
- console.log(W4(` Agent ID: #${agentIdStr}`));
4202
- console.log(W4(` Asset: ${assetSymbol} (${asset.slice(0, 10)}...)`));
4203
- console.log(W4(` Share token: ${symbol}`));
4204
- console.log(W4(` Open deposits: ${openDeposits ? G4("yes") : chalk8.red("no (whitelist)")}`));
4205
- SEP4();
4686
+ console.log(LABEL5(" \u25C6 Review"));
4687
+ SEP5();
4688
+ console.log(W5(` Name: ${BOLD5(name)}`));
4689
+ console.log(W5(` ENS: ${G5(`${subdomain}.sherwoodagent.eth`)}`));
4690
+ console.log(W5(` Description: ${DIM5(description)}`));
4691
+ console.log(W5(` Agent ID: #${agentIdStr}`));
4692
+ console.log(W5(` Asset: ${assetSymbol} (${asset.slice(0, 10)}...)`));
4693
+ console.log(W5(` Share token: ${symbol}`));
4694
+ console.log(W5(` Open deposits: ${openDeposits ? G5("yes") : chalk9.red("no (whitelist)")}`));
4695
+ SEP5();
4206
4696
  if (!nonInteractive) {
4207
- const go = await confirm({ message: G4("Deploy syndicate?"), default: true });
4697
+ const go = await confirm({ message: G5("Deploy syndicate?"), default: true });
4208
4698
  if (!go) {
4209
- console.log(DIM4(" Cancelled."));
4699
+ console.log(DIM5(" Cancelled."));
4210
4700
  return;
4211
4701
  }
4212
4702
  }
4213
4703
  let metadataURI = opts.metadataUri || "";
4214
4704
  if (!metadataURI) {
4215
- const spinner2 = ora7({ text: W4("Uploading metadata to IPFS..."), color: "green" }).start();
4705
+ const spinner2 = ora8({ text: W5("Uploading metadata to IPFS..."), color: "green" }).start();
4216
4706
  try {
4217
4707
  const metadata = {
4218
4708
  schema: "sherwood/syndicate/v1",
@@ -4226,9 +4716,9 @@ syndicate.command("create").description("Create a new syndicate via the factory
4226
4716
  links: {}
4227
4717
  };
4228
4718
  metadataURI = await uploadMetadata(metadata);
4229
- spinner2.succeed(G4(`Metadata pinned: ${DIM4(metadataURI)}`));
4719
+ spinner2.succeed(G5(`Metadata pinned: ${DIM5(metadataURI)}`));
4230
4720
  } catch (err) {
4231
- spinner2.warn(chalk8.yellow(`IPFS upload failed \u2014 using inline metadata`));
4721
+ spinner2.warn(chalk9.yellow(`IPFS upload failed \u2014 using inline metadata`));
4232
4722
  const json = JSON.stringify({ name, description, subdomain, asset: assetSymbol, openDeposits, createdBy: "@sherwoodagent/cli" });
4233
4723
  metadataURI = `data:application/json;base64,${Buffer.from(json).toString("base64")}`;
4234
4724
  }
@@ -4238,43 +4728,43 @@ syndicate.command("create").description("Create a new syndicate via the factory
4238
4728
  const existingInfo = await getSyndicate(existingId);
4239
4729
  const callerAddress = getAccount().address.toLowerCase();
4240
4730
  if (existingInfo.creator.toLowerCase() !== callerAddress) {
4241
- console.error(chalk8.red(`
4731
+ console.error(chalk9.red(`
4242
4732
  \u2716 Subdomain '${subdomain}' is already taken by another syndicate.
4243
4733
  `));
4244
4734
  process.exit(1);
4245
4735
  }
4246
- console.log(chalk8.yellow(`
4736
+ console.log(chalk9.yellow(`
4247
4737
  \u26A0 Syndicate '${subdomain}' already exists \u2014 resuming setup...
4248
4738
  `));
4249
- const spinner2 = ora7({ text: W4("Resuming setup..."), color: "green" }).start();
4739
+ const spinner2 = ora8({ text: W5("Resuming setup..."), color: "green" }).start();
4250
4740
  const chainId2 = getChain().id;
4251
4741
  setChainContract(chainId2, "vault", existingInfo.vault);
4252
4742
  addSyndicate(chainId2, { subdomain, vault: existingInfo.vault, role: "creator" });
4253
4743
  setPrimarySyndicate(chainId2, subdomain);
4254
- spinner2.text = W4("Checking agent registration...");
4744
+ spinner2.text = W5("Checking agent registration...");
4255
4745
  try {
4256
4746
  setVaultAddress(existingInfo.vault);
4257
4747
  const isAlreadyAgent = await isAgent(getAccount().address);
4258
4748
  if (!isAlreadyAgent) {
4259
- spinner2.text = W4("Registering creator as agent...");
4749
+ spinner2.text = W5("Registering creator as agent...");
4260
4750
  await registerAgent(BigInt(agentIdStr), getAccount().address);
4261
4751
  }
4262
4752
  } catch {
4263
4753
  }
4264
- spinner2.text = W4("Checking chat group...");
4754
+ spinner2.text = W5("Checking chat group...");
4265
4755
  try {
4266
4756
  const xmtp = await loadXmtp();
4267
4757
  const xmtpClient = await xmtp.getXmtpClient();
4268
4758
  try {
4269
4759
  await xmtp.getGroup(xmtpClient, subdomain);
4270
4760
  } catch {
4271
- spinner2.text = W4("Creating chat group...");
4761
+ spinner2.text = W5("Creating chat group...");
4272
4762
  const groupId = await xmtp.createSyndicateGroup(xmtpClient, subdomain, opts.publicChat);
4273
4763
  await setTextRecord(subdomain, "xmtpGroupId", groupId, existingInfo.vault);
4274
4764
  cacheGroupId(subdomain, groupId);
4275
4765
  }
4276
4766
  } catch {
4277
- console.warn(chalk8.yellow("\n \u26A0 Could not set up XMTP chat group"));
4767
+ console.warn(chalk9.yellow("\n \u26A0 Could not set up XMTP chat group"));
4278
4768
  }
4279
4769
  try {
4280
4770
  const cron = await loadCron();
@@ -4283,20 +4773,20 @@ syndicate.command("create").description("Create a new syndicate via the factory
4283
4773
  }
4284
4774
  spinner2.stop();
4285
4775
  console.log();
4286
- console.log(LABEL4(" \u25C6 Syndicate Setup Resumed"));
4287
- SEP4();
4288
- console.log(W4(` ID: ${G4(`#${existingId}`)}`));
4289
- console.log(W4(` Vault: ${G4(existingInfo.vault)}`));
4290
- console.log(W4(` ENS: ${G4(`${subdomain}.sherwoodagent.eth`)}`));
4291
- console.log(W4(` Chat: ${DIM4(`sherwood chat ${subdomain}`)}`));
4776
+ console.log(LABEL5(" \u25C6 Syndicate Setup Resumed"));
4777
+ SEP5();
4778
+ console.log(W5(` ID: ${G5(`#${existingId}`)}`));
4779
+ console.log(W5(` Vault: ${G5(existingInfo.vault)}`));
4780
+ console.log(W5(` ENS: ${G5(`${subdomain}.sherwoodagent.eth`)}`));
4781
+ console.log(W5(` Chat: ${DIM5(`sherwood chat ${subdomain}`)}`));
4292
4782
  const refParam2 = getAgentId() ? `?ref=${getAgentId()}` : "";
4293
- console.log(W4(` Share: ${G4(`https://sherwood.sh/syndicate/${subdomain}${refParam2}`)}`));
4294
- SEP4();
4295
- console.log(G4(" \u2713 Syndicate saved to ~/.sherwood/config.json (set as primary)"));
4783
+ console.log(W5(` Share: ${G5(`https://sherwood.sh/syndicate/${subdomain}${refParam2}`)}`));
4784
+ SEP5();
4785
+ console.log(G5(" \u2713 Syndicate saved to ~/.sherwood/config.json (set as primary)"));
4296
4786
  console.log();
4297
4787
  return;
4298
4788
  }
4299
- const spinner = ora7({ text: W4("Deploying vault via factory..."), color: "green" }).start();
4789
+ const spinner = ora8({ text: W5("Deploying vault via factory..."), color: "green" }).start();
4300
4790
  const result = await createSyndicate({
4301
4791
  creatorAgentId: BigInt(agentIdStr),
4302
4792
  metadataURI,
@@ -4311,7 +4801,7 @@ syndicate.command("create").description("Create a new syndicate via the factory
4311
4801
  addSyndicate(chainId, { subdomain, vault: result.vault, role: "creator" });
4312
4802
  setPrimarySyndicate(chainId, subdomain);
4313
4803
  await new Promise((r) => setTimeout(r, 2e3));
4314
- spinner.text = W4("Registering creator as agent...");
4804
+ spinner.text = W5("Registering creator as agent...");
4315
4805
  try {
4316
4806
  setVaultAddress(result.vault);
4317
4807
  const creatorAddress = getAccount().address;
@@ -4321,9 +4811,9 @@ syndicate.command("create").description("Create a new syndicate via the factory
4321
4811
  // agentAddress = creator EOA (direct execution)
4322
4812
  );
4323
4813
  } catch (regErr) {
4324
- console.warn(chalk8.yellow("\n \u26A0 Could not auto-register creator as agent \u2014 register manually with `syndicate add`"));
4814
+ console.warn(chalk9.yellow("\n \u26A0 Could not auto-register creator as agent \u2014 register manually with `syndicate add`"));
4325
4815
  }
4326
- spinner.text = W4("Setting up chat...");
4816
+ spinner.text = W5("Setting up chat...");
4327
4817
  try {
4328
4818
  const xmtp = await loadXmtp();
4329
4819
  const xmtpClient = await xmtp.getXmtpClient();
@@ -4334,42 +4824,42 @@ syndicate.command("create").description("Create a new syndicate via the factory
4334
4824
  } catch {
4335
4825
  }
4336
4826
  } catch {
4337
- console.warn(chalk8.yellow("\n \u26A0 Could not create XMTP chat group"));
4338
- console.warn(chalk8.dim(` Recover later with: sherwood chat ${subdomain} init`));
4827
+ console.warn(chalk9.yellow("\n \u26A0 Could not create XMTP chat group"));
4828
+ console.warn(chalk9.dim(` Recover later with: sherwood chat ${subdomain} init`));
4339
4829
  }
4340
4830
  try {
4341
4831
  const cron = await loadCron();
4342
4832
  const cronResult = cron.registerSyndicateCrons(subdomain, isTestnet(), getNotifyTo());
4343
4833
  if (cronResult.isOpenClaw && cronResult.registered) {
4344
- console.log(G4(" \u2713 Participation crons registered (15m check + hourly summary)"));
4834
+ console.log(G5(" \u2713 Participation crons registered (15m check + hourly summary)"));
4345
4835
  } else if (!cronResult.isOpenClaw) {
4346
- console.log(DIM4(" Tip: Set up a scheduled process to run `sherwood session check " + subdomain + "` periodically"));
4836
+ console.log(DIM5(" Tip: Set up a scheduled process to run `sherwood session check " + subdomain + "` periodically"));
4347
4837
  }
4348
4838
  } catch {
4349
4839
  }
4350
4840
  spinner.stop();
4351
4841
  console.log();
4352
- console.log(LABEL4(" \u25C6 Syndicate Created"));
4353
- SEP4();
4354
- console.log(W4(` ID: ${G4(`#${result.syndicateId}`)}`));
4355
- console.log(W4(` Vault: ${G4(result.vault)}`));
4356
- console.log(W4(` ENS: ${G4(`${subdomain}.sherwoodagent.eth`)}`));
4357
- console.log(W4(` Metadata: ${DIM4(metadataURI.length > 50 ? metadataURI.slice(0, 50) + "..." : metadataURI)}`));
4358
- console.log(W4(` Explorer: ${DIM4(getExplorerUrl(result.hash))}`));
4359
- console.log(W4(` Chat: ${DIM4(`sherwood chat ${subdomain}`)}`));
4842
+ console.log(LABEL5(" \u25C6 Syndicate Created"));
4843
+ SEP5();
4844
+ console.log(W5(` ID: ${G5(`#${result.syndicateId}`)}`));
4845
+ console.log(W5(` Vault: ${G5(result.vault)}`));
4846
+ console.log(W5(` ENS: ${G5(`${subdomain}.sherwoodagent.eth`)}`));
4847
+ console.log(W5(` Metadata: ${DIM5(metadataURI.length > 50 ? metadataURI.slice(0, 50) + "..." : metadataURI)}`));
4848
+ console.log(W5(` Explorer: ${DIM5(getExplorerUrl(result.hash))}`));
4849
+ console.log(W5(` Chat: ${DIM5(`sherwood chat ${subdomain}`)}`));
4360
4850
  const refParam = getAgentId() ? `?ref=${getAgentId()}` : "";
4361
- console.log(W4(` Share: ${G4(`https://sherwood.sh/syndicate/${subdomain}${refParam}`)}`));
4362
- SEP4();
4363
- console.log(G4(" \u2713 Syndicate saved to ~/.sherwood/config.json (set as primary)"));
4851
+ console.log(W5(` Share: ${G5(`https://sherwood.sh/syndicate/${subdomain}${refParam}`)}`));
4852
+ SEP5();
4853
+ console.log(G5(" \u2713 Syndicate saved to ~/.sherwood/config.json (set as primary)"));
4364
4854
  console.log();
4365
4855
  } catch (err) {
4366
- console.error(chalk8.red(`
4856
+ console.error(chalk9.red(`
4367
4857
  \u2716 ${formatContractError(err)}`));
4368
4858
  process.exit(1);
4369
4859
  }
4370
4860
  });
4371
4861
  syndicate.command("list").description("List active syndicates (queries subgraph, falls back to on-chain)").option("--creator <address>", "Filter by creator address").action(async (opts) => {
4372
- const spinner = ora7("Loading syndicates...").start();
4862
+ const spinner = ora8("Loading syndicates...").start();
4373
4863
  try {
4374
4864
  let syndicates;
4375
4865
  if (process.env.SUBGRAPH_URL) {
@@ -4388,39 +4878,39 @@ syndicate.command("list").description("List active syndicates (queries subgraph,
4388
4878
  }
4389
4879
  spinner.stop();
4390
4880
  if (syndicates.length === 0) {
4391
- console.log(chalk8.dim("No active syndicates found."));
4881
+ console.log(chalk9.dim("No active syndicates found."));
4392
4882
  return;
4393
4883
  }
4394
4884
  console.log();
4395
- console.log(chalk8.bold(`Active Syndicates (${syndicates.length})`));
4885
+ console.log(chalk9.bold(`Active Syndicates (${syndicates.length})`));
4396
4886
  if (!process.env.SUBGRAPH_URL) {
4397
- console.log(chalk8.dim(" (Set SUBGRAPH_URL for faster indexed queries)"));
4887
+ console.log(chalk9.dim(" (Set SUBGRAPH_URL for faster indexed queries)"));
4398
4888
  }
4399
- console.log(chalk8.dim("\u2500".repeat(70)));
4889
+ console.log(chalk9.dim("\u2500".repeat(70)));
4400
4890
  for (const s of syndicates) {
4401
4891
  const ts = typeof s.createdAt === "string" ? Number(s.createdAt) : Number(s.createdAt);
4402
4892
  const date = new Date(ts * 1e3).toLocaleDateString();
4403
4893
  const ensName = s.subdomain ? `${s.subdomain}.sherwoodagent.eth` : "";
4404
- console.log(` #${s.id} ${chalk8.bold(ensName || String(s.vault))}`);
4405
- if (ensName) console.log(` Vault: ${chalk8.cyan(String(s.vault))}`);
4894
+ console.log(` #${s.id} ${chalk9.bold(ensName || String(s.vault))}`);
4895
+ if (ensName) console.log(` Vault: ${chalk9.cyan(String(s.vault))}`);
4406
4896
  console.log(` Creator: ${s.creator}`);
4407
4897
  console.log(` Created: ${date}`);
4408
4898
  if (s.totalDeposits) {
4409
4899
  console.log(` Deposits: ${s.totalDeposits} USDC`);
4410
4900
  }
4411
4901
  if (s.metadataURI) {
4412
- console.log(` Metadata: ${chalk8.dim(s.metadataURI)}`);
4902
+ console.log(` Metadata: ${chalk9.dim(s.metadataURI)}`);
4413
4903
  }
4414
4904
  console.log();
4415
4905
  }
4416
4906
  } catch (err) {
4417
4907
  spinner.fail("Failed to load syndicates");
4418
- console.error(chalk8.red(formatContractError(err)));
4908
+ console.error(chalk9.red(formatContractError(err)));
4419
4909
  process.exit(1);
4420
4910
  }
4421
4911
  });
4422
4912
  syndicate.command("info").description("Display syndicate details by ID or subdomain").argument("<id>", "Syndicate ID or subdomain name").action(async (idStr) => {
4423
- const spinner = ora7("Loading syndicate info...").start();
4913
+ const spinner = ora8("Loading syndicate info...").start();
4424
4914
  try {
4425
4915
  let id;
4426
4916
  if (/^\d+$/.test(idStr)) {
@@ -4432,33 +4922,33 @@ syndicate.command("info").description("Display syndicate details by ID or subdom
4432
4922
  const info = await getSyndicate(id);
4433
4923
  spinner.stop();
4434
4924
  if (!info.vault || info.vault === "0x0000000000000000000000000000000000000000") {
4435
- console.log(chalk8.red(`Syndicate #${id} not found.`));
4925
+ console.log(chalk9.red(`Syndicate #${id} not found.`));
4436
4926
  process.exit(1);
4437
4927
  }
4438
4928
  const date = new Date(Number(info.createdAt) * 1e3).toLocaleDateString();
4439
4929
  console.log();
4440
- console.log(chalk8.bold(`Syndicate #${info.id}`));
4441
- console.log(chalk8.dim("\u2500".repeat(40)));
4930
+ console.log(chalk9.bold(`Syndicate #${info.id}`));
4931
+ console.log(chalk9.dim("\u2500".repeat(40)));
4442
4932
  if (info.subdomain) {
4443
- console.log(` ENS: ${chalk8.bold(`${info.subdomain}.sherwoodagent.eth`)}`);
4933
+ console.log(` ENS: ${chalk9.bold(`${info.subdomain}.sherwoodagent.eth`)}`);
4444
4934
  }
4445
- console.log(` Vault: ${chalk8.cyan(info.vault)}`);
4935
+ console.log(` Vault: ${chalk9.cyan(info.vault)}`);
4446
4936
  console.log(` Creator: ${info.creator}`);
4447
4937
  console.log(` Created: ${date}`);
4448
- console.log(` Active: ${info.active ? chalk8.green("yes") : chalk8.red("no")}`);
4938
+ console.log(` Active: ${info.active ? chalk9.green("yes") : chalk9.red("no")}`);
4449
4939
  if (info.metadataURI) {
4450
- console.log(` Metadata: ${chalk8.dim(info.metadataURI)}`);
4940
+ console.log(` Metadata: ${chalk9.dim(info.metadataURI)}`);
4451
4941
  }
4452
4942
  if (info.subdomain) {
4453
4943
  const xmtpGroupId = getCachedGroupId(info.subdomain);
4454
4944
  if (xmtpGroupId) {
4455
- console.log(` XMTP Group: ${chalk8.cyan(xmtpGroupId)}`);
4945
+ console.log(` XMTP Group: ${chalk9.cyan(xmtpGroupId)}`);
4456
4946
  }
4457
4947
  }
4458
4948
  setVaultAddress(info.vault);
4459
4949
  const vaultInfo = await getVaultInfo();
4460
4950
  console.log();
4461
- console.log(chalk8.bold(" Vault Stats"));
4951
+ console.log(chalk9.bold(" Vault Stats"));
4462
4952
  console.log(` Total Assets: ${vaultInfo.totalAssets}`);
4463
4953
  console.log(` Agent Count: ${vaultInfo.agentCount}`);
4464
4954
  console.log(` Redemptions Locked: ${vaultInfo.redemptionsLocked}`);
@@ -4466,12 +4956,12 @@ syndicate.command("info").description("Display syndicate details by ID or subdom
4466
4956
  console.log();
4467
4957
  } catch (err) {
4468
4958
  spinner.fail("Failed to load syndicate info");
4469
- console.error(chalk8.red(formatContractError(err)));
4959
+ console.error(chalk9.red(formatContractError(err)));
4470
4960
  process.exit(1);
4471
4961
  }
4472
4962
  });
4473
4963
  syndicate.command("update-metadata").description("Update syndicate metadata (creator only)").requiredOption("--id <id>", "Syndicate ID").option("--name <name>", "Syndicate name").option("--description <text>", "Short description").option("--uri <uri>", "Direct metadata URI (skips IPFS upload)").action(async (opts) => {
4474
- const spinner = ora7({ text: W4("Loading syndicate..."), color: "green" }).start();
4964
+ const spinner = ora8({ text: W5("Loading syndicate..."), color: "green" }).start();
4475
4965
  try {
4476
4966
  const syndicateId = BigInt(opts.id);
4477
4967
  let metadataURI = opts.uri;
@@ -4483,7 +4973,7 @@ syndicate.command("update-metadata").description("Update syndicate metadata (cre
4483
4973
  }
4484
4974
  const name = opts.name || info.subdomain;
4485
4975
  const description = opts.description || `${name} \u2014 a Sherwood syndicate on ${info.subdomain}.sherwoodagent.eth`;
4486
- spinner.text = W4("Uploading metadata to IPFS...");
4976
+ spinner.text = W5("Uploading metadata to IPFS...");
4487
4977
  const metadata = {
4488
4978
  schema: "sherwood/syndicate/v1",
4489
4979
  name,
@@ -4494,48 +4984,48 @@ syndicate.command("update-metadata").description("Update syndicate metadata (cre
4494
4984
  links: {}
4495
4985
  };
4496
4986
  metadataURI = await uploadMetadata(metadata);
4497
- spinner.text = W4("Updating on-chain metadata...");
4987
+ spinner.text = W5("Updating on-chain metadata...");
4498
4988
  }
4499
4989
  const hash = await updateMetadata(syndicateId, metadataURI);
4500
- spinner.succeed(G4(`Metadata updated`));
4501
- console.log(DIM4(` IPFS: ${metadataURI}`));
4502
- console.log(DIM4(` ${getExplorerUrl(hash)}`));
4990
+ spinner.succeed(G5(`Metadata updated`));
4991
+ console.log(DIM5(` IPFS: ${metadataURI}`));
4992
+ console.log(DIM5(` ${getExplorerUrl(hash)}`));
4503
4993
  } catch (err) {
4504
4994
  spinner.fail("Metadata update failed");
4505
- console.error(chalk8.red(formatContractError(err)));
4995
+ console.error(chalk9.red(formatContractError(err)));
4506
4996
  process.exit(1);
4507
4997
  }
4508
4998
  });
4509
4999
  syndicate.command("approve-depositor").description("Approve an address to deposit (owner only)").option("--vault <address>", "Vault address (default: from config)").requiredOption("--depositor <address>", "Address to approve").action(async (opts) => {
4510
5000
  resolveVault(opts);
4511
- const spinner = ora7("Approving depositor...").start();
5001
+ const spinner = ora8("Approving depositor...").start();
4512
5002
  try {
4513
5003
  const depositor = validateAddress(opts.depositor, "depositor");
4514
5004
  const hash = await approveDepositor(depositor);
4515
5005
  spinner.succeed(`Depositor approved: ${hash}`);
4516
- console.log(chalk8.dim(` ${getExplorerUrl(hash)}`));
5006
+ console.log(chalk9.dim(` ${getExplorerUrl(hash)}`));
4517
5007
  } catch (err) {
4518
5008
  spinner.fail("Approval failed");
4519
- console.error(chalk8.red(formatContractError(err)));
5009
+ console.error(chalk9.red(formatContractError(err)));
4520
5010
  process.exit(1);
4521
5011
  }
4522
5012
  });
4523
5013
  syndicate.command("remove-depositor").description("Remove an address from the depositor whitelist (owner only)").option("--vault <address>", "Vault address (default: from config)").requiredOption("--depositor <address>", "Address to remove").action(async (opts) => {
4524
5014
  resolveVault(opts);
4525
- const spinner = ora7("Removing depositor...").start();
5015
+ const spinner = ora8("Removing depositor...").start();
4526
5016
  try {
4527
5017
  const depositor = validateAddress(opts.depositor, "depositor");
4528
5018
  const hash = await removeDepositor(depositor);
4529
5019
  spinner.succeed(`Depositor removed: ${hash}`);
4530
- console.log(chalk8.dim(` ${getExplorerUrl(hash)}`));
5020
+ console.log(chalk9.dim(` ${getExplorerUrl(hash)}`));
4531
5021
  } catch (err) {
4532
5022
  spinner.fail("Removal failed");
4533
- console.error(chalk8.red(formatContractError(err)));
5023
+ console.error(chalk9.red(formatContractError(err)));
4534
5024
  process.exit(1);
4535
5025
  }
4536
5026
  });
4537
5027
  syndicate.command("add").description("Register an agent on a syndicate vault (creator only)").option("--vault <address>", "Vault address (default: from config)").option("--agent-id <id>", "Agent's ERC-8004 identity token ID (resolved from wallet if omitted)").requiredOption("--wallet <address>", "Agent wallet address").action(async (opts) => {
4538
- const spinner = ora7("Verifying creator...").start();
5028
+ const spinner = ora8("Verifying creator...").start();
4539
5029
  try {
4540
5030
  resolveVault(opts);
4541
5031
  const vaultAddress = getVaultAddress();
@@ -4550,15 +5040,15 @@ syndicate.command("add").description("Register an agent on a syndicate vault (cr
4550
5040
  if (opts.agentId) {
4551
5041
  agentId = BigInt(opts.agentId);
4552
5042
  } else {
4553
- const { AGENT_REGISTRY: AGENT_REGISTRY2 } = await import("./addresses-J4NSZRGB.js");
4554
- const registry = AGENT_REGISTRY2().IDENTITY_REGISTRY;
4555
- if (registry === "0x0000000000000000000000000000000000000000") {
5043
+ const { AGENT_REGISTRY: AGENT_REGISTRY2 } = await import("./addresses-JBIU5U3T.js");
5044
+ const registry2 = AGENT_REGISTRY2().IDENTITY_REGISTRY;
5045
+ if (registry2 === "0x0000000000000000000000000000000000000000") {
4556
5046
  agentId = 0n;
4557
5047
  } else {
4558
5048
  spinner.text = "Looking up ERC-8004 identity from wallet...";
4559
5049
  const client = getPublicClient();
4560
5050
  const balance = await client.readContract({
4561
- address: registry,
5051
+ address: registry2,
4562
5052
  abi: [{
4563
5053
  name: "balanceOf",
4564
5054
  type: "function",
@@ -4571,11 +5061,11 @@ syndicate.command("add").description("Register an agent on a syndicate vault (cr
4571
5061
  });
4572
5062
  if (balance === 0n) {
4573
5063
  spinner.fail("Agent wallet does not own an ERC-8004 identity NFT");
4574
- console.error(chalk8.dim(" Mint one first: sherwood identity mint --name <name>"));
5064
+ console.error(chalk9.dim(" Mint one first: sherwood identity mint --name <name>"));
4575
5065
  process.exit(1);
4576
5066
  }
4577
5067
  const tokenId = await client.readContract({
4578
- address: registry,
5068
+ address: registry2,
4579
5069
  abi: [{
4580
5070
  name: "tokenOfOwnerByIndex",
4581
5071
  type: "function",
@@ -4587,13 +5077,13 @@ syndicate.command("add").description("Register an agent on a syndicate vault (cr
4587
5077
  args: [agentWallet, 0n]
4588
5078
  });
4589
5079
  agentId = tokenId;
4590
- console.log(chalk8.dim(` Resolved agent ID: #${agentId}`));
5080
+ console.log(chalk9.dim(` Resolved agent ID: #${agentId}`));
4591
5081
  }
4592
5082
  }
4593
5083
  spinner.text = "Registering agent...";
4594
5084
  const hash = await registerAgent(agentId, agentWallet);
4595
5085
  spinner.succeed(`Agent registered: ${hash}`);
4596
- console.log(chalk8.dim(` ${getExplorerUrl(hash)}`));
5086
+ console.log(chalk9.dim(` ${getExplorerUrl(hash)}`));
4597
5087
  try {
4598
5088
  const xmtp = await loadXmtp();
4599
5089
  const xmtpClient = await xmtp.getXmtpClient();
@@ -4605,14 +5095,14 @@ syndicate.command("add").description("Register an agent on a syndicate vault (cr
4605
5095
  syndicate: subdomain,
4606
5096
  timestamp: Math.floor(Date.now() / 1e3)
4607
5097
  });
4608
- console.log(chalk8.dim(` Added to chat: ${subdomain}`));
5098
+ console.log(chalk9.dim(` Added to chat: ${subdomain}`));
4609
5099
  } catch {
4610
- console.warn(chalk8.yellow(" \u26A0 Could not add agent to chat group"));
4611
- console.warn(chalk8.dim(` If no group exists, run: sherwood chat ${subdomain} init`));
5100
+ console.warn(chalk9.yellow(" \u26A0 Could not add agent to chat group"));
5101
+ console.warn(chalk9.dim(` If no group exists, run: sherwood chat ${subdomain} init`));
4612
5102
  }
4613
5103
  } catch (err) {
4614
5104
  spinner.fail("Registration failed");
4615
- console.error(chalk8.red(formatContractError(err)));
5105
+ console.error(chalk9.red(formatContractError(err)));
4616
5106
  process.exit(1);
4617
5107
  }
4618
5108
  });
@@ -4620,7 +5110,7 @@ syndicate.command("share").description("Print the shareable dashboard URL for yo
4620
5110
  try {
4621
5111
  const subdomain = opts.subdomain || getPrimarySyndicate(getChain().id)?.subdomain;
4622
5112
  if (!subdomain) {
4623
- console.error(chalk8.red(" No syndicate configured. Pass --subdomain <name> or run 'syndicate create/join' first."));
5113
+ console.error(chalk9.red(" No syndicate configured. Pass --subdomain <name> or run 'syndicate create/join' first."));
4624
5114
  process.exit(1);
4625
5115
  }
4626
5116
  const syndicateInfo = await resolveSyndicate(subdomain);
@@ -4628,13 +5118,13 @@ syndicate.command("share").description("Print the shareable dashboard URL for yo
4628
5118
  const refParam = agentId ? `?ref=${agentId}` : "";
4629
5119
  const dashboardUrl = `https://sherwood.sh/syndicate/${subdomain}${refParam}`;
4630
5120
  console.log();
4631
- console.log(LABEL4(" \u25C6 Share Your Syndicate"));
4632
- SEP4();
4633
- console.log(W4(` Dashboard: ${G4(dashboardUrl)}`));
4634
- console.log(W4(` ENS: ${DIM4(`${subdomain}.sherwoodagent.eth`)}`));
4635
- console.log(W4(` Vault: ${DIM4(syndicateInfo.vault)}`));
4636
- console.log(W4(` Join CLI: ${DIM4(`sherwood syndicate join --subdomain ${subdomain}`)}`));
4637
- SEP4();
5121
+ console.log(LABEL5(" \u25C6 Share Your Syndicate"));
5122
+ SEP5();
5123
+ console.log(W5(` Dashboard: ${G5(dashboardUrl)}`));
5124
+ console.log(W5(` ENS: ${DIM5(`${subdomain}.sherwoodagent.eth`)}`));
5125
+ console.log(W5(` Vault: ${DIM5(syndicateInfo.vault)}`));
5126
+ console.log(W5(` Join CLI: ${DIM5(`sherwood syndicate join --subdomain ${subdomain}`)}`));
5127
+ SEP5();
4638
5128
  try {
4639
5129
  const { exec } = await import("child_process");
4640
5130
  const platform = (await import("os")).platform();
@@ -4642,17 +5132,17 @@ syndicate.command("share").description("Print the shareable dashboard URL for yo
4642
5132
  const proc = exec(cmd);
4643
5133
  proc.stdin?.write(dashboardUrl);
4644
5134
  proc.stdin?.end();
4645
- console.log(G4(" \u2713 Dashboard URL copied to clipboard"));
5135
+ console.log(G5(" \u2713 Dashboard URL copied to clipboard"));
4646
5136
  } catch {
4647
5137
  }
4648
5138
  console.log();
4649
5139
  } catch (err) {
4650
- console.error(chalk8.red(` \u2716 ${formatContractError(err)}`));
5140
+ console.error(chalk9.red(` \u2716 ${formatContractError(err)}`));
4651
5141
  process.exit(1);
4652
5142
  }
4653
5143
  });
4654
5144
  syndicate.command("join").description("Request to join a syndicate (creates an EAS attestation)").option("--subdomain <name>", "Syndicate subdomain to join").option("--ref <agentId>", "Referrer agent ID (from invite link)").option("--message <text>", "Message to the creator", "Requesting to join your syndicate").action(async (opts) => {
4655
- const spinner = ora7("Resolving syndicate...").start();
5145
+ const spinner = ora8("Resolving syndicate...").start();
4656
5146
  try {
4657
5147
  const subdomain = opts.subdomain || getPrimarySyndicate(getChain().id)?.subdomain;
4658
5148
  if (!subdomain) {
@@ -4674,17 +5164,17 @@ syndicate.command("join").description("Request to join a syndicate (creates an E
4674
5164
  try {
4675
5165
  const xmtp = await loadXmtp();
4676
5166
  await xmtp.getXmtpClient();
4677
- console.log(chalk8.dim(" XMTP identity ready"));
5167
+ console.log(chalk9.dim(" XMTP identity ready"));
4678
5168
  } catch {
4679
- console.warn(chalk8.yellow(" \u26A0 Could not initialize XMTP identity"));
5169
+ console.warn(chalk9.yellow(" \u26A0 Could not initialize XMTP identity"));
4680
5170
  }
4681
5171
  try {
4682
5172
  const cron = await loadCron();
4683
5173
  const cronResult = cron.registerSyndicateCrons(subdomain, isTestnet(), getNotifyTo());
4684
5174
  if (cronResult.isOpenClaw && cronResult.registered) {
4685
- console.log(chalk8.green(" \u2713 Participation crons registered"));
5175
+ console.log(chalk9.green(" \u2713 Participation crons registered"));
4686
5176
  } else if (!cronResult.isOpenClaw) {
4687
- console.log(chalk8.dim(" Tip: Set up a scheduled process to run `sherwood session check " + subdomain + "` periodically"));
5177
+ console.log(chalk9.dim(" Tip: Set up a scheduled process to run `sherwood session check " + subdomain + "` periodically"));
4688
5178
  }
4689
5179
  } catch {
4690
5180
  }
@@ -4697,14 +5187,14 @@ syndicate.command("join").description("Request to join a syndicate (creates an E
4697
5187
  );
4698
5188
  if (existingRequest) {
4699
5189
  spinner.succeed("You already have a pending join request for this syndicate");
4700
- console.log(chalk8.dim(` Attestation: ${existingRequest.uid}`));
4701
- console.log(chalk8.dim(` Submitted: ${new Date(existingRequest.time * 1e3).toLocaleString()}`));
5190
+ console.log(chalk9.dim(` Attestation: ${existingRequest.uid}`));
5191
+ console.log(chalk9.dim(` Submitted: ${new Date(existingRequest.time * 1e3).toLocaleString()}`));
4702
5192
  try {
4703
5193
  const xmtp = await loadXmtp();
4704
5194
  await xmtp.getXmtpClient();
4705
- console.log(chalk8.dim(" XMTP identity ready"));
5195
+ console.log(chalk9.dim(" XMTP identity ready"));
4706
5196
  } catch {
4707
- console.warn(chalk8.yellow(" \u26A0 Could not initialize XMTP identity"));
5197
+ console.warn(chalk9.yellow(" \u26A0 Could not initialize XMTP identity"));
4708
5198
  }
4709
5199
  return;
4710
5200
  }
@@ -4725,7 +5215,7 @@ syndicate.command("join").description("Request to join a syndicate (creates an E
4725
5215
  spinner.succeed("Join request created (XMTP identity ready)");
4726
5216
  } catch {
4727
5217
  spinner.succeed("Join request created");
4728
- console.warn(chalk8.yellow(" \u26A0 Could not initialize XMTP identity \u2014 creator may not be able to auto-add you to chat"));
5218
+ console.warn(chalk9.yellow(" \u26A0 Could not initialize XMTP identity \u2014 creator may not be able to auto-add you to chat"));
4729
5219
  }
4730
5220
  addSyndicate(getChain().id, { subdomain, vault: syndicate2.vault, role: "agent" });
4731
5221
  setPrimarySyndicate(getChain().id, subdomain);
@@ -4733,34 +5223,34 @@ syndicate.command("join").description("Request to join a syndicate (creates an E
4733
5223
  const cron = await loadCron();
4734
5224
  const cronResult = cron.registerSyndicateCrons(subdomain, isTestnet(), getNotifyTo());
4735
5225
  if (cronResult.isOpenClaw && cronResult.registered) {
4736
- console.log(G4(" \u2713 Participation crons registered (will activate after approval)"));
5226
+ console.log(G5(" \u2713 Participation crons registered (will activate after approval)"));
4737
5227
  } else if (!cronResult.isOpenClaw) {
4738
- console.log(DIM4(" Tip: Set up a scheduled process to run `sherwood session check " + subdomain + "` periodically"));
5228
+ console.log(DIM5(" Tip: Set up a scheduled process to run `sherwood session check " + subdomain + "` periodically"));
4739
5229
  }
4740
5230
  } catch {
4741
5231
  }
4742
5232
  console.log();
4743
- console.log(LABEL4(" \u25C6 Join Request Submitted"));
4744
- SEP4();
4745
- console.log(W4(` Syndicate: ${G4(`${subdomain}.sherwoodagent.eth`)}`));
4746
- console.log(W4(` Agent ID: #${agentId}`));
4747
- console.log(W4(` Creator: ${DIM4(syndicate2.creator)}`));
4748
- console.log(W4(` Attestation: ${DIM4(uid)}`));
4749
- console.log(W4(` EAS Scan: ${DIM4(getEasScanUrl(uid))}`));
4750
- console.log(W4(` Explorer: ${DIM4(getExplorerUrl(hash))}`));
4751
- SEP4();
4752
- console.log(G4(" \u2713 Syndicate saved to ~/.sherwood/config.json (set as primary)"));
4753
- console.log(G4(" \u2713 The creator can review with:"));
4754
- console.log(DIM4(` sherwood syndicate requests --subdomain ${subdomain}`));
5233
+ console.log(LABEL5(" \u25C6 Join Request Submitted"));
5234
+ SEP5();
5235
+ console.log(W5(` Syndicate: ${G5(`${subdomain}.sherwoodagent.eth`)}`));
5236
+ console.log(W5(` Agent ID: #${agentId}`));
5237
+ console.log(W5(` Creator: ${DIM5(syndicate2.creator)}`));
5238
+ console.log(W5(` Attestation: ${DIM5(uid)}`));
5239
+ console.log(W5(` EAS Scan: ${DIM5(getEasScanUrl(uid))}`));
5240
+ console.log(W5(` Explorer: ${DIM5(getExplorerUrl(hash))}`));
5241
+ SEP5();
5242
+ console.log(G5(" \u2713 Syndicate saved to ~/.sherwood/config.json (set as primary)"));
5243
+ console.log(G5(" \u2713 The creator can review with:"));
5244
+ console.log(DIM5(` sherwood syndicate requests --subdomain ${subdomain}`));
4755
5245
  console.log();
4756
5246
  } catch (err) {
4757
5247
  spinner.fail("Join request failed");
4758
- console.error(chalk8.red(formatContractError(err)));
5248
+ console.error(chalk9.red(formatContractError(err)));
4759
5249
  process.exit(1);
4760
5250
  }
4761
5251
  });
4762
5252
  syndicate.command("requests").description("View pending join requests for a syndicate (creator only)").option("--subdomain <name>", "Syndicate subdomain").option("--vault <address>", "Vault address (default: from config)").action(async (opts) => {
4763
- const spinner = ora7("Loading join requests...").start();
5253
+ const spinner = ora8("Loading join requests...").start();
4764
5254
  try {
4765
5255
  let creatorAddress;
4766
5256
  let subdomain;
@@ -4796,39 +5286,39 @@ syndicate.command("requests").description("View pending join requests for a synd
4796
5286
  );
4797
5287
  spinner.stop();
4798
5288
  if (requests.length === 0) {
4799
- console.log(DIM4("\n No pending join requests.\n"));
5289
+ console.log(DIM5("\n No pending join requests.\n"));
4800
5290
  return;
4801
5291
  }
4802
5292
  console.log();
4803
- console.log(LABEL4(` \u25C6 Pending Join Requests (${requests.length})`));
4804
- SEP4();
5293
+ console.log(LABEL5(` \u25C6 Pending Join Requests (${requests.length})`));
5294
+ SEP5();
4805
5295
  for (let i = 0; i < requests.length; i++) {
4806
5296
  const req = requests[i];
4807
5297
  const date = new Date(req.time * 1e3).toLocaleString();
4808
5298
  const referrer = parseReferrer(req.decoded.message);
4809
5299
  const cleanMessage = stripReferrerPrefix(req.decoded.message);
4810
- console.log(W4(` ${i + 1}. Agent #${req.decoded.agentId} ${DIM4(`(${req.attester})`)}`));
4811
- console.log(DIM4(` Message: "${cleanMessage}"`));
5300
+ console.log(W5(` ${i + 1}. Agent #${req.decoded.agentId} ${DIM5(`(${req.attester})`)}`));
5301
+ console.log(DIM5(` Message: "${cleanMessage}"`));
4812
5302
  if (referrer !== null) {
4813
- console.log(G4(` Referred by: Agent #${referrer}`));
5303
+ console.log(G5(` Referred by: Agent #${referrer}`));
4814
5304
  }
4815
- console.log(DIM4(` Requested: ${date}`));
4816
- console.log(DIM4(` Attestation: ${req.uid}`));
5305
+ console.log(DIM5(` Requested: ${date}`));
5306
+ console.log(DIM5(` Attestation: ${req.uid}`));
4817
5307
  console.log();
4818
5308
  }
4819
- console.log(G4(" To approve:"));
4820
- console.log(DIM4(` sherwood syndicate approve --agent-id <id> --wallet <addr>`));
4821
- console.log(G4(" To reject:"));
4822
- console.log(DIM4(` sherwood syndicate reject --attestation <uid>`));
5309
+ console.log(G5(" To approve:"));
5310
+ console.log(DIM5(` sherwood syndicate approve --agent-id <id> --wallet <addr>`));
5311
+ console.log(G5(" To reject:"));
5312
+ console.log(DIM5(` sherwood syndicate reject --attestation <uid>`));
4823
5313
  console.log();
4824
5314
  } catch (err) {
4825
5315
  spinner.fail("Failed to load requests");
4826
- console.error(chalk8.red(formatContractError(err)));
5316
+ console.error(chalk9.red(formatContractError(err)));
4827
5317
  process.exit(1);
4828
5318
  }
4829
5319
  });
4830
5320
  syndicate.command("approve").description("Approve an agent join request (registers agent + creates EAS approval)").option("--vault <address>", "Vault address (default: from config)").option("--subdomain <name>", "Syndicate subdomain (alternative to --vault)").requiredOption("--agent-id <id>", "Agent's ERC-8004 identity token ID").requiredOption("--wallet <address>", "Agent wallet address").action(async (opts) => {
4831
- const spinner = ora7("Verifying creator...").start();
5321
+ const spinner = ora8("Verifying creator...").start();
4832
5322
  try {
4833
5323
  const approveSubdomain = opts.subdomain || getPrimarySyndicate(getChain().id)?.subdomain;
4834
5324
  if (approveSubdomain && !opts.vault) {
@@ -4853,11 +5343,11 @@ syndicate.command("approve").description("Approve an agent join request (registe
4853
5343
  agentWallet
4854
5344
  );
4855
5345
  agentWasRegistered = true;
4856
- console.log(DIM4(` Agent registered: ${getExplorerUrl(regHash)}`));
5346
+ console.log(DIM5(` Agent registered: ${getExplorerUrl(regHash)}`));
4857
5347
  } catch (regErr) {
4858
5348
  const msg = regErr instanceof Error ? regErr.message : String(regErr);
4859
5349
  if (msg.includes("0xe098d3ee") || msg.includes("AgentAlreadyRegistered")) {
4860
- console.log(DIM4(" Agent already registered on vault \u2014 skipping"));
5350
+ console.log(DIM5(" Agent already registered on vault \u2014 skipping"));
4861
5351
  } else {
4862
5352
  throw regErr;
4863
5353
  }
@@ -4873,7 +5363,7 @@ syndicate.command("approve").description("Approve an agent join request (registe
4873
5363
  let approvalUid;
4874
5364
  if (alreadyApproved) {
4875
5365
  approvalUid = alreadyApproved.uid;
4876
- console.log(DIM4(` Approval attestation already exists \u2014 skipping`));
5366
+ console.log(DIM5(` Approval attestation already exists \u2014 skipping`));
4877
5367
  } else {
4878
5368
  spinner.text = "Creating approval attestation...";
4879
5369
  const result = await createApproval(
@@ -4896,48 +5386,48 @@ syndicate.command("approve").description("Approve an agent join request (registe
4896
5386
  syndicate: subdomain,
4897
5387
  timestamp: Math.floor(Date.now() / 1e3)
4898
5388
  });
4899
- console.log(DIM4(` Added to chat: ${subdomain}`));
5389
+ console.log(DIM5(` Added to chat: ${subdomain}`));
4900
5390
  } catch {
4901
- console.warn(chalk8.yellow(" \u26A0 Could not add agent to chat group"));
4902
- console.warn(chalk8.dim(` If no group exists, run: sherwood chat ${subdomain} init`));
5391
+ console.warn(chalk9.yellow(" \u26A0 Could not add agent to chat group"));
5392
+ console.warn(chalk9.dim(` If no group exists, run: sherwood chat ${subdomain} init`));
4903
5393
  }
4904
5394
  spinner.succeed("Agent approved and registered");
4905
5395
  console.log();
4906
- console.log(LABEL4(" \u25C6 Agent Approved"));
4907
- SEP4();
4908
- console.log(W4(` Agent ID: #${opts.agentId}`));
4909
- console.log(W4(` Wallet: ${G4(opts.wallet)}`));
4910
- console.log(W4(` Approval: ${DIM4(approvalUid)}`));
4911
- console.log(W4(` EAS Scan: ${DIM4(getEasScanUrl(approvalUid))}`));
4912
- SEP4();
5396
+ console.log(LABEL5(" \u25C6 Agent Approved"));
5397
+ SEP5();
5398
+ console.log(W5(` Agent ID: #${opts.agentId}`));
5399
+ console.log(W5(` Wallet: ${G5(opts.wallet)}`));
5400
+ console.log(W5(` Approval: ${DIM5(approvalUid)}`));
5401
+ console.log(W5(` EAS Scan: ${DIM5(getEasScanUrl(approvalUid))}`));
5402
+ SEP5();
4913
5403
  } catch (err) {
4914
5404
  spinner.fail("Approval failed");
4915
- console.error(chalk8.red(formatContractError(err)));
5405
+ console.error(chalk9.red(formatContractError(err)));
4916
5406
  process.exit(1);
4917
5407
  }
4918
5408
  });
4919
5409
  syndicate.command("reject").description("Reject a join request by revoking its attestation").requiredOption("--attestation <uid>", "Join request attestation UID to revoke").action(async (opts) => {
4920
- const spinner = ora7("Revoking attestation...").start();
5410
+ const spinner = ora8("Revoking attestation...").start();
4921
5411
  try {
4922
5412
  const hash = await revokeAttestation(
4923
5413
  EAS_SCHEMAS().SYNDICATE_JOIN_REQUEST,
4924
5414
  opts.attestation
4925
5415
  );
4926
5416
  spinner.succeed("Join request rejected");
4927
- console.log(DIM4(` ${getExplorerUrl(hash)}`));
5417
+ console.log(DIM5(` ${getExplorerUrl(hash)}`));
4928
5418
  } catch (err) {
4929
5419
  spinner.fail("Rejection failed");
4930
- console.error(chalk8.red(formatContractError(err)));
5420
+ console.error(chalk9.red(formatContractError(err)));
4931
5421
  process.exit(1);
4932
5422
  }
4933
5423
  });
4934
5424
  syndicate.command("leave").description("Leave a syndicate \u2014 removes participation crons and session state").option("--subdomain <name>", "Syndicate subdomain to leave").action(async (opts) => {
4935
5425
  const subdomain = opts.subdomain || getPrimarySyndicate(getChain().id)?.subdomain;
4936
5426
  if (!subdomain) {
4937
- console.error(chalk8.red(" No syndicate configured. Pass --subdomain <name>."));
5427
+ console.error(chalk9.red(" No syndicate configured. Pass --subdomain <name>."));
4938
5428
  process.exit(1);
4939
5429
  }
4940
- const spinner = ora7("Cleaning up...").start();
5430
+ const spinner = ora8("Cleaning up...").start();
4941
5431
  try {
4942
5432
  let cronsRemoved = false;
4943
5433
  try {
@@ -4950,17 +5440,17 @@ syndicate.command("leave").description("Leave a syndicate \u2014 removes partici
4950
5440
  resetSession(subdomain);
4951
5441
  spinner.succeed("Left syndicate");
4952
5442
  if (cronsRemoved) {
4953
- console.log(G4(" \u2713 Participation crons removed"));
5443
+ console.log(G5(" \u2713 Participation crons removed"));
4954
5444
  }
4955
- console.log(G4(" \u2713 Session state cleared"));
5445
+ console.log(G5(" \u2713 Session state cleared"));
4956
5446
  console.log();
4957
- console.log(chalk8.dim(" Note: This does not remove you on-chain. To exit your position:"));
4958
- console.log(chalk8.dim(" sherwood vault balance \u2014 check your LP share balance"));
4959
- console.log(chalk8.dim(" Redeem shares via the vault contract or dashboard"));
5447
+ console.log(chalk9.dim(" Note: This does not remove you on-chain. To exit your position:"));
5448
+ console.log(chalk9.dim(" sherwood vault balance \u2014 check your LP share balance"));
5449
+ console.log(chalk9.dim(" Redeem shares via the vault contract or dashboard"));
4960
5450
  console.log();
4961
5451
  } catch (err) {
4962
5452
  spinner.fail("Leave failed");
4963
- console.error(chalk8.red(err instanceof Error ? err.message : String(err)));
5453
+ console.error(chalk9.red(err instanceof Error ? err.message : String(err)));
4964
5454
  process.exit(1);
4965
5455
  }
4966
5456
  });
@@ -4971,21 +5461,21 @@ syndicate.command("set-primary").description("Set the active syndicate for CLI c
4971
5461
  if (!opts.subdomain && !opts.vault) {
4972
5462
  const primary = getPrimarySyndicate(chainId);
4973
5463
  if (memberships.length === 0) {
4974
- console.log(DIM4("\n No syndicates saved. Create or join one first.\n"));
5464
+ console.log(DIM5("\n No syndicates saved. Create or join one first.\n"));
4975
5465
  return;
4976
5466
  }
4977
5467
  console.log();
4978
- console.log(LABEL4(" \u25C6 Your Syndicates"));
4979
- SEP4();
5468
+ console.log(LABEL5(" \u25C6 Your Syndicates"));
5469
+ SEP5();
4980
5470
  for (const m of memberships) {
4981
5471
  const isPrimary = primary?.subdomain === m.subdomain;
4982
- const marker = isPrimary ? G4(" \u2605") : "";
4983
- console.log(W4(` ${m.subdomain}.sherwoodagent.eth${marker} ${DIM4(`(${m.role})`)}`));
4984
- console.log(DIM4(` vault: ${m.vault}`));
5472
+ const marker = isPrimary ? G5(" \u2605") : "";
5473
+ console.log(W5(` ${m.subdomain}.sherwoodagent.eth${marker} ${DIM5(`(${m.role})`)}`));
5474
+ console.log(DIM5(` vault: ${m.vault}`));
4985
5475
  }
4986
- SEP4();
5476
+ SEP5();
4987
5477
  if (memberships.length > 1) {
4988
- console.log(DIM4(" Switch with: sherwood syndicate set-primary --subdomain <name>"));
5478
+ console.log(DIM5(" Switch with: sherwood syndicate set-primary --subdomain <name>"));
4989
5479
  }
4990
5480
  console.log();
4991
5481
  return;
@@ -5011,15 +5501,15 @@ syndicate.command("set-primary").description("Set the active syndicate for CLI c
5011
5501
  }
5012
5502
  }
5013
5503
  if (!target) {
5014
- console.error(chalk8.red(" Could not resolve syndicate. Pass --subdomain or --vault."));
5504
+ console.error(chalk9.red(" Could not resolve syndicate. Pass --subdomain or --vault."));
5015
5505
  process.exit(1);
5016
5506
  }
5017
5507
  setPrimarySyndicate(chainId, target);
5018
- console.log(G4(`
5508
+ console.log(G5(`
5019
5509
  \u2713 Primary syndicate set to ${target}.sherwoodagent.eth
5020
5510
  `));
5021
5511
  } catch (err) {
5022
- console.error(chalk8.red(formatContractError(err)));
5512
+ console.error(chalk9.red(formatContractError(err)));
5023
5513
  process.exit(1);
5024
5514
  }
5025
5515
  });
@@ -5027,18 +5517,18 @@ var vaultCmd = program.command("vault");
5027
5517
  vaultCmd.command("deposit").description("Deposit into a vault").option("--vault <address>", "Vault address (default: from config)").requiredOption("--amount <amount>", "Amount to deposit (in asset units)").option("--use-eth", "Auto-wrap ETH \u2192 WETH before depositing (for WETH vaults)").action(async (opts) => {
5028
5518
  resolveVault(opts);
5029
5519
  const decimals = await getAssetDecimals();
5030
- const amount = parseUnits4(opts.amount, decimals);
5520
+ const amount = parseUnits6(opts.amount, decimals);
5031
5521
  try {
5032
5522
  if (!opts.useEth) {
5033
5523
  await preflightDeposit(amount);
5034
5524
  }
5035
5525
  } catch (err) {
5036
- console.error(chalk8.red(`
5526
+ console.error(chalk9.red(`
5037
5527
  \u2716 ${err instanceof Error ? err.message : String(err)}
5038
5528
  `));
5039
5529
  process.exit(1);
5040
5530
  }
5041
- const spinner = ora7(`Depositing ${opts.amount}...`).start();
5531
+ const spinner = ora8(`Depositing ${opts.amount}...`).start();
5042
5532
  try {
5043
5533
  let hash;
5044
5534
  if (opts.useEth) {
@@ -5048,22 +5538,22 @@ vaultCmd.command("deposit").description("Deposit into a vault").option("--vault
5048
5538
  hash = await deposit(amount);
5049
5539
  }
5050
5540
  spinner.succeed(`Deposited: ${hash}`);
5051
- console.log(chalk8.dim(` ${getExplorerUrl(hash)}`));
5541
+ console.log(chalk9.dim(` ${getExplorerUrl(hash)}`));
5052
5542
  } catch (err) {
5053
5543
  spinner.fail("Deposit failed");
5054
- console.error(chalk8.red(formatContractError(err)));
5544
+ console.error(chalk9.red(formatContractError(err)));
5055
5545
  process.exit(1);
5056
5546
  }
5057
5547
  });
5058
5548
  vaultCmd.command("info").description("Display vault state").option("--vault <address>", "Vault address (default: from config)").action(async (opts) => {
5059
5549
  resolveVault(opts);
5060
- const spinner = ora7("Loading vault info...").start();
5550
+ const spinner = ora8("Loading vault info...").start();
5061
5551
  try {
5062
5552
  const info = await getVaultInfo();
5063
5553
  spinner.stop();
5064
5554
  console.log();
5065
- console.log(chalk8.bold("Vault Info"));
5066
- console.log(chalk8.dim("\u2500".repeat(40)));
5555
+ console.log(chalk9.bold("Vault Info"));
5556
+ console.log(chalk9.dim("\u2500".repeat(40)));
5067
5557
  console.log(` Address: ${info.address}`);
5068
5558
  console.log(` Total Assets: ${info.totalAssets}`);
5069
5559
  console.log(` Agent Count: ${info.agentCount}`);
@@ -5072,26 +5562,26 @@ vaultCmd.command("info").description("Display vault state").option("--vault <add
5072
5562
  console.log();
5073
5563
  } catch (err) {
5074
5564
  spinner.fail("Failed to load vault info");
5075
- console.error(chalk8.red(formatContractError(err)));
5565
+ console.error(chalk9.red(formatContractError(err)));
5076
5566
  process.exit(1);
5077
5567
  }
5078
5568
  });
5079
5569
  vaultCmd.command("balance").description("Show LP share balance and asset value").option("--vault <address>", "Vault address (default: from config)").option("--address <address>", "Address to check (default: your wallet)").action(async (opts) => {
5080
5570
  resolveVault(opts);
5081
- const spinner = ora7("Loading balance...").start();
5571
+ const spinner = ora8("Loading balance...").start();
5082
5572
  try {
5083
5573
  const balance = await getBalance(opts.address);
5084
5574
  spinner.stop();
5085
5575
  console.log();
5086
- console.log(chalk8.bold("LP Position"));
5087
- console.log(chalk8.dim("\u2500".repeat(40)));
5576
+ console.log(chalk9.bold("LP Position"));
5577
+ console.log(chalk9.dim("\u2500".repeat(40)));
5088
5578
  console.log(` Shares: ${balance.shares.toString()}`);
5089
5579
  console.log(` Asset Value: ${balance.assetsValue}`);
5090
5580
  console.log(` % of Vault: ${balance.percentOfVault}`);
5091
5581
  console.log();
5092
5582
  } catch (err) {
5093
5583
  spinner.fail("Failed to load balance");
5094
- console.error(chalk8.red(formatContractError(err)));
5584
+ console.error(chalk9.red(formatContractError(err)));
5095
5585
  process.exit(1);
5096
5586
  }
5097
5587
  });
@@ -5102,22 +5592,22 @@ vaultCmd.command("redeem").description("Redeem vault shares for the underlying a
5102
5592
  let shares;
5103
5593
  try {
5104
5594
  if (opts.shares) {
5105
- shares = parseUnits4(opts.shares, shareDecimals);
5595
+ shares = parseUnits6(opts.shares, shareDecimals);
5106
5596
  } else {
5107
5597
  shares = await getShareBalance();
5108
5598
  if (shares === 0n) {
5109
- console.error(chalk8.red("\n \u2716 No shares to redeem.\n"));
5599
+ console.error(chalk9.red("\n \u2716 No shares to redeem.\n"));
5110
5600
  process.exit(1);
5111
5601
  }
5112
5602
  }
5113
5603
  } catch (err) {
5114
- console.error(chalk8.red(`
5604
+ console.error(chalk9.red(`
5115
5605
  \u2716 ${err instanceof Error ? err.message : String(err)}
5116
5606
  `));
5117
5607
  process.exit(1);
5118
5608
  }
5119
- if (opts.receiver && !isAddress5(opts.receiver)) {
5120
- console.error(chalk8.red(`
5609
+ if (opts.receiver && !isAddress6(opts.receiver)) {
5610
+ console.error(chalk9.red(`
5121
5611
  \u2716 Invalid receiver address: ${opts.receiver}
5122
5612
  `));
5123
5613
  process.exit(1);
@@ -5125,24 +5615,24 @@ vaultCmd.command("redeem").description("Redeem vault shares for the underlying a
5125
5615
  try {
5126
5616
  await preflightRedeem(shares);
5127
5617
  } catch (err) {
5128
- console.error(chalk8.red(`
5618
+ console.error(chalk9.red(`
5129
5619
  \u2716 ${err instanceof Error ? err.message : String(err)}
5130
5620
  `));
5131
5621
  process.exit(1);
5132
5622
  }
5133
- const sharesDisplay = formatUnits4(shares, shareDecimals);
5134
- const spinner = ora7(`Redeeming ${sharesDisplay} shares...`).start();
5623
+ const sharesDisplay = formatUnits5(shares, shareDecimals);
5624
+ const spinner = ora8(`Redeeming ${sharesDisplay} shares...`).start();
5135
5625
  try {
5136
5626
  const { hash, assetsOut } = await redeem(
5137
5627
  shares,
5138
5628
  opts.receiver
5139
5629
  );
5140
5630
  spinner.succeed(`Redeemed: ${hash}`);
5141
- console.log(chalk8.dim(` ${getExplorerUrl(hash)}`));
5142
- console.log(` Assets received: ${formatUnits4(assetsOut, assetDecimals)}`);
5631
+ console.log(chalk9.dim(` ${getExplorerUrl(hash)}`));
5632
+ console.log(` Assets received: ${formatUnits5(assetsOut, assetDecimals)}`);
5143
5633
  } catch (err) {
5144
5634
  spinner.fail("Redeem failed");
5145
- console.error(chalk8.red(formatContractError(err)));
5635
+ console.error(chalk9.red(formatContractError(err)));
5146
5636
  process.exit(1);
5147
5637
  }
5148
5638
  });
@@ -5160,28 +5650,29 @@ ${info.name} (${info.type})`);
5160
5650
  }
5161
5651
  });
5162
5652
  try {
5163
- const { registerChatCommands } = await import("./chat-EYCDCZUA.js");
5653
+ const { registerChatCommands } = await import("./chat-3GE6474H.js");
5164
5654
  registerChatCommands(program);
5165
5655
  } catch {
5166
5656
  program.command("chat <name> [action] [actionArgs...]").description("Syndicate chat (XMTP) \u2014 requires @xmtp/cli").action(() => {
5167
- console.error(chalk8.red("XMTP CLI not available."));
5168
- console.error(chalk8.dim("Install with: npm install -g @xmtp/cli"));
5169
- console.error(chalk8.dim("Or reinstall: npm i -g @sherwoodagent/cli"));
5657
+ console.error(chalk9.red("XMTP CLI not available."));
5658
+ console.error(chalk9.dim("Install with: npm install -g @xmtp/cli"));
5659
+ console.error(chalk9.dim("Or reinstall: npm i -g @sherwoodagent/cli"));
5170
5660
  process.exit(1);
5171
5661
  });
5172
5662
  }
5173
- var { registerSessionCommands } = await import("./session-NL6KF2Q5.js");
5663
+ var { registerSessionCommands } = await import("./session-EST3O7W3.js");
5174
5664
  registerSessionCommands(program);
5175
5665
  registerVeniceCommands(program);
5176
5666
  registerAllowanceCommands(program);
5177
5667
  registerIdentityCommands(program);
5178
5668
  registerProposalCommands(program);
5179
5669
  registerGovernorCommands(program);
5180
- var { registerResearchCommands } = await import("./research-HXOXZA4N.js");
5670
+ registerGuardianCommands(program);
5671
+ var { registerResearchCommands } = await import("./research-HDEPP2SL.js");
5181
5672
  registerResearchCommands(program);
5182
- var { registerAgentCommands } = await import("./agent-XBYSALOA.js");
5673
+ var { registerAgentCommands } = await import("./agent-LBF6OZRW.js");
5183
5674
  registerAgentCommands(program);
5184
- var { registerTradeCommands } = await import("./trade-WMPWF6RT.js");
5675
+ var { registerTradeCommands } = await import("./trade-XTLUZJB6.js");
5185
5676
  registerTradeCommands(program);
5186
5677
  var configCmd = program.command("config");
5187
5678
  configCmd.command("set").description("Save settings to ~/.sherwood/config.json (persists across sessions)").option("--private-key <key>", "Wallet private key (0x-prefixed)").option("--vault <address>", "Default SyndicateVault address").option("--rpc <url>", "Custom RPC URL for the active --chain network").option("--notify-to <id>", "Destination for cron summaries (Telegram chat ID, phone, etc.)").option("--uniswap-api-key <key>", "Uniswap Trading API key (from developers.uniswap.org)").option("--venice-api-key <key>", "Venice AI inference API key").option("--xmtp-group <subdomain:groupId>", "Cache an XMTP group ID for a syndicate (e.g. my-fund:abc123)").action((opts) => {
@@ -5189,53 +5680,53 @@ configCmd.command("set").description("Save settings to ~/.sherwood/config.json (
5189
5680
  if (opts.privateKey) {
5190
5681
  setPrivateKey(opts.privateKey);
5191
5682
  const account = getAccount();
5192
- console.log(chalk8.green("Private key saved to ~/.sherwood/config.json"));
5193
- console.log(chalk8.dim(` Wallet: ${account.address}`));
5683
+ console.log(chalk9.green("Private key saved to ~/.sherwood/config.json"));
5684
+ console.log(chalk9.dim(` Wallet: ${account.address}`));
5194
5685
  saved = true;
5195
5686
  }
5196
5687
  if (opts.vault) {
5197
5688
  const chainId = getChain().id;
5198
5689
  setChainContract(chainId, "vault", opts.vault);
5199
- console.log(chalk8.green(`Vault saved to ~/.sherwood/config.json (chain ${chainId})`));
5200
- console.log(chalk8.dim(` Vault: ${opts.vault}`));
5690
+ console.log(chalk9.green(`Vault saved to ~/.sherwood/config.json (chain ${chainId})`));
5691
+ console.log(chalk9.dim(` Vault: ${opts.vault}`));
5201
5692
  saved = true;
5202
5693
  }
5203
5694
  if (opts.rpc) {
5204
5695
  const network = getNetwork();
5205
5696
  setConfigRpcUrl(network, opts.rpc);
5206
- console.log(chalk8.green(`RPC URL saved for ${network}`));
5207
- console.log(chalk8.dim(` RPC: ${opts.rpc}`));
5697
+ console.log(chalk9.green(`RPC URL saved for ${network}`));
5698
+ console.log(chalk9.dim(` RPC: ${opts.rpc}`));
5208
5699
  saved = true;
5209
5700
  }
5210
5701
  if (opts.notifyTo) {
5211
5702
  setNotifyTo(opts.notifyTo);
5212
- console.log(chalk8.green("Notify destination saved to ~/.sherwood/config.json"));
5213
- console.log(chalk8.dim(` Notify to: ${opts.notifyTo}`));
5703
+ console.log(chalk9.green("Notify destination saved to ~/.sherwood/config.json"));
5704
+ console.log(chalk9.dim(` Notify to: ${opts.notifyTo}`));
5214
5705
  saved = true;
5215
5706
  }
5216
5707
  if (opts.uniswapApiKey) {
5217
5708
  setUniswapApiKey(opts.uniswapApiKey);
5218
- console.log(chalk8.green("Uniswap API key saved to ~/.sherwood/config.json"));
5709
+ console.log(chalk9.green("Uniswap API key saved to ~/.sherwood/config.json"));
5219
5710
  saved = true;
5220
5711
  }
5221
5712
  if (opts.veniceApiKey) {
5222
5713
  setVeniceApiKey(opts.veniceApiKey);
5223
- console.log(chalk8.green("Venice API key saved to ~/.sherwood/config.json"));
5714
+ console.log(chalk9.green("Venice API key saved to ~/.sherwood/config.json"));
5224
5715
  saved = true;
5225
5716
  }
5226
5717
  if (opts.xmtpGroup) {
5227
5718
  const parts = opts.xmtpGroup.split(":");
5228
5719
  if (parts.length !== 2 || !parts[0] || !parts[1]) {
5229
- console.log(chalk8.red("Format: --xmtp-group <subdomain>:<groupId>"));
5720
+ console.log(chalk9.red("Format: --xmtp-group <subdomain>:<groupId>"));
5230
5721
  process.exit(1);
5231
5722
  }
5232
5723
  cacheGroupId(parts[0], parts[1]);
5233
- console.log(chalk8.green(`XMTP group ID cached for ${parts[0]}`));
5234
- console.log(chalk8.dim(` Group ID: ${parts[1]}`));
5724
+ console.log(chalk9.green(`XMTP group ID cached for ${parts[0]}`));
5725
+ console.log(chalk9.dim(` Group ID: ${parts[1]}`));
5235
5726
  saved = true;
5236
5727
  }
5237
5728
  if (!saved) {
5238
- console.log(chalk8.red("Provide at least one of: --private-key, --vault, --rpc, --notify-to, --uniswap-api-key, --venice-api-key, --xmtp-group"));
5729
+ console.log(chalk9.red("Provide at least one of: --private-key, --vault, --rpc, --notify-to, --uniswap-api-key, --venice-api-key, --xmtp-group"));
5239
5730
  process.exit(1);
5240
5731
  }
5241
5732
  });
@@ -5246,25 +5737,25 @@ configCmd.command("show").description("Display current config for the active net
5246
5737
  const config = loadConfig();
5247
5738
  const customRpc = config.rpc?.[network];
5248
5739
  console.log();
5249
- console.log(chalk8.bold(`Sherwood Config`));
5250
- console.log(chalk8.dim("\u2500".repeat(50)));
5251
- console.log(` Network: ${chalk8.cyan(network)} (chain ${chainId})`);
5252
- console.log(` RPC: ${customRpc ? chalk8.green(customRpc) : chalk8.dim("default")}`);
5253
- console.log(` Wallet: ${config.privateKey ? chalk8.green("configured") : chalk8.dim("not set")}`);
5254
- console.log(` Agent ID: ${config.agentId ?? chalk8.dim("not set")}`);
5255
- console.log(` Vault: ${contracts.vault ?? chalk8.dim("not set")}`);
5256
- console.log(` Uniswap: ${getUniswapApiKey() ? chalk8.green("API key configured") : chalk8.dim("not set")}`);
5257
- console.log(` Venice: ${getVeniceApiKey() ? chalk8.green("API key configured") : chalk8.dim("not set")}`);
5740
+ console.log(chalk9.bold(`Sherwood Config`));
5741
+ console.log(chalk9.dim("\u2500".repeat(50)));
5742
+ console.log(` Network: ${chalk9.cyan(network)} (chain ${chainId})`);
5743
+ console.log(` RPC: ${customRpc ? chalk9.green(customRpc) : chalk9.dim("default")}`);
5744
+ console.log(` Wallet: ${config.privateKey ? chalk9.green("configured") : chalk9.dim("not set")}`);
5745
+ console.log(` Agent ID: ${config.agentId ?? chalk9.dim("not set")}`);
5746
+ console.log(` Vault: ${contracts.vault ?? chalk9.dim("not set")}`);
5747
+ console.log(` Uniswap: ${getUniswapApiKey() ? chalk9.green("API key configured") : chalk9.dim("not set")}`);
5748
+ console.log(` Venice: ${getVeniceApiKey() ? chalk9.green("API key configured") : chalk9.dim("not set")}`);
5258
5749
  const groupEntries = Object.entries(config.groupCache || {}).filter(([, v]) => v);
5259
5750
  if (groupEntries.length > 0) {
5260
5751
  console.log();
5261
- console.log(chalk8.bold(" XMTP Groups"));
5752
+ console.log(chalk9.bold(" XMTP Groups"));
5262
5753
  for (const [sub, gid] of groupEntries) {
5263
- console.log(` ${sub}: ${chalk8.cyan(gid)}`);
5754
+ console.log(` ${sub}: ${chalk9.cyan(gid)}`);
5264
5755
  }
5265
5756
  }
5266
5757
  console.log();
5267
- console.log(chalk8.dim(" Config file: ~/.sherwood/config.json"));
5758
+ console.log(chalk9.dim(" Config file: ~/.sherwood/config.json"));
5268
5759
  console.log();
5269
5760
  });
5270
5761
  program.parse();