curl --request POST \
--url https://api.pontisglobe.com/api/v1/payouts/sendPayoutRequest \
--header 'Authorization: Bearer <token>' \
--header 'Content-Type: application/json' \
--header 'x-api-key: <api-key>' \
--header 'x-signature: <x-signature>' \
--header 'x-timestamp: <x-timestamp>' \
--data '
{
"idempotency_key": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"source_amount": "250.00",
"source_currency": "USDT",
"purpose_of_payment": "<string>",
"source_of_funds": "<string>",
"beneficiary_id": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"country_code": "NG",
"currency_code": "NGN",
"payment_method": "bank_local",
"payment_network": "<string>",
"recipient_details": {}
}
'import requests
url = "https://api.pontisglobe.com/api/v1/payouts/sendPayoutRequest"
payload = {
"idempotency_key": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"source_amount": "250.00",
"source_currency": "USDT",
"purpose_of_payment": "<string>",
"source_of_funds": "<string>",
"beneficiary_id": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"country_code": "NG",
"currency_code": "NGN",
"payment_method": "bank_local",
"payment_network": "<string>",
"recipient_details": {}
}
headers = {
"x-timestamp": "<x-timestamp>",
"x-signature": "<x-signature>",
"x-api-key": "<api-key>",
"Authorization": "Bearer <token>",
"Content-Type": "application/json"
}
response = requests.post(url, json=payload, headers=headers)
print(response.text)const options = {
method: 'POST',
headers: {
'x-timestamp': '<x-timestamp>',
'x-signature': '<x-signature>',
'x-api-key': '<api-key>',
Authorization: 'Bearer <token>',
'Content-Type': 'application/json'
},
body: JSON.stringify({
idempotency_key: '3c90c3cc-0d44-4b50-8888-8dd25736052a',
source_amount: '250.00',
source_currency: 'USDT',
purpose_of_payment: '<string>',
source_of_funds: '<string>',
beneficiary_id: '3c90c3cc-0d44-4b50-8888-8dd25736052a',
country_code: 'NG',
currency_code: 'NGN',
payment_method: 'bank_local',
payment_network: '<string>',
recipient_details: {}
})
};
fetch('https://api.pontisglobe.com/api/v1/payouts/sendPayoutRequest', options)
.then(res => res.json())
.then(res => console.log(res))
.catch(err => console.error(err));<?php
$curl = curl_init();
curl_setopt_array($curl, [
CURLOPT_URL => "https://api.pontisglobe.com/api/v1/payouts/sendPayoutRequest",
CURLOPT_RETURNTRANSFER => true,
CURLOPT_ENCODING => "",
CURLOPT_MAXREDIRS => 10,
CURLOPT_TIMEOUT => 30,
CURLOPT_HTTP_VERSION => CURL_HTTP_VERSION_1_1,
CURLOPT_CUSTOMREQUEST => "POST",
CURLOPT_POSTFIELDS => json_encode([
'idempotency_key' => '3c90c3cc-0d44-4b50-8888-8dd25736052a',
'source_amount' => '250.00',
'source_currency' => 'USDT',
'purpose_of_payment' => '<string>',
'source_of_funds' => '<string>',
'beneficiary_id' => '3c90c3cc-0d44-4b50-8888-8dd25736052a',
'country_code' => 'NG',
'currency_code' => 'NGN',
'payment_method' => 'bank_local',
'payment_network' => '<string>',
'recipient_details' => [
]
]),
CURLOPT_HTTPHEADER => [
"Authorization: Bearer <token>",
"Content-Type: application/json",
"x-api-key: <api-key>",
"x-signature: <x-signature>",
"x-timestamp: <x-timestamp>"
],
]);
$response = curl_exec($curl);
$err = curl_error($curl);
curl_close($curl);
if ($err) {
echo "cURL Error #:" . $err;
} else {
echo $response;
}package main
import (
"fmt"
"strings"
"net/http"
"io"
)
func main() {
url := "https://api.pontisglobe.com/api/v1/payouts/sendPayoutRequest"
payload := strings.NewReader("{\n \"idempotency_key\": \"3c90c3cc-0d44-4b50-8888-8dd25736052a\",\n \"source_amount\": \"250.00\",\n \"source_currency\": \"USDT\",\n \"purpose_of_payment\": \"<string>\",\n \"source_of_funds\": \"<string>\",\n \"beneficiary_id\": \"3c90c3cc-0d44-4b50-8888-8dd25736052a\",\n \"country_code\": \"NG\",\n \"currency_code\": \"NGN\",\n \"payment_method\": \"bank_local\",\n \"payment_network\": \"<string>\",\n \"recipient_details\": {}\n}")
req, _ := http.NewRequest("POST", url, payload)
req.Header.Add("x-timestamp", "<x-timestamp>")
req.Header.Add("x-signature", "<x-signature>")
req.Header.Add("x-api-key", "<api-key>")
req.Header.Add("Authorization", "Bearer <token>")
req.Header.Add("Content-Type", "application/json")
res, _ := http.DefaultClient.Do(req)
defer res.Body.Close()
body, _ := io.ReadAll(res.Body)
fmt.Println(string(body))
}HttpResponse<String> response = Unirest.post("https://api.pontisglobe.com/api/v1/payouts/sendPayoutRequest")
.header("x-timestamp", "<x-timestamp>")
.header("x-signature", "<x-signature>")
.header("x-api-key", "<api-key>")
.header("Authorization", "Bearer <token>")
.header("Content-Type", "application/json")
.body("{\n \"idempotency_key\": \"3c90c3cc-0d44-4b50-8888-8dd25736052a\",\n \"source_amount\": \"250.00\",\n \"source_currency\": \"USDT\",\n \"purpose_of_payment\": \"<string>\",\n \"source_of_funds\": \"<string>\",\n \"beneficiary_id\": \"3c90c3cc-0d44-4b50-8888-8dd25736052a\",\n \"country_code\": \"NG\",\n \"currency_code\": \"NGN\",\n \"payment_method\": \"bank_local\",\n \"payment_network\": \"<string>\",\n \"recipient_details\": {}\n}")
.asString();require 'uri'
require 'net/http'
url = URI("https://api.pontisglobe.com/api/v1/payouts/sendPayoutRequest")
http = Net::HTTP.new(url.host, url.port)
http.use_ssl = true
request = Net::HTTP::Post.new(url)
request["x-timestamp"] = '<x-timestamp>'
request["x-signature"] = '<x-signature>'
request["x-api-key"] = '<api-key>'
request["Authorization"] = 'Bearer <token>'
request["Content-Type"] = 'application/json'
request.body = "{\n \"idempotency_key\": \"3c90c3cc-0d44-4b50-8888-8dd25736052a\",\n \"source_amount\": \"250.00\",\n \"source_currency\": \"USDT\",\n \"purpose_of_payment\": \"<string>\",\n \"source_of_funds\": \"<string>\",\n \"beneficiary_id\": \"3c90c3cc-0d44-4b50-8888-8dd25736052a\",\n \"country_code\": \"NG\",\n \"currency_code\": \"NGN\",\n \"payment_method\": \"bank_local\",\n \"payment_network\": \"<string>\",\n \"recipient_details\": {}\n}"
response = http.request(request)
puts response.read_body{
"ok": true,
"data": {
"transaction_id": "029b2038-6166-4bea-80a9-f1a2425a85eb",
"status": "pending"
}
}{
"ok": false,
"request_id": "8c1f4b2a-9d3e-4a71-b6c8-5e2f0a7d1934",
"error": {
"code": "insufficient_funds",
"message": "Insufficient available balance. Available: 5.00 USDT"
}
}{
"ok": false,
"request_id": "8c1f4b2a-9d3e-4a71-b6c8-5e2f0a7d1934",
"error": {
"code": "insufficient_funds",
"message": "Insufficient available balance. Available: 5.00 USDT"
}
}{
"ok": false,
"request_id": "8c1f4b2a-9d3e-4a71-b6c8-5e2f0a7d1934",
"error": {
"code": "insufficient_funds",
"message": "Insufficient available balance. Available: 5.00 USDT"
}
}{
"ok": false,
"request_id": "8c1f4b2a-9d3e-4a71-b6c8-5e2f0a7d1934",
"error": {
"code": "insufficient_funds",
"message": "Insufficient available balance. Available: 5.00 USDT"
}
}{
"ok": false,
"request_id": "8c1f4b2a-9d3e-4a71-b6c8-5e2f0a7d1934",
"error": {
"code": "insufficient_funds",
"message": "Insufficient available balance. Available: 5.00 USDT"
}
}{
"ok": false,
"request_id": "8c1f4b2a-9d3e-4a71-b6c8-5e2f0a7d1934",
"error": {
"code": "insufficient_funds",
"message": "Insufficient available balance. Available: 5.00 USDT"
}
}{
"ok": false,
"request_id": "8c1f4b2a-9d3e-4a71-b6c8-5e2f0a7d1934",
"error": {
"code": "insufficient_funds",
"message": "Insufficient available balance. Available: 5.00 USDT"
}
}/api/v1/payouts/sendPayoutRequest
Create a transaction. Quote, limits check, and creation happen in one call.
curl --request POST \
--url https://api.pontisglobe.com/api/v1/payouts/sendPayoutRequest \
--header 'Authorization: Bearer <token>' \
--header 'Content-Type: application/json' \
--header 'x-api-key: <api-key>' \
--header 'x-signature: <x-signature>' \
--header 'x-timestamp: <x-timestamp>' \
--data '
{
"idempotency_key": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"source_amount": "250.00",
"source_currency": "USDT",
"purpose_of_payment": "<string>",
"source_of_funds": "<string>",
"beneficiary_id": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"country_code": "NG",
"currency_code": "NGN",
"payment_method": "bank_local",
"payment_network": "<string>",
"recipient_details": {}
}
'import requests
url = "https://api.pontisglobe.com/api/v1/payouts/sendPayoutRequest"
payload = {
"idempotency_key": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"source_amount": "250.00",
"source_currency": "USDT",
"purpose_of_payment": "<string>",
"source_of_funds": "<string>",
"beneficiary_id": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"country_code": "NG",
"currency_code": "NGN",
"payment_method": "bank_local",
"payment_network": "<string>",
"recipient_details": {}
}
headers = {
"x-timestamp": "<x-timestamp>",
"x-signature": "<x-signature>",
"x-api-key": "<api-key>",
"Authorization": "Bearer <token>",
"Content-Type": "application/json"
}
response = requests.post(url, json=payload, headers=headers)
print(response.text)const options = {
method: 'POST',
headers: {
'x-timestamp': '<x-timestamp>',
'x-signature': '<x-signature>',
'x-api-key': '<api-key>',
Authorization: 'Bearer <token>',
'Content-Type': 'application/json'
},
body: JSON.stringify({
idempotency_key: '3c90c3cc-0d44-4b50-8888-8dd25736052a',
source_amount: '250.00',
source_currency: 'USDT',
purpose_of_payment: '<string>',
source_of_funds: '<string>',
beneficiary_id: '3c90c3cc-0d44-4b50-8888-8dd25736052a',
country_code: 'NG',
currency_code: 'NGN',
payment_method: 'bank_local',
payment_network: '<string>',
recipient_details: {}
})
};
fetch('https://api.pontisglobe.com/api/v1/payouts/sendPayoutRequest', options)
.then(res => res.json())
.then(res => console.log(res))
.catch(err => console.error(err));<?php
$curl = curl_init();
curl_setopt_array($curl, [
CURLOPT_URL => "https://api.pontisglobe.com/api/v1/payouts/sendPayoutRequest",
CURLOPT_RETURNTRANSFER => true,
CURLOPT_ENCODING => "",
CURLOPT_MAXREDIRS => 10,
CURLOPT_TIMEOUT => 30,
CURLOPT_HTTP_VERSION => CURL_HTTP_VERSION_1_1,
CURLOPT_CUSTOMREQUEST => "POST",
CURLOPT_POSTFIELDS => json_encode([
'idempotency_key' => '3c90c3cc-0d44-4b50-8888-8dd25736052a',
'source_amount' => '250.00',
'source_currency' => 'USDT',
'purpose_of_payment' => '<string>',
'source_of_funds' => '<string>',
'beneficiary_id' => '3c90c3cc-0d44-4b50-8888-8dd25736052a',
'country_code' => 'NG',
'currency_code' => 'NGN',
'payment_method' => 'bank_local',
'payment_network' => '<string>',
'recipient_details' => [
]
]),
CURLOPT_HTTPHEADER => [
"Authorization: Bearer <token>",
"Content-Type: application/json",
"x-api-key: <api-key>",
"x-signature: <x-signature>",
"x-timestamp: <x-timestamp>"
],
]);
$response = curl_exec($curl);
$err = curl_error($curl);
curl_close($curl);
if ($err) {
echo "cURL Error #:" . $err;
} else {
echo $response;
}package main
import (
"fmt"
"strings"
"net/http"
"io"
)
func main() {
url := "https://api.pontisglobe.com/api/v1/payouts/sendPayoutRequest"
payload := strings.NewReader("{\n \"idempotency_key\": \"3c90c3cc-0d44-4b50-8888-8dd25736052a\",\n \"source_amount\": \"250.00\",\n \"source_currency\": \"USDT\",\n \"purpose_of_payment\": \"<string>\",\n \"source_of_funds\": \"<string>\",\n \"beneficiary_id\": \"3c90c3cc-0d44-4b50-8888-8dd25736052a\",\n \"country_code\": \"NG\",\n \"currency_code\": \"NGN\",\n \"payment_method\": \"bank_local\",\n \"payment_network\": \"<string>\",\n \"recipient_details\": {}\n}")
req, _ := http.NewRequest("POST", url, payload)
req.Header.Add("x-timestamp", "<x-timestamp>")
req.Header.Add("x-signature", "<x-signature>")
req.Header.Add("x-api-key", "<api-key>")
req.Header.Add("Authorization", "Bearer <token>")
req.Header.Add("Content-Type", "application/json")
res, _ := http.DefaultClient.Do(req)
defer res.Body.Close()
body, _ := io.ReadAll(res.Body)
fmt.Println(string(body))
}HttpResponse<String> response = Unirest.post("https://api.pontisglobe.com/api/v1/payouts/sendPayoutRequest")
.header("x-timestamp", "<x-timestamp>")
.header("x-signature", "<x-signature>")
.header("x-api-key", "<api-key>")
.header("Authorization", "Bearer <token>")
.header("Content-Type", "application/json")
.body("{\n \"idempotency_key\": \"3c90c3cc-0d44-4b50-8888-8dd25736052a\",\n \"source_amount\": \"250.00\",\n \"source_currency\": \"USDT\",\n \"purpose_of_payment\": \"<string>\",\n \"source_of_funds\": \"<string>\",\n \"beneficiary_id\": \"3c90c3cc-0d44-4b50-8888-8dd25736052a\",\n \"country_code\": \"NG\",\n \"currency_code\": \"NGN\",\n \"payment_method\": \"bank_local\",\n \"payment_network\": \"<string>\",\n \"recipient_details\": {}\n}")
.asString();require 'uri'
require 'net/http'
url = URI("https://api.pontisglobe.com/api/v1/payouts/sendPayoutRequest")
http = Net::HTTP.new(url.host, url.port)
http.use_ssl = true
request = Net::HTTP::Post.new(url)
request["x-timestamp"] = '<x-timestamp>'
request["x-signature"] = '<x-signature>'
request["x-api-key"] = '<api-key>'
request["Authorization"] = 'Bearer <token>'
request["Content-Type"] = 'application/json'
request.body = "{\n \"idempotency_key\": \"3c90c3cc-0d44-4b50-8888-8dd25736052a\",\n \"source_amount\": \"250.00\",\n \"source_currency\": \"USDT\",\n \"purpose_of_payment\": \"<string>\",\n \"source_of_funds\": \"<string>\",\n \"beneficiary_id\": \"3c90c3cc-0d44-4b50-8888-8dd25736052a\",\n \"country_code\": \"NG\",\n \"currency_code\": \"NGN\",\n \"payment_method\": \"bank_local\",\n \"payment_network\": \"<string>\",\n \"recipient_details\": {}\n}"
response = http.request(request)
puts response.read_body{
"ok": true,
"data": {
"transaction_id": "029b2038-6166-4bea-80a9-f1a2425a85eb",
"status": "pending"
}
}{
"ok": false,
"request_id": "8c1f4b2a-9d3e-4a71-b6c8-5e2f0a7d1934",
"error": {
"code": "insufficient_funds",
"message": "Insufficient available balance. Available: 5.00 USDT"
}
}{
"ok": false,
"request_id": "8c1f4b2a-9d3e-4a71-b6c8-5e2f0a7d1934",
"error": {
"code": "insufficient_funds",
"message": "Insufficient available balance. Available: 5.00 USDT"
}
}{
"ok": false,
"request_id": "8c1f4b2a-9d3e-4a71-b6c8-5e2f0a7d1934",
"error": {
"code": "insufficient_funds",
"message": "Insufficient available balance. Available: 5.00 USDT"
}
}{
"ok": false,
"request_id": "8c1f4b2a-9d3e-4a71-b6c8-5e2f0a7d1934",
"error": {
"code": "insufficient_funds",
"message": "Insufficient available balance. Available: 5.00 USDT"
}
}{
"ok": false,
"request_id": "8c1f4b2a-9d3e-4a71-b6c8-5e2f0a7d1934",
"error": {
"code": "insufficient_funds",
"message": "Insufficient available balance. Available: 5.00 USDT"
}
}{
"ok": false,
"request_id": "8c1f4b2a-9d3e-4a71-b6c8-5e2f0a7d1934",
"error": {
"code": "insufficient_funds",
"message": "Insufficient available balance. Available: 5.00 USDT"
}
}{
"ok": false,
"request_id": "8c1f4b2a-9d3e-4a71-b6c8-5e2f0a7d1934",
"error": {
"code": "insufficient_funds",
"message": "Insufficient available balance. Available: 5.00 USDT"
}
}{ "data": "<aes-256-gcm ciphertext>" } — see Authentication.beneficiary_id for a saved
recipient, or the full corridor plus recipient_details inline.
Sending both is a validation error, not a merge.Example request
import { randomUUID } from 'node:crypto'
const payout = await call(
'/api/v1/payouts/sendPayoutRequest',
{
idempotency_key: randomUUID(),
country_code: 'IN',
currency_code: 'INR',
payment_method: 'imps',
source_amount: '10.00',
source_currency: 'USDT',
recipient_details: {
name: 'Jane Doe',
account_number: '123456789012',
ifsc: 'BANK0000001',
customer_email: 'recipient@example.com',
customer_phone: '+919999999999',
},
},
jwt,
)
import uuid
status, body = call('/api/v1/payouts/sendPayoutRequest', {
'idempotency_key': str(uuid.uuid4()),
'country_code': 'IN',
'currency_code': 'INR',
'payment_method': 'imps',
'source_amount': '10.00',
'source_currency': 'USDT',
'recipient_details': {
'name': 'Jane Doe',
'account_number': '123456789012',
'ifsc': 'BANK0000001',
'customer_email': 'recipient@example.com',
'customer_phone': '+919999999999',
},
}, jwt)
curl -X POST "https://api.pontisglobe.com/api/v1/payouts/sendPayoutRequest" \
-H "content-type: application/json" \
-H "x-api-key: YOUR_API_KEY" \
-H "x-timestamp: 1748023400" \
-H "x-signature: 2f8a9b…" \
-H "authorization: Bearer eyJhbGciOi…" \
-d '{"data":"<encrypted blob>"}'
req, _ := http.NewRequest("POST",
"https://api.pontisglobe.com/api/v1/payouts/sendPayoutRequest",
strings.NewReader(`{"data":"`+encryptedBody+`"}`))
req.Header.Set("content-type", "application/json")
req.Header.Set("x-api-key", apiKey)
req.Header.Set("x-timestamp", timestamp)
req.Header.Set("x-signature", signature)
req.Header.Set("authorization", "Bearer "+jwt)
res, _ := http.DefaultClient.Do(req)
HttpRequest req = HttpRequest.newBuilder()
.uri(URI.create("https://api.pontisglobe.com/api/v1/payouts/sendPayoutRequest"))
.header("content-type", "application/json")
.header("x-api-key", apiKey)
.header("x-timestamp", timestamp)
.header("x-signature", signature)
.header("authorization", "Bearer " + jwt)
.POST(HttpRequest.BodyPublishers.ofString("{\"data\":\"" + encryptedBody + "\"}"))
.build();
HttpResponse<String> res = HttpClient.newHttpClient().send(req, BodyHandlers.ofString());
val req = Request.Builder()
.url("https://api.pontisglobe.com/api/v1/payouts/sendPayoutRequest")
.post("""{"data":"$encryptedBody"}""".toRequestBody("application/json".toMediaType()))
.addHeader("x-api-key", apiKey)
.addHeader("x-timestamp", timestamp)
.addHeader("x-signature", signature)
.addHeader("authorization", "Bearer $jwt")
.build()
val res = OkHttpClient().newCall(req).execute()
$ch = curl_init('https://api.pontisglobe.com/api/v1/payouts/sendPayoutRequest');
curl_setopt_array($ch, [
CURLOPT_POST => true,
CURLOPT_HTTPHEADER => [
'content-type: application/json',
"x-api-key: $apiKey",
"x-timestamp: $timestamp",
"x-signature: $signature",
"authorization: Bearer $jwt",
],
CURLOPT_POSTFIELDS => json_encode(['data' => $encryptedBody]),
CURLOPT_RETURNTRANSFER => true,
]);
$res = curl_exec($ch);
uri = URI('https://api.pontisglobe.com/api/v1/payouts/sendPayoutRequest')
req = Net::HTTP::Post.new(uri, {
'content-type' => 'application/json',
'x-api-key' => api_key,
'x-timestamp' => timestamp,
'x-signature' => signature,
'authorization' => "Bearer #{jwt}",
})
req.body = { data: encrypted_body }.to_json
res = Net::HTTP.start(uri.hostname, uri.port, use_ssl: true) { |http| http.request(req) }
var req = new HttpRequestMessage(HttpMethod.Post,
"https://api.pontisglobe.com/api/v1/payouts/sendPayoutRequest");
req.Headers.Add("x-api-key", apiKey);
req.Headers.Add("x-timestamp", timestamp);
req.Headers.Add("x-signature", signature);
req.Headers.Add("authorization", $"Bearer {jwt}");
req.Content = new StringContent($"{{\"data\":\"{encryptedBody}\"}}",
Encoding.UTF8, "application/json");
var res = await new HttpClient().SendAsync(req);
var req = URLRequest(url: URL(string: "https://api.pontisglobe.com/api/v1/payouts/sendPayoutRequest")!)
req.httpMethod = "POST"
req.setValue("application/json", forHTTPHeaderField: "content-type")
req.setValue(apiKey, forHTTPHeaderField: "x-api-key")
req.setValue(timestamp, forHTTPHeaderField: "x-timestamp")
req.setValue(signature, forHTTPHeaderField: "x-signature")
req.setValue("Bearer \(jwt)", forHTTPHeaderField: "authorization")
req.httpBody = #"{"data":"\#(encryptedBody)"}"#.data(using: .utf8)
let (data, _) = try await URLSession.shared.data(for: req)
Recipient details
The shape ofrecipient_details depends on payment_method. Every method
requires name (the recipient’s full name, max 200 chars). Additional fields
per method are listed below.
imps / rtgs / neft — India bank transfer (INR)
For payment_method: "imps", send the following inside recipient_details.
The API picks the underlying rail (IMPS, RTGS, or NEFT) automatically based on
the amount and bank availability.
| Field | Type | Required | Notes |
|---|---|---|---|
name | string (max 200) | yes | Recipient’s full name as on the bank account |
account_number | string | yes | 9–18 digits |
ifsc | string | yes | 11-char IFSC — uppercase; format AAAA0BBBBBB (e.g. BANK0000001) |
customer_email | string | yes | Valid email address |
customer_phone | string | yes | E.164 format (e.g. +919999999999) |
bank_name | string | no | Free text, max 120 chars |
{
"idempotency_key": "f0e9d8c7-b6a5-4321-9876-0123456789ab",
"country_code": "IN",
"currency_code": "INR",
"payment_method": "imps",
"source_amount": "100.00",
"source_currency": "USDT",
"recipient_details": {
"name": "Jane Doe",
"account_number": "123456789012",
"ifsc": "BANK0000001",
"customer_email": "recipient@example.com",
"customer_phone": "+919999999999"
}
}
validation_error pointing at the offending field — for example:
{
"ok": false,
"error": {
"code": "validation_error",
"message": "'recipient_details.customer_email' is required"
}
}
Reading the outcome
pending_approval is not a failure. It means the amount exceeds your auto-approval limit and a
human on your account has to release it. The payout proceeds normally once they do.
A 422 means a business rule refused the payout, and the code tells you which:
| Code | When |
|---|---|
insufficient_funds | Wallet balance is too low |
daily_limit_exceeded | Today’s volume would exceed your daily cap |
monthly_limit_exceeded | This month’s volume would exceed your monthly cap |
fee_exceeds_amount | The fee exceeds the send amount — try a larger amount |
rate_moved | Exchange rate moved more than 0.5% since the quote was issued — retry |
screening_failed | Recipient failed sanctions screening |
rate_moved is worth retrying automatically. The rest need something to change first.
A 404 is no_route — that country/currency/method combination is not enabled on your account.
Full code list in Errors.
Sandbox tip
In sandbox, the trailing cents ofsource_amount decide the eventual status — see Sandbox.Authorizations
Identifies your account. Issued from Developer Tools in the dashboard.
Short-lived token from /api/v1/user/login, bound to your account and
mode. Expires in 900 seconds.
Headers
Unix epoch in seconds — not milliseconds. Must be within ±5 minutes of our clock, which is what makes a captured request unusable later. Keep your client's clock NTP-synced.
1748023400
HMAC-SHA256 over the signing string, hex encoded. The timestamp is part of what is signed, so a replayed body cannot be re-dated. See https://docs.pontisglobe.com/authentication for how it is built.
"2f8a9b4c1d7e0a3f6b8c2d5e9f1a4b7c0d3e6f9a2b5c8d1e4f7a0b3c6d9e2f5a"
Body
A positive decimal string. Never send a float — precision is the whole point, and a JSON number cannot hold these exactly.
^\d+(\.\d+)?$"250.00"
Send this explicitly rather than relying on the default. The supported set grows; code written against it keeps working.
2 - 8200200Beneficiary mode. Mutually exclusive with the fields below.
2"NG"
2 - 8"NGN"
1 - 32"bank_local"
32Per-corridor fields, plus name. Required fields vary by corridor —
do not assume a fixed recipient shape.