Developer Platform

Open Scoreboard API

Technical documentation for the current v1 REST API, with copyable examples, route-by-route notes, and authenticated personal API key management.

Public developer docs

Authentication

Open Scoreboard accepts bearer tokens on every authenticated v1 route and supports OAuth token exchange for installed applications.

Available in v1

For local testing and single-account automation, use a developer key from this page. For production partner apps, exchange an authorization code or refresh token at /oauth/token and then send the returned access token as Authorization: Bearer <token>.

HeaderAuthorization: Bearer <token>
Token exchangePOST /oauth/token
DisconnectDELETE /connection

Implementation notes

  • OAuth token exchange accepts application/json and application/x-www-form-urlencoded payloads.
  • Refresh tokens are single-use and rotated on every successful refresh.
  • PKCE S256 is supported for authorization code flows, but the registered client secret is still required.

Endpoints

OpenAPI
POST/oauth/token

Exchange an authorization code

Turn an authorization code into an access token, refresh token, scopes, and connection metadata.

Response

Returns access_token, refresh_token, expires_in, refresh_expires_in, connection_id, and scope.

  • grant_type must be authorization_code or refresh_token.
  • If the original authorization request used PKCE, send the matching code_verifier.
curl
curl https://your-domain.example/api/v1/oauth/token \
  -H "Content-Type: application/json" \
  -d '{
    "grant_type": "authorization_code",
    "client_id": "osb_app_your_client_id",
    "client_secret": "osb_client_your_client_secret",
    "code": "osb_code_your_authorization_code",
    "redirect_uri": "https://partner.example/oauth/callback",
    "code_verifier": "your-pkce-code-verifier"
  }'
JavaScript
const response = await fetch("https://your-domain.example/api/v1/oauth/token", {
  method: "POST",
  headers: {
    "Content-Type": "application/json"
  },
  body: JSON.stringify({
    grant_type: "refresh_token",
    client_id: "osb_app_your_client_id",
    client_secret: "osb_client_your_client_secret",
    refresh_token: "osb_refresh_your_refresh_token"
  })
});

const tokens = await response.json();
console.log(tokens);
DELETE/connection

Disconnect the current installation

Revoke the active connection and all of its issued access and refresh tokens.

Any valid bearer token
Response

Returns the revoked connectionID and revokedOn timestamp.

curl
curl -X DELETE https://your-domain.example/api/v1/connection \
  -H "Authorization: Bearer osb_test_your_key_here"
JavaScript
const baseURL = "https://your-domain.example/api/v1";
const apiKey = "osb_test_your_key_here";

async function api(path, init = {}) {
  const response = await fetch(`${baseURL}${path}`, {
    ...init,
    headers: {
      "Authorization": `Bearer ${apiKey}`,
      "Content-Type": "application/json",
      "OpenScoreboard-Request-ID": "demo-request-001",
      ...(init.headers || {})
    }
  });

  const body = await response.json();
  if (!response.ok) {
    throw new Error(body.error?.message || "Request failed");
  }

  return body.data;
}

await api("/connection", { method: "DELETE" });
console.log("Connection revoked");