Docs v1
API Operational
Login Merchant

API Reference ZANNPAY

Integrasi API ZANNPAY menggunakan arsitektur Single Endpoint (`POST /v1`). Semua request dikirimkan dalam format JSON.

POST https://pay.zannstore.com/v1
Catatan Endpoint: Jenis aksi API ditentukan oleh nilai field request (contoh: request=new untuk transaksi baru, request=status untuk cek status, request=cancel untuk pembatalan).

Mode Sandbox & Production

Gunakan Mode DEV (Sandbox) untuk menguji alur integrasi dan respon API tanpa menggunakan dana riil.

Alur Pengujian Sandbox:
  • Aktifkan mode DEV via toggle di dashboard merchant.
  • Transaksi yang dibuat via API saat mode DEV aktif otomatis berstatus Sandbox.
  • Gunakan tombol Simulasikan Pembayaran Berhasil di invoice Sandbox untuk menguji notifikasi Webhook ke server Anda.

Otentikasi & Signature

Setiap request API wajib menyertakan parameter merchant ID dan signature SHA-256.

1. Formula Signature Transaksi (`new`, `status`, `cancel`):

SHA-256 FORMULA
signature = sha256(merchant + secret_key + trx_id)

2. Formula Signature Penarikan (`withdraw_auto`):

WITHDRAW SHA-256 FORMULA
signature = sha256(merchant + pin)

Gabungkan string parameter di atas tanpa spasi, lalu hitung hash SHA-256 dalam format huruf kecil (*lowercase*).

Signature Calculator

Kalkulator instan untuk menguji hasil perhitungan SHA-256 signature:

Hasil Hash SHA-256:
Menghitung...

1. Buat Transaksi Baru (`request: "new"`)

Gunakan parameter request = "new" untuk menghasilkan transaksi dan QRIS / Link pembayaran baru.

Parameter Request (POST /v1):

Field Name Type Status Deskripsi & Ketentuan
request string REQUIRED Wajib diisi string "new"
merchant string REQUIRED Merchant ID terdaftar Anda (cth: MERCHANT123)
trx_id string REQUIRED ID Transaksi unik dari sistem toko Anda (cth: INV-1001)
payment string REQUIRED Kode pembayaran (cth: QRISNB, BRIVA, ALFAMART)
amount integer REQUIRED Nominal transaksi dalam Rupiah (minimal 1000)
note string REQUIRED Catatan pesanan (cth: Pembayaran Invoice #1001)
expired_time string REQUIRED Masa berlaku transaksi (cth: 30m, 1h, 24h)
type_fee string REQUIRED Beban biaya: "user" (pelanggan) atau "merchant"
callback_url string REQUIRED URL Webhook merchant tempat menerima status sukses
customer_name string OPTIONAL Nama pembeli (Opsional. Default: Nama Toko Anda)
return_url string OPTIONAL URL pengalihan otomatis setelah sukses bayar (Opsional. Default: https://pay.zannstore.com)
signature string REQUIRED Hash sha256(merchant + secret_key + trx_id)

Contoh Integrasi Kode:

curl -X POST https://pay.zannstore.com/v1 \
  -H "Content-Type: application/json" \
  -d '{
    "request": "new",
    "merchant": "MERCHANT123",
    "trx_id": "INV-1001",
    "payment": "QRISNB",
    "amount": 10000,
    "customer_name": "I Putu Anantha Saputra",
    "note": "Pembayaran Tagihan INV-1001",
    "expired_time": "30m",
    "type_fee": "user",
    "return_url": "https://tokoanda.com/sukses",
    "callback_url": "https://tokoanda.com/api/callback",
    "signature": "HASIL_SHA256_SIGNATURE"
  }'
<?php
$merchant = "MERCHANT123";
$secretKey = "your_secret_key_here";
$trxId = "INV-1001";
$signature = hash('sha256', $merchant . $secretKey . $trxId);

$payload = [
    "request"       => "new",
    "merchant"      => $merchant,
    "trx_id"        => $trxId,
    "payment"       => "QRISNB",
    "amount"        => 10000,
    "customer_name" => "I Putu Anantha Saputra",
    "note"          => "Pembayaran Tagihan INV-1001",
    "expired_time"  => "30m",
    "type_fee"      => "user",
    "return_url"    => "https://tokoanda.com/sukses",
    "callback_url"  => "https://tokoanda.com/api/callback",
    "signature"     => $signature
];

$ch = curl_init("https://pay.zannstore.com/v1");
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_setopt($ch, CURLOPT_POST, true);
curl_setopt($ch, CURLOPT_POSTFIELDS, json_encode($payload));
curl_setopt($ch, CURLOPT_HTTPHEADER, ['Content-Type: application/json']);
$response = curl_exec($ch);
curl_close($ch);

echo $response;
const crypto = require('crypto');

const merchant = "MERCHANT123";
const secretKey = "your_secret_key_here";
const trxId = "INV-1001";

const signature = crypto
  .createHash('sha256')
  .update(merchant + secretKey + trxId)
  .digest('hex');

const payload = {
  request: "new",
  merchant: merchant,
  trx_id: trxId,
  payment: "QRISNB",
  amount: 10000,
  customer_name: "I Putu Anantha Saputra",
  note: "Pembayaran Tagihan INV-1001",
  expired_time: "30m",
  type_fee: "user",
  return_url: "https://tokoanda.com/sukses",
  callback_url: "https://tokoanda.com/api/callback",
  signature: signature
};

fetch('https://pay.zannstore.com/v1', {
  method: 'POST',
  headers: { 'Content-Type': 'application/json' },
  body: JSON.stringify(payload)
})
.then(res => res.json())
.then(data => console.log(data));
import hashlib
import requests

merchant = "MERCHANT123"
secret_key = "your_secret_key_here"
trx_id = "INV-1001"

raw_str = merchant + secret_key + trx_id
signature = hashlib.sha256(raw_str.encode('utf-8')).hexdigest()

payload = {
    "request": "new",
    "merchant": merchant,
    "trx_id": trx_id,
    "payment": "QRISNB",
    "amount": 10000,
    "customer_name": "I Putu Anantha Saputra",
    "note": "Pembayaran Tagihan INV-1001",
    "expired_time": "30m",
    "type_fee": "user",
    "return_url": "https://tokoanda.com/sukses",
    "callback_url": "https://tokoanda.com/api/callback",
    "signature": signature
}

res = requests.post("https://pay.zannstore.com/v1", json=payload)
print(res.json())

Contoh Response Success (HTTP 200 OK):

{
  "status": true,
  "message": "Berhasil membuat transaksi",
  "data": {
    "trx_svr": "ZP260727ABC123",
    "trx_id": "INV-1001",
    "method_code": "QRISNB",
    "method_name": "QRIS by Nationalnobu",
    "status": "Pending",
    "amount": 10000,
    "unique_code": 0,
    "diterima": 9990,
    "fee": 10,
    "type_fee": "user",
    "qr_url": "https://cekid.zannstore.com/qris/render/ZP260727ABC123",
    "qr_content": "00020101021226670016ID.CO.QRIS.WWW.NOBU...",
    "note": "Pembayaran Tagihan INV-1001",
    "checkout_url": "https://pay.zannstore.com/invoice?reffID=ZP260727ABC123&payRef=HASH",
    "expired_at": "2026-07-27 20:30:00",
    "callback_url": "https://tokoanda.com/api/callback"
  }
}
{
  "status": true,
  "message": "Berhasil membuat transaksi",
  "data": {
    "trx_svr": "ZP260727VA987",
    "trx_id": "INV-1002",
    "method_code": "BRIVA",
    "method_name": "BANK RAKYAT INDONESIA VA",
    "status": "Pending",
    "amount": 50000,
    "diterima": 50000,
    "fee": 3500,
    "type_fee": "user",
    "virtual_account": "8881008123456789",
    "note": "Pembayaran Tagihan INV-1002",
    "checkout_url": "https://pay.zannstore.com/invoice?reffID=ZP260727VA987&payRef=HASH",
    "created_at": "2026-07-27 20:00:00",
    "expired_at": "2026-07-27 20:30:00",
    "callback_url": "https://tokoanda.com/api/callback"
  }
}
{
  "status": true,
  "message": "Berhasil membuat transaksi",
  "data": {
    "trx_svr": "ZP260727RET456",
    "trx_id": "INV-1003",
    "method_code": "ALFAMART",
    "method_name": "RETAIL ALFAMART",
    "status": "Pending",
    "amount": 100000,
    "diterima": 100000,
    "fee": 2500,
    "type_fee": "user",
    "payment_code": "895012345678",
    "note": "Pembayaran Tagihan INV-1003",
    "checkout_url": "https://pay.zannstore.com/invoice?reffID=ZP260727RET456&payRef=HASH",
    "created_at": "2026-07-27 20:00:00",
    "expired_at": "2026-07-27 20:30:00",
    "callback_url": "https://tokoanda.com/api/callback"
  }
}

2. Cek Status Transaksi (`request: "status"`)

Gunakan parameter request = "status" untuk memeriksa status real-time transaksi yang pernah dibuat.

Parameter Request (POST /v1):

Field Name Type Status Deskripsi
request string REQUIRED Wajib diisi string "status"
merchant string REQUIRED Merchant ID terdaftar Anda (cth: MERCHANT123)
trx_id string REQUIRED ID Transaksi dari merchant (cth: INV-1001)
signature string REQUIRED Hash sha256(merchant + secret_key + trx_id)

Contoh Response Check Status:

{
  "status": true,
  "msg": "Yeay, detail transaksi berhasil diambil",
  "data": {
    "trx_svr": "ZP260727ABC123",
    "trx_id": "INV-1001",
    "metode_name": "QRISNB",
    "status": "Success",
    "amount": 10000,
    "fee": 70,
    "diterima": 9930,
    "note": "Pembayaran Tagihan INV-1001",
    "type_fee": "user",
    "issuer_bank": "QRIS",
    "rrn": "REF123456789",
    "paid_at": "2026-07-27 19:40:12",
    "created_at": "2026-07-27 19:35:00",
    "expired_at": "2026-07-27 20:05:00"
  }
}

3. Batalkan Transaksi (`request: "cancel"`)

Gunakan parameter request = "cancel" untuk membatalkan transaksi yang berstatus Pending.

Aturan Pembatalan: Hanya transaksi Pending yang dapat dibatalkan. Transaksi yang sudah Success, Expired, atau Canceled tidak dapat dibatalkan lagi.

Parameter Request (POST /v1):

Field Name Type Status Deskripsi
request string REQUIRED Wajib diisi string "cancel"
merchant string REQUIRED Merchant ID terdaftar Anda (cth: MERCHANT123)
trx_id string REQUIRED ID Transaksi dari merchant (cth: INV-1001)
signature string REQUIRED Hash sha256(merchant + secret_key + trx_id)

4. Penarikan Otomatis (`request: "withdraw_auto"`)

Gunakan parameter request = "withdraw_auto" untuk mencairkan saldo merchant secara otomatis ke rekening bank atau e-wallet.

Pengujian di Mode Sandbox: Saat mode akun berada di DEV (Development), request withdraw akan memvalidasi PIN & signature, lalu mengembalikan respon JSON sukses tanpa memotong dana riil atau mengirimkan transaksi ke vendor bank.

Parameter Request (POST /v1):

Field Name Type Status Deskripsi
request string REQUIRED Wajib diisi string "withdraw_auto"
merchant string REQUIRED Merchant ID terdaftar Anda
pin string REQUIRED PIN Keamanan 6-digit akun Anda
amount integer REQUIRED Nominal penarikan saldo (dalam Rupiah)
type_bank string REQUIRED Jenis tujuan: "bank" atau "emoney"
tujuan string REQUIRED Nomor rekening bank / nomor HP e-wallet tujuan
bank_code string REQUIRED Kode bank / e-wallet (cth: BRI, BCA, DANA)
signature string REQUIRED Hash sha256(merchant + pin)

Spesifikasi Webhook Callback Notification

Ketika pembayaran berhasil dibayar (atau disimulasikan pada mode Sandbox), sistem ZANNPAY akan mengirimkan request POST notifikasi ke callback_url merchant.

Payload Notifikasi Webhook:

{
  "data": {
    "trx_svr": "ZP260727ABC123",
    "trx_id": "INV-1001",
    "status": "Success",
    "amount": "10000",
    "fee": "70",
    "type_fee": "user",
    "issuer_bank": "QRIS",
    "rrn": "REF123456789",
    "diterima": "10000",
    "paid_at": "2026-07-27 19:40:12"
  }
}
Respon Wajib Dari Merchant: Server merchant wajib merespon notifikasi ini dengan HTTP Status 200 OK dan body JSON: {"status": true} agar sistem mencatat bahwa notifikasi berhasil dikirimkan.

Daftar Metode Pembayaran & Bank (Dinamis)

Metode Pembayaran Aktif (Request `new`):

Kode Payment Nama Metode Pembayaran Kategori Biaya Fee Status System
QRISNB QRIS by National Nobu QRIS / E-Wallet 0.1% ACTIVE
QRISCUSTOM QRIS Custom Name QRIS / E-Wallet 0.7% + Rp 100 ACTIVE
QRIS2 QRIS Realtime Dynamic QRIS / E-Wallet 0.2% ACTIVE
QRIS QRIS by Danamon QRIS / E-Wallet 0.7% ACTIVE
BNCVA BANK NEO COMMERCE VA Virtual Account Rp 3.500 ACTIVE
BRIVA BANK RAKYAT INDONESIA VA Virtual Account Rp 3.500 ACTIVE
BSIVA BANK BSI VA Virtual Account Rp 3.500 ACTIVE
BNIVA BANK NEGARA INDONESIA VA Virtual Account Rp 3.500 ACTIVE
DANAMONVA DANAMON VA Virtual Account Rp 3.500 ACTIVE
CIMBVA CIMB NIAGA VA Virtual Account Rp 3.500 ACTIVE
MANDIRIVA BANK MANDIRI VA Virtual Account Rp 3.500 ACTIVE
MAYBANKVA BANK MAYBANK VA Virtual Account Rp 3.500 ACTIVE
MUAMALATVA BANK MUAMALAT VA Virtual Account Rp 3.500 ACTIVE
PERMATAVA BANK PERMATA VA Virtual Account Rp 3.500 ACTIVE
SINARMASVA SINARMAS VA Virtual Account Rp 3.500 ACTIVE
ALFAMART RETAIL ALFAMART Retail / Paylink Rp 2.500 ACTIVE
INDOMARET RETAIL INDOMARET Retail / Paylink Rp 2.500 ACTIVE
QRIS3 QRIS by DANA 0% QRIS / E-Wallet 0.1% INACTIVE

Daftar Status Transaksi

Nama Status Badge Indicator Penjelasan & Keterangan
Pending Pending Transaksi telah dibuat dan sedang menunggu pembayaran dari pelanggan.
Success Success Transaksi telah berhasil dibayar, saldo diteruskan ke merchant, & callback dikirim.
Expired Expired Pembayaran tidak dilakukan hingga batas waktu kedaluwarsa (expired_time) habis.
Canceled Canceled Transaksi dibatalkan secara manual oleh merchant via API request: "cancel".

Daftar Status Code & Exception Error

Status HTTP Pesan Error Penyebab & Solusi Penanganan
400 Signature tidak valid Perhitungan SHA256 signature tidak cocok. Pastikan rumus sha256(merchant + secret_key + trx_id) disusun tanpa spasi dengan huruf kecil.
400 trx_id sudah digunakan trx_id yang Anda kirimkan sudah terdaftar pada sistem. Gunakan ID unik untuk setiap transaksi baru.
403 Akun merchant diblokir Akun merchant Anda sedang dinonaktifkan oleh administrator. Hubungi tim support ZANNPAY.
404 Transaksi tidak ditemukan trx_id tidak ditemukan pada sistem saat dipanggil untuk request status atau cancel.