1C-Bitrix Integration with Alfa-Bank Internet Acquiring (Belarus)
Alfa-Bank Belarus is one of the most technologically advanced banks in the Belarusian market, providing internet acquiring through its own payment gateway. Unlike Russian Alfa-Bank, the Belarusian subsidiary uses a different API — based on the OpenWay protocol — which means separate documentation and a separate onboarding process.
Gateway Technology Stack
Alfa-Bank Belarus uses a payment gateway built on OpenWay processing (ecom.alfa-bank.by). The workflow is a standard redirect flow:
- The store sends an order registration request → receives
formUrlandorderId - The buyer is redirected to
formUrl - After payment — redirect to
returnUrl+ notification tocallbackUrl - The store verifies the status via
getOrderStatus
The API accepts requests via HTTPS; authentication uses userName/password as request parameters (basic parameters, not a header). The format is form-urlencoded or JSON depending on the endpoint.
Order Registration
class AlfaBankBelarusGateway
{
private const API_URL = 'https://ecom.alfa-bank.by/payment/rest/';
private string $userName;
private string $password;
public function registerOrder(array $orderData): array
{
$params = [
'userName' => $this->userName,
'password' => $this->password,
'orderNumber' => $orderData['number'],
'amount' => (int)($orderData['amount'] * 100), // kopecks
'currency' => 933, // BYN per ISO 4217
'returnUrl' => $orderData['returnUrl'],
'failUrl' => $orderData['failUrl'],
'description' => 'Order #' . $orderData['number'],
'language' => 'ru',
'pageView' => 'DESKTOP', // or MOBILE
];
$response = $this->request('register.do', $params);
if (!empty($response['errorCode']) && $response['errorCode'] !== '0') {
throw new \RuntimeException(
'Registration error: ' . ($response['errorMessage'] ?? 'unknown error')
);
}
return $response; // contains orderId and formUrl
}
private function request(string $method, array $params): array
{
$ch = curl_init(self::API_URL . $method);
curl_setopt_array($ch, [
CURLOPT_POST => true,
CURLOPT_POSTFIELDS => http_build_query($params),
CURLOPT_RETURNTRANSFER => true,
CURLOPT_SSL_VERIFYPEER => true,
CURLOPT_TIMEOUT => 30,
]);
$result = curl_exec($ch);
curl_close($ch);
return json_decode($result, true);
}
}
Order Status Check
public function getOrderStatus(string $orderId): array
{
return $this->request('getOrderStatus.do', [
'userName' => $this->userName,
'password' => $this->password,
'orderId' => $orderId,
'language' => 'ru',
]);
}
Status codes are similar to other gateways based on comparable processing systems:
| Code | Meaning | Action |
|---|---|---|
| 0 | Registered | Wait |
| 1 | Pre-authorized | Two-stage — wait |
| 2 | Paid | Confirm in Bitrix |
| 3 | Cancelled | Notify the buyer |
| 4 | Refunded | Update status |
| 6 | Rejected | Suggest retry |
Integration with the Bitrix Payment System
// /local/php_interface/include/sale_payment/alfabank_by/handler.php
class AlfaBankByHandler extends \Bitrix\Sale\PaySystem\ServiceHandler
{
public function initiatePay(
\Bitrix\Sale\Payment $payment,
\Bitrix\Main\Request $request
): \Bitrix\Sale\PaySystem\ServiceResult {
$result = new \Bitrix\Sale\PaySystem\ServiceResult();
$order = $payment->getOrder();
$gateway = new AlfaBankBelarusGateway(
$this->getBusinessValue($payment, 'ALFABANK_BY_USER'),
$this->getBusinessValue($payment, 'ALFABANK_BY_PASSWORD')
);
try {
$response = $gateway->registerOrder([
'number' => 'BX' . $order->getId(),
'amount' => $payment->getSum(),
'returnUrl' => $this->getSuccessUrl($payment),
'failUrl' => $this->getFailUrl($payment),
]);
// Save the bank's orderId for subsequent verification
$payment->setField('PS_INVOICE_ID', $response['orderId']);
$payment->save();
$result->setPaymentUrl($response['formUrl']);
} catch (\Exception $e) {
$result->addError(new \Bitrix\Main\Error($e->getMessage()));
}
return $result;
}
}
Handling Callback Notifications
Alfa-Bank Belarus sends a GET request to callbackUrl (or POST, depending on the contract settings). Parameters include mdOrder (bank's orderId) and orderNumber (store's order number).
Important: do not update the status based solely on callback parameters. Always call getOrderStatus.do for verification:
public function processRequest(
\Bitrix\Sale\Payment $payment,
\Bitrix\Main\Request $request
): \Bitrix\Sale\PaySystem\ServiceResult {
$result = new \Bitrix\Sale\PaySystem\ServiceResult();
$orderId = $request->get('mdOrder') ?: $payment->getField('PS_INVOICE_ID');
$gateway = new AlfaBankBelarusGateway(/* credentials */);
$status = $gateway->getOrderStatus($orderId);
if (($status['OrderStatus'] ?? -1) === 2) {
$payment->setPaid('Y');
$payment->save();
$result->setOperationType(\Bitrix\Sale\PaySystem\ServiceResult::MONEY_COMING);
}
return $result;
}
Currency and Amounts
- Currency BYN — ISO code
933 - Amount in Belarusian kopecks (integer)
- If the site uses a different currency — convert before creating the payment on the store side
Testing
Alfa-Bank Belarus provides a test environment (ecom-test.alfa-bank.by). Test credentials are issued individually during onboarding. Minimum test scenario: successful payment → callback → status 2 → record in Bitrix → repeated payment with the same orderNumber must return an "order already paid" error.
Timeline
| Task | Duration |
|---|---|
| Handler development | 2–3 days |
| Testing | 1 day |
| Live connection and acceptance | 1 day |







