API-Referenz
Die API ist dafür gemacht, die Partien eines Nutzers in ein anderes System zu übernehmen. Du bekommst schlanke JSON-Listen, vollständige Partiedaten, einen PGN-Export und einen Feed für die inkrementelle Synchronisierung. Jede Antwort ist auf den Nutzer hinter dem Access-Token beschränkt.
Basis-URL: https://api.chessscanner.com
Authentifiziere jede Anfrage mit dem Bearer-Token aus der Autorisierung:
Authorization: Bearer ACCESS_TOKEN
Aktuellen Nutzer abrufen
GET /api/v1/me (Scope user.read)
Gibt das Basisprofil des authentifizierten Nutzers zurück.
curl https://api.chessscanner.com/api/v1/me \
-H "Authorization: Bearer $TOKEN"
{
"data": {
"id": "5f8c…",
"name": "Magnus",
"email": "magnus@example.com",
"image": "https://cdn.chessscanner.com/…"
}
}
Die id ist eine paarweise pseudonyme Kennung. Sie ist für deine App stabil,
aber für jede App unterschiedlich, und nie die echte interne id des Nutzers.
Nutze sie als Schlüssel für den Nutzer in deinem System.
Datenbanken auflisten
GET /api/v1/databases (Scope databases.read)
Gibt die Datenbanken zurück, die dem Nutzer gehören.
curl https://api.chessscanner.com/api/v1/databases \
-H "Authorization: Bearer $TOKEN"
{
"data": [
{
"id": "9a1c…",
"name": "Meine Partien",
"slug": "meine-partien",
"private": true,
"maxGames": 500,
"createdAt": "2026-06-14T10:00:00.000Z",
"updatedAt": "2026-06-14T10:00:00.000Z"
}
]
}
Partien einer Datenbank auflisten
GET /api/v1/databases/{id}/games (Scope games.read)
Gibt die Partien einer Datenbank zurück. Mit format=pgn lädst du alle Partien
als eine einzige PGN-Datei herunter statt als JSON.
Parameter
- Name
- id
- Type
- Required
- Description
Datenbank-UUID oder Slug, im Pfad.
string- Name
- limit
- Type
- OptionalDefault: 50
- Description
Anzahl der Partien pro Seite (max. 200).
integer- Name
- offset
- Type
- OptionalDefault: 0
- Description
Wie viele Partien übersprungen werden.
integer- Name
- format
- Type
- Optional
- Description
Auf
pgnsetzen für einen PGN-Sammelexport.
string
# JSON
curl "https://api.chessscanner.com/api/v1/databases/<id>/games?limit=25" \
-H "Authorization: Bearer $TOKEN"
# PGN
curl "https://api.chessscanner.com/api/v1/databases/<id>/games?format=pgn" \
-H "Authorization: Bearer $TOKEN"
Partien auflisten
GET /api/v1/games (Scope games.read)
Gibt die Partien des Nutzers über alle Datenbanken hinweg als schlanke Liste
zurück (ohne Züge oder PGN). Für eine einzelne Datenbank nutze
GET /api/v1/databases/{id}/games.
Parameter
- Name
- limit
- Type
- OptionalDefault: 50
- Description
Anzahl der Partien pro Seite (max. 200).
integer- Name
- offset
- Type
- OptionalDefault: 0
- Description
Wie viele Partien übersprungen werden.
integer
{
"data": [
{
"id": "1b2d…",
"slug": "magnus-vs-hikaru",
"databaseId": "9a1c…",
"event": "Casual",
"date": "2026-05-01",
"result": "1-0",
"eco": "B90",
"white": {
"name": "Magnus",
"elo": 2830,
"fideId": "1503014",
"country": "NOR"
},
"black": {
"name": "Hikaru",
"elo": 2790,
"fideId": "2016192",
"country": "USA"
}
}
]
}
Die Spieler-Referenzen white/black enthalten fideId und country in
jeder Partienliste, im Änderungs-Feed und im Partie-Detail — nutze die FIDE-ID,
um Spieler deinen eigenen Datensätzen zuzuordnen.
Eine Partie abrufen
GET /api/v1/games/{id} (Scope games.read)
Gibt eine Partie mit allen Daten zurück, inklusive Zügen, PGN und metadata —
den zusätzlichen PGN-Tag-Paaren der Partie (z. B. ein Site-Tag) als
JSON-Objekt. Mit format=pgn (oder dem Header Accept: application/x-chess-pgn)
bekommst du direkt das PGN; die PGN-Exporte enthalten diese zusätzlichen Tags
ebenfalls.
Parameter
- Name
- id
- Type
- Required
- Description
Partie-UUID, im Pfad.
string- Name
- format
- Type
- Optional
- Description
Auf
pgnsetzen, um das PGN statt JSON zurückzubekommen.
string
curl "https://api.chessscanner.com/api/v1/games/<id>?format=pgn" \
-H "Authorization: Bearer $TOKEN"
{
"data": {
"id": "1b2d…",
"result": "1-0",
"white": { "name": "Magnus", "fideId": "1503014", "country": "NOR" },
"black": { "name": "Hikaru", "fideId": "2016192", "country": "USA" },
"fen": "…",
"moves": "e2e4 c7c5 …",
"pgn": "1. e4 c5 …",
"metadata": { "Site": "Oslo" }
}
}
Änderungs-Feed
GET /api/v1/changes (Scope games.read)
Der empfohlene Weg, ein externes System aktuell zu halten. Der Feed gibt Partien
in der Reihenfolge ihrer letzten Änderung zurück, einschließlich gelöschter
Partien (mit deleted: true), und blättert mit einem undurchsichtigen Cursor.
Parameter
- Name
- cursor
- Type
- Optional
- Description
Undurchsichtiger Cursor aus einer früheren Antwort. Beim ersten Lauf weglassen.
string- Name
- since
- Type
- Optional
- Description
ISO-Zeitstempel, ab dem beim ersten Lauf begonnen wird, statt eines kompletten Backfills.
string- Name
- limit
- Type
- OptionalDefault: 100
- Description
Anzahl der Änderungen pro Seite (max. 500).
integer
# Erster Lauf
curl "https://api.chessscanner.com/api/v1/changes?limit=200" \
-H "Authorization: Bearer $TOKEN"
# Spätere Läufe: den vorherigen nextCursor übergeben
curl "https://api.chessscanner.com/api/v1/changes?cursor=<opaque>" \
-H "Authorization: Bearer $TOKEN"
{
"data": [
{
"id": "1b2d…",
"databaseId": "9a1c…",
"updatedAt": "2026-06-14T10:00:00.000Z",
"deleted": false,
"white": { "name": "Magnus" },
"black": { "name": "Hikaru" },
"result": "1-0"
}
],
"nextCursor": "<opaque>",
"hasMore": true
}
Behandle den Feed als Signal, dass sich etwas geändert hat, und hole dann den
aktuellen Stand. Für die vollständigen Züge folge mit GET /api/v1/games/{id}
oder ?format=pgn. Für sofortige Updates nutze einen
Webhook statt zu pollen.
Rate Limiting
Anfragen sind pro App und Nutzer begrenzt. Bei Überschreitung bekommst du
429 Too Many Requests mit einem Retry-After-Header und X-RateLimit-*-Headern.
Warte die angegebene Zeit ab und versuche es dann erneut.
Fehler
| Status | Bedeutung |
|---|---|
401 invalid_token | Access-Token fehlt, ist ungültig oder abgelaufen. Erneut autorisieren. |
403 insufficient_scope | Dem Token fehlt der nötige Scope |
404 not_found | Ressource nicht gefunden oder gehört nicht dem Nutzer |
429 rate_limited | Zu viele Anfragen. Siehe Retry-After. |
Fehler haben die Form { "error": "<code>", "error_description": "<message>" }.