Pular para o conteúdo

Pagamentos

Um pagamento representa uma transação no OrcaPay. Este guia mostra o fluxo de criação via Pix e cartão, consulta e gestão do ciclo de vida.

Envie um POST /payments/pix (requer o escopo payments:pix):

Terminal window
curl -X POST https://api.orcapay.com.br/payments/pix \
-H "X-Api-Key: op_live_..." \
-H "Content-Type: application/json" \
-d '{
"amount": 159.90,
"description": "Pedido #1042",
"externalId": "pedido-1042",
"customerName": "Maria Silva",
"customerDocument": "12345678900",
"customerEmail": "maria@exemplo.com.br",
"customerPhone": "62999990000",
"pixExpirationHours": 24
}'

A resposta 201 traz o QR Code para pagamento:

{
"id": "9f8a7b6c-5d4e-4a3b-2c1d-0e9f8a7b6c5d",
"externalId": "pedido-1042",
"referenceId": "PIX-7c1e4b2a-3f5d-4e8a-9b6c-2d1f0a9e8b7c",
"paymentType": "PIX",
"paymentMethod": "PIX",
"amount": 159.90,
"feeAmount": 1.60,
"feePercent": 1.00,
"status": "PENDING",
"statusDescription": "Pendente",
"pixQrCode": "00020126580014br.gov.bcb.pix...",
"pixQrCodeImageUrl": "https://...",
"pixQrCodeBase64": "iVBORw0KGgo...",
"pixExpiresAt": "2026-07-19T14:30:00Z",
"createdAt": "2026-07-18T14:30:00Z",
"expectedSettlementDate": "2026-07-19"
}

O campo externalId é um identificador seu (por exemplo, o número do pedido) que volta em consultas e webhooks para facilitar a correlação — e também protege contra cobranças duplicadas: repetir o POST /payments/pix com o mesmo externalId e o mesmo valor retorna o mesmo pagamento e o mesmo QR Code, em vez de criar outro. Veja externalId e idempotência.

O fluxo de cartão tem duas etapas: criptografar os dados do cartão no navegador com o SDK JavaScript do OrcaPay e enviar o pagamento pelo seu backend. Os dados abertos do cartão nunca passam pelo seu servidor.

Inclua o SDK na sua página de checkout:

<script src="https://sdk.orcapay.com.br/v1/orcapay.min.js"></script>

Inicialize com o identificador do seu estabelecimento e criptografe os dados do cartão:

const orcapay = new OrcaPay({
establishmentId: 'e1f2a3b4-c5d6-7e8f-9a0b-1c2d3e4f5a6b',
});
const encryptedCard = await orcapay.encryptCard({
holder: 'Maria Silva',
number: '4111 1111 1111 1111',
expMonth: '12',
expYear: '2030',
securityCode: '123',
});

O SDK descobre sozinho o provedor de pagamento e a chave pública configurados para o seu estabelecimento — nenhuma credencial precisa ser exposta no front-end. O retorno é a string encryptedCard, pronta para ser enviada ao seu backend. Espaços no número do cartão são removidos automaticamente; expMonth usa dois dígitos ("01" a "12") e expYear quatro ("2030").

Se preferir não usar o SDK, obtenha a chave pública diretamente em GET /payments/card/public-key/{establishmentId} (endpoint público) e criptografe conforme a documentação do provedor retornado no campo provider.

Envie um POST /payments/card (requer o escopo payments:card):

Terminal window
curl -X POST https://api.orcapay.com.br/payments/card \
-H "X-Api-Key: op_live_..." \
-H "Content-Type: application/json" \
-d '{
"amount": 159.90,
"installments": 3,
"encryptedCard": "encrypted-card-token...",
"holderName": "Maria Silva",
"holderDocument": "12345678900",
"description": "Pedido #1042",
"externalId": "pedido-1042",
"customerName": "Maria Silva",
"customerDocument": "12345678900",
"customerEmail": "maria@exemplo.com.br",
"softDescriptor": "MINHALOJA"
}'

O parcelamento aceita de 1 a 24 parcelas. O softDescriptor é o texto que aparece na fatura do portador.

Envie sempre o externalId: se já existir um pagamento ativo com o mesmo identificador, a requisição retorna 409 CONFLICT sem processar o cartão de novo — é a proteção contra cobrança dupla em retentativas. Veja externalId e idempotência.

Nem todo cartão é aprovado ou recusado na hora. A operadora pode colocar a cobrança em análise antifraude e só decidir depois, em geral em poucos minutos e, em casos raros, em algumas horas. O campo opcional allowPending do POST /payments/card diz à OrcaPay se a sua integração sabe esperar por essa decisão:

allowPendingQuando o cartão entra em análiseResposta
trueO pagamento fica PENDING e a decisão chega depois por webhook201 com "status": "PENDING"
omitido ou falseO OrcaPay cancela a cobrança na operadora na mesma requisição e registra o pagamento como FAILED400 com "code": "BAD_REQUEST"

Cartões aprovados ou recusados na hora seguem o fluxo normal nos dois casos: 201 com CONFIRMED ou 400 com o motivo da recusa. Recomendamos enviar "allowPending": true sempre que a sua integração receber webhooks.

Inclua o campo no corpo do pagamento:

Terminal window
curl -X POST https://api.orcapay.com.br/payments/card \
-H "X-Api-Key: op_live_..." \
-H "Content-Type: application/json" \
-d '{
"amount": 159.90,
"installments": 3,
"encryptedCard": "encrypted-card-token...",
"holderName": "Maria Silva",
"holderDocument": "12345678900",
"description": "Pedido #1042",
"externalId": "pedido-1042",
"customerName": "Maria Silva",
"customerDocument": "12345678900",
"customerEmail": "maria@exemplo.com.br",
"allowPending": true
}'

Se o cartão entrar em análise, a resposta é 201 com o pagamento pendente e sem paidAt:

{
"id": "9f8a7b6c-5d4e-4a3b-2c1d-0e9f8a7b6c5d",
"externalId": "pedido-1042",
"referenceId": "CARTAO-4d2a9f1e-8b3c-4a7d-9e6f-1c0b2a3d4e5f",
"paymentType": "CREDIT",
"paymentMethod": "CREDIT_CARD",
"amount": 159.90,
"installments": 3,
"status": "PENDING",
"statusDescription": "Pendente",
"cardBrand": "VISA",
"cardLastFour": "1111",
"paidAt": null,
"createdAt": "2026-07-18T14:30:00Z"
}

O pagamento existe, mas ainda não foi pago: não libere o pedido. Junto com a resposta o OrcaPay envia o webhook PAYMENT_CREATED com "status": "PENDING". A decisão da operadora chega por um destes webhooks:

WebhookStatus finalSignificado
PAYMENT_CONFIRMEDCONFIRMEDAnálise aprovada e cobrança capturada. Pode liberar o pedido; paidAt passa a ter o momento da confirmação
PAYMENT_FAILEDFAILEDAnálise reprovada. Nada foi cobrado do portador
PAYMENT_CANCELLEDCANCELLEDCobrança cancelada antes da decisão, pela operadora ou por você via API

Se a notificação da operadora atrasar ou se perder, o OrcaPay consulta a cobrança na operadora periodicamente e envia o mesmo webhook assim que a decisão sair. Você também pode acompanhar o status com GET /payments/{id}.

Enquanto o pagamento estiver PENDING:

  • Não envie o cartão de novo. Um novo POST /payments/card com o mesmo externalId retorna 409, porque o pagamento pendente continua ativo.
  • Para desistir da venda, use POST /payments/{id}/cancel. O OrcaPay cancela a cobrança na operadora, o pagamento vai para CANCELLED e você recebe PAYMENT_CANCELLED.
  • Marque os eventos PAYMENT_CONFIRMED, PAYMENT_FAILED e PAYMENT_CANCELLED no seu endpoint de webhooks. Sem eles, a única forma de saber a decisão é consultar o pagamento.

Sem o campo, ou com "allowPending": false, o OrcaPay entende que a sua integração só trata aprovação ou recusa imediata. Se o cartão entrar em análise, o OrcaPay cancela a cobrança na operadora na mesma requisição, para que ela não seja capturada depois sem o seu sistema saber, e responde 400:

{
"timestamp": "2026-07-18T14:30:00Z",
"status": 400,
"code": "BAD_REQUEST",
"message": "Pagamento não autorizado pela operadora",
"path": "/payments/card"
}

O pagamento fica registrado como FAILED (aparece no console e em GET /payments), nenhum webhook é enviado e o externalId fica livre para uma nova tentativa, com outro cartão ou mais tarde.

Em casos raros a operadora não aceita o cancelamento e a cobrança ainda é aprovada depois da análise. Se você receber PAYMENT_CONFIRMED de um pagamento que tinha respondido 400, confira se o cliente não foi cobrado duas vezes e estorne o pagamento repetido. Com allowPending: true esse risco não existe, porque a cobrança em análise nunca é tratada como recusa.

StatusSignificado
PENDINGAguardando pagamento (Pix) ou cartão em análise na operadora, veja Cartão em análise antifraude
PROCESSINGEm processamento
CONFIRMEDPagamento confirmado
FAILEDNão aprovado
CANCELLEDCancelado
REVERSEDEstornado integralmente (com estorno parcial o pagamento segue CONFIRMED)
CHARGEBACKContestado pelo portador

Para acompanhar as mudanças de status em tempo real, configure webhooks.

Consulta individual (requer payments:read):

Terminal window
curl https://api.orcapay.com.br/payments/{id} \
-H "X-Api-Key: op_live_..."

Listagem com filtros e paginação:

Terminal window
curl "https://api.orcapay.com.br/payments?createdFrom=2026-07-01T00:00:00Z&createdTo=2026-07-18T23:59:59Z&paymentMethod=PIX&page=0&size=20&sort=createdAt,desc" \
-H "X-Api-Key: op_live_..."

A resposta é paginada: os resultados vêm em content, com totalElements, totalPages, number (página atual, iniciando em 0) e size. Também é possível listar por status com GET /payments/status/{status} e consultar o histórico de eventos de um pagamento com GET /payments/{id}/logs.

Além do período de criação, a listagem aceita paidFrom e paidTo (período de confirmação, comparado com paidAt) e search, que procura um trecho de texto no id, no externalId, no referenceId e nos dados do cliente.

Cada pagamento tem vários identificadores, e cada um serve para cruzar com um sistema diferente:

CampoQuem geraOnde aparecePara que serve
idOrcaPayRespostas da API, paymentId nos webhooks, consoleConsultar, cancelar e estornar o pagamento na API (GET /payments/{id})
externalIdVocêRespostas da API e webhooksLigar o pagamento ao pedido, fatura ou inscrição no seu sistema
referenceIdOrcaPay, ao criar a cobrança na operadoraRespostas da API, webhooks e coluna “Código de Referência” no relatório de transações do PagBankConciliar com o extrato da operadora. Prefixo PIX- no Pix e CARTAO- no cartão
chargeIdPagBank, ao criar a cobrançaConsulta e listagem (GET /payments/{id}, GET /payments)Conferir com o extrato e o EDI do PagBank. Exemplo: CHAR_A892BA8A-9DED-40C4-A23E-15D1753F9E4A. No cartão vem desde a criação; no Pix aparece quando o pagamento é confirmado
pixEndToEndIdInstituição do pagador, quando o Pix é pagoConsulta e listagem (GET /payments/{id}, GET /payments)Localizar o Pix no extrato bancário ou no comprovante do pagador. Exemplo: E60746948202610291321A3545HAyL4k. Nulo no cartão e no Pix ainda não pago
pixTxIdPagBank, ao criar a cobrança PixConsulta e listagem e coluna “Código TX ID (PIX)” no relatório de vendas do PagBankConferir o Pix no relatório do PagBank. Exemplo: 20261106081229527533983314153372 (32 dígitos que começam pela data e hora). Nulo no cartão
splitIdPagBank, ao criar a cobrança com splitConsulta e listagem e coluna “ID Split” no relatório de vendas do PagBankConferir a divisão do pagamento. Exemplo: SPLI_1F580EAD-9EA2-45B4-9ED7-8A51718CAD16. Nulo quando o pagamento não tem split

O id e o referenceId são diferentes: o id não aparece no relatório do PagBank. Para conferir o extrato da operadora, guarde o referenceId junto com o id ou consulte o pagamento quando precisar.

No extrato e no EDI do PagBank, a transação aparece pelo codigo_transacao, que é o chargeId sem o prefixo CHAR_ e sem hífens. O chargeId CHAR_A892BA8A-9DED-40C4-A23E-15D1753F9E4A, por exemplo, aparece no EDI como A892BA8A9DED40C4A23E15D1753F9E4A. Isso vale quando a conta do estabelecimento é a principal da cobrança. Quando ela recebe como participante secundário do split, o código da transação no relatório dela é o da parte dela na divisão, diferente do chargeId; nesse caso, confira pelo splitId. O chargeId, o pixEndToEndId, o pixTxId e o splitId não vêm na resposta de criação nem nos webhooks: consulte o pagamento para obtê-los.

Para cruzar os pagamentos confirmados em um dia com o relatório de transações do PagBank, liste pelo período de confirmação e compare o referenceId de cada pagamento com a coluna “Código de Referência”:

Terminal window
curl "https://api.orcapay.com.br/payments/status/CONFIRMED?paidFrom=2026-09-24T03:00:00Z&paidTo=2026-09-25T02:59:59Z&paymentMethod=PIX&size=100" \
-H "X-Api-Key: op_live_..."

Os instantes da API estão em UTC; o exemplo cobre o dia 24/09 no horário de Brasília. Para o caminho inverso, partindo de uma linha do relatório do PagBank, busque pelo código de referência:

Terminal window
curl "https://api.orcapay.com.br/payments?search=PIX-7c1e4b2a-3f5d-4e8a-9b6c-2d1f0a9e8b7c" \
-H "X-Api-Key: op_live_..."

Cancelar um pagamento pendente (requer payments:cancel):

Terminal window
curl -X POST https://api.orcapay.com.br/payments/{id}/cancel \
-H "X-Api-Key: op_live_..." \
-H "Content-Type: application/json" \
-d '{ "reason": "Pedido cancelado pelo cliente" }'

Estornar um pagamento confirmado, total ou parcialmente (requer payments:refund). Sem corpo, o OrcaPay estorna todo o saldo; com amount (valor exato) ou percentage (percentual do valor total), estorna só uma parte:

Terminal window
curl -X POST https://api.orcapay.com.br/payments/{id}/reverse \
-H "X-Api-Key: op_live_..." \
-H "Content-Type: application/json" \
-H "Idempotency-Key: 0b8e7c1d-6f2a-4c55-9e0b-3f1d2a7c9b14" \
-d '{ "amount": 40.00, "reason": "Item devolvido pelo cliente" }'

O pagamento continua CONFIRMED enquanto houver saldo e passa para REVERSED quando o valor total é devolvido. Regras de cálculo, validações, prazos e webhooks estão em Estornos.

Para conferência financeira, a API oferece dois relatórios (requerem payments:read):

  • GET /payments/conciliation?from=2026-07-01T00:00:00Z&to=2026-07-18T23:59:59Z — totais do período agrupados por status (quantidade, valor bruto, taxas e valor líquido).
  • GET /payments/settlement-agenda?from=2026-07-18&to=2026-08-18 — agenda de liquidação: quanto será liquidado por dia.

Ambos aceitam o filtro opcional method (PIX, CREDIT_CARD, DEBIT_CARD).