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

# Migrate to OAuth 2.0 API credentials

If your integration signs in through `POST /login` with a Connector username, password and the `X-Api-Key` header, follow these steps to switch it to an OAuth 2.0 API credential.

> [!WARNING]
>
> `POST /login` is deprecated. It keeps working until **31 January 2027**. From 1 February 2027, the API accepts integrations only with an API credential, and integrations that still use `POST /login` can no longer access the API.

## Timeline

| When | What happens |
| - | - |
| Now | API credentials are available. `POST /login` still works. |
| By 31 January 2027 | Switch every integration to an API credential. |
| From 1 February 2027 | Only API credentials work. Integrations that still use `POST /login` can no longer access the API. |

Both methods work at the same time until 31 January 2027, so you can switch one integration at a time without downtime. You do not need to contact Quivo.

Switch early. An integration that signs in as a Connector user stops working as soon as that user turns on multi-factor authentication (MFA).

## What changes

| | Legacy login | API credential |
| - | - | - |
| Credentials | Connector username and password, plus a static API key | Client ID and client secret |
| Get a token | `POST ${BASE_URL}/login` | `POST ${BASE_URL}/v2/oauth2/token` |
| API paths | `${BASE_URL}/...` | `${BASE_URL}/v2/...` |
| Headers on API calls | `X-Api-Key: <YOUR_STATIC_API_KEY>` and `Authorization: <YOUR_SESSION_TOKEN>` | `Authorization: Bearer <YOUR_ACCESS_TOKEN>` |
| Token lifetime | 1 hour | 1 hour |

Everything else stays the same: request and response bodies, pagination, webhooks and the error codes of all other endpoints. What changes is the token request and its response, the path prefix and the headers.

> [!NOTE]
>
> All API examples in this guide use `${BASE_URL}` as a placeholder. Replace it with the correct base URL configured for the correct environment. For more information see [Environments page](https://api-docs.quivo.co/api-reference/environments.md).

## Migrate step by step

**1. Create an API credential**

An Account Admin creates the credential in The Connector under **Admin** › **API Credentials**. Copy the client ID and the client secret. The secret is shown only once. Store both in a secrets manager or another secure place. See [Create an API credential](https://api-docs.quivo.co/docs/quickstart/request-api-key.md).

Choose the role the integration needs: **User**, or **Account Admin** if the integration manages users, seller settings or shop settings.

Create one credential per integration. For tests, create a second credential in the sandbox. A credential works only in the environment where you created it.

**2. Replace the login call with a token request**

Remove the call to `POST /login`. Request an access token with your client ID and client secret instead.

> [tab] Before (legacy)
>
> ```bash theme={null}
> curl -X POST "${BASE_URL}/login" \
>   -H "Content-Type: application/json" \
>   -H "X-Api-Key: <YOUR_STATIC_API_KEY>" \
>   -d '{
>     "username": "<YOUR_USERNAME>",
>     "password": "<YOUR_PASSWORD>"
>   }'
> ```
>
> The response contains the session token in the `Token` field.

> [tab] After (API credential)
>
> ```bash theme={null}
> # CLIENT_ID and CLIENT_SECRET hold your credential, for example loaded from your secrets manager
> curl -X POST "${BASE_URL}/v2/oauth2/token" \
>   -u "${CLIENT_ID}:${CLIENT_SECRET}" \
>   -H "Content-Type: application/x-www-form-urlencoded" \
>   -d "grant_type=client_credentials"
> ```
>
> The response contains the access token in the `access_token` field. See [Obtain an access token](https://api-docs.quivo.co/api-reference/authentication.md#obtain-an-access-token) for Python and Node.js examples.

**3. Update every API call**

Add `/v2` to the path, send the access token as a Bearer token, and remove the `X-Api-Key` header.

> [tab] Before (legacy)
>
> ```bash theme={null}
> curl -X GET "${BASE_URL}/orders" \
>   -H "X-Api-Key: <YOUR_STATIC_API_KEY>" \
>   -H "Authorization: <YOUR_SESSION_TOKEN>"
> ```

> [tab] After (API credential)
>
> ```bash theme={null}
> curl -X GET "${BASE_URL}/v2/orders" \
>   -H "Authorization: Bearer <YOUR_ACCESS_TOKEN>"
> ```

**4. Update the token handling**

Both tokens are valid for one hour. Reuse the access token until it expires. When a call returns `401 Unauthorized`, request a new access token and retry the call once.

If the token request itself returns `401` with `invalid_client`, stop retrying and check the credential. See [Errors](https://api-docs.quivo.co/api-reference/authentication.md#errors).

**5. Test in the sandbox, then switch production**

Run your integration against `https://api-sandbox.quivo.co` with the sandbox credential. When it works, deploy it to production with the production credential.

## Migration checklist

Your integration is migrated when:

* It never calls `POST /login`.
* Every API call goes to `${BASE_URL}/v2/...`.
* No request sends an `X-Api-Key` header.
* Every API call sends `Authorization: Bearer <YOUR_ACCESS_TOKEN>`.

## Where to go next

> [card] [Authentication](https://api-docs.quivo.co/api-reference/authentication.md)
>
> Token requests, errors, token expiration and rate limits in detail.

> [card] [Legacy login (deprecated)](https://api-docs.quivo.co/api-reference/legacy-login.md)
>
> The old `POST /login` method, for reference until it is retired.

> [card] [Create an API credential](https://api-docs.quivo.co/docs/quickstart/request-api-key.md)
>
> Create, rotate and revoke the credential your integration uses.


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