diff --git a/packages/cli/CHANGELOG.md b/packages/cli/CHANGELOG.md index 60cf35f..07dd71a 100644 --- a/packages/cli/CHANGELOG.md +++ b/packages/cli/CHANGELOG.md @@ -4,6 +4,12 @@ All notable changes to the `nirium-cli` package are documented here. ## Unreleased +## 3.1.1 - 2026-11-07 + +### Fixed + +- `nirium verify` with no `--gateway` tried only `gateway.pinata.cloud`, which often takes 5-7s and can hit the 8s timeout, so a healthy CID failed to verify. It now tries Filebase's dedicated gateway first, then Pinata, `ipfs.io` and `dweb.link` - the same chain the `verify-audit-cid` Action has used since [#259](https://github.com/nirium-protocol/nirium/pull/259), plus Pinata. Passing `--gateway` still replaces the default list. + ## 3.1.0 - 2026-11-07 ### Added diff --git a/packages/cli/README.md b/packages/cli/README.md index b18b975..4d44361 100644 --- a/packages/cli/README.md +++ b/packages/cli/README.md @@ -288,7 +288,11 @@ Signatures are accepted as base64 or hex, raw ed25519 or SEP-53 short backoff first - a fresh pin can take a moment to propagate, so a 404 there doesn't mean the CID is wrong, just not there *yet*. Any other failure (a real error, or a timed-out request) moves straight to the -next gateway instead, since retrying the same one won't help: +next gateway instead, since retrying the same one won't help. + +With no `--gateway`, it tries Filebase's dedicated gateway, then Pinata, +then `ipfs.io`, then `dweb.link`. Shared public gateways often answer +`429` under load, so the dedicated one goes first: ```bash nirium verify --gateway https://gateway.pinata.cloud --gateway https://ipfs.io --retries 3 @@ -296,7 +300,7 @@ nirium verify --gateway https://gateway.pinata.cloud --gateway https://ipf | Option | Purpose | Default | |---|---|---| -| `-g, --gateway ` | IPFS gateway to fetch from - repeat for fallbacks | `https://gateway.pinata.cloud` | +| `-g, --gateway ` | IPFS gateway to fetch from - repeat for fallbacks | `nirium.myfilebase.com`, then `gateway.pinata.cloud`, `ipfs.io`, `dweb.link` | | `--retries ` | retries per gateway on a 404, with backoff | `2` | | `--timeout ` | per-request timeout | `8000` | | `--json` | machine-readable result | off | diff --git a/packages/cli/bin/nirium.js b/packages/cli/bin/nirium.js index e273e8d..dcf08e7 100755 --- a/packages/cli/bin/nirium.js +++ b/packages/cli/bin/nirium.js @@ -158,11 +158,22 @@ program } }); +// Tried in order when no --gateway is given. ipfs.io and dweb.link answer 429 +// for healthy CIDs under load (#185), and Pinata serves our pins but often +// takes 5-7s, so a dedicated gateway goes first. Same chain as the +// verify-audit-cid Action (#259), plus Pinata. +const DEFAULT_GATEWAYS = [ + 'https://nirium.myfilebase.com', + 'https://gateway.pinata.cloud', + 'https://ipfs.io', + 'https://dweb.link', +]; + // --- COMMAND: verify --- program .command('verify') .argument('', 'IPFS Content Identifier (CID) of the audit document') - .option('-g, --gateway ', 'IPFS gateway URL - repeatable, tried in order as fallbacks', (val, prev) => [...(prev || []), val], []) + .option('-g, --gateway ', 'IPFS gateway URL - repeatable, tried in order as fallbacks (default: Filebase, Pinata, ipfs.io, dweb.link)', (val, prev) => [...(prev || []), val], []) .option('--retries ', 'Retries per gateway on a 404 (content may not be propagated yet), with backoff', '2') .option('--timeout ', 'Per-request timeout in milliseconds', '8000') .option('--json', 'Output result as JSON') @@ -191,7 +202,7 @@ program process.exit(1); } - const gateways = options.gateway.length > 0 ? options.gateway : ['https://gateway.pinata.cloud']; + const gateways = options.gateway.length > 0 ? options.gateway : DEFAULT_GATEWAYS; const result = await fetchAndVerifyCid(cid, gateways, globalThis.fetch, { expectedHash, retries, timeoutMs }); if (options.json) { console.log(JSON.stringify(result, null, 2)); diff --git a/packages/cli/package.json b/packages/cli/package.json index f18e185..d59985d 100644 --- a/packages/cli/package.json +++ b/packages/cli/package.json @@ -1,6 +1,6 @@ { "name": "nirium-cli", - "version": "3.1.0", + "version": "3.1.1", "description": "Nirium CLI \u2014 scaffold Stellar agent projects and check agent status", "main": "bin/nirium.js", "type": "module", diff --git a/packages/cli/test/verify-retry-gateway.test.js b/packages/cli/test/verify-retry-gateway.test.js index 070bc3d..07b7b68 100644 --- a/packages/cli/test/verify-retry-gateway.test.js +++ b/packages/cli/test/verify-retry-gateway.test.js @@ -161,3 +161,15 @@ test('--timeout rejects a non-positive value', async () => { assert.equal(r.code, 1); assert.match(r.stderr, /Invalid --timeout/); }); + +test('no --gateway given: tries the default chain in order (Filebase, Pinata, ipfs.io, dweb.link)', async () => { + // 1ms timeout aborts every request before it reaches the network, so this + // checks only the order of the default list, never a real gateway's answer. + const r = await run(['--timeout', '1', '--retries', '0']); + assert.equal(r.code, 1); + const json = JSON.parse(r.stdout); + assert.deepEqual( + json.attempts.map((a) => a.gateway), + ['https://nirium.myfilebase.com', 'https://gateway.pinata.cloud', 'https://ipfs.io', 'https://dweb.link'], + ); +});