
swap-planner
This skill should be used when the user asks to "swap tokens", "trade ETH for USDC", "exchange tokens on Uniswap", "buy tokens", "sell tokens", "convert ETH to stablecoins", "find memecoins", "discover tokens", "research tokens", "tokens to buy", "find tokens to swap", "what should I buy", or mentions swapping, trading, researching, discovering, buying, or exchanging tokens on any Uniswap-supported chain. Supports both known token swaps and token discovery workflows (discovery uses keyword search and web search — there is no live "trending" feed). Generates deep links to execute swaps in the Uniswap interface.
- Installs
- 1.2K
- Last 24h
- —
- Trending rank
- —
- Security
- Not audited
Install
Works with every agent the skills CLI supports.
npx skills add https://github.com/uniswap/uniswap-ai --skill swap-planner- 01
Install
Run the command in your project. The CLI asks which agents to install for.
- 02
Describe the task
Ask your agent for something this skill covers. It loads swap-planner automatically when relevant.
- 03
Review the result
The agent follows the SKILL.md steps, scripts and references bundled with the skill.
SKILL.md
The instructions your agent reads when the skill is triggered.
Swap Planning
Plan and generate deep links for token swaps on Uniswap across all supported chains.
Runtime Compatibility: This skill uses
AskUserQuestionfor interactive prompts. IfAskUserQuestionis not available in your runtime, collect the same parameters through natural language conversation instead.
Overview
Plan token swaps by:
- Gathering swap intent (tokens, amounts, chain)
- Verifying token contracts on-chain
- Researching tokens via web search when needed
- Generating a deep link that opens in the Uniswap interface with parameters pre-filled
The generated link opens Uniswap with all parameters ready for execution.
<!-- markdownlint-disable-next-line MD028 -->Note: Browser opening (
xdg-open/open) may fail in SSH, containerized, or headless environments. Always display the URL prominently so users can copy and access it manually if needed.
File Access: This skill has read-only filesystem access. Never read files outside the current project directory unless explicitly requested by the user.
Workflow
Step 0: Token Discovery (When Needed)
If the user wants to discover tokens rather than swap a known token (e.g., "find me a memecoin", "what's trending on Base"), help them explore before proceeding to the swap.
Option A: Search by Keyword
DexScreener search works best with specific terms:
# Search for tokens by name/category (e.g., "degen", "pepe", "ai agent")
curl -s "https://api.dexscreener.com/latest/dex/search?q=degen" | \
jq '[.pairs[] | select(.chainId == "base" and .dexId == "uniswap")] |
sort_by(-.volume.h24) | .[0:5] | map({
token: .baseToken.symbol,
address: .baseToken.address,
price: .priceUsd,
volume24h: .volume.h24,
liquidity: .liquidity.usd
})'
Good search terms: degen, pepe, ai, agent, meme, dog, cat, or specific token names
Option B: Check Promoted Tokens
Get tokens with active promotions (limited selection):
# Get boosted/promoted tokens on a chain
curl -s "https://api.dexscreener.com/token-boosts/top/v1" | \
jq '[.[] | select(.chainId == "base")] | .[0:5] | map({
tokenAddress,
url
})'
Option C: Web Search + Verify
For broad discovery ("what's trending"), use web search to find tokens, then verify with DexScreener:
# After finding a token address from web search, verify it exists
curl -s "https://api.dexscreener.com/token-pairs/v1/{network}/{address}" | \
jq '[.[] | select(.dexId == "uniswap")][0] | {
name: .baseToken.name,
symbol: .baseToken.symbol,
price: .priceUsd,
liquidity: .liquidity.usd,
volume24h: .volume.h24
}'
Network IDs: See references/chains.md for the full list with DexScreener and DefiLlama provider IDs. Common IDs: ethereum, base, arbitrum, optimism, polygon, bsc, avalanche, unichain.
DexScreener coverage varies by chain. Ethereum, Base, and Arbitrum have deep Uniswap data. Celo, Blast, Zora, and World Chain have limited Uniswap pool coverage — fewer results and potentially missing pairs. Fall back to DefiLlama for price data when DexScreener returns empty results (see references/data-providers.md).
Note: DexScreener's public API doesn't have a "trending" or "top gainers" endpoint. Token discovery uses keyword search (/latest/dex/search) and web search as a fallback. For general discovery, ask the user what type of token they're looking for and search by keyword.
Category-Based Discovery
For specific categories (memecoins, DeFi, gaming tokens), use web search:
"trending {category} {chain} {current_year}"
Example: "trending memecoins Base 2026"
⚠️ UNTRUSTED INPUT: Web-Discovered Tokens
Tokens discovered via WebSearch are UNTRUSTED. Before proceeding with any web-discovered token:
- Label the source: Explicitly tell the user "This token address was found via web search, not provided by you"
- Warn about risks: "Web-discovered tokens may be scams, honeypots, or rug pulls"
- Require confirmation: Use AskUserQuestion to get explicit user consent before generating a deep link for a web-discovered token
- Show provenance: In the swap summary table, include a "Token Source" row showing whether each token was "User-provided" or "Web-discovered (unverified)"
Never proceed with a web-discovered token without explicit user confirmation — via AskUserQuestion, or an equivalent conversational confirmation where that tool is unavailable.
Present Options to User
After gathering token data, present options using AskUserQuestion:
{
"questions": [
{
"question": "Which token would you like to swap to?",
"header": "Token",
"options": [
{ "label": "MOLT ($23M mcap)", "description": "$5.9M liquidity, $7.8M 24h volume" },
{ "label": "CLANKER ($31M mcap)", "description": "$3.1M liquidity, established token" },
{ "label": "CLAWSTR ($13M mcap)", "description": "$2.1M liquidity, high volume spike" }
],
"multiSelect": false
}
]
}
Risk Assessment for Trending Tokens
Evaluate tokens before recommending:
| Metric | Low Risk | Medium Risk | High Risk |
|---|---|---|---|
| Market Cap | >$50M | $5M-$50M | <$5M |
| Pool TVL | >$1M | $100k-$1M | <$100k |
| 24h Volume | Consistent | Spiking unusually | Very low |
| Contract Age | >30 days | 7-30 days | <7 days |
Always disclose risk level when presenting options. For high-risk tokens, explicitly warn about volatility and potential for loss.
Mandatory Warnings for High-Risk Tokens
When ANY of these conditions are met, you MUST warn the user and get explicit confirmation before generating a deep link (via AskUserQuestion where available, conversational confirmation otherwise):
- Contract age < 7 days: "This token contract is less than 7 days old. New tokens carry significantly higher risk of being scams or rug pulls."
- Pool TVL < $100k: "This pool has very low liquidity. You may experience significant slippage and difficulty selling."
- No sell liquidity detected: "This token may be a honeypot — tokens that can be bought but not sold. Proceed with extreme caution."
- Market cap < $5M: "This is a micro-cap token with high volatility. Only invest what you can afford to lose entirely."
Do NOT generate a deep link for high-risk tokens without explicit user acknowledgment.
Step 1: Gather Swap Intent
Extract from the user's request:
| Parameter | Required | Example |
|---|---|---|
| Input token | Yes | ETH, USDC, token address |
| Output token | Yes | USDC, WBTC, token address |
| Amount | Yes | 1.5 ETH, $500 worth |
| Chain | Yes (default: Ethereum) | Base, Arbitrum, etc. |
If any required parameter is missing, use AskUserQuestion with structured options:
For missing chain:
{
"questions": [
{
"question": "Which chain do you want to swap on?",
"header": "Chain",
"options": [
{ "label": "Base (Recommended)", "description": "Low gas fees, fast transactions" },
{ "label": "Ethereum", "description": "Main network, higher gas" },
{ "label": "Arbitrum", "description": "Low fees, Ethereum L2" },
{ "label": "Optimism", "description": "Low fees, Ethereum L2" }
],
"multiSelect": false
}
]
}
For missing output token (when input is ETH):
{
"questions": [
{
"question": "What token do you want to receive?",
"header": "Output",
"options": [
{ "label": "USDC", "description": "USD stablecoin" },
{ "label": "USDT", "description": "Tether stablecoin" },
{ "label": "DAI", "description": "Decentralized stablecoin" },
{ "label": "WBTC", "description": "Wrapped Bitcoin" }
],
"multiSelect": false
}
]
}
For missing amount:
{
"questions": [
{
"question": "How much do you want to swap?",
"header": "Amount",
"options": [
{ "label": "0.1 ETH", "description": "~$320" },
{ "label": "0.5 ETH", "description": "~$1,600" },
{ "label": "1 ETH", "description": "~$3,200" },
{ "label": "Custom amount", "description": "Enter specific amount" }
],
"multiSelect": false
}
]
}
Always use forms instead of plain text questions for better UX.
Step 2: Resolve Token Addresses
For token symbols, resolve to addresses using known tokens or web search:
Native tokens: Use NATIVE as the address parameter.
Common tokens by chain - see ../../references/chains.md for full list:
| Token | Ethereum | Base | Arbitrum |
|---|---|---|---|
| USDC | 0xA0b86991c6218b36c1d19D4a2e9Eb0cE3606eB48 | 0x833589fCD6eDb6E08f4c7C32D4f71b54bdA02913 | 0xaf88d065e77c8cC2239327C5EDb3A432268e5831 |
| WETH | 0xC02aaA39b223FE8D0A0e5C4F27eAD9083C756Cc2 | 0x4200000000000000000000000000000000000006 | 0x82aF49447D8a07e3bd95BD0d56f35241523fBab1 |
| WBTC | 0x2260FAC5E5542a773Aa44fBCfeDf7C193bc2C599 | N/A | 0x2f2a2543B76A4166549F7aaB2e75Bef0aefC5B0f |
For unknown tokens, use web search to find the contract address, then verify on-chain.
Step 3: Verify Token Contracts (Basic)
Input Validation (Required Before Any Shell Command):
Before interpolating user-provided values into any shell command, validate all inputs:
- Token addresses MUST match:
^0x[a-fA-F0-9]{40}$ - Chain/network names MUST be from the allowed list in
../../references/chains.md - Amounts MUST be valid decimal numbers (match:
^[0-9]+\.?[0-9]*$) - Reject any input containing shell metacharacters (
;,|,$,`,&,(,),>,<,\,',", newlines)
Verify token contracts exist on-chain using curl (RPC call):
# Check if address is a contract using eth_getCode
# IMPORTANT: Validate token_address matches ^0x[a-fA-F0-9]{40}$ before use
curl -s -X POST "$rpc_url" \
-H "Content-Type: application/json" \
-d "$(jq -n --arg addr "$token_address" '{"jsonrpc":"2.0","method":"eth_getCode","params":[$addr,"latest"],"id":1}')" \
| jq -r '.result'
If the result is 0x or empty, the address is not a valid contract.
Alternative with cast (optional, requires Foundry):
# Validate token_address matches ^0x[a-fA-F0-9]{40}$ before use
cast code "$token_address" --rpc-url "$rpc_url"
Note: The curl/RPC method above is preferred for broader compatibility. Only use cast if already available in the environment. This skill ONLY uses cast code for contract verification. Do not use any other cast subcommands. The PreToolUse hook in .claude/hooks/validate-forge-cast.sh enforces this programmatically.
RPC URLs by chain - see ../../references/chains.md for full list.
Step 4: Research (If Needed)
For unfamiliar tokens, use web search to research:
- Token legitimacy and project info
- Recent news or security concerns
- Liquidity availability on Uniswap
Include relevant findings in the summary.
Step 5: Fetch Price Data
Before generating the deep link, fetch current prices to estimate swap output. See references/data-providers.md for full API details.
Quick price lookup with DexScreener:
# Get token price and pool liquidity
curl -s "https://api.dexscreener.com/token-pairs/v1/{network}/{address}" | \
jq '[.[] | select(.dexId == "uniswap")][0] | {
price: .priceUsd,
liquidity: .liquidity.usd,
volume24h: .volume.h24
}'
Network IDs: ethereum, base, arbitrum, optimism, polygon, bsc, avalanche, unichain
Liquidity warnings:
| Pool TVL | Risk Level | Action |
|---|---|---|
| > $1M | Low | Proceed normally |
| $100k - $1M | Medium | Note potential slippage |
| < $100k | High | Warn user about slippage risk |
If API is unavailable, fall back to DefiLlama or web search for price estimates.
Step 6: Generate Deep Link
Construct the Uniswap swap URL:
https://app.uniswap.org/swap?chain={chain}&inputCurrency={input}&outputCurrency={output}&value={amount}&field=INPUT
URL Parameters:
| Parameter | Description | Values |
|---|---|---|
chain | Network name | ethereum, base, arbitrum, optimism, polygon, bnb, avalanche, celo, blast, zora, unichain, worldchain |
inputCurrency | Input token | Address or NATIVE |
outputCurrency | Output token | Address or NATIVE |
value | Amount | Decimal number (e.g., 1.5) |
field | Which field value applies to | INPUT or OUTPUT |
Step 7: Present Output and Open Browser
Format the response with:
- Summary of the swap parameters
- Deep link URL (displayed for reference)
- Notes about risks or considerations
- Open the browser automatically using system command
Example output format:
## Swap Summary
| Parameter | Value |
| ---------------- | -------------------------- |
| From | 1 ETH |
| To | USDC |
| Chain | Base |
| Current Rate | ~3,200 USDC per ETH |
| Estimated Output | ~3,200 USDC |
| Pool Liquidity | $15.2M (Low slippage risk) |
### Notes
- Final amount depends on current market price
- Default slippage is 0.5% - adjust in Uniswap if needed
- Review all details in Uniswap before confirming
Opening Uniswap in your browser...
After displaying the summary, open the URL in the browser:
# Linux
xdg-open "https://app.uniswap.org/swap?chain=base&inputCurrency=NATIVE&outputCurrency=0x833589fCD6eDb6E08f4c7C32D4f71b54bdA02913&value=1&field=INPUT"
# macOS
open "https://app.uniswap.org/swap?..."
Environment limitations: Browser opening may fail in remote SSH, containerized, or headless environments. If xdg-open/open fails, display the full URL prominently so users can copy and paste it manually:
**[Click here to open in Uniswap](https://app.uniswap.org/swap?...)**
Or copy this URL: `https://app.uniswap.org/swap?...`
Always present the summary and URL so users can review and execute.
Important Considerations
Slippage
The deep link uses Uniswap's default slippage (0.5%). For volatile tokens or large trades, advise users to adjust slippage in the interface.
Gas Estimation
Gas costs vary by chain and network congestion. Base and Arbitrum typically have lower gas than Ethereum mainnet.
Token Verification
Always verify token contracts before generating links. Scam tokens often use similar names to legitimate tokens.
Price Impact
For large trades, warn users about potential price impact. Suggest splitting into smaller trades if impact would be significant.
Supported Chains
All chains supported by the Uniswap interface:
- Ethereum Mainnet (
ethereum) - Base (
base) - Arbitrum One (
arbitrum) - Optimism (
optimism) - Polygon (
polygon) - BNB Chain (
bnb) - Avalanche (
avalanche) - Celo (
celo) - Blast (
blast) - Zora (
zora) - World Chain (
worldchain) - Unichain (
unichain)
Additional Resources
Reference Files
../../references/chains.md- Chain IDs, RPC URLs, native tokens, common token addressesreferences/data-providers.md- DexScreener and DefiLlama APIs for prices and liquidity
Examples
Common swap scenarios:
- ETH → USDC on Ethereum
- ETH → USDC on Base (lower gas)
- USDC → WBTC on Arbitrum
FAQ
What does the swap-planner skill do?
This skill should be used when the user asks to "swap tokens", "trade ETH for USDC", "exchange tokens on Uniswap", "buy tokens", "sell tokens", "convert ETH to stablecoins", "find memecoins", "discover tokens", "research tokens", "tokens to buy", "find tokens to swap", "what should I buy", or mentions swapping, trading, researching, discovering, buying, or exchanging tokens on any Uniswap-supported chain. Supports both known token swaps and token discovery workflows (discovery uses keyword search and web search — there is no live "trending" feed). Generates deep links to execute swaps in the Uniswap interface.
How do I install swap-planner?
Run npx skills add https://github.com/uniswap/uniswap-ai --skill swap-planner in your project. The skills CLI detects the agents you use and copies the skill into the right folder. For Claude Code you can also place the skill folder at ~/.claude/skills/swap-planner/ (personal) or .claude/skills/swap-planner/ (project).
Which AI agents can use swap-planner?
Any agent that supports the open Agent Skills format (a folder with a SKILL.md file), including Claude Code, Codex, Cursor, GitHub Copilot, Gemini CLI, Windsurf, Cline, OpenCode and more.
Is swap-planner safe to install?
No partner security audit is available yet. Skills can run commands and scripts, so read the SKILL.md and any bundled files before installing.
Who maintains swap-planner?
It is published by uniswap in uniswap/uniswap-ai. It has 1,193 recorded installs.
More from uniswap/uniswap-ai
swap-integration
uniswap/uniswap-ai
Integrate Uniswap swaps into applications. Use when user says "integrate swaps", "uniswap", "trading api", "add swap functionality", "build a swap frontend", "create a swap script", "smart contract swap integration", "use Universal Router", "Trading API", or mentions swapping tokens via Uniswap.
viem-integration
uniswap/uniswap-ai
Integrate EVM blockchains using viem. Use when user says "read blockchain data", "send transaction", "interact with smart contract", "connect to Ethereum", "use viem", "use wagmi", "wallet integration", "viem setup", or mentions blockchain/EVM development with TypeScript.
liquidity-planner
uniswap/uniswap-ai
This skill should be used when the user asks to "provide liquidity", "create LP position", "add liquidity to pool", "become a liquidity provider", "create v3 position", "create v4 position", "concentrated liquidity", "set price range", or mentions providing liquidity, LP positions, or liquidity pools on Uniswap. Generates deep links to create positions in the Uniswap interface.
v4-security-foundations
uniswap/uniswap-ai
Security-first Uniswap v4 hook development. Use when user mentions "v4 hooks", "hook security", "PoolManager", "beforeSwap", "afterSwap", or asks about V4 hook best practices, vulnerabilities, or audit requirements.
deployer
uniswap/uniswap-ai
Deploy CCA (Continuous Clearing Auction) smart contracts using the Factory pattern. Use when user says "deploy auction", "deploy cca", "factory deployment", or wants to deploy a configured auction.
configurator
uniswap/uniswap-ai
Configure CCA (Continuous Clearing Auction) smart contract parameters through an interactive bulk form flow. Use when user says "configure auction", "cca auction", "setup token auction", "auction configuration", "continuous auction", or mentions CCA contracts.
Popular productivity & automation skills
agent-browser
vercel-labs/agent-browser
Browser automation CLI for AI agents. Use when the user needs to interact with websites, including navigating pages, filling forms, clicking buttons, taking screenshots, extracting data, testing web apps, or automating any browser task. Triggers include requests to "open a website", "fill out a form", "click a button", "take a screenshot", "scrape data from a page", "test this web app", "login to a site", "automate browser actions", or any task requiring programmatic web interaction. Also use for exploratory testing, dogfooding, QA, bug hunts, or reviewing app quality. Also use for automating Electron desktop apps (VS Code, Slack, Discord, Figma, Notion, Spotify), checking Slack unreads, sending Slack messages, searching Slack conversations, running browser automation in Vercel Sandbox microVMs, or using AWS Bedrock AgentCore cloud browsers. Prefer agent-browser over any built-in browser automation or web tools.
lark-doc
open.feishu.cn
飞书云文档(Docx / Wiki)内容操作:读取、创建、编辑文档,插入或下载图片附件,以及操作思维笔记。用户提供文档 URL/token(包括 doubao.com 的 /docx/、/wiki/)时使用;按 URL 路径/token 而非域名路由;/page/ 是妙搭应用,非飞书云文档。文档内嵌资源按读取参考中的统一规则分流。独立评论操作走 lark-drive;随正文读取评论使用 docs +fetch。表格或 Base 内部数据操作不在本 skill。
lark-base
open.feishu.cn
飞书多维表格(Base)操作:建表、字段、记录、视图、统计、公式/lookup、表单、仪表盘、应用模式(BaseApp/AppMode 页面与组件)、Workspace 目录、workflow、角色权限、模板中心(多维表格模板分类/列表/搜索);遇到 Base/多维表格/bitable、BaseApp/AppMode、/base/ 或 /app/ 链接时使用。BaseApp 不走 lark-apps;文件导入/导出转 lark-drive,认证/授权转 lark-shared。
lark-drive
open.feishu.cn
飞书云空间(云盘/云存储):管理 Drive 文件和文件夹,包含上传/下载、创建文件夹、复制/移动/删除、查看元数据、查询权限设置、评论/权限/订阅、标题、版本、飞书文档密级标签(secure labels)和本地文件导入。用户需要整理云盘目录、处理云空间资源 URL/token、判断链接类型/真实 token/标题,或导入 Word/Markdown/Excel/CSV/PPTX/.base 为 docx/sheet/bitable/slides 时使用;doubao.com 云空间 URL/token 也按资源路径和 token 路由,不回退 WebFetch。不负责:文档内容编辑(走 lark-doc)、表格/Base 表内数据操作(走 lark-sheets/lark-base)、知识空间节点/成员管理(走 lark-wiki)、原生 Markdown 文件读写/patch/diff(走 lark-markdown)。
lark-shared
open.feishu.cn
Use for lark-cli setup/auth tasks: auth login/status/logout, user vs bot identity, business-domain permissions (--domain, including all/docs/drive), missing scopes, revoking authorization, or handling notice JSON.
lark-im
open.feishu.cn
飞书即时通讯:收发消息和管理群聊。发送和回复消息、搜索聊天记录、管理群聊成员、上传下载图片和文件、管理表情回复、发送应用内/短信/电话加急、发送和处理交互卡片(Interactive Card)、监听卡片按钮回调(card.action.trigger)。当用户需要发消息、查看或搜索聊天记录、下载聊天中的文件、查看群成员、搜索群、创建群聊或话题群、管理标记数据、管理 Feed 置顶(添加/移除/查询置顶会话)、管理标签数据、处理卡片回调时使用。