A máquina de estados do pagamento
As transições de status são decididas somente pela API, de forma central, com um compare-and-set sobre a versão da intenção, e cada uma é gravada na linha do tempo append-only junto com a sua evidência. Os workers em segundo plano nunca alteram um status diretamente; eles enviam observações e a máquina de estados as avalia.
Status e o que fazer
Seção intitulada “Status e o que fazer”| Status | Significa | Entregável | Sua ação |
|---|---|---|---|
created |
Intenção criada; o cliente ainda não escolheu uma rede | não | Mostrar “aguardando pagamento” |
awaiting_payment |
Cotação travada, endereço exclusivo atribuído | não | Aguardar |
detected |
Uma transferência foi vista, mas ainda não está em um bloco | não | Aguardar — ela ainda pode desaparecer |
confirming |
A transferência está em um bloco e acumulando confirmações | não | Aguardar |
confirmed |
O valor esperado atingiu as confirmações exigidas | sim | Entregar (depois de verificar o webhook e reler a intenção) |
underpaid |
Foi confirmado menos do que o cotado | não | Decidir: pedir o restante, aceitar parcialmente ou reembolsar fora da cadeia; depois resolver |
overpaid |
Foi confirmado mais do que o cotado | sim | Entregar; contatar o cliente sobre o excedente; depois resolver |
expired |
A cotação expirou antes de qualquer pagamento ser visto | não | Oferecer um novo checkout se o cliente ainda quiser pagar |
late_payment |
Uma transferência chegou após a expiração | não | Revisar — o preço pode ter mudado; aceitar, reembolsar ou rejeitar; depois resolver |
reorged |
Um bloco que continha o pagamento foi substituído | não | Pausar ou reverter a entrega; aguardar nova confirmação ou revisão |
manual_review |
Retida para uma decisão documentada | não | Revisar a evidência; resolver |
resolved |
Uma decisão registrada encerrou a intenção | conforme a decisão | Seguir a sua decisão (resolution.kind) |
failed |
Falhou, apenas por um motivo validado | não | Ler status_reason |
canceled |
Você cancelou antes de qualquer transferência | não | Nada |
Regras que a máquina de estados garante
Seção intitulada “Regras que a máquina de estados garante”- Crédito exatamente uma vez. Cada transferência na cadeia tem uma identidade determinística (rede + transação + saída ou índice de log). Entregar a mesma observação duas vezes nunca credita duas vezes.
- Identidade do ativo, não símbolos. Uma transferência só conta se a rede, o endereço do contrato e as casas decimais corresponderem à entrada do registro do ativo cotado. Um token que apenas compartilha o símbolo é registrado e sinalizado, nunca creditado.
- Nenhuma reversão silenciosa. Um status final nunca volta atrás em silêncio. Se a cadeia se reorganizar depois
de
confirmed, a intenção passa parareorgede um webhookpayment.reorgedé enviado; ela só volta a confirmar com nova evidência. - A pontualidade é decidida na primeira observação. Uma transferência vista pela primeira vez antes de a cotação expirar conta para o pagamento mesmo que confirme depois. Uma transferência vista pela primeira vez após a expiração é classificada como atrasada.
- Pagamentos extras após a confirmação não alteram uma intenção confirmada; eles criam uma divergência de
conciliação e um evento
payment.review_required. - Cotações são imutáveis. Atualizar uma cotação substitui a antiga; nunca a edita.
Rótulos para o cliente
Seção intitulada “Rótulos para o cliente”O checkout hospedado, o painel e @feitpay/react exibem cada status com um rótulo de texto e um símbolo, em
inglês, português (Brasil) e finlandês — nunca apenas com cor. Se você construir a sua própria interface, faça o
mesmo.