Hosted Checkout — Node.js

Create payment link, redirect, confirm status, and refund using Node.js fetch.

Complete Hosted Checkout flow in Node.js (18+). Your server creates a payment link, redirects the customer, then confirms payment server-side.

Prerequisites: Sandbox Setup, staging x-api-key, Node.js 18+ with native fetch.

The path is spelled /payment/checkout/intiate — not /session.

Never mark an order paid based only on arrival at successUrl. Always confirm via status API or webhook.


Architecture

sequenceDiagram
  participant Browser as Customer Browser
  participant Shop as Your Node Server
  participant API as DigetPay API
  participant Checkout as DigetPay Checkout

  Browser->>Shop: Checkout (order total)
  Shop->>API: POST /payment/checkout/intiate
  API-->>Shop: redirectUrl
  Shop->>Browser: HTTP 302 redirect
  Browser->>Checkout: Pay (card / Mada / Apple Pay)
  Checkout->>Browser: Redirect successUrl / failureUrl
  Browser->>Shop: Return to your site
  Shop->>API: GET /payment/checkout/status
  API-->>Shop: transactionStatus

Step 1 — Configuration

.env:

DIGETPAY_ENV=staging
DIGETPAY_API_KEY=your_fin_staging_key
// config/digetpay.js
const env = process.env.DIGETPAY_ENV || 'staging';
const API_BASES = {
  staging: 'https://fin-api.digetpay.com/v1',
  production: 'https://api.digetpay.com/v1',
};
export const config = {
  environment: env,
  apiKey: process.env.DIGETPAY_API_KEY || '',
  apiBase: API_BASES[env],
};
if (!config.apiKey) throw new Error('DIGETPAY_API_KEY is not set');

Step 2 — API client

// src/digetpayClient.js
import { config } from '../config/digetpay.js';

async function request(method, path, body) {
  const res = await fetch(`${config.apiBase}${path}`, {
    method,
    headers: {
      'Content-Type': 'application/json',
      'x-api-key': config.apiKey,
    },
    body: body ? JSON.stringify(body) : undefined,
  });
  const data = await res.json().catch(() => ({}));
  if (!res.ok) throw new Error(`DigetPay HTTP ${res.status}: ${JSON.stringify(data)}`);
  return data;
}

export function createPaymentLink(payload) {
  return request('POST', '/payment/checkout/intiate', payload);
}

export function getTransactionStatus(gatewayTransactionId) {
  const q = new URLSearchParams({ id: gatewayTransactionId });
  return request('GET', `/payment/checkout/status?${q}`);
}

export function processRefund(transactionId, amount) {
  return request('POST', '/payment/refund', { transactionId, amount });
}

Step 3 — Create payment link and redirect

// routes/checkout.js (Express example)
import express from 'express';
import { createPaymentLink } from '../src/digetpayClient.js';
import { config } from '../config/digetpay.js';

const router = express.Router();

router.get('/checkout', async (req, res) => {
  const isStaging = config.environment === 'staging';
  const successUrl = isStaging
    ? 'https://fin-admin.digetpay.com/pay/checkout/success'
    : 'https://yourstore.com/checkout/success';
  const failureUrl = isStaging
    ? 'https://fin-admin.digetpay.com/pay/checkout/failure'
    : 'https://yourstore.com/checkout/failure';

  try {
    const session = await createPaymentLink({
      merchantOrderId: `ORD-${Date.now()}`,
      amount: 10.0,
      currency: 'SAR',
      customerName: 'Ahmed Ali',
      customerEmail: '[email protected]',
      customerPhone: '501223324',
      successUrl,
      failureUrl,
    });
    // Store session.id in your DB before redirect
    res.redirect(302, session.redirectUrl);
  } catch (err) {
    console.error(err);
    res.status(500).send('Payment initiation failed.');
  }
});

export default router;

Apple Pay: DigetPay checkout displays Apple Pay when the customer uses Safari and customerPhone was sent. No additional Node.js code required — see Apple Pay on Hosted Checkout.


Step 4 — Handle return URLs

router.get('/checkout/success', (req, res) => {
  // Customer landed here — payment NOT confirmed yet
  const sessionId = req.query.sessionId;
  res.send('Processing your payment… We will confirm shortly.');
});

Step 5 — Confirm payment

import { getTransactionStatus } from '../src/digetpayClient.js';

const response = await getTransactionStatus('2232e99b-0257-47d5-bbfd-022c8951767f');
const content = response?.data?.content?.[0];
if (content?.transactionStatus === 'SUCCESS') {
  // Mark order paid
}

See Query Transaction Status.


Step 6 — Webhook handler

app.post('/webhooks/digetpay', express.raw({ type: 'application/json' }), (req, res) => {
  const payload = JSON.parse(req.body.toString());
  res.status(200).send('OK');
  const { transactionId, orderId, status } = payload;
  // Idempotent update — skip if already processed
  console.log('DigetPay webhook:', payload);
});

Full details: Handle Webhooks, Verify Signatures.


Step 7 — Refund

import { processRefund } from '../src/digetpayClient.js';
await processRefund('2232e99b-0257-47d5-bbfd-022c8951767f', 5.0);

Process Refund guide →


Next steps


Did this page help you?