- criar uma cobrança vinculada ao objeto do seu sistema;
- exibir o QR Code e o copia-e-cola de um PIX;
- concluir a operação de negócio somente quando o pagamento for confirmado;
- tratar corretamente tentativas que falham ou são canceladas;
- lidar com retries, eventos duplicados e eventos fora de ordem;
- receber eventos de organizações conectadas quando a integração for de plataforma.
A integração server-to-server usa a API REST. Você não precisa de um SDK da
Chargefy: os exemplos abaixo usam HTTP diretamente. Mantenha a API key apenas
no seu backend.
O desenho da integração
Opayment_intent representa uma cobrança: uma compra, uma invoice ou um ciclo
que precisa ser pago. Cada tentativa concreta dentro dela é registrada como
uma charge. O objeto de negócio continua pertencendo ao seu sistema; guarde
nele o ID do Payment Intent que representa aquela cobrança.
Separe os estados do seu objeto de negócio dos estados do pagamento:
Antes de começar
Você precisa de:- uma API key do ambiente correto;
- um registro no seu banco para relacionar a cobrança ao seu objeto de negócio;
- uma URL HTTPS para receber webhooks assinados;
- uma restrição de unicidade para os IDs
evt_*já processados.
1. Crie e confirme o PIX
Para obter o QR Code em uma única chamada, envieconfirm: true e permita
somente pix.
Use uma chave de idempotência estável para criar a cobrança. Se sua chamada
sofrer timeout, repita a mesma requisição com a mesma chave em vez de criar
outro intent.
pending, e next_action contém os dados que o frontend deve apresentar.
- grave
pi_yEiGAw9jN95nBBL8empayment_intent_id; - mantenha a operação local em
awaiting_payment; - grave
next_action.pix_display_qr_code.expires_atempix_code_expires_at; - envie ao frontend apenas os campos necessários de
next_action; - aguarde o webhook para concluir a operação ou encerrar a tentativa.
Se você opera uma plataforma
Use a API key da plataforma e envie o headerOrganization com a organização
conectada que receberá o pagamento:
2. Exiba o PIX
Leianext_action.type. Para PIX, o valor é pix_display_qr_code.
O frontend pode mostrar uma contagem regressiva, mas não deve alterar o estado
financeiro. Quando a contagem terminar, consulte o Payment Intent no backend ou
aguarde
payment.intent.canceled.
expires_at pertence ao código PIX dentro de next_action; o
payment_intent não tem um expires_at top-level. O prazo comercial para
concluir o pagamento (payment_expires_at) também é seu e pode ser diferente
da validade do código de pagamento.Eventos da confirmação e da expiração
Quando a confirmação muda o intent derequires_confirmation para pending,
a Chargefy emite payment.intent.updated. Use o objeto completo do evento para
sincronizar status, latest_charge, next_action e pix_code_expires_at.
Se o PIX vencer sem pagamento, a expiração encerra a tentativa — não o intent:
O intent aceita um novo código via
/regenerate_pix. Não espere
recuperar expires_at no payload da expiração: persista-o a partir da resposta
de confirmação ou do payment.intent.updated que trouxe o código. A sequência
acima é lógica; as requisições de webhook ainda podem chegar fora de ordem ou
ser reentregues.
3. Cobre um cartão salvo
Para cartão, informe umpayment_method salvo do customer. Com confirm: true,
a cobrança costuma ser resolvida na mesma chamada.
Se ainda não existe um método salvo, use um Setup Intent
e a tokenização segura do cartão antes de criar a cobrança.
4. Cadastre os webhooks necessários
Os tipos devem ser cadastrados individualmente. Não existe wildcard parapayment.intent.*.
Para manter uma visão completa do ciclo da cobrança, inscreva:
secret whsec_... aparece somente na resposta de criação. Guarde-o em um
gerenciador de secrets.
Organização ou plataforma
events_from: "platform" não inclui os eventos próprios da organização da
plataforma. Se você precisa dos dois fluxos, crie dois endpoints. Eles podem
usar a mesma URL, mas terão secrets independentes.
5. Verifique a assinatura
A implementação oficial segue Standard Webhooks. Cada entrega inclui:webhook-id;webhook-timestamp;webhook-signature;- um secret no formato
whsec_....
6. Processe os eventos sem duplicar efeitos
Cadadata.object contém o objeto payment_intent público completo no estado
registrado pelo evento. data.previous_attributes, quando presente, contém
somente os valores anteriores dos campos alterados.
Um handler seguro segue esta ordem:
Duplicação e ordem
- A entrega é at least once: o mesmo
event.idpode chegar novamente. - Eventos diferentes podem chegar fora de ordem.
- Não compare apenas a ordem em que as requisições chegaram.
- Não deixe um evento antigo rebaixar uma operação que já está
completed. data.objecté o snapshot completo do momento do evento, não uma garantia de que continua atual quando a entrega chega.- Antes de aplicar falha ou cancelamento, consulte o Payment Intent pelo ID e
preserve
succeeded.
7. Consulte o pagamento ao reabrir a tela
O webhook mantém o backend sincronizado. OGET é útil quando o comprador
reabre a tela de pagamento, atualiza a página ou volta depois de um período
offline.
Polling contínuo não é necessário. Se você optar por polling apenas para
atualizar a tela do comprador, trate-o como conveniência de UX; o efeito de
negócio continua sendo processado no backend.
8. Cancele a tentativa quando necessário
Você pode cancelar um intent que ainda não está emsucceeded ou canceled:
A Chargefy também escreve motivos por conta própria —
automatic, expired,
failed_invoice e void_invoice. Você recebe esses valores na resposta e nos
webhooks, mas não pode enviá-los: a requisição responde 400.
Se a tentativa nasceu de uma sessão de checkout, o cancelamento não vai por
aqui. A sessão é a dona do ciclo de vida do intent, então use
POST /v1/checkout-sessions/{id}/expire —
o intent é cancelado junto, com expired. O cancelamento direto responde
409, exceto em requires_capture.Você não precisa cruzar dados para saber o que aconteceu:
expired já diz que
um prazo acabou. E abandoned nunca chega da Chargefy — se você recebeu esse
motivo, foi porque você mesmo o enviou.payment.intent.canceled. Faça a atualização local de maneira idempotente para
que a resposta e o webhook não produzam o mesmo efeito duas vezes.
9. Permita outra tentativa com segurança
Use uma destas estratégias:
Cada novo fluxo terminal deve ter um identificador próprio no seu sistema. Um
padrão simples é
payment-order-8f4c2a, payment-order-8f4c2a-retry-2 e assim por diante.
Dentro do mesmo intent, latest_charge e os eventos charge.* identificam as
tentativas concretas, como um PIX regenerado.
10. Entenda Payment Intent, Charge e Transaction
Os três objetos respondem perguntas diferentes:
Para avançar ou encerrar a operação no seu sistema, use o Payment Intent. Para
investigar uma recusa, consulte
latest_charge. Para conciliação financeira e
liquidação, consulte Transactions.
Checklist de testes
Antes de produção, valide pelo menos:- PIX criado e confirmado com
next_actioncompleto; - pagamento PIX concluído de forma assíncrona;
- PIX não pago e tentativa encerrada corretamente;
- cancelamento manual solicitado pelo comprador;
- cartão aprovado;
- cartão recusado com
last_payment_error; - reentrega do mesmo
event.idsem duplicar efeitos; - eventos de intents antigos sem alterar a cobrança atual ou uma operação concluída;
- webhook indisponível temporariamente e recuperado pelos retries;
- assinatura inválida rejeitada antes do processamento;
- fluxo
events_from: "platform"identificando a origem pororganization; - ambiente de teste separado do ambiente live.
Referência rápida
Objeto Payment Intent
Campos, enums, status,
next_action, valores e timestamps.Criar Payment Intent
Parâmetros e respostas de criação.
Consultar Payment Intent
Estado atual e expansões de
payment_method e latest_charge.Confirmar Payment Intent
Confirmação de cartão e PIX.
Cancelar Payment Intent
Estados canceláveis e motivos de cancelamento.
Eventos de Payment Intent
Catálogo e páginas individuais de cada payload.
Entrega e assinatura
Standard Webhooks, retry, timeout, duplicação e ordem.
Lifecycle financeiro
Relação entre Payment Intent, Charge, Transaction e Invoice.

