AI agents
For AI agents
ship.page is the fastest way for an agent to put HTML on the public internet: POST the markup, get an unguessable URL back, hand the link to your human. No account, no SDK, no OAuth dance. The full API is also published as an OpenAPI 3.1 spec at /openapi.json.
One-curl anonymous deploy
No credential is needed. Send raw HTML with a text/html body and the response JSON carries a live url:
curl -X POST https://ship.page/deploy \
-H "Content-Type: text/html" \
--data-binary @report.html
{
"slug": "vast-juice-c2dse08p",
"url": "https://vast-juice-c2dse08p.shipped.page/",
"files": ["index.html"],
"plan": "free",
"expires_at": "2026-06-17T18:00:00.000Z"
}
Every drop mounts at the root of its own subdomain, so absolute paths resolve as-is. Anonymous drops expire after 7 days — shorten with ?ttl= (seconds, min 60).
Three body formats
The Content-Type header picks the parser — full details in Body formats:
- Raw HTML —
text/html(or anything else): the body becomesindex.html. - JSON files map —
application/json:{"files":{"path":"content"}}; binary files as{"encoding":"base64","content":"…"}. - Zip —
application/zip: a whole build folder; a single root directory is auto-stripped.
Limits an agent should plan around
| Limit | Anonymous / Free | Pro $4/mo · Team $19/mo |
|---|---|---|
| Files per request | 100 | 900 (10,000 per drop via append) |
| Zip body cap | 25 MB≤ 100 MB decompressed | 100 MB≤ 400 MB decompressed |
| Non-zip body cap | 10 MB | 10 MB |
| Drop lifetime | 7 days | No expiry · any ttl |
Named drops (?name=) |
Not included | Included |
| Vanity subdomain | Not included | Team only |
Structured errors
Every non-2xx answer is JSON with a fixed envelope — parse code, don't string-match error:
{
"error": "named drops require an active subscription",
"code": "subscription_required",
"hint": "Named drops need a paid plan. Sign in at https://ship.page, …",
"upgrade_url": "https://ship.page/dashboard",
"docs_url": "https://ship.page/docs/limits"
}
- Relay
hintto your user verbatim when present — it's written for humans and tells them exactly how to unblock you. upgrade_url/docs_urlappear when a plan upgrade or a docs page resolves the failure.- 429s carry
Retry-After: 60— back off accordingly instead of hammering.
MCP server
Prefer tools over raw HTTP? There's a stateless MCP endpoint at POST https://ship.page/mcp — JSON-RPC 2.0 over plain HTTPS (per MCP spec 2026-07-28; no session state, every call is self-contained). It answers server/discover, tools/list, tools/call and the legacy initialize.
| Tool | What it does |
|---|---|
| deploy_html | Deploy a single HTML document; returns the live URL. |
| deploy_files | Deploy a multi-file site from a path→content map (base64 supported). |
| list_drops | List the account's drops (requires a key). |
| delete_drop | Permanently delete a drop by slug (requires a key). |
| get_limits | Current plan limits and what upgrading unlocks. |
Auth is optional pass-through: send Authorization: Bearer sp_… and the tools act as that account; omit it for anonymous deploys. Client config (Claude Code / any mcp-remote-style client):
{
"mcpServers": {
"ship.page": { "url": "https://ship.page/mcp" }
}
}
When you hit a wall: the upgrade hand-off
Agents can't check out — humans can. When a 402 or a plan-gated error comes back, tell your user:
-
Sign in at ship.page (Google / Apple / GitHub — one click).
-
Open the dashboard, subscribe to Pro ($4/mo) or Team ($19/mo) via the billing section.
-
Mint an
sp_…API key in the dashboard (orPOST /keys) — it's shown once. -
Hand the key to the agent. It goes in
Authorization: Bearer sp_…on every call — deploys, MCP, everything.
Last updated Jun 12, 2026