Uniswap Mcp Server — independently scanned and version-tracked by SaferSkills.
SaferSkills independently audited Uniswap Mcp Server (Agent Skill) and scored it 100/100 (green). The audit ran 55 deterministic rules across Security, Supply Chain, Maintenance, Transparency, and Community; it found 0 high-severity and 0 lower-severity findings. The full rule-by-rule trace and per-finding evidence are below. Free, methodology-open.
Findings & checks · 0 flagged
Every scanned point with the score it earned and what moved between them.
First recorded scan — no prior version to compare against.
The primary manifest — the file an agent reads to learn what this artifact does.
A Model Context Protocol (MCP) server that exposes Uniswap V2 and V3 on-chain data and swap execution as tools, resources, and prompts. It connects any MCP-compatible AI client directly to the blockchain, allowing the model to query token prices, inspect liquidity pools, get swap quotes, and execute trades.
This server implements the Model Context Protocol using the FastMCP framework. When connected to an MCP client (such as Claude Desktop, Cursor, or any MCP-compatible agent), the AI model gains access to live Uniswap data without any custom integration code on the client side.
The server operates in two modes:
Clone the repository and install dependencies.
git clone https://github.com/rakibhossain72/uniswap-mcp-server.git
cd uniswap-mcp-serverUsing uv (recommended):
uv syncUsing pip:
pip install -e .The server reads its configuration from environment variables. Create a .env file in the project root:
cp .env.example .envThen edit .env:
# Required — your RPC endpoint URL
RPC_URL=https://mainnet.infura.io/v3/YOUR_PROJECT_ID
# Optional — required only for swap execution
PRIVATE_KEY=0xYOUR_PRIVATE_KEY
# Optional — default Uniswap V3 fee tier in bps (500, 3000, or 10000)
# Default: 3000 (0.3%)
DEFAULT_FEE_TIER=3000
# Optional — default slippage tolerance in basis points
# Default: 50 (0.5%)
DEFAULT_SLIPPAGE_BPS=50| Variable | Required | Default | Description |
|---|---|---|---|
RPC_URL | Yes | — | RPC endpoint for the target network |
PRIVATE_KEY | No | None | Wallet private key for executing swaps |
DEFAULT_FEE_TIER | No | 3000 | Default V3 fee tier: 500, 3000, or 10000 |
DEFAULT_SLIPPAGE_BPS | No | 50 | Slippage tolerance in basis points (50 = 0.5%) |
The server determines the network automatically from the chain_id reported by the RPC endpoint. To connect to Polygon, for example, set RPC_URL to a Polygon RPC URL.
Start the server directly with uv:
uv run python server.pyOr using the MCP CLI:
uv run mcp run server.pyThe server starts and listens for MCP client connections over stdio (the default transport).
Add the following to your Claude Desktop configuration file.
On macOS: ~/Library/Application Support/Claude/claude_desktop_config.json On Windows: %APPDATA%\Claude\claude_desktop_config.json
{
"mcpServers": {
"uniswap": {
"command": "uv",
"args": ["run", "python", "server.py"],
"cwd": "/absolute/path/to/uniswap-mcp-server",
"env": {
"RPC_URL": "https://mainnet.infura.io/v3/YOUR_PROJECT_ID",
"PRIVATE_KEY": "0xYOUR_PRIVATE_KEY"
}
}
}
}Restart Claude Desktop after saving. The Uniswap tools will be available immediately in the next conversation.
Add the server to your .cursor/mcp.json or workspace MCP settings:
{
"mcpServers": {
"uniswap": {
"command": "uv",
"args": ["run", "python", "server.py"],
"cwd": "/absolute/path/to/uniswap-mcp-server"
}
}
}Any client that supports the MCP stdio transport can connect to this server. The command to run is:
uv run python server.pyfrom the project root directory, with RPC_URL available in the environment.
The server supports the following EVM networks. The active network is determined by the RPC_URL you configure.
| Network | Chain ID | Notes |
|---|---|---|
| Ethereum Mainnet | 1 | Full V2 and V3 support |
| Polygon | 137 | Full V2 and V3 support |
| Optimism | 10 | Full V2 and V3 support |
| Arbitrum One | 42161 | Full V2 and V3 support |
All protocol contract addresses (factory, quoter, router, WETH, USDC, USDT) are hardcoded per network and validated at startup.
Tools are callable functions exposed to the AI model. The model invokes them during a conversation to retrieve data or take action.
Retrieve basic metadata for any ERC-20 token.
Parameters
| Name | Type | Description |
|---|---|---|
token_address | string | Checksummed ERC-20 contract address |
Returns
{
"address": "0xA0b86991c6218b36c1d19D4a2e9Eb0cE3606eB48",
"name": "USD Coin",
"symbol": "USDC",
"decimals": 6,
"total_supply": "45102345678901234"
}Get the real-time USD price of a token derived from on-chain Uniswap V3 pool data. The server tries USDC, USDT, and WETH quote pools across fee tiers (500, 3000, 10000) and returns the first valid result.
Parameters
| Name | Type | Description |
|---|---|---|
token_address | string | Checksummed ERC-20 contract address |
Returns
{
"token": "WETH",
"address": "0xC02aaA39b223FE8D0A0e5C4F27eAD9083C756Cc2",
"price_usd": 3421.57,
"quote_token": "USDC",
"fee_tier": 500,
"pool_address": "0x88e6A0c2dDD26FEEb64F039a2c41296FcB3f5640",
"chain_id": 1
}If no pool is found for the token, the response includes an error key instead.
Look up a Uniswap V3 pool by token pair and fee tier, then return its full on-chain state.
Parameters
| Name | Type | Default | Description |
|---|---|---|---|
token0 | string | — | Address of the first token |
token1 | string | — | Address of the second token |
fee | integer | 3000 | Fee tier: 500, 3000, or 10000 |
Returns
{
"pool_address": "0x88e6A0c2dDD26FEEb64F039a2c41296FcB3f5640",
"chain_id": 1,
"version": "v3",
"token0": { "address": "0xA0b8...", "symbol": "USDC", "decimals": 6 },
"token1": { "address": "0xC02a...", "symbol": "WETH", "decimals": 18 },
"fee_tier": 500,
"fee_percent": "0.0500%",
"liquidity": "12345678901234567890",
"sqrt_price_x96": "1234567890123456789012345678",
"current_tick": -197624,
"price_token1_per_token0": 0.00029287
}Look up a Uniswap V2 pair by token addresses and return its reserves and implied price.
Parameters
| Name | Type | Description |
|---|---|---|
token0 | string | Address of the first token |
token1 | string | Address of the second token |
Returns
{
"pair_address": "0xB4e16d0168e52d35CaCD2c6185b44281Ec28C9Dc",
"chain_id": 1,
"version": "v2",
"token0": { "address": "0xA0b8...", "symbol": "USDC", "decimals": 6 },
"token1": { "address": "0xC02a...", "symbol": "WETH", "decimals": 18 },
"reserve0": 45231890.123456,
"reserve1": 13218.987654,
"price_token1_per_token0": 0.00029231,
"block_timestamp_last": 1718000000
}Fetch full Uniswap V3 pool state directly by pool contract address, without needing the token pair.
Parameters
| Name | Type | Description |
|---|---|---|
pool_address | string | V3 pool contract address |
Returns
Same structure as get_v3_pool.
Simulate a Uniswap V3 swap using the on-chain Quoter contract and return the expected output amount. No transaction is sent.
Parameters
| Name | Type | Default | Description |
|---|---|---|---|
token_in | string | — | Address of the token to sell |
token_out | string | — | Address of the token to buy |
amount_in | string | — | Human-readable input amount (e.g. "1.5") |
fee | integer | 3000 | Fee tier of the pool to route through |
Returns
{
"token_in": { "address": "0xA0b8...", "symbol": "USDC" },
"token_out": { "address": "0xC02a...", "symbol": "WETH" },
"amount_in": 1000.0,
"amount_out": 0.29231,
"price": 0.00029231,
"fee_tier": 3000,
"chain_id": 1
}Execute a Uniswap V3 swap on-chain. This tool sends a real transaction and requires PRIVATE_KEY to be configured. The router is approved automatically if the current allowance is insufficient.
Parameters
| Name | Type | Default | Description |
|---|---|---|---|
token_in | string | — | Address of the token to sell |
token_out | string | — | Address of the token to buy |
amount_in | string | — | Human-readable input amount (e.g. "100") |
slippage_bps | integer | 50 | Maximum acceptable slippage in basis points |
fee | integer | 3000 | Fee tier of the pool to route through |
deadline_minutes | integer | 20 | Transaction deadline in minutes from now |
Returns
{
"status": "success",
"tx_hash": "0xabc123...",
"token_in": { "symbol": "USDC", "amount": 1000.0 },
"token_out": { "symbol": "WETH", "expected_amount": 0.29231 },
"slippage_bps": 50,
"gas_used": 142381,
"block_number": 20000001,
"approval": "already_approved"
}If PRIVATE_KEY is not set, the tool returns immediately with:
{
"error": "PRIVATE_KEY is not set — required for executing swaps"
}Resources are read-only data sources that the AI model can fetch at any point during a conversation.
Returns the canonical protocol and token contract addresses for the currently connected chain.
URI: protocol://addresses
Example response
{
"v2_factory": "0x5C69bEe701ef814a2B6a3EDD4B1652CB9cc5aA6f",
"v3_factory": "0x1F98431c8aD98523631AE4a59f267346ea31F984",
"v3_quoter": "0xb27308f9F90D607463bb33eA1BeBb41C27CE5AB6",
"v3_router": "0xE592427A0AEce92De3Edee1F18E0157C05861564",
"weth": "0xC02aaA39b223FE8D0A0e5C4F27eAD9083C756Cc2",
"usdc": "0xA0b86991c6218b36c1d19D4a2e9Eb0cE3606eB48",
"usdt": "0xdAC17F958D2ee523a2206206994597C13D831ec7",
"chain_id": 1,
"chain_name": "MAINNET"
}Returns the current connection state, chain ID, and latest block number.
URI: network://status
Example response
{
"chain_id": 1,
"latest_block": 20123456,
"connected": true
}Prompts are structured instruction templates that guide the AI model through multi-step workflows. They are invoked by name from a compatible MCP client.
Guides the model through a full token analysis: fetches addresses, retrieves the USD price, inspects the V3 pool, and produces a summary report.
Parameters
| Name | Type | Description |
|---|---|---|
token_address | string | Address of the token to analyze |
What the model does
protocol://addresses to get WETH and USDC addresses for the current chain.get_token_price to fetch the current USD price.get_v3_pool for the token paired against WETH and USDC at the 3000 fee tier.Guides the model through a safe, confirmation-gated swap workflow. The model will not send a transaction without explicit user approval.
Parameters
| Name | Type | Description |
|---|---|---|
token_in | string | Symbol or address of the token to sell |
token_out | string | Symbol or address of the token to buy |
amount | string | Human-readable amount to sell |
What the model does
get_swap_quote and presents the result to the user.execute_swap only after confirmation is received..
├── pyproject.toml
├── README.md
├── scripts
├── server.py
├── src
│ ├── config.py
│ ├── main.py
│ ├── prompts
│ │ ├── analyze.py
│ │ ├── __init__.py
│ │ └── swap.py
│ ├── resources
│ │ ├── addresses.py
│ │ ├── __init__.py
│ │ └── network.py
│ ├── tools
│ │ ├── __init__.py
│ │ ├── pools.py
│ │ ├── prices.py
│ │ ├── swaps.py
│ │ └── tokens.py
│ └── uniswap_client
│ ├── abis
│ │ ├── ERC20_ABI.json
│ │ ├── get_abi.py
│ │ ├── __init__.py
│ │ ├── V2_FACTORY_ABI.json
│ │ ├── V2_PAIR_ABI.json
│ │ ├── V3_FACTORY_ABI.json
│ │ ├── V3_POOL_ABI.json
│ │ ├── V3_QUOTER_ABI.json
│ │ └── V3_ROUTER_ABI.json
│ ├── addresses.py
│ ├── contracts
│ │ ├── base.py
│ │ ├── erc20.py
│ │ ├── __init__.py
│ │ ├── v2_factory.py
│ │ ├── v2_pair.py
│ │ ├── v3_factory.py
│ │ ├── v3_pool.py
│ │ ├── v3_quoter.py
│ │ └── v3_router.py
│ ├── core
│ │ ├── client.py
│ │ └── __init__.py
│ ├── __init__.py
│ └── utils
│ └── __init__.py
├── tests
│ ├── conftest.py
│ ├── __init__.py
│ ├── test_abis.py
│ ├── test_addresses.py
│ ├── test_client.py
│ ├── test_config.py
│ ├── test_contracts.py
│ ├── test_prompts.py
│ ├── test_resources.py
│ └── test_tools.py
├── .env
└── uv.lockThe test suite requires no network connection. All blockchain calls are mocked.
Install dev dependencies:
uv syncRun the full suite:
uv run pytest tests/Run a specific file:
uv run pytest tests/test_client.pyRun with verbose output:
uv run pytest tests/ -vThe suite covers 204 tests across configuration, address validation, ABI loading, all contract wrappers, the UniswapClient, every MCP tool, resource, and prompt.
Private key handling. The PRIVATE_KEY environment variable is read at startup and stored in memory for the lifetime of the server process. Never commit a .env file containing a real private key. Use a dedicated wallet with only the funds needed for the operations you intend to run.
Token approvals. execute_swap grants the V3 router an unlimited (2^256 - 1) token allowance if the current allowance is insufficient. This is standard practice for Uniswap interactions but means the router contract can spend that token on behalf of the wallet indefinitely. Revoke allowances manually if needed.
Slippage. The default slippage tolerance is 0.5% (50 basis points). For low-liquidity tokens or large trade sizes, set a tighter slippage or verify the quote before confirming a swap.
RPC endpoint trust. The server trusts the data returned by the configured RPC URL. Use a reputable, authenticated endpoint rather than an unknown public RPC for any transaction-sending use case.
Prompt confirmation gate. The execute_trade prompt is designed to require explicit user confirmation before calling execute_swap. Do not bypass or modify this flow when using the server for live trading.
~30 seconds. Free. No account. Every finding cites a rule and a line of evidence.