Configuring Product View Count Display for 1C-Bitrix
A view counter on a product card creates a sense of popularity. Unlike purchases, views accumulate faster — even a new product will show real numbers within a few days. Bitrix does not track product view counts by default, but provides the tools to implement it.
Built-In Statistics Module
The statistic module maintains the b_stat_page_hit table — every page request is recorded there with a PATH field (the page URI). The number of views for a product detail page can be retrieved from this table by its URL. However, this is a heavy approach: the table grows fast, queries on it are slow, and the statistics module is often disabled on high-traffic sites.
Custom View Counter
The correct approach is to store the counter directly in an info block property. A numeric VIEW_COUNT property is created in b_iblock_property. An event handler increments the value every time the product detail page is opened.
The event fires in the bitrix:catalog.element component, in component_epilog.php:
if (!defined("B_PROLOG_INCLUDED") || B_PROLOG_INCLUDED !== true) die();
$elementId = $arResult["ID"];
$iblockId = $arResult["IBLOCK_ID"];
$currentCount = (int)$arResult["PROPERTIES"]["VIEW_COUNT"]["VALUE"];
CIBlockElement::SetPropertyValuesEx(
$elementId,
$iblockId,
["VIEW_COUNT" => $currentCount + 1]
);
Writing in component_epilog.php does not block page rendering — it executes after the response has been sent to the client (using ob_flush/flush or Bitrix's built-in mechanisms).
Bot and Repeat View Filtering
Without filtering, search engine bots will inflate the counter. Minimum protection — do not count views if:
-
$_SERVER['HTTP_USER_AGENT']contains bot signatures (Googlebot, YandexBot, Bingbot) - The visitor's IP has already viewed this product within the last N minutes
Session-based deduplication is used: $_SESSION['viewed_products'][$elementId] = time(). If the entry exists and less than 30 minutes have passed — the counter is not incremented.
Caching and Performance
If the detail page is cached (and it should be), component_epilog.php is called on every view, even when the main content is served from cache. This is exactly the desired behavior — the counter works independently of the page cache.
Under high load (>100 views per minute on one product), direct writes to b_iblock_element_prop cause concurrent updates to a single row. Solution: atomic increment via UPDATE:
$DB->Query("UPDATE b_iblock_element_prop_s{$iblockId}
SET PROPERTY_VIEW_COUNT = COALESCE(PROPERTY_VIEW_COUNT, 0) + 1
WHERE IBLOCK_ELEMENT_ID = " . intval($elementId));
The column name depends on the property ID — it is generated automatically by Bitrix when the property is created.
Displaying the Counter
In the bitrix:catalog.element template, the property value is output:
$viewCount = (int)$arResult["PROPERTIES"]["VIEW_COUNT"]["VALUE"];
echo '<span>' . $viewCount . ' views</span>';
The value is displayed with correct pluralization depending on the number.
What Is Included in the Setup
- Creating the
VIEW_COUNTproperty in the catalog info block - Adding the handler in
component_epilog.phpwith bot filtering - Implementing session-based repeat-view protection
- Atomic INCREMENT for high-traffic stores
- Displaying the counter with correct word forms in the product card template

