Skip to content
API

Connect anything to Verso.

One key, plain HTTP. Everything on this page works today. If it is not on this page, it does not exist yet.

Getting a key

In Verso, open Settings, Integrations and connect a source. You are handed a key that looks like vrs_<source-id>.<secret> once, and never again, because nothing stores it in a form anyone can read back. Lost it? Connect again: that mints a new one and stops the old one working.

A key is not an account key. It belongs to one source, in one workspace. It cannot read your billing, cannot see another source, and cannot reach another workspace, which the database itself enforces rather than the code remembering to. Send it as a bearer token:

Authorization: Bearer vrs_...

Pushing documents in

PATCH/api/connectors/{sourceId}

Declare what this source is reading. scope is a list of paths; "*" means everything, and a leading ! excludes, beating every include whatever order the list is in. An empty list matches nothing, which is the safe default rather than an accident.

curl -X PATCH https://app.versovoice.com/api/connectors/$SOURCE \
  -H "Authorization: Bearer $KEY" \
  -H "Content-Type: application/json" \
  -d '{"scope": ["*", "!Journal"]}'

POST/api/connectors/{sourceId}/sync

Send a batch of files. Up to 200 per request. Each one is checked before it is stored, and anything holding a live key, a password, a confidentiality marker or somebody else's personal details is refused with its reason recorded, which you can read back in Verso.

curl -X POST https://app.versovoice.com/api/connectors/$SOURCE/sync \
  -H "Authorization: Bearer $KEY" \
  -H "Content-Type: application/json" \
  -d '{"files": [{"path": "Work/standup.md", "text": "..."}]}'

{"ingested": 1, "unchanged": 0, "skipped": 0, "skips": []}

A file whose text has not changed since last time comes back as unchanged and costs nothing, so re-sending your whole set is cheap and safe.

MCP, for AI tools

Verso is also an MCP server, which is the socket Claude, Cursor, VS Code and the rest already speak. Point a client at /api/mcp with the same bearer key and it can search your work, add to it, and ask Verso for a draft.

{
  "mcpServers": {
    "verso": {
      "url": "https://app.versovoice.com/api/mcp",
      "headers": { "Authorization": "Bearer vrs_..." }
    }
  }
}

It offers four tools: search_my_work, add_to_verso, draft_post and list_drafts. There is no publish tool, on purpose. Verso writes drafts. A person opens Verso and decides what goes out, and there is no setting that changes that.

The exact block for your own workspace, including the key, is on the Integrations page inside Verso. It speaks the 2025-06-18 revision over Streamable HTTP, and it is stateless, so there is no session to manage.

Or connect with no key at all

Verso is a full OAuth 2.1 authorization server, so a client can register itself and send its user through a normal sign-in instead of asking them to paste a secret. Start at the discovery document; everything else is in there.

GET https://app.versovoice.com/.well-known/oauth-protected-resource
GET https://app.versovoice.com/.well-known/oauth-authorization-server
  • PKCE is required, and only S256 counts. An MCP client runs on somebody's laptop and cannot keep a secret, so this is what protects the code exchange.
  • Dynamic client registration is open, so nobody has to paste a client id anywhere.
  • A person always sees a consent screen, whatever the client asks for. Verso adds prompt=consent itself rather than leaving the decision to ask to the party being asked about.
  • A 401 from /api/mcp carries WWW-Authenticate with the address of the first document above, so a client can find its way from a refusal.

Limits, and what comes back

  • 200 files per sync, 8 MB of text per file. Bigger than that is a data dump, not a note.
  • 30 syncs a minute per workspace, and the MCP endpoint has its own per-tool limits. Over either and you get a 429, so wait and retry rather than looping.
  • A wrong, missing, or disconnected key is a plain 401. A key aimed at a source it does not own is also a 401, not a 403, because confirming that somebody else's source exists is itself a leak.
  • Errors are plain text and say what a person can do about it. They never carry a stack or anything internal.

What Verso will not do

It never publishes anything by itself, over any of these routes. Everything you send is encrypted before it is stored. Disconnecting a source deletes the source, its key, and every document that came in through it, in one press.