curl --request POST \
--url http://localhost:3001/api/v1/business/collections \
--header 'Content-Type: application/json' \
--header 'x-api-key: <x-api-key>' \
--data '
{
"amount": 2,
"currency": "ngn",
"country": "NG",
"customer": {
"name": "<string>",
"email": "jsmith@example.com",
"phone": "<string>",
"networkId": "<string>"
},
"metadata": {},
"successUrl": "<string>",
"expiresInSeconds": 600,
"idempotencyKey": "<string>"
}
'import requests
url = "http://localhost:3001/api/v1/business/collections"
payload = {
"amount": 2,
"currency": "ngn",
"country": "NG",
"customer": {
"name": "<string>",
"email": "jsmith@example.com",
"phone": "<string>",
"networkId": "<string>"
},
"metadata": {},
"successUrl": "<string>",
"expiresInSeconds": 600,
"idempotencyKey": "<string>"
}
headers = {
"x-api-key": "<x-api-key>",
"Content-Type": "application/json"
}
response = requests.post(url, json=payload, headers=headers)
print(response.text)const options = {
method: 'POST',
headers: {'x-api-key': '<x-api-key>', 'Content-Type': 'application/json'},
body: JSON.stringify({
amount: 2,
currency: 'ngn',
country: 'NG',
customer: {
name: '<string>',
email: 'jsmith@example.com',
phone: '<string>',
networkId: '<string>'
},
metadata: {},
successUrl: '<string>',
expiresInSeconds: 600,
idempotencyKey: '<string>'
})
};
fetch('http://localhost:3001/api/v1/business/collections', options)
.then(res => res.json())
.then(res => console.log(res))
.catch(err => console.error(err));<?php
$curl = curl_init();
curl_setopt_array($curl, [
CURLOPT_PORT => "3001",
CURLOPT_URL => "http://localhost:3001/api/v1/business/collections",
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([
'amount' => 2,
'currency' => 'ngn',
'country' => 'NG',
'customer' => [
'name' => '<string>',
'email' => 'jsmith@example.com',
'phone' => '<string>',
'networkId' => '<string>'
],
'metadata' => [
],
'successUrl' => '<string>',
'expiresInSeconds' => 600,
'idempotencyKey' => '<string>'
]),
CURLOPT_HTTPHEADER => [
"Content-Type: application/json",
"x-api-key: <x-api-key>"
],
]);
$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 := "http://localhost:3001/api/v1/business/collections"
payload := strings.NewReader("{\n \"amount\": 2,\n \"currency\": \"ngn\",\n \"country\": \"NG\",\n \"customer\": {\n \"name\": \"<string>\",\n \"email\": \"jsmith@example.com\",\n \"phone\": \"<string>\",\n \"networkId\": \"<string>\"\n },\n \"metadata\": {},\n \"successUrl\": \"<string>\",\n \"expiresInSeconds\": 600,\n \"idempotencyKey\": \"<string>\"\n}")
req, _ := http.NewRequest("POST", url, payload)
req.Header.Add("x-api-key", "<x-api-key>")
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("http://localhost:3001/api/v1/business/collections")
.header("x-api-key", "<x-api-key>")
.header("Content-Type", "application/json")
.body("{\n \"amount\": 2,\n \"currency\": \"ngn\",\n \"country\": \"NG\",\n \"customer\": {\n \"name\": \"<string>\",\n \"email\": \"jsmith@example.com\",\n \"phone\": \"<string>\",\n \"networkId\": \"<string>\"\n },\n \"metadata\": {},\n \"successUrl\": \"<string>\",\n \"expiresInSeconds\": 600,\n \"idempotencyKey\": \"<string>\"\n}")
.asString();require 'uri'
require 'net/http'
url = URI("http://localhost:3001/api/v1/business/collections")
http = Net::HTTP.new(url.host, url.port)
request = Net::HTTP::Post.new(url)
request["x-api-key"] = '<x-api-key>'
request["Content-Type"] = 'application/json'
request.body = "{\n \"amount\": 2,\n \"currency\": \"ngn\",\n \"country\": \"NG\",\n \"customer\": {\n \"name\": \"<string>\",\n \"email\": \"jsmith@example.com\",\n \"phone\": \"<string>\",\n \"networkId\": \"<string>\"\n },\n \"metadata\": {},\n \"successUrl\": \"<string>\",\n \"expiresInSeconds\": 600,\n \"idempotencyKey\": \"<string>\"\n}"
response = http.request(request)
puts response.read_body{
"success": true,
"data": {
"id": "<string>",
"object": "collection",
"status": "pending",
"amount": 123,
"currency": "<string>",
"country": "<string>",
"expiresAt": "<string>",
"channel": {
"rail": "bank",
"provider": "<string>",
"channelId": "<string>",
"networkId": "<string>"
},
"instructions": {
"kind": "bank_transfer",
"bankName": "<string>",
"accountNumber": "<string>",
"accountName": "<string>",
"reference": {},
"phone": "<string>",
"prompt": "<string>",
"url": "<string>",
"provider": "<string>"
},
"businessPaymentId": "<string>",
"source": "api",
"createdAt": "<string>",
"metadata": {}
}
}{
"success": false,
"error": {
"code": "VALIDATION_ERROR",
"message": "email must be an email",
"statusCode": 400,
"errors": {}
}
}{
"success": false,
"error": {
"code": "VALIDATION_ERROR",
"message": "email must be an email",
"statusCode": 400,
"errors": {}
}
}{
"success": false,
"error": {
"code": "VALIDATION_ERROR",
"message": "email must be an email",
"statusCode": 400,
"errors": {}
}
}{
"success": false,
"error": {
"code": "VALIDATION_ERROR",
"message": "email must be an email",
"statusCode": 400,
"errors": {}
}
}{
"success": false,
"error": {
"code": "VALIDATION_ERROR",
"message": "email must be an email",
"statusCode": 400,
"errors": {}
}
}{
"success": false,
"error": {
"code": "VALIDATION_ERROR",
"message": "email must be an email",
"statusCode": 400,
"errors": {}
}
}{
"success": false,
"error": {
"code": "VALIDATION_ERROR",
"message": "email must be an email",
"statusCode": 400,
"errors": {}
}
}{
"success": false,
"error": {
"code": "VALIDATION_ERROR",
"message": "email must be an email",
"statusCode": 400,
"errors": {}
}
}Create a local-rails collection (S2S)
Starts a local bank transfer or mobile money collection and returns the instructions the customer follows to pay. The currency must be enabled on your account and the corridor priced, or the request is refused as unsupported; a momo channel additionally requires customer.phone. Send an idempotencyKey to make retries safe — a repeat returns the collection already created rather than a second one. The window defaults to 60 minutes for mobile money and 30 minutes for bank and EFT, overridable with expiresInSeconds.
curl --request POST \
--url http://localhost:3001/api/v1/business/collections \
--header 'Content-Type: application/json' \
--header 'x-api-key: <x-api-key>' \
--data '
{
"amount": 2,
"currency": "ngn",
"country": "NG",
"customer": {
"name": "<string>",
"email": "jsmith@example.com",
"phone": "<string>",
"networkId": "<string>"
},
"metadata": {},
"successUrl": "<string>",
"expiresInSeconds": 600,
"idempotencyKey": "<string>"
}
'import requests
url = "http://localhost:3001/api/v1/business/collections"
payload = {
"amount": 2,
"currency": "ngn",
"country": "NG",
"customer": {
"name": "<string>",
"email": "jsmith@example.com",
"phone": "<string>",
"networkId": "<string>"
},
"metadata": {},
"successUrl": "<string>",
"expiresInSeconds": 600,
"idempotencyKey": "<string>"
}
headers = {
"x-api-key": "<x-api-key>",
"Content-Type": "application/json"
}
response = requests.post(url, json=payload, headers=headers)
print(response.text)const options = {
method: 'POST',
headers: {'x-api-key': '<x-api-key>', 'Content-Type': 'application/json'},
body: JSON.stringify({
amount: 2,
currency: 'ngn',
country: 'NG',
customer: {
name: '<string>',
email: 'jsmith@example.com',
phone: '<string>',
networkId: '<string>'
},
metadata: {},
successUrl: '<string>',
expiresInSeconds: 600,
idempotencyKey: '<string>'
})
};
fetch('http://localhost:3001/api/v1/business/collections', options)
.then(res => res.json())
.then(res => console.log(res))
.catch(err => console.error(err));<?php
$curl = curl_init();
curl_setopt_array($curl, [
CURLOPT_PORT => "3001",
CURLOPT_URL => "http://localhost:3001/api/v1/business/collections",
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([
'amount' => 2,
'currency' => 'ngn',
'country' => 'NG',
'customer' => [
'name' => '<string>',
'email' => 'jsmith@example.com',
'phone' => '<string>',
'networkId' => '<string>'
],
'metadata' => [
],
'successUrl' => '<string>',
'expiresInSeconds' => 600,
'idempotencyKey' => '<string>'
]),
CURLOPT_HTTPHEADER => [
"Content-Type: application/json",
"x-api-key: <x-api-key>"
],
]);
$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 := "http://localhost:3001/api/v1/business/collections"
payload := strings.NewReader("{\n \"amount\": 2,\n \"currency\": \"ngn\",\n \"country\": \"NG\",\n \"customer\": {\n \"name\": \"<string>\",\n \"email\": \"jsmith@example.com\",\n \"phone\": \"<string>\",\n \"networkId\": \"<string>\"\n },\n \"metadata\": {},\n \"successUrl\": \"<string>\",\n \"expiresInSeconds\": 600,\n \"idempotencyKey\": \"<string>\"\n}")
req, _ := http.NewRequest("POST", url, payload)
req.Header.Add("x-api-key", "<x-api-key>")
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("http://localhost:3001/api/v1/business/collections")
.header("x-api-key", "<x-api-key>")
.header("Content-Type", "application/json")
.body("{\n \"amount\": 2,\n \"currency\": \"ngn\",\n \"country\": \"NG\",\n \"customer\": {\n \"name\": \"<string>\",\n \"email\": \"jsmith@example.com\",\n \"phone\": \"<string>\",\n \"networkId\": \"<string>\"\n },\n \"metadata\": {},\n \"successUrl\": \"<string>\",\n \"expiresInSeconds\": 600,\n \"idempotencyKey\": \"<string>\"\n}")
.asString();require 'uri'
require 'net/http'
url = URI("http://localhost:3001/api/v1/business/collections")
http = Net::HTTP.new(url.host, url.port)
request = Net::HTTP::Post.new(url)
request["x-api-key"] = '<x-api-key>'
request["Content-Type"] = 'application/json'
request.body = "{\n \"amount\": 2,\n \"currency\": \"ngn\",\n \"country\": \"NG\",\n \"customer\": {\n \"name\": \"<string>\",\n \"email\": \"jsmith@example.com\",\n \"phone\": \"<string>\",\n \"networkId\": \"<string>\"\n },\n \"metadata\": {},\n \"successUrl\": \"<string>\",\n \"expiresInSeconds\": 600,\n \"idempotencyKey\": \"<string>\"\n}"
response = http.request(request)
puts response.read_body{
"success": true,
"data": {
"id": "<string>",
"object": "collection",
"status": "pending",
"amount": 123,
"currency": "<string>",
"country": "<string>",
"expiresAt": "<string>",
"channel": {
"rail": "bank",
"provider": "<string>",
"channelId": "<string>",
"networkId": "<string>"
},
"instructions": {
"kind": "bank_transfer",
"bankName": "<string>",
"accountNumber": "<string>",
"accountName": "<string>",
"reference": {},
"phone": "<string>",
"prompt": "<string>",
"url": "<string>",
"provider": "<string>"
},
"businessPaymentId": "<string>",
"source": "api",
"createdAt": "<string>",
"metadata": {}
}
}{
"success": false,
"error": {
"code": "VALIDATION_ERROR",
"message": "email must be an email",
"statusCode": 400,
"errors": {}
}
}{
"success": false,
"error": {
"code": "VALIDATION_ERROR",
"message": "email must be an email",
"statusCode": 400,
"errors": {}
}
}{
"success": false,
"error": {
"code": "VALIDATION_ERROR",
"message": "email must be an email",
"statusCode": 400,
"errors": {}
}
}{
"success": false,
"error": {
"code": "VALIDATION_ERROR",
"message": "email must be an email",
"statusCode": 400,
"errors": {}
}
}{
"success": false,
"error": {
"code": "VALIDATION_ERROR",
"message": "email must be an email",
"statusCode": 400,
"errors": {}
}
}{
"success": false,
"error": {
"code": "VALIDATION_ERROR",
"message": "email must be an email",
"statusCode": 400,
"errors": {}
}
}{
"success": false,
"error": {
"code": "VALIDATION_ERROR",
"message": "email must be an email",
"statusCode": 400,
"errors": {}
}
}{
"success": false,
"error": {
"code": "VALIDATION_ERROR",
"message": "email must be an email",
"statusCode": 400,
"errors": {}
}
}Headers
Body
Amount in major units (matches hosted checkout)
x >= 1/^[a-z]{3}$/"ngn"
2"NG"
Show child attributes
Show child attributes
Show child attributes
Show child attributes
Ignored. The payer is returned to the return URL configured on your business settings (PUT /v1/business/config returnUrl), or to Axra's payment-complete page.
60 <= x <= 36001 - 128