Developer docs

API, CLI, and MCP docs.

Use one account API key across API, CLI, and MCP.

Open ai-native.md Open llms.txt

API

Backend jobs

Status: launch candidate. Use account API keys for upload, polling, downloads, and job lookup after production activation.

Copy API calls
CLI

Account-metered scripts

Product API. Run remote conversion from shell scripts with the same account quota and billing as API calls.

View commands
MCP

AI agents

Account-metered tools. Let agents convert, inspect usage, and open billing through the same API key.

Configure MCP

Choose the right integration

Match the interface to the operator.

Use API for server uploadsBest for SaaS products, backend jobs, and user-facing upload flows that need billing and API keys.

Use CLI for scripted uploadsBest for shell jobs that can read local files but should still use account quota and billing.

Use MCP for agent tool callsBest when an AI host should call conversion, job status, usage, and billing actions directly.

Quickstart

From browser trial to production call.

  1. Try a fileUse the homepage uploader to confirm output quality.
  2. Create an accountSign in with Google or GitHub, then open API keys.
  3. Generate a keyCopy the key once and store it in your server environment.
  4. Open Developer SetupUse the account app snippets for API, CLI, and MCP configuration.
  5. Install clientsRun the editable package install when CLI or MCP should upload local files through the product API.
  6. AutomateCall API, CLI, or MCP depending on who operates the workflow.

Copy-ready sequence

Set PDF2MD_API_KEY, then upload.

Keep production keys in server or agent secrets. Never place API keys in browser code.

export PDF2MD_API_KEY="$(op read 'op://PDF2MD/prod/api-key')"

curl -X POST https://markovo.net/v1/convert \
  -H "Authorization: Bearer ${PDF2MD_API_KEY}" \
  -F "file=@paper.pdf" \
  -F "file=@appendix.pdf" \
  -F "mode=fast" \
  -F "max_credits=30"

Developer Setup

Copy-ready Developer Setup.

The account app shows the same snippets after sign-in. Replace placeholders with your API key and keep secrets in backend or agent environments.

export PDF2MD_BASE_URL="https://markovo.net"
export PDF2MD_API_KEY="$(op read 'op://PDF2MD/prod/api-key')"
python -m pip install -e ".[api,ocr,cloudflare]"
pdf2md doctor --json
pdf2md convert paper.pdf --out runs/paper --mode fast
pdf2md usage
{
  "mcpServers": {
    "pdf2md": {
      "command": "pdf2md-mcp",
      "env": {
        "PDF2MD_BASE_URL": "https://markovo.net",
        "PDF2MD_API_KEY": "${PDF2MD_API_KEY}"
      }
    }
  }
}
Open Developer Setup

API quickstart

Upload, poll, download.

Use multipart upload for one or more source PDFs, then poll each returned job until it succeeds. Put API keys in backend environments, not browser code.

curl -X POST https://markovo.net/v1/convert \
  -H "Authorization: Bearer mk_live_..." \
  -F "file=@paper.pdf" \
  -F "file=@appendix.pdf" \
  -F "mode=fast" \
  -F "max_credits=30"

The response includes jobs[]. For backwards compatibility, job_id points to the first queued job.

curl https://markovo.net/v1/jobs/{job_id} \
  -H "Authorization: Bearer ${PDF2MD_API_KEY}"
curl -L "https://markovo.net/v1/jobs/{job_id}/download?format=md" \
  -H "Authorization: Bearer ${PDF2MD_API_KEY}" \
  -o output.md

Authentication

Use account API keys for production.

Create a key inside the account app after signing in. Plaintext is shown once.

  • Header: Authorization: Bearer mk_live_...
  • Scope: markovo:convert
  • Usage is settled against the single conversion.credits balance.
  • Login capability: GET /v1/account/auth/providers reports enabled OAuth providers and email-code signup state.
Open API keys

OAuth setup

Use the product domain as the callback origin.

Markovo keeps auth same-origin through /api/auth/*. Configure providers with the product gateway callback, not the account service URL.

Google redirect URIhttps://markovo.net/api/auth/callback/google

GitHub callback URLhttps://markovo.net/api/auth/callback/github

Trusted originBETTER_AUTH_TRUSTED_ORIGINS=https://markovo.net

Provider discoveryGET /v1/account/auth/providers should list Google and GitHub before buttons are enabled.

Keep the existing workers.dev callback only for the seven-day rollback window. The production Google and GitHub apps must both be verified against the exact Markovo callbacks above.

CLI

Remote conversion with account quota.

Product API client. The CLI uploads through PDF2MD_BASE_URL with PDF2MD_API_KEY, then polls and downloads the result bundle.

python -m pip install -e ".[api,ocr,cloudflare]"
export PDF2MD_BASE_URL="https://markovo.net"
export PDF2MD_API_KEY="mk_live_..."
pdf2md convert paper.pdf --out runs/paper --mode fast
pdf2md usage
pdf2md billing

Internal workers and local development can still use pdf2md local-convert; customer docs should use pdf2md convert.

MCP

Agent-callable account tools.

The MCP server exposes remote conversion, job status, usage, billing, and local diagnostics over stdio. Use pdf2md-mcp with account API key env.

python -m pip install -e ".[api,ocr,cloudflare]"
export PDF2MD_BASE_URL="https://markovo.net"
export PDF2MD_API_KEY="mk_live_..."
pdf2md-mcp
# or: pdf2md mcp
{
  "mcpServers": {
    "pdf2md": {
      "command": "pdf2md-mcp",
      "env": {
        "PDF2MD_BASE_URL": "https://markovo.net",
        "PDF2MD_API_KEY": "${PDF2MD_API_KEY}"
      }
    }
  }
}

Production domain

Activate markovo.net, then keep workers.dev as a seven-day rollback path.

  1. Review migrationsApprove the production account and conversion D1 migrations before applying them.
  2. Activate the Worker custom domainsRoute markovo.net to Markovo Edge and redirect www.markovo.net permanently to the root domain.
  3. Verify authenticationTest Google, GitHub, email verification, password reset, logout, and cross-device sessions.
  4. Verify conversion and BillingRun a real estimate, Credit reservation, conversion, download, Creem Sandbox checkout, webhook, and Portal round trip.

Availability

What is usable now.

BrowserThe launch UI and edge routes are ready; production domain activation remains pending.

AccountGoogle, GitHub, and email flows are implemented; real production callback and delivery smoke remains pending.

API keysPro keys unlock account usage, billing, and job lookup.

CLIpdf2md convert, account, usage, and billing use account API keys.

MCPpdf2md-mcp exposes remote conversion, job status, usage, billing, and diagnostics.

Email codesSignup, verification, and reset use Alibaba Cloud DirectMail over TLS from the verified support@markovo.net sender.

Integration readiness

What is verified today.

API: verified locallyTests cover estimates, Credit ceilings, ownership, queue messages, downloads, and aggregate analytics.

Usage: verified by worker testsAuthenticated worker reserves and settles page usage around conversion, then releases reservations after failure.

CLI: account-metered clientRemote client tests cover upload, polling, download, usage, billing, and quota errors.

MCP: account-metered toolsstdio tools expose remote conversion, job lookup, usage, billing, and structured quota errors.

Production release smoke: pendingReal domain, login, Container, download, quota, and Checkout verification starts only after approved deployment.

Limits

Plans control file, page, OCR, and mode access.

  • Anonymous users get 1 conversion per UTC day, with 10 MB and 10 pages per file.
  • Signed-in free users get 5 conversions per UTC day across browser and API, with 25 MB and 50 pages per file.
  • Plus is $8/month with 2,000 Credits, allows 100 conversions per UTC day, up to 20 files per request, and 50 MB / 500 pages per file.
  • Pro is $19/month with 6,000 Credits, allows 500 conversions per UTC day, up to 50 files per request, and 50 MB / 500 pages per file.
  • Credit packs add to the current account without changing plan limits and expire after 365 days.
  • Subscriptions use conversion.credits, roll over at most one month, and cap the balance at twice the monthly grant.
  • Anonymous and Free results expire after one hour; Plus after 7 days; Pro after 30 days. Source files are deleted after processing.
  • Jobs estimated above 12 minutes are rejected before storage or queueing.