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

# Authentication

> Authenticate every request with your Kalixo API key.

The Kalixo API authenticates requests with an **API key** sent in the `x-api-key` header.
Each key is scoped to a single partner account. Your egress IP must also be whitelisted
before you can reach the API — use `GET /ping` to confirm connectivity once both are in place.

```bash theme={"dark"}
curl -X GET "https://api.kalixo.io/v2/wallet" \
  -H "x-api-key: $KALIXO_API_KEY"
```

<ParamField header="x-api-key" type="string" required>
  Your secret API key. Sent on every request.
</ParamField>

## Sandbox vs production

You receive two keys during onboarding. Sandbox runs against test data; production is live.

<Info>
  **Pre-release:** Base URLs below are placeholders during the pre-release period. Your
  account manager will confirm the final endpoints when your keys are issued.
</Info>

| Environment | Base URL                       | Key prefix   |
| ----------- | ------------------------------ | ------------ |
| Sandbox     | `https://sandbox.kalixo.io/v2` | `kal_test_…` |
| Production  | `https://api.kalixo.io/v2`     | `kal_live_…` |

## Keeping your key safe

<Warning>
  Treat your API key like a password. Never commit it to source control, embed it in
  client-side code, or share it in screenshots. Store it in an environment variable or secret manager.
</Warning>

<CardGroup cols={2}>
  <Card title="Rotate if leaked" icon="rotate">
    API keys are issued during onboarding. There is no self-serve rotation in the API today -
    contact [integrations@kalixo.io](mailto:integrations@kalixo.io) or your account manager
    to rotate a key. The old key is revoked once a new one is issued.
  </Card>

  <Card title="Server-side only" icon="server">
    Call the API from your backend, never from a browser or mobile app.
  </Card>
</CardGroup>

## Errors

A missing or invalid key returns `401 Unauthorized`:

**Header omitted**

```json theme={"dark"}
{
  "statusCode": 401,
  "error": "Unauthorized",
  "message": "Missing API key"
}
```

**Wrong or revoked key**

```json theme={"dark"}
{
  "statusCode": 401,
  "error": "Unauthorized",
  "message": "Invalid API key"
}
```

See [Errors](/concepts/errors) for the full error catalogue.
