Este guia mostra o caminho completo de uma conexão bancária na Malvo: o seu backend gera um connectToken, o frontend abre o Connect Widget, o usuário autoriza no banco e — quando o webhook item/created chega — você lê os dados com o X-API-KEY no servidor.
Há um único host de API: https://api.malvo.io. O widget é servido em https://malvo.io. O clientId, o clientSecret e o apiKey vivem apenas no backend; o navegador só recebe o connectToken (válido por 30 minutos).

Visão geral do fluxo

1

O backend gera um connectToken

Troque suas credenciais por um apiKey (POST /auth, válido por 2 horas) e o apiKey por um connectToken (POST /connect_token, válido por 30 minutos). Os dois passos rodam no servidor.
2

O frontend abre o Connect Widget

Com o connectToken, abra o widget (React com @malvo/react-connect ou via script global). O usuário escolhe a instituição e autoriza.
3

O usuário autoriza no banco

Em conectores Open Finance/Open Banking, o usuário é redirecionado para a autorização do banco e volta depois para o seu oauthRedirectUri. No Brasil, o conector normalmente pede CPF/CNPJ; no fluxo internacional, normalmente não há entrada antes do redirect, mas alguns ASPSPs podem anunciar uma seleção de método de autenticação.
4

O webhook item/created chega

Quando a conexão é concluída, a Malvo envia item/created para o seu webhookUrl. Esse é o sinal autoritativo de que o Item existe.
5

Você lê os dados no servidor

Com o itemId, leia GET /items/{id} e GET /accounts?itemId=... usando o X-API-KEY.
Os webhooks são a fonte da verdade. O callback onSuccess do widget é best-effort — o usuário pode fechar a aba antes de ele disparar. Nunca dispare lógica de negócio crítica no onSuccess; aja sobre item/created / item/updated.

1. Gere o connectToken no backend

Exponha um endpoint autenticado no seu backend (ex.: POST /api/malvo/connect-token) que devolve um accessToken novo a cada chamada. Ele faz a cadeia POST /authapiKeyPOST /connect_tokenaccessToken.
Node (fetch)
Faça cache do apiKey (renove antes de 1h50). Em um 403 no /connect_token, refaça o POST /auth e tente de novo — nesse endpoint, falha de autenticação aparece como 403, não 401. Gere um connectToken novo a cada vez que o usuário abrir o widget.
O clientUserId correlaciona os webhooks de volta ao seu usuário sem consulta ao banco de dados — ele é ecoado em cada payload de webhook.

2. Abra o Connect Widget no frontend

Passe o accessToken ao frontend e abra o widget. Você pode usar o componente React ou o script global.
O componente monta o widget assim que é renderizado; desmontar fecha o widget.
Se o onError retornar TOKEN_EXPIRED ou UNAUTHORIZED, gere um novo connectToken (POST /connect_token) e reabra o widget. Os demais códigos de erro de Item são tratados no fluxo de atualização (veja Tratar MFA).

3. O caminho regulado (dados do conector → redirect)

Em conectores regulados, o usuário não digita senha na sua aplicação. No Brasil, informa CPF ou CNPJ conforme connector.credentials; no fluxo internacional, não há senha ou token bancário antes do redirect. Alguns ASPSPs podem declarar o select authMethod; nesse caso, envie apenas um value anunciado em connector.credentials[].options. Depois de autorizar, a Malvo conclui o callback do provedor e devolve o usuário ao oauthRedirectUri configurado no connect_token.
connect_token com oauthRedirectUri
Os campos brasileiros de CPF/CNPJ são exibidos a partir de connector.credentials; o widget não aceita pré-preenchimento de documento. No fluxo internacional, selecione o catálogo por countries, connectorIds e connectorTypes. Quando necessário, o próprio widget renderiza authMethod; as credenciais bancárias são coletadas depois pela interface de autorização:
O oauthRedirectUri deve ser HTTPS ou um deep link (ex.: myapp://oauth/callback). URLs http:// e localhost são rejeitadas. O link de login do Open Finance é de uso único — entregue-o por navegador in-app ou copiar/colar, nunca por apps de mensagem que pré-carregam links.
A cobertura internacional é dinâmica. A Malvo pode ser configurada para 31 países, mas publica somente os ASPSPs AIS ativos para a configuração contratada. Liste GET /connectors em runtime; não hardcode bancos ou IDs.

4. Receba o webhook item/created

Quando a conexão termina, a Malvo envia item/created para o seu webhookUrl. Responda 2XX em até 5 segundos e processe de forma assíncrona.
Webhook item/created
Handler do webhook (Node)
O eventId é a chave de idempotência: persista-o e trate entregas repetidas como no-op. No Brasil, a coleta inicial busca até 365 dias; no fluxo internacional ela usa a maior janela que o ASPSP disponibiliza. Ao concluir, chega item/updated.

5. Leia os dados no servidor

Com o itemId, leia o Item e suas contas usando o X-API-KEY (sempre server-side — o connectToken recebe 403 nessas rotas).
A resposta de GET /accounts traz bankData (contas) ou creditData (cartões) em cada conta. Para ler as transações de cada conta, use accountId em /v2/transactions.

Próximos passos

Sincronizar transações

Pagine /v2/transactions por cursor e mantenha as transações em dia via webhooks.

Tratar MFA

Resolva WAITING_USER_INPUT enviando o token ou abrindo o widget em update mode.

Connect Widget

Todas as opções, callbacks e o fluxo OAuth do Open Finance.

Webhooks

Os payloads exatos de cada evento do ciclo de vida do Item.