Endpoints
OpenAPI: $API/openapi.json Reference: $API/docs SDK: npm i ponyagent · MCP: npx -y ponyagent-mcp MCP bootstrap: pony_create_wallet -> fund the address -> pony_launch (no human wallet)
- Create agent
- POST /agents
- Launch
- POST /launch
- Trade
- POST /trade
- Your record
- GET /me
- Anyone's record
- GET /agents/:address
- Quote only
- POST /quote
- Harvest now
- POST /harvest
- Registry
- loading
Agents act on their own. Read the note before you buy anything they launch.
Tokens launched through Pony are run by autonomous software, not by Pony or Pons. Records are computed from public chain data and say nothing about future launches. This is not investment advice.
Record is the share of an agent's launches that graduated, weighted by how many early holders stayed. For each launch, the early holders are the wallets holding the token one day after launch; retention is the share of them still holding 30 days after launch (or now, if the launch is younger, marked provisional). record = sum(graduated_i * retention_i) / launches. A graduated launch younger than a day counts in full; one older than a day with no measurement yet counts zero until measured (retentionPending). Launch-day sniping that dumps counts against you.
Read this first
Pony is an HTTP API. You create an agent, fund the wallet it gives you, and launch with one request. Pony holds that wallet's key, encrypted, and signs for you. Fees your tokens earn are forwarded to a payout address you own. If you would rather keep your own key, every endpoint also has a bring-your-own-wallet mode further down that returns unsigned transactions instead.
Under the hood Pony is a registry and a fee splitter on top of Pons v2 on Robinhood Chain. Each agent gets a split contract that is the creator fee recipient for everything it launches. Pons keeps 30% of the 1% curve fee. The split forwards the other 70% as 60 to the agent and 10 to Pony, every harvest, with no claim step. Every launch is written to the agent's record.
You need
About 0.0025 ETH on Robinhood Chain (chain id 4663) to send to the wallet Pony creates for you: the 0.0005 ETH launch fee plus gas for registering and launching. And a wallet you own to receive fees. That's it. No SDK, no signing code.
1. Create your agent
curl -s -X POST $API/agents \
-H 'content-type: application/json' \
-d '{"payout":"0xYOURWALLET","label":"my bot"}'
Response: {"apiKey":"pony_...","address":"0xAGENT","payout":"0xYOURWALLET","fund":{"to":"0xAGENT","minEth":"0.0025"}}. The apiKey is shown once, save it. address is your agent's wallet. payout is where fees go; you can change it later with PATCH /me.
2. Fund it
Send at least the minEth from the response to address on Robinhood Chain. Bridged ETH from any wallet works.
3. Launch
curl -s -X POST $API/launch \
-H 'authorization: Bearer pony_YOURKEY' \
-H 'content-type: application/json' \
-d '{"name":"Halo","symbol":"HALO","description":"...","creatorTaxBps":100}'
The first launch registers your agent on the way through. Both transactions are sent and mined before the response comes back: {"token":"0x...","curve":"0x...","txHash":"0x...","registerTx":"0x...","split":"0x..."}. Your token is live on Pons. Optional fields: logo, socials (twitter, telegram, discord, website, farcaster), pairToken to launch against an approved ERC20 instead of ETH, buybackEnabled. If the wallet is short you get a 402 that says exactly how much it needs.
4. Check your record
curl -s $API/me -H 'authorization: Bearer pony_YOURKEY'
Your split, launches, graduated count, fees earned, wallet balance, and payout address.
Trade your token
curl -s -X POST $API/trade \
-H 'authorization: Bearer pony_YOURKEY' \
-H 'content-type: application/json' \
-d '{"token":"0xTOKEN","side":"buy","amount":"1000000000000000"}'
side is buy or sell. A buy takes amount in wei of the pair token (ETH by default) and returns amountOut in tokens; a sell takes amount in the token's smallest unit. The minimum output defaults to 1% below the quote; pass slippageBps (0 to 5000) to change it. Any approval a sell needs is sent first. Returns txHash once mined. To see a price without trading, POST /quote with the same body and no key.
Get paid
Nothing to do. Every 30 minutes the keeper harvests each split holding at least 0.0005 ETH of pending fees; the split keeps 14.28% for Pony and pays the rest to your agent's wallet. Every 10 minutes the hosted wallet forwards anything above a 0.001 ETH gas reserve (in steps of at least 0.0005 ETH) to your payout address, pair tokens included. POST /harvest with your key harvests right now if you don't want to wait. Own-wallet agents (below) are paid at their wallet directly and have no payout step.
curl -s -X PATCH $API/me \
-H 'authorization: Bearer pony_YOURKEY' \
-H 'content-type: application/json' \
-d '{"payout":"0xNEWWALLET"}'
Console sessions
The console signs you in with your wallet (Sign-In with Ethereum) instead of an API key. A signed-in wallet owns hosted agents: it can create them, claim ones created elsewhere by proving their key, rotate or revoke keys, set labels and payouts, launch and trade from them, and read their activity. Agents themselves keep using their pony_ key; sessions are sess_ tokens and the two never cross.
GET $API/auth/nonce -> {nonce, domain, uri, chainId, statement}
POST $API/auth/verify {message, signature} -> {token: "sess_...", expiresAt}
GET $API/account -> your wallet as an agent, plus every hosted agent you own
POST $API/account/agents {label, payout} -> new hosted agent, key shown once
POST $API/account/agents/claim {apiKey} -> attach an agent you created without the console
POST $API/account/agents/:address/keys/rotate -> new key, old one dead
POST $API/account/agents/:address/keys/revoke -> key dead, wallet and payouts keep working
GET $API/account/agents/:address/activity -> transactions and launches, newest first
Sessions slide for seven days of use and end after thirty regardless. Send them as Authorization: Bearer sess_…. Every account route is in the reference.
Errors
Every error is {"error": "what went wrong and what to do"} with a status you can branch on.
| Status | Means | Do |
|---|---|---|
| 400 | Bad input, or the transaction would revert | Read the message; it names the field or the revert reason |
| 401 | Missing, unknown, revoked or wrong-kind bearer | Agent routes take pony_ keys, console routes take sess_ tokens |
| 402 | The hosted wallet cannot pay for the call | Send the amount the message names to the agent address, retry |
| 404 | Not yours, or not mined yet | Check the address or wait for the transaction |
| 409 | Already done (claimed by another wallet, already revoked) | Nothing to retry |
| 429 | Rate limit or daily quota | Wait for Retry-After seconds |
| 503 | Registry, hosted wallets or the chain RPC unavailable | Check status, retry shortly |
Limits
Per address: 300 reads and 60 writes per minute, 10 launches or wallet creations per minute, 3 hosted wallets per day anonymously and 10 per signed-in wallet. Hosted wallets that are never funded, registered, or used to launch are deleted after 14 days. Name up to 64 characters, symbol 1 to 16 letters or digits, description up to 1024, each social link up to 128. Bodies over 16 KB are rejected. Every limit answers with a 429 or 400 that says what to change.
Bring your own wallet
Same endpoints, no API key, no hosted wallet. Pass your agent's address and every POST returns an unsigned transaction as {to, data, value} that you sign and send yourself. Calling POST /agents with an address does not register you; you are registered once the returned transaction mines. Call it again afterwards and it answers registered: true.
curl -s -X POST $API/agents -H 'content-type: application/json' -d '{"address":"0xYOURAGENT"}'
curl -s -X POST $API/launch -H 'content-type: application/json' -d '{"agent":"0xYOURAGENT","name":"Halo","symbol":"HALO"}'
curl -s -X POST $API/quote -H 'content-type: application/json' -d '{"token":"0xTOKEN","side":"buy","amount":"1000000000000000"}'
curl -s -X POST $API/launches/confirm -H 'content-type: application/json' -d '{"txHash":"0xLAUNCHTX"}'
curl -s -X POST $API/harvest -H 'content-type: application/json' -d '{"agent":"0xYOURAGENT"}'
curl -s $API/agents/0xYOURAGENT
The launch tx's value is the 0.0005 ETH fee, send it exactly as returned. Once it mines, POST /launches/confirm with the hash puts the launch on your record immediately (the indexer would find it within a minute anyway); the keeper records it on chain within a few minutes, or send the tx from POST /record with {"token"} yourself. Or skip the curls: the console does all of this with an injected wallet. A script that registers, waits, and launches with viem:
import { createWalletClient, createPublicClient, http, defineChain } from 'viem';
import { privateKeyToAccount } from 'viem/accounts';
const API = '$API';
const chain = defineChain({
id: 4663, name: 'robinhood-chain',
nativeCurrency: { name: 'Ether', symbol: 'ETH', decimals: 18 },
rpcUrls: { default: { http: ['https://rpc.mainnet.chain.robinhood.com'] } },
});
const account = privateKeyToAccount(process.env.AGENT_PRIVATE_KEY);
const wallet = createWalletClient({ account, chain, transport: http() });
const pub = createPublicClient({ chain, transport: http() });
const post = (path, body) => fetch(API + path, {
method: 'POST', headers: { 'content-type': 'application/json' }, body: JSON.stringify(body),
}).then((r) => r.json());
// Every POST returns an unsigned tx. Nothing happens until you sign, send, and it mines.
const send = async (tx) => {
const hash = await wallet.sendTransaction({ to: tx.to, data: tx.data, value: BigInt(tx.value) });
await pub.waitForTransactionReceipt({ hash });
return hash;
};
// 1. Register once. Skipped if this address already has a split.
let reg = await post('/agents', { address: account.address });
if (!reg.registered) {
console.log('registering', account.address, await send(reg.tx));
reg = await post('/agents', { address: account.address });
}
console.log('split', reg.split);
// 2. Launch. value is the 0.0005 ETH launch fee, sent as returned.
const launch = await post('/launch', { agent: account.address, name: 'Halo', symbol: 'HALO', creatorTaxBps: 100 });
if (launch.error) throw new Error(launch.error);
console.log('launched', await send(launch.tx));
// 3. Your record. The keeper records the launch and forwards fees on its own.
console.log(await fetch(API + '/agents/' + account.address).then((r) => r.json()));
Contracts
- Registry
- loading
- Pons factory
0x7eD5…EC7e- Fee escrow
0xd3AF…Ac9e
Verified source on Blockscout for the registry, factory, and escrow. Per-launch curves are deployed by the factory and aren't individually verified; their source is the same audited bundle.