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

# Errors

> The error format, every error code the Partner API returns, and the rate limit.

## Error format

Errors return an HTTP status and a JSON body with a machine-readable `code` and a human-readable `message`:

```json theme={null}
{
  "code": "CUSTOMER_NOT_FOUND",
  "message": "No customer found for this externalUserId"
}
```

Branch on `code`, not `message`: messages can be reworded, codes are stable.

Some errors add a `fields` array naming the fields at fault:

```json theme={null}
{
  "code": "CUSTOMER_IDENTITY_REQUIRED",
  "message": "Your identityPolicy is SHARED: firstName, lastName, email and phoneNumber are required",
  "fields": ["email", "phoneNumber"]
}
```

Validation errors (a malformed or unknown field) use the code `BAD_REQUEST`, with `message` describing the first problem found:

```json theme={null}
{
  "code": "BAD_REQUEST",
  "message": "verifiedOn must be a date in YYYY-MM-DD format"
}
```

## Error codes

| Status | Code | Meaning | What to do |
| - | - | - | - |
| `400` | `BAD_REQUEST` | A field is missing, malformed or not allowed, or an uploaded file is the wrong type or too large. | Fix the request using `message`. |
| `400` | `CUSTOMER_IDENTITY_REQUIRED` | `SHARED` account: `firstName`, `lastName`, `email` or `phoneNumber` is missing on create. | Send the fields in `fields`. |
| `400` | `CUSTOMER_PII_NOT_ACCEPTED` | `REFERENCED` account: personal data or a document was sent. | Remove the fields in `fields`; send only `externalUserId` and `kycVerification`. |
| `400` | `IDEMPOTENCY_KEY_REQUIRED` | `invest`: no `Idempotency-Key` header, or one over 255 characters. | Send a key you generated for this investment. See [Idempotency-Key](https://docs.ndovu.co/investing.md#idempotency-key). |
| `400` | `INVALID_CUSTOMER_CURSOR` | Listing customers: `cursor` isn't one of your customers. | Pass the `nextCursor` from the previous page unchanged. |
| `400` | `UNSUPPORTED_DOCUMENT_TYPE` | The document type isn't one you can upload. | Use a `shortName` from [document types](https://docs.ndovu.co/uploading-documents.md#list-document-types). |
| `400` | `DOCUMENT_SIDE_REQUIRED` | The document type has sides and none was given. | Add `?side=` with one of `requiredSides`. |
| `400` | | `invest`: the amount is below the plan's minimum for the currency, or the plan has no minimum for it. `message` gives the minimum. | Invest at least the minimum, in a currency the plan accepts. See [minimums](https://docs.ndovu.co/investing.md#minimums). |
| `400` | `MAXIMUM_TRANSFER_LIMIT_EXCEEDED` | `invest`: the amount is over the channel's limit for one payment. | Invest less, or split it. |
| `400` | `DEPOSIT_WITH_PENDING_WITHDRAW_TRANSACTION` | `invest`: the customer has a withdrawal pending on the plan. | Wait for the withdrawal to finish. |
| `400` | `INVALID_DOCUMENT_SIDE` | The side isn't valid for the document type. | Use one of `requiredSides`, or no side for a single-sided type. |
| `401` | `UNAUTHORIZED` | Authentication: missing or malformed Basic header. | Send `Authorization: Basic base64(clientId:clientSecret)`. See [Authentication](https://docs.ndovu.co/authentication.md). |
| `401` | | Authentication: wrong client secret. The body is `{"message": "Unauthorized"}`, with no `code`. | Check your client secret. |
| `401` | `INVALID_PARTNER_TOKEN` | Missing, expired or invalid access token, or a token that isn't a partner token. | Get a new token and retry. |
| `403` | `FORBIDDEN` | The `{shortName}` in the URL isn't yours. | Use your own `shortName`. |
| `403` | `PARTNER_REFERENCE_CODE_MISSING` | `invest`: your account has no payment reference code yet. | Contact us to finish setting up your account. |
| `403` | `FUNDING_METHOD_NOT_ENABLED` | `invest`: the channel isn't enabled for your account. | Use an enabled channel. See [funding channels](https://docs.ndovu.co/configuration.md#funding-channels). |
| `403` | `PARTNER_DISABLED` | Your account is disabled: reads work, writes are refused. | Contact us. See [status](https://docs.ndovu.co/configuration.md#status). |
| `404` | `PARTNER_NOT_FOUND` | Authentication: the client ID doesn't exist. | Check your client ID. |
| `404` | `CUSTOMER_NOT_FOUND` | You have no customer with this `externalUserId`. | Check the ID, or create the customer. |
| `404` | `PLAN_NOT_FOUND` | `invest`: the plan isn't one of your products. | Use a plan `id` from [Getting Products](https://docs.ndovu.co/getting-products.md). |
| `404` | `PAYMENT_NOT_FOUND` | No payment with this reference for this customer. | Check the reference. |
| `404` | `TRANSACTION_IS_NOT_FOUND` | No transaction with this ID for this customer. | Check the ID. |
| `409` | `IDEMPOTENCY_KEY_REUSED` | `invest`: this key was already used for a different investment. | Use a new key for a new investment. |
| `409` | `CUSTOMER_EXTERNAL_ID_CONFLICT` | Create was resent for an existing `externalUserId` with different details. | Use update to change details. |
| `409` | `CUSTOMER_EMAIL_OR_PHONE_IN_USE` | Another of your customers has this email or phone number. | Check for a duplicate customer on your side. |
| `409` | `CUSTOMER_IDENTITY_IN_USE` | Another of your customers has this ID number and issuing country. | Check for a duplicate customer on your side. |
| `422` | `PLAN_NOT_INVESTABLE` | `invest`: the plan isn't accepting new money. `message` says why. | Choose another plan, or try later. |
| `429` | | Rate limit exceeded. | Back off and retry. See below. |
| `500` | `INTERNAL_SERVER_ERROR` | Something went wrong on our side. | Retry with backoff. Customer create is [safe to retry](https://docs.ndovu.co/onboarding-customers.md#retrying-safely), and so is `invest` with the same `Idempotency-Key` (see [Retrying](https://docs.ndovu.co/investing.md#retrying)). If it persists, contact us. |

## Rate limits

Each partner account can make **300 requests per minute** to the customer endpoints. The limit is per account, not per IP address, so other partners never use up your budget. Over the limit, requests return `429 Too Many Requests` until the minute rolls over.

Your current limits are in your [configuration](https://docs.ndovu.co/configuration.md) under `limits`.

## Retrying

* On `401 INVALID_PARTNER_TOKEN`, get a new token and retry once.
* On `429` and `5xx`, retry with exponential backoff. For `invest`, resend with the same `Idempotency-Key`.
* Don't retry other `4xx` errors unchanged: they fail the same way again.


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