Документация

Файл theme.json и настройки темы

Как описать настройки, которые владелец магазина увидит в панели, и как прочитать их значения в шаблоне.

На этой странице

theme.json — единственный обязательный файл темы. Он говорит магазину, как тема называется, какой версии магазина требует и какие настройки владелец увидит в панели.

Минимальный файл

{
    "id": "my-theme",
    "name": "Моя тема",
    "version": "1.0.0",
    "requires": { "core": "2.0.0" }
}
Поле Обязательно Что означает
id да идентификатор темы; обязан совпадать с именем папки
name да название, которое видит владелец магазина
version да версия темы
requires.core нет, но нужно с какой версии магазина тема работает
settings нет настройки темы: панель строит форму по этому описанию

Поля author, preview и locales записать можно, но магазин их сейчас нигде не показывает — на работу темы они не влияют.

Если theme.json испорчен и не читается как JSON, магазин всё равно считает папку темой, но без имени и версии: в списке она называется по имени папки. Витрина при этом работает. А вот без самого файла папка темой не считается, и витрина, назначенная на неё, падает.

Совместимость с версией магазина

"requires": { "core": "2.0.0" }                            эта версия и новее
"requires": { "core": ">=2.0.0" }                          то же, со знаком
"requires": { "core": { "min": "2.0.0", "max": "3.0" } }   с верхней границей

Обычный случай — только нижняя граница. Верхняя нужна, когда вы точно знаете, что следующая большая версия магазина ломает вашу тему.

Ставьте ту версию, возможностями которой тема действительно пользуется, и убедитесь, что эта версия магазина уже вышла. Тема, рассчитанная на магазин новее установленного, обратится к тому, чего ещё нет, и покупатель встретит ошибку вместо страницы.

Проверка идёт до подмены папки, поэтому отказ безопасен: прежняя тема остаётся на месте, магазин продолжает работать. Владелец увидит понятное сообщение: «Это дополнение рассчитано на CartiX 3.1.0 и новее, а у вас установлена версия 2.5.0. Сначала обновите магазин».

Что тема ведёт сама

Поведение витрины — корзину, выбор варианта, отбор в разделе, окно аксессуаров — магазин подключает сам, и тема получает всё это рабочим. Если вы написали свою замену какой-то части, объявите её в манифесте, и магазин свой код подключать не станет:

"runtime": {
    "sku": "theme",
    "catalog": "theme",
    "accessories_popup": "theme"
}
Ключ Что перестанет подключать магазин
sku выбор варианта товара на карточке
catalog отбор товаров в разделе (галочки, цена, «показать ещё»)
accessories_popup окно «возьмите к этому» после покупки из каталога

Объявляйте только то, что действительно заменили: две копии поведения ответят на одно нажатие дважды, а без замены покупатель останется без возможности вовсе. Заявленное приходит скриптам в window.CartiX.runtime — по нему ваш код узнаёт, что работает он.

Настройки темы

Настройки описываются схемой: вы перечисляете группы и поля, а панель строит форму сама. Ни верстать её, ни писать код для сохранения не нужно.

"settings": {
    "groups": [
        {
            "id": "colors",
            "name": "Цвета",
            "fields": [
                { "key": "primary", "type": "color", "label": "Основной", "default": "#4f46e5" },
                { "key": "accent", "type": "color", "label": "Акцент",
                  "hint": "Цвет звёзд рейтинга и кнопки предзаказа.", "default": "#f59e0b" }
            ]
        },
        {
            "id": "catalog",
            "name": "Каталог",
            "fields": [
                { "key": "per_page", "type": "number", "label": "Товаров на странице", "default": 24 },
                { "key": "products_per_row", "type": "select", "label": "Товаров в ряд",
                  "options": [2, 3, 4, 5], "default": 4 },
                { "key": "show_sku_on_card", "type": "boolean",
                  "label": "Показывать артикул на карточке", "default": true }
            ]
        }
    ]
}

Поля группы

Ключ Что задаёт
id идентификатор группы; по нему настройка доступна как {$theme.colors.primary}
name заголовок группы в форме
fields список полей

Поля настройки

Ключ Что задаёт
key имя настройки; по нему значение доступно как {$theme.primary}
type вид поля
label подпись поля
default значение по умолчанию
hint пояснение под полем
placeholder подсказка внутри пустого поля
options список вариантов — только для select

Виды полей

type Что рисует панель
text однострочное поле
textarea многострочное поле
number число
boolean переключатель
color выбор цвета
select выбор из списка options
font выбор шрифта из готового списка
image ссылка на файл картинки

image пока рисуется обычным текстовым полем: владелец вставляет туда адрес файла, выбора картинки из галереи нет.

Как прочитать настройку в шаблоне

Два способа, оба работают всегда:

{$theme.primary}          плоско, по имени настройки
{$theme.colors.primary}   через группу

Плюс два набора есть в теме всегда, даже если вы их не объявляли:

{$theme.assets}           /theme-assets/имя-темы — адрес папки статики
{$theme.colors.primary}   {$theme.colors.accent} {$theme.colors.bg} {$theme.colors.text}

Все поля схемы присутствуют в $theme, даже незаполненные — они приходят пустыми. Шаблон на них не падает, проверка вида {if $theme.logo} безопасна.

⚠️ Настройки, не объявленной в theme.json, для магазина не существует. Написать {$theme.my_setting} и ждать значения бессмысленно: пока поля нет в схеме, значения у него нет и быть не может. Схема — источник правды.

Тот же подвох с другой стороны: настройку card_variants, которая включает показ вариантов покупки прямо на карточках товаров в списке, читает сам магазин. У базовой темы её в схеме нет — поэтому базовая тема варианты на карточках не показывает, сколько ни правь шаблон. Нужны варианты — объявите поле:

{ "key": "card_variants", "type": "boolean", "label": "Варианты покупки на карточке", "default": true }

⚠️ Имя настройки не должно совпадать с именем группы. Настройки лежат в $theme и плоско, и по группам, в одном наборе: поле colors внутри группы catalog затрёт всю группу colors.

Где хранятся значения

Значения настроек лежат у витрины, а не у темы. Отсюда три следствия, о которых нужно знать.

Настройки переживают обновление темы. Файлы заменяются целиком, значения остаются в базе — по совпадающим ключам новая версия увидит всё, что владелец настроил.

Отсюда правило автора темы: не переименовывайте ключи между версиями. Переименовали primary_color в primary — владелец получит цвет по умолчанию вместо своего и решит, что обновление сломало магазин. Нужно новое поведение — заводите новый ключ, а старый оставляйте работать.

Набор значений один на витрину, а не отдельный на каждую тему. Совпадающие ключи (primary, per_page, container_width) переезжают из темы в тему, а ключи, которых у новой темы нет, просто лежат дальше. Но сохранение настроек новой темы перезаписывает весь набор своими полями — то есть переключились на другую тему, нажали «Сохранить» — значения прежней темы потеряны. Владельцу, который собирается вернуться, стоит сначала выписать их или скачать архив темы.

При нескольких витринах каждая настраивается отдельно: одна и та же тема может быть синей на одной витрине и зелёной на другой.

Настройка обязана что-то делать

Поле, которое сохраняется и ни на что не влияет, — обман владельца магазина. Объявили в схеме container_width — читайте его в разметке:

<style>:root { --container: {$theme.container_width}px; }</style>

Хорошая привычка: писать hint там, где название поля не объясняет последствие, и placeholder в каждом поле ввода.

Обновлено 25 августа 2026