@thirdfy/agent-cli 0.4.1 → 0.4.3
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 +39 -0
- package/README.md +4 -7
- package/package.json +5 -3
- package/src/cli/help.mjs +1 -1
- package/src/cli/options/index.mjs +11 -11
- package/src/cli/options/onboarding/credentials.mjs +17 -0
- package/src/cli/program.mjs +1 -1
- package/src/commands/{agent.mjs → account/agent.mjs} +5 -5
- package/src/commands/{credits.mjs → account/credits.mjs} +13 -15
- package/src/commands/{wallet.mjs → account/wallet.mjs} +29 -33
- package/src/commands/{walletControl.mjs → account/walletControl.mjs} +3 -3
- package/src/commands/discovery.mjs +1 -1
- package/src/commands/doctor.mjs +5 -5
- package/src/commands/execute.mjs +4 -13
- package/src/commands/index.mjs +9 -9
- package/src/commands/{bootstrap.mjs → onboarding/bootstrap.mjs} +8 -8
- package/src/commands/{consoleMandate.mjs → onboarding/consoleMandate.mjs} +2 -2
- package/src/commands/{credentials.mjs → onboarding/credentials.mjs} +16 -29
- package/src/commands/{delegation.mjs → onboarding/delegation.mjs} +5 -5
- package/src/commands/{avantis.mjs → venues/avantis.mjs} +1 -1
- package/src/commands/{condor.mjs → venues/condor.mjs} +4 -4
- package/src/commands/{hummingbot.mjs → venues/hummingbot.mjs} +4 -4
- package/src/commands/{hyperliquid.mjs → venues/hyperliquid.mjs} +1 -1
- package/src/commands/{lighter.mjs → venues/lighter.mjs} +1 -1
- package/src/commands/{polymarket.mjs → venues/polymarket.mjs} +4 -4
- package/src/commands/{venue.mjs → venues/venue.mjs} +3 -3
- package/src/core/chainRegistry.mjs +11 -0
- package/src/core/constants.mjs +0 -19
- package/src/core/earnclawAttribution.mjs +1 -1
- package/src/core/{actionTimeouts.mjs → execution/actionTimeouts.mjs} +2 -2
- package/src/core/{walletExecuteChainId.mjs → execution/walletExecuteChainId.mjs} +1 -1
- package/src/core/http.mjs +1 -1
- package/src/runtime/actions/selection.mjs +0 -1
- package/src/runtime/execution/hostedRuntimeWriteGate.mjs +1 -1
- package/src/runtime/execution/payloads.mjs +4 -4
- package/src/runtime/execution/runners/agentWalletLane.mjs +109 -0
- package/src/runtime/execution/runners/createExecutionRunners.mjs +312 -0
- package/src/runtime/execution/runners/hybridLane.mjs +88 -0
- package/src/runtime/execution/runners/managedPreflight.mjs +253 -0
- package/src/runtime/execution/runners/managedResponse.mjs +119 -0
- package/src/runtime/execution/runners/selfLane.mjs +233 -0
- package/src/runtime/execution/runners/thirdfyLane.mjs +97 -0
- package/src/runtime/execution/svmLane.mjs +1 -1
- package/src/runtime/handlers.mjs +15 -20
- package/src/runtime/main.mjs +1 -11
- package/src/runtime/owsSigning.mjs +17 -16
- package/src/runtime/providerHints/cex.mjs +1 -52
- package/src/runtime/risk/notional.mjs +1 -1
- package/src/runtime/validation/actionParamsGate.mjs +1 -1
- package/src/cli/options/credentials.mjs +0 -15
- package/src/runtime/bitfinexProbe.mjs +0 -121
- package/src/runtime/execution/runners.mjs +0 -1134
- package/src/runtime/onboardingHints.mjs +0 -54
- /package/src/cli/options/{agent.mjs → account/agent.mjs} +0 -0
- /package/src/cli/options/{credits.mjs → account/credits.mjs} +0 -0
- /package/src/cli/options/{wallet.mjs → account/wallet.mjs} +0 -0
- /package/src/cli/options/{walletControl.mjs → account/walletControl.mjs} +0 -0
- /package/src/cli/options/{bootstrap.mjs → onboarding/bootstrap.mjs} +0 -0
- /package/src/cli/options/{delegation.mjs → onboarding/delegation.mjs} +0 -0
- /package/src/cli/options/{condor.mjs → venues/condor.mjs} +0 -0
- /package/src/cli/options/{hummingbot.mjs → venues/hummingbot.mjs} +0 -0
- /package/src/cli/options/{polymarket.mjs → venues/polymarket.mjs} +0 -0
- /package/src/cli/options/{venue.mjs → venues/venue.mjs} +0 -0
- /package/src/core/{executionContext.mjs → execution/executionContext.mjs} +0 -0
- /package/src/core/{fundingTokenIn.mjs → execution/fundingTokenIn.mjs} +0 -0
- /package/src/core/{hostedRuntimeIdempotency.mjs → execution/hostedRuntimeIdempotency.mjs} +0 -0
- /package/src/core/{readOnlyActions.mjs → execution/readOnlyActions.mjs} +0 -0
- /package/src/core/{signedTx.mjs → execution/signedTx.mjs} +0 -0
package/CHANGELOG.md
CHANGED
|
@@ -4,6 +4,45 @@ All notable changes to `@thirdfy/agent-cli` are documented here. The format is b
|
|
|
4
4
|
|
|
5
5
|
## Unreleased
|
|
6
6
|
|
|
7
|
+
## [0.4.3] - 2026-10-14
|
|
8
|
+
|
|
9
|
+
Bitfinex support is removed, ethers loads again for local signing and RPC checks, and an unreachable RPC no longer floods `--json` output. Older `credentials upsert` scripts keep working: the removed flags are accepted and ignored.
|
|
10
|
+
|
|
11
|
+
### Removed
|
|
12
|
+
|
|
13
|
+
- **Bitfinex support.** It was unused and extra code to maintain. Removed:
|
|
14
|
+
- the Bitfinex static provider hint (`actions --provider bitfinex` no longer carries one; thirdfy-mcp removed its hint too, thirdfy/thirdfy-mcp#270);
|
|
15
|
+
- the `credentials upsert` permission probe, and the `bitfinex:funding-primary` / `bitfinex:spot-primary` credential-ref defaults (pass `--credential-ref` yourself);
|
|
16
|
+
- the Bitfinex onboarding hint (`data.onboardingHint` on error envelopes and on `preflight` / `run` results);
|
|
17
|
+
- `src/runtime/bitfinexProbe.mjs`, `src/runtime/onboardingHints.mjs`, `src/runtime/execution/runners/fallbackHints.mjs`, and the Bitfinex docs.
|
|
18
|
+
|
|
19
|
+
`credentials upsert` and `credentials status` stay for the other venues (Hummingbot connectors, Polymarket, Hyperliquid, Lighter, Avantis). The probe's flags (`--permission-profile`, `--verify-permissions`, `--skip-permissions-probe`, `--bitfinex-base-url`) are still accepted, ignored, and named in `meta.warnings`, so older scripts keep working; they go in the next minor version. The API still serves the Bitfinex catalog rows until it removes them.
|
|
20
|
+
|
|
21
|
+
### Fixed
|
|
22
|
+
|
|
23
|
+
- **`loadEthers` loads ethers again.** `src/runtime/owsSigning.mjs` called `require` in an ES module, where it is undefined, and the `ReferenceError` was swallowed. So ethers never loaded, and these failed: `doctor self`'s `ethers-runtime` and `rpc-connectivity` checks, OWS sign-and-broadcast, the self lane's effect-check balance reads, and `wallet submit`. It now loads through `createRequire(import.meta.url)`.
|
|
24
|
+
- **RPC calls fail once instead of retrying forever.** Every RPC connection (`doctor self`, OWS broadcast, `wallet submit`, effect-check balance reads) is now pinned to its chain id (`pinnedRpcProvider` in `src/core/chainRegistry.mjs`). An unreachable RPC is one error, not an ethers retry line on stdout every second that breaks `--json` output and keeps the process running. `doctor self`'s `rpc-chain-id` check asks the RPC itself (`eth_chainId`), so a wrong RPC is still reported. Tests: `test/runtime/owsSigning.test.cjs`.
|
|
25
|
+
|
|
26
|
+
## [0.4.2] - 2026-10-14
|
|
27
|
+
|
|
28
|
+
A cleanup release: two small `wallet profile` / `pricing quote` fixes from the 0.4.1 review, and source files moved into domain folders. Commands answer as in 0.4.1, apart from the two fixes.
|
|
29
|
+
|
|
30
|
+
### Fixed
|
|
31
|
+
|
|
32
|
+
- **`wallet profile` and `readiness` report the agent key in lowercase** whether it came from `--agent-key` or from env/config. Before, a checksummed config key was echoed as stored, so one agent could appear with two spellings.
|
|
33
|
+
- **`pricing quote` on an API without the agent quote route** names the agent only from `--agent-key`. The branch that took the configured agent could not be reached (a stored owner token already puts the quote on the owner ledger) and is removed.
|
|
34
|
+
|
|
35
|
+
### Changed
|
|
36
|
+
|
|
37
|
+
- **Source files moved into domain subfolders (no behavior change).** The `thirdfy-agent` command is unchanged. Code that deep-imports package files must use the new paths:
|
|
38
|
+
- `src/runtime/execution/runners.mjs` → `src/runtime/execution/runners/` (one file per lane; `createExecutionRunners` is in `createExecutionRunners.mjs`).
|
|
39
|
+
- `src/core/{actionTimeouts,executionContext,fundingTokenIn,hostedRuntimeIdempotency,readOnlyActions,signedTx,walletExecuteChainId}.mjs` → `src/core/execution/`.
|
|
40
|
+
- `src/commands/{avantis,condor,hummingbot,hyperliquid,lighter,polymarket,venue}.mjs` → `src/commands/venues/`; `{bootstrap,consoleMandate,credentials,delegation}.mjs` → `src/commands/onboarding/`; `{agent,credits,wallet,walletControl}.mjs` → `src/commands/account/`.
|
|
41
|
+
- `src/cli/options/` uses the same `venues/`, `onboarding/` and `account/` subfolders.
|
|
42
|
+
- `src/core/index.mjs` and `src/commands/index.mjs` export the same names as before.
|
|
43
|
+
- `wallet profile` uses the same owner/agent precedence code as the credits commands (`resolveCreditsLedger`) instead of its own copy. Same behavior.
|
|
44
|
+
- `validate:provider-parity` names the files it looked in when it finds no MCP provider-hints file.
|
|
45
|
+
|
|
7
46
|
## [0.4.1] - 2026-10-14
|
|
8
47
|
|
|
9
48
|
The last MCP tool with no CLI command (`wallet profile`), who pays for an action (`pricing quote`), owner session tokens for credits, and a parity check that follows thirdfy-mcp's new file layout.
|
package/README.md
CHANGED
|
@@ -22,7 +22,6 @@ If you want the full developer docs, start here:
|
|
|
22
22
|
- [Action inventory and compatibility](./docs/action-inventory-and-compatibility.md)
|
|
23
23
|
- [Command reference](./docs/command-reference.md)
|
|
24
24
|
- [DogeOS quickstart (repo)](./docs/dogeos-quickstart.md)
|
|
25
|
-
- [Bitfinex CEX workflow (repo)](./docs/bitfinex-cex-workflow.md)
|
|
26
25
|
- [Action onboarding standard](./docs/action-onboarding-standard.md)
|
|
27
26
|
- [Provider docs governance model](./docs/provider-docs-governance.md)
|
|
28
27
|
- [Skill integration RFC](./docs/skill-integration-rfc.md)
|
|
@@ -40,12 +39,11 @@ Run without global install:
|
|
|
40
39
|
npx @thirdfy/agent-cli --help
|
|
41
40
|
```
|
|
42
41
|
|
|
43
|
-
## What's new in v0.4.
|
|
42
|
+
## What's new in v0.4.3
|
|
44
43
|
|
|
45
|
-
-
|
|
46
|
-
-
|
|
47
|
-
- **
|
|
48
|
-
- **Safer agent identity:** with an explicit `--agent-api-key`, `readiness`, `wallet profile` and `pricing quote` name the agent from `--agent-key`, never a configured agent that may belong to another key.
|
|
44
|
+
- **Local signing works again:** ethers now loads, so `doctor self`, OWS sign-and-broadcast, `wallet submit` and the self lane's balance checks run as documented.
|
|
45
|
+
- **A dead RPC is one clear error:** every RPC call is pinned to its chain, so an unreachable RPC no longer prints retry lines into `--json` output or keeps the command running.
|
|
46
|
+
- **Bitfinex support removed from the CLI:** no Bitfinex provider hint, credential permission probe or docs any more. The Thirdfy API still serves the Bitfinex actions for now. `credentials upsert` still works for the other venues, and its old Bitfinex flags are accepted and ignored with a warning.
|
|
49
47
|
- Older versions: see [CHANGELOG.md](./CHANGELOG.md).
|
|
50
48
|
|
|
51
49
|
## Quick start
|
|
@@ -347,7 +345,6 @@ thirdfy-agent run --agent-api-key "$THIRDFY_AGENT_API_KEY" --action swap \
|
|
|
347
345
|
Provider and venue guides are kept outside `README` so this page stays stable as integrations grow.
|
|
348
346
|
|
|
349
347
|
- Provider index: [`docs/providers/index.md`](./docs/providers/index.md)
|
|
350
|
-
- Bitfinex runbook: [`docs/providers/bitfinex.md`](./docs/providers/bitfinex.md)
|
|
351
348
|
- DogeOS runbook: [`docs/providers/dogeos.md`](./docs/providers/dogeos.md)
|
|
352
349
|
|
|
353
350
|
## Command groups
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@thirdfy/agent-cli",
|
|
3
|
-
"version": "0.4.
|
|
3
|
+
"version": "0.4.3",
|
|
4
4
|
"description": "Thirdfy Agent CLI for onboarding, governance preflight, execute-intent, and status polling.",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"bin": {
|
|
@@ -22,8 +22,8 @@
|
|
|
22
22
|
"LICENSE"
|
|
23
23
|
],
|
|
24
24
|
"scripts": {
|
|
25
|
-
"test": "node --test test
|
|
26
|
-
"lint": "node --check ./bin/thirdfy-agent.mjs && node --check ./src/core/*.mjs && node --check ./src/commands/*.mjs && node --check ./src/commands/signals/*.mjs && node --check ./src/cli/*.mjs && node --check ./src/cli/options/*.mjs && node --check ./src/runtime/*.mjs && node --check ./src/runtime/execution/*.mjs && node --check ./src/runtime/actions/*.mjs && node --check ./src/runtime/validation/*.mjs && node --check ./src/runtime/certification/*.mjs && node --check ./src/runtime/providerHints/*.mjs && node --check ./src/runtime/risk/*.mjs",
|
|
25
|
+
"test": "node --test test/*/*.test.cjs test/*/*/*.test.cjs",
|
|
26
|
+
"lint": "node --check ./bin/thirdfy-agent.mjs && node --check ./src/core/*.mjs && node --check ./src/core/execution/*.mjs && node --check ./src/commands/*.mjs && node --check ./src/commands/venues/*.mjs && node --check ./src/commands/onboarding/*.mjs && node --check ./src/commands/account/*.mjs && node --check ./src/commands/signals/*.mjs && node --check ./src/cli/*.mjs && node --check ./src/cli/options/*.mjs && node --check ./src/cli/options/venues/*.mjs && node --check ./src/cli/options/onboarding/*.mjs && node --check ./src/cli/options/account/*.mjs && node --check ./src/runtime/*.mjs && node --check ./src/runtime/execution/*.mjs && node --check ./src/runtime/execution/runners/*.mjs && node --check ./src/runtime/actions/*.mjs && node --check ./src/runtime/validation/*.mjs && node --check ./src/runtime/certification/*.mjs && node --check ./src/runtime/providerHints/*.mjs && node --check ./src/runtime/risk/*.mjs",
|
|
27
27
|
"validate:cli-manifest-handlers": "node ./scripts/validate-cli-manifest-handlers.mjs",
|
|
28
28
|
"validate:runtime-boundaries": "node ./scripts/validate-runtime-boundaries.mjs",
|
|
29
29
|
"validate:npm-pack": "node ./scripts/validate-npm-pack.mjs",
|
|
@@ -36,6 +36,8 @@
|
|
|
36
36
|
"e2e:local-api:smoke": "node ./scripts/e2e/local-api-smoke.mjs",
|
|
37
37
|
"e2e:base:simulate": "node ./scripts/e2e/base-simulate.mjs",
|
|
38
38
|
"e2e:base:real": "node ./scripts/e2e/base-realtx.mjs",
|
|
39
|
+
"e2e:agent-wallet:simulate": "node ./scripts/e2e/agent-wallet/run.mjs",
|
|
40
|
+
"e2e:agent-wallet:real": "node ./scripts/e2e/agent-wallet/run.mjs --real",
|
|
39
41
|
"e2e:delegation:discovery": "node ./scripts/e2e/delegation-discovery.mjs",
|
|
40
42
|
"e2e:delegation:lifecycle": "node ./scripts/e2e/delegation-lifecycle.mjs",
|
|
41
43
|
"e2e:delegation:commands": "node ./scripts/e2e/delegation-command-parity.mjs",
|
package/src/cli/help.mjs
CHANGED
|
@@ -54,7 +54,7 @@ Core commands:
|
|
|
54
54
|
thirdfy-agent wallet sign --agent-api-key <key> --action <id> --params <json> [--chain-id <id>] [--json]
|
|
55
55
|
thirdfy-agent wallet submit --signed-tx-hex <hex> [--chain-id <id>] [--rpc-url <url>] [--json]
|
|
56
56
|
thirdfy-agent agent run --agent-api-key <key> --action <id> --params <json> [--signer-method managed_wallet_server|byow|fanout_intent] [--strategy-intent single_wallet|fanout] [--run-mode <mode>] [--user-did <did>] [--json]
|
|
57
|
-
thirdfy-agent credentials upsert --auth-token <token> --venue <id> --api-key <key> --api-secret <secret> [--
|
|
57
|
+
thirdfy-agent credentials upsert --auth-token <token> --venue <id> --api-key <key> --api-secret <secret> [--credential-ref <ref>] [--json]
|
|
58
58
|
thirdfy-agent credentials status --auth-token <token> [--venue <id>] [--json]
|
|
59
59
|
thirdfy-agent agent auth challenge --agent-key <key> [--wallet-address <addr>] [--chain-id <id>] [--json]
|
|
60
60
|
thirdfy-agent agent auth verify --challenge-id <id> --signature <hex> --agent-key <key> [--wallet-address <addr>] [--json]
|
|
@@ -1,24 +1,24 @@
|
|
|
1
1
|
import { attachGlobalOptions } from './global.mjs';
|
|
2
2
|
import { attachAuthOptions } from './auth.mjs';
|
|
3
3
|
import { attachExecutionOptions } from './execution.mjs';
|
|
4
|
-
import { attachDelegationOptions } from './delegation.mjs';
|
|
4
|
+
import { attachDelegationOptions } from './onboarding/delegation.mjs';
|
|
5
5
|
import { attachTrackingOptions } from './tracking.mjs';
|
|
6
|
-
import { attachWalletOptions } from './wallet.mjs';
|
|
7
|
-
import { attachBootstrapOptions, attachOnboardingHelpOptions } from './bootstrap.mjs';
|
|
8
|
-
import { attachCredentialsOptions } from './credentials.mjs';
|
|
6
|
+
import { attachWalletOptions } from './account/wallet.mjs';
|
|
7
|
+
import { attachBootstrapOptions, attachOnboardingHelpOptions } from './onboarding/bootstrap.mjs';
|
|
8
|
+
import { attachCredentialsOptions } from './onboarding/credentials.mjs';
|
|
9
9
|
import { attachAnalyticsOptions } from './analytics.mjs';
|
|
10
|
-
import { attachPolymarketOptions } from './polymarket.mjs';
|
|
11
|
-
import { attachHummingbotOptions } from './hummingbot.mjs';
|
|
12
|
-
import { attachCondorOptions } from './condor.mjs';
|
|
13
|
-
import { attachAgentRegisterOptions } from './agent.mjs';
|
|
10
|
+
import { attachPolymarketOptions } from './venues/polymarket.mjs';
|
|
11
|
+
import { attachHummingbotOptions } from './venues/hummingbot.mjs';
|
|
12
|
+
import { attachCondorOptions } from './venues/condor.mjs';
|
|
13
|
+
import { attachAgentRegisterOptions } from './account/agent.mjs';
|
|
14
14
|
import { attachChainListOptions, attachChainOptions } from './chains.mjs';
|
|
15
|
-
import { attachCreditsBuyOptions, attachCreditsOptions } from './credits.mjs';
|
|
15
|
+
import { attachCreditsBuyOptions, attachCreditsOptions } from './account/credits.mjs';
|
|
16
16
|
import { attachChatOptions } from './chat.mjs';
|
|
17
|
-
import { attachVenueOptions } from './venue.mjs';
|
|
17
|
+
import { attachVenueOptions } from './venues/venue.mjs';
|
|
18
18
|
import { attachBrainOptions } from './brain.mjs';
|
|
19
19
|
import { attachCertificationOptions } from './certification.mjs';
|
|
20
20
|
import { attachActionListOptions, attachDataCategoryOptions, attachSignalsOptions } from './data.mjs';
|
|
21
|
-
import { attachWalletControlOptions } from './walletControl.mjs';
|
|
21
|
+
import { attachWalletControlOptions } from './account/walletControl.mjs';
|
|
22
22
|
|
|
23
23
|
const BUNDLES = {
|
|
24
24
|
auth: attachAuthOptions,
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
export function attachCredentialsOptions(cmd) {
|
|
2
|
+
return cmd
|
|
3
|
+
.option('--venue <id>', 'credential venue')
|
|
4
|
+
.option('--api-key <key>', 'exchange API key')
|
|
5
|
+
.option('--api-secret <secret>', 'exchange API secret')
|
|
6
|
+
.option('--credential-ref <ref>', 'credential reference')
|
|
7
|
+
.option('--credential-type <type>', 'credential type')
|
|
8
|
+
.option('--passphrase <value>', 'exchange passphrase')
|
|
9
|
+
.option('--metadata <json>', 'credential metadata JSON')
|
|
10
|
+
.option('--policy <json>', 'credential policy JSON')
|
|
11
|
+
// Accepted and ignored since Bitfinex support was removed, so older scripts keep working; the
|
|
12
|
+
// command says so in meta.warnings. Drop them in the next minor version.
|
|
13
|
+
.option('--permission-profile <profile>', 'ignored (Bitfinex support was removed)')
|
|
14
|
+
.option('--verify-permissions', 'ignored (Bitfinex support was removed)')
|
|
15
|
+
.option('--skip-permissions-probe', 'ignored (Bitfinex support was removed)')
|
|
16
|
+
.option('--bitfinex-base-url <url>', 'ignored (Bitfinex support was removed)');
|
|
17
|
+
}
|
package/src/cli/program.mjs
CHANGED
|
@@ -3,4 +3,4 @@ import { buildCliProgram } from './register.mjs';
|
|
|
3
3
|
export { buildCliProgram };
|
|
4
4
|
export { collectRootFlags, collectLegacyFlags } from './flags.mjs';
|
|
5
5
|
export { configureCommanderErrors, handleRootOnlyFlows, collectVersionFlagsFromArgv } from './errors.mjs';
|
|
6
|
-
export { normalizeLegacyShortFlags } from './options/bootstrap.mjs';
|
|
6
|
+
export { normalizeLegacyShortFlags } from './options/onboarding/bootstrap.mjs';
|
|
@@ -1,11 +1,11 @@
|
|
|
1
1
|
import { createRequire } from 'module';
|
|
2
|
-
import { requireFlag, parseJsonFlag } from '
|
|
3
|
-
import { apiPost, safeJsonParse } from '
|
|
4
|
-
import { createCliError } from '
|
|
5
|
-
import { DEFAULT_TIMEOUT_MS } from '
|
|
2
|
+
import { requireFlag, parseJsonFlag } from '../../core/args.mjs';
|
|
3
|
+
import { apiPost, safeJsonParse } from '../../core/http.mjs';
|
|
4
|
+
import { createCliError } from '../../core/envelope.mjs';
|
|
5
|
+
import { DEFAULT_TIMEOUT_MS } from '../../core/constants.mjs';
|
|
6
6
|
|
|
7
7
|
const require = createRequire(import.meta.url);
|
|
8
|
-
const { version: CLI_VERSION } = require('
|
|
8
|
+
const { version: CLI_VERSION } = require('../../../package.json');
|
|
9
9
|
export function createAgentCommands({ printEnvelope, extractAgentApiKey, extractAgentKey, buildOwnerAuthHeaders }) {
|
|
10
10
|
async function commandAgentRegister(ctx, flags, capabilities) {
|
|
11
11
|
const ownerHeaders = buildOwnerAuthHeaders(
|
|
@@ -1,13 +1,13 @@
|
|
|
1
|
-
import { requireFlag, usageError } from '
|
|
2
|
-
import { apiGet, apiPost } from '
|
|
3
|
-
import {
|
|
4
|
-
import { createCliError } from '
|
|
5
|
-
import { toAvantisSpelling } from '
|
|
1
|
+
import { requireFlag, usageError } from '../../core/args.mjs';
|
|
2
|
+
import { apiGet, apiPost } from '../../core/http.mjs';
|
|
3
|
+
import { resolveCreditsLedger } from '../../core/context.mjs';
|
|
4
|
+
import { createCliError } from '../../core/envelope.mjs';
|
|
5
|
+
import { toAvantisSpelling } from '../../core/venueBrand.mjs';
|
|
6
6
|
import {
|
|
7
7
|
formatCreditsEstimateSummary,
|
|
8
8
|
formatCreditsModelsSummary,
|
|
9
9
|
stripUsdFields,
|
|
10
|
-
} from '
|
|
10
|
+
} from '../../lib/creditsUsdSummary.mjs';
|
|
11
11
|
|
|
12
12
|
function resolveToolCallsEstimate(flags) {
|
|
13
13
|
const raw = flags.toolCalls ?? flags.toolCallsList;
|
|
@@ -151,14 +151,13 @@ export function createCreditsCommands({ printEnvelope, getAuthToken, buildOwnerA
|
|
|
151
151
|
* (thirdfy-api-v2#887). The ledger follows `resolveCreditsLedger`. Agent: `POST /agent/credits/quote`
|
|
152
152
|
* with the agent's key. Owner (session token or auth token): `/credits/pricing/quote`, for one of the
|
|
153
153
|
* owner's agents with --agent-key. An API without the agent route (404, before #887) is quoted
|
|
154
|
-
* through the owner route when owner auth is set and the key's agent
|
|
155
|
-
* configured agent when the key also comes from env or config. Credits only.
|
|
154
|
+
* through the owner route when owner auth is set and --agent-key names the key's agent. Credits only.
|
|
156
155
|
*/
|
|
157
156
|
async function commandPricingQuote(ctx, flags) {
|
|
158
157
|
const action = requireFlag(flags, 'action', 'Missing --action for pricing quote');
|
|
159
158
|
// Veranta names price as their Avantis spelling, which every API deployment knows.
|
|
160
159
|
const body = { actionKey: toAvantisSpelling(action), chainId: Number(flags.chainId || 8453) };
|
|
161
|
-
const { ledger: requestedLedger, agentApiKey
|
|
160
|
+
const { ledger: requestedLedger, agentApiKey } = resolveCreditsLedger(flags);
|
|
162
161
|
const flagAgentKey = String(flags.agentKey || '').trim();
|
|
163
162
|
const ownerHeaders = () =>
|
|
164
163
|
buildOwnerAuthHeaders(flags, 'Missing --owner-session-token or --auth-token (or THIRDFY_OWNER_SESSION_TOKEN / THIRDFY_AUTH_TOKEN), or an agent key, for pricing quote');
|
|
@@ -191,8 +190,9 @@ export function createCreditsCommands({ printEnvelope, getAuthToken, buildOwnerA
|
|
|
191
190
|
{ blockedStage: 'auth' },
|
|
192
191
|
);
|
|
193
192
|
}
|
|
194
|
-
|
|
195
|
-
|
|
193
|
+
// Only --agent-key can name the key's agent here. The agent ledger without --agent-api-key means
|
|
194
|
+
// no owner auth is stored, and then the owner check above has already refused.
|
|
195
|
+
if (!flagAgentKey) {
|
|
196
196
|
throw createCliError(
|
|
197
197
|
'AGENT_IDENTITY_UNAVAILABLE',
|
|
198
198
|
'This Thirdfy API has no agent quote route yet; to quote through the owner route, pass --agent-key (the agent of this API key).',
|
|
@@ -200,8 +200,8 @@ export function createCreditsCommands({ printEnvelope, getAuthToken, buildOwnerA
|
|
|
200
200
|
);
|
|
201
201
|
}
|
|
202
202
|
ledger = 'owner';
|
|
203
|
-
quotedAgentKey =
|
|
204
|
-
response = await ownerQuote(
|
|
203
|
+
quotedAgentKey = flagAgentKey;
|
|
204
|
+
response = await ownerQuote(flagAgentKey);
|
|
205
205
|
}
|
|
206
206
|
} else {
|
|
207
207
|
response = await ownerQuote(flagAgentKey);
|
|
@@ -223,8 +223,6 @@ export function createCreditsCommands({ printEnvelope, getAuthToken, buildOwnerA
|
|
|
223
223
|
});
|
|
224
224
|
}
|
|
225
225
|
|
|
226
|
-
|
|
227
|
-
|
|
228
226
|
return {
|
|
229
227
|
commandCreditsBuy,
|
|
230
228
|
commandCreditsTransactions,
|
|
@@ -1,15 +1,14 @@
|
|
|
1
|
-
import { requireFlag, usageError } from '
|
|
2
|
-
import { createCliError, exitAfterOutput } from '
|
|
3
|
-
import { findAgentApiKey, loadProfileConfig } from '
|
|
4
|
-
import { DEFAULT_CHAIN_ID, chainGasNote, isSvmChainId, parseChainIdFlag, resolveChainRpcUrl } from '
|
|
5
|
-
import { apiGet } from '
|
|
6
|
-
import { getEffectiveRunMode } from '
|
|
7
|
-
import { readWalletControl } from '
|
|
8
|
-
import { blockedResultFields } from '
|
|
9
|
-
import { assertSvmChainRunByApi } from '
|
|
10
|
-
import {
|
|
11
|
-
import {
|
|
12
|
-
import { runNotionalWarnings } from '../runtime/risk/notional.mjs';
|
|
1
|
+
import { requireFlag, usageError } from '../../core/args.mjs';
|
|
2
|
+
import { createCliError, exitAfterOutput } from '../../core/envelope.mjs';
|
|
3
|
+
import { findAgentApiKey, loadProfileConfig, resolveCreditsLedger } from '../../core/context.mjs';
|
|
4
|
+
import { DEFAULT_CHAIN_ID, chainGasNote, isSvmChainId, parseChainIdFlag, resolveChainRpcUrl } from '../../core/chainRegistry.mjs';
|
|
5
|
+
import { apiGet } from '../../core/http.mjs';
|
|
6
|
+
import { getEffectiveRunMode } from '../../core/runMode.mjs';
|
|
7
|
+
import { readWalletControl } from '../../runtime/execution/walletControl.mjs';
|
|
8
|
+
import { blockedResultFields } from '../../core/errorEnvelope.mjs';
|
|
9
|
+
import { applySvmLane, assertSvmChainRunByApi } from '../../runtime/execution/svmLane.mjs';
|
|
10
|
+
import { readSignedTxChainId } from '../../core/execution/signedTx.mjs';
|
|
11
|
+
import { runNotionalWarnings } from '../../runtime/risk/notional.mjs';
|
|
13
12
|
|
|
14
13
|
export function createWalletCommands(deps) {
|
|
15
14
|
const {
|
|
@@ -182,12 +181,6 @@ function resolveReadinessChain(flags) {
|
|
|
182
181
|
};
|
|
183
182
|
}
|
|
184
183
|
|
|
185
|
-
/**
|
|
186
|
-
* The agent's execution wallet on a chain, read with its own key (`GET /agent/execution-wallet`, as
|
|
187
|
-
* thirdfy-mcp agentWalletBootstrap): the API answer, the chain's gas note, wallet control (API 4.0),
|
|
188
|
-
* whether it holds the funding token, and whether it can sign (`ready`). Used by `readiness` and
|
|
189
|
-
* `wallet profile`.
|
|
190
|
-
*/
|
|
191
184
|
/**
|
|
192
185
|
* The agent an agent API key acts for. With an explicit --agent-api-key, only --agent-key or
|
|
193
186
|
* --user-did name it: an agent from env or config may belong to another key. Otherwise the env or
|
|
@@ -196,7 +189,7 @@ function resolveReadinessChain(flags) {
|
|
|
196
189
|
*/
|
|
197
190
|
function resolveAgentIdentity(flags) {
|
|
198
191
|
const explicitKey = Boolean(String(flags.agentApiKey || '').trim());
|
|
199
|
-
const agentKey = explicitKey ?
|
|
192
|
+
const agentKey = String((explicitKey ? flags.agentKey : resolveAgentKey(flags)) || '').trim().toLowerCase();
|
|
200
193
|
const explicitDid = String(flags.userDid || '').trim();
|
|
201
194
|
const userDid = explicitKey
|
|
202
195
|
? explicitDid || (agentKey ? `did:wallet:${agentKey}` : '')
|
|
@@ -213,6 +206,12 @@ function resolveAgentIdentity(flags) {
|
|
|
213
206
|
return { agentKey: agentKey || null, userDid };
|
|
214
207
|
}
|
|
215
208
|
|
|
209
|
+
/**
|
|
210
|
+
* The agent's execution wallet on a chain, read with its own key (`GET /agent/execution-wallet`, as
|
|
211
|
+
* thirdfy-mcp agentWalletBootstrap): the API answer, the chain's gas note, wallet control (API 4.0),
|
|
212
|
+
* whether it holds the funding token, and whether it can sign (`ready`). Used by `readiness` and
|
|
213
|
+
* `wallet profile`.
|
|
214
|
+
*/
|
|
216
215
|
async function readAgentExecutionWallet(ctx, flags, agentApiKey, chainId) {
|
|
217
216
|
const { agentKey, userDid } = resolveAgentIdentity(flags);
|
|
218
217
|
const query = new URLSearchParams({ chainId: String(chainId), runMode: 'agent_wallet' });
|
|
@@ -236,20 +235,17 @@ async function readAgentExecutionWallet(ctx, flags, agentApiKey, chainId) {
|
|
|
236
235
|
*/
|
|
237
236
|
async function commandWalletProfile(ctx, flags, capabilities) {
|
|
238
237
|
const meta = { apiBase: ctx.apiBase, capabilitiesVersion: capabilities?.contractVersion || null };
|
|
239
|
-
|
|
240
|
-
|
|
241
|
-
|
|
242
|
-
|
|
243
|
-
|
|
244
|
-
|
|
245
|
-
|
|
246
|
-
|
|
247
|
-
|
|
248
|
-
|
|
249
|
-
|
|
250
|
-
const explicitAgent = Boolean(String(flags.agentApiKey || '').trim());
|
|
251
|
-
const agentPath = !explicitOwner && (explicitAgent || (!ownerHeaders && Boolean(agentApiKey)));
|
|
252
|
-
if (!agentPath) {
|
|
238
|
+
// Same precedence as the credits commands (as thirdfy-mcp): an owner flag the caller passed, then an
|
|
239
|
+
// explicit --agent-api-key, then owner auth from env or config, then an agent key from env or config.
|
|
240
|
+
const { ledger, agentApiKey } = resolveCreditsLedger(flags);
|
|
241
|
+
if (ledger !== 'agent') {
|
|
242
|
+
const ownerHeaders = (() => {
|
|
243
|
+
try {
|
|
244
|
+
return buildOwnerAuthHeaders(flags, 'no owner auth');
|
|
245
|
+
} catch {
|
|
246
|
+
return null;
|
|
247
|
+
}
|
|
248
|
+
})();
|
|
253
249
|
if (!ownerHeaders) {
|
|
254
250
|
throw createCliError(
|
|
255
251
|
'OWNER_AUTH_REQUIRED',
|
|
@@ -1,6 +1,6 @@
|
|
|
1
|
-
import { loadProfileConfig } from '
|
|
2
|
-
import { parseJsonFlag, requireFlag } from '
|
|
3
|
-
import { apiGet, apiPost } from '
|
|
1
|
+
import { loadProfileConfig } from '../../core/context.mjs';
|
|
2
|
+
import { parseJsonFlag, requireFlag } from '../../core/args.mjs';
|
|
3
|
+
import { apiGet, apiPost } from '../../core/http.mjs';
|
|
4
4
|
|
|
5
5
|
/**
|
|
6
6
|
* The owner's side of API 4.0 wallet control (`/api/v1/agent/:agentKey/wallet-control/*`), for a
|
|
@@ -52,7 +52,7 @@ function solanaExecutionContract() {
|
|
|
52
52
|
'Solana execution runs only with --run-mode agent_wallet on chain 101 (103 devnet where a provider supports it). self, hybrid and thirdfy stay EVM-only. Check `actions --chain-id 101` (supportedChains) for each action\'s chains.',
|
|
53
53
|
};
|
|
54
54
|
}
|
|
55
|
-
export function createDiscoveryCommands({ printEnvelope, applyActionFilters, getProviderHintForActions, resolveChainSupport,
|
|
55
|
+
export function createDiscoveryCommands({ printEnvelope, applyActionFilters, getProviderHintForActions, resolveChainSupport, buildOwnerAuthHeaders, resolveAgentApiKey }) {
|
|
56
56
|
async function commandCatalogsList(ctx, flags, capabilities) {
|
|
57
57
|
const response = await apiGet(ctx, '/api/v1/agent/actions/catalog');
|
|
58
58
|
const actions = extractActions(response);
|
package/src/commands/doctor.mjs
CHANGED
|
@@ -3,7 +3,7 @@ import { requireFlag } from '../core/args.mjs';
|
|
|
3
3
|
import { apiGet, requestWithRouteFallback } from '../core/http.mjs';
|
|
4
4
|
import { loadProfileConfig, getProfileConfigPath, getCachedActionsCatalog } from '../core/context.mjs';
|
|
5
5
|
import { DEFAULT_API_BASE, PROFILE_DEFAULTS } from '../core/constants.mjs';
|
|
6
|
-
import { describeChainGas, parseChainIdFlag, resolveChainRpcUrl } from '../core/chainRegistry.mjs';
|
|
6
|
+
import { DEFAULT_CHAIN_ID, describeChainGas, parseChainIdFlag, pinnedRpcProvider, resolveChainRpcUrl } from '../core/chainRegistry.mjs';
|
|
7
7
|
import { exitAfterOutput } from '../core/envelope.mjs';
|
|
8
8
|
import { normalizeRunMode, normalizeManagedRunMode } from '../core/runMode.mjs';
|
|
9
9
|
import { buildExecutionCertificationReport } from '../runtime/certification/executionCertify.mjs';
|
|
@@ -63,13 +63,13 @@ async function commandDoctorSelf(ctx, flags) {
|
|
|
63
63
|
try {
|
|
64
64
|
if (!rpcUrl) throw new Error(`no known RPC for chain ${flags.chainId}; pass --rpc-url <url>`);
|
|
65
65
|
const ethers = await loadEthers();
|
|
66
|
-
const
|
|
66
|
+
const expectedChainId = parseChainIdFlag(flags.chainId);
|
|
67
|
+
const provider = pinnedRpcProvider(ethers, { rpcUrl, chainId: expectedChainId || DEFAULT_CHAIN_ID });
|
|
67
68
|
const block = await provider.getBlockNumber();
|
|
68
69
|
checks.push({ name: 'rpc-connectivity', ok: Number.isFinite(block), detail: `latestBlock=${block}` });
|
|
69
|
-
const expectedChainId = parseChainIdFlag(flags.chainId);
|
|
70
70
|
if (expectedChainId) {
|
|
71
|
-
|
|
72
|
-
const rpcChainId = Number(
|
|
71
|
+
// The provider's network is pinned, so ask the RPC itself which chain it serves.
|
|
72
|
+
const rpcChainId = Number(await provider.send('eth_chainId', []));
|
|
73
73
|
checks.push({
|
|
74
74
|
name: 'rpc-chain-id',
|
|
75
75
|
ok: rpcChainId === expectedChainId,
|
package/src/commands/execute.mjs
CHANGED
|
@@ -8,8 +8,8 @@ import {
|
|
|
8
8
|
} from '../core/runMode.mjs';
|
|
9
9
|
import { apiGet } from '../core/http.mjs';
|
|
10
10
|
import { applySvmLane } from '../runtime/execution/svmLane.mjs';
|
|
11
|
-
import { isReadOnlyResolvedAction } from '../core/readOnlyActions.mjs';
|
|
12
|
-
import { resolveWalletExecuteChainId } from '../core/walletExecuteChainId.mjs';
|
|
11
|
+
import { isReadOnlyResolvedAction } from '../core/execution/readOnlyActions.mjs';
|
|
12
|
+
import { resolveWalletExecuteChainId } from '../core/execution/walletExecuteChainId.mjs';
|
|
13
13
|
import { resolveExecuteEstimatedAmountUsd } from '../runtime/execution/payloads.mjs';
|
|
14
14
|
import { assertPreviewSized, buildPreviewOrder, shapeOrderPreview } from '../runtime/risk/orderPreview.mjs';
|
|
15
15
|
import { actionNameForApi } from '../runtime/actions/selection.mjs';
|
|
@@ -33,7 +33,6 @@ export function createExecuteCommands(deps) {
|
|
|
33
33
|
runPreflightByMode,
|
|
34
34
|
runExecutionByMode,
|
|
35
35
|
resolveManagedExecutionPreflight,
|
|
36
|
-
applyExecutionFallbackHints,
|
|
37
36
|
performSelfBroadcast,
|
|
38
37
|
executeManagedWalletRun,
|
|
39
38
|
executeSelfRun,
|
|
@@ -57,11 +56,7 @@ async function commandPreflight(ctx, flags, capabilities) {
|
|
|
57
56
|
|| (await applyLighterAgentWalletAddressDefault(ctx, flags, resolved, runMode))
|
|
58
57
|
|| (await applyAvantisAgentWalletAddressDefault(ctx, flags, resolved, runMode));
|
|
59
58
|
const backendResult = await runPreflightByMode(runMode, ctx, flags, resolved, { hybridWalletMode, managedPreflight });
|
|
60
|
-
const normalized =
|
|
61
|
-
flags,
|
|
62
|
-
runMode,
|
|
63
|
-
resolvedAction: resolved.resolvedAction,
|
|
64
|
-
});
|
|
59
|
+
const normalized = backendResult.normalized;
|
|
65
60
|
const data = flags.__polymarketSetupGuide
|
|
66
61
|
? {
|
|
67
62
|
...normalized,
|
|
@@ -195,11 +190,7 @@ async function commandRun(ctx, flags, capabilities) {
|
|
|
195
190
|
hybridWalletMode,
|
|
196
191
|
managedPreflight,
|
|
197
192
|
});
|
|
198
|
-
const normalized =
|
|
199
|
-
flags,
|
|
200
|
-
runMode,
|
|
201
|
-
resolvedAction: resolved.resolvedAction,
|
|
202
|
-
});
|
|
193
|
+
const normalized = backendResult.normalized;
|
|
203
194
|
if (runMode === 'self' && parseBooleanFlag(flags.broadcast, false) && normalized?.success) {
|
|
204
195
|
const executed = await performSelfBroadcast(ctx, flags, resolved.resolvedAction, normalized);
|
|
205
196
|
printEnvelope({
|
package/src/commands/index.mjs
CHANGED
|
@@ -1,10 +1,10 @@
|
|
|
1
|
-
export { createPolymarketCommands, resolveConfigAgentKey } from './polymarket.mjs';
|
|
2
|
-
export { createHyperliquidHelpers } from './hyperliquid.mjs';
|
|
3
|
-
export { createLighterHelpers } from './lighter.mjs';
|
|
4
|
-
export { createAvantisHelpers } from './avantis.mjs';
|
|
5
|
-
export { createHummingbotCommands } from './hummingbot.mjs';
|
|
6
|
-
export { createCondorCommands } from './condor.mjs';
|
|
1
|
+
export { createPolymarketCommands, resolveConfigAgentKey } from './venues/polymarket.mjs';
|
|
2
|
+
export { createHyperliquidHelpers } from './venues/hyperliquid.mjs';
|
|
3
|
+
export { createLighterHelpers } from './venues/lighter.mjs';
|
|
4
|
+
export { createAvantisHelpers } from './venues/avantis.mjs';
|
|
5
|
+
export { createHummingbotCommands } from './venues/hummingbot.mjs';
|
|
6
|
+
export { createCondorCommands } from './venues/condor.mjs';
|
|
7
7
|
export { createExecuteCommands } from './execute.mjs';
|
|
8
|
-
export { createWalletCommands } from './wallet.mjs';
|
|
9
|
-
export { createDelegationCommands } from './delegation.mjs';
|
|
10
|
-
export { createBootstrapCommands } from './bootstrap.mjs';
|
|
8
|
+
export { createWalletCommands } from './account/wallet.mjs';
|
|
9
|
+
export { createDelegationCommands } from './onboarding/delegation.mjs';
|
|
10
|
+
export { createBootstrapCommands } from './onboarding/bootstrap.mjs';
|
|
@@ -1,26 +1,26 @@
|
|
|
1
|
-
import { requireFlag, isNonInteractive, usageError } from '
|
|
2
|
-
import { createCliError } from '
|
|
3
|
-
import { PROFILE_DEFAULTS } from '
|
|
1
|
+
import { requireFlag, isNonInteractive, usageError } from '../../core/args.mjs';
|
|
2
|
+
import { createCliError } from '../../core/envelope.mjs';
|
|
3
|
+
import { PROFILE_DEFAULTS } from '../../core/constants.mjs';
|
|
4
4
|
import {
|
|
5
5
|
normalizeRunMode,
|
|
6
6
|
normalizeProfileName,
|
|
7
7
|
normalizeCustodyMode,
|
|
8
8
|
defaultCustodyModeForRunMode,
|
|
9
9
|
parseBooleanFlag,
|
|
10
|
-
} from '
|
|
10
|
+
} from '../../core/runMode.mjs';
|
|
11
11
|
import {
|
|
12
12
|
loadProfileConfig,
|
|
13
13
|
persistProfileConfig,
|
|
14
14
|
clonePlainConfigTree,
|
|
15
15
|
setNestedConfigValue,
|
|
16
16
|
getProfileConfigPath,
|
|
17
|
-
} from '
|
|
18
|
-
import { apiGet, apiPost, requestWithRouteFallback } from '
|
|
19
|
-
import { isEvmAddress, isSolanaAddress } from '
|
|
17
|
+
} from '../../core/context.mjs';
|
|
18
|
+
import { apiGet, apiPost, requestWithRouteFallback } from '../../core/http.mjs';
|
|
19
|
+
import { isEvmAddress, isSolanaAddress } from '../../core/chainRegistry.mjs';
|
|
20
20
|
import { createRequire } from 'module';
|
|
21
21
|
|
|
22
22
|
const require = createRequire(import.meta.url);
|
|
23
|
-
const { version: CLI_VERSION } = require('
|
|
23
|
+
const { version: CLI_VERSION } = require('../../../package.json');
|
|
24
24
|
|
|
25
25
|
export function createBootstrapCommands(deps) {
|
|
26
26
|
const {
|
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
import { requireFlag } from '
|
|
2
|
-
import { apiGet, apiPost } from '
|
|
1
|
+
import { requireFlag } from '../../core/args.mjs';
|
|
2
|
+
import { apiGet, apiPost } from '../../core/http.mjs';
|
|
3
3
|
|
|
4
4
|
/** Aligned with chat.mjs NETWORK_CHAIN_IDS and thirdfy-mcp consoleMandateChains. */
|
|
5
5
|
const CONSOLE_MANDATE_NETWORK_CHAIN_IDS = {
|
|
@@ -1,48 +1,35 @@
|
|
|
1
1
|
import { createRequire } from 'module';
|
|
2
|
-
import { requireFlag, parseJsonFlag } from '
|
|
3
|
-
import { requestWithRouteFallback } from '
|
|
4
|
-
import { createCliError } from '
|
|
5
|
-
import { BITFINEX_PERMISSION_PROFILES, DEFAULT_BITFINEX_BASE_URL } from '../core/constants.mjs';
|
|
6
|
-
import { parseBooleanFlag } from '../core/runMode.mjs';
|
|
2
|
+
import { requireFlag, parseJsonFlag } from '../../core/args.mjs';
|
|
3
|
+
import { requestWithRouteFallback } from '../../core/http.mjs';
|
|
4
|
+
import { createCliError } from '../../core/envelope.mjs';
|
|
7
5
|
|
|
8
6
|
const require = createRequire(import.meta.url);
|
|
9
|
-
const { normalizeCredentialStatus } = require('
|
|
10
|
-
|
|
7
|
+
const { normalizeCredentialStatus } = require('../../utils/cli/delegationNormalization.cjs');
|
|
8
|
+
/** `credentials upsert` flags of the removed Bitfinex permission probe: accepted, ignored, and named in a warning. */
|
|
9
|
+
const REMOVED_BITFINEX_FLAGS = [
|
|
10
|
+
['permissionProfile', '--permission-profile'],
|
|
11
|
+
['verifyPermissions', '--verify-permissions'],
|
|
12
|
+
['skipPermissionsProbe', '--skip-permissions-probe'],
|
|
13
|
+
['bitfinexBaseUrl', '--bitfinex-base-url'],
|
|
14
|
+
];
|
|
15
|
+
|
|
16
|
+
export function createCredentialsCommands({ printEnvelope, getAuthToken, buildOwnerAuthHeaders }) {
|
|
11
17
|
async function commandCredentialsUpsert(ctx, flags, capabilities) {
|
|
12
18
|
const authToken = getAuthToken(flags, 'Missing --auth-token (or THIRDFY_AUTH_TOKEN) for credentials upsert');
|
|
13
19
|
const venue = requireFlag(flags, 'venue', 'Missing --venue');
|
|
14
|
-
const permissionProfile = String(flags.permissionProfile || 'funding').trim().toLowerCase();
|
|
15
|
-
const bitfinexProfile =
|
|
16
|
-
String(venue).trim().toLowerCase() === 'bitfinex'
|
|
17
|
-
? BITFINEX_PERMISSION_PROFILES[permissionProfile] || BITFINEX_PERMISSION_PROFILES.funding
|
|
18
|
-
: null;
|
|
19
20
|
const payload = {
|
|
20
21
|
venue,
|
|
21
22
|
apiKey: requireFlag(flags, 'apiKey', 'Missing --api-key'),
|
|
22
23
|
apiSecret: requireFlag(flags, 'apiSecret', 'Missing --api-secret'),
|
|
23
24
|
credentialType: String(flags.credentialType || 'api_key'),
|
|
24
|
-
credentialRef: String(flags.credentialRef ||
|
|
25
|
+
credentialRef: String(flags.credentialRef || ''),
|
|
25
26
|
};
|
|
26
27
|
if (flags.passphrase) payload.passphrase = String(flags.passphrase);
|
|
27
28
|
if (flags.metadata) payload.metadata = parseJsonFlag(flags, 'metadata');
|
|
28
29
|
if (flags.policy) payload.policy = parseJsonFlag(flags, 'policy');
|
|
29
30
|
if (flags.agentKey) payload.agentKey = String(flags.agentKey).trim();
|
|
30
31
|
if (flags.chainId) payload.chainId = Number(flags.chainId);
|
|
31
|
-
const
|
|
32
|
-
String(venue).trim().toLowerCase() === 'bitfinex' &&
|
|
33
|
-
!parseBooleanFlag(flags.skipPermissionsProbe, false) &&
|
|
34
|
-
parseBooleanFlag(flags.verifyPermissions, true);
|
|
35
|
-
let permissionProbe = null;
|
|
36
|
-
if (probeEnabled) {
|
|
37
|
-
permissionProbe = await probeBitfinexPermissions({
|
|
38
|
-
apiKey: payload.apiKey,
|
|
39
|
-
apiSecret: payload.apiSecret,
|
|
40
|
-
permissionProfile: bitfinexProfile?.id || 'funding',
|
|
41
|
-
timeoutMs: ctx.timeoutMs,
|
|
42
|
-
baseUrl: String(flags.bitfinexBaseUrl || process.env.BITFINEX_BASE_URL || DEFAULT_BITFINEX_BASE_URL),
|
|
43
|
-
});
|
|
44
|
-
}
|
|
45
|
-
|
|
32
|
+
const ignoredFlags = REMOVED_BITFINEX_FLAGS.filter(([key]) => flags[key] !== undefined).map(([, flag]) => flag);
|
|
46
33
|
const response = await requestWithRouteFallback(ctx, {
|
|
47
34
|
method: 'POST',
|
|
48
35
|
routes: ['/api/v1/agent/delegation/credentials/upsert', '/api/v1/agent/agent/delegation/credentials/upsert'],
|
|
@@ -58,8 +45,8 @@ async function commandCredentialsUpsert(ctx, flags, capabilities) {
|
|
|
58
45
|
data: response,
|
|
59
46
|
meta: {
|
|
60
47
|
apiBase: ctx.apiBase,
|
|
61
|
-
permissionProbe,
|
|
62
48
|
capabilitiesVersion: capabilities?.contractVersion || null,
|
|
49
|
+
...(ignoredFlags.length ? { warnings: [`Ignored ${ignoredFlags.join(', ')}: Bitfinex support was removed. Drop these flags; they will stop being accepted in the next minor version.`] } : {}),
|
|
63
50
|
},
|
|
64
51
|
});
|
|
65
52
|
}
|