HTTP API
Public HTTP API for programmatic access. OpenAI-compatible chat completions, pay-per-use credits, one key for Fast / Pro / Heavy.
The Dropstone HTTP API gives you programmatic access to the same three models the CLI uses — Dropstone Fast, Pro, and Heavy — over an OpenAI-compatible interface. One key, one bill, three model families.
Use the API when you want to call Dropstone from your own code: CI pipelines, internal tools, automation, or third-party apps. For interactive coding, use the CLI instead.
Status:
The public API is in preview. The endpoint shape is stable but pricing and rate limits may change before GA. Pin the surface you depend on.
Base URL
https://api.dropstone.io/api/v1
All endpoints are mounted under /api/v1. The path is versioned so future breaking changes will land under /api/v2 without disrupting your code.
Authentication
Every request must include an API key in the Authorization header:
Authorization: Bearer dsk_live_<your-key>
Generate a key
- Sign in to dropstone.io/dashboard
- Open Settings → API
- Click Create key, give it a name (e.g.
Production CI) - Copy the full key — you will only see it once
Keys look like dsk_live_<43 chars>. Store them in a secrets manager or in the DROPSTONE_API_KEY environment variable.
Revoking a key
Revoke from the same Settings → API page. Revocation is immediate; in-flight requests with the key continue, new requests get 401.
Security:
Treat your API key like a password. Never commit it to git, never paste it in chat or screenshots, never embed it in a frontend bundle. If a key leaks, revoke it immediately and create a new one.
Credits & billing
The API is pay-per-use against a credit balance. There is no free tier and no subscription on the API surface.
- Buy credits at dropstone.io/dashboard/billing. Stripe handles checkout.
- Each request deducts its cost from your
creditBalance. - When
creditBalancedrops to $0, the API returns402 Insufficient creditsuntil you top up. - Subscription credits (Pro/Teams monthly allowance) and free-request quotas do not apply to API key requests.
Pricing
Pricing is real OpenRouter cost passed through with a 30% markup (1.3x). The full per-request cost is returned in the response usage.cost field, so you can verify every charge.
| Tier | Backend | Approx $/M input | Approx $/M output |
|---|---|---|---|
dropstone-fast | DeepSeek V4 Flash | $0.35 | $1.43 |
dropstone-pro | DeepSeek V4 Pro | $0.72 | $2.86 |
dropstone-heavy | Kimi K2.6 | $0.78 | $3.25 |
Cached prompt tokens are billed at the provider's cached rate (typically ~5–10% of the normal input rate), so multi-turn conversations get progressively cheaper.
Models
GET /api/v1/models
List the three available tiers.
curl https://api.dropstone.io/api/v1/models \
-H "Authorization: Bearer $DROPSTONE_API_KEY"
Response:
{
"object": "list",
"data": [
{ "id": "dropstone-fast", "object": "model", "display_name": "Dropstone Fast", "owned_by": "dropstone" },
{ "id": "dropstone-pro", "object": "model", "display_name": "Dropstone Pro", "owned_by": "dropstone" },
{ "id": "dropstone-heavy", "object": "model", "display_name": "Dropstone Heavy", "owned_by": "dropstone" }
]
}
Chat completions
POST /api/v1/chat/completions
OpenAI-compatible chat completions. If you've used the OpenAI, Anthropic, or DeepSeek APIs, this looks identical.
Request body
| Field | Type | Required | Description |
|---|---|---|---|
model | string | yes | One of dropstone-fast, dropstone-pro, dropstone-heavy |
messages | array | yes | List of message objects with role and content |
stream | boolean | no | When true, returns Server-Sent Events. Default false |
temperature | number | no | Sampling temperature, 0..2. Default model-specific |
max_tokens | number | no | Cap on output tokens |
tools | array | no | Function-calling tool schemas, OpenAI format |
tool_choice | string | object | no | "auto", "none", or a specific tool |
Example: simple chat
curl https://api.dropstone.io/api/v1/chat/completions \
-H "Authorization: Bearer $DROPSTONE_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"model": "dropstone-fast",
"messages": [
{"role": "user", "content": "Write a haiku about debugging."}
]
}'
Response
{
"id": "gen-1779530142-EfBhlhO1U2frV6tvMgKV",
"object": "chat.completion",
"created": 1779530142,
"model": "dropstone-fast",
"choices": [
{
"index": 0,
"message": { "role": "assistant", "content": "Stack trace at midnight..." },
"finish_reason": "stop"
}
],
"usage": {
"prompt_tokens": 11,
"completion_tokens": 23,
"total_tokens": 34,
"cost": 0.0000098
}
}
The usage.cost field is the billed amount in USD — what was deducted from your credit balance for this request (real provider cost × 1.3 markup).
Streaming
Set "stream": true to get a Server-Sent Events stream of token chunks. The stream ends with a data: [DONE] line and a final chunk containing the full usage block.
curl https://api.dropstone.io/api/v1/chat/completions \
-H "Authorization: Bearer $DROPSTONE_API_KEY" \
-H "Content-Type: application/json" \
-N \
-d '{
"model": "dropstone-fast",
"stream": true,
"messages": [{"role": "user", "content": "Count to 5."}]
}'
OpenAI SDK compatibility
Because the surface is OpenAI-compatible, you can use the official OpenAI SDK by overriding base_url:
from openai import OpenAI
client = OpenAI(
base_url="https://api.dropstone.io/api/v1",
api_key=os.environ["DROPSTONE_API_KEY"],
)
resp = client.chat.completions.create(
model="dropstone-fast",
messages=[{"role": "user", "content": "Hello"}],
)
print(resp.choices[0].message.content)
Error codes
| Code | Meaning | Action |
|---|---|---|
400 | Invalid request body (bad model, missing messages, etc.) | Check the response error.message |
401 | Missing, malformed, or revoked API key | Generate a new key in the dashboard |
402 | Insufficient credits. Balance is $0 or negative | Top up at /dashboard/billing |
403 | Account suspended or banned | Contact support |
429 | Rate limit (future — not enforced today) | Back off and retry |
500 | Server error | Retry with exponential backoff |
502 | Upstream provider error | Retry with exponential backoff |
402 response shape
{
"error": "Insufficient credits",
"balance": 0,
"message": "Your credit balance is empty. Top up at https://dropstone.io/dashboard/billing to continue.",
"topUpUrl": "https://dropstone.io/dashboard/billing"
}
Rate limits
There are no hard rate limits enforced on the API today. Per-key usage tiers and daily spend caps are planned — when they ship, your existing keys will be auto-tiered based on lifetime spend, similar to OpenAI's tier system.
For now, set per-key budgets yourself by tracking the usage.cost field in your application.
Recommended practices
- Use environment variables, never inline keys:
DROPSTONE_API_KEY=dsk_live_.... - One key per service, not one key shared everywhere. Easier to revoke when a service is compromised.
- Watch
usage.costin responses to track spend in real time. - Handle 402 gracefully — your app should detect it and surface a top-up CTA rather than retrying.
- Cache responses for repeated identical requests on your side — we cache at the model level, but you save the full markup by short-circuiting before reaching us.
Differences from the CLI and SDK
| Surface | Auth | Pricing model | Models | Use case |
|---|---|---|---|---|
| HTTP API (this page) | API key | Pay-per-use from credit balance | Fast / Pro / Heavy | CI, automation, integrations |
| CLI (docs) | Interactive sign-in | Subscription + credit balance | Same three + free open-source models | Day-to-day coding in a terminal |
| JS SDK (docs) | Spawns local CLI, inherits its auth | Same as CLI | Same as CLI | Embedding the agent in a Node app |
If you want headless programmatic access in CI or a server, the HTTP API is the right surface. The SDK is for embedding the interactive agent in a Node process where a human is still in the loop.
Coming soon
These are on the roadmap and will land under the same /api/v1 namespace:
POST /api/v1/agent/run— agent loop endpoint. Send a task, get a finished diff. Server-side multi-turn loop with built-in tools (file editing, web search, code execution). Flat per-task pricing.POST /api/v1/memory/store+GET /api/v1/memory/query— stateful memory via Qdrant. Agent context that persists across calls.- MCP tool injection — include your own MCP server URLs in agent requests, agent calls them as native tools.
- Per-key spend caps — set a daily $ limit per key from the dashboard. CI safety net.
Star the GitHub repo or watch the changelog to know when they ship.