nansen-cli 1.6.0 → 1.8.0

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/AGENTS.md ADDED
@@ -0,0 +1,176 @@
1
+ # AGENTS.md — Contributor Guide
2
+
3
+ Guidance for AI coding agents (Claude Code, Codex, Copilot, etc.) working on this repository. If you're an agent **using** the CLI, see [README.md](README.md).
4
+
5
+ ## Architecture
6
+
7
+ ```
8
+ src/
9
+ ├── index.js # Entry point (shebang, calls runCLI)
10
+ ├── cli.js # Command router, arg parsing, schema, help text
11
+ ├── api.js # NansenAPI client (REST, retry, cache, x402 auto-pay)
12
+ ├── wallet.js # Wallet CRUD (create/list/show/export/delete/send)
13
+ ├── trading.js # Quote + execute swaps (OKX router via API)
14
+ ├── transfer.js # Token/native transfers (EVM + Solana)
15
+ ├── x402.js # x402 payment orchestration (picks network, signs)
16
+ ├── x402-evm.js # EVM payment signing (EIP-3009 transferWithAuthorization)
17
+ ├── x402-svm.js # Solana payment signing (SPL transfer)
18
+ ├── crypto.js # Key encryption/decryption (AES-256-GCM or plaintext)
19
+ └── update-check.js # Version upgrade notice
20
+ ```
21
+
22
+ ### Command routing
23
+
24
+ `src/index.js` → `runCLI()` in `src/cli.js`
25
+
26
+ Commands are built by three functions, merged in `runCLI()`:
27
+ - `buildCommands()` in cli.js — analytics commands (smart-money, profiler, token, etc.)
28
+ - `buildWalletCommands()` in wallet.js — wallet subcommands
29
+ - `buildTradingCommands()` in trading.js — quote/execute
30
+
31
+ Commands listed in `NO_AUTH_COMMANDS` skip API initialization. Everything else instantiates `NansenAPI` with retry, cache, and x402 config.
32
+
33
+ ### Data flow: trade
34
+
35
+ ```
36
+ CLI args → api.js GET /defi/quote → quote response
37
+ → wallet.js decrypt key → trading.js sign tx → api.js POST /defi/execute → broadcast
38
+ ```
39
+
40
+ ### Data flow: x402 auto-pay
41
+
42
+ ```
43
+ api.js (any call) → 402 response with payment requirements
44
+ → x402.js rankRequirements() → picks cheapest network (EVM first)
45
+ → x402-evm.js or x402-svm.js → sign USDC payment
46
+ → api.js retries original request with Payment-Signature header
47
+ ```
48
+
49
+ If EVM payment fails (insufficient funds), the async generator yields a Solana signature as fallback.
50
+
51
+ ### Output convention
52
+
53
+ Core functions return data objects. The CLI layer formats via `formatOutput()`. Never `console.log` in core functions — use the `log` dependency injection for CLI output.
54
+
55
+ ## Development
56
+
57
+ ```bash
58
+ npm install # Install dependencies
59
+ npm test # Run tests (vitest)
60
+ npm run test:watch # Watch mode
61
+ npm run test:coverage # With coverage
62
+ ```
63
+
64
+ ### Running locally
65
+
66
+ ```bash
67
+ node src/index.js <command> [options]
68
+
69
+ # Examples
70
+ node src/index.js wallet create my-wallet
71
+ node src/index.js smart-money --chain solana --limit 5
72
+ ```
73
+
74
+ ## Testing
75
+
76
+ - **Framework:** Vitest
77
+ - **Test files:** `src/__tests__/*.test.js`
78
+ - **Current:** 577 tests across 13 test files
79
+ - **All new code must have tests**
80
+ - **Mock all RPC/API calls** — never hit real networks in tests
81
+
82
+ ### Test structure
83
+
84
+ ```js
85
+ import { describe, it, expect, vi, beforeEach } from 'vitest';
86
+
87
+ global.fetch = vi.fn();
88
+
89
+ describe('featureName', () => {
90
+ beforeEach(() => {
91
+ fetch.mockReset();
92
+ });
93
+
94
+ it('should do the thing', async () => {
95
+ fetch.mockResolvedValueOnce({
96
+ ok: true,
97
+ json: async () => ({ jsonrpc: '2.0', result: '0x...', id: 1 })
98
+ });
99
+ // test logic
100
+ });
101
+ });
102
+ ```
103
+
104
+ ### Required RPC mocks by code path
105
+
106
+ **EVM transfers:** `eth_getBalance`, `eth_gasPrice`, `eth_maxPriorityFeePerGas`, `eth_getTransactionCount`, `eth_estimateGas`, `eth_getCode`, `eth_sendRawTransaction`, `eth_getTransactionReceipt`
107
+
108
+ **Solana transfers:** `getBalance`, `getLatestBlockhash`, `sendTransaction`, `getSignatureStatuses`
109
+
110
+ **SPL token transfers** (additionally): `getTokenAccountsByOwner`, `getAccountInfo`
111
+
112
+ **Wallet operations:** No RPC mocks needed (file I/O only). Mock `fs` if testing file paths.
113
+
114
+ **API calls:** Mock `fetch` to return `{ ok: true, json: () => ({...}) }` or `{ ok: false, status: 402, headers: new Headers({...}) }` for x402 paths.
115
+
116
+ ## Style Guide
117
+
118
+ - **ESM only** (`import`/`export`). No TypeScript, no transpilation.
119
+ - **No interactive prompts in core functions.** Use env vars: `NANSEN_WALLET_PASSWORD`, `NANSEN_API_KEY`.
120
+ - **Error handling:** `throw new Error('descriptive message')` in core. CLI catches and formats.
121
+ - **Actionable error messages** — tell the user what to do:
122
+ - ❌ `"Authentication failed"`
123
+ - ✅ `"Not logged in. Run: nansen login"`
124
+ - **BigInt for token amounts.** Never use floating point. Parse to BigInt with decimals.
125
+ - **Chain branching:** Use `chain === 'solana'` checks, not inheritance/polymorphism.
126
+ - **Minimal dependencies.** Prefer Node.js built-in APIs (crypto, fs, path, http).
127
+
128
+ ## PR Checklist
129
+
130
+ - [ ] `npm test` passes (all tests)
131
+ - [ ] New code paths have test coverage
132
+ - [ ] No hardcoded secrets, API keys, or private keys
133
+ - [ ] No `console.log` in core functions (use `log` dep injection)
134
+ - [ ] Error messages are actionable (tell user what to do)
135
+ - [ ] CLI help text updated if adding/changing commands
136
+ - [ ] RPC mocks cover all methods in the code path
137
+ - [ ] Wallet flows work both with and without `NANSEN_WALLET_PASSWORD`
138
+ - [ ] Changeset added if changing user-facing behavior (add a `.changeset/<name>.md` file — `npm test` will warn if missing)
139
+
140
+ ## Chains & Networks
141
+
142
+ **EVM:** Ethereum (chain ID 1), Base (8453). `CHAIN_IDS` in transfer.js only maps these two — other EVM chains will fail for transfers.
143
+
144
+ **Solana:** mainnet-beta. Supports native SOL, standard SPL tokens, and Token-2022 (Token Extensions).
145
+
146
+ **RPC endpoints:** Hardcoded in `CHAIN_RPCS` (transfer.js). Nansen API handles RPC for trading.
147
+
148
+ ## Key Constants
149
+
150
+ | Constant | Value |
151
+ |----------|-------|
152
+ | USDC (Base) | `0x833589fCD6eDb6E08f4c7C32D4f71b54bdA02913` |
153
+ | USDC (Solana) | `EPjFWdd5AufqSSqeM2qN1xzybapC8G4wEGGkZwyTDt1v` |
154
+ | x402 payment | $0.05 USDC per API call |
155
+ | Gas buffer | API provides `quote.gas` with 1.5x multiplier — use directly |
156
+
157
+ ## Endpoint Quirks
158
+
159
+ These are internal details agents should know when writing or debugging tests:
160
+
161
+ - **`token holders --smart-money`** — Returns `UNSUPPORTED_FILTER` for tokens without smart money tracking. Not all tokens have this data.
162
+ - **`token flow-intelligence`** — May return all-zero flows for illiquid tokens. Normal, not an error.
163
+ - **`token screener --search`** — Client-side filtering. The CLI fetches up to 500 results, then filters locally.
164
+ - **`--fields`** — Applies to the entire response tree, including the `success`/`data` wrapper.
165
+ - **Profiler beta endpoints** use `recordsPerPage` instead of `per_page`. The CLI handles this automatically.
166
+ - **`profiler perp-positions`** — No pagination support; the API ignores the pagination parameter.
167
+
168
+ ## Known Gotchas
169
+
170
+ 1. **EIP-7702 delegated accounts** on Base have contract code. Always use `eth_estimateGas`, never hardcode 21000 gas.
171
+ 2. **Solana SPL account ordering:** Writable accounts (destATA) must precede readonly (mint) in the transaction message.
172
+ 3. **`getSignatureStatuses`** over `confirmTransaction` — the latter is deprecated and unreliable on public RPCs.
173
+ 4. **`--max` native SOL:** Reserve 5000 lamports for fee. On EVM L2s, reserve 3x estimated gas for L1 data posting fees.
174
+ 5. **Token-2022:** Use `TOKEN_2022_PROGRAM_ID` and `TransferCheckedInstruction` (not plain `Transfer`).
175
+ 6. **CreateATA path:** When recipient doesn't have a token account, the sender creates it. This path in transfer.js has limited test coverage — add tests if modifying.
176
+ 7. **`CHAIN_IDS` is incomplete:** Only ethereum and base are mapped. Adding new EVM chain support requires updating this map.
package/CLAUDE.md CHANGED
@@ -125,7 +125,7 @@ Returns JSON with all commands, subcommands, option types/defaults, return field
125
125
 
126
126
  ### Field Filtering
127
127
  ```bash
128
- nansen smart-money netflow --fields token_symbol,net_flow_usd,chain
128
+ nansen research smart-money netflow --fields token_symbol,net_flow_usd,chain
129
129
  ```
130
130
  Reduces response size by including only specified fields. Works with nested data structures.
131
131
 
@@ -180,41 +180,38 @@ Structured error codes for programmatic handling:
180
180
 
181
181
  ## Publishing (npm)
182
182
 
183
- **⚠️ DO NOT manually run `npm version` or `npm publish`. CI handles everything.**
183
+ **DO NOT manually run `npm version` or `npm publish`. CI handles everything.**
184
184
 
185
- ### How it works:
185
+ 1. **Push to main** — CI runs tests
186
+ 2. **CI creates a "Version Packages" PR** — bumps version + updates CHANGELOG
187
+ 3. **Merge the Version PR** — CI auto-publishes to npm
186
188
 
187
- 1. **Add a changeset** for user-facing changes:
188
- ```bash
189
- npx changeset
190
- # Or manually create .changeset/<name>.md
191
- ```
189
+ If you mess up: accidentally bumped version manually? `git revert` and add a changeset instead. CI publish failed? Check GitHub Actions logs, likely needs `NPM_TOKEN` secret refresh.
192
190
 
193
- 2. **Push to main** — CI runs tests
191
+ ## Changesets
194
192
 
195
- 3. **CI creates a "Version Packages" PR** This bumps version + updates CHANGELOG
193
+ Every PR that changes user-facing behavior **must** include a changeset file. `npm test` will warn if one is missing. The changeset description ends up in CHANGELOG.md (auto-generated by CI), so write it as a user-facing changelog entry.
196
194
 
197
- 4. **Merge the Version PR** CI auto-publishes to npm
195
+ **Needs a changeset:** new features, bug fixes, breaking changes, changed CLI output, new/modified commands.
196
+
197
+ **Does NOT need a changeset:** docs-only, test-only, refactors with no behavior change, CI/tooling.
198
+
199
+ Add a file to `.changeset/` with a descriptive kebab-case name:
198
200
 
199
- ### Changeset format:
200
201
  ```markdown
201
202
  ---
202
203
  "nansen-cli": minor
203
204
  ---
204
205
 
205
- Description of changes (appears in CHANGELOG)
206
+ Short description of the change (appears in CHANGELOG)
206
207
  ```
207
208
 
208
- Choose: `patch` (bug fixes), `minor` (new features), `major` (breaking changes)
209
-
210
- ### If you mess up:
211
- - Accidentally bumped version manually? `git revert` and add a changeset instead
212
- - CI publish failed? Check GitHub Actions logs, likely needs `NPM_TOKEN` secret refresh
209
+ Use `patch` for bug fixes, `minor` for new features, `major` for breaking changes.
213
210
 
214
211
  ## PR Checklist
215
212
 
216
213
  - [ ] Tests pass (`npm test`)
217
214
  - [ ] New endpoints have tests in all 3 test files
218
215
  - [ ] README.md updated if adding user-facing features
219
- - [ ] CHANGELOG.md updated for releases
216
+ - [ ] Changeset added for user-facing changes (see above)
220
217
  - [ ] No new dependencies (keep it lightweight)
package/README.md CHANGED
@@ -2,8 +2,7 @@
2
2
 
3
3
  [![npm version](https://img.shields.io/npm/v/nansen-cli.svg)](https://www.npmjs.com/package/nansen-cli)
4
4
  [![License: MIT](https://img.shields.io/badge/License-MIT-yellow.svg)](https://opensource.org/licenses/MIT)
5
- [![Tests](https://img.shields.io/badge/tests-325%20passing-brightgreen.svg)]()
6
- [![Coverage](https://img.shields.io/badge/coverage-83%25-brightgreen.svg)]()
5
+ [![Tests](https://img.shields.io/badge/tests-577%20passing-brightgreen.svg)]()
7
6
 
8
7
  > **Built by agents, for agents.** We prioritize the best possible AI agent experience.
9
8
 
@@ -27,39 +26,83 @@ npm link
27
26
 
28
27
  ## Configuration
29
28
 
30
- **Option 1: Interactive login (recommended)**
29
+ ### For AI Agents (Recommended)
30
+
31
+ Use the [AI Agent Setup](https://app.nansen.ai/auth/agent-setup) flow:
32
+
33
+ 1. Your agent will ask you to visit: **[app.nansen.ai/auth/agent-setup](https://app.nansen.ai/auth/agent-setup)**
34
+ 2. Sign in with your Nansen account
35
+ 3. Copy the message shown
36
+ 4. Paste it back to your agent
37
+
38
+ Your agent saves the key and handles everything else automatically.
39
+
40
+ ### Manual Setup
41
+
42
+ **Option 1: Interactive login**
31
43
  ```bash
32
44
  nansen login
33
45
  # Enter your API key when prompted
34
46
  # ✓ Saved to ~/.nansen/config.json
35
47
  ```
36
48
 
37
- **Option 2: Environment variable**
49
+ **Option 2: Environment variable (best for agents)**
38
50
  ```bash
39
51
  export NANSEN_API_KEY=your-api-key
40
52
  ```
41
53
 
54
+ **Option 3: Direct config file**
55
+ ```bash
56
+ mkdir -p ~/.nansen && echo '{"apiKey":"<key>","baseUrl":"https://api.nansen.ai"}' > ~/.nansen/config.json && chmod 600 ~/.nansen/config.json
57
+ ```
58
+
42
59
  Get your API key at [app.nansen.ai/api](https://app.nansen.ai/api).
43
60
 
61
+ ### Auth Priority
62
+
63
+ 1. `NANSEN_API_KEY` env var (highest)
64
+ 2. `~/.nansen/config.json` file
65
+ 3. Interactive prompt
66
+
67
+ ### Verify It Works
68
+
69
+ ```bash
70
+ # Check CLI is installed (no API key needed):
71
+ nansen schema | head -1
72
+
73
+ # Verify API access:
74
+ nansen research token screener --chain solana --limit 1
75
+ ```
76
+
44
77
  ## Quick Start
45
78
 
46
79
  ```bash
47
80
  # Get trending tokens on Solana
48
- nansen token screener --chain solana --timeframe 24h --pretty
81
+ nansen research token screener --chain solana --timeframe 24h --pretty
49
82
 
50
83
  # Check Smart Money activity
51
- nansen smart-money netflow --chain solana --pretty
84
+ nansen research smart-money netflow --chain solana --pretty
52
85
 
53
86
  # Profile a wallet
54
- nansen profiler balance --address 0x28c6c06298d514db089934071355e5743bf21d60 --chain ethereum --pretty
87
+ nansen research profiler balance --address 0x28c6c06298d514db089934071355e5743bf21d60 --chain ethereum --pretty
55
88
 
56
- # Search for an entity
57
- nansen profiler search --query "Vitalik Buterin" --pretty
89
+ # Search for tokens/entities
90
+ nansen research search "Vitalik Buterin" --pretty
58
91
  ```
59
92
 
60
93
  ## Commands
61
94
 
62
- ### `smart-money` - Smart Money Analytics
95
+ All analytics live under `nansen research`, trading under `nansen trade`, and wallet management under `nansen wallet`.
96
+
97
+ ### `research` - Research & Analytics
98
+
99
+ ```
100
+ nansen research <category> <subcommand> [options]
101
+ ```
102
+
103
+ **Category aliases:** `sm` (smart-money), `tgm` (token), `prof` (profiler), `port` (portfolio)
104
+
105
+ #### `research smart-money` - Smart Money Analytics
63
106
 
64
107
  Track trading and holding activity of sophisticated market participants.
65
108
 
@@ -72,17 +115,19 @@ Track trading and holding activity of sophisticated market participants.
72
115
  | `dcas` | DCA strategies on Jupiter |
73
116
  | `historical-holdings` | Historical holdings over time |
74
117
 
75
- **Smart Money Labels:**
76
- - `Fund` - Institutional investment funds
77
- - `Smart Trader` - Historically profitable traders
78
- - `30D Smart Trader` - Top performers (30-day window)
79
- - `90D Smart Trader` - Top performers (90-day window)
80
- - `180D Smart Trader` - Top performers (180-day window)
81
- - `Smart HL Perps Trader` - Profitable Hyperliquid traders
118
+ **Smart Money Labels:** `Fund`, `Smart Trader`, `30D Smart Trader`, `90D Smart Trader`, `180D Smart Trader`, `Smart HL Perps Trader`
119
+
120
+ #### `research profiler` - Wallet Profiling
82
121
 
83
- ### `profiler` - Wallet Profiling
122
+ **ENS Name Resolution:** You can use `.eth` names anywhere an `--address` is accepted:
123
+
124
+ ```bash
125
+ nansen research profiler balance --address vitalik.eth
126
+ nansen research profiler labels --address nansen.eth --chain ethereum
127
+ nansen research profiler transactions --address vitalik.eth --table
128
+ ```
84
129
 
85
- Detailed information about any blockchain address.
130
+ ENS names are automatically resolved to `0x` addresses via public APIs (with onchain RPC fallback). Works on all EVM chains. The resolved name and address are included as `_ens` metadata in JSON output.
86
131
 
87
132
  | Subcommand | Description |
88
133
  |------------|-------------|
@@ -98,9 +143,7 @@ Detailed information about any blockchain address.
98
143
  | `perp-positions` | Current perpetual positions |
99
144
  | `perp-trades` | Perpetual trading history |
100
145
 
101
- ### `token` - Token God Mode
102
-
103
- Deep analytics for any token.
146
+ #### `research token` - Token God Mode
104
147
 
105
148
  | Subcommand | Description |
106
149
  |------------|-------------|
@@ -113,53 +156,51 @@ Deep analytics for any token.
113
156
  | `flow-intelligence` | Detailed flow intelligence by label |
114
157
  | `transfers` | Token transfer history |
115
158
  | `jup-dca` | Jupiter DCA orders for token |
159
+ | `ohlcv` | OHLCV candle data for a token |
116
160
  | `perp-trades` | Perp trades by token symbol |
117
161
  | `perp-positions` | Open perp positions by token symbol |
118
162
  | `perp-pnl-leaderboard` | Perp PnL leaderboard by token |
119
163
 
120
- ### `portfolio` - Portfolio Analytics
121
-
122
- | Subcommand | Description |
123
- |------------|-------------|
124
- | `defi` | DeFi holdings across protocols |
164
+ #### `research search` / `research perp` / `research portfolio` / `research points`
125
165
 
126
- ### `search` - Search
166
+ See `nansen research help` or `nansen schema --pretty` for full details.
127
167
 
128
- Search for tokens and entities across Nansen.
168
+ ### `trade` - DEX Trading
129
169
 
130
170
  ```bash
131
- nansen search "uniswap" --pretty
132
- nansen search "uniswap" --type token --chain ethereum
171
+ # Get a swap quote
172
+ nansen trade quote --from USDC --to SOL --amount 10 --chain solana
173
+
174
+ # Execute the swap
175
+ nansen trade execute --from USDC --to SOL --amount 10 --chain solana
133
176
  ```
134
177
 
135
- | Option | Description |
136
- |--------|-------------|
137
- | `--type` | Filter by result type: `token`, `entity`, or `any` (default) |
138
- | `--chain` | Filter by chain |
139
- | `--limit` | Max results, 1-50 (default: 25) |
178
+ ### `wallet` - Local Wallet Management
179
+
180
+ | Subcommand | Description |
181
+ |------------|-------------|
182
+ | `create` | Create a new wallet (EVM + Solana keypair) |
183
+ | `list` | List all wallets |
184
+ | `show` | Show wallet addresses |
185
+ | `export` | Export private keys |
186
+ | `default` | Set default wallet |
187
+ | `delete` | Delete a wallet |
188
+ | `send` | Send tokens (native or ERC-20/SPL) |
189
+
190
+ Wallets are passwordless by default (keys stored like SSH keys). Set `NANSEN_WALLET_PASSWORD` env var for encryption at rest.
140
191
 
141
192
  ### `schema` - Schema Discovery
142
193
 
143
- Output JSON schema for agent introspection. No API key required.
194
+ No API key required. Machine-readable command reference for agent introspection.
144
195
 
145
196
  ```bash
146
- # Get full schema
147
- nansen schema --pretty
148
-
149
- # Get schema for specific command
150
- nansen schema smart-money --pretty
197
+ nansen schema --pretty # All commands
198
+ nansen schema research --pretty # Research commands
151
199
  ```
152
200
 
153
- Returns command definitions, option types/defaults, supported chains, and smart money labels.
154
-
155
- ### `cache` - Cache Management
201
+ ### Deprecated Flat Commands
156
202
 
157
- Manage the local response cache.
158
-
159
- ```bash
160
- # Clear all cached responses
161
- nansen cache clear
162
- ```
203
+ The old flat commands (`nansen smart-money`, `nansen token`, `nansen profiler`, `nansen search`, `nansen perp`, `nansen portfolio`, `nansen points`, `nansen quote`, `nansen execute`) still work but print a deprecation warning to stderr. Use the new `research` and `trade` namespaces instead.
163
204
 
164
205
  ## Options
165
206
 
@@ -168,10 +209,9 @@ nansen cache clear
168
209
  | `--pretty` | Format JSON output for readability |
169
210
  | `--table` | Format output as human-readable table |
170
211
  | `--fields <list>` | Comma-separated fields to include (reduces response size) |
171
- | `--cache` | Enable response caching |
172
- | `--no-cache` | Bypass cache for this request |
212
+ | `--stream` | Output as NDJSON for incremental processing |
213
+ | `--cache` / `--no-cache` | Enable/disable response caching |
173
214
  | `--cache-ttl <s>` | Cache TTL in seconds (default: 300) |
174
- | `--stream` | Output as JSON lines (NDJSON) for incremental processing |
175
215
  | `--chain <chain>` | Blockchain to query |
176
216
  | `--chains <json>` | Multiple chains as JSON array |
177
217
  | `--limit <n>` | Number of results |
@@ -179,91 +219,120 @@ nansen cache clear
179
219
  | `--sort <field:dir>` | Sort results (e.g., `--sort value_usd:desc`) |
180
220
  | `--symbol <sym>` | Token symbol for perp endpoints (e.g., BTC, ETH) |
181
221
  | `--filters <json>` | Filter criteria as JSON |
182
- | `--order-by <json>` | Sort order as JSON array (advanced) |
183
222
  | `--labels <label>` | Smart Money label filter |
184
223
  | `--smart-money` | Filter for Smart Money only |
185
224
  | `--timeframe <tf>` | Time window (5m, 10m, 1h, 6h, 24h, 7d, 30d) |
186
225
 
187
226
  ## Supported Chains
188
227
 
189
- `ethereum`, `solana`, `base`, `bnb`, `arbitrum`, `polygon`, `optimism`, `avalanche`, `linea`, `scroll`, `zksync`, `mantle`, `ronin`, `sei`, `plasma`, `sonic`, `unichain`, `monad`, `hyperevm`, `iotaevm`
228
+ `ethereum` `solana` `base` `bnb` `arbitrum` `polygon` `optimism` `avalanche` `linea` `scroll` `zksync` `mantle` `ronin` `sei` `plasma` `sonic` `unichain` `monad` `hyperevm` `iotaevm`
190
229
 
191
- ## AI Agent Integration
230
+ > Run `nansen schema` to get the current chain list (source of truth).
192
231
 
193
- This CLI is built specifically for AI agents. Every design decision prioritizes agent usability.
232
+ ## Agent-Optimized Patterns
194
233
 
195
- **Why agents love it:**
196
- - **Structured Output**: All responses are JSON with consistent schema — no parsing HTML or unstructured text
197
- - **Predictable Errors**: Errors include status codes and actionable details agents can handle programmatically
198
- - **Zero Config**: Works with just an API key — no complex setup
199
- - **Composable**: Commands can be chained with shell pipes
200
- - **Discoverable**: `help` commands at every level for agent introspection
234
+ ### Reduce Token Burn with `--fields`
201
235
 
202
- ```json
203
- // Success response
204
- {
205
- "success": true,
206
- "data": {
207
- "results": [...],
208
- "pagination": {...}
209
- }
210
- }
211
-
212
- // Error response
213
- {
214
- "success": false,
215
- "error": "API error message",
216
- "code": "UNAUTHORIZED",
217
- "status": 401,
218
- "details": {...}
219
- }
236
+ ```bash
237
+ # Returns everything (huge JSON, wastes agent context)
238
+ nansen research smart-money netflow --chain solana
239
+
240
+ # ✅ Only what you need
241
+ nansen research smart-money netflow --chain solana --fields token_symbol,net_flow_usd,chain --limit 10
242
+ ```
243
+
244
+ ### Use `--stream` for Large Results
245
+
246
+ ```bash
247
+ # NDJSON mode — process line by line, don't buffer giant arrays
248
+ nansen research token dex-trades --chain solana --limit 100 --stream
220
249
  ```
221
250
 
222
- ## Examples
251
+ ### x402 Micropayments
252
+
253
+ When the API returns a 402 Payment Required, the CLI automatically handles payment if a funded wallet exists:
254
+
255
+ 1. CLI detects 402 response with payment requirements
256
+ 2. Signs a USDC payment ($0.05/call) using your wallet
257
+ 3. Retries the request with the payment signature
258
+ 4. Falls back from EVM to Solana if first network has insufficient funds
223
259
 
224
260
  ```bash
225
- # Get trending tokens as a table, sorted by volume
226
- nansen token screener --chain solana --sort buy_volume:desc --table
261
+ # Fund your wallet, then API calls auto-pay
262
+ nansen wallet create
263
+ # Send USDC to the displayed address
264
+ nansen research smart-money netflow --chain solana # auto-pays if no API key
265
+ ```
227
266
 
228
- # Get Smart Money DEX trades from Funds only
229
- nansen smart-money dex-trades --chain ethereum --labels Fund --table
267
+ ## Pagination
230
268
 
231
- # Get token holders with Smart Money filter
232
- nansen token holders --token So11111111111111111111111111111111111111112 --chain solana --smart-money
269
+ Use `--limit N` to control result count. The CLI always fetches page 1 (there is no `--page` flag).
233
270
 
234
- # Get historical holdings for the past 7 days
235
- nansen smart-money historical-holdings --chain solana --days 7
271
+ **Detecting the last page:** If results returned < your `--limit`, you've reached the end.
236
272
 
237
- # Get BTC perpetual positions on Hyperliquid
238
- nansen token perp-positions --symbol BTC --pretty
273
+ ## Output Format
239
274
 
240
- # Get top PnL traders for a token, sorted by realized PnL
241
- nansen token pnl --token JUPyiwrYJFskUPiHa7hkeR8VUtAeFoSYbKedZNsDvCN --chain solana --days 30 --sort pnl_usd:desc --table
275
+ ### Response envelope
242
276
 
243
- # Filter response to specific fields (reduces tokens for AI agents)
244
- nansen smart-money netflow --chain solana --fields token_symbol,net_flow_usd,chain
277
+ ```json
278
+ // Success
279
+ { "success": true, "data": <raw_api_response> }
245
280
 
246
- # Get schema for agent introspection
247
- nansen schema --pretty
248
- nansen schema token --pretty
281
+ // Error
282
+ { "success": false, "error": "message", "code": "ERROR_CODE", "status": 401, "details": {...} }
249
283
  ```
250
284
 
251
- ## Development
285
+ ### Response shapes vary by endpoint
252
286
 
253
- ```bash
254
- # Run tests (mocked, no API key needed)
255
- npm test
287
+ The `data` field structure differs across endpoints:
256
288
 
257
- # Run with coverage
258
- npm run test:coverage
289
+ | Shape | Example endpoints |
290
+ |-------|------------------|
291
+ | `data.data` (array) | token screener |
292
+ | `data.results` (array) | entity search |
293
+ | `data.data.results` (array) | most profiler endpoints |
294
+ | `data.netflows` | smart-money netflow |
295
+ | `data.trades` | smart-money dex-trades |
296
+ | `data.holdings` | smart-money holdings |
297
+ | `data.holders` | token holders |
259
298
 
260
- # Run against live API
261
- NANSEN_API_KEY=your-key npm run test:live
299
+ `--table` and `--stream` handle this automatically. For raw JSON parsing:
300
+
301
+ ```bash
302
+ nansen research smart-money netflow --chain solana | jq 'keys, .data | keys'
262
303
  ```
263
304
 
264
- See [CONTRIBUTING.md](CONTRIBUTING.md) for development guidelines.
305
+ ### Error codes
306
+
307
+ | Code | Action |
308
+ |------|--------|
309
+ | `CREDITS_EXHAUSTED` | Stop all API calls immediately — do not retry. Check your plan at [app.nansen.ai](https://app.nansen.ai). |
310
+ | `RATE_LIMITED` | Auto-retry handles this. |
311
+ | `UNSUPPORTED_FILTER` | Remove the filter and retry. |
312
+ | `UNAUTHORIZED` | Key is wrong or missing. Re-auth. |
313
+ | `INVALID_ADDRESS` | Check address format for the chain. |
314
+
315
+ ## Troubleshooting
316
+
317
+ | Symptom | Fix |
318
+ |---------|-----|
319
+ | `command not found: nansen` | `npm install -g nansen-cli` or `npx nansen-cli` |
320
+ | `UNAUTHORIZED` after login | Check `cat ~/.nansen/config.json`. Write directly if needed. |
321
+ | Login hangs | Skip `nansen login`, write config directly. |
322
+ | Huge JSON response | Use `--fields` to select only needed columns. |
323
+ | Perp endpoints empty | Use `--symbol BTC` not `--token`. Perps are Hyperliquid-only. |
324
+ | `UNSUPPORTED_FILTER` on token holders | Not all tokens have smart money data. Remove `--smart-money`. |
325
+ | `CREDITS_EXHAUSTED` | Check your plan at [app.nansen.ai](https://app.nansen.ai). |
326
+
327
+ ## Development
328
+
329
+ ```bash
330
+ npm test # Run tests (mocked, no API key needed)
331
+ npm run test:coverage # With coverage
332
+ npm run test:live # Against live API (needs NANSEN_API_KEY)
333
+ ```
265
334
 
266
- **AI contributors:** See [CLAUDE.md](CLAUDE.md) for agent-specific guidance on contributing to this repo.
335
+ See [AGENTS.md](AGENTS.md) for contributor guidance (architecture, testing patterns, style guide).
267
336
 
268
337
  ## API Coverage
269
338