# Internal transfers

Internal transfers move value between virtual accounts inside the same omnibus structure. These transfers are off-chain ledger operations. They do not create blockchain transactions, do not require vault signing, and do not pay transaction fees.

Key behavior
Intra-omnibus transfers are fast because they update virtual account balances in the Accounting Service instead of moving funds on-chain.

## Transfer flow


```mermaid
sequenceDiagram
    actor Client
    participant Omnibus as Omnibus Service
    participant Accounting as Accounting Service

    Client->>Omnibus: Request internal transfer
    Omnibus->>Accounting: Get source virtual account balance
    Omnibus->>Omnibus: Validate source, destination, ledger, and lock state
    Omnibus->>Accounting: Record cross-account entry
    Accounting-->>Omnibus: Source debited, destination credited
    Omnibus-->>Client: Transfer response
```

## Validation

Omnibus validates that:

- The source and destination virtual accounts belong to the same omnibus structure.
- The source virtual account is not locked.
- The omnibus structure is not locked.
- The omnibus structure supports the asset and ledger.
- The source virtual account has enough available balance after subtracting local reservations.
- The transfer does not require cross-chain movement.


## No notarization

Internal transfers do not move blockchain assets and cannot directly lose on-chain funds. For that reason, clients do not submit them as custody intents, and custody policies do not notarize them.

This differs from a withdrawal or same-instance transfer that leaves the omnibus wallet. Custody policies still govern those on-chain operations.

## Governance considerations

Omnibus does not add a separate permission system for tenants or virtual accounts. Customer integrations decide which users can operate which tenants and virtual accounts.

If your organization needs approval workflows for intra-omnibus transfers, implement that governance outside the custody notary. Complete the approval workflow before the API call records the internal transfer.

## API payload

[POST `/v1/domains/{domainId}/omnibus/{omnibusId}/tenants/{tenantId}/internal-transfers`](/products/custody/v1.36/reference/api/openapi/internal-transfers/createinternaltransfer) accepts:

| Field | Required | Description |
|  --- | --- | --- |
| `destTenantId` | Yes | Destination virtual account ID. |
| `amount` | Yes | Positive integer string in the ticker's smallest unit. |
| `tickerId` | Yes | Ticker to transfer. |
| `ledgerId` | Yes | Ledger for the transfer. |


The response contains `operationId`, `transferId`, `status`, `sourceTenantId`, `destTenantId`, `amount`, `tickerId`, and `ledgerId`. The Accounting Service records both sides of the movement in one double-entry operation.

[GET `/v1/domains/{domainId}/omnibus/{omnibusId}/internal-transfers`](/products/custody/v1.36/reference/api/openapi/internal-transfers/getinternaltransfers) lists internal transfers for an omnibus structure.

The list endpoint supports:

| Query parameter | Description |
|  --- | --- |
| `page` | Page number. |
| `size` | Page size. |
| `tenantId` | Filter by source or destination virtual account. |
| `role` | Use with `tenantId` to restrict the tenant filter to `SOURCE` or `DEST`. |
| `status` | Filter by one or more transfer statuses: `PENDING`, `IN_PROGRESS`, `COMPLETED`, `FAILED`, `CANCELLED`, or `PENDING_VERIFICATION`. |
| `tickerId` | Filter by ticker. |
| `ledgerIds` | Filter by one or more ledgers. |
| `createdAfter` | Include transfers created after this timestamp. |
| `createdBefore` | Include transfers created before this timestamp. |
| `sort` | Sort expression. |


List responses contain `content` and `page`. Successful create requests return
`201 Created`.

## Operational notes

- Internal transfers do not require on-chain fees, so the host virtual account and Gas Station are excluded from this flow.
- Omnibus does not perform compliance screening because no blockchain transaction occurs.
- Use operation history and virtual account statements for audit and customer reporting.
- Use [Withdrawals](/products/custody/v1.36/accounts-and-assets/omnibus/withdrawals) when funds need to leave the omnibus wallet.