1С Битрикс · 6 мин чтения

Шаблон компонента Битрикс: кастомизация без потери обновлений

Шаблон компонента Битрикс - единственный правильный способ поменять внешний вид и логику вывода компонента, не трогая файлы в /bitrix/. За несколько лет работы с проектами на 1С-Битрикс я регулярно вижу одну и ту же картину: разработчик правит template.php прямо в /bitrix/components/bitrix/catalog.element/templates/.default/, магазин работает месяц-два, потом прилетает обновление модуля catalog - и все правки исчезают вместе с новым файлом ядра.

Почему нельзя редактировать компоненты ядра напрямую

Ядро Битрикс обновляется через магазин решений и центр обновлений, и каждое обновление модуля перезаписывает файлы в /bitrix/. Это касается и типовых компонентов bitrix:catalog.element, bitrix:sale.order, bitrix:news.list - при любом апдейте модуля их шаблоны в /bitrix/components/bitrix/…/templates/ переписываются заново. Если правки лежат там же, они теряются без предупреждения: диффа никто не покажет, бэкап делать никто не обязан.

На практике я видел ситуацию, когда интернет-магазин на Битрикс полгода жил с доработанной карточкой товара - добавили блок с остатками по складам и кнопку быстрого заказа прямо в template.php ядра. После планового обновления модуля catalog карточка вернулась к дефолтному виду, а клиент заметил это только когда пошли жалобы от менеджеров, что кнопка быстрого заказа пропала. Восстановление заняло два дня, потому что исходников доработки в системе контроля версий не было - они физически лежали в папке, которую никто не коммитил.

Как устроено наследование шаблона компонента

Битрикс ищет шаблон компонента по цепочке путей, и первый найденный файл побеждает. Порядок примерно такой:

  • /local/templates/[текущий_шаблон_сайта]/components/[namespace]/[component]/[template_name]/
  • /bitrix/templates/[текущий_шаблон_сайта]/components/[namespace]/[component]/[template_name]/
  • /bitrix/components/[namespace]/[component]/templates/[template_name]/ (шаблон, поставляемый с модулем)

Если задать template_name как .default и не переопределять, движок пойдёт по этой цепочке автоматически - вам достаточно положить файл с тем же именем компонента и тем же именем шаблона в local/templates, и он получит приоритет. Ядро при этом остаётся нетронутым, а обновления модулей проходят мимо ваших файлов, потому что apache обновляет только /bitrix/.

Путь Что там лежит Переживает обновление модуля
/bitrix/components/…/templates/.default/ Шаблон из коробки, ставится модулем Нет
/bitrix/templates/[шаблон_сайта]/components/ Переопределения на уровне шаблона сайта Да, но перезатирается при обновлении маркетплейс-шаблона
/local/templates/[шаблон_сайта]/components/ Ваши кастомные шаблоны Да, всегда

Поэтому правило простое: всё, что вы правите руками, должно жить в /local/. Каталог /local/ Битрикс не трогает никогда, ни при обновлении ядра, ни при обновлении модулей, ни при смене редакции.

Создание собственного шаблона компонента пошагово

Беру для примера доработку карточки товара - компонент bitrix:catalog.element с типовым шаблоном .default.

1. Копируем структуру

Создаю папку по точной структуре пути наследования и копирую туда содержимое исходного шаблона:

mkdir -p /local/templates/.default/components/bitrix/catalog.element/element_page
cp -r /bitrix/components/bitrix/catalog.element/templates/.default/* 
 /local/templates/.default/components/bitrix/catalog.element/element_page/

Важный момент: имя шаблона (element_page) должно совпадать с тем, что указано в параметре TEMPLATE_NAME при вызове компонента на странице. Если компонент вызывается с template_name=”.default”, копируйте именно в папку .default, а не придумывайте своё имя - иначе Битрикс продолжит искать в старом месте.

2. Правим template.php

Дальше редактирую уже свою копию - добавляю, например, блок с остатками по складам:

<?php if (!empty($arResult['STORE_QUANTITY'])): ?>
 <div class="product-stock">
 В наличии на складах: <?= (int)$arResult['STORE_QUANTITY'] ?> шт.
 </div>
<?php endif; ?>

Остальные файлы - style.css, script.js, .description.php - тоже держу рядом в этой папке, а не в общих ассетах сайта. Так вся логика конкретного шаблона компонента остаётся в одном месте, и при переносе на другой проект я просто копирую папку целиком.

Бесплатный материал

🎁 Полезный скрипт в подарок

Подпишитесь на Telegram - пришлю готовый скрипт по этой теме.

Без спама. Отписка в 1 клик.

Кастомизация через параметры и result_modifier.php

Не всё нужно решать через переписывание HTML в template.php. Если требуется изменить логику выборки данных - добавить сортировку, отфильтровать элементы, посчитать что-то на основе $arResult - используют result_modifier.php, который лежит рядом с template.php в той же папке шаблона и выполняется после работы класса компонента, но до рендера.

<?php
if (!empty($arResult['ITEMS'])) {
 foreach ($arResult['ITEMS'] as &$item) {
 $item['DISPLAY_PROPERTIES']['DISCOUNT_BADGE'] = 
 $item['PRICES']['BASE']['DISCOUNT_DIFF'] > 0 ? 'Скидка' : '';
 }
 unset($item);
}

Этот подход не ломает логику самого компонента (класс component.php остаётся заводским) и не требует трогать ядро вообще - правки живут в вашем шаблоне и переживают любые обновления. Для параметров, которые компонент поддерживает из коробки (число элементов на странице, сортировка, показ свойств), обычно хватает .parameters.php в том же шаблоне - там можно добавить свои настраиваемые опции, которые появятся в визуальном редакторе компонента в административном интерфейсе.

Кейс из практики: доставка СДЭК в шаблоне sale.order

Один из частых запросов на доработку интернет-магазинов на Битрикс - вывод калькулятора стоимости доставки СДЭК прямо в шаблоне компонента bitrix:sale.order на шаге выбора способа доставки. Стандартный шаблон показывает только список служб доставки без расчёта стоимости до подтверждения заказа.

Решение такое же: копирую шаблон sale.order (или конкретно ту его часть, что отвечает за шаг доставки, если используется композитный компонент bitrix:sale.order.ajax) в /local/templates/.default/components/bitrix/sale.order.ajax/, добавляю AJAX-запрос к обработчику, который дергает метод расчёта СДЭК и подставляет стоимость рядом с каждым пунктом выдачи. Модуль sale при обновлении переписывает свои файлы в /bitrix/, но моя копия в /local/ остаётся нетронутой, и после апдейта калькулятор продолжает работать без дополнительных действий.

Если у вас нет времени разбираться в структуре компонента sale.order.ajax самостоятельно - такие интеграции с доставкой и эквайрингом я беру в разработку под задачу, обычно с расчётом стоимости по факту объёма правок.

Типичные ошибки при кастомизации шаблонов

Забыли почистить кэш компонента

Если компонент вызван с CACHE_TYPE=“A”, изменения в шаблоне могут не отображаться, пока не очистится кэш управляемого кэша или файловый кэш в /bitrix/cache/. После правок в /local/templates я всегда чищу кэш через административную панель (Настройки → Автокэширование → Очистить кэш) или удаляю папку кэша вручную на тестовом окружении.

Путаница с именем шаблона

Если в компонент передан параметр “TEMPLATE_NAME” => “” без явного указания, Битрикс возьмёт .default, и правки в шаблоне с произвольным именем просто не подключатся. Всегда сверяю имя папки с тем, что реально передано в компонент на странице.

Правки в bitrix/templates вместо local/templates

Эта папка тоже переживает обновления модулей, но её перезаписывает обновление самого шаблона сайта, если он куплен в маркетплейсе решений. Для собственных правок используйте только /local/.

Нет версионирования

Папку /local/ обязательно веду в git отдельно от остального проекта или в общем репозитории, но с явным исключением /bitrix/ из отслеживания. Без этого при переносе на новый сервер или после сбоя восстановить кастомные шаблоны неоткуда.

На поддержке такие правки шаблонов обычно укладываются в текущий тариф техподдержки (от 15 000 ₽/мес), если объём небольшой и не требует новой логики с нуля - крупная переработка каталога или чекаута считается отдельным проектом.

Чтобы сайт работал без сбоев

Техподдержка

от 15 000 ₽/мес

Подробнее →

Частые вопросы

Можно ли переопределить только часть шаблона, а не копировать весь template.php?

Можно частично - через result_modifier.php для логики или через include отдельных файлов внутри своего template.php. Но сам файл template.php копируется целиком, потому что Битрикс подключает его как единый файл, частичного наследования на уровне разметки внутри одного шаблона не существует.

Что делать, если компонент не композитный и не поддерживает AJAX-версию шаблона?

Переопределяется так же, через local/templates, разница только в том, что для старых некомпозитных компонентов (без .ajax в имени) достаточно скопировать один template.php без дополнительных JS-обработчиков для подгрузки без перезагрузки страницы.

Обновление ядра затронет мой шаблон в local/templates?

Нет, обновления через /bitrix/admin/update_system.php и обновления модулей пишут файлы только в директорию /bitrix/. Папка /local/ в принципе не входит в зону ответственности системы обновлений и не проверяется на конфликты.

Как понять, какой шаблон сейчас реально используется у компонента на странице?

В параметрах вызова компонента на странице в визуальном редакторе или в коде компонента ищите значение TEMPLATE_NAME. Если оно пустое, применяется .default. Также можно включить показ отладочной информации компонентов в настройках модуля “Информационный блок” или через параметр show_component_info в файле dbconn.php на тестовом окружении - Битрикс покажет прямо на странице, какой файл шаблона подключен для каждого компонента.

Есть задача?

Обсудим в мессенджере

Расскажите, что нужно сделать — отвечу в течение 4 часов в рабочее время. Первая консультация бесплатно.

Самозанятый Калинкин Н. А. · работаю с физлицами и юрлицами

Продолжая пользование настоящим сайтом Вы выражаете своё согласие на обработку Ваших персональных данных (файлов куки) с использованием Yandex.Metrika.
Понятно