Extract Banking Data in Brazil (API with Hosted Widget)
In this guide, we walk you through everything you need to extract banking data about your users from Brazil's Open Finance Network using our API. This includes:
- An overview of the data flow
- Setting up Belvo's Hosted Widget to connect your users.
- Getting your user's data based on webhook events sent by Belvo.
- Providing your users a way to manage their consents.
Prerequisites
Before you proceed with your integration, make sure that you have:
- Gone through our getting started guide
In the getting started guide, you'll create a Belvo account, generate some sandbox API keys, and set up a webhook URL.
For testing purposes and developing your integration, we highly recommend using the Sandbox environment along with the Mockbank institution. You can find example credentials to simulate different users for the Mockbank institution here.
Data flow overview
Belvo uses an asynchronous workflow to improve the extraction of data and your flow. As you can see from the diagram below, once your user has connected their account using the Hosted Widget and the link is created, Belvo loads all the data asynchronously and then notifies you using webhooks that the data is available for you to retrieve.
Setting up the Hosted Widget
We highly recommend using Belvo's hosted widget. It is designed to simplify your development and integration process, is compliant with Open Finance regulations, and is constantly monitored by a team of specialists to improve the user experience.
Our Hosted Widget can be embedded in your application as a webview and will guide your user through all the steps to grant their consent for you to access their data. This includes redirecting the user to their institution to provide consent and then back to your application.
You can view a simplified flow of what happens during the widget connection process in the diagram below:
Basically, whenever you want your user to connect their account from a financial institution in Brazil, you will need to:
1. Generate an access_token
for the Hosted Widget (OFDA) using the users CPF or CNPJ.
access_token
for the Hosted Widget (OFDA) using the users CPF or CNPJ.See our step-by-step walkthrough on how to generate access token in the recipe below.
Additionally, check out our Generating an access_token section of our Hosted Widget (OFDA) guide.
2. Start the widget inside a webview in your application for your user.
See our step-by-step walkthrough on how to start the hosted widget in the recipe below.
Additionally, check out ourStarting the widget section of our Hosted Widget (OFDA) guide.
3.Listen for the success event that will include the link id
.
id
.This step requires some knowledge of handling redirects and their query parameters. For details regarding the events we send (and their format), see the Handling callback events section of our Hosed Widget (OFDA) guide.
To aid your development, we've created guides on how to set up deep links and listen for events for the following platforms:
Wait for webhooks and retrieve data
As Belvo utilizes an asynchronous workflow, once the link is created we automatically retrieve the last 12 months of historical data for the user that just connected their account. We'll notify you via webhook events once the data is extracted and you can retrieve it. For more details, see the Getting data section.
Getting data
Regardless if you use single or recurrent links, once your user completes the widget flow successfully, Belvo asynchronously retrieves the last 12 months of owner, account, transaction, and bill data for the link (historical updates). Once we have extracted the data, we notify you using a webhook that the information is ready to be retrieved.
If you are using recurrent links, Belvo will retrieve the updated information for the link according to your refresh rate (recurrent updates). Just like historical updates, we notify you using a webhook that the new information is ready to be retrieved.
When generating consent and creating the link, Belvo already consumes one operational limit of Owners, Accounts, Transactions, and Bills (to retrieve the historical data for your user). However, Belvo has implemented certain internal mechanisms to optimize the data retrieval limits. For more information, please see our dedicated Open Finance Network Limits (Brazil) article.
Brazil's Open Finance Network sets monthly limits regarding how often you can retrieve data for a specific person or business. These operational limits are linked to a combination of:
- the user’s CPF or CNPJ
- the API data you want to get (Owner, Account, Transaction, or Bill)
- the Open Finance network certificate
Once the monthly operational limit of API calls is reached, no more information can be retrieved for the CPF/CNPJ until the start of the next calendar month. However, Belvo has implemented optimizations to maximize the amount of data you can retrieve for your users according to your data needs. For more information, please see our dedicated Open Finance Network Limits (Brazil) article.
Historical updates
Below you can see the flow of data for both single and recurrent links once a link is created:
Each time that you receive a webhook for a given resource (owners, accounts, transactions, or bills), you will need to make a GET call to that endpoint, using the link ID, to retrieve the information.
Get Owner information
Belvo will asynchronously retrieve the last 12 months owner data for your link and then send you a webhook once the information is ready to retrieve (see the webhook example below):
{
"webhook_id": "aadf41a1fc8e4f79a49f7f04027ac999",
"webhook_type": "OWNERS",
"process_type": "historical_update",
"webhook_code": "historical_update",
"link_id": "2f8ca7a1-c28f-46f2-bb41-21633099a280",
"request_id": "4363b08b-51eb-4350-9c74-5df5ac92a7f6",
"external_id": "your_external_id",
"data": {
"total_owners": 2 // Total number of owners
}
}
Once you receive the webhook, you just need to make the following GET Owners request to retrieve the data for the given link:
curl --request GET 'https://api.belvo.com/api/owners/?link={id}' \
-u [Secret Key ID]:[Secret Key PASSWORD]
{
"count": 1,
"next": null,
"previous": null,
"results": [
{
"id": "cf3acafc-8b89-4350-8350-3dc1a02c03c8",
"link": "3d54d0d0-7ba6-453e-88ed-9963f76677a2",
"created_at": "2024-05-23T11:02:48.229221Z",
"email": "[email protected]",
"emails": [
{
"email": "[email protected]",
"is_main": true
}
],
"gender": "MALE",
"address": "Rua Laguna 129, Porto Alegre, RS, 90820060, Brasil",
"addresses": [
{
"town": "Porto Alegre",
"state": "RS",
"address": "Rua Laguna 129",
"is_main": true,
"latitude": "-30.0953952",
"longitude": "-51.2279909",
"town_code": "4314902",
"postal_code": "90820060",
"country_code": "BRA",
"country_name": "Brasil",
"district_name": "Cavalhada",
"additional_info": "Casa Amarela"
}
],
"last_name": "Galvão",
"birth_date": "1989-03-23",
"filiations": [
{
"type": "MOTHER",
"civil_name": "Andreia Galvao",
"social_name": "NA"
}
],
"first_name": "Tatiana",
"document_id": {
"document_type": "CPF",
"document_number": "535.807.930-04"
},
"social_name": "",
"collected_at": "2024-05-23T11:04:50.891662Z",
"companies_id": [
"25349207000105"
],
"display_name": "Tatiana Galvão",
"phone_number": "+55 51325421328",
"nationalities": [
{
"info": "true",
"documents": [
{
"type": "SOCIAL SEC",
"number": "423929299",
"issue_date": "2020-05-30",
"additional_info": "",
"expiration_date": "2022-08-21",
"country_of_issuance": "Brasil"
}
]
}
],
"phone_numbers": [
{
"type": "LANDLINE",
"number": "325421328",
"is_main": true,
"area_code": "51",
"extension": "258",
"country_code": "55",
"additional_info": "Informações adicionais."
}
],
"marital_status": "SINGLE",
"second_last_name": "",
"financial_profile": {
"patrimony": {
"year": 2010,
"amount": "100000.04",
"currency": "BRL"
},
"company_id": "50685362000131",
"informed_income": {
"date": "2021-05-21",
"amount": "100000.04",
"currency": "BRL",
"frequency": "OTHERS"
},
"occupation_code": "OTHER",
"occupation_description": "01"
},
"is_local_resident": false,
"financial_relation": {
"products": [
{
"type": "SAVINGS_ACCOUNT",
"agency": "6272",
"number": "11188222",
"subtype": "INDIVIDUAL",
"check_digit": "4",
"clearing_code": "123"
},
{
"type": "CHECKING_ACCOUNT",
"agency": "6272",
"number": "94088392",
"subtype": "INDIVIDUAL",
"check_digit": "4",
"clearing_code": "123"
}
],
"start_date": "2020-05-21T12:00:00Z",
"procurators": [
{
"type": "ATTORNEY",
"civil_name": "NA",
"social_name": "NA",
"document_number": "76109277673"
}
],
"product_services": [
"CHECKING_ACCOUNT"
],
"product_services_additional_info": "Additional Information"
},
"additional_documents": [
{
"type": "DRIVERS_LICENSE",
"number": "58438287",
"issue_date": null,
"check_digit": "P",
"additional_info": "SSP/RS",
"expiration_date": "2025-05-21",
"country_of_issuance": null,
"type_additional_info": "NA"
},
{
"type": "PASSPORT",
"number": "34229643119827236458",
"issue_date": "2018-05-24",
"check_digit": null,
"additional_info": null,
"expiration_date": "2022-05-24",
"country_of_issuance": "CAN",
"type_additional_info": null
}
],
"internal_identification": "9455ce84-f978-480e-be11-435119568b5d",
"marital_status_additional_info": null
}
]
}
Parameter | Type | Required | Description | Example |
---|---|---|---|---|
id | string | true | The link_id you receive in your historical_update notification. | 2f8ca7a1-c28f-46f2-bb41-21633099a280 |
Get Account information
Belvo will asynchronously retrieve the last 12 months of account data for your link and then send you a webhook once the information is ready to retrieve (see the webhook example below):
{
"webhook_id": "aadf41a1fc8e4f79a49f7f04027ac999",
"webhook_type": "ACCOUNTS",
"process_type": "historical_update",
"webhook_code": "historical_update",
"link_id": "2f8ca7a1-c28f-46f2-bb41-21633099a280",
"request_id": "4363b08b-51eb-4350-9c74-5df5ac92a7f6",
"external_id": "your_external_id",
"data": {
"total_accounts": 5 // Total number of accounts found.
}
}
Once you receive the webhook, you just need to make the following GET Accounts request to retrieve the data for the given link:
curl --request GET 'https://api.belvo.com/api/accounts/?link={id}' \
-u [Secret Key ID]:[Secret Key PASSWORD]
Parameter | Type | Required | Description | Example |
---|---|---|---|---|
id | string | true | The link_id you receive in your historical_update notification. | 2f8ca7a1-c28f-46f2-bb41-21633099a280 |
Get Transaction information
Belvo will asynchronously retrieve the last 12 months of transaction data for your link and then send you a webhook once the information is ready to retrieve (see the webhook example below):
{
"webhook_id": "aadf41a1fc8e4f79a49f7f04027ac999",
"webhook_type": "TRANSACTIONS",
"process_type": "historical_update",
"webhook_code": "historical_update",
"link_id": "2f8ca7a1-c28f-46f2-bb41-21633099a280",
"request_id": "4363b08b-51eb-4350-9c74-5df5ac92a7f6",
"external_id": "your_external_id",
"data": {
"total_transactions": 19, // Total number of transactions found
"total_inflow_transactions": 10, // Total number of inflow transactions
"total_outflow_transactions": 9, // Total number of outflow transactions
"first_transaction_date": "2017-01-03", // First transaction date
"last_transaction_date": "2020-03-25" // Last transaction date
}
}
Once you receive the webhook, you just need to make the following GET Transactions request to retrieve the data for the given link:
curl --request GET 'https://api.belvo.com/api/transactions/?link={id}' \
-u [Secret Key ID]:[Secret Key PASSWORD]
Parameter | Type | Required | Description | Example |
---|---|---|---|---|
id | string | true | The link_id you receive in your historical_update notification. | 2f8ca7a1-c28f-46f2-bb41-21633099a280 |
Get Bill information
Belvo will asynchronously retrieve the last 12 months bill data for your link and then send you a webhook once the information is ready to retrieve (see the webhook example below):
{
"webhook_id": "aadf41a1fc8e4f79a49f7f04027ac999",
"webhook_type": "BILLS",
"process_type": "historical_update",
"webhook_code": "historical_update",
"link_id": "16f68516-bcbc-4cf7-b815-c500d4204e28",
"request_id": "4363b08b-51eb-4350-9c74-5df5ac92a7f6",
"external_id": "your_external_id",
"data": {
"total_bills": 2 // Total number of bills
}
}
Once you receive the webhook, you just need to make the following GET Bills request to retrieve the data for the given link:
curl --request GET 'https://api.belvo.com/api/bills/?link={id}' \
-u [Secret Key ID]:[Secret Key PASSWORD]
Parameter | Type | Required | Description | Example |
---|---|---|---|---|
id | string | true | The link_id you receive in your historical_update notification. | 2f8ca7a1-c28f-46f2-bb41-21633099a280 |
Recurrent updates
If you are using recurrent links, you will receive webhook events according to the frequency you established with Belvo (daily, weekly, monthly, and so on). Belvo sends the following webhook events for updates:
new_owners_available
You will receive anew_owners_available
webhook whenever we detect that there has been a change in account owners details. For more information, please see our dedicated Owners (Aggregation) webhook article.new_accounts_available
You will receive anew_accounts_available
webhook whenever we detect that there has been a change in the accounts that the link has. For more information, please see our dedicated Accounts (Aggregation) webhook article.new_transactions_available
You will receive anew_transactions_available
webhook whenever we detect that new transactions have occurred for any account the link has. For more information, please see our dedicated Transactions (Aggregation) webhook article.new_bills_available
You will receive anew_bills_available
webhook whenever a new credit card bill statements has been generated for a billing period. For more information, please see our dedicated Bills (Aggregation) webhook article.
As soon as you receive a webhook about newly updated information, you just need to make the same GET call as you did for the historical update to receive the updated information.
# Retrieve owner data
curl --request GET 'https://api.belvo.com/api/owners/?link={id}'
# Retrieve account data
curl --request GET 'https://api.belvo.com/api/accounts/?link={id}'
# Retrieve transaction data
curl --request GET 'https://api.belvo.com/api/transactions/?link={id}'
# Retrieve bill data
curl --request GET 'https://api.belvo.com/api/bills/?link={id}'
Other webhook events
Belvo also notifies you when there are changes to your link's consent. You may receive the following webhooks relating to consents:
openfinance_consent_expired
openfinance_consent_with_unrecoverable_resources
openfinance_consent_with_temporarily_unavailable_resources
For the openfinance_consent_expired
events, you can prompt your user to renew their consent using the My Belvo Portal. For more information, please see our dedicated Consent webhook article.
Adding a link to My Belvo Portal
According to Open Finance regulations, your users must have an easy-to-access way of managing their consents within your application or website.
Belvo has created the My Belvo Portal (MBP) that allows users to manage their consents in a simple and straightforward way, meeting all the requirements of the regulations.
In your application, you must include a clearly visible link to the MBP for your users to manage their consents.
The MBP can be set up in three different ways:
- Public MBP
On Belvo's website, we host a universal instance of the MBP that any user can use to manage their consents. This instance consolidates all the consents they have granted using Belvo's OFDA product. You simply need to redirect your user tohttps://meuportal.belvo.com/?mode=landing
, where they can input their details. Your user will be able to see all the consents they’ve granted using Belvo (including other applications using Belvo to extract data from Brazil's Open Finance Network). - Customized MBP
You can customize the MBP to display only the consents that your user has granted your application, making it easier for them to manage the consents. - Consent Renewal Mode
The MBP can also be used to renew an expired consent. Belvo will send you a webhook when one of your user's consent's has expired.
For details on how to set up the My Belvo Portal in your application, see our dedicated My Belvo Portal (OFDA) guide.
Additional resources
Integration checklist
We have created a dedicated checklist of all the things you should take into consideration when developing your OFDA integration. Check it out here: OFDA Integration Checklist.
Open Finance Network Errors
During the consent creation process, institutions in the Open Finance Network perform checks to ensure that the connection is stable and secure. If the institution determines that the connection is not stable or secure, it will redirect the user to a custom error page with the following content:
Ocorreu um error. Por favor, verifique o seu CPF or CNPJ para ter certeza de que está correto, feche o aplicativo e reinicie o processo para conectar sua conta.
And in the redirect URL, you will see a URL fragment with the following details:
api.belvo.com/api/consents/callback/#error_description=risk_analysis_denied...
This error can occur for the following reasons:
- Your user has an active VPN connection on their device. We recommend turning the VPN off an trying again.
- Your user is accessing their institution via their app on their mobile device, however, it is not the latest version of the app. Some institutions require that the app version is the latest possible version to allow for consent authorization. We recommend updating the institution app to the latest available version and trying again.
- [Itaú only] Your user is accessing their institution on their desktop computer, however, they do not have Itaú's Guardião 30 horas app installed on their computer. Itaú requires that users have this app installed on their desktop computer in order to perform the consent process.
Updated about 1 month ago