@thirdfy/agent-cli 0.1.45 → 0.1.48

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/CHANGELOG.md CHANGED
@@ -4,6 +4,26 @@ All notable changes to `@thirdfy/agent-cli` are documented here. The format is b
4
4
 
5
5
  ## [Unreleased]
6
6
 
7
+ ## [0.1.48] - 2026-05-23
8
+
9
+ ### Fixed
10
+
11
+ - `actions --provider <earn-adapter>` only includes generic `deposit_earn_position` / `withdraw_earn_position` when catalog provider is `earn` or matches the requested adapter (avoids morpho filter showing vaults-fyi-tagged rows).
12
+
13
+ ## [0.1.47] - 2026-05-23
14
+
15
+ ### Added
16
+
17
+ - Provider discovery hints for `capyfi`, `fx`, and `bridge`; expanded Kyber `supportedChains` on `trading`.
18
+ - `docs/providers/capyfi.md` operator guide.
19
+
20
+ ## [0.1.46] - 2026-05-22
21
+
22
+ ### Changed
23
+
24
+ - `polymarket status` uses `get_polymarket_funding_status` with `agentKey` from flags or `~/.thirdfy/config.json` so operators see the agent-owned deposit wallet and nested setup readiness (not the legacy server setup path).
25
+ - `polymarket dry-run` defaults to `place-polymarket-order` for preflight. Pairs with thirdfy-api-v2 **v3.4.37** CLOB derive-miss → create fallback.
26
+
7
27
  ## [0.1.45] - 2026-05-22
8
28
 
9
29
  ### Added
package/README.md CHANGED
@@ -42,7 +42,7 @@ npx @thirdfy/agent-cli --help
42
42
 
43
43
  ## Release notes
44
44
 
45
- Version history and highlights: [CHANGELOG.md](./CHANGELOG.md). **v0.1.45** adds `polymarket status`, `polymarket setup`, and `polymarket dry-run` for agent-scoped setup/geoblock preflight (pairs with API **v3.4.35**). **v0.1.44** adds Aegis provider hints for Base and Unichain earn reads and fail-closed Engine writes (pairs with API **v3.4.28**). **v0.1.43** injects Hyperliquid `userAddress` from the managed execution wallet for solo `agent_wallet` reads when omitted (pairs with API **v3.4.27**). **v0.1.42** persists API `executionWallets` from email login, updates `doctor auth` / onboarding help for agent execution wallet funding vs owner embedded auth wallet, and documents Bridge2 `FUND_AGENT_EXECUTION_WALLET` remediation (pairs with API **v3.4.25**). **v0.1.41** documents Hyperliquid `get_hyperliquid_funding_status` as setup step 0, Bridge2 sender custody, and `deposit_hyperliquid_bridge --estimated-amount-usd` (pairs with API **v3.4.24**). **v0.1.40** fixes email/bootstrap credential persistence when the API returns nested registration payloads, so owner-session onboarding can save the hidden execution identity without exposing a raw agent API key. **v0.1.39** makes `agent_wallet` the fresh solo default, adds framework guidance for Hermes/OpenClaw/Claude Managed Agents, clarifies Gator/ERC-7710 delegation flows, and keeps BYOW/self plus hybrid/thirdfy mode switching explicit. **v0.1.38** is a **documentation and metadata patch**: it republishes to npm so the package homepage matches the updated `README.md` on `main`, and aligns root `package-lock.json` version fields with `package.json`. **v0.1.37** adds **email OTP** `thirdfy-agent login email` (send code, then complete with `--code --accept-terms`), **`help onboarding`**, **`doctor auth`**, **`wallet list`**, and **masked `whoami`** output so agents and operators get first-run guidance without dumping secrets. Earlier releases added provider discovery parity, portfolio analytics, managed-wallet swap normalization, and **self/build-tx** swap human-decimal `amountIn` parity when using `amountInHuman` + `tokenInDecimals`.
45
+ Version history and highlights: [CHANGELOG.md](./CHANGELOG.md). **v0.1.48** fixes earn provider filtering so generic `deposit_earn_position` / `withdraw_earn_position` rows only appear for matching adapters (not unrelated morpho/vaults-fyi filters). **v0.1.47** adds CapyFi, FX, and bridge provider discovery hints. **v0.1.46** routes `polymarket status` through `get_polymarket_funding_status` with config `agentKey` and defaults dry-run to `place-polymarket-order` (pairs with API **v3.4.37**). **v0.1.45** adds `polymarket status`, `polymarket setup`, and `polymarket dry-run` for agent-scoped setup/geoblock preflight (pairs with API **v3.4.35**). **v0.1.44** adds Aegis provider hints for Base and Unichain earn reads and fail-closed Engine writes (pairs with API **v3.4.28**). **v0.1.43** injects Hyperliquid `userAddress` from the managed execution wallet for solo `agent_wallet` reads when omitted (pairs with API **v3.4.27**). **v0.1.42** persists API `executionWallets` from email login, updates `doctor auth` / onboarding help for agent execution wallet funding vs owner embedded auth wallet, and documents Bridge2 `FUND_AGENT_EXECUTION_WALLET` remediation (pairs with API **v3.4.25**). **v0.1.41** documents Hyperliquid `get_hyperliquid_funding_status` as setup step 0, Bridge2 sender custody, and `deposit_hyperliquid_bridge --estimated-amount-usd` (pairs with API **v3.4.24**). **v0.1.40** fixes email/bootstrap credential persistence when the API returns nested registration payloads, so owner-session onboarding can save the hidden execution identity without exposing a raw agent API key. **v0.1.39** makes `agent_wallet` the fresh solo default, adds framework guidance for Hermes/OpenClaw/Claude Managed Agents, clarifies Gator/ERC-7710 delegation flows, and keeps BYOW/self plus hybrid/thirdfy mode switching explicit. **v0.1.38** is a **documentation and metadata patch**: it republishes to npm so the package homepage matches the updated `README.md` on `main`, and aligns root `package-lock.json` version fields with `package.json`. **v0.1.37** adds **email OTP** `thirdfy-agent login email` (send code, then complete with `--code --accept-terms`), **`help onboarding`**, **`doctor auth`**, **`wallet list`**, and **masked `whoami`** output so agents and operators get first-run guidance without dumping secrets. Earlier releases added provider discovery parity, portfolio analytics, managed-wallet swap normalization, and **self/build-tx** swap human-decimal `amountIn` parity when using `amountInHuman` + `tokenInDecimals`.
46
46
 
47
47
  **Maintainers — npm:** follow [docs/releasing.md](./docs/releasing.md). From a clone with gitignored `.env`, use `npm run publish:npm:local -- --dry-run` then `npm run publish:npm:local`. Or run `npm run release:npm` after exporting tokens in the shell. Never commit npm tokens — use [.env.example](./.env.example) as a template only.
48
48
 
@@ -477,6 +477,9 @@ function getTradingProviderHint(providerId) {
477
477
  provider,
478
478
  category: 'onchain_spot',
479
479
  canonicalWriteAction: 'swap',
480
+ supportedChains: [1, 10, 130, 137, 8453, 84532, 42161],
481
+ laneCompatibility:
482
+ 'Kyber quote/build is live on Ethereum, Optimism, Unichain, Polygon, Base, and Arbitrum; sponsored Kyber execution is validated on Base only. Gnosis FX uses the fx provider via CoW.',
480
483
  credentialUx: 'Use normal Thirdfy login/delegation; do not use this provider for Hyperliquid or Polymarket.',
481
484
  };
482
485
  }
@@ -670,6 +673,18 @@ function getTradingProviderHint(providerId) {
670
673
  compatibilityProvider: 'polymarket',
671
674
  };
672
675
  }
676
+ if (provider === 'bridge') {
677
+ return {
678
+ provider,
679
+ category: 'bridge',
680
+ canonicalReadAction: 'get_bridge_quote',
681
+ canonicalWriteAction: 'execute_bridge',
682
+ readActions: ['get_bridge_quote', 'get_supported_bridge_chains', 'check_bridge_status'],
683
+ orderManagementActions: ['execute_bridge'],
684
+ supportedChains: [1, 8453, 42161, 10, 137, 56, 43114, 250, 100, 1284, 1285, 25, 288, 1088, 42220, 122, 324, 59144, 534352, 5000, 81457, 169],
685
+ laneCompatibility: 'Li.Fi bridge supports mainnet value movement only; testnets are not auto-mapped to mainnet.',
686
+ };
687
+ }
673
688
  if (provider === 'earn') {
674
689
  return {
675
690
  provider,
@@ -693,6 +708,31 @@ function getTradingProviderHint(providerId) {
693
708
  'Generic earn writes use deposit_earn_position / withdraw_earn_position on normal Thirdfy policy/delegation rails; routing selects Morpho, Curve, Vaults.fyi, or Yield.xyz adapters per provider/opportunity.',
694
709
  };
695
710
  }
711
+ if (provider === 'capyfi') {
712
+ return {
713
+ provider,
714
+ category: 'earn',
715
+ canonicalReadAction: 'get_capyfi_markets',
716
+ canonicalWriteAction: 'deposit_earn_position',
717
+ readActions: ['get_capyfi_markets', 'get_earn_opportunities', 'get_earn_position'],
718
+ orderManagementActions: ['deposit_earn_position', 'withdraw_earn_position'],
719
+ supportedChains: [1, 480],
720
+ laneCompatibility: 'CapyFi Compound-v2 supply on Ethereum and World Chain; Gnosis pending deployment addresses.',
721
+ example:
722
+ 'thirdfy-agent run --action deposit_earn_position --params \'{"providerId":"capyfi","opportunityId":"capyfi-1-usdc","amount":"100","chainId":1,"tokenAddress":"0xA0b86991c6218b36c1d19D4a2e9Eb0cE3606eB48"}\'',
723
+ };
724
+ }
725
+ if (provider === 'fx') {
726
+ return {
727
+ provider,
728
+ category: 'fx',
729
+ canonicalReadAction: 'get_fx_supported_assets',
730
+ readActions: ['get_fx_supported_assets', 'quote_fx_swap', 'get_monerium_profile_status'],
731
+ supportedChains: [100],
732
+ laneCompatibility:
733
+ 'Gnosis FX: quote_fx_swap is read-only; on-chain execution uses the trading/cow path on chain 100. Monerium IBAN flows need credentials.',
734
+ };
735
+ }
696
736
  if (provider === 'morpho') {
697
737
  return {
698
738
  provider,
@@ -4166,6 +4206,10 @@ function inferActionProvider(action) {
4166
4206
  'get-earn-position': 'earn',
4167
4207
  'deposit-earn-position': 'earn',
4168
4208
  'withdraw-earn-position': 'earn',
4209
+ 'get-capyfi-markets': 'capyfi',
4210
+ 'get-fx-supported-assets': 'fx',
4211
+ 'quote-fx-swap': 'fx',
4212
+ 'get-monerium-profile-status': 'fx',
4169
4213
  'get-morpho-vaults': 'morpho',
4170
4214
  'deposit-morpho-vault': 'morpho',
4171
4215
  'withdraw-morpho-vault': 'morpho',
@@ -4214,6 +4258,8 @@ function inferActionProvider(action) {
4214
4258
  if (key.includes('polymarket') || key.includes('prediction')) return 'polymarket';
4215
4259
  if (key.includes('vaults-fyi')) return 'vaults-fyi';
4216
4260
  if (key.includes('yield-xyz')) return 'yield-xyz';
4261
+ if (key.includes('capyfi')) return 'capyfi';
4262
+ if (key.includes('fx') || key.includes('monerium')) return 'fx';
4217
4263
  if (key.includes('morpho')) return 'morpho';
4218
4264
  if (key.includes('aegis')) return 'aegis';
4219
4265
  if (key.includes('curve')) return 'curve';
@@ -4238,6 +4284,21 @@ function isEarnCatalogAction(action) {
4238
4284
  );
4239
4285
  }
4240
4286
 
4287
+ function isGenericEarnWriteAction(action) {
4288
+ const actionKey = rowActionKey(action);
4289
+ return actionKey === 'deposit_earn_position' || actionKey === 'withdraw_earn_position';
4290
+ }
4291
+
4292
+ /** Generic earn writes are shared catalog rows; only attach to the matching adapter or unlabeled rows. */
4293
+ function isGenericEarnWriteForProvider(action, requestedProvider) {
4294
+ if (!isGenericEarnWriteAction(action)) return false;
4295
+ const provider = getActionProviderWithInference(action);
4296
+ if (!provider) return true;
4297
+ if (provider === requestedProvider) return true;
4298
+ if (provider === 'earn' && requestedProvider === 'earn') return true;
4299
+ return false;
4300
+ }
4301
+
4241
4302
  function isSpotTradingCatalogAction(action) {
4242
4303
  const actionKey = rowActionKey(action);
4243
4304
  return actionKey === 'swap' || actionKey === 'execute_optimal_swap' || actionKey === 'get_best_trading_quote';
@@ -4263,14 +4324,22 @@ function actionMatchesProvider(action, requestedProvider, allActions) {
4263
4324
  // Here resolved metadata already disagrees with the filter; fall back to action-key shape only.
4264
4325
  if (requestedProvider === 'hyperliquid') return isProviderActionKey(action, 'hyperliquid');
4265
4326
  if (requestedProvider === 'polymarket') return isProviderActionKey(action, 'polymarket');
4266
- if (requestedProvider === 'bridge') return isProviderActionKey(action, 'bridge');
4327
+ if (requestedProvider === 'bridge') {
4328
+ // Hyperliquid Bridge2 setup actions are owned by Hyperliquid, not the cross-chain bridge provider.
4329
+ if (provider === 'hyperliquid') return false;
4330
+ return isProviderActionKey(action, 'bridge');
4331
+ }
4267
4332
  if (requestedProvider.startsWith('dogeos')) return isProviderActionKey(action, requestedProvider);
4268
4333
  if (requestedProvider === 'earn') {
4269
- return provider === 'earn' || provider === 'morpho' || provider === 'aegis' || provider === 'curve' || provider === 'vaults-fyi' || provider === 'yield-xyz' || isEarnCatalogAction(action);
4334
+ return provider === 'earn' || provider === 'morpho' || provider === 'aegis' || provider === 'curve' || provider === 'capyfi' || provider === 'vaults-fyi' || provider === 'yield-xyz' || isEarnCatalogAction(action);
4270
4335
  }
4271
- if (requestedProvider === 'morpho' || requestedProvider === 'aegis' || requestedProvider === 'curve' || requestedProvider === 'vaults-fyi' || requestedProvider === 'yield-xyz') {
4336
+ if (requestedProvider === 'morpho' || requestedProvider === 'aegis' || requestedProvider === 'curve' || requestedProvider === 'capyfi' || requestedProvider === 'vaults-fyi' || requestedProvider === 'yield-xyz') {
4272
4337
  const hasProtocolSpecificEarnRows = allActions.some((candidate) => getActionProviderWithInference(candidate) === requestedProvider);
4273
- return isProviderActionKey(action, requestedProvider) || (!hasProtocolSpecificEarnRows && isEarnCatalogAction(action));
4338
+ return (
4339
+ isProviderActionKey(action, requestedProvider) ||
4340
+ isGenericEarnWriteForProvider(action, requestedProvider) ||
4341
+ (!hasProtocolSpecificEarnRows && isEarnCatalogAction(action))
4342
+ );
4274
4343
  }
4275
4344
  if (requestedProvider === 'prediction') {
4276
4345
  return (
@@ -4887,31 +4956,53 @@ function printEnvelope(payload) {
4887
4956
  process.stdout.write(`${JSON.stringify(payload.data || {}, null, 2)}\n`);
4888
4957
  }
4889
4958
 
4959
+ function resolveConfigAgentKey(flags) {
4960
+ const fromFlags = String(flags.agentKey || flags.agentApiKey || '').trim();
4961
+ if (fromFlags) return fromFlags;
4962
+ const config = loadProfileConfig();
4963
+ const fromAgent = String(config?.agent?.agentKey || '').trim();
4964
+ if (fromAgent) return fromAgent;
4965
+ return extractAgentKey(config);
4966
+ }
4967
+
4890
4968
  async function commandPolymarketStatus(ctx, flags) {
4891
- const params = {
4892
- includeBalance: parseBooleanFlag(flags.includeBalance, true),
4893
- includeGeoblock: parseBooleanFlag(flags.includeGeoblock, true),
4894
- };
4895
- if (flags.agentKey) params.agentKey = String(flags.agentKey);
4896
- if (flags.amountPusd) params.amountPusd = String(flags.amountPusd);
4969
+ const agentKey = resolveConfigAgentKey(flags);
4897
4970
  const capabilities = await negotiateCapabilities(ctx);
4898
- flags.action = 'get_polymarket_setup_status';
4899
- flags.params = JSON.stringify(params);
4900
4971
  if (!flags.runMode) flags.runMode = 'agent_wallet';
4972
+ if (agentKey) {
4973
+ flags.action = 'get_polymarket_funding_status';
4974
+ flags.params = JSON.stringify({
4975
+ agentKey,
4976
+ amountPusd: flags.amountPusd ? String(flags.amountPusd) : '5',
4977
+ includeSetupStatus: true,
4978
+ });
4979
+ } else {
4980
+ const params = {
4981
+ includeBalance: parseBooleanFlag(flags.includeBalance, true),
4982
+ includeGeoblock: parseBooleanFlag(flags.includeGeoblock, true),
4983
+ };
4984
+ flags.action = 'get_polymarket_setup_status';
4985
+ flags.params = JSON.stringify(params);
4986
+ }
4901
4987
  await commandPreflight(ctx, flags, capabilities);
4902
4988
  }
4903
4989
 
4904
4990
  async function commandPolymarketSetup(ctx, flags) {
4905
4991
  const capabilities = await negotiateCapabilities(ctx);
4906
4992
  flags.action = 'get_polymarket_onboarding_plan';
4907
- flags.params = flags.params || JSON.stringify({ agentKey: flags.agentKey || undefined });
4993
+ const agentKey = resolveConfigAgentKey(flags);
4994
+ flags.params =
4995
+ flags.params ||
4996
+ JSON.stringify({
4997
+ ...(agentKey ? { agentKey } : {}),
4998
+ });
4908
4999
  if (!flags.runMode) flags.runMode = 'agent_wallet';
4909
5000
  flags.__polymarketSetupGuide = true;
4910
5001
  await commandPreflight(ctx, flags, capabilities);
4911
5002
  }
4912
5003
 
4913
5004
  async function commandPolymarketDryRun(ctx, flags) {
4914
- if (!flags.action) flags.action = 'place_polymarket_order';
5005
+ if (!flags.action) flags.action = 'place-polymarket-order';
4915
5006
  if (!flags.params) {
4916
5007
  printEnvelope({
4917
5008
  success: false,
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@thirdfy/agent-cli",
3
- "version": "0.1.45",
3
+ "version": "0.1.48",
4
4
  "description": "Thirdfy Agent CLI for onboarding, governance preflight, execute-intent, and status polling.",
5
5
  "type": "module",
6
6
  "bin": {