понедельник, 28 апреля 2014 г.

Две заметки о Bitrix

1. Для создания сложных форм на bitrix я использую кастомный компонент в котором вытаскиваю все данные о инфоблоке с помощью такого запроса:
function getIblockProps($id) {
 global $DB;
 $sql = "SELECT b.id, b.code, b.name,
   -----
   p.id as pid, p.code as pcode, p.name as pname, p.SORT psort, 
    UPPER(CASE 
     WHEN p.USER_TYPE IS NOT NULL THEN p.USER_TYPE
     WHEN p.PROPERTY_TYPE = 'S' AND p.ROW_COUNT > 1 THEN 'T'
     ELSE p.PROPERTY_TYPE
    END) as ptype, 
    CASE WHEN p.MULTIPLE = 'Y' THEN 1 END as pmultiple, CASE WHEN p.MULTIPLE = 'Y' THEN p.MULTIPLE_CNT END pmultiple_cnt, 
   CASE WHEN p.LINK_IBLOCK_ID > 0 THEN p.LINK_IBLOCK_ID END as piblock, 
   CASE WHEN p.IS_REQUIRED = 'Y' THEN p.IS_REQUIRED END preq, p.HINT as phint,
   -----
   e.ID as eid, e.VALUE as evalue, e.DEF as edef, e.SORT as esort
  FROM b_iblock b , b_iblock_property p
  LEFT JOIN b_iblock_property_enum e
  ON(e.property_id = p.id)
  WHERE b.id = %u
  AND b.id = p.IBLOCK_ID AND p.ACTIVE = 'Y'
  ORDER BY p.sort,e.SORT";
 $rs = $DB->Query( sprintf( $sql, intval($id) ) );

 $rows = array();
 while ($row = $rs->Fetch()) {
  $rows[] = $row;
 }

 return $rows;
}

Запрос берет информацию о полях и свойствах инфоблока. Если поле ссылочное, то функцию можно вызывать рекурсивно.

2. Особенность создания товарных предложений через код.
Создали мы товарное предложение через код:
$el = new CIBlockElement;  
$id = $el->Add($arFields);

Задали цену:
CPrice::SetBasePrice( $id,  $arFields['PRICE'],  "RUB", 1);

Заполнили остатки:
$arFields = Array(
  "PRODUCT_ID" => $id,
  "STORE_ID" => 1,
  "AMOUNT" => $v['Количество'],
 );
 
CCatalogStoreProduct::Add($arFields);

Вроде все. Но товар не покупается, хотя все атрибуты присутствуют.

Чтобы все заработало, нужно еще раз добавить (именно добавить, а не обновить) предложение, но другой функцией:
$arFields = array('ID'=>$id, 'PRICE_TYPE' => 'S', 'QUANTITY' => floatval($f['Количество']));
CCatalogProduct::Add($arFields);