Payment Link vs. Alternative Payments — which flow should I use?
Migo exposes two backend integrations that overlap in scope but produce different rendering responsibilities and serve different UX needs. Both authenticate with the same long-lived merchant token; the difference is what the merchant has to render and where the customer interacts with the rail.
Decision tree (start here)
-
Do you want Migo to host the entire checkout UI for you?
- Yes → use Payment Link (
POST /transactions). You ship a URL; Migo renders the full webview, including the rail picker (akisiQR, BAM, Zigi, cards, …). No frontend code on your side. - No, I want to render rails inside my own UI → use Alternative Payments (
POST /api/v1/integrations/transactions[…]). Migo returns rail-specific payloads (URL, QR string, base64 image, push button); your frontend decides how to display them.
- Yes → use Payment Link (
-
Do you have a backend that can hold a 64-char merchant secret?
- Yes → either flow is safe.
- No (static SPA, no server) → use
POST /transactions-hook. It accepts body credentials with a CORS-friendly browser flow.
-
Do you need the human-friendly
referencecode (ALI001189SB-style)?- Yes → Payment Link is the only flow that returns it in the create response.
- No → Alternative Payments is enough; you can still correlate with
customKeys.orderIdand the Merchant Generic Callback.
Side-by-side
| Aspect | Payment Link (POST /transactions) | Alternative Payments (POST /api/v1/integrations/transactions[…]) |
|---|---|---|
| What you receive | A hosted webview URL | Rail-specific payloads (url, qr, base64, json, payButton) |
| Rail picker | Hosted by Migo | Yours — read paymentMethods from the create-transaction response |
| Header format | Authorization: <token> (raw token recommended) | Authorization: Bearer <token> (recommended) |
| CORS on the create endpoint | Enabled at the service level (cors: true); a backend is still recommended to keep the merchant token server-side | Enabled at the service level (cors: true); a backend is still recommended to keep the merchant token server-side |
Response includes reference? | Yes (e.g. ALI001189SB) | No |
| QR generation for akisiQR | Customer scans the QR rendered inside the webview | You receive data:image/png;base64,… to render in your UI |
| Refunds | Supported by per-rail flows behind the scenes | Same per-rail support, called explicitly via /refund and /revert |
| Source of truth for outcome | Merchant Generic Callback | Merchant Generic Callback |
Both surfaces emit the same final webhook, so your reconciliation pipeline is the same regardless of which one created the transaction.
Payment Link and Alternative Payments are guarded by the same custom authorizer, which strips a leading Bearer before validating the token. The two formats above are recommended conventions per family — the authorizer accepts the merchant token with or without the Bearer prefix on both. Pick the convention shown for the family you use and stay consistent.
Can I combine both?
Yes — and it's a common pattern when you want to render an APM in your UI but still fall back to the hosted webview for users who don't have the wallet app installed.
- One option: create the transaction via Alternative Payments, render the APM payload inline (e.g. the akisiQR base64 image), and also offer "open hosted checkout" by issuing a second transaction via Payment Link for the same
userId/amount. - Migo treats them as independent transactions (different
uids andreferences). Use your owncustomKeys.orderIdto correlate them. - Don't try to mix the two endpoints on the same
uid: a transaction owns one fulfillment lane.
If you need the same uid to feed both a hosted webview and an inline APM, ask Migo Operations to enable that scenario for your merchant account — it is supported but opt-in per account.
When in doubt
- New integration, you control a backend, you want the simplest path → Payment Link.
- You are building an embedded checkout, branded merchant UI, or you specifically need the akisiQR base64 in your own component → Alternative Payments.
- You are migrating from a legacy
apiKey/apiSecretintegration → keep the JWT login if your runtime depends on it; otherwise switch to the merchant token to drop the refresh complexity.
What next?
- Payment Link: Create a Payment Link · React quickstart
- Alternative Payments: Overview · Create transaction · Process payment · Recipes — Guatemala
- Auth: Header format by endpoint