> This page is for Financial Rider Flow.

> For clean Markdown of any page, append .md to the page URL.
> For a complete documentation index, see https://infonite.dev/llms.txt.
> For AI client integration (Claude Code, Cursor, etc.), connect to the MCP server at https://infonite.dev/_mcp/server.

# Financial Rider Flow

**New to flows?** What every flow shares — the session you create, the widget your customer goes through, how the results reach you — is explained once, on its own page. This one is what Financial Rider adds to it.

What is a flow

**Financial Rider** is the flow that connects your customer's banks — with their consent — and gives you what those banks hold: accounts and their movements, cards, deposits, loans, investments and direct debits, read from each bank and delivered as one structured document. Like every *flow*, it works out of the box: there is nothing to build between the session you open and the data you receive.

Your customer does it in a secure experience hosted by INFONITE: they consent, pick their bank, sign in to it — with the bank's own login and whatever second factor it asks for — and, when your session allows it, connect a second and a third one. **Their banking credentials are typed into our widget and never reach your servers.**

**If the interface is yours, this is not the door.** A screen you build and control belongs to direct executions: the same bank engines, called server to server, with your UI in front and the credentials provided by you.

Direct Executions

---

## One-shot or recurring access

The first decision of an integration: whether you need your customer's banks **once**, or **for as long as you work with them**.

**One-shot.** Your customer connects their banks in the widget and you read the result — an onboarding, a loan application, a verification. Nothing else to build, and nothing stays behind once you delete the session.

The integration

**Recurring access.** Your customer connects once, in the widget; from then on your backend refreshes those banks on its own schedule, without them — bank reconciliation, money management, monitoring, a renewal.

Recurring Access

**Recurring access** is one setting at [Create Session](https://infonite.dev/flows/financial-rider/api-reference/financial-rider-api/sessions-management/flows-financial-rider-v-1-session-create): `tokenized_access`. Each bank your customer connects keeps its credentials tokenized, and every later read is a server-to-server call — [Initiate with a token](https://infonite.dev/direct-executions/api-reference/direct-executions-api/starting-executions/direct-executions-v-1-init-tokenized), on the direct executions API — with no widget and no customer in front. Not every bank's engine supports it — each one says so in `tokenized_access`, on [List your engines](https://infonite.dev/direct-executions/api-reference/direct-executions-api/engines/direct-executions-v-1-engines-list) —, and a session with recurring access offers only the banks that do. [Recurring Access](/flows/financial-rider/recurring-access) walks through both phases.

---

## Use cases

What a connected bank gives you, and what it is used for. Each one says whether it is a **one-shot** read, needs **recurring access**, or works **both** ways.

Bank reconciliation Recurring access

Your customer — a company — connects its business accounts once, and from then on your system reads every new movement, with its amounts, dates and references, and matches it against the invoices and payments it expects. The books close against what the bank actually booked, without anybody downloading a statement.

Account verification One-shot

Who holds an account and its IBAN, as the bank itself reports them — before paying out to it or setting up a direct debit on it.

Balance check One-shot

The available and booked balance of every account, at the moment your customer connects: enough for an instalment, a deposit, a purchase.

Transactions Both

Every movement of every account and card — categorised as salary, rent, utilities and the rest when data enrichment is enabled for your application.

Income verification One-shot

Salaries, pensions and other income, read from the movements that came in, to check what an applicant declares.

Affordability One-shot

Rent, mortgage, utilities and the other recurring expenses beside the balances, to decide what an applicant can take on.

Loans and liabilities Both

Personal loans and mortgages, with what is still owed and what each instalment costs, and what every credit card has drawn.

Recurring payments Both

SEPA direct debits: who charges your customer, how much and how often, with the receipt the bank keeps for each charge.

Savings and investments Both

Deposits, investment accounts, stocks, funds and pension plans: what your customer owns, next to what they owe.

Money management Recurring access

One view of the accounts, cards, savings and debts your customer holds across their banks, kept up to date for budgets, alerts and advice.

Customer profile One-shot

The name, document, addresses and contact details the bank holds for your customer, to prefill an onboarding or check it against what they typed.

Every one of them is a set of [features](/flows/financial-rider/features) you name when you create the session — `customer_information_read`, `accounts_read`, `cards_read`, `deposits_read`, `loans_read`, `investment_accounts_read`, `stocks_read`, `funds_read`, `pensions_read` and `direct_debits_read` —, and every record they return is described field by field in the [banking data models](/flows/financial-rider/data-models/banking/overview).

---

## Choosing the banks

* **Let your customer choose.** Send the `markets` and `entity_types` you work with — `corporate` for business banking — and the [features](/flows/financial-rider/features) you need. INFONITE resolves the banks your application may offer — the most used ones first — and your customer picks theirs. With `max_connections` (up to 3) they may connect more than one, and the session merges what every bank returned into one answer.
* **Name the bank.** When you already know where your customer banks, send its `engine_reference` instead of the filters. The session connects that one bank and your customer chooses nothing.

Either way, INFONITE decides which connection technology reaches each bank: you never maintain a list of engines. The fields, their limits and every refusal are in [Create Session](https://infonite.dev/flows/financial-rider/api-reference/financial-rider-api/sessions-management/flows-financial-rider-v-1-session-create).

---

## What your customer goes through

#### Consent

The consent screen is your application's, as agreed for it — never chosen per session. With `consent_level: basic` the widget shows what will be read and the documents your application wired: your customer reads to its end each one wired to be read, signs the ones that ask for a signature, and then consents. With `none` it skips straight to the banks — you collected the consent yourself and answer for it.

#### Pick a bank and sign in

The list puts the most used banks first — or yours, in your order (`priority_engines`) —, the first ones as rows of tiles (`engines_layout`) and up to three highlighted (`featured_engines`), for each session or as your application's setting. Your customer signs in to the one they choose, inside our widget, with whatever that bank asks for.

#### Connect another one, or finish

While the session allows more connections, they may add another bank. **Finish** delivers what is connected so far.

> **Note**
>
> **A bank that turned the credentials down is never taken away.** Your customer may pick it again: the widget warns them first, so they do not lock their own access by insisting, and they decide. Only failed attempts adding up to 20 end the session, on what it has: `COMPLETED` with the banks already connected, `FAILED` with none.

---

## Integration Lifecycle

#### Initialize Session

Call [Create Session](https://infonite.dev/flows/financial-rider/api-reference/financial-rider-api/sessions-management/flows-financial-rider-v-1-session-create) from your backend with the filters — or the named bank —, the [features](/guides/features) you need, and an optional encryption `aes_key` ([what it protects](/flows/financial-rider/authentication#the-session-key-aes_key)); add `tokenized_access` for recurring access. You get a `session_id` and the `widget_url`.

#### User Interaction

Open the `widget_url` for your customer — in a redirect, an iframe or a new tab. Where they land when they are done is yours to choose: [Redirects & Completion](/flows/financial-rider/redirects).

#### Receive Results

The [two ways the platform offers](/guides/webhooks#synchronous-and-asynchronous), and note that **neither of them is the redirect in the step above** — that one moves a browser, not data.

* **Asynchronous (Recommended)**: Listen for the [webhook event](/flows/financial-rider/webhooks) `financial-rider:ended`, a call from our servers to yours. If an `aes_key` was provided, the results travel in it, encrypted.
* **Synchronous (Optional Fallback)**: [Poll the session](https://infonite.dev/flows/financial-rider/api-reference/financial-rider-api/sessions-management/flows-financial-rider-v-1-session-status) and read [Get Session Results](https://infonite.dev/flows/financial-rider/api-reference/financial-rider-api/sessions-results/flows-financial-rider-v-1-session-results) once the session is closed.

#### Keep the access (recurring access only)

[Exchange a ticket](https://infonite.dev/direct-executions/api-reference/direct-executions-api/tokenization/direct-executions-v-1-token-exchange) once per connection the results list — on the Direct Executions API, from your backend — and store the token each exchange returns, keyed by its `token_id`: a bank your customer had already connected comes back as the same `token_id`, with `renewed: true`. From then on, [Initiate with a token](https://infonite.dev/direct-executions/api-reference/direct-executions-api/starting-executions/direct-executions-v-1-init-tokenized) reads that bank again from your backend. [Recurring Access](/flows/financial-rider/recurring-access).

#### Cleanup Session (Optional)

Purge the session and its results with [Delete Session](https://infonite.dev/flows/financial-rider/api-reference/financial-rider-api/sessions-management/flows-financial-rider-v-1-session-delete) as soon as you have processed them. If omitted, the session and its data are deleted automatically after a security retention timeout.

---

## Knowing when a session is finished

> **Warning**
>
> **A session is finished when `is_closed` is `true`. Nothing else means finished.**
>
> `is_closed` is in the session state from [Get Session State](https://infonite.dev/flows/financial-rider/api-reference/financial-rider-api/sessions-management/flows-financial-rider-v-1-session-state) and at the top of every `ended` webhook — however the session ended, with an `aes_key` or without one. While it is `false`, the results are **partial**: they hold what the banks connected so far have returned, and another bank may still be added.

A session ends in one of these ways — and only a session that connected at least one bank has results:

| What happens                                                                                                                             | It ends as                                            | Results |
| :--------------------------------------------------------------------------------------------------------------------------------------- | :---------------------------------------------------- | :------ |
| Your customer connected as many banks as the session allows                                                                              | `COMPLETED`                                           | Yes     |
| Your customer chose **Finish**, with at least one bank connected                                                                         | `COMPLETED`                                           | Yes     |
| 15 minutes pass after a connection without a new one, or the session is 10 minutes from its time limit, with at least one bank connected | `COMPLETED`                                           | Yes     |
| You cancel it with at least one bank connected                                                                                           | `COMPLETED`, with a `cancelled_with_products` warning | Yes     |
| You cancel it before anything was connected                                                                                              | `CLIENT_CANCELLED`                                    | No      |
| Your customer leaves the experience — the `ended` webhook says why                                                                       | `CUSTOMER_CANCELLED`                                  | No      |
| 20 attempts failed, with at least one bank connected                                                                                     | `COMPLETED`                                           | Yes     |
| 20 attempts failed, with nothing connected                                                                                               | `FAILED`                                              | No      |
| It reaches its time limit with nothing connected                                                                                         | `TIMED_OUT`                                           | No      |

When your customer leaves from the widget, the `ended` webhook carries `user_feedback`: `reason`, the option they chose — `took_too_long`, `entity_not_listed`, `missing_credentials`, `distrust`, `unclear_steps` or `other` —, and `feedback`, what they wrote, as they wrote it.

---

## What comes back

[Get Session Results](https://infonite.dev/flows/financial-rider/api-reference/financial-rider-api/sessions-results/flows-financial-rider-v-1-session-results) — and the `ended` webhook, when it carries data — returns:

* **`data`** — the financial position, in the same shape as the one [direct executions](/direct-executions/overview) return: one list per family you asked for and the customer profile. A family you did not ask for is absent.
* **`connections`** — each bank connection that finished, and the engine that ran it. A connection still running is never in `data`: what you read is only what finished. With recurring access, these are the ids each ticket exchange takes.
* **`consent`** — what your customer agreed to and the proof of it.
* **`messages`** — what the session found while it ran, below.

> **Note**
>
> **Documents travel beside the records.** A bank can deliver a document with a record — the receipt of a direct debit's last charge, under that debit's `attachments`. Each one downloads with [Download Attachments](https://infonite.dev/flows/financial-rider/api-reference/financial-rider-api/sessions-results/flows-attachment-download).

### When the banks do not agree on who your customer is

The customer profile is the one the **first** connected bank returned. Your customer chooses their own credentials for each bank, so two banks may describe different people — a shared account, a relative's login. When another connected bank disagrees, the session raises a **`crossed_identity` flag** at `["data", "customer", "profile"]`: the profile is still the first one, and the flag is what tells you the banks were not unanimous.

A flag never means something failed on our side: it is something about the person or the data that deserves a decision on yours, so route it to whatever already decides when a case needs a second look. `messages`, its four types and its fields are described in [Get Session Results](/flows/financial-rider/api-reference/financial-rider-api/sessions-results/flows-financial-rider-v-1-session-results).

---

## Sandbox and production

A session created with `sandbox: true` connects demo banks that answer with test data — **Demo Bank**, in Spain — and any application may open one, recurring access included. A production session never offers a demo bank.

Before production

**Financial Rider in production needs its capability**

Sandbox sessions work from the first minute, for every application. A production session needs the application in production and holding the **Financial Rider** capability — and **Tokenized access** for recurring access. Without them, Create Session answers `403` with `insufficient_capabilities@` and what is missing: `product:financial_rider`, `login:tokenized_access`, or both.

How to request it

---

## Payload Decryption (AES-256-GCM)

When an `aes_key` is provided at session creation, webhook payloads are encrypted. The `data` field contains a string prefixed with `aes::`:

```json
{
  "data": "aes::U2FsdGVkX19..."
}
```

1. **Remove Prefix:** Strip the `aes::` prefix from the string.
2. **Decode Base64:** Decode the remaining string to retrieve the raw bytes.
3. **Extract Parts:** the first 12 bytes are the IV, the last 16 the authentication tag, everything between them the ciphertext.
4. **Decrypt:** Decrypt using AES-256-GCM with your session key (`aes_key`), the extracted IV, and the Tag.

Without an `aes_key`, no webhook carries `data` at all: your customer's financial records never travel in the clear, and you read them from [Get Session Results](https://infonite.dev/flows/financial-rider/api-reference/financial-rider-api/sessions-results/flows-financial-rider-v-1-session-results).

**Webhooks.** The three events the session sends, the envelope every delivery shares, and what travels in it with a session key and without one.

Webhooks

**API Reference.** Every endpoint and every schema of the flow, in the order you call them, with a request explorer beside each one.

API Reference

---

**Interactive Decryption Sandbox.** Test your decryption against a real payload, or copy the implementation templates in Node.js, Python and Java.

Payload Encryption