DEV Community

Suleiman
Suleiman

Posted on

Start a Paymish payment from your backend in 10 minutes

description: Go from a new Paymish account to your first test payment using only your backend and a test key.

tags: api, fintech, node, nigeria

If you build for Nigerian users, you already know the checkout reality: cards get declined, networks drop, and plenty of customers would rather just send a transfer. This guide gets you from a new Paymish account to your first test payment, using only your backend and a test key.

You need: a Paymish account, your test keys, and Node 18+ or Python 3.9+.

Step 1: Get your test keys

Open Dashboard, Settings, API. Test keys start with pk_test_ and sk_test_ and simulate production without moving real money. Live keys start with pk_live_ and sk_live_. Your secret key lives on your server only, never in browser or mobile code.

export PAYMISH_SECRET_KEY='sk_test_...'
Enter fullscreen mode Exit fullscreen mode

Step 2: Initialize a transaction (Node)

Every request carries your secret key as a Bearer token. Amounts are strings in the currency's subunit, so kobo for NGN: 250000 is NGN 2,500.00.

// initialize.js (Node 18+)
const BASE = 'https://api.paymish.com/api/transaction-service/external/v1';

async function initializeTransaction() {
  const res = await fetch(`${BASE}/transaction-initialize`, {
    method: 'POST',
    headers: {
      Authorization: `Bearer ${process.env.PAYMISH_SECRET_KEY}`,
      'Content-Type': 'application/json',
    },
    body: JSON.stringify({
      email: 'ada@example.com',
      amount: '250000', // kobo, so NGN 2,500.00
    }),
  });

  const data = await res.json();
  if (!res.ok) throw new Error(`Paymish error ${res.status}: ${JSON.stringify(data)}`);
  return data; // { status, transactionId, message }
}

initializeTransaction().then(console.log).catch(console.error);
Enter fullscreen mode Exit fullscreen mode

The same thing in Python:

import os, requests

BASE = 'https://api.paymish.com/api/transaction-service/external/v1'

res = requests.post(
    f'{BASE}/transaction-initialize',
    headers={'Authorization': 'Bearer ' + os.environ['PAYMISH_SECRET_KEY']},
    json={'email': 'ada@example.com', 'amount': '250000'},  # kobo
    timeout=15,
)
res.raise_for_status()
print(res.json())  # status, transactionId, message
Enter fullscreen mode Exit fullscreen mode

Step 3: Save the transaction ID

The response includes a transactionId. Store it against your order so you can match the payment later. [CONFIRM: what the customer sees next. The docs do not show a checkout URL in this response.]

Step 4: Confirm with a webhook, not a redirect

A customer closing the page does not mean the payment failed, and reaching a success page does not mean it succeeded. Treat the signed webhook as the source of truth.

Step 5: Break it on purpose

Send an empty email, a zero amount, and a bad key. Your code should handle each error without crashing or showing raw API errors to customers.

Want to skip the hosted checkout?

Paymish can also return a one-time bank account for a customer to pay into, straight from your backend. That is covered in the next article in this series.

Docs: docs.paymish.com

Top comments (0)