Bitrix24 CRM Integration

Our company is engaged in the development, support and maintenance of sites of any complexity. From simple one-page sites to large-scale cluster systems built on micro services. Experience of developers is confirmed by certificates from vendors.
Development and maintenance of all types of websites:
Informational websites or web applications
Business card websites, landing pages, corporate websites, online catalogs, quizzes, promo websites, blogs, news resources, informational portals, forums, aggregators
E-commerce websites or web applications
Online stores, B2B portals, marketplaces, online exchanges, cashback websites, exchanges, dropshipping platforms, product parsers
Business process management web applications
CRM systems, ERP systems, corporate portals, production management systems, information parsers
Electronic service websites or web applications
Classified ads platforms, online schools, online cinemas, website builders, portals for electronic services, video hosting platforms, thematic portals

These are just some of the technical types of websites we work with, and each of them can have its own specific features and functionality, as well as be customized to meet the specific needs and goals of the client.

Our competencies:
Development stages
Latest works
  • image_web-applications_feedme_466_0.webp
    Development of a web application for FEEDME
    1161
  • image_ecommerce_furnoro_435_0.webp
    Development of an online store for the company FURNORO
    1041
  • image_crm_enviok_479_0.webp
    Development of a web application for Enviok
    822
  • image_crm_chasseurs_493_0.webp
    CRM development for Chasseurs
    847
  • image_website-sbh_0.png
    Website development for SBH Partners
    999
  • image_website-_0.png
    Website development for Red Pear
    451

Bitrix24 CRM Integration with Website

Bitrix24 is an enterprise platform with built-in CRM, tasks, and communications. Website integration with Bitrix24 comes down to two tasks: sending leads/deals from website forms to CRM and synchronizing data bidirectionally via REST API.

Bitrix24 REST API

Bitrix24 provides REST API based on webhooks or OAuth applications. For external websites, it's easiest to use incoming webhooks:

  1. In Bitrix24: Settings → Integrations → Webhooks → Add webhook
  2. Select required permissions (CRM, Tasks)
  3. Get a URL like https://your-company.bitrix24.ru/rest/1/abc123xyz/

Creating a Lead from a Form

class Bitrix24Client {
    private string $webhookUrl;

    public function __construct() {
        $this->webhookUrl = config('bitrix24.webhook_url');
    }

    public function callMethod(string $method, array $params = []): array {
        $response = Http::timeout(15)
            ->post($this->webhookUrl . $method, $params);

        if ($response->failed()) {
            throw new \RuntimeException('Bitrix24 API error: ' . $response->status());
        }

        $data = $response->json();
        if (!empty($data['error'])) {
            throw new \RuntimeException('Bitrix24: ' . $data['error_description']);
        }

        return $data['result'] ?? [];
    }

    public function createLead(array $fields): int {
        return $this->callMethod('crm.lead.add', [
            'fields' => $fields,
            'params' => ['REGISTER_SONET_EVENT' => 'Y'],
        ]);
    }
}

Contact form handler:

class ContactFormController extends Controller {
    public function submit(ContactFormRequest $request): JsonResponse {
        // Save to our database
        $contact = ContactRequest::create($request->validated());

        // Send to Bitrix24
        try {
            $bitrix = app(Bitrix24Client::class);
            $leadId = $bitrix->createLead([
                'TITLE'         => 'Request from website: ' . $request->name,
                'NAME'          => $request->name,
                'PHONE'         => [['VALUE' => $request->phone, 'VALUE_TYPE' => 'WORK']],
                'EMAIL'         => [['VALUE' => $request->email, 'VALUE_TYPE' => 'WORK']],
                'COMMENTS'      => $request->message,
                'SOURCE_ID'     => 'WEB',
                'SOURCE_DESCRIPTION' => 'Form: ' . $request->form_id,
                'ASSIGNED_BY_ID' => config('bitrix24.default_responsible_id'),
                'UF_CRM_UTM_SOURCE' => session('utm_source'),
                'UF_CRM_UTM_MEDIUM' => session('utm_medium'),
                'UF_CRM_UTM_CAMPAIGN' => session('utm_campaign'),
            ]);
            $contact->update(['bitrix_lead_id' => $leadId]);
        } catch (\Exception $e) {
            Log::error('Bitrix24 lead creation failed', ['error' => $e->getMessage()]);
            // Don't interrupt flow — request saved in our database
        }

        return response()->json(['success' => true]);
    }
}

Deals Instead of Leads

For e-commerce, deals are often needed instead of leads:

public function createDealFromOrder(Order $order): void {
    $bitrix = app(Bitrix24Client::class);

    // Find or create contact
    $contacts = $bitrix->callMethod('crm.contact.list', [
        'filter' => ['PHONE' => $order->customer_phone],
        'select' => ['ID', 'NAME'],
    ]);

    $contactId = $contacts[0]['ID'] ?? $bitrix->callMethod('crm.contact.add', [
        'fields' => [
            'NAME'  => $order->customer_name,
            'PHONE' => [['VALUE' => $order->customer_phone, 'VALUE_TYPE' => 'WORK']],
            'EMAIL' => [['VALUE' => $order->customer_email, 'VALUE_TYPE' => 'WORK']],
        ],
    ]);

    // Create deal
    $dealId = $bitrix->callMethod('crm.deal.add', [
        'fields' => [
            'TITLE'          => 'Order #' . $order->number,
            'CONTACT_ID'     => $contactId,
            'OPPORTUNITY'    => $order->total,
            'CURRENCY_ID'    => 'RUB',
            'STAGE_ID'       => 'NEW',
            'COMMENTS'       => $this->buildOrderComment($order),
        ],
    ]);

    // Attach products to deal
    $productRows = $order->items->map(fn($item) => [
        'PRODUCT_NAME' => $item->product->name,
        'PRICE'        => $item->price,
        'QUANTITY'     => $item->quantity,
        'MEASURE_NAME' => 'pc.',
    ])->toArray();

    $bitrix->callMethod('crm.deal.productrows.set', [
        'id'   => $dealId,
        'rows' => $productRows,
    ]);

    $order->update(['bitrix_deal_id' => $dealId]);
}

Incoming Webhook: Status Updates

When a manager changes deal status in Bitrix24, the website should update order status. Configure an outgoing webhook from Bitrix24:

// routes/api.php
Route::post('/webhooks/bitrix24', [Bitrix24WebhookController::class, 'handle'])
    ->middleware('bitrix24.signature');

class Bitrix24WebhookController extends Controller {
    public function handle(Request $request): Response {
        $event = $request->input('event');
        $data  = $request->input('data');

        match ($event) {
            'ONCRMDEALSTAGEUPDATED' => $this->onDealStageUpdated($data),
            'ONCRMLEADADD'          => $this->onLeadAdded($data),
            default                 => null,
        };

        return response('OK');
    }

    private function onDealStageUpdated(array $data): void {
        $dealId  = $data['FIELDS']['ID'];
        $stageId = $data['FIELDS']['STAGE_ID'];

        $order = Order::where('bitrix_deal_id', $dealId)->first();
        if (!$order) return;

        $statusMap = [
            'WON'        => 'completed',
            'LOSE'       => 'cancelled',
            'IN_PROCESS' => 'processing',
        ];

        if ($status = $statusMap[$stageId] ?? null) {
            $order->update(['status' => $status]);
        }
    }
}

Signature Verification Middleware

class Bitrix24SignatureMiddleware {
    public function handle(Request $request, Closure $next): Response {
        // Bitrix24 passes auth[member_id] — check by token
        $memberId = $request->input('auth.member_id');
        if ($memberId !== config('bitrix24.member_id')) {
            abort(403);
        }
        return $next($request);
    }
}

Batch Requests

Bitrix24 limits REST API: 2 requests per second per webhook. For bulk operations, use the batch method:

$batch = [
    'get_lead'    => 'crm.lead.get?id=' . $leadId,
    'get_contact' => 'crm.contact.list?filter[EMAIL]=' . urlencode($email),
];

$results = $bitrix->callMethod('batch', [
    'halt'  => 0,
    'cmd'   => $batch,
]);
// $results['result']['get_lead'], $results['result']['get_contact']

One batch call contains up to 50 methods.

Implementation Timeline

Basic integration: leads from forms to Bitrix24, save ID to local database: 1–2 days. Bidirectional synchronization (deals, contacts, incoming webhooks, UTM tags): 3–4 days. Product catalog synchronization + integration with Bitrix24 telephony for callback forms: plus 2–3 days.