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

# Bank accounts

> Create a stored ACH bank account payment method for a borrower.

Use this flow to store a borrower's checking or savings account for ACH payments. Send the request to `https://eapi.montereyfinancial.com`. Unlike cards, bank accounts don't go through the secure card host.

> [!NOTE]
>
> Availability is environment-specific. Until Monterey enables bank capture for your environment, this endpoint returns `503 bank_capture_unavailable`.

## Before you call

* An API key that can mint an access token
* The `payment_methods:write` scope
* A unique `account_id` for the borrower's servicing account

## Choose the borrower

| If you know\... | Send... | Result |
| - | - | - |
| The account's primary borrower | Omit `party_id` | Monterey uses the primary borrower automatically |
| A different active borrower on the account | `party_id` | Monterey creates the bank account for that borrower |

`party_id` must be visible to your API key and attached to the account. These rules match [card capture](https://docs.montereyfinancial.com/api-reference/card-capture.md#choose-the-borrower).

## Create the bank account

```bash theme={null}
set -euo pipefail

ACCESS_TOKEN=$(curl --fail-with-body -sS -X POST \
  -H "Content-Type: application/json" \
  -d '{
    "grant_type": "client_credentials",
    "client_id": "mfs_AbCd1234",
    "client_secret": "mk_your_key_here"
  }' \
  https://eapi.montereyfinancial.com/v1/oauth/token | jq -er .access_token)

curl --fail-with-body -sS -X POST \
  -H "Authorization: Bearer $ACCESS_TOKEN" \
  -H "Content-Type: application/json" \
  -d '{
    "account_id": "01J...",
    "routing_number": "121000358",
    "account_number": "1234567890",
    "account_type": "checking",
    "name_on_account": "Jane Smith",
    "bank_name": "Bank of America",
    "nickname": "Personal checking",
    "set_default": true
  }' \
  https://eapi.montereyfinancial.com/v1/payment-methods/bank
```

## Field rules

A request that breaks a rule returns `422`. The `detail` list names each failing field.

| Field | Type | Rule | Example |
| - | - | - | - |
| `account_id` | string | Required. | `"01J..."` |
| `party_id` | string | Optional. Omit to use the primary borrower. | `"01J..."` |
| `routing_number` | string | Required. Exactly 9 digits. Must pass the ABA checksum. | `"121000358"` |
| `account_number` | string | Required. 4 to 17 digits. No spaces or dashes. | `"1234567890"` |
| `account_type` | string | Required. `checking` or `savings`. | `"checking"` |
| `name_on_account` | string | Optional. Up to 255 characters. Used for account verification. | `"Jane Smith"` |
| `bank_name` | string | Optional. Up to 255 characters. | `"Bank of America"` |
| `nickname` | string | Optional. Up to 100 characters. | `"Personal checking"` |
| `set_default` | boolean | Optional. JSON `true` or `false`, not a string. Defaults to `false`. A borrower's first payment method always becomes the default. | `true` |

> [!WARNING]
>
> Send routing and account numbers as JSON strings. A number such as `021000021` loses its leading zero.

Unknown fields fail the request.

## Verification

Monterey verifies the account before saving it.

| Outcome | Response | `validation_status` |
| - | - | - |
| The account passes verification | `201` | `validated` |
| Verification is temporarily unavailable | `201` | `pending_giact`. The account is saved and verification runs later. |
| The account fails verification | `422 bank_account_declined` | Nothing is saved |

## Responses

| Status | `error_code` | Meaning | What to do |
| - | - | - | - |
| `201` | | Bank account payment method created | Store the returned `id`. Check `validation_status`. |
| `401` | | The access token is invalid or expired | Request a new access token |
| `403` | `insufficient_scope` | The token lacks `payment_methods:write` | Use an API key with the required scope |
| `404` | `account_not_found` | `account_id` is not visible to your API key | Check the account ID and your org scope |
| `409` | `duplicate_bank_account` | This bank account is already on file for the borrower | Use the existing payment method. `existing_payment_method_id` is included when your key can see it. |
| `422` | | A field failed a rule in [Field rules](#field-rules) | Fix the fields named in `detail` |
| `422` | `invalid_routing_number` | The routing number failed the ABA checksum | Check the routing number with the borrower |
| `422` | `bank_account_declined` | The account failed verification | Don't retry with the same numbers. Ask for another account. |
| `422` | `party_not_on_account` | `party_id` is not an active borrower on the account | Omit `party_id` or send a borrower on the account |
| `422` | `account_has_no_primary_borrower` | You omitted `party_id` and the account has no primary borrower | Send `party_id` |
| `429` | `rate_limited` | You exceeded the rate limit | Wait for `Retry-After`, then retry |
| `503` | `bank_capture_unavailable` | Bank capture is not enabled in this environment | Contact Monterey |

## Read next

> [card] [Card capture](https://docs.montereyfinancial.com/api-reference/card-capture.md)
>
> Store a card payment method through the secure proxy.

> [card] [Conventions](https://docs.montereyfinancial.com/api-reference/conventions.md)
>
> Read the shared rate-limit and error rules.

> [card] [Domain concepts](https://docs.montereyfinancial.com/api-reference/domain-concepts.md)
>
> See how parties, accounts, and payment methods fit together.


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