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

# Sub-account notification recipients: route rate-sheet and balance-alert emails per sub-account

> Set per-subaccount recipient lists for rate-sheet emails and account-balance alerts, with inheritance up the reseller chain and a safe fallback when nothing is configured.

# Sub-account notification recipients

Rate-sheet emails and account-balance alerts for a subaccount default to the recipients Orbit already resolves for your organization: your parent-org finance contacts, or the platform catch-all. Per-subaccount notification recipients let you route each of those two categories to a different inbox per child organization: a franchise-level ops inbox for one child, the CFO inbox for another.

This page covers **who receives** rate-sheet and balance-alert emails on behalf of a subaccount. The neighboring setting, the notification sender (`from_name` / `from_address`), controls **who the email appears to come from**. The two are independent:

| Setting | Controls | Guide |
| - | - | - |
| Notification sender | The `From` name and address on notification emails | [Custom notification-email identity](/guides/subaccounts-custom-notification-email) |
| Notification recipients | Which inboxes receive rate-sheet and balance-alert emails | This page |

For the sender configuration, see [Set up a custom notification-email identity for a sub-account](/guides/subaccounts-custom-notification-email); come back here for recipient routing.

## Why this exists

Until this release, rate-sheet emails and account-balance notifications were always addressed to the resolver's default recipient set: the parent organization's finance contact, or the per-organization platform catch-all. A reseller with three children therefore could not send one child's rate sheet to a franchise ops inbox and another's to a CFO inbox; everything landed in the same mailbox. You can now set each category separately per child organization, and children you leave unconfigured keep the previous behavior unchanged.

## The data model

A subaccount's recipient lists are stored in the organization's settings under `notification_recipients`:

```json theme={null}
{
  "rate_sheet_emails": "billing@acme.example, ops@acme.example",
  "balance_alert_emails": ["cfo@acme.example"]
}
```

* Both fields are optional. Each accepts a comma-separated string (`"billing@acme.example, ops@acme.example"`) or an array of addresses; the API normalizes either form into a clean address list.
* Clearing a field (send `null` or an empty list) restores the previous recipients. When nothing is configured, rate-sheet and balance-alert emails go exactly where they went before this feature.
* A malformed settings value is safe: Orbit treats an unparseable value as "not configured" instead of failing, so a bad settings entry can never drop an email. It routes to the previous recipients.
* Every entry must be a single clean address (`local@domain`, no stray commas, spaces, or line breaks). A list containing even one bad entry is rejected as a whole and falls back to the previous recipients. Orbit never silently drops the one address you thought you had configured.

These lists route rate-sheet emails and account-balance alerts only. Invites, security notifications, digests, and webhook failure alerts keep their own recipient rules.

## Where it shows in the dashboard

Open **Settings → Sub-accounts**, then open a sub-account. The notification recipients panel sits beside the existing notification-sender panel:

* The **sender** panel shows the white-label `From` name and address for this subaccount and whether the sending domain passed verification. It answers "who does the email come from?"
* The **recipients** panel holds the two address lists, `rate_sheet_emails` and `balance_alert_emails`. It answers "which inboxes receive these two billing email categories?"

Saving either panel takes effect on the next email of that category; nothing already queued is re-addressed.

## The API

Both endpoints use the same authentication as the other subaccount settings writes: owner or admin on the parent organization, or the subaccount's own admin when `{id}` is the caller's own organization.

### Read the configured lists

```bash theme={null}
curl -s https://api.orbit.devotel.io/api/v1/subaccounts/sub_abc123/notification-recipients \
  -H "X-API-Key: dv_live_sk_your_parent_key"
```

```json theme={null}
{
  "data": {
    "rate_sheet_emails": null,
    "balance_alert_emails": ["cfo@acme.example"]
  }
}
```

A `null` field means "not configured here": the subaccount inherits recipients from the parent chain (see [Resolution and precedence](#resolution-and-precedence)).

### Set the lists

```bash theme={null}
curl -s -X PUT https://api.orbit.devotel.io/api/v1/subaccounts/sub_abc123/notification-recipients \
  -H "X-API-Key: dv_live_sk_your_parent_key" \
  -H "Content-Type: application/json" \
  -d '{
    "rate_sheet_emails": "billing@acme.example, ops@acme.example",
    "balance_alert_emails": ["cfo@acme.example"]
  }'
```

The response echoes the normalized lists (comma-separated strings are stored as arrays). Sending `null` or `[]` for a field clears it. Sending an entry that is not a single clean address rejects the write for that field with a `422`, so a typo can never half-save a recipient list.

## Resolution and precedence

When Orbit prepares a rate-sheet email for a subaccount, it picks the recipients in this order:

1. The subaccount's own `rate_sheet_emails`, when set to at least one clean address.
2. The nearest ancestor organization up the reseller chain that has `rate_sheet_emails` set.
3. The platform catch-all recipient list.

`balance_alert_emails` resolves through the same chain for account-balance alerts. Resolution stops at the first tier that has a usable list; a cleared (null) field is the same as an absent one.

Consider a reseller with three children:

```
Parent org (you) — rate_sheet_emails: finance@reseller.example
 ├── Acme Retail       rate_sheet_emails: ops@acmeretail.example   → override wins
 ├── Delta Logistics   (not configured)                         → inherits finance@reseller.example
 └── West Clinic       (not configured)                         → inherits finance@reseller.example
```

Acme Retail's rate sheets go only to `ops@acmeretail.example`; Delta and West inherit your finance inbox. All three children's balance alerts inherit whatever your organization resolves, because none of them sets `balance_alert_emails`.

## Worked example

You want Acme Retail's balance alerts to reach two inboxes, and you want its rate sheets to stop overriding and return to your finance inbox.

```bash theme={null}
curl -s -X PUT https://api.orbit.devotel.io/api/v1/subaccounts/sub_abc123/notification-recipients \
  -H "X-API-Key: dv_live_sk_your_parent_key" \
  -H "Content-Type: application/json" \
  -d '{
    "balance_alert_emails": ["finance@acmeretail.example", "alerts@acmeretail.example"],
    "rate_sheet_emails": null
  }'
```

Reading the config back:

```bash theme={null}
curl -s https://api.orbit.devotel.io/api/v1/subaccounts/sub_abc123/notification-recipients \
  -H "X-API-Key: dv_live_sk_your_parent_key"
```

```json theme={null}
{
  "data": {
    "rate_sheet_emails": null,
    "balance_alert_emails": ["finance@acmeretail.example", "alerts@acmeretail.example"]
  }
}
```

From the next cycle on, Acme Retail's balance alerts are addressed to the two configured inboxes only. Its rate-sheet email goes to the previous recipients again: your organization's list when you have one set, otherwise the platform catch-all.

The email your recipients see keeps its usual sender identity; routing recipients never changes the `From` line. If your organization (or the subaccount) has a DNS-verified notification sender, the email arrives from that address; otherwise it arrives from the platform sender, exactly as described in [White-label subaccounts](/guides/subaccounts-reseller):

```text theme={null}
From: Acme Messaging <billing@acme.example>        <- your verified sender, or the platform sender
To:   finance@acmeretail.example, alerts@acmeretail.example
```

## Misconfiguration and troubleshooting

| Symptom | What happened | What to do |
| - | - | - |
| Emails still go to the old inboxes after saving | A field you set contains a bad entry, so the whole field fell back to the previous recipients | Read the config back with `GET`; fix or remove the malformed address and save again |
| A manually edited settings value is malformed | Orbit treats unparseable settings as "not configured" rather than failing, so sends continue to the previous recipients | Re-save the lists from the dashboard or the `PUT` endpoint to restore a clean value |
| Recipients receive, but the email shows the platform sender, not your brand | Recipient routing and sender verification are independent: an unverified `from_address` falls back to the parent's verified sender, then the platform sender | Verify the sending domain's DKIM/SPF as described in [White-label subaccounts](/guides/subaccounts-reseller) |
| A configured inbox reports it never got the email | The address was saved but bounces (full mailbox, retired domain) | A delivery failure surfaces as an alert in your notifications feed and in the send's record under **Insights → Activity**. Check the address and re-save |
| You expected signup invites or webhook alerts to follow these lists | These lists route only rate-sheet emails and balance alerts; other platform emails use their own recipient rules | Configure those notifications where their own settings live, e.g. [In-dashboard notifications](/guides/in-dashboard-notifications) |

## See also

* [White-label subaccounts](/guides/subaccounts-reseller) — provision, brand, and fund subaccounts; parent-level notification sender
* [Subaccounts console guide](/guides/subaccounts-console) — the dashboard surfaces for managing subaccounts
* [In-dashboard notifications](/guides/in-dashboard-notifications) — where platform alerts surface for your team
* [Pricing and rate resolution](/concepts/pricing-rate-resolution) — how subaccount pricing resolves, including rate sheets
* [Billing and wallet](/concepts/billing-and-wallet) — credits, balances, and what balance alerts watch
* [Automatic top-up](/guides/billing-auto-topup) — low-balance behavior and alerts


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