Authentication
Every protected request sends Authorization: Bearer <token>. There are two distinct credentials:
| Credential | Issued to | Used for |
|---|---|---|
| OAuth M2M access token | Your trusted backend | Server events, profile operations, purchases, and issuing client credentials |
| User-bound client credential | Your authenticated browser or mobile user | Scoring model, client event batches, and that user’s profile |
Server access tokens
Section titled “Server access tokens”Create an OAuth M2M client in the workspace for the intended environment. Request only the scopes that service needs. Exchange its ID and secret using HTTP Basic authentication:
curl --fail-with-body https://api.qa.streakline.dev/api/auth/oauth2/token \ --user "$STREAKLINE_CLIENT_ID:$STREAKLINE_CLIENT_SECRET" \ --data-urlencode 'grant_type=client_credentials' \ --data-urlencode 'resource=https://api.qa.streakline.dev' \ --data-urlencode 'scope=events:write profiles:read'Requested scopes must be allowed for the client. The response includes access_token, token_type, expires_in, and scope information. Renew the token before its expiry by making another exchange; M2M tokens do not include a refresh token.
The TypeScript server SDK accepts a token or an async auth callback. It does not exchange client secrets, cache tokens, or renew them. Your backend’s token provider owns that lifecycle.
Scope selection
Section titled “Scope selection”| Scope | Purpose |
|---|---|
events:write |
Track single and batched server events |
events:read |
Read a user’s event history |
profiles:read |
Read a user’s profile and achievements |
profiles:write |
Import existing user progress |
profiles:delete |
Delete a user |
store:purchase |
Purchase a configured store item |
client_credentials:issue |
Issue a user-bound client credential |
User-bound client credentials
Section titled “User-bound client credentials”Use a separate backend OAuth client with client_credentials:issue. After authenticating a request in your application, derive the user’s internal UUID from the server session and issue their credential:
import { StreaklineServer } from "@streakline/sdk/server";
const issuer = new StreaklineServer({ baseUrl: "https://api.qa.streakline.dev", auth: process.env.STREAKLINE_ISSUER_ACCESS_TOKEN!,});
// Inside your authenticated backend route:// session.user.internalId comes from your own verified session.const credential = await issuer.createClientCredential({ userId: session.user.internalId,});// Return this structured response to the same authenticated user.Client credentials expire after five minutes and are bound to one user, project, and environment. The web and React Native SDKs accept the full structured response, check its subject and expiry, and retry once with a new credential after a 401.
Keep server secrets and M2M access tokens out of browser and mobile bundles. The client SDK keeps the user-bound token in memory rather than persisting it.