JF Pay API Reference
The JF Pay API enables merchants to create checkout sessions, receive automated payment confirmations via webhooks, and poll verification statuses programmatically. All requests require HTTPS and JSON payloads.
Base URL: https://www.payment.jfsolution-bd.com/api/v1
Authentication
Authenticate requests by including your Public Key in the Authorization: Bearer header or as X-API-KEY. For sensitive server operations, also provide X-API-SECRET.
Authorization: Bearer pk_live_your_public_key_here X-API-SECRET: sk_live_your_secret_key_here Idempotency-Key: 9b1deb4d-3b7d-4bad-9bdd-2b0d7b3dcb6d
POST
/api/v1/payment/create
Create a unique hosted payment session for customer checkout.
curl -X POST https://www.payment.jfsolution-bd.com/api/v1/payment/create \
-H "Authorization: Bearer pk_live_demo_merchant_public_key_8899" \
-H "Content-Type: application/json" \
-H "Idempotency-Key: $(uuidgen)" \
-d '{
"amount": 500.00,
"currency": "BDT",
"order_id": "ORDER-10001",
"customer": {
"name": "Rahim Ahmed",
"email": "customer@example.com",
"phone": "01700000000"
},
"return_url": "https://myshop.com/checkout/success",
"cancel_url": "https://myshop.com/checkout/cancel"
}'
use JFPay\Client\JFPayClient;
$client = new JFPayClient([
'public_key' => 'pk_live_demo_merchant_public_key_8899',
'secret_key' => 'sk_live_demo_merchant_secret_key_99887766',
'base_url' => 'https://www.payment.jfsolution-bd.com',
]);
$payment = $client->createPayment([
'amount' => 500.00,
'currency' => 'BDT',
'order_id' => 'ORDER-10001',
'customer' => ['name' => 'Rahim Ahmed', 'phone' => '01700000000'],
'return_url' => 'https://myshop.com/checkout/success',
]);
header("Location: " . $payment['checkout_url']);
exit;
const axios = require('axios');
const response = await axios.post('https://www.payment.jfsolution-bd.com/api/v1/payment/create', {
amount: 500.00,
currency: 'BDT',
order_id: 'ORDER-10001',
customer: { name: 'Rahim Ahmed', phone: '01700000000' }
}, {
headers: {
'Authorization': 'Bearer pk_live_demo_merchant_public_key_8899',
'Idempotency-Key': crypto.randomUUID()
}
});
console.log('Redirect user to:', response.data.data.checkout_url);
import requests, uuid
payload = {
"amount": 500.00,
"currency": "BDT",
"order_id": "ORDER-10001",
"customer": {"name": "Rahim Ahmed", "phone": "01700000000"}
}
headers = {
"Authorization": "Bearer pk_live_demo_merchant_public_key_8899",
"Idempotency-Key": str(uuid.uuid4())
}
r = requests.post("https://www.payment.jfsolution-bd.com/api/v1/payment/create", json=payload, headers=headers)
print("Checkout URL:", r.json()["data"]["checkout_url"])
Response (201 Created)
{
"success": true,
"message": "Payment session created successfully.",
"data": {
"session_id": "pay_9f8e7d6c5b4a3210",
"order_id": "ORDER-10001",
"amount": 500.00,
"total_payable": 500.00,
"currency": "BDT",
"payment_reference": "REF-ABC12345",
"checkout_url": "https://www.payment.jfsolution-bd.com/checkout/pay_9f8e7d6c5b4a3210",
"status": "PENDING",
"expires_at": "2026-08-25T10:30:00Z"
},
"request_id": "a1b2c3d4e5f6"
}
Webhook HMAC Signature Verification
When a payment completes verification, JF Pay sends an HTTP POST with the X-JFPay-Signature header. Verify the signature in PHP as follows:
<?php
$payload = file_get_contents('php://input');
$signatureHeader = $_SERVER['HTTP_X_JFPAY_SIGNATURE'] ?? '';
$secret = 'whsec_your_webhook_secret';
// Parse t=... and v1=...
preg_match('/t=(?<ts>[0-9]+)/', $signatureHeader, $tMatch);
preg_match('/v1=(?<hash>[a-f0-9]+)/', $signatureHeader, $vMatch);
$timestamp = $tMatch['ts'] ?? 0;
$expected = $vMatch['hash'] ?? '';
// Prevent replay attacks (tolerance 5 minutes)
if (abs(time() - $timestamp) > 300) {
http_response_code(400);
exit('Timestamp out of range');
}
$computed = hash_hmac('sha256', "{$timestamp}.{$payload}", $secret);
if (hash_equals($computed, $expected)) {
$event = json_decode($payload, true);
if ($event['event'] === 'payment.success') {
$orderId = $event['data']['order_id'];
$amount = $event['data']['amount'];
$trxId = $event['data']['transaction_id'];
// Mark order paid in database!
}
http_response_code(200);
echo "OK";
} else {
http_response_code(403);
echo "Invalid Signature";
}