Skip to content

Accounts HTTP API ​

Accounts.route(request) answers these requests under its prefix, /api/accounts by default. AccountClient wraps all of them; this page is for clients written in other languages, and for debugging.

Bodies are JSON (Content-Type: application/json). A signed-in request carries the session either as the cookie (tf_session by default) or as Authorization: Bearer <session token>.

Endpoints ​

Method and pathBodyNeedsAnswer
POST /guestnone, or { token } to renewnothing{ id, token, expiresAt, renewAt }
POST /register{ name, password, email?, guestToken? }nothing201 { account, token }, sets the cookie
POST /login{ name, password }nothing{ account, token }, sets the cookie
POST /logoutnonea session204, clears the cookie
GET /mea sessionthe account
DELETE /me{ password }a session204: the account and everything in it is deleted
POST /password{ current, next }a session{ account, token }: every other session ends
POST /recovery-code{ password }a session201 { code }: a recovery code, shown this once. It replaces the one before
POST /recover{ name, code, password }nothing{ account, token }, sets the cookie. The code is used up and every other session ends
POST /forgot{ name } or { email }sendPasswordReset to be set204, whether or not there is such an account
POST /reset{ token, password }nothing{ account, token }, sets the cookie. The token is used up and every other session ends
POST /name{ name }a sessionthe account
POST /email{ password, email }a sessionthe account. email: null removes it
GET /exporta sessioneverything stored about the player, as a JSON download
POST /token{ scope? }a session{ token, expiresAt }: a join token with the account name
GET /data/:keya session{ key, value }, or 404
PUT /data/:key{ value }a session; key with write: "owner"{ key, value }
DELETE /data/:keya session; key with write: "owner"204
GET /players/:idnothingthe public profile, or 404
GET /leaderboards/:stat?limit=&offset=nothing{ stat, entries, total }. limit is 1 to 100, default 20

Times are epoch milliseconds. Join and guest tokens go in the token query parameter when connecting to a room or a queue.

Guests ​

POST /guest without a body makes up a new player. With { token }, where token is a guest token that is still valid, it returns a fresh token for the same player. Renew once renewAt has passed; a token past expiresAt can't be renewed.

POST /register with guestToken creates the account under the guest's player id, so what the guest earned stays theirs.

The account ​

GET /me and the endpoints that change the account return:

json
{
  "id": "4b7c…",
  "name": "Ada",
  "email": null,
  "createdAt": 1767225600000,
  "data": { "settings": { "music": false } },
  "stats": { "wins": 12, "games": 30 }
}

A public profile (GET /players/:id) has the same shape without email, and with only the public data keys.

Errors ​

Errors are JSON, with a machine-readable code:

json
{ "error": "name_taken", "message": "That name is taken." }
StatusCodeMeaning
400invalid_requestThe body or URL is malformed
400invalid_nameThe name breaks the name rules
400weak_passwordThe password is shorter than 8 characters
400invalid_emailThe email address is not one
400invalid_tokenThe password reset token is wrong, used, replaced or more than an hour old
400invalid_keyA data key must be 1 to 64 letters, digits, dots, dashes or underscores
400invalid_valueThe data value is not JSON, or a stat is not a finite number
400invalid_statA stat name must be 1 to 64 letters, digits, dots, dashes or underscores
401not_signed_inThe request needs a session and has none that is valid
401invalid_credentialsWrong name or password
401invalid_codeWrong name or recovery code
403wrong_passwordThe password given to confirm a change is wrong
403read_onlyPlayers can't write this data key
403origin_not_allowedThe request came from a page on an origin not in allowedOrigins
404not_foundNo such endpoint, player or data key
404not_enabledPOST /forgot on a game that has no sendPasswordReset
409name_takenSomeone has that name
409account_existsThis player id already has an account, e.g. a guest who registered before
409too_many_keysThe player has maxDataKeys keys already
413value_too_largeThe value is over maxDataBytes
415json_requiredThe body must be JSON
429too_many_attemptsToo many failed sign-ins: wait and try again

MIT licence. Tickflare is an independent project and is not affiliated with Cloudflare.