При работе с интернет-магазином на 1С-Битрикс иногда возникает задача автоматически задать цену товаров — например, взять её из определённого свойства инфоблока или подгрузить из внешнего источника. В этой статье разберём, как написать подобный скрипт и какие методы d7 для этого использовать.

Устанавливаем цену из свойства инфоблока

Предположим, есть инфоблок, где в свойстве «Цена» (например, CUSTOM_PRICE) хранится стоимость товара и ее нужно установить в качестве базовой цены для всех элементов.

Для работы с элементами используется класс \Bitrix\Iblock\Elements\ElementIBLOCKCODETable, где IBLOCKCODE — Символьный код API. Он устанавливается в настройках инфоблока. Для примера наш код будет mycatalog и, название класса, соответственно, \Bitrix\Iblock\Elements\ElementMycatalogTable.

<?php

require($_SERVER['DOCUMENT_ROOT'] . '/bitrix/modules/main/include/prolog_before.php');

$catalogGroupId = 1; // id типа цены

try {
    $elements = \Bitrix\Iblock\Elements\ElementMyCatalogTable::getList([
        'select' => ['ID', 'NAME', 'CUSTOM_PRICE', 'PRICE.ID'],
        'filter' => [],
        'runtime' => [
            (new Bitrix\Main\ORM\Fields\Relations\Reference(
                "PRICE",
                Bitrix\Catalog\PriceTable::class,
                Bitrix\Main\Entity\Query\Join::on("this.ID", "ref.PRODUCT_ID")
                    ->where("ref.CATALOG_GROUP_ID", "=", $catalogGroupId)
            ))->configureJoinType(
                \Bitrix\Main\ORM\Query\Join::TYPE_LEFT,
            )
        ]
    ])->fetchCollection();

    foreach ($elements as $element) {
        $price = $element->get('PRICE');
        $newPriceValue = $element->getCustomPrice()?->getValue();

        if (!is_null($newPriceValue)) {
            // обновляем текущую цену или добавляем новую
            if (is_object($price)) {
                $result = \Bitrix\Catalog\Model\Price::update($price->getId(), ['PRICE' => $newPriceValue]);
            } else {
                $result = \Bitrix\Catalog\Model\Price::add([
                    'PRODUCT_ID' => $element->getId(),
                    'CATALOG_GROUP_ID' => $catalogGroupId,
                    'CURRENCY' => 'RUB', // валюту по умолчанию можно получить через \Bitrix\Currency\CurrencyManager::getBaseCurrency()
                    'PRICE' => $newPriceValue,
                ]);
            }
            if (!$result->isSuccess()) {
                echo sprintf(
                    "Ошибка при обновлении элемента %s: %s\n",
                    $element->getName(),
                    implode(', ', $result->getErrorMessages())
                );
            }
        }
    }
} catch (Throwable $e) {
    echo "Непредвиденная ошибка " . $e->getMessage();
}

require($_SERVER["DOCUMENT_ROOT"] . '/bitrix/modules/main/include/epilog_after.php');

Кратко разберем, что же здесь происходит:

  • Выбираем все элементы из инфоблока my_catalog. В select явно добавлено свойство CUSTOM_PRICE, из которого мы будем устанавливать цену
  • В примере фильтр пустой и предполагаем, что обновлять будем сразу все элементы. В реальности можно как угодно ограничить выборку
  • В секции runtime мы джойним таблицу с текущими ценами элементов. При этом используется LEFT JOIN, чтобы при отсутствии цены элемент инфоблока все равно попал в выборку. Также мы ограничиваем join типом цены, по которой будем обновлять.
  • Пробегаемся по всем элементам и обновляем цену, если она уже есть или добавляем, если ее ранее не было

Больше статей и материалов по web-разработке в tg-канале - подписывайтесь!

Подписаться в telegram

Добавить комментарий

Ваш адрес email не будет опубликован.