Quickstart
Quickstart · React Native custodial cash-out (Stellar)
WebView custodial cash-out: RAMPS_DEPOSIT_ADDRESS, omnibus transfer, and sandbox reference number.
~20 minCustodialReact NativeUSDC
Quickstart · React Native custodial cash-out (Stellar / USDC)
Time: about 20 minutes · Success: WebView loads the widget; your app receives a deposit address, your server transfers USDC from the omnibus wallet, and the sandbox flow returns a reference number.
- Credentials & environments (API keys for widget partners), or Sign in if you already have a partner account
- React Native app with a WebView
- Omnibus / hot wallet funded with testnet USDC
- Confirmed you are custodial (you move customer USDC; users do not sign)
Wrong track? User-owned wallets → RN non-custodial Quickstart. Web custodial → Web custodial Quickstart.
Same rule as Web: secret key stays on the server. Your app calls your backend; the backend calls MoneyGram POST /v1/sessions with a stable internal user ID.
TypeScript
const res = await fetch('https://playground.xramps.moneygram.com/api/v1/sessions', { method: 'POST', headers: { 'Content-Type': 'application/json', 'x-api-key': process.env.MONEYGRAM_SK!, }, body: JSON.stringify({ customerIdentifier: authenticatedUserId, walletAddress: process.env.PARTNER_OMNIBUS_WALLET, chain: 'stellar', }),})const session = await res.json()
On RAMPS_READY, post RAMPS_CONFIG with walletType: 'custodial' and your omnibus wallet G-address (not the end user's address).
Handle RAMPS_DEPOSIT_ADDRESS (not RAMPS_SIGN_TRANSACTION):
TypeScript
case 'RAMPS_DEPOSIT_ADDRESS': { const { address, amount, memo } = payload try { // Your backend must authenticate this request and validate address, // amount, and memo against the customer's active Ramps transaction // (looked up server-side) before moving any funds. Never authorize a // transfer from values the WebView supplied alone. const res = await fetch(INTERNAL_TRANSFER_URL, { method: 'POST', headers: { 'Content-Type': 'application/json', Authorization: `Bearer ${appAuthToken}` }, body: JSON.stringify({ to: address, amount, memo, chain: 'stellar', asset: 'USDC' }), }) if (!res.ok) throw new Error(`Transfer failed (${res.status})`) const { txHash } = await res.json() if (typeof txHash !== 'string' || !txHash) throw new Error('Transfer returned no txHash') post('RAMPS_SIGN_SUCCESS', { txHash, walletAddress: PARTNER_OMNIBUS_WALLET }) } catch (err) { post('RAMPS_SIGN_ERROR', { error: err instanceof Error ? err.message : 'Transfer failed' }) } break}
- Session created with a stable
customerIdentifier - WebView opens MoneyGram UI without blank-screen / cookie issues
- Deposit address step triggers your internal transfer
- Hot-wallet Stellar transfer confirms (memo included when required)
- Widget surfaces a sandbox reference number
- React Native · Custodial cash-out guide
- Web · Custodial cash-out guide (shared session + transfer concepts)
- API reference
- Troubleshooting