A USD on-ramp and a USDC to BRL Pix off-ramp, step by step: who does what, where the exchange rate is locked, where fees apply, and what expiry changes.
In a quote-based on-ramp or off-ramp, the exchange rate is fixed once: when the quote is created. A payout quote locks the rate and fees before any stablecoins move, and a payin quote locks them before the payer sends money. Every later step, from the on-chain transfer to the local rail, moves money at that locked rate.
One flow has no exchange rate at all. A dollar deposit into a US virtual account becomes USDC or USDT without a quote, because no currency changes hands. The cost there is a fee, not a rate. This guide maps both flows step by step, using the terms defined in the on/off-ramp liquidity glossary.
Key takeaways
At quote creation. Before the quote exists, any rate you see is indicative. Once it exists, the rate, the fees, the sender amount, and the receiver amount are locked until expires_at.
BlindPay's docs group the flows as Receive (payins, the on-ramp side) and Send (payouts, the off-ramp side), with the stablecoins held in a wallet in between. On the Send side, the payout quote locks the exchange rate and the fee split, and a payout can only execute against a valid, unexpired quote. On the Receive side, the payin quote locks the amount, method, fees, and destination before the payer sends anything.
At BlindPay, payout and payin quotes expire 5 minutes after creation by default. OTC payin quotes expire in 10 seconds. Read expires_at (epoch milliseconds) from each response rather than hardcoding the window.
A US virtual account is a bank account in your customer's name with its own routing and account number. Each deposit creates a payin, and BlindPay sends USDC or USDT to the wallet linked to the account.
payin.new webhook.payin.complete when the stablecoins land.Where is the rate set? Nowhere, because there is no FX. USDC is designed to be redeemable 1:1 for US dollars, so dollars in and dollar stablecoins out is not a currency exchange. What you pay is a fee: at BlindPay, deposits below $100 accrue the fee to your monthly invoice (billing_fee_amount), and deposits of $100 or more have it deducted when the deposit converts (transaction_fee_amount).
Timing depends on the rail the payer chose. BlindPay's corridor table lists RTP as instant and ACH and wire deposits at up to 5 business days. Stablecoin virtual accounts explained covers the account itself.
This is the flow where the rate matters, because USDC becomes Brazilian reais.
request_amount in minor units, currency_type, cover_fees, network, and token. The rate and fees are fixed here.receiver_amount in BRL with a countdown to expires_at.approve with the contract payload from the quote. See payout with EVM.quote_id and sender_wallet_address before the quote expires. BlindPay collects the quoted stablecoin amount, and payout.new fires once the funds are captured.payout.complete fires when the deposit is confirmed.Pix is Brazil's instant payment system and runs 24 hours a day, every day, according to the Banco Central do Brasil. BlindPay's corridor table lists Pix payouts as instant, with up to 5 minutes to confirm.
Only one step sets the rate. Fees are also fixed at that step, then applied when money moves.
| Step | What happens | Who acts | Where the rate is set | Where fees apply |
|---|---|---|---|---|
| 1. Bank account | Pix details registered and approved | You, BlindPay | Not yet | None |
| 2. Payout quote | Rate, fees, and both amounts locked | BlindPay | Here | Fees calculated and shown |
| 3. Confirmation screen | Receiver amount and countdown shown | Your app | Already fixed | None |
| 4. Authorization | Token approval signed | Sender's wallet | Already fixed | Network gas for the approval |
| 5. Execution | Stablecoins collected | BlindPay, blockchain | Already fixed | Quoted fees taken |
| 6. Delivery | BRL paid over Pix | Pix | Already fixed | None beyond the quote |
On the virtual account on-ramp, step 2 does not exist. The fee is applied at step 4 of that flow, or on your invoice for deposits under $100.
It is rejected, and nothing moves. An expired quote is never executed at a new rate.
Request a new quote, show the user the new receiver_amount, and ask them to confirm again. Do not resubmit the old quote ID in a retry loop. If you fund from an EVM wallet, check that your approval still covers the new quote's contract.amount, since the amount can shift when the rate does. If an approval transaction is slow to mine, quote again rather than executing against a quote that is about to lapse.
Expiry is a normal path, not an error. Stablecoin FX slippage explains why a binding window is what keeps slippage at zero.
The conversion, the liquidity, and the local rail. You do not choose a market maker, hold reais, open a Brazilian bank account, or connect to Pix.
You touch the blockchain once per payout when you fund from your own wallet: a single signed approval, with the payload handed to you in the quote. With a BlindPay managed wallet, which is in beta and custodial, payouts skip the approval step entirely. What happens on-chain in a stablecoin payment shows the transactions behind the scenes.
Illustrative example. A company off-ramps 10,000 USDC to a supplier's Pix account, with cover_fees: false. The rates and fee are made up for the arithmetic, not BlindPay pricing.
| Moment | Number | Arithmetic |
|---|---|---|
| Quote created | Market rate 5.40, quoted rate 5.373 BRL per USDC | Margin (5.40 - 5.373) / 5.40 = 0.50% |
| Quote created | Receiver amount before flat fee: 53,730 BRL | 10,000 x 5.373 |
| Quote created | Flat fee 20 BRL, receiver amount 53,710 BRL | 53,730 - 20 |
| Approval and execution | 10,000 USDC collected | Sender amount from the quote |
| Pix delivery | 53,710 BRL credited | Same as the quote |
Now suppose the user waits too long and the quote expires. The new quote comes back at 5.360. The new receiver amount is 10,000 x 5.360 - 20 = 53,580 BRL, which is 130 BRL less than the first screen. The user sees that number before anything moves, and decides again.
For reference, Brazil's central bank publishes daily buy and sell PTAX dollar rates. They are a sanity check, not an executable price.
Create one payout quote on a development instance and map each field to the six steps above. The payout quotes docs show the full request and response.
Seven places blockchain payments beat bank rails: contractor payroll, remittances, B2B suppliers, marketplaces, 24/7 treasury, bill pay, and PSP payouts.
AP2, ACP, and x402 each verify that an AI agent had permission to spend. Here is what every protocol covers, who backs it, and the reconciliation gap none of them close.
The three roles behind every card program, stablecoin cards included: what each one does, who carries liability, and what to ask a provider.