/api/v1/payment/requestDirect Payment Request
Initiates a direct payment transaction through the Beqelal payment gateway.
When to Use
Use this endpoint when a merchant wants to integrate with Beqelal via API without using the checkout page. It enables the merchant to initiate direct push payments from their system to the customer's bank account through the customer's financial institution, streamlining the user experience and avoiding redirection to an external checkout interface.
Authentication
Requires the following headers:
app-id: Your application identifier (from Account Management → Generate API Key → APP id)api-key: Your secret API key (from Account Management → Generate API Key → API Keys)How It Works
- Merchant Initiates Request: You send a payment request with customer details and amount
- Customer Receives Notification: The customer gets a push notification on their mobile banking app
- Customer Authorizes: The customer reviews and approves the payment in their banking app
- Payment Processed: Once authorized, the payment is processed immediately
- Webhook Notification: You receive a webhook callback with the payment result
Authorization Methods
The processing behavior depends on the financial institution's authorization method. Check the authorization_method field in the response to determine the flow.
1. OTP (One-Time Password)
- Beqelal will return an initial response
- The merchant must call the /authorize/ endpoint with the OTP to confirm the transaction
- Webhook notification is sent after authorization (if webhook URL is configured)
2. PUSH_USSD (Automatic Push)
- The transaction is processed directly by pushing a USSD prompt to the customer's phone
- Result is sent asynchronously to the configured webhook URL (portal setting or
callback_urloverride) - If no webhook URL is configured (neither in portal nor in request), the request will be rejected
Request Parameters
Required Fields
bankstringRequiredInstitution ID of the receiving bank
account_nostringRequiredCustomer's account number at the financial institution
amountnumberRequiredAmount to be paid (in ETB)
trace_numberstringRequiredMerchant's own transaction reference (must be unique)
Optional Fields
callback_urlstring (url)OptionalIf provided, overrides the portal-configured webhook URL for this transaction. If not provided, the portal-configured webhook URL will be used.
Response
Returns JSON containing:
- Payment reference ID
- Request status (PENDING, PROCESSED, or FAILED)
- Transaction details
Key Differences from Checkout
- No Browser Required: Customer doesn't need to visit a URL - payment request goes directly to their banking app
- Push Notification: Customer receives a mobile push notification instead of clicking a link
- Immediate Response: Customer can approve/decline instantly from their phone
- No Return URL: Not needed since there's no browser redirect flow
Code Examples
curl -X POST "{base_url}/api/v1/payment/request" \
-H "Content-Type: application/json" \
-H "app-id: YOUR_APP_ID" \
-H "api-key: YOUR_API_KEY" \
-d '{
"bank": "404050",
"account_no": "251911000000",
"amount": 100,
"trace_number": "70RNVPO548",
"callback_url": "https://www.example.et/v1/"
}'Response Examples
Successful response (200)
200 - OK{
"id": "4EA310DX85",
"bank_name": "Kacha DFS",
"authorization_method": "OTP",
"merchant": "Example Merchant",
"merchant_phone": "251912000000",
"phone": "251911000000",
"account_no": "251911000000",
"from_name": "Abebe Kebede",
"amount": 100,
"fee": 0,
"total_amount": 100,
"reference": "",
"trace_number": "70RNV0r145PO548",
"process": "Direct Payment(API)",
"description": "Direct Payment(AP)",
"updated_at": "2025-05-10T21:33:15.799012",
"status": "PENDING",
"status_code": 200,
"message": "SUCCESS",
"detail": "Operation Completed Successfully"
}Unknown user (400)
400 - Unknown user{
"error": {
"status": "FAILED",
"status_code": "430",
"message": "UNKNOWN_USER",
"detail": "Unknown User",
"trace_number": "74878TRPO548"
}
}Duplicate trace number (400)
400 - Duplicate trace number{
"error": {
"status": "FAILED",
"status_code": "439",
"message": "TRACE_NUMBER",
"detail": "trace number must be unique"
}
}Inactive Service Account (400)
400 - Inactive Service Account{
"error": {
"status": "FAILED",
"status_code": "426",
"message": "INACTIVE_USER_ACCOUNT",
"detail": "Inactive Service Account",
"trace_number": "704T0NVPO548"
}
}Insufficient Balance (400)
400 - If customer have Insufficient Balance{
"error": {
"status": "FAILED",
"status_code": "433",
"message": "INSUFFICIENT_BALANCE",
"detail": "Insufficient Balance"
}
}Unauthorized IP Access (479)
479 - Unauthorized IP{
"error": {
"status": "FAILED",
"status_code": "479",
"message": "UNAUTHORIZED_IP_ACCESS",
"detail": "Unauthorized IP address access."
}
}Important Notes
- Mobile Banking Required: Customer must have mobile banking enabled on their account
- Time Limit: Payment requests expire after 5 minutes if not responded to
- Webhook Essential: You must have webhooks configured to receive payment authorization results
- Customer Experience: Ensure your customers expect the payment request notification