---
title: "Introspect this API key's scopes and rate-limit status"
method: GET
path: "/introspect"
---

# Introspect this API key's scopes and rate-limit status

`GET /introspect`

## Request

- Base URL: `https://localselections.com/api/v1`
- URL: `https://localselections.com/api/v1/introspect`
- Auth: API key in header `X-API-Key`

Stage 104 Part C: returns the calling key's real granted scopes, which of the six v1 endpoints each is currently allowed to call, and the current rate-limit tier/window usage — call this before attempting an endpoint to avoid discovering a 403 insufficient_scope or a 429 rate_limited only by triggering it. Open to any valid key regardless of its own scopes (no scope requirement), and read-only against the rate limit: checking never spends any of the key's own budget.

## Response `200`

The key's real current scopes, per-endpoint access, and rate-limit usage.

- object
  - `scopes` string[], required: The raw scopes array stored on this key, e.g. ["all"] or ["spin", "search"].
  - `grants` object, required: One boolean per real v1 endpoint scope, resolved the same way authenticateApiRequest() resolves it (an "all"-scoped key shows every value as true).
    - `spin` boolean, required
    - `search` boolean, required
    - `surprise_me` boolean, required
    - `bracket` boolean, required
    - `groups_host` boolean, required
    - `groups_join` boolean, required
    - `places` boolean, required
    - `events` boolean, required
    - `movies` boolean, required
  - `rateLimit` object, required
    - `tier` 'free' | 'subscribed', required
    - `limit` integer, required: Total rate-limit budget (in cost units, not raw request count) for the current window.
    - `remaining` integer, required
    - `windowSeconds` integer, required
    - `resetAt` string, date-time, required
  - `commercial` boolean, required: Stage 198: true only after the owner has contacted us and been granted a paid commercial license. A commercial key is exempt from the free-tier daily ceiling on places/events/movies (see those paths' own 429 daily_limit_exceeded response) — its real limits are whatever was negotiated in that license, not enforced by this API.
  - `dataSearchUsage` object, required: Stage 198: today's real usage against the separate per-key-per-day ceiling on places/events/movies specifically (UTC calendar day) — checking this never spends any of it. Present regardless of `commercial` status; only enforced (429 daily_limit_exceeded) for a non-commercial key.
    - `places` object, required
      - `callCount` integer, required: Real calls made to this scope so far today (UTC).
      - `hardCeiling` integer, required: The free-tier daily limit for this scope (not enforced for a commercial key).
      - `dateKey` string, date, required: The UTC calendar day this count is for.
    - `events` object, required
      - `callCount` integer, required: Real calls made to this scope so far today (UTC).
      - `hardCeiling` integer, required: The free-tier daily limit for this scope (not enforced for a commercial key).
      - `dateKey` string, date, required: The UTC calendar day this count is for.
    - `movies` object, required
      - `callCount` integer, required: Real calls made to this scope so far today (UTC).
      - `hardCeiling` integer, required: The free-tier daily limit for this scope (not enforced for a commercial key).
      - `dateKey` string, date, required: The UTC calendar day this count is for.

## Other responses

- `401`: Missing or invalid API key.

---

[API](https://skmtc.dev/localselections/apis/localselections-public-api.md) · [All operations](https://skmtc.dev/localselections/apis/localselections-public-api/llms.txt) · [OpenAPI document](https://skmtc.dev/localselections/apis/localselections-public-api/revisions/a24e9598add4?raw)
