Skip to main content
This page is part of the Payments Library Guides. Prefer direct API calls instead? See REST API Guides.
Prerequisites: API key, Payment Gateway Account, and eWallet Account configured. This page provides a complete working example showing how to integrate the Orchestra Payments Library from server to client.

View on GitHub

Clone the complete example project

Server-Side: Create Session

Your server creates a session with the Orchestra API and returns the token to the client.
const express = require('express');
const app = express();

// eWallet account IDs from environment variables
const eWalletAccounts = {
  cardPay: process.env.EWALLET_CARDPAY_ACCOUNT_ID,
  googlePay: process.env.EWALLET_GOOGLEPAY_ACCOUNT_ID,
  applePay: process.env.EWALLET_APPLEPAY_ACCOUNT_ID,
  payPal: process.env.EWALLET_PAYPAL_ACCOUNT_ID,
};

// Build array of only the configured account IDs
// Note: This helper is for the example's flexibility. In practice, you would
// simply list your eWallet account names directly in the request, e.g.:
// allowedeWalletAccountIds: ['my-cardpay-account', 'my-paypal-account']
function getConfiguredEWalletAccountIds() {
  return Object.values(eWalletAccounts).filter(Boolean);
}

app.post('/api/create-session', async (req, res) => {
  const response = await fetch('https://api.orchestrasolutions.com/EWalletOperations', {
    method: 'POST',
    headers: {
      'X-Api-Key': process.env.ORCHESTRA_API_KEY,
      'Content-Type': 'application/json'
    },
    body: JSON.stringify({
      operation: 'CHARGE',
      paymentGatewayAccountId: process.env.PAYMENT_GATEWAY_ACCOUNT_ID,
      allowedeWalletAccountIds: getConfiguredEWalletAccountIds(),
      allowedBrands: ['VISA', 'MASTERCARD', 'AMEX'],
      currencyCode: 'USD',
      countryCode: 'US',
      amount: 49.99,
      mode: 'TEST'
    })
  });

  const data = await response.json();
  res.json({ sessionToken: data.token });
});

app.listen(3000);

Client-Side: HTML

Create container elements for each payment method you want to display:
<!DOCTYPE html>
<html>
<head>
  <title>Checkout</title>
</head>
<body>
  <h1>Complete Your Purchase</h1>
  <p>Total: $<span id="amount">49.99</span></p>

  <!-- Each payment method needs its own container -->
  <div id="card-button"></div>
  <div id="gpay-button"></div>
  <div id="applepay-button"></div>
  <div id="paypal-button"></div>

  <div id="result"></div>

  <script src="https://cdn.jsdelivr.net/npm/bluetime-ewallet@latest/dist/index.js"></script>
  <script src="checkout.js"></script>
</body>
</html>

Client-Side: JavaScript

Initialize the library and render payment buttons:
// checkout.js

let engine = null;

async function initPayment() {
  // 1. Get session token from your server
  const response = await fetch('/api/create-session', { method: 'POST' });
  const { sessionToken } = await response.json();

  // 2. Initialize the engine
  engine = new eWallet.Engine(sessionToken);

  // 3. Check which payment methods are available
  const available = await engine.checkAvailability();
  console.log('Available payment methods:', available);

  // 4. Build list of buttons to display
  const allButtons = [
    { name: 'CardPay', domEntitySelector: '#card-button' },
    { name: 'GooglePay', domEntitySelector: '#gpay-button' },
    { name: 'ApplePay', domEntitySelector: '#applepay-button' },
    { name: 'PayPal', domEntitySelector: '#paypal-button' }
  ];

  const buttons = allButtons.filter(btn => available.includes(btn.name));

  // 5. Render the buttons
  engine.payBy(buttons, handleResult, { color: 'Dark', text: 'Pay' });
}

async function handleResult(result) {
  const resultEl = document.getElementById('result');

  // User cancelled
  if (!result) {
    resultEl.textContent = 'Payment cancelled';
    return;
  }

  // Parse the result token
  const [data, success] = engine.parseResultToken(result.token);
  console.log('Payment result:', data);

  // Check if payment succeeded
  if (!data.clientSuccess) {
    resultEl.textContent = 'Payment failed: ' + (data.clientErrorMessage || 'Unknown error');
    return;
  }

  // Handle PSP charge results (CardPay, GooglePay, ApplePay)
  if (data.upgChargeResults) {
    if (data.upgChargeResults.operationResultCode === 'Success') {
      resultEl.innerHTML = `
        <strong>Payment successful!</strong><br>
        Gateway: ${data.upgChargeResults.gatewayName}<br>
        Reference: ${data.upgChargeResults.gatewayReference}<br>
        Amount: ${data.upgChargeResults.amount} ${data.upgChargeResults.currency}
      `;
    } else {
      resultEl.textContent = 'Payment declined: ' + (data.upgChargeResults.operationResultDescription || data.upgChargeResults.operationResultCode);
      return;
    }
  }

  // Handle direct charge results (PayPal, BankPay)
  if (data.directChargeResults) {
    if (data.directChargeResults.success) {
      resultEl.innerHTML = '<strong>Payment successful!</strong><br>Provider: PayPal';
    } else {
      resultEl.textContent = 'Payment failed: ' + data.directChargeResults.message;
      return;
    }
  }

  // Server-side validation (recommended for production)
  try {
    const validationResponse = await fetch('/api/validate-payment', {
      method: 'POST',
      headers: { 'Content-Type': 'application/json' },
      body: JSON.stringify({ resultToken: result.token })
    });

    if (validationResponse.ok) {
      const validationResult = await validationResponse.json();
      console.log('Server validation:', validationResult);
    }
  } catch (error) {
    console.warn('Could not reach server for validation:', error.message);
  }
}

// Start when page loads
document.addEventListener('DOMContentLoaded', initPayment);

Server-Side: Validate Results

After a successful payment, validate the result token with Orchestra to confirm the payment:
app.post('/api/validate-payment', async (req, res) => {
  const { resultToken } = req.body;

  const response = await fetch('https://api.orchestrasolutions.com/EWalletOperations/validateResults', {
    method: 'POST',
    headers: {
      'X-Api-Key': process.env.ORCHESTRA_API_KEY,
      'Content-Type': 'application/json'
    },
    body: JSON.stringify(resultToken)
  });

  const validationResult = await response.json();

  if (validationResult.clientSuccess) {
    // Payment confirmed - fulfill the order
    res.json({ success: true, data: validationResult });
  } else {
    res.json({ success: false, error: validationResult.clientErrorMessage });
  }
});