С выходом 20-й версии 1С Битрикс, появилась возможность работы с элементами инфоблока средствами ORM. Для того, чтобы начать использовать эту возможность вам необходимо зайти в настройки информационного блока и задать значения для поля «Символьный код API». Согласно документации, символьный код API это строка от 1 до 50 символов состоящая из букв и  цифр, начинающаяся с буквы. Я взял инфоблок «Одежда» из коробки БУС редакции «Бизнес» и задал код products.

Символьный код API

Для работы с элементами инфоблока средствами ORM, необходимо использовать класс \Bitrix\Iblock\Elements\Element_Символьный_код_API_инфоблока_Table, в моём случае это класс \Bitrix\Iblock\Elements\ElementProductsTable. Можно убедиться в этом вызвав следующий код:


//Подключим модуль «Информационные блоки»
\Bitrix\Main\Loader::includeModule('iblock');

//Имя ORM класса для работы с инфоблоком «Одежда»
echo \Bitrix\Iblock\Iblock::wakeUp(IBLOCK_CATALOG_ID)->getEntityDataClass(); //Где IBLOCK_CATALOG_ID - содержит ID инфоблока «Одежда»


Выведет строку \Bitrix\Iblock\Elements\ElementProductsTable. Давайте рассмотрим практические примеры работы, подберём аналоги уже привычных нам методов старого ядра.

Аналог CIBlockElement::GetById() в ORM

Для получения данных по элементу инфоблока, по ID этого элемента, используется метод getByPrimary() вашего «виртуального класса»:


$product = \Bitrix\Iblock\Elements\ElementProductsTable::getByPrimary(10, [ //10 - ID товара, «Платье, Красная фея»
    'select' => ['ID', 'NAME', 'PREVIEW_TEXT', 'DETAIL_PICTURE', 'MANUFACTURER', 'MATERIAL'],
])->fetch();

В переменной $product будет примерно такая информация:

Содержимое переменной: Array
(
    [ID] => 10
    [NAME] => Платье Красная Фея
    [PREVIEW_TEXT] => 
    [DETAIL_PICTURE] => 68
    [IBLOCK_ELEMENTS_ELEMENT_PRODUCTS_MANUFACTURER_ID] => 2148
    [IBLOCK_ELEMENTS_ELEMENT_PRODUCTS_MANUFACTURER_IBLOCK_ELEMENT_ID] => 10
    [IBLOCK_ELEMENTS_ELEMENT_PRODUCTS_MANUFACTURER_IBLOCK_PROPERTY_ID] => 10
    [IBLOCK_ELEMENTS_ELEMENT_PRODUCTS_MANUFACTURER_VALUE] => Россия "Модница"
    [IBLOCK_ELEMENTS_ELEMENT_PRODUCTS_MATERIAL_ID] => 2156
    [IBLOCK_ELEMENTS_ELEMENT_PRODUCTS_MATERIAL_IBLOCK_ELEMENT_ID] => 10
    [IBLOCK_ELEMENTS_ELEMENT_PRODUCTS_MATERIAL_IBLOCK_PROPERTY_ID] => 11
    [IBLOCK_ELEMENTS_ELEMENT_PRODUCTS_MATERIAL_VALUE] => трикотаж
)

Обратите внимание, что ключи пользовательских свойств инфоблока, MANUFACTURER и MATERIAL указываются как есть, без префикса PROPERTY_. Чтобы избежать таких длинных ключей как IBLOCK_ELEMENTS_ELEMENT_PRODUCTS_MANUFACTURER_IBLOCK_ELEMENT_ID в результирующем массиве, можно использовать псевдонимы, вот так:

$product = \Bitrix\Iblock\Elements\ElementProductsTable::getByPrimary(10, [ //10 - ID товара, «Платье, Красная фея»
    'select' => ['ID', 'NAME', 'PREVIEW_TEXT', 'DETAIL_PICTURE', 'MANUFACTURER_' => 'MANUFACTURER', 'MATERIAL_'=>'MATERIAL'],
])->fetch();

В таком случае, данные приходят в более удобном виде:

Содержимое переменной: Array
(
    [ID] => 10
    [NAME] => Платье Красная Фея
    [PREVIEW_TEXT] => 
    [DETAIL_PICTURE] => 68
    [MANUFACTURER_ID] => 2148
    [MANUFACTURER_IBLOCK_ELEMENT_ID] => 10
    [MANUFACTURER_IBLOCK_PROPERTY_ID] => 10
    [MANUFACTURER_VALUE] => Россия "Модница"
    [MATERIAL_ID] => 2156
    [MATERIAL_IBLOCK_ELEMENT_ID] => 10
    [MATERIAL_IBLOCK_PROPERTY_ID] => 11
    [MATERIAL_VALUE] => трикотаж
)

Элемент инфоблока как объект

С данными элемента инфоблока можно работать не только как с массивом, но и как с объектом. Для этого используйте метод fetchObject() вместо fetch() после вызова getByPrimary().


$product = \Bitrix\Iblock\Elements\ElementProductsTable::getByPrimary(10, [ //10 - ID товара, «Платье, Красная фея»
    'select' => ['ID', 'NAME', 'PREVIEW_TEXT', 'DETAIL_PICTURE', 'MANUFACTURER_' => 'MANUFACTURER', 'MATERIAL_'=>'MATERIAL'],
])->fetchObject();

В данном случае, в $product будет получен объект класса Bitrix\Iblock\Elements\EO_ElementProducts с множеством методов для работы с ним. Например:

//Получить id товара
echo $product->getId(); //10

//Получить наименование товара
echo $product->getName(); //"Платье Красная Фея"

//Получить id детального изображения
echo $product->getDetailPicture(); //68

Как видите для получения значений элемента инфоблока используются так называемые геттеры (методы getXXXX где XXX — название поля в «верблюжьей нотации» или CamelCase). Существует так же общий метод get() который принимает наименование поля, значение которого вам нужно получить. Например:

//Получим id элемента
echo $product->Get('ID'); // 10

//Получим наименование элемента
echo $product->Get('NAME'); // "Платье Красная фея"

Свойства элемента

Свойства элементов (когда мы работаем с ними в виде объекта) так же получаются при помощи геттеров (методов getXXXX где XXXX — код свойства записанный как CamelCase). У каждого свойства есть поле значения VALUE и описания DESCRIPTION и соответcnвующие методы для доступа к ним getValue() и getDescription().  Рассмотрим пример:


//Получим данные товара
$product = \Bitrix\Iblock\Elements\ElementProductsTable::getByPrimary(10, [ //10 - ID товара, «Платье, Красная фея»
    'select' => ['ID', 'NAME', 'PREVIEW_TEXT', 'DETAIL_PICTURE', 'MANUFACTURER', 'MATERIAL'], //MANUFACTURER и MATERIAL свойства типа «Строка»
])->fetchObject();

//Получим значение свойства MANUFACTURER
var_dump($product->getManufacturer()->getValue());

В результате получим строку:

string(29) "Россия "Модница""

Чтобы получить дополнительную информацию для некоторых типов свойств через ORM, нужно указать дополнительный ключ при выборке свойства:

  • FILE — свойство типа файл
  • ITEM — свойство типа список,
  • ELEMENT — свойство типа привязка к элементу инфоблока
  • SECTION — свойство типа привязка к разделу инфоблока

Давайте рассмотрим это детальнее. У нашего элемента есть следующие свойства требуемых типов:

  • MORE_PHOTO — Картинки галереи (тип файл)
  • NEWPRODUCT — Новинка (тип список)
  • RECOMMEND — С этим товаром рекомендуем (тип привязка к элементу)
  • NEWS_SECTION — Показывать в рекламном блоке в новостях (тип привязка к разделу), это я создал для теста, в «коробке» такого нет 

Давайте получим их в ORM:


//Получим данные товара
$product = \Bitrix\Iblock\Elements\ElementProductsTable::getByPrimary(10, [
    'select' => [
        'ID',
        'NAME',
        'PREVIEW_TEXT',
        'DETAIL_PICTURE',
        'MORE_PHOTO.FILE', //Обратите внимание на доп.ключи
        'NEWPRODUCT.ITEM',
        'RECOMMEND.ELEMENT',
        'NEWS_SECTION.SECTION'
    ],
])->fetchObject();

Свойство типа файл в ORM

Рассмотрим следующий код:

//Выведем доп.фотографии товара
foreach ($product->getMorePhoto()->getAll() as $photo){
    echo '<img src="/upload/' . $photo->getFile()->getSubdir() . '/' . $photo->getFile()->getFileName() . '" alt="'. $product->getName() .'" />';
}


Обратите внимание во первых на метод getAll(), т.к. свойство MORE_PHOTO — множественное, по сути оно представляет из себя коллекцию значений. Чтобы получить всю коллекцию и применяют метод getAll(). Далее при обходе элемента коллекции свойства типа файл мы получаем в распоряжение метод getFile() , который в свою очередь открывает нам доступ к методам getSubdir() и getFileName() для получения дополнительной информации о файле.

Свойство типа список в ORM


//Свойство типа список
var_dump($product->getNewproduct()->getItem()->getId());
//int(1)
var_dump($product->getNewproduct()->getItem()->getXmlId());
//string(1) "Y"
var_dump($product->getNewproduct()->getItem()->getValue());
//string(4) "да"

Как видите для свойств типа список (при использовании специального ключа .ITEM) добавляется метод getItem() который позволяет получить ID значения списка методом getId(), внешний код значения getXmlId() и само значение методом getValue().

Свойство типа привязка к элементам инфоблока в ORM


//Получим привязанные элементы
foreach ($product->getRecommend()->getAll() as $recommendedProduct){
    echo 'Рекомендуемый товар ID -' . $recommendedProduct->getElement()->getId() . ' наименование - ' . $recommendedProduct->getElement()->getName() . '<br/>';
}

Т.е. рекомендуемые товары так же являются множественным свойством получаем коллекцию значений через getAll(). Далее мы видим, что элементу коллекции доступен метод getElement() через который мы можем узнать некоторую информацию об элементе, например ID getId() и наименование getName().

Свойство типа привязка к разделу инфоблока в ORM


//Получим id привязанного раздела
var_dump($product->getNewsSection()->getSection()->getId());
//Получим наименование привязанного раздела
var_dump($product->getNewsSection()->getSection()->getName());

Как и в случае с предыдущим типом свойств нам доступен метод getSection() через который мы можем узнать некоторую дополнительную информацию о связанном с элементом разделе другого инфоблока.

Аналог CIBlockElement::GetList() в ORM

В качестве аналога к всем полюбившимся методу CIBlockElement::GetList() используется getList() из D7 который применялся к HL-блокам ранее. Приведу пример:


$products = \Bitrix\Iblock\Elements\ElementProductsTable::getList([
    'select' => ['ID', 'NAME', 'PREVIEW_TEXT', 'DETAIL_PICTURE', 'MANUFACTURER_' => 'MANUFACTURER', 'MATERIAL_'=>'MATERIAL'],
    'filter' => ['=ACTIVE' => 'Y'],
])->fetchAll();
foreach ($products as $product) {
    //...что-то делаем с данными продуктов...
}

Тут всё как в HL блоках D7, поэтому детально разбирать этот вопрос я не стану.

Кеширование результата выборки данных

В Битрикс ORM несколько упростили процедуру кеширования результатов выборки из инфоблока. Для этого вам достаточно добавить в массив параметра метода getList() поле cache и указать параметры кеширования:


$product = \Bitrix\Iblock\Elements\ElementCatalogTable::getList([
    'select' => [
        'ID', 
        'NAME', 
        'PREVIEW_TEXT', 
        'DETAIL_PICTURE'
    ],
    'filter' => [
        'ID' => 10,
    ],
    'cache' => [
        'ttl' => 3600
    ],
])->fetchObject();

В одной из ближайших статей я напишу простой компонент в двух версиях, старой с использованием классических приёмов работы с ифноблокми и новой с использованием ORM и сравню производительность.

Надеюсь статья окажется для вас полезной, желаю удачи!

Полезная статья?
(Голосов: 37, Рейтинг: 3.92)
Вам также могут понравиться
Обновление остатков товара на складе в 1С Битрикс

Обновление остатков товара на складе в 1С Битрикс

Как правильно обновлять остатки товара на сайта под управлением CMS 1С Битрикс.

Английский для программистов

Английский для программистов

Почему IT-специалисту необходимо освоить английский язык? Разбираем в статье.

Как подключить CSS и JS файлы к шаблону 1С Битрикс

Как подключить CSS и JS файлы к шаблону 1С Битрикс

Как правильно подключать стили и скрипты к шаблону 1С Битрикс.


Комментарии
Защита от автоматических сообщений
CAPTCHA
Введите слово на картинке
04.12.2024 | Иван

Спасибо, описали гораздо проще и лучше, чем на офф сайте битрикса) Подскажите, а как через D7 сохранять значения в свойства элемента? Допустим есть форма на сайте. Мы сохраняем в ИБ заявки на услуги по api. Как передать значения в свойства элемента на D7 и ORM?

Комментировать | 0  
Защита от автоматических сообщений
CAPTCHA
Введите слово на картинке
Закрыть
04.12.2024 | Алексей

$element->setPropertyName($value);//свойство типа строка $element->addToPropertyName($value);//множественное свойство типа строка $element->save();

Комментировать | 0  
Защита от автоматических сообщений
CAPTCHA
Введите слово на картинке
Закрыть