Выборка с учётом языка
Два пути в зависимости от того, как вы получаете элементы.
D7: подстановка на уровне запроса
use mrLexndr\Translate\IblockHelper;
$fields = ['NAME', 'CODE', 'PREVIEW_TEXT', 'DETAIL_TEXT', 'DETAIL_PAGE_URL',
'PREVIEW_PICTURE', 'COLOR', 'TITLE'];
$select = IblockHelper::prepareD7Select($iblockId, $fields);
$entity = IblockHelper::getEntityDataClass($iblockId);
if ($entity === null) {
// У инфоблока не задан символьный код API — этот путь недоступен.
return;
}
$rows = $entity::getList([
'select' => $select,
'filter' => ['IBLOCK_ID' => $iblockId, 'ACTIVE' => 'Y'],
'order' => ['ID' => 'DESC'],
'limit' => 20,
])->fetchAll();
$rows = IblockHelper::processD7Result($rows);
В $rows поле NAME уже содержит перевод, если он есть.
Именно сущность инфоблоков 2.0, а не общая таблица элементов:
prepareD7Select() обращается к свойствам через связи, а такие поля есть только
у сгенерированных классов. Если у инфоблока не задан символьный код API,
сущности нет — используйте второй путь.
Как это устроено: поля, имена которых совпадают со стандартными, кладутся в выборку под псевдонимом и очищаются на разборе результата. Файловые поля и даты проходят как есть. Если свойства с суффиксом языка нет, ищется свойство без суффикса, потом стандартное поле.
Старый API: подстановка в готовый массив
$arItem = $obElement->GetNext(true, false);
IblockHelper::substituteStandardFields($arItem);
Для раздела:
IblockHelper::substituteSectionFields($arSection);
Этот путь работает всегда и не зависит от настроек инфоблока. Им же пользуются штатные компоненты — см. Штатные компоненты.
Правило про запросы в цикле
Подстановка в цикле — нормально. Запрос в базу в цикле — нет.
Хелперы рассчитаны на то, что данные у вас уже на руках. Если для подстановки приходится идти в базу за каждым элементом, значит выборка построена неправильно, и лечится это выборкой, а не переводом.
На базовом языке ничего не происходит
Все хелперы подстановки на базовом языке возвращают исходные значения и в словарь не ходят. Поэтому оставлять вызовы в коде безопасно: на русской версии они не стоят почти ничего.
Служебные методы фасада
Кроме подстановки, на фасаде есть методы, которые обычно не нужны, но встречаются в чужом коде и в примерах. Коротко, что каждый делает.
| Метод | Что делает |
|---|---|
getSuffix() |
суффикс языка, который дописывается к имени свойства |
isDefaultLang() |
текущий язык базовый? На нём вся подстановка — пустая операция |
extractProps() |
вытаскивает свойства из массива элемента в плоский вид |
getActiveIblocksGrouped() |
список активных инфоблоков по типам, для экранов выбора |
getTranslationMap() |
карта пар «свойство — его языковой близнец» для инфоблока |
getSectionTranslationMap() |
то же для полей разделов |
getHlTranslationMap() |
то же для полей справочника |
clearTranslationMapCache() |
сбросить эти карты после правки структуры |
getEnumLookup() |
карта вариантов свойства-списка |
enumXmlKey() |
ключ варианта списка, по которому ищется пара на другом языке |
Карты кешируются: они строятся из структуры инфоблока, а она меняется редко. Поэтому после синхронизации свойств кеш сбрасывается — иначе новые языковые свойства не появились бы в подстановке до истечения кеша.
Два последних метода нужны там, где значения списков переносятся не текстом, а по совпадению внешнего кода варианта. См. Названия и подсказки свойств.