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

# API Overview

> Reviewed public API surfaces and control plane model

The Zentra API is organized around REST principles. Our API has predictable resource-oriented URLs, accepts JSON-encoded request bodies, returns JSON-encoded responses, and uses standard HTTP response codes, authentication, and verbs.

## Base URL

All API requests should be made to:

<CodeGroup>
  ```text Sandbox theme={null}
  https://sandbox.api.usezentra.com
  ```

  ```text Production theme={null}
  https://api.usezentra.com
  ```
</CodeGroup>

<Note>
  The reviewed gateway contract is rooted at `/api/v1/*`. When an older page in this workspace still shows a legacy `/v1/*` example, prefer the reviewed route manifest, the reviewed OpenAPI bundle, and the stronger route-specific pages until that leaf page is reconciled.
</Note>

## Control Plane Model

Zentra is documented as a reviewed public API control plane:

* reviewed money movement primitives: transfers, payments, and webhook delivery
* reviewed optional and tenant-gated rails: identity, virtual accounts, card issuing, and billpay
* internal primitives and controls: auth, fees, routing, and operator tooling
* reference accelerators: higher-level product flows you can build yourself on top of the primitives

<Warning>
  The reviewed public route manifest currently includes transfers, payments, identity, cards, virtual accounts, billpay, and webhooks. Draft, tenant-specific, or reference namespaces still include customers, wallets, analytics, plans, and subscriptions.
</Warning>

## Current Documentation Status

The API Reference pages in this workspace are not uniformly complete yet. Some endpoint pages still exist as explicit placeholders while the reviewed OpenAPI contract and the stronger endpoint pages continue to expand.

Today, the most trustworthy endpoint-level documentation is concentrated in:

* payments
  * charge
  * refund
  * verify
* transfers
  * overview
  * create
  * get
  * list
  * bulk
  * resolve-account
  * banks
* cards
  * overview
  * create
  * list
  * fund
  * balance
  * funding-history
  * auto-reload
  * jit-fund
  * security
  * lock
  * unlock
* virtual accounts
  * overview
  * create
  * list
  * get
  * close
* webhooks
  * overview
  * configure
  * verify-signature
  * events

The remaining placeholder backlog is concentrated in draft, tenant-specific, or reference-only namespaces and should not be read as proof of reviewed public support:

* customers
* wallets
* analytics
* plans
* subscriptions
* `payments/initialize`
* a small set of identity endpoint pages that are reviewed but still tenant-gated and not yet documented in full page detail

If a page is explicitly labeled placeholder, tenant-specific, or draft, treat it as backlog or compatibility guidance, not as the endpoint contract itself. When a page and the reviewed route contract disagree, prefer the reviewed public OpenAPI surface, the reviewed route manifest, and the stronger route-specific pages in this workspace.

This means the docs are useful as a source of truth for the reviewed surfaces above, but they are not yet complete enough to treat the entire API reference tree as fully implemented contract coverage.

## API Versioning

The Zentra API uses versioning in the URL path. The current version is `v1`.

When we make backwards-incompatible changes, we'll release a new version. Backwards-compatible changes don't require a new version:

* Adding new endpoints
* Adding new optional request parameters
* Adding new properties to responses
* Changing the order of properties in responses

## Request Format

All POST, PUT, and PATCH requests must include a `Content-Type: application/json` header and a JSON body.

```bash theme={null}
curl https://api.usezentra.com/api/v1/transfers \
  -H "Authorization: Bearer YOUR_SECRET_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "amount_minor": 10000,
    "destination_bank_code": "058",
    "destination_account_number": "0123456789",
    "reference": "TRF_123456"
  }'
```

## Response Format

All responses are returned in JSON format with the following structure:

### Success Response

```json theme={null}
{
  "success": true,
  "data": {
    "reference": "TRF_123456",
    "status": "processing",
    "amount_minor": 10000,
    "created_at": "2024-01-15T10:30:00Z"
  }
}
```

### Error Response

```json theme={null}
{
  "success": false,
  "error": {
    "code": "validation_error",
    "message": "Invalid email address",
    "field": "email",
    "status": 400
  }
}
```

## HTTP Status Codes

Zentra uses conventional HTTP response codes:

| Code    | Meaning               | Description                               |
| ------- | --------------------- | ----------------------------------------- |
| **2xx** | **Success**           | Request succeeded                         |
| `200`   | OK                    | Request successful                        |
| `201`   | Created               | Resource created successfully             |
| `204`   | No Content            | Request successful, no content to return  |
| **4xx** | **Client Error**      | Error in the request                      |
| `400`   | Bad Request           | Invalid request format or parameters      |
| `401`   | Unauthorized          | Invalid or missing API key                |
| `403`   | Forbidden             | API key doesn't have required permissions |
| `404`   | Not Found             | Resource not found                        |
| `422`   | Unprocessable Entity  | Validation errors                         |
| `429`   | Too Many Requests     | Rate limit exceeded                       |
| **5xx** | **Server Error**      | Error on Zentra's side                    |
| `500`   | Internal Server Error | Something went wrong                      |
| `503`   | Service Unavailable   | API temporarily offline                   |

## Idempotency

To prevent duplicate operations (especially for financial transactions), use idempotency keys.

Pass a unique `idempotency_key` in your request:

```bash theme={null}
curl https://api.usezentra.com/api/v1/transfers \
  -H "Authorization: Bearer YOUR_SECRET_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "amount_minor": 10000,
    "destination_account_number": "0123456789",
    "destination_bank_code": "058",
    "idempotency_key": "unique_key_123"
  }'
```

If you retry a request with the same idempotency key, you'll get the same response as the original request.

<Info>
  Idempotency keys are valid for 24 hours. After that, the same key can be reused.
</Info>

## Rate Limiting

API requests are subject to rate limits based on your plan:

| Plan       | Rate Limit            |
| ---------- | --------------------- |
| Sandbox    | 100 requests/minute   |
| Starter    | 1,000 requests/minute |
| Growth     | 5,000 requests/minute |
| Enterprise | Custom                |

Rate limit information is included in response headers:

```
X-RateLimit-Limit: 1000
X-RateLimit-Remaining: 999
X-RateLimit-Reset: 1640995200
```

See [Rate Limits](/api-reference/rate-limits) for details.

## Pagination

List endpoints return paginated results. Use `page` and `limit` parameters:

```bash theme={null}
curl "https://api.usezentra.com/api/v1/transfers?page=2&limit=50" \
  -H "Authorization: Bearer YOUR_SECRET_KEY"
```

Response includes pagination metadata:

```json theme={null}
{
  "success": true,
  "data": [...],
  "pagination": {
    "page": 2,
    "limit": 50,
    "total": 243,
    "pages": 5
  }
}
```

See [Pagination](/api-reference/pagination) for details.

## Filtering & Sorting

Many list endpoints support filtering and sorting:

```bash theme={null}
# Filter by status
GET /api/v1/transfers?status=completed

# Filter by date range
GET /api/v1/transfers?start_date=2024-01-01&end_date=2024-01-31

# Sort by created_at descending
GET /api/v1/transfers?sort=-created_at
```

## Timestamps

All timestamps are returned in ISO 8601 format (UTC):

```
2024-01-15T10:30:00Z
```

## Testing

Use our sandbox environment for testing:

* **Base URL**: `https://sandbox.api.usezentra.com`
* **API Keys**: Use keys starting with `sk_sandbox_`
* **Test Data**: See [Test Data](/resources/test-data) for test cards, BVNs, etc.

<Warning>
  Sandbox and production are completely separate environments. Data does not sync between them.
</Warning>

## API Resources

<CardGroup cols={2}>
  <Card title="Identity" icon="shield-check" href="/api-reference/identity/overview">
    Reviewed, tenant-gated verification rails and decisioning
  </Card>

  <Card title="Virtual Accounts" icon="building-columns" href="/api-reference/virtual-accounts/overview">
    Optional add-on for inbound collection rails
  </Card>

  <Card title="Transfers" icon="money-bill-transfer" href="/api-reference/transfers/overview">
    Primitive money movement and payout orchestration
  </Card>

  <Card title="Payments" icon="credit-card" href="/api-reference/payments/overview">
    Optional add-on for charges, refunds, and saved payment methods
  </Card>

  <Card title="Cards" icon="credit-card" href="/api-reference/cards/overview">
    Optional add-on for issuing and card controls
  </Card>

  <Card title="Webhooks" icon="webhook" href="/api-reference/webhooks/overview">
    Real-time event notifications
  </Card>
</CardGroup>

## Draft & Reference Namespaces

<CardGroup cols={2}>
  <Card title="Customers" icon="users" href="/api-reference/customers/overview">
    Draft customer overlays retained for compatibility
  </Card>

  <Card title="Wallets" icon="wallet" href="/api-reference/wallets/overview">
    Draft wallet overlays retained for compatibility
  </Card>

  <Card title="Analytics" icon="chart-line" href="/api-reference/analytics/overview">
    Tenant-specific telemetry and reporting overlays
  </Card>
</CardGroup>

## SDKs

Use our official SDKs for easier integration:

* [JavaScript/Node.js](/sdks/javascript)
* [Python](/sdks/python)
* [PHP](/sdks/php)

## Support

Need help? We're here for you:

* **Support routing**: [Support and escalation paths](/support/contact)
* **Status Page**: [status.usezentra.com](https://status.usezentra.com)

## Next Steps

<CardGroup cols={2}>
  <Card title="Authentication" icon="key" href="/authentication">
    Learn how to authenticate requests
  </Card>

  <Card title="Errors" icon="triangle-exclamation" href="/api-reference/errors">
    Understand error responses
  </Card>

  <Card title="Quickstart" icon="rocket" href="/quickstart">
    Make your first API call
  </Card>

  <Card title="Webhooks" icon="webhook" href="/api-reference/webhooks/overview">
    Set up event notifications
  </Card>
</CardGroup>
