Integração Lunium

Sandbox: PIX, custódia e cripto

Testar agoraBaixar kit

Use a mesma base https://api.luniumpay.com com uma chave lun_test_. Toda operação financeira é fictícia. O QR de entrada contém SANDBOX:NAO_PAGAVEL:: não é um PIX bancário. Confirme o pagamento pela API de simulação. Nenhum saque é enviado à corretora parceira ou à blockchain.

Testar agora

Abra a integração guiada, escolha o fluxo, informe o seu e-mail e execute a demonstração. Pela conexão pública de IA, use lunium_start_sandbox_demo com flow igual a custody, cashin, payout ou cashout, além de um request_id aleatório e estável e do email de quem vai testar (opcional nas ferramentas MCP, mas fortemente recomendado: com ele a LuniumPay manda à pessoa o guia de integração (o que é a LuniumPay, manual, fluxograma, próximos passos) uma única vez; sem ele, crie a chave mesmo assim e colete o e-mail depois com lunium_contact). Continue com lunium_get_sandbox_demo; ele pode criar o saque fictício já previsto na jornada após confirmar o crédito.

Para testar seu backend, baixe o kit:

node sandbox.mjs all
# ou Python 3.9+, sem dependências:
python3 sandbox.py all

O kit cria uma chave em memória com o e-mail de quem vai testar (defina LUNIUM_SANDBOX_EMAIL=voce@empresa.com; sem ele, o kit para com uma mensagem clara), confirma GET /keys/me antes de operar e recusa credenciais de produção. Também aceita LUNIUM_API_KEY contendo exclusivamente uma chave de teste. Não imprime credenciais. Selecione custody, cashin, payout ou cashout no lugar de all para uma jornada específica.

Jornadas e conclusão

Jornada Criar Confirmar e acompanhar Sucesso
PIX → custódia BRL POST /cashin/charge, destino: "saldo" POST /sandbox/cashin/{cashin_id}/pay, depois /cashin/{cashin_id}/status e /saldo status=paid, settlement_status=sent; disponível na subconta correta
PIX → BTC, USDC ou outra rota do catálogo de teste POST /cashin/charge, destino: "cripto", asset, chain, payout_address Mesma confirmação de PIX e consulta de cash-in paid e sent; hash começa com sandbox:, sem transação real
Custódia → cripto POST /saldo/sacar-cripto, amount_cents, tax_number, asset, chain, payout_address /cashin/{cashin_id}/status paid e sent; débito inclui fee_cents
Custódia → PIX POST /payouts, amount_cents, pix_key GET /payouts/{payout_id} status=sent; E2E fictício com ISPB 00000000
Transferência interna POST /saldo/transferir, from_customer_ref, to_customer_ref, amount_cents /saldo/extrato, /saldo/clientes, /saldo/consolidado Débito e crédito atômicos; total custodiado conservado
DePix/Liquid → PIXPOST /cash-outs, asset: "DEPIX", network: "liquid", destinatário Pix e, se quiser, refund_addressPOST /cash-outs/{cashout_id}/accept, depois GET /cash-outs/{cashout_id}state=COMPLETED; depósito e PIX simulados
Cripto externa → PIX POST /cash-outs, depois POST /cash-outs/{cashout_id}/accept GET /cash-outs/{cashout_id} state=COMPLETED; depósito também simulado

Custódia não exige carteira fixa. O saldo é BRL. Escolha moeda, rede, endereço e memo apenas no saque. O kit percorre BTC nativo, USDC na Polygon e saque de USDC na Base; o catálogo de testes oferece outras rotas nominadas. No cash-in e saque use chain; no cash-out use network.

Testar PIX → DePix/Liquid

Use uma chave lun_test_ e confirme key.sandbox=true em GET /keys/me. A rota DEPIX/liquid aparece em instant no GET /cashin/catalog?asset=depix&network=liquid. O teste cobre PIX → DePix; saque da custódia para Liquid continua indisponível.

Envie asset: "depix", chain: "liquid", delivery_mode: "split" e um endereço Liquid em payout_address. Substitua SEU_ENDERECO_LIQUID abaixo pelo endereço da sua carteira. O CPF do exemplo é sintético, exclusivo de sandbox. O endereço não recebe moedas: este fluxo não usa Liquid mainnet nem testnet.

Consulte POST /cashin/preview com os mesmos parâmetros antes de criar a cobrança. A taxa básica da compra de DePix é 2% + R$ 1,00, com mínimo de R$ 2,00 por PIX, salvo condição própria da chave. A parcela fixa é descontada antes do percentual: R$ 500,00 resultam em 489,02 DePix na política padrão. Confira net_cents e fee_total_cents retornados; a taxa de compra de USDC/USDT e a comissão do parceiro não são somadas ao DePix.

curl --fail-with-body https://api.luniumpay.com/cashin/charge \
  -H "X-API-Key: $LUNIUM_API_KEY" -H 'Content-Type: application/json' \
  -d '{"amount_cents":50000,"payer_tax_number":"12345678901","destino":"cripto","asset":"depix","chain":"liquid","delivery_mode":"split","payout_address":"SEU_ENDERECO_LIQUID","external_id":"sandbox-depix-001"}'

# Use o cashin_id devolvido na criação:
curl --fail-with-body -X POST "https://api.luniumpay.com/sandbox/cashin/$CASHIN_ID/pay" \
  -H "X-API-Key: $LUNIUM_API_KEY" -H 'Content-Type: application/json' -d '{}'

curl --fail-with-body "https://api.luniumpay.com/cashin/$CASHIN_ID/status" \
  -H "X-API-Key: $LUNIUM_API_KEY"

Confirme o pagamento pela rota /sandbox/cashin/{cashin_id}/pay e consulte o status até paid e sent. A API e os webhooks cashin.paid/cashin.settled mantêm delivery_mode, net_cents e fee_total_cents. O hash começa com sandbox: e settlement_tx_url é null. Não pague o QR em banco: nenhum PIX ou envio em blockchain é feito.

Testar DePix/Liquid → PIX

Use asset: "DEPIX", network: "liquid" e uma chave lun_test_. Consulte GET /catalog?asset=DEPIX&network=liquid: a rota aparece em fast. Informe amount em DePix ou brl_amount para cotar a partir do PIX desejado, sem combinar os dois. A paridade é 1 DePix = R$ 1,00 antes das taxas; confira o valor efetivo retornado, inclusive na cotação reversa.

A venda usa sua própria tarifa vigente na chave, informada em fee_bps, fee_fixed_cents, fee_total_cents e net_cents. Na política padrão de venda de 1,5% + R$ 1,00, enviar 100,00 DePix resulta em PIX de R$ 97,51. A tarifa de compra de DePix é separada.

Na criação, informe a chave Pix. refund_address, uma carteira Liquid de devolução confirmada pelo cliente, é opcional desde a API 1.44.0: sem ela, uma venda que precise ser devolvida para em AWAITING_REFUND_ADDRESS até você informar a carteira em POST /cash-outs/{cashout_id}/refund-address. Para chave Pix de e-mail, telefone ou aleatória, payee_tax_number é obrigatório; para CPF/CNPJ, o documento vem da própria chave. O exemplo usa destinatário e CPF sintéticos. Substitua SUA_CARTEIRA_LIQUID_DE_DEVOLUCAO por um endereço Liquid válido (ou retire o campo); nenhum ativo é enviado a ele pelo sandbox.

# Prévia: não cria ordem nem exige destinatário ou carteira de devolução.
curl --fail-with-body https://api.luniumpay.com/cash-outs/preview \
  -H "X-API-Key: $LUNIUM_API_KEY" -H 'Content-Type: application/json' \
  -d '{"asset":"DEPIX","network":"liquid","amount":"100.00"}'

# Criar a cotação simulada:
curl --fail-with-body https://api.luniumpay.com/cash-outs \
  -H "X-API-Key: $LUNIUM_API_KEY" -H 'Content-Type: application/json' \
  -d '{"asset":"DEPIX","network":"liquid","amount":"100.00","pix_key":"depix@example.invalid","pix_key_type":"email","payee_tax_number":"12345678901","refund_address":"SUA_CARTEIRA_LIQUID_DE_DEVOLUCAO","external_id":"sandbox-depix-pix-001","sandbox_scenario":"success"}'

# Use o cashout_id devolvido na criação:
curl --fail-with-body -X POST "https://api.luniumpay.com/cash-outs/$CASHOUT_ID/accept" \
  -H "X-API-Key: $LUNIUM_API_KEY" -H 'Content-Type: application/json' -d '{}'

curl --fail-with-body "https://api.luniumpay.com/cash-outs/$CASHOUT_ID" \
  -H "X-API-Key: $LUNIUM_API_KEY"

O aceite inicia automaticamente o depósito simulado. deposit_address começa com SANDBOX:LIQUID:NAO_ENVIAR: e não é um endereço pagável. Não envie moedas e não procure uma rede testnet: a simulação ocorre na API. Consulte a ordem até COMPLETED, normalmente cerca de 14 segundos depois do aceite. Ela percorre AWAITING_DEPOSIT → DEPOSIT_DETECTED → PROCESSING → COMPLETED. O pix_e2e final usa ISPB fictício 00000000; a verificação também identifica o sandbox. Não há pagamento bancário, comprovante bancário real ou transação Liquid.

Os eventos são cashout.awaiting_deposit, cashout.deposit_detected, cashout.processing e cashout.completed. Em uma devolução, também há cashout.refunding e cashout.refunded; o hash de devolução começa com sandbox:. Configure o callback antes de criar a operação ou inspecione GET /sandbox/events.

Para DePix → PIX, escolha sandbox_scenario: success, delayed (cerca de 54 segundos), failed, expired (deixe a cotação sem aceite por mais de 5 segundos), refunded, settlement_uncertain, provider_unavailable (503 sem criar ordem), route_unavailable ou no_deposit (sem depósito até expirar). O cenário explícito prevalece sobre os gatilhos por centavos descritos abaixo; sem cenário explícito, esses gatilhos continuam ativos.

Para testar a devolução sem carteira, crie a cotação sem refund_address e com o cenário refunded. Depois do aceite, a ordem passa por REFUNDING e para em AWAITING_REFUND_ADDRESS (webhook cashout.awaiting_refund_address), com refund_amount, refund_asset e refund_network preenchidos. Informe uma carteira Liquid em POST /cash-outs/{cashout_id}/refund-address: a ordem segue para REFUNDING e, cerca de 4 segundos depois, REFUNDED, com hash de devolução começando por sandbox:. Repetir a mesma carteira responde 200; outra carteira, 409 refund_address_imutavel.

Em settlement_uncertain, a ordem permanece em PROCESSING. Resolva com POST /sandbox/operations/{cashout_id}/resolve e {"outcome":"sent"} para concluir, ou {"outcome":"failed"} para simular a devolução (REFUNDING → REFUNDED após cerca de 4 segundos; sem refund_address, a ordem para em AWAITING_REFUND_ADDRESS, como acima). Repetir a mesma resolução ou o aceite não duplica a operação. Repetir external_id com destinatário, documento, carteira, valor ou cenário diferentes retorna 409. Recupere a intenção com GET /cash-outs?external_id=....

Este fluxo de DePix usa chave PIX; br_code é recurso das rotas USDT/USDC. sandbox_scenario e /sandbox/operations/.../resolve são recusados com chave de produção. Consulte também GET /sandbox, em scenarios_by_flow.cashout_depix.

Receber na custódia sem carteira

Crie a chave com POST /keys/sandbox, enviando o email de quem vai testar (obrigatório: é para ele que mandamos o manual, o fluxograma e o passo a passo da integração), e guarde api_key em LUNIUM_API_KEY somente no backend. Confirme key.sandbox=true em GET /keys/me antes das chamadas abaixo. O documento deste exemplo é sintético e serve apenas ao sandbox.

curl --fail-with-body https://api.luniumpay.com/cashin/charge \
  -H "X-API-Key: $LUNIUM_API_KEY" -H 'Content-Type: application/json' \
  -d '{"amount_cents":100000,"payer_tax_number":"12345678901","destino":"saldo","customer_ref":"cliente-teste","external_id":"sandbox-deposito-001"}'

Guarde cashin_id. Para simular o pagamento:

curl --fail-with-body -X POST "https://api.luniumpay.com/sandbox/cashin/$CASHIN_ID/pay" \
  -H "X-API-Key: $LUNIUM_API_KEY" -H 'Content-Type: application/json' -d '{}'

Consulte /cashin/{cashin_id}/status até paid e sent, geralmente cerca de 6 segundos. Depois consulte /saldo?customer_ref=cliente-teste. O crédito é líquido das taxas da chave; não compare o saldo com o valor bruto da cobrança. Repetir o pagamento não duplica crédito.

Cenários determinísticos de cash-in, custódia e payout

Envie sandbox_scenario ao criar a operação. Consulte GET /sandbox para a matriz de cenários por fluxo.

Cenário Resultado
success Sucesso; padrão quando omitido
delayed Retenção/demora de aproximadamente 30 segundos antes da continuação
held Somente depósito em custódia: crédito bloqueado por 30 segundos, depois disponível
expired Cash-in expira ao tentar simular pagamento
payer_mismatch Cash-in devolvido por divergência de pagador, sem crédito/entrega
refunded Cash-in devolvido sem crédito; payout devolvido com estorno único
failed Falha de pagamento; payout devolve o débito uma vez
settlement_failed Pagamento pode estar confirmado, mas a entrega falha; saque estorna débito e taxas
settlement_uncertain Entrega fica incerto; payout continua processing. Não estorna antes da conciliação
route_unavailable Criação recusada, sem débito
provider_unavailable HTTP 503 simulado, sem operação criada; enquanto o cenário continuar, a recusa continua

Para resolver uma incerteza somente em teste, chame POST /sandbox/operations/{operation_id}/resolve com {"outcome":"sent"} ou {"outcome":"failed"}. Repetir a mesma resolução é idempotente. A rota exige uma operação incerta da própria chave. Não existe confirmação fictícia em produção.

Teste também payload inválido, mínimo por moeda/rede, saldo insuficiente, gasto concorrente, conta bloqueada, ID de outra chave e external_id reutilizado com parâmetros diferentes. Use uma intenção e um external_id estáveis para retry; parâmetros divergentes são recusados. Cobrança e saque cripto compartilham o espaço de referências. Após timeout, recupere pelo ID ou pelas listas filtradas por external_id.

Cenários de cripto → PIX

O cash-out mantém os gatilhos nas duas casas decimais de amount (ou brl_amount na cotação reversa): .00 sucesso, .01 demora, .02 falha, .03 expiração, .04 limite, .05 lento, .06 recusa do provedor, .07 primeira tentativa de aceite retorna 503 e a segunda funciona, .08 limite de pagador. Na prévia, nenhum registro é criado. Nunca envie cripto ao endereço devolvido pelo simulador.

Carteira USDT/USDC

A chave de teste usa o simulador da carteira: as mesmas rotas /carteira-usdt, as mesmas formas e os mesmos estados da produção, sem nada real. O depósito devolve um endereço fictício (SANDBOX-NAO-ENVIE-FUNDOS; nunca envie fundos) e é creditado sozinho em cerca de 15 segundos. O PIX pago com o saldo de teste conclui em cerca de 15 segundos, com E2E de teste e receipt_url: null. Gatilhos pelos centavos: depósito .02 não chega e expira em cerca de 1 minuto; PIX .01 passa cerca de 40 segundos em revisao, .02 falha antes do envio e devolve a reserva, .05 demora cerca de 2 minutos. Os webhooks wallet.deposit_credited, wallet.payment_completed e wallet.payment_failed chegam com sandbox: true.

Webhooks reais sobre eventos fictícios

Configure uma URL HTTPS pública que você controla em PATCH /keys/me com webhook_url e guarde webhook_secret com segurança. Os eventos do sandbox usam a mesma fila de entrega e assinatura do produto; levam sandbox:true. Valide HMAC sobre o corpo bruto, timestamp, event_id e tolerância a duplicatas conforme o manual. Não confunda evento fictício entregue via HTTP real com liquidação financeira real.

Use GET /sandbox/events para inspecionar eventos gerados, mesmo sem callback configurado. GET /webhooks/deliveries mostra tentativas e POST /webhooks/deliveries/{event_id}/retry reenvia. Eventos anteriores à configuração do callback não são enviados retroativamente: crie uma nova operação ou use /webhooks/test. Cash-in publica cashin.paid, cashin.settled ou a falha correspondente. Retenção/liberação e transferência têm seus eventos específicos. Payout publica seu resultado final; cash-out publica progressão e conclusão.

Persistência, preços e fronteiras do teste

Cash-in, custódia, payout e transferências persistem isolados do livro financeiro real, inclusive após reinício. Cash-out também é persistido, com retenção de duas horas. Há limite de 1.000 operações por chave para as novas jornadas e 1.000 cash-outs. POST /sandbox/reset com {"confirm":true} apaga apenas o estado fictício da sua chave; entregas de webhook já enfileiradas mantêm seu histórico.

Cotações e catálogos são snapshots sintéticos identificados na resposta. Os preços, mínimos, disponibilidade e análise de risco da produção podem mudar. O sandbox não chama a corretora parceira, bancos ou carteiras. O custo de provedor do payout de teste é fixado em 100 centavos e informado em /saldo; não representa a tarifa real. A escada por CPF não consulta histórico de pessoas; /cashin/limits informa essa diferença. Testes de retenção têm tempo comprimido.

O simulador cobre ativos nominados de seu catálogo; não simula tokens DEX arbitrários por contrato, leitura bancária de QR dinâmico, a rede blockchain nem políticas privadas de cada provedor. Em produção, leia novamente /keys/me, /saldo, limites e catálogos com a chave real. Um piloto com PIX efetivamente pago e cripto enviada pela corretora parceira é uma operação real, com valor e destinatário autorizados. A conclusão do sandbox valida a integração de software, não certifica liquidez ou execução dos provedores.