> ## Documentation Index
> Fetch the complete documentation index at: https://docs.platform.toloka.ai/docs/llms.txt
> Use this file to discover all available pages before exploring further.

# Client and credentials

> Configure the client, issue project-scoped tokens, and handle request limits.

Call [`createClient`](https://docs.platform.toloka.ai/docs/sdk/reference/create-client) with a `baseUrl` and exactly one credential. The SDK does not read environment variables or the CLI's saved login automatically. This example reads your account with [`client.me()`](https://docs.platform.toloka.ai/docs/sdk/reference/account/me).

```ts theme={null}
import { createClient } from "@toloka-platform/sdk";

const apiKey = process.env.TOLOKA_API_KEY;
if (!apiKey) throw new Error("Set TOLOKA_API_KEY");

const client = createClient({
  baseUrl: process.env.TOLOKA_BASE_URL ?? "https://platform.toloka.ai",
  apiKey,
});

console.log((await client.me()).email);
```

## Choose a credential

| Configuration | Type | Header |
| - | - | - |
| `apiKey` | `string` | `Authorization: ApiKey <key>` |
| `scopedToken` | `string` | `X-Scoped-Token: <token>` |
| `accessToken` | `() => Promise<string>` | `Authorization: Bearer <token>` |

An `apiKey` beginning with `pst_` is also sent as `X-Scoped-Token`. The `accessToken` callback runs for each SDK request; your callback is responsible for obtaining a valid token. The client does not renew it for you.

The `ClientConfig` type makes the three credentials mutually exclusive. API keys and scoped tokens must be nonempty strings.

## Delegate access to a project

Use a short-lived, project-scoped token for a CI job or coding agent. It acts as the issuing user with a selected permission set and project scope. Call [`projects.createToken()`](https://docs.platform.toloka.ai/docs/sdk/reference/projects/create-token) using an API key or access token; a scoped token cannot create another token.

This example uses the `client.ts` module from the [quickstart](https://docs.platform.toloka.ai/docs/sdk/quickstart.md#2-create-a-client). Set `TOLOKA_PROJECT_ID` to the project you want the job to read with [`projects.get()`](https://docs.platform.toloka.ai/docs/sdk/reference/projects/get).

```ts theme={null}
import { createClient } from "@toloka-platform/sdk";
import { client } from "./client";

const projectId = process.env.TOLOKA_PROJECT_ID;
if (!projectId) throw new Error("Set TOLOKA_PROJECT_ID");

const issued = await client.projects.createToken({
  projectId,
  preset: "read",
  expiresInSeconds: 3_600,
});

const scopedClient = createClient({
  baseUrl: process.env.TOLOKA_BASE_URL ?? "https://platform.toloka.ai",
  scopedToken: issued.token,
});

try {
  const project = await scopedClient.projects.get({ projectId });
  console.log(project.name);
} finally {
  await scopedClient.projects.revokeCurrentToken();
}
```

Pass `preset` or an explicit `permissions` array. Presets are `read`, `write`, `deploy`, `labeling-read`, `labeling-write`, and `labeling-deploy`. `expiresInSeconds` accepts 60–21,600 seconds and defaults to six hours. The `token` value is returned only when issued; keep it in your job's secret storage. See [issue a project-scoped token](https://docs.platform.toloka.ai/docs/api-reference/projects/create-project-token.md) for the permission contract and additional project scope.

Manage issued tokens with these methods:

| Method | Result |
| - | - |
| [`projects.listTokens({ projectId, limit, offset })`](https://docs.platform.toloka.ai/docs/sdk/reference/projects/list-tokens) | One page of live token metadata in `tokens`, plus `pagination` |
| [`projects.listAllTokens({ projectId })`](https://docs.platform.toloka.ai/docs/sdk/reference/projects/list-tokens) | An async generator of live token metadata |
| [`projects.revokeToken({ projectId, tokenId })`](https://docs.platform.toloka.ai/docs/sdk/reference/projects/revoke-token) | Revokes one token; resolves to `undefined` |
| [`projects.revokeAllTokens({ projectId })`](https://docs.platform.toloka.ai/docs/sdk/reference/projects/revoke-all-tokens) | Revokes all live tokens for the project; returns `{ revokedCount }` |
| [`projects.revokeCurrentToken()`](https://docs.platform.toloka.ai/docs/sdk/reference/projects/revoke-current-token) | Revokes the scoped token authenticating this client; resolves to `undefined` |

Listing tokens and revoking them by project require an API key or access token. Only a scoped token can revoke itself. Revoking a token stops all its access, including access to any other projects it covers.

## Customize requests

`fetch` accepts a function with the same type as `globalThis.fetch`. Use it to add request instrumentation or inspect response headers. Keep credentials out of logs.

```ts theme={null}
import { createClient } from "@toloka-platform/sdk";

const apiKey = process.env.TOLOKA_API_KEY;
if (!apiKey) throw new Error("Set TOLOKA_API_KEY");

const observedFetch: typeof globalThis.fetch = async (input, init) => {
  const response = await globalThis.fetch(input, init);
  if (response.status === 429) {
    console.error("Retry after:", response.headers.get("Retry-After"));
    console.error("Rate limit reset:", response.headers.get("RateLimit-Reset"));
  }
  return response;
};

const client = createClient({
  baseUrl: "https://platform.toloka.ai",
  apiKey,
  fetch: observedFetch,
});

await client.me();
```

The client sends JSON request bodies. State-changing calls that take no body send `{}` with `Content-Type: application/json`. Successful JSON responses become typed objects; an empty response becomes `undefined`.

For the platform directly, use `https://platform.toloka.ai` as `baseUrl`. A path prefix is preserved: `https://gateway.example/platform` produces requests under `https://gateway.example/platform/api/v2-beta/...`. Do not append `/api/v2-beta` yourself.

## Rate limits and retries

The shared API limit is **60 requests per minute per endpoint route and user**. Different resource IDs on the same route share that limit. The SDK throws `PotatoApiError` for `429` and does not automatically retry it.

Delay subsequent requests and retry with backoff. Use a custom `fetch` to read `RateLimit-*` or `Retry-After` headers; `PotatoApiError` does not retain those headers. When token creation returns `429` because you hold 1,000 live tokens for a project, revoke unused tokens before creating another.

See [errors](https://docs.platform.toloka.ai/docs/sdk/errors.md) for a catch pattern and [pagination](https://docs.platform.toloka.ai/docs/sdk/pagination.md) for fetching more results per request.


This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.