AZA-ZPayA-ZPay bank-transfer API

Quickstart

This flow creates a deposit, redirects the player to A-ZPay, lets the player mark the transfer as sent, and then waits for your verified webhook.

1. Create a deposit

POST /v1/deposits
Content-Type: application/json
X-Api-Key: pk_live_xxx
X-Timestamp: 1778940000
X-Signature: <hmac sha256>
{
  "amount": "100.00",
  "currency": "TRY",
  "externalReference": "casino-deposit-1001",
  "redirectUrl": "https://casino.example/cashier/deposits/1001",
  "customer": {
    "id": "player-42",
    "username": "turbo_player",
    "fullName": "Ada Yilmaz"
  }
}
Create a deposit from your cashier
import crypto from 'node:crypto';

const baseUrl = 'https://api.azpay.example';
const apiKey = process.env.AZPAY_API_KEY;
const apiSecret = process.env.AZPAY_API_SECRET;
const hashSecret = process.env.AZPAY_HASH_SECRET;

function headers(method, path, body) {
const timestamp = Math.floor(Date.now() / 1000).toString();
const canonical = [timestamp, method, path, body, hashSecret].join('.');
const signature = crypto.createHmac('sha256', apiSecret).update(canonical).digest('hex');
return { 'content-type': 'application/json', 'x-api-key': apiKey, 'x-timestamp': timestamp, 'x-signature': signature };
}

const path = '/v1/deposits';
const body = JSON.stringify({
amount: '100.00',
currency: 'TRY',
externalReference: 'casino-deposit-1001',
redirectUrl: 'https://casino.example/cashier/deposits/1001',
customer: { id: 'player-42', username: 'turbo_player', fullName: 'Ada Yilmaz' },
});
const response = await fetch(baseUrl + path, { method: 'POST', headers: headers('POST', path, body), body });
const result = await response.json();
// Redirect the player to result.transaction.hostedUrl.
<?php
$baseUrl = 'https://api.azpay.example';
$apiKey = getenv('AZPAY_API_KEY');
$apiSecret = getenv('AZPAY_API_SECRET');
$hashSecret = getenv('AZPAY_HASH_SECRET');

function azPayHeaders(string $method, string $path, string $body): array {
  global $apiKey, $apiSecret, $hashSecret;
  $timestamp = (string) time();
  $canonical = implode('.', [$timestamp, strtoupper($method), $path, $body, $hashSecret]);
  $signature = hash_hmac('sha256', $canonical, $apiSecret);
  return ['content-type: application/json', 'x-api-key: ' . $apiKey, 'x-timestamp: ' . $timestamp, 'x-signature: ' . $signature];
}

$path = '/v1/deposits';
$payload = [
  'amount' => '100.00',
  'currency' => 'TRY',
  'externalReference' => 'casino-deposit-1001',
  'redirectUrl' => 'https://casino.example/cashier/deposits/1001',
  'customer' => ['id' => 'player-42', 'username' => 'turbo_player', 'fullName' => 'Ada Yilmaz'],
];
$body = json_encode($payload, JSON_UNESCAPED_SLASHES);
$ch = curl_init($baseUrl . $path);
curl_setopt_array($ch, [CURLOPT_POST => true, CURLOPT_HTTPHEADER => azPayHeaders('POST', $path, $body), CURLOPT_POSTFIELDS => $body, CURLOPT_RETURNTRANSFER => true]);
$result = json_decode(curl_exec($ch), true);
// Redirect the player to $result['transaction']['hostedUrl'].

2. Send the player to the hosted URL

{
  "transaction": {
    "id": "txn_...",
    "status": "waiting_payment",
    "hostedUrl": "https://pay.example/pay/txn_...",
    "redirectUrl": "https://casino.example/cashier/deposits/1001",
    "referenceCode": "BP-A1B2C3D4"
  }
}

3. Process the webhook

When a A-ZPay operator approves the transaction, your webhook receives deposit.approved. The actual received amount may differ from the requested deposit amount, so credit the player by playerAmountCents after signature verification.

Minimal webhook crediting flow
app.post('/azpay/webhook', express.raw({ type: 'application/json' }), async (req, res) => {
const eventId = req.header('x-azpay-event-id');
const body = req.body.toString('utf8');
const payload = JSON.parse(body);

if (await alreadyProcessed(eventId)) return res.sendStatus(200);
if (payload.type === 'deposit' && payload.status === 'approved') {
  await creditPlayer(payload.externalReference, payload.playerAmountCents);
}
await rememberEvent(eventId);
res.sendStatus(200);
});
<?php
$rawBody = file_get_contents('php://input');
$payload = json_decode($rawBody, true);
$eventId = $_SERVER['HTTP_X_AZPAY_EVENT_ID'] ?? '';

if (!alreadyProcessed($eventId)) {
  if ($payload['type'] === 'deposit' && $payload['status'] === 'approved') {
      creditPlayer($payload['externalReference'], $payload['playerAmountCents']);
  }
  rememberEvent($eventId);
}
http_response_code(200);

Local sandbox partner API

The local development seed creates demo partner API credentials visible inside the partner portal. Use the signed partner API headers above; do not treat browser redirects or player handoff URLs as settlement approval.