Skip to content

Quickstart

A getting-started guide for direct customers (the data controller of their own club) who want to automate Kolleges via API. The canonical contract = the Open API v2 reference. If you’re a channel partner operating multiple clubs on others’ behalf, see the separate Partner API reference (host partner.kolleges.net).

  • API client (apiClient) = the credential unit you issue in the dashboard. Bound to exactly one club.
  • Authentication = OAuth2 client_credentials. No long-lived static keys — exchange your client_secret for a 15-minute ES256 token and use that.
  • Surface = https://openapi.kolleges.net/v2/clubs/{clubDomain}/…. clubDomain lives in the path only.
  • Responses = { data } (single) · { data, meta } (cursor list) · BatchResultDto (issuance batch). Errors = RFC 9457 application/problem+json.
  1. In the admin-next sidebar, Developers“New client”:

    • Copy client_id + client_secret once, on screen — this is the only time they’re shown. The platform keeps only a hash and cannot show them again. If lost, rotate.
    • Select scopes (deny-by-default · least privilege): clubs:read · billing:read · achievements:read · achievements:manage · designs:read · designs:manage · issuance:read · issuance:write · issuance:revoke · events:read.
  2. Get a token (every 15 minutes · server-side)

    Section titled “Get a token (every 15 minutes · server-side)”
    Terminal window
    curl -s -u "$CLIENT_ID:$CLIENT_SECRET" \
    -d 'grant_type=client_credentials' \
    -d 'scope=kolleges:openapi:issuance:write kolleges:openapi:issuance:read' \
    https://auth.kolleges.net/token
    # → { "access_token": "<ES256 JWT>", "token_type": "Bearer", "expires_in": 900, "scope": "…" }
  3. Terminal window
    TOKEN=<access_token>
    CLUB=<clubDomain>
    # Club identity and whether issuance is allowed
    curl -s -H "Authorization: Bearer $TOKEN" \
    https://openapi.kolleges.net/v2/clubs/$CLUB/
    # → { data: { domain, name, canIssue, grantedOperations } }
  4. Issue (bulk · a single issuance = an array of one)

    Section titled “Issue (bulk · a single issuance = an array of one)”
    Terminal window
    curl -s -X POST -H "Authorization: Bearer $TOKEN" \
    -H 'Content-Type: application/json' \
    -H "Idempotency-Key: order-2026-07-19-0001" \
    -d '{
    "achievementFormId": 123,
    "mode": "email",
    "recipients": [{ "externalUserId": "u-42", "name": "Jane Doe", "email": "jane@example.com" }]
    }' \
    https://openapi.kolleges.net/v2/clubs/$CLUB/issuances
    # → { results: [{ ref, status: "issued|skipped|failed", resourceId, error }],
    # summary: { total, ok, skipped, failed } }
  5. Terminal window
    # List issuances (cursor)
    curl -s -H "Authorization: Bearer $TOKEN" "https://openapi.kolleges.net/v2/clubs/$CLUB/issuances?limit=20"
    # Detail (recipient PII)
    curl -s -H "Authorization: Bearer $TOKEN" "https://openapi.kolleges.net/v2/clubs/$CLUB/issuances/456"
    # Certificate file
    curl -s -H "Authorization: Bearer $TOKEN" "https://openapi.kolleges.net/v2/clubs/$CLUB/issuances/456/file?format=pdf" -o cert.pdf
    # Revoke (= invalidate)
    curl -s -X POST -H "Authorization: Bearer $TOKEN" "https://openapi.kolleges.net/v2/clubs/$CLUB/issuances/456/revoke"
    # Event feed
    curl -s -H "Authorization: Bearer $TOKEN" "https://openapi.kolleges.net/v2/clubs/$CLUB/events?limit=20"

Learn more

  • Authentication — token flow, scope, and key rotation in depth.
  • Concepts — issuance, achievement, holder, and the response envelope.
  • Errors — RFC 9457 problem+json.
  • API reference — full endpoints, schemas, and interactive exploration.