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

> ## Agent Instructions
> When building application code, use `@naturalpay/sdk` for TypeScript or `naturalpay` for Python.
> When operating Natural directly for a user, use the payments MCP at `https://mcp.natural.com`.
> When searching Natural documentation, use the docs MCP at `https://docs.natural.com/mcp`.
> Use the Natural CLI for terminal and CI automation.
> Use REST only for unsupported languages or when the user explicitly requests raw HTTP.
> Start integration development and testing in the sandbox. Do not use production unless the user explicitly requests it.
> For sandbox requests that require `customerPartyId`, list customers first. Reuse only the intended fixture; otherwise create a customer.
> REST and SDK amounts use integer minor units. Payments MCP amounts use decimal strings with a required currency code.

# Authentication

> API keys, agent keys, OAuth, and Bearer authentication

The Natural API uses Bearer authentication. Include your credential in the `Authorization` header of every request:

```bash theme={null}
curl https://api.natural.com/payments \
  -H "Authorization: Bearer sk_ntl_prod_abc123..."
```

The same credential authenticates the [SDKs](/guides/platform/sdks), the [CLI](/guides/platform/cli), and REST calls. AI hosts using [MCP](/guides/platform/mcp) authenticate with browser OAuth by default.

## Credential modes

Natural supports four credential modes. They differ in **who the request acts as** and **how agent identity is established**:

| Mode | Prefix / flow | Acts as |
| - | - | - |
| [API key](#api-keys) | `sk_ntl_…` | Your party |
| [Agent key](#agent-keys) | `ak_ntl_…` | One specific agent, verified |
| [User-scoped MCP OAuth](/guides/platform/mcp) | Browser OAuth consent | The authorizing user |
| [Agent-scoped MCP OAuth](/guides/platform/mcp) | Browser OAuth consent | Selected or new agent, verified |

Key rules:

* **Bound credentials carry verified agent identity.** With an agent key or agent-scoped OAuth grant, Natural resolves the agent from the credential itself. This is the only way to act as an agent: a party API key or user credential always acts as the party.
* **User-scoped money movement is valid.** Dashboard users and party API keys can move money without any agent attribution.
* **Agent-attributed money movement requires `X-Instance-ID`.** See [instance attribution](#instance-attribution-for-agent-money-movement).

## API keys

API keys are party-scoped credentials in the format `sk_ntl_{environment}_{secret}`:

| Prefix | Environment | Base URL |
| - | - | - |
| `sk_ntl_prod_` | Production | `https://api.natural.com` |
| `sk_ntl_sandbox_` | Sandbox | `https://api.sandbox.natural.com` |

Agent keys carry the same environment segment (`ak_ntl_prod_`, `ak_ntl_sandbox_`). See the [Sandbox](/api-reference/sandbox/overview).

An API key acts as your party and cannot act as an agent. To act as an agent, authenticate with an agent key or an agent-scoped OAuth grant.

### Creating API keys

Create API keys from the [dashboard](/guides/platform/dashboard) or via [`POST /api-keys`](/api-reference/api-keys/create-api-key). The key secret is shown once; store it immediately.

Each key can be scoped to a subset of permissions. Scope a key down to exactly what the integration needs, for example a read-only key or one limited to payments:

```json theme={null}
{
  "data": {
    "attributes": {
      "name": "Carrier Payment Agent",
      "scopes": ["agents.read", "payments.create", "payments.read"]
    }
  }
}
```

## Agent keys

Agent keys are credentials bound to exactly one of your [agents](/guides/concepts/agents), in the format `ak_ntl_{environment}_{secret}`. Requests authenticated with an agent key resolve as that agent, verified by the credential itself.

```bash theme={null}
# Acts as the bound agent
curl https://api.natural.com/parties/me \
  -H "Authorization: Bearer ak_ntl_prod_abc123..."
```

Agent keys work everywhere API keys work: SDKs, CLI, MCP fallback, and REST.

### Creating agent keys

Create agent keys from the dashboard or via [`POST /agent-keys`](/api-reference/agent-keys/create-agent-key), naming the existing agent it is bound to:

```json theme={null}
{
  "data": {
    "attributes": {},
    "relationships": {
      "agent": { "data": { "type": "agent", "id": "agt_019cd1798d637a4da75dce386343931d" } }
    }
  }
}
```

The create response includes the full secret in `attributes.agentKey` exactly once. List and revoke responses only include the non-secret `agentKeyPrefix`.

### Agent key permissions

Agent keys take no scopes. Natural applies one fixed policy to every agent credential: the bound agent can move money and read wallets and customers, and can never do any of the following.

* Creating agents
* Creating, listing, or revoking API keys or agent keys
* Team membership and account control
* Party profile/admin changes
* Wallet lifecycle/admin operations
* Vault funds

Agent-scoped MCP OAuth grants are clamped by the same policy, plus the ability to link external accounts.

### Rotation

[`POST /agent-keys/{keyId}/rotate`](/api-reference/agent-keys/rotate-agent-key) issues a replacement while the old key stays valid for a grace period you choose, up to 24 hours. Multiple active keys per agent are valid, so a running deployment never loses access mid-rotation.

## Instance attribution for agent money movement

Agent-attributed commands on payments, payment requests, payment intents, refunds, voice sessions, approvals, transfers, and Direct (including cancel) require an `X-Instance-ID` header, a caller-chosen identifier of up to 1024 characters for the agent run making the call. Without it, the request is rejected with `400 missing_instance_id`. Reads don't require it, and user-scoped requests (dashboard, user-scoped MCP, and plain API keys) are never agent-attributed.

In the SDKs, pass the instance ID when constructing the client; it is sent as `X-Instance-ID` on every request:

```python theme={null}
from naturalpay import Natural

client = Natural(instance_id="invoice-run-1234")
```

## MCP OAuth

[MCP](/guides/platform/mcp) signs AI hosts in with browser OAuth. On the consent screen, you pick an existing agent or create a new one. Tool calls then run as that agent, with the agent's permissions, and can't create agents or manage keys. If there is no agent for you to pick or create, the connection acts as you instead.

To switch agents, disconnect and reconnect. To act as your party, use an [API key](#api-keys).

## Security

* Store keys in a dedicated secret management system. Never commit them to source control. Add the `sk_ntl_` and `ak_ntl_` prefixes to your secret scanners.
* Rotate keys periodically. You can have multiple active keys to enable zero-downtime rotation.
* Revoke compromised keys immediately from the dashboard or with [`DELETE /api-keys/{keyId}`](/api-reference/api-keys/revoke-api-key). Revoke an agent key with [`DELETE /agent-keys/{keyId}`](/api-reference/agent-keys/revoke-agent-key).
* All requests require HTTPS.

## Related

* [Agents](/guides/concepts/agents): The agent model, instances, and audit trail
* [MCP](/guides/platform/mcp): Connect Claude, Cursor, and other AI hosts to Natural
* [API keys](/guides/concepts/api-keys): Your party's server-side credential and its scopes
* [Error Handling](/api-reference/errors/error-handling): Authentication error codes


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