Skip to main content
O último dígito de um cartão não é informação — é conferência. Ele é escolhido para fazer uma conta fechar, e essa conta é o algoritmo de Luhn. Um número que não fecha essa conta não existe. Nenhuma adquirente do mundo autoriza, porque não há cartão emitido com aquele número. Conferir isso é uma operação local, de microssegundos, que não depende de rede.

O que a Cakto faz

Tokenização recusa com 422

POST /public_api/card-tokens/ (e createToken, no SDK) valida o dígito verificador antes de tokenizar. Número que não fecha volta 422:
Como o pagamento por cartão só aceita cardToken, um número que falha na tokenização não chega a ser cobrado — não existe outro caminho de número de cartão na API. O checkout hospedado da Cakto também confere, direto no campo, enquanto o comprador digita.
A validação não diz que o cartão existe, que está ativo, que tem limite ou que não está bloqueado. Ela só descarta o que é impossível. Recusa por saldo, limite, antifraude ou emissor continua vindo da adquirente, como sempre.

Como o algoritmo funciona

  1. Percorra os dígitos da direita para a esquerda.
  2. Dobre um sim, um não, começando pelo segundo (o penúltimo dígito do cartão).
  3. Se o dobro passar de 9, subtraia 9 (8 × 2 = 16 → 7).
  4. Some tudo. Se o total for múltiplo de 10, o número passa.
Com 4111 1111 1111 1111, os dobrados são sete 1 → 2 e o 4 → 8; os outros oito dígitos entram como estão:
Troque só o último dígito para 2 e a soma vira 31 — resto 1, recusado.

O que ele pega

Os dois primeiros são os erros de digitação mais comuns de quem preenche um formulário, e é para eles que o dígito verificador existe.

Como conferir antes de chamar a API

Vale conferir no seu lado mesmo com a API validando: o comprador vê o erro no campo, no ato, sem esperar o round-trip, e você não gasta chamada nem rate limit com um número que já nasce recusado.
As duas implementações normalizam por dentro: espaço e hífen que o comprador digita não invalidam o número. 4111 1111-1111.1111 passa.

Dois enganos que custam caro

Uma função que resolve bandeira e comprimento a partir do BIN aceita 4111 1111 1111 1112 sem reclamar: o prefixo e o comprimento estão certos, só o dígito verificador não fecha.São checagens diferentes e independentes — faça as duas. Foi exatamente assim que um número inválido atravessou o formulário do nosso próprio checkout e só foi recusado pela adquirente, na autorização.
Validação no formulário melhora a experiência de quem digita, mas é contornável: qualquer um pode chamar a sua API diretamente.Se você tem backend próprio no meio do caminho, confira lá também. É por isso que a Cakto valida na tokenização, e não só no checkout.

Números para teste

Estes fecham o dígito verificador e servem para exercitar a sua integração sem tomar 422:
Fechar o Luhn não os torna cobráveis: são números de teste e a adquirente recusa a autorização. Eles servem para validar o seu fluxo até a tokenização, não para simular venda aprovada.
Se a sua suíte de testes usa número inventado, troque por um destes. Desde a mudança anunciada em Changelog, número que não fecha o dígito verificador volta 422 na tokenização.