Setting up cashless payments for legal entities in 1C-Bitrix

Our company is engaged in the development, support and maintenance of Bitrix and Bitrix24 solutions of any complexity. From simple one-page sites to complex online stores, CRM systems with 1C and telephony integration. The experience of developers is confirmed by certificates from the vendor.
Our competencies:
Development stages
Latest works
  • image_website-b2b-advance_0.png
    B2B ADVANCE company website development
    1175
  • image_bitrix-bitrix-24-1c_fixper_448_0.png
    Website development for FIXPER company
    811
  • image_bitrix-bitrix-24-1c_development_of_an_online_appointment_booking_widget_for_a_medical_center_594_0.webp
    Development based on Bitrix, Bitrix24, 1C for the company Development of an Online Appointment Booking Widget for a Medical Center
    564
  • image_bitrix-bitrix-24-1c_mirsanbel_458_0.webp
    Development based on 1C Enterprise for MIRSANBEL
    747
  • image_crm_dolbimby_434_0.webp
    Website development on CRM Bitrix24 for DOLBIMBY
    655
  • image_crm_technotorgcomplex_453_0.webp
    Development based on Bitrix24 for the company TECHNOTORGKOMPLEKS
    976

Non-Cash Payment Setup for Legal Entities in 1C-Bitrix

Online stores that work with B2B clients regularly face the same situation: a legal entity wants to pay by bank transfer, with VAT, a contract, and closing documents. The standard Bitrix sale module partially supports this (payment type "Bank Transfer"), but out of the box it cannot generate an invoice as a PDF, does not look up company details by Tax ID (INN), and does not track payments. All of this requires customisation.

Payment Type "Bank Transfer"

In Bitrix, non-cash payment is implemented as a payment system with a Bitrix\Sale\PaySystem\BaseServiceHandler handler that does not redirect to an external gateway:

// .description.php of the payment handler
$HANDLER_NAME = 'Bank Transfer for Legal Entities';
$HANDLER_CODE = 'bank_transfer_b2b';

// At checkout — the buyer sees bank details, not a card form
// Payment is marked as "awaiting payment" until manually confirmed by a manager

Legal Entity Form at Checkout

When "Legal Entity" is selected in the order form — display additional fields:

// Additional order properties for a legal entity
$arOrderProps = [
    'INN'           => ['NAME' => 'Tax ID (INN)', 'TYPE' => 'STRING', 'REQUIRED' => 'Y'],
    'KPP'           => ['NAME' => 'KPP', 'TYPE' => 'STRING'],
    'COMPANY_NAME'  => ['NAME' => 'Company Name', 'TYPE' => 'STRING', 'REQUIRED' => 'Y'],
    'LEGAL_ADDRESS' => ['NAME' => 'Legal Address', 'TYPE' => 'STRING'],
    'DIRECTOR_NAME' => ['NAME' => 'Director Full Name', 'TYPE' => 'STRING'],
    'ACCOUNTANT'    => ['NAME' => 'Accountant Full Name', 'TYPE' => 'STRING'],
];

Auto-Fill by Tax ID (INN)

// DADATA API — auto-fill company details by INN
document.getElementById('inn-field').addEventListener('blur', async function() {
    const inn = this.value;
    if (inn.length < 10) return;

    const res = await fetch('https://suggestions.dadata.ru/suggestions/api/4_1/rs/findById/party', {
        method: 'POST',
        headers: {
            'Authorization': 'Token YOUR_DADATA_TOKEN',
            'Content-Type': 'application/json',
        },
        body: JSON.stringify({ query: inn }),
    });
    const data = await res.json();
    const company = data.suggestions?.[0]?.data;
    if (company) {
        document.getElementById('company-name').value = company.name?.short_with_opf || '';
        document.getElementById('kpp').value = company.kpp || '';
        document.getElementById('legal-address').value = company.address?.value || '';
    }
});

PDF Invoice Generation

// Invoice generation via mPDF or TCPDF
use Mpdf\Mpdf;

class InvoiceGenerator
{
    public function generate(\Bitrix\Sale\Order $order): string
    {
        $mpdf = new Mpdf(['format' => 'A4']);
        $mpdf->SetFont('dejavusans');  // Cyrillic support

        $html = $this->renderTemplate($order, [
            'invoice_number' => 'INV-' . str_pad($order->getId(), 6, '0', STR_PAD_LEFT),
            'invoice_date'   => date('d.m.Y'),
            'seller'         => $this->getSellerDetails(),
            'buyer'          => $this->getBuyerDetails($order),
            'items'          => $this->getOrderItems($order),
            'total'          => $order->getPrice(),
            'vat_amount'     => $this->calculateVat($order),
        ]);

        $mpdf->WriteHTML($html);

        $pdfPath = '/upload/invoices/invoice_' . $order->getId() . '.pdf';
        $mpdf->Output($_SERVER['DOCUMENT_ROOT'] . $pdfPath, 'F');

        return $pdfPath;
    }
}

Manual Payment Confirmation by a Manager

The manager receives a notification about an order with the payment type "Bank Transfer". After the funds arrive in the bank account, the manager manually marks the payment as received:

// Admin page or CRM integration
// Manager clicks "Confirm Payment"
$order = \Bitrix\Sale\Order::load($orderId);
foreach ($order->getPaymentCollection() as $payment) {
    if (!$payment->isPaid()) {
        $payment->setPaid('Y');
        $payment->setField('PS_STATUS_MESSAGE', 'Payment confirmed by manager ' . $currentUserName);
        $payment->save();
    }
}
$order->save();

For automation — bank API integration (Sber, Tinkoff Business, Tochka) allows receiving incoming payment notifications and automatically matching them to orders by the invoice number in the payment reference.

Timeline

Task Duration
Legal entity form + auto-fill by INN 1 day
PDF invoice generation 1–2 days
Manual payment confirmation in Admin 0.5 day
Automatic matching via bank API 2–3 days