Segmented Push Notification Setup in 1C-Bitrix
Mass push notifications with a 0.5% CTR and growing unsubscribe rates result from lack of segmentation. Push with relevant offer (discount on a category the user was browsing) achieves 4–8% CTR. This is the difference in approach: not "everyone about everything," but specific message to specific segment.
Push Notification Infrastructure in Bitrix
The standard 1C-Bitrix module does not include push notifications for an online store. Infrastructure is built on:
- Firebase Cloud Messaging (FCM) — for web push and Android
- Apple Push Notification Service (APNs) — for iOS (if there's a mobile app)
- Third-party platforms: OneSignal, Pushwoosh, SendPulse — with built-in segmentation
For Bitrix integration, the most practical option is OneSignal or custom token storage + FCM API.
Storing Tokens and User Attributes
Push subscription tokens are stored in a custom table:
CREATE TABLE custom_push_tokens (
id INT AUTO_INCREMENT PRIMARY KEY,
user_id INT,
token TEXT NOT NULL,
platform ENUM('web', 'android', 'ios') DEFAULT 'web',
created_at DATETIME,
last_active DATETIME,
INDEX idx_user (user_id),
INDEX idx_platform (platform)
);
Attributes for segmentation are stored separately:
CREATE TABLE custom_push_user_attrs (
user_id INT,
attr_key VARCHAR(100),
attr_value VARCHAR(255),
updated_at DATETIME,
PRIMARY KEY (user_id, attr_key)
);
Attributes are updated by Bitrix events: category view → last_category_viewed, purchase → last_purchase_date and total_orders, cart amount → cart_value.
Segmentation: What and How to Divide
Typical segments for an online store:
| Segment | Criteria | Example Notification |
|---|---|---|
| Abandoned Cart | cart_value > 0, last_cart_update > 2h | "Your cart is waiting. Checkout now" |
| Active Customers | total_orders >= 3 in 90 days | Exclusive offer for loyal customers |
| New Users | registration_date < 7 days | Promo code for first order |
| Category Interest | last_category_viewed = 'electronics' | Electronics discount today |
| Inactive | last_purchase_date > 60 days | "We miss you" + special offer |
Sending via FCM
Wrapper class for sending:
class PushSender {
private const FCM_URL = 'https://fcm.googleapis.com/fcm/send';
public function sendToSegment(array $filter, string $title, string $body, array $data = []): void {
$tokens = $this->getTokensByFilter($filter);
// FCM accepts max 500 tokens per request
foreach (array_chunk($tokens, 500) as $chunk) {
$this->sendBatch($chunk, $title, $body, $data);
}
}
private function sendBatch(array $tokens, string $title, string $body, array $data): void {
$payload = [
'registration_ids' => $tokens,
'notification' => [
'title' => $title,
'body' => $body,
'icon' => '/favicon-192.png',
'click_action' => $data['url'] ?? '/',
],
'data' => $data,
];
$http = new \Bitrix\Main\Web\HttpClient();
$http->setHeader('Authorization', 'key=' . FCM_SERVER_KEY);
$http->setHeader('Content-Type', 'application/json');
$http->post(self::FCM_URL, json_encode($payload));
}
}
Attribute Update Triggers
Segmentation attributes must update in real time. Implemented via Bitrix event handlers:
-
OnSaleOrderSaved→ updatetotal_orders,last_purchase_date -
OnSaleBasketItemSaved→ updatecart_value - Custom event on catalog section view →
last_category_viewed
Attribute updates — simple REPLACE INTO custom_push_user_attrs.
Browser Push Subscription
JavaScript to request permission and save token:
async function subscribeToPush() {
const registration = await navigator.serviceWorker.register('/sw.js');
const subscription = await registration.pushManager.subscribe({
userVisibleOnly: true,
applicationServerKey: VAPID_PUBLIC_KEY
});
await fetch('/api/push/subscribe/', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify(subscription)
});
}
Execution Timeline
| Scope | Timeline |
|---|---|
| Token storage + basic sending | 1–2 days |
| Attributes + 5–7 segments | 2–3 days |
| Management UI + delivery analytics | +2 days |
Segmented push is a retention tool that pays for itself with a subscriber base of 5,000+.

