Quickstart
Accept your first payment in 10 minutes. We will install the Node SDK, create a session on your server, open the hosted checkout, and verify a webhook.
Already have an account? Grab a TEST key from Dashboard → Developers → API Keys.
1. Install the server SDK
bash
npm install @minnha/node2. Create a session
Add a route on your backend (Next.js, Express, NestJS — anything):
ts
// app/api/checkout/route.ts
import { Minnha } from "@minnha/node";
const minnha = new Minnha(process.env.MINNHA_API_KEY!); // mp_test_...
export async function POST() {
const session = await minnha.sessions.create({
amount: 199.50,
currency: "SAR",
description: "Order #123",
customerEmail: "customer@example.com",
customerPhone: "+966512345678",
successUrl: "https://yourapp.com/orders/123/success",
cancelUrl: "https://yourapp.com/orders/123/cancel",
metadata: { orderId: "ord_123" },
});
return Response.json({ sessionToken: session.sessionToken });
}3. Open the checkout on the client
tsx
// React example — npm install @minnha/pay-react
import { MinnhaCheckoutButton } from "@minnha/pay-react";
<MinnhaCheckoutButton
createSession={async () => (await fetch("/api/checkout", { method: "POST" })).json()}
checkoutOptions={{ mode: "popup", locale: "ar" }}
onSuccess={({ transactionId }) => router.push(`/orders/${transactionId}`)}
>
Pay 199.50 SAR
</MinnhaCheckoutButton>Don't use React? Use the framework-agnostic
@minnha/pay-js, or for mobile see the iOS / Android / RN guides.4. Test with a card
On the hosted checkout, use any of:
| Card number | Result |
|---|---|
4111 1111 1111 1111 | SUCCESS |
4000 0000 0000 0002 | FAILED |
4000 0027 6000 3184 | 3-D Secure required |
Use any future expiry, any 3-digit CVV, and any name.
5. Receive the webhook
Register a webhook endpoint from Dashboard → Developers → Webhooks. Then verify the signature on your server:
ts
import { Minnha, MinnhaSignatureError } from "@minnha/node";
app.post("/webhooks/minnha", express.raw({ type: "application/json" }), (req, res) => {
try {
const event = Minnha.Webhooks.parse(
req.body,
req.header("x-minnha-signature")!,
process.env.MINNHA_WEBHOOK_SECRET!
);
if (event.event === "payment.success") {
// mark order paid
}
res.status(200).end();
} catch (err) {
if (err instanceof MinnhaSignatureError) return res.status(400).send("bad signature");
throw err;
}
});