Полное руководство по работе с элементами инфоблоков через D7 ORM в Битрикс
Введение в работу с элементами инфоблоков через ORM
С выходом 20-й версии 1С-Битрикс появилась удобная возможность работать с элементами инфоблоков через объектно-реляционную модель (ORM) ядра D7. Этот подход предлагает более современный и структурированный способ взаимодействия с данными.
Основные преимущества ORM подхода:
- Объектно-ориентированный синтаксис
- Автодополнение в современных IDE
- Безопасность типов данных
- Встроенное кеширование
- Отсутствие проблем с дублированием строк
Перед началом работы необходимо убедиться, что для инфоблока задан символьный код API в настройках. Это строка от 1 до 50 символов, состоящая из латинских букв и цифр.
Подготовка к работе
Первым делом нужно подключить модуль инфоблоков:
use Bitrix\Main\Loader;
Loader::includeModule('iblock');
Класс для работы с элементами конкретного инфоблока можно получить несколькими способами. Самый простой - по ID инфоблока:
$entityClass = \Bitrix\Iblock\Iblock::wakeUp($iblockId)->getEntityDataClass();
Или через IblockTable с предварительной выборкой:
$iblock = \Bitrix\Iblock\IblockTable::getList([
'select' => ['ID', 'API_CODE'],
'filter' => ['=ID' => $iblockId]
])->fetchObject();
$entityClass = $iblock->getEntityDataClass();
Получение элементов
Получение одного элемента (аналог GetByID)
Работа с элементом как с массивом:
$element = \Bitrix\Iblock\Elements\ElementCatalogTable::getByPrimary($elementId, [
'select' => ['ID', 'NAME', 'DETAIL_TEXT', 'DETAIL_PICTURE', 'ARTNUMBER_' => 'ARTNUMBER'],
])->fetch();
Работа с элементом как с объектом (рекомендуемый способ):
$element = \Bitrix\Iblock\Elements\ElementCatalogTable::getByPrimary($elementId, [
'select' => ['ID', 'NAME', 'DETAIL_PICTURE']
])->fetchObject();
// Получение значений
echo $element->getName(); // через геттер
echo $element->get('NAME'); // через универсальный метод
Выборка элементов (аналог GetList)
Пример выборки с фильтрацией и кешированием:
$elements = \Bitrix\Iblock\Elements\ElementCatalogTable::getList([
'select' => ['ID', 'NAME', 'ARTNUMBER_' => 'ARTNUMBER'],
'filter' => [
'=ACTIVE' => 'Y',
'>=DATE_ACTIVE_FROM' => new \Bitrix\Main\Type\DateTime(),
],
'order' => ['SORT' => 'ASC', 'NAME' => 'DESC'],
'cache' => ['ttl' => 3600] // Кеширование на 1 час
])->fetchCollection();
foreach ($elements as $element) {
echo $element->getName();
}
Работа со свойствами элементов
Базовые типы свойств
Текст/Число:
$element = \Bitrix\Iblock\Elements\ElementCatalogTable::getByPrimary($id, [
'select' => ['ID', 'ARTNUMBER', 'PRICE', 'DESCRIPTION']
])->fetchObject();
// Использование
echo $element->getArtnumber()->getValue();
echo $element->getPrice()->getValue();
Файлы:
$element = \Bitrix\Iblock\Elements\ElementCatalogTable::getByPrimary($id, [
'select' => [
'ID',
'MAIN_IMAGE' => 'DETAIL_PICTURE.FILE',
'GALLERY' => 'MORE_PHOTO.FILE'
]
])->fetchObject();
// Основное изображение
echo $element->getMainImage()->getFile()->getFileName();
// Галерея изображений
foreach ($element->getGallery()->getAll() as $file) {
if (!$file->getFile()) continue;
echo $file->getFile()->getId().'\n';
echo $file->getFile()->getFileName().'\n';
echo $file->getFile()->getSubdir().'\n';
echo $file->getFile()->getFileSize().'\n';
echo $file->getFile()->getWidth().'\n';
echo $file->getFile()->getHeight().'\n';
echo '/upload/' . $file->getFile()->getSubdir() . '/' . $file->getFile()->getFileName();
}
Сложные типы свойств
Списки:
$element = \Bitrix\Iblock\Elements\ElementCatalogTable::getByPrimary($id, [
'select' => [
'ID',
'AVAILABILITY',
'AVAILABILITY_DATA' => 'AVAILABILITY.ITEM',
'TAGS' => 'TAGS.ITEM'
]
])->fetchObject();
// Простое значение
echo $element->getAvailability()->getValue();
// С дополнительными данными
echo $element->getAvailabilityData()->getItem()->getValue();
echo $element->getAvailabilityData()->getItem()->getXmlId();
// Множественное свойство
foreach ($element->getTags()->getAll() as $tag) {
echo $tag->getItem()->getValue();
}
Привязки к элементам и разделам:
$element = \Bitrix\Iblock\Elements\ElementCatalogTable::getByPrimary($id, [
'select' => [
'ID',
'RELATED_ITEMS' => 'RELATED.ELEMENT',
'PRIMARY_SECTION_DATA' => 'IBLOCK_SECTION.SECTION',
'ADDITIONAL_SECTIONS' => 'ADDITIONAL_SECTIONS.SECTION'
]
])->fetchObject();
// Привязанные элементы
foreach ($element->getRelatedItems()->getAll() as $related) {
echo $related->getElement()->getName();
}
// Основной раздел
echo $element->getPrimarySectionData()->getSection()->getName();
// Дополнительные разделы
foreach ($element->getAdditionalSections()->getAll() as $section) {
echo $section->getSection()->getName();
}
Чтобы получить свойства элемента, добавленного в свойство типа "привазка к элементу", необходимо в select передать через точку имя свойства:
'select'=>[ ... 'ORGANIZER.ELEMENT', 'ORGANIZER.ELEMENT.USER', ... ]
И в таком варианте это свойство можно получить так:
$travelObject->getOrganizer()?->getElement()?->get('USER')?->getValue(),
Практические примеры
Пример 1: Получение товара с полными данными
$product = \Bitrix\Iblock\Elements\ElementProductsTable::getByPrimary($id, [
'select' => [
'ID',
'NAME',
'CODE',
'DETAIL_PICTURE_FILE' => 'DETAIL_PICTURE.FILE',
'PRICE',
'CURRENCY',
'ARTICLE' => 'ARTNUMBER',
'COLOR' => 'COLOR.ITEM',
'SIZES' => 'AVAILABLE_SIZES.ITEM',
'BRAND' => 'BRAND.ELEMENT',
'CATEGORY' => 'IBLOCK_SECTION.NAME',
'RELATED' => 'RELATED_PRODUCTS.ELEMENT'
],
'cache' => ['ttl' => 86400]
])->fetchObject();
// Использование
echo $product->getName();
echo $product->getPrice()->getValue();
echo $product->getBrand()->getElement()->getName();
foreach ($product->getRelated()->getAll() as $related) {
echo $related->getElement()->getName();
}
Пример 2: Сложная выборка новостей
$newsList = \Bitrix\Iblock\Elements\ElementNewsTable::getList([
'select' => [
'ID',
'NAME',
'DATE' => 'ACTIVE_FROM',
'PREVIEW_TEXT',
'PREVIEW_IMAGE' => 'PREVIEW_PICTURE.FILE',
'AUTHOR' => 'AUTHOR.ELEMENT',
'TAGS' => 'TAGS.ITEM',
'VIEW_COUNT' => 'SHOW_COUNTER'
],
'filter' => [
'=ACTIVE' => 'Y',
'<=ACTIVE_FROM' => new \Bitrix\Main\Type\DateTime(),
'>=ACTIVE_TO' => new \Bitrix\Main\Type\DateTime(),
],
'order' => ['ACTIVE_FROM' => 'DESC'],
'limit' => 10,
'cache' => ['ttl' => 3600]
])->fetchCollection();
foreach ($newsList as $news) {
echo $news->getName();
echo $news->getAuthor()->getElement()->getName();
}
Оптимизация работы
- Используйте только необходимые поля в select - это уменьшает объем обрабатываемых данных
- Применяйте кеширование для часто используемых запросов
- Используйте fetchCollection вместо fetchAll при работе с объектами
- Комбинируйте подходы - для сложных сценариев можно сочетать ORM и старые API методы
- Обрабатывайте ошибки:
try {
$element = \Bitrix\Iblock\Elements\ElementCatalogTable::getByPrimary($id, [
'select' => ['ID', 'NAME']
])->fetchObject();
if (!$element) {
throw new \Exception('Element not found');
}
// Работа с элементом
} catch (\Exception $e) {
// Обработка ошибки
echo $e->getMessage();
}
Заключение
ORM D7 предоставляет мощный и удобный инструмент для работы с элементами инфоблоков. По сравнению с традиционными методами, этот подход предлагает:
- Более чистый и читаемый код
- Лучшую поддержку в IDE
- Встроенные механизмы безопасности
- Гибкие возможности кеширования
- Удобную работу со сложными типами данных
Рекомендации по эффективному использованию:
- Всегда указывать явный select
- Использовать объектный подход (fetchObject/fetchCollection)
- Кешировать запросы там, где это уместно
- Комбинировать ORM с другими современными возможностями Битрикс
Пример комплексного использования:
// Получаем класс для работы с инфоблоком
$iblockClass = \Bitrix\Iblock\Iblock::wakeUp($iblockId)->getEntityDataClass();
// Выборка элементов
$elements = $iblockClass::getList([
'select' => [
'ID',
'NAME',
'DETAIL_PAGE_URL' => 'IBLOCK.DETAIL_PAGE_URL',
'PROPERTIES' => [
'PRICE',
'OLD_PRICE',
'COLOR' => 'COLOR.ITEM',
'SIZE' => 'SIZE.ITEM'
]
],
'filter' => [
'=ACTIVE' => 'Y',
'!PROPERTY_PRICE' => false,
'<=PROPERTY_OLD_PRICE' => 1000
],
'order' => ['PROPERTY_PRICE' => 'ASC'],
'limit' => 5,
'cache' => ['ttl' => 3600, 'cache_joins' => true]
])->fetchCollection();
// Обработка результатов
foreach ($elements as $element) {
$detailUrl = \CIBlock::ReplaceDetailUrl(
$element->getIblock()->getDetailPageUrl(),
$element->collectValues(),
false,
'E'
);
echo '<a href="'.$detailUrl.'">'.$element->getName().'</a>';
echo 'Price: '.$element->getPrice()->getValue();
}
Таким образом, ORM D7 для работы с инфоблоками в Битрикс - это современный, эффективный и безопасный способ взаимодействия с данными, который стоит освоить каждому разработчику, работающему с этой CMS.
Обновление от 29.12.2025 г
Пример выборки, позволяющий сразу получить данные об анонсовом и детальном изображениям товаров
use Bitrix\Iblock\Elements\ElementStoriesTable;
use Bitrix\Main\Entity\ReferenceField;
use Bitrix\Main\FileTable;
use Bitrix\Main\Loader;
use Bitrix\Main\Type\DateTime;
private function getStoriesForRss(): array
{
if (!Loader::includeModule('iblock')) {
return [];
}
$stories = [];
try {
$filterDate = new DateTime();
$filterDate->add('- 30 days');
$elements = ElementStoriesTable::getList([
'select' => [
'ID',
'NAME',
'CODE',
'PREVIEW_TEXT',
'DETAIL_TEXT',
'PREVIEW_PICTURE',
'DETAIL_PICTURE',
'DATE_CREATE',
'TIMESTAMP_X',
'ACTIVE_FROM',
'PREVIEW_PICTURE_FILE' => 'PREVIEW_PICTURE_FILE',
'DETAIL_PICTURE_FILE' => 'DETAIL_PICTURE_FILE',
'MORE_PHOTOS' => 'MORE_PHOTO.FILE'
],
'filter' => [
'=ACTIVE' => 'Y',
'!=CODE' => false,
'!=MODERATE.VALUE' => 'Y',
'!=DRAFT.VALUE' => 'Y',
'!=REJECT.VALUE' => 'Y',
'>=TIMESTAMP_X' => $filterDate
],
'order' => ['TIMESTAMP_X' => 'DESC'],
'runtime' => [
new ReferenceField(
'PREVIEW_PICTURE_FILE',
FileTable::class,
['=this.PREVIEW_PICTURE' => 'ref.ID'],
['join_type' => 'LEFT']
),
new ReferenceField(
'DETAIL_PICTURE_FILE',
FileTable::class,
['=this.DETAIL_PICTURE' => 'ref.ID'],
['join_type' => 'LEFT']
)
]
])->fetchCollection();
foreach ($elements as $element) {
$story = $this->enrichStoryData($element);
if ($story) {
$stories[] = $story;
}
if (count($stories) >= self::MAX_ITEMS) {
break;
}
}
} catch (Exception $e) {
CEventLog::Add([
'SEVERITY' => 'ERROR',
'AUDIT_TYPE_ID' => 'RSS_GENERATION',
'MODULE_ID' => 'pai.seometa',
'ITEM_ID' => 'rss_generator',
'DESCRIPTION' => 'Error getting stories: ' . $e->getMessage(),
]);
}
return $stories;
}