Skip to main content

srs-mcp

Agent-agnostic MCP server for spaced-repetition learningno Anki GUI, no Xvfb, no AnkiConnect. Bring your own agent; this brings the card box + the scheduler.

It wraps FSRS (the Free Spaced Repetition Scheduler, the same algorithm modern Anki uses) around a tiny SQLite store, so an agent can author cards, see what's due, and record recall — entirely headless.

Why not headless Anki?

Driving the Anki desktop app headless means Qt + a virtual framebuffer (Xvfb) + the AnkiConnect add-on — brittle and version-coupled. The anki PyPI package can drive a real .anki2 collection GUI-less if you need interop with your phone's Anki. But if you just want spaced repetition behind an API, you don't need Anki at all: FSRS is a library, and this server is ~200 lines around it.

Tools

  • add_card(front, back) -> {card_id, due} — author + schedule a card. Keep back short — a word or a phrase; a card you can't grade in seconds is a note, not a flashcard
  • due_cards(q=None, limit=20) -> [{card_id, front, back, deck, due}] — what's due now, optionally narrowed to a topic (q="horace")
  • grade_card(card_id, rating) -> {card_id, rating, next_due, reps} — record recall (again/hard/good/easy, or 1-4)
  • edit_card(card_id, front=None, back=None) — edit content in place; schedule is preserved (fix typos / shorten a long answer instead of duplicating)
  • suspend_card(card_id) / unsuspend_card(card_id) — shelve a card (kept with its history, removed from the due queue) / restore it
  • list_cards(q=None, limit=50) — overview regardless of due date
  • delete_card(card_id) — remove one (reset / cleanup)
  • stats(deck=None) -> {total, due_now, suspended, reviews, decks}

Finding cards: search, not decks

Cards are found by searching their textdue_cards(q="horace") — rather than by filing them into decks up front. Nothing writes the deck field any more; put the topic in the card itself ("Horace, Odes 1.11: …") and it stays findable.

Decks were a single-valued, free-text, exact-match label with no per-deck scheduling attached, so they bought nothing a search doesn't, and cost accuracy: on the deck this was measured against, agents had invented ten names for Horace across five separator conventions, so the best possible deck="Horace" returned 20 of 97 Horace cards while q="horac" returns 89 — including ones misfiled under Talks. The column and the deck= filter on due_cards/list_cards/stats remain for cards labelled by older versions. See plans/002-decks.md.

The review loop: due_cards → quiz the user with front → check against backgrade_card. FSRS computes the next due date from the rating.

Run

uv sync
# HTTP (default; for Railway / remote agents)
PORT=8000 uv run srs-mcp
# or stdio (local agent)
MCP_TRANSPORT=stdio uv run srs-mcp

Storage

Two backends, chosen at startup:

  • Postgres (shared deck) — set SRS_DATABASE_URL (or DATABASE_URL) to a Postgres connection string (e.g. a Neon DB). Every deployment that points at the same URL reads/writes one shared deck, so you can add and review cards from anywhere (local, Railway, etc.). FSRS card ids are large, so the cards.card_id column is BIGINT on Postgres. Requires the psycopg dependency (already declared).
  • SQLite (fallback) — when no *DATABASE_URL is set, cards live in a SQLite file at SRS_DB (default ./srs.db). Single-host / offline. In a SQLite-on-Railway setup, mount a volume at /data and keep SRS_DB=/data/srs.db so the box survives redeploys.

The schema is identical (table cards) and auto-created on first use.

Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

srs_mcp-0.3.0.tar.gz (96.7 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

srs_mcp-0.3.0-py3-none-any.whl (11.6 kB view details)

Uploaded Python 3

File details

Details for the file srs_mcp-0.3.0.tar.gz.

File metadata

  • Download URL: srs_mcp-0.3.0.tar.gz
  • Upload date:
  • Size: 96.7 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: uv/0.8.17

File hashes

Hashes for srs_mcp-0.3.0.tar.gz
Algorithm Hash digest
SHA256 3a892628dd53e9c5ddf15470710766e494f1ae3cf6c1c232828a7b967bf28d5e
MD5 5805563529d166d961b7bd626236fdf4
BLAKE2b-256 129cd4946a380eeb2ccf6d89f5137c3f84efe39d166ff38b5c185366f34e06df

See more details on using hashes here.

File details

Details for the file srs_mcp-0.3.0-py3-none-any.whl.

File metadata

  • Download URL: srs_mcp-0.3.0-py3-none-any.whl
  • Upload date:
  • Size: 11.6 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? No
  • Uploaded via: uv/0.8.17

File hashes

Hashes for srs_mcp-0.3.0-py3-none-any.whl
Algorithm Hash digest
SHA256 ac47c680ca4fe5eb37a535b23bd7bc141fd3a028dc895b589833ed190a829108
MD5 8d008cccea4a5fb881475a83b92b27bf
BLAKE2b-256 1f7eafe27f2a0defc7a1784a290a6479bb792503621ee88488249af693bb3bfb

See more details on using hashes here.

Release history Release notifications | RSS feed

This release

0.3.0 This release

2 files

0.2.1

2 files

0.2.0

2 files

0.1.0

2 files

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page