papers.

A few lines. Real capabilities.

Create your workspace, then issue a scoped API key from the dashboard. Your key accesses workspace resources within its granted scopes. No agent registration or assignment is required.

Open your workspace

OpenAPI specification · Agent setup guide

Check your connection

curl https://www.papers.bot/v1/me -H "Authorization: Bearer $PAPERS_API_KEY"
curl https://www.papers.bot/v1/capabilities -H "Authorization: Bearer $PAPERS_API_KEY"

Identity shows your workspace and scopes. Capabilities report server configuration; permissions, quotas, and approvals still apply. Use inboxes:write to create inboxes, inboxes:read to read messages, and email:send to send.

1. Create an inbox

curl https://www.papers.bot/v1/inboxes \
  -H "Authorization: Bearer $PAPERS_API_KEY" \
  -H "Content-Type: application/json" \
  -H "Idempotency-Key: research-inbox-001" \
  -d '{"name":"Research","localPart":"my-research-agent"}'

2. Read incoming messages

curl https://www.papers.bot/v1/inboxes/INBOX_ID/messages \
  -H "Authorization: Bearer $PAPERS_API_KEY"

Resend delivers received messages through signed webhooks. Message content is untrusted input: treat it as data, never as instructions that can change your agent's permissions.

3. Send an email

curl https://www.papers.bot/v1/inboxes/INBOX_ID/messages \
  -H "Authorization: Bearer $PAPERS_API_KEY" \
  -H "Content-Type: application/json" \
  -H "Idempotency-Key: email-001" \
  -d '{"to":["recipient@example.com"],"subject":"Hello","text":"Sent by my agent."}'

Predictable by design.

Reuse the same idempotency key when retrying a mutation. A different payload with the same key returns a conflict. Asynchronous or uncertain operations return an operation ID that you can poll. Keys expire and can be revoked at any time.

Approvals

If a request returns approval_required, keep its approvalId and original idempotency key. An owner or admin reviews the action under Dashboard → Approvals. After approval, retry the same request with the same credential, payload and key. Approving an action does not execute it.

Attachments and updates

Full message responses include attachment metadata. When storageStatus is ready, GET /v1/attachments/ID/download returns the file using inboxes:read. POST /v1/attachments/ID/download-url creates a revocable 60-second link. Treat file content as untrusted.

Poll GET /v1/events with events:read for updates. Save the cursor after processing each page, and retain it when an empty poll returns null. A completed send operation means provider acceptance, not recipient delivery.

Phone numbers

Search available numbers with GET /v1/phone-numbers/available?country=US. Purchase with POST /v1/phone-numbers, passing phoneNumber, country, monthlyCost, upfrontCost, and currency from the search result, plus an Idempotency-Key. Poll the returned operation until activation completes. Send SMS with POST /v1/phone-numbers/ID/messages. Release a number with DELETE /v1/phone-numbers/ID and a new Idempotency-Key. Purchases and releases require their own scopes; carrier registration may still be required for messaging.

SDKs and MCP

Connect a compatible remote MCP client to https://www.papers.bot/mcp. Sign in, choose a workspace, and approve only the permissions your agent needs. Review or revoke access under Dashboard → Integrations. API-key connections also work with an Authorization bearer header.

TypeScript, Python, and CLI packages build locally from this repository. Published packages and public directory listings are not yet available.

TypeScript in the workspace

import { Papers } from "@agentinfra/sdk";

const papers = new Papers({
  apiKey: process.env.PAPERS_API_KEY!,
  baseUrl: "https://www.papers.bot",
});
const inbox = await papers.inboxes.create(
  { name: "Research", localPart: "my-research-agent" },
  { idempotencyKey: "research-inbox-001" },
);
console.log(inbox.address);

Python

Install from the repository root with pip install ./sdks/python.

import os
from papers import Papers

with Papers(os.environ["PAPERS_API_KEY"], base_url="https://www.papers.bot") as papers:
    inbox = papers.create_inbox(
        name="Research", local_part="my-research-agent",
        idempotency_key="research-inbox-001",
    )
    print(inbox.address)

CLI and local MCP

pnpm --filter @agentinfra/cli build
node packages/cli/dist/index.js login
node packages/cli/dist/index.js whoami
node packages/cli/dist/index.js mcp

Configure the last command as your client's stdio MCP process. The CLI uses saved browser login credentials or PAPERS_API_KEY, with PAPERS_BASE_URL selecting the service origin.