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

# Dictation Web Component - Authentication

> Access tokens and automatic token refresh for the Dictation Web Component

The Dictation Web Component requires authentication to connect to the Corti Dictation API. You provide an access token directly — the component does **not** handle OAuth internally.

<Info>The component is automatically hidden until authentication is provided. Once you set `accessToken` or `authConfig`, it becomes visible.</Info>

<Info>If you're using [proxying](/sdk/dictation/proxy) (`socketUrl` or `socketProxy`), authentication is handled by your proxy — `accessToken` and `authConfig` are ignored.</Info>

## Using `accessToken`

Set it as an HTML attribute or JavaScript property. You must update it manually before it expires:

```html theme={null}
<corti-dictation id="dictation" accessToken="YOUR_TOKEN"></corti-dictation>
```

```js theme={null}
dictation.accessToken = freshToken;
```

This approach is suitable for short-lived sessions or prototyping. For production, use `authConfig` with automatic refresh.

<Warning>If you're connecting without a proxy, prefer [scoped tokens](/sdk/js/authentication#scoped-tokens) so the frontend token can only access the WebSocket endpoint you need. When requesting tokens directly from Corti Auth (no SDK), use `scope="openid transcribe"` for the `/transcribe` endpoint and/or `scope="openid streams"` for the `/streams` endpoint — see [Security best practices](/authentication/security_best_practices#4-if-you-must-use-tokens-in-special-cases-use-limited-scope-credentials).</Warning>

<Tip>If you need to obtain an `accessToken`, you can use the [Corti JavaScript SDK authentication flows](/sdk/js/authentication) and then pass the resulting token into `accessToken` or `authConfig`.</Tip>

## Using `authConfig` (recommended)

Use `authConfig` when you want to supply token metadata and (optionally) enable automatic refresh. If you provide a `refreshAccessToken` callback, the component calls it automatically when the token is about to expire:

```js theme={null}
const dictation = document.querySelector("corti-dictation");

dictation.authConfig = {
    accessToken: "<your-access-token>",
    expiresIn: 300,
    refreshToken: "<your-refresh-token>",
    refreshAccessToken: async ({ refreshToken }) => {
        const res = await fetch("/api/token/refresh");
        const data = await res.json();

        return {
            accessToken: data.access_token,
            expiresIn: data.expires_in,
            refreshToken: data.refresh_token,
        };
    },
};
```

| Field                | Type                            | Required | Description                                                                                                                                                      |
| :------------------- | :------------------------------ | :------- | :--------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `accessToken`        | `string`                        | No       | Initial access token. If omitted, the component can only obtain a token if you also provide `refreshAccessToken`.                                                |
| `expiresIn`          | `number`                        | No       | Token lifetime in seconds. Used to schedule the next refresh.                                                                                                    |
| `refreshToken`       | `string`                        | No       | Refresh token passed to `refreshAccessToken` when a refresh is needed (if you provide the callback).                                                             |
| `refreshAccessToken` | `({ refreshToken }) => Promise` | No       | Optional callback for automatic refresh. Returns `{ accessToken, expiresIn?, refreshToken? }`. Without it, you must update `accessToken` yourself before expiry. |

## How token refresh works

Under the hood, Dictation Web Component uses Corti JavaScript SDK to connect. See [How token refresh works](/sdk/js/authentication#how-token-refresh-works) for the full behavior.

```js theme={null}
const dictation = document.querySelector("corti-dictation");

dictation.authConfig = {
    refreshAccessToken: async ({ refreshToken }) => {
        const res = await fetch("/api/token/refresh", {
            method: "POST",
            headers: { "Content-Type": "application/json" },
            body: JSON.stringify({ refreshToken }),
        });
        const data = await res.json();

        return {
            accessToken: data.access_token,
            expiresIn: data.expires_in,
            refreshToken: data.refresh_token,
        };
    },
};
```

1. **Initial token** -- If `accessToken` is provided in `authConfig`, it's used immediately. Otherwise, `refreshAccessToken` is called with `undefined` to obtain the first token.

2. **Automatic refresh** -- The component monitors the token's expiration and calls `refreshAccessToken` before it expires. The `refreshToken` parameter will be:
   * `undefined` on the first call (if no initial `refreshToken` was provided)
   * The `refreshToken` returned from the previous refresh call

3. **Seamless operation** -- Refresh happens in the background. Active dictation sessions continue without interruption.

## Using with modular components

When using individual components, set `authConfig` on `<dictation-root>`:

```html theme={null}
<dictation-root id="root">
    <dictation-recording-button></dictation-recording-button>
</dictation-root>

<script type="module">
    import "@corti/dictation-web";

    const root = document.getElementById("root");
    root.authConfig = {
        refreshAccessToken: async ({ refreshToken }) => {
            const res = await fetch("/api/token/refresh");
            const data = await res.json();
            return {
                accessToken: data.access_token,
                expiresIn: data.expires_in,
                refreshToken: data.refresh_token,
            };
        },
    };
</script>
```

## See also

* [API Reference](/sdk/dictation/reference) -- full property tables for all components
* [Proxy Guide](/sdk/dictation/proxy) -- route traffic through your own server (auth handled by proxy)
* [Examples](https://github.com/corticph/corti-examples/tree/main/dictation/typescript/web-component) -- token refresh example
