Create account transfer

View as Markdown
Creates an account transfer to move funds between two treasury main accounts. **Request Headers** | Header | Type | Required | Description | |--------|------|----------|-------------| | `Idempotency-Key` | String | No | Unique key to prevent duplicate requests. If provided, the same key cannot be used for another account transfer. | **Request Body** | Field | Type | Required | Description | Validation Rules | |-------|------|----------|-------------|------------------| | `from_account_id` | UUID | Yes | Treasury account to send funds from. | Must be an onboarded main account belonging to your organization | | `to_account_id` | UUID | Yes | Treasury account to receive funds. | Must differ from `from_account_id` | | `amount_in_minor_units` | Integer | Yes | Amount in the smallest unit of the currency. For USD, cents (100 = $1.00). | Must be a positive whole number | | `rail` | String | Yes | Payment rail for the transfer. | Must be supported for the source account (see rail-options) | | `currency_code` | String | Yes | ISO 4217 currency code. | Must match the source account currency | | `auto_approve` | Boolean | Yes | When `true`, automatically approve and initiate the transfer after create. | Must be explicitly set; there is no default | | `metadata` | Object | No | Optional client key-value metadata. | String values only | **Response Body** | Field | Type | Description | |-------|------|-------------| | `id` | UUID | Unique identifier for the account transfer. | | `from_account_id` | UUID | Source treasury account ID. | | `to_account_id` | UUID | Destination treasury account ID. | | `amount_in_minor_units` | Integer | Transfer amount in minor units. | | `currency_code` | String | ISO 4217 currency code. | | `rail` | String | Payment rail used. | | `status` | String | Current status (`created`, `approved`, `initiated`, `settled`, `failed`). | | `client_metadata` | Object | Client-supplied metadata. | | `created_at` | DateTime | Timestamp when the transfer was created. | | `updated_at` | DateTime | Timestamp when the transfer was last updated. | **Idempotency Key** When you include an `Idempotency-Key` header: - **200 OK** — An account transfer with the same idempotency key already exists; the existing transfer is returned. - **201 Created** — A new account transfer was created. **Success Responses** | Status Code | Description | |-------------|-------------| | 200 | OK — existing account transfer returned for the provided idempotency key | | 201 | Created — account transfer created; with **`auto_approve`**, processing finished within this response for your request (**`status`** reflects the result) | | 202 | Accepted — account transfer created (and approved when **`auto_approve`** is true). **`status`** in the body may still change; poll list endpoints until the transfer reaches a terminal status | | 207 | Multi-Status — account transfer was created but **`auto_approve`** approval or initiation failed; the transfer is returned with a **`warning`** | **Error Responses** | Status Code | Error Code | Description | |-------------|------------|-------------| | 400 | VALIDATION_ERROR | Invalid request body, incompatible currency, or incompatible account combination | | 401 | AUTHENTICATION_ERROR | Authentication credentials are invalid or missing | | 403 | AUTHORIZATION_ERROR | You do not have permission to perform this action | | 404 | NOT_FOUND | One or both treasury accounts were not found | | 422 | Unprocessable Entity | Request body failed schema validation (e.g. missing required fields such as `auto_approve` or `currency_code`) | | 503 | ASYNC_INITIATION_UNAVAILABLE | With **`auto_approve`**, the transfer was created (and approved) but initiation hit a **transient error**. **Retry** after a short wait | **`auto_approve` behavior** When **`auto_approve=true`**, the API creates the account transfer and continues approval and initiation as far as this request allows. You may receive **201**, **202**, **207**, or **503** depending on outcome: - **201** / **202**: The account transfer id is always in the response. If you receive **202**, poll until **`status`** reaches a value you treat as final for your integration. - **207**: The transfer was created but approval or initiation failed; review the **`warning`** and current **`status`**. - **503**: Transient error while completing **`auto_approve`**—**retry** the create; use the response **`message`** (and **`error_code`**) for support and automation.

Authentication

x-api-keystring

RootPay API key sent in the x-api-key header. Keys are environment-scoped: live_* for production, test_* for sandbox.

Headers

Idempotency-Keystring or nullOptional
Unique key to prevent duplicate requests

Request

This endpoint expects an object.
from_account_idstringRequiredformat: "uuid"

Main operating account ID (Account.id) to send funds from.

to_account_idstringRequiredformat: "uuid"

Main operating account ID (Account.id) to send funds to.

amount_in_minor_unitsintegerRequired
Transfer amount in the source account currency minor units.
railenumRequired

Payment rail (must be in supported_rails)

currency_codeenumRequired

Currency code; must match the source account.

auto_approvebooleanRequired
When true, approve and initiate immediately after create.
metadatamap from strings to strings or nullOptional

Optional client key-value metadata stored as client_metadata.

Response

Existing account transfer returned for idempotency key