POST /api/v2/payment/process
POST
/api/v2/payment/process
Submit an Apple Pay payment for processing. The token object is the raw PKPaymentToken from the Apple Pay framework.
Request Headers
| Header | Required | Value |
x-merchant-key | Required | Your merchant API key |
Content-Type | Required | application/json |
Request Body
| Field | Type | Required | Description |
order_id | string | Required | Your unique order ID. Max 128 characters. Duplicate order_id per merchant returns the existing payment. |
amount | number | Optional | Major currency units. Min: 0.01. Max 2 decimal places. Overrides token amount if provided. |
token | object | Required | Apple Pay PKPaymentToken object |
token.paymentData.data | string | Required | Base64-encoded encrypted payment data |
token.paymentData.signature | string | Required | PKCS #7 detached signature |
token.paymentData.version | string | Required | e.g. "EC_v1" |
token.paymentData.header | object | Required | publicKeyHash, ephemeralPublicKey, transactionId |
token.paymentMethod | object | Required | displayName, network, type |
token.transactionIdentifier | string | Required | Apple's unique transaction identifier |
Example Request
curl -X POST https://<your-domain>/api/v2/payment/process \
-H "Content-Type: application/json" \
-H "x-merchant-key: mk_live_xxxxxxxxxxxxxxxxxxxx" \
-d '{
"order_id": "ORDER-2024-00123",
"amount": 150.50,
"token": {
"paymentData": {
"data": "aGVsbG8gd29ybGQ...",
"signature": "MIAGCSqGSIb3DQ...",
"header": {
"publicKeyHash": "Hmng9JBG...",
"ephemeralPublicKey": "MFkwEwYH...",
"transactionId": "9AFDA47D..."
},
"version": "EC_v1"
},
"paymentMethod": {
"displayName": "Visa 4242",
"network": "Visa",
"type": "debit"
},
"transactionIdentifier": "9AFDA47D..."
}
}'
Response Body (200 OK)
| Field | Type | Description |
paymentId | string (UUID) | Bonum payment identifier. Use for polling or webhook matching. |
orderId | string | Your order_id echoed back |
status | string | Always "PENDING" — final result delivered via webhook |
acceptedAt | string (ISO 8601) | Time the request was accepted |
statusUrl | string | Full URL (including PSP domain) to check current status at any time |
awaitUrl | string | Full URL (including PSP domain) to block and wait for the final status. Use directly — do not prepend a domain. Recommended for closing wallet sessions. |
{
"paymentId": "a1b2c3d4-e5f6-7890-abcd-ef1234567890",
"orderId": "ORD-20240521-001",
"status": "PENDING",
"acceptedAt": "2026-05-21T14:30:00.000+08:00",
"statusUrl": "https://psp.bonum.mn/api/v2/payments/a1b2c3d4-e5f6-7890-abcd-ef1234567890",
"awaitUrl": "https://psp.bonum.mn/api/v2/payments/a1b2c3d4-e5f6-7890-abcd-ef1234567890/await"
}
Error Codes
| HTTP Status | Condition |
400 | Missing order_id, missing token, amount < 0.01 |
401 | Missing or invalid x-merchant-key |
429 | Rate limit exceeded |
POST /api/v2/payment/process/google
POST
/api/v2/payment/process/google
Submit a Google Pay payment for processing.
Request Body
| Field | Type | Required | Description |
order_id | string | Required | Your unique order ID |
token | string | Required | Encrypted Google Pay token string from PaymentData.paymentMethodData.tokenizationData.token |
currency_code | string | Required | One of: MNT, USD, EUR, JPY |
amount | number | Optional | Amount in major currency units. Min: 0.01. |
Example Request
curl -X POST https://<your-domain>/api/v2/payment/process/google \
-H "Content-Type: application/json" \
-H "x-merchant-key: mk_live_xxxxxxxxxxxxxxxxxxxx" \
-d '{
"order_id": "ORDER-2024-00124",
"token": "eyJzaWduYXR1cmUiOiJNRUlDSVFDa...",
"currency_code": "MNT",
"amount": 150.50
}'
Response Body (200 OK)
Identical structure to the Apple Pay response, including awaitUrl.
{
"paymentId": "b2c3d4e5-f6a7-8901-bcde-f12345678901",
"orderId": "ORD-20240521-002",
"status": "PENDING",
"acceptedAt": "2026-05-21T14:31:00.000+08:00",
"statusUrl": "https://psp.bonum.mn/api/v2/payments/b2c3d4e5-f6a7-8901-bcde-f12345678901",
"awaitUrl": "https://psp.bonum.mn/api/v2/payments/b2c3d4e5-f6a7-8901-bcde-f12345678901/await"
}
GET /api/v2/payments/{paymentId}
GET
/api/v2/payments/{paymentId}
Retrieve the current status and details of a payment by its paymentId.
Path Parameters
| Parameter | Type | Description |
paymentId | string (UUID) | The paymentId returned when the payment was submitted |
Example Request
curl https://<your-domain>/api/v2/payments/550e8400-e29b-41d4-a716-446655440000 \
-H "x-merchant-key: mk_live_xxxxxxxxxxxxxxxxxxxx"
Response Body (200 OK)
| Field | Type | Description |
paymentId | string (UUID) | Bonum payment identifier |
orderId | string | Your order ID |
amount | string | Amount in major currency units as a decimal string (e.g. "150.50") |
currency | string | ISO 4217 numeric currency code (e.g. 496 for MNT) |
walletType | string | APPLE_PAY or GOOGLE_PAY |
status | string | PENDING, AUTHORIZED, or FAILED |
providerReference | string | null | Bank/acquirer reference number. Present when AUTHORIZED. |
failureReason | string | null | Reason for failure. Present when FAILED. |
createdAt | string (ISO 8601) | When the payment was created |
updatedAt | string (ISO 8601) | When the payment was last updated |
{
"paymentId": "550e8400-e29b-41d4-a716-446655440000",
"orderId": "ORDER-2024-00123",
"amount": "150.50",
"currency": "496",
"walletType": "APPLE_PAY",
"status": "AUTHORIZED",
"providerReference": "GBK20240415001234",
"failureReason": null,
"createdAt": "2024-04-15T10:30:00.000Z",
"updatedAt": "2024-04-15T10:30:04.000Z"
}
Error Codes
| HTTP Status | Condition |
401 | Missing or invalid x-merchant-key |
404 | Payment ID does not exist or belongs to a different merchant |
GET /api/v2/payments/{paymentId}/await
GET
/api/v2/payments/{paymentId}/await
Blocks until the payment reaches a terminal status (AUTHORIZED or FAILED), then returns immediately. Designed for closing Apple Pay and Google Pay wallet sessions — call it with the awaitUrl from the submission response.
Unlike GET /api/v2/payments/{paymentId} which always returns the current state immediately, this endpoint holds the connection open on the server side and responds only when the bank has replied or the timeout is reached.
Path Parameters
| Parameter | Type | Description |
paymentId | string (UUID) | The paymentId returned when the payment was submitted |
Query Parameters
| Parameter | Type | Default | Max | Description |
timeoutMs | number | 25000 | 28000 | How long to wait (milliseconds) before returning a timeout response. Capped at 28 000ms to leave buffer before Apple Pay's 30-second hard limit. |
Example Request
curl "https://<your-domain>/api/v2/payments/550e8400-e29b-41d4-a716-446655440000/await?timeoutMs=25000" \
-H "x-merchant-key: mk_live_xxxxxxxxxxxxxxxxxxxx"
Response Body (200 OK)
Returns only what is needed to close the wallet session. Full payment details are delivered via webhook.
| Field | Type | Description |
paymentId | string (UUID) | Bonum payment identifier |
status | string | AUTHORIZED, FAILED, or PENDING (only when timedOut) |
failureReason | string | null | Reason for failure. Non-null when status is FAILED. |
timedOut | boolean | Present and true only when the wait window expired before the bank responded. Absent on success. |
// Authorized
{
"paymentId": "550e8400-e29b-41d4-a716-446655440000",
"status": "AUTHORIZED",
"failureReason": null
}
// Failed
{
"paymentId": "550e8400-e29b-41d4-a716-446655440000",
"status": "FAILED",
"failureReason": "Insufficient funds"
}
// Timed out — bank still processing, rely on webhook for final result
{
"paymentId": "550e8400-e29b-41d4-a716-446655440000",
"status": "PENDING",
"failureReason": null,
"timedOut": true
}
Error Codes
| HTTP Status | Condition |
400 | paymentId is not a valid UUID |
401 | Missing or invalid x-merchant-key |
404 | Payment ID does not exist |
GET /api/v2/payments/lookup/by-order-id
GET
/api/v2/payments/lookup/by-order-id
Look up a payment using your own order_id. Returns the same payment detail object as the paymentId lookup.
Query Parameters
| Parameter | Type | Required | Description |
orderId | string | Required | Your order ID used when submitting the payment |
Example Request
curl "https://<your-domain>/api/v2/payments/lookup/by-order-id?orderId=ORDER-2024-00123" \
-H "x-merchant-key: mk_live_xxxxxxxxxxxxxxxxxxxx"
Error Codes
| HTTP Status | Condition |
400 | orderId query parameter is missing or empty |
401 | Missing or invalid x-merchant-key |
404 | No payment found for this order ID under your merchant account |