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

# Get Balances

> Retrieve live account balances for one or more accounts

<Info>
  The REST API is in **beta**. This endpoint's response shape may change.
</Info>

Returns live balances for the specified accounts. Balances are fetched directly from the banking provider on each request. No balance data is stored on Redbark servers.

## Request

```
GET /v1/balances
```

### Headers

| Header          | Required | Description           |
| --------------- | -------- | --------------------- |
| `Authorization` | Yes      | `Bearer YOUR_API_KEY` |

Trialing customers retain full API access, including brokerage endpoints, regardless of trial plan.

### Query parameters

| Parameter    | Type     | Required | Description                                                                                                                              |
| ------------ | -------- | -------- | ---------------------------------------------------------------------------------------------------------------------------------------- |
| `accountIds` | `string` | Yes      | Comma-separated list of account UUIDs. The list is deduplicated server-side, and the 100-account cap is checked **after** deduplication. |

<Info>
  Use the [List Accounts](/api-reference/accounts) endpoint to get account IDs. Mixing a brokerage `accountId` into the request fails the **entire** request, not per-account. To tell banking and brokerage accounts apart, join each account's `connectionId` to [List Connections](/api-reference/connections) and check the connection's `category`; route brokerage IDs to [`/v1/holdings`](/api-reference/holdings).
</Info>

## Response

Balances may be served from a short-lived server-side cache for up to 30 minutes; see [Caching](/api-reference/overview#caching) for purge and opt-out behaviour. Returned in the order the provider responds (iterates by provider, then by each provider's response ordering, so accounts on different providers are interleaved per-provider); not guaranteed to match the input order.

```json theme={null}
{
  "data": [
    {
      "accountId": "a1b2c3d4-e5f6-7890-a1b2-c3d4e5f67890",
      "currentBalance": "1234.56",
      "availableBalance": "1200.00",
      "currency": "AUD"
    },
    {
      "accountId": "b2c3d4e5-f6a7-8901-b2c3-d4e5f6a78901",
      "currentBalance": "8750.00",
      "availableBalance": "8750.00",
      "currency": "AUD"
    }
  ]
}
```

### Balance object

| Field              | Type             | Description                                                                                                                                                                                                                                        |
| ------------------ | ---------------- | -------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `accountId`        | `string`         | UUID of the account (matches IDs from the accounts endpoint)                                                                                                                                                                                       |
| `currentBalance`   | `string \| null` | Current balance as a decimal string. Negative if the account is in debit. `null` if the provider call failed for this account.                                                                                                                     |
| `availableBalance` | `string \| null` | Available balance (funds available for transfer). `null` if the provider call failed.                                                                                                                                                              |
| `currency`         | `string \| null` | ISO 4217 currency code (e.g. `"AUD"`, `"NZD"`). Falls back to the account's stored currency when the provider omits it, so it is usually present even when the balance fields are `null`. `null` only when no stored currency is available either. |

<Tip>
  Balance values are strings to preserve decimal precision. Parse them as decimals in your application. When the provider errors for a given account, `currentBalance` and `availableBalance` come back `null`; `currency` still resolves to the account's stored currency where we have one. Parsers must handle null balances.
</Tip>

## Error responses

Errors use the standard envelope `{ "error": { "message": string, "code"?: string, "details"?: string[] } }`. The optional `code` field is set for the structured cases below — clients should branch on `code` rather than parsing `message`.

| Status | `code`                        | When                                                                                                                                                                                                                                                                                                                               |
| ------ | ----------------------------- | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `400`  | `invalid_params`              | `accountIds` is present but empty after trimming (e.g. `accountIds=,,`). A missing or empty `accountIds` param instead fails schema validation and returns `Invalid request parameters` with no `code`.                                                                                                                            |
| `400`  | `too_many_accounts`           | More than 100 accounts requested (checked after deduplication)                                                                                                                                                                                                                                                                     |
| `400`  | `wrong_endpoint_for_category` | A requested account belongs to a non-banking connection. Brokerage message: `Balances are only available for banking accounts. Use /v1/holdings for brokerage accounts (<ids>).` Documents message: `Balances are not available for these accounts (<ids>). Documents connections expose transactions only, via /v1/transactions.` |
| `404`  | *(none)*                      | One or more accounts not found, or do not belong to you                                                                                                                                                                                                                                                                            |
| `501`  | *(none)*                      | `Balances are not yet available for provider: <name>` — returned when an account belongs to a provider whose `getBalances` is not yet implemented                                                                                                                                                                                  |
| `503`  | *(none)*                      | Banking provider temporarily unavailable. Retry later.                                                                                                                                                                                                                                                                             |

Example error body:

```json theme={null}
{
  "error": {
    "message": "Balances are only available for banking accounts. Use /v1/holdings for brokerage accounts (d4e5f6a7-b8c9-0123-d4e5-f6a7b8c90123).",
    "code": "wrong_endpoint_for_category"
  }
}
```

## Examples

### Basic request

```bash theme={null}
curl -H "Authorization: Bearer YOUR_API_KEY" \
  "https://api.redbark.com/v1/balances?accountIds=a1b2c3d4-e5f6-7890-a1b2-c3d4e5f67890,b2c3d4e5-f6a7-8901-b2c3-d4e5f6a78901"
```

### Python

```python theme={null}
import requests

API_KEY = "YOUR_API_KEY"

# Get account IDs first
accounts_resp = requests.get(
    "https://api.redbark.com/v1/accounts",
    headers={"Authorization": f"Bearer {API_KEY}"},
)
account_ids = [a["id"] for a in accounts_resp.json()["data"]]

# Fetch balances for all accounts
resp = requests.get(
    "https://api.redbark.com/v1/balances",
    headers={"Authorization": f"Bearer {API_KEY}"},
    params={"accountIds": ",".join(account_ids)},
)
balances = resp.json()["data"]

for b in balances:
    print(f"{b['accountId']}: {b['currency']} {b['currentBalance']} (available: {b['availableBalance']})")
```

### JavaScript

```javascript theme={null}
const API_KEY = "YOUR_API_KEY";
const BASE = "https://api.redbark.com";

// Get account IDs first
const accountsResp = await fetch(`${BASE}/v1/accounts`, {
  headers: { Authorization: `Bearer ${API_KEY}` },
});
const { data: accounts } = await accountsResp.json();
const accountIds = accounts.map((a) => a.id).join(",");

// Fetch balances
const resp = await fetch(`${BASE}/v1/balances?accountIds=${accountIds}`, {
  headers: { Authorization: `Bearer ${API_KEY}` },
});
const { data: balances } = await resp.json();

for (const b of balances) {
  console.log(`${b.accountId}: ${b.currency} ${b.currentBalance} (available: ${b.availableBalance})`);
}
```
