<?require($_SERVER["DOCUMENT_ROOT"]. "/bitrix/modules/main/include/prolog_before.php");?>
<?
CModule::IncludeModule('iblock');
class ClImportCategory extends ClImportConfig
{
public $arCategory = array();
public function __construct() {}
public function __destruct()
{
unset($arCategory);
}
/**
* Получаем список всех категорий из xml.
*/
public function AddCatsFromXml($addTo = 'db')
{
$reader = new XMLReader();
$reader->open($_SERVER["DOCUMENT_ROOT"].$this->xmlSiteUrl.$this->xmlFile);
$counter = 0;
while ($reader->read())
{
if ($reader->nodeType == XMLReader::ELEMENT && $reader->localName == 'categories')
{
while ($reader->read())
{
if ($reader->nodeType == XMLReader::ELEMENT)
{
$sectionId = $reader->getAttribute('id');
$parentId = $reader->getAttribute('parentId');
}
elseif ($reader->nodeType == XMLReader::TEXT)
{
switch($addTo)
{
case 'ew':
case 'db':
if ($counter < $this->maxAddCat)
{
$id = $this->AddCats(
$reader->value,
$sectionId,
$parentId
);
$this->AddCat2Session(
$id,
$reader->value,
$sectionId,
$parentId
//$this->translitIt($reader->value)
);
if ($addTo == 'ew')
{
$this->arCategory[] = array(
'ID' => $id,
'UF_ID' => $sectionId,
'NAME' => $reader->value,
'UF_PARENT_ID' => $parentId
);
}
}
else
{
break 3;
}
$counter++;
break;
case 'array':
$this->arCategory[] = array(
'UF_ID' => $sectionId,
'NAME' => $reader->value,
'UF_PARENT_ID' => $parentId
);
break;
case 'session':
if ($counter < $this->maxAddCat)
{
$this->AddCat2Session(
$counter,
$reader->value,
$sectionId,
$parentId
//$this->translitIt($reader->value)
);
}
else
{
break 3;
}
$counter++;
break;
}
}
if ($reader->nodeType == XMLReader::END_ELEMENT && $reader->localName == 'categories')
{
break;
}
}
}
if ($reader->nodeType == XMLReader::END_ELEMENT && $reader->localName == 'categories')
{
break;
}
}
$reader->close();
unset($reader);
//echo "<pre>"; var_dump(count($_SESSION['CATS'])); echo "</pre>";
//die();
}
/**
* Добовляем разделы в ИБ
* @param $name
* @param $ufId
* @param $ufParentId
* @param bool $code
* @return bool|int
*/
public function AddCats($name, $ufId, $ufParentId, $code = false)
{
$bs = new CIBlockSection;
$arFields = array(
'IBLOCK_ID' => $this->iblockId,
'IBLOCK_SECTION_ID' => false,
'NAME' => $name,
//'CODE' => !$code ? $code : $this->translitIt($name),
'UF_ID' => $ufId,
'UF_PARENT_ID' => $ufParentId,
);
$id = $bs->Add($arFields);
if (!$id)
{
$this->pre($bs->LAST_ERROR);
die('no add elem');
}
else
{
$this->pre('Добавлена категория: '.$name.'<br>');
return $id;
}
}
/**
* Перегруппировка массива по атрибуту parentId
*/
public function GetArCatParentId()
{
foreach ($_SESSION['CATS'] as $key => $arItem)
{
$_SESSION['CATS_PARENT_ID'][$arItem['UF_PARENT_ID']][] = array(
$arItem['ID'],
$arItem['NAME'],
$arItem['UF_ID'],
$arItem['UF_PARENT_ID'],
$arItem['CODE']
);
}
}
/**
* Удалить разделы без корневого родителя
* @param $parentId
*/
public function DelateCatOrphan($parentId)
{
if (isset($_SESSION['CATS_PARENT_ID'][$parentId]))
{
foreach ($_SESSION['CATS_PARENT_ID'][$parentId] as $arItem)
{
$_SESSION['CATS_WITHOUT_ORPHAN'][] = array(
'ID' => $arItem[0],
'NAME' => $arItem[1],
'UF_ID' => $arItem[2],
'UF_PARENT_ID' => $arItem[3],
'CODE' => $arItem[4]
);
$this->DelateCatOrphan($arItem[2]);
}
}
}
/**
* Создаем связи между категориями
* @param $arElement
* @return bool|int
*/
public function UpdateRelation($arElement)
{
$sectionId = $this->GetParentID($arElement['UF_PARENT_ID']);
$bs = new CIBlockSection;
$arFields = array('IBLOCK_SECTION_ID' => $sectionId);
$result = $bs->Update($arElement['ID'], $arFields);
if ($result)
{
return $result;
}
else
{
$this->pre($bs->LAST_ERROR);
die('no upd elem');
}
}
/**
* Получаем ID категории сайта из родителя XML
* @param $parentId
* @return $id
*/
function GetParentId($parentId)
{
foreach ($_SESSION['CATS'] as $key => $arItem)
{
if ($parentId == $arItem['UF_ID'])
{
return $arItem['ID'];
}
}
}
/**
* Сохраняем радел в сессию для пошаговости
* @param $id
* @param $name
* @param $ufId
* @param $ufParentId
* @param $code
*/
function AddCat2Session($id, $name, $ufId, $ufParentId, $code = false)
{
$_SESSION['CATS'][$id]['ID'] = $id;
$_SESSION['CATS'][$id]['NAME'] = $name;
$_SESSION['CATS'][$id]['UF_ID'] = $ufId;
$_SESSION['CATS'][$id]['UF_PARENT_ID'] = $ufParentId;
$_SESSION['CATS'][$id]['CODE'] = $code;
$_SESSION['CATS_UF_IDS'][] = $ufId;
$_SESSION['CATS_COUNT']++;
}
};
class ClImportOffer extends ClImportCategory
{
/**
* Сохраняем радел в сессию для пошаговости
* @param $id
* @param $name
* @param $ufId
* @param $ufParentId
* @param $code
*/
function AddOffer2Session($arOffer)
{
$id = $arOffer['ID'];
$_SESSION['OFFERS'][$id]['ID'] = $arOffer['ID'];
$_SESSION['OFFERS'][$id]['SECTION_UF_ID'] = $arOffer['SECTION_UF_ID'];
$_SESSION['OFFERS'][$id]['DESCRIPTION'] = $arOffer['DESCRIPTION'];
$_SESSION['OFFERS'][$id]['MODEL'] = $arOffer['MODEL'];
$_SESSION['OFFERS'][$id]['COLOR'] = $arOffer['COLOR'];
$_SESSION['OFFERS'][$id]['COLLECTION'] = $arOffer['COLLECTION'];
$_SESSION['OFFERS'][$id]['EXTERIOR'] = $arOffer['EXTERIOR'];
$_SESSION['OFFERS'][$id]['FASTENER'] = $arOffer['FASTENER'];
$_SESSION['OFFERS'][$id]['SEASONALITY'] = $arOffer['SEASONALITY'];
$_SESSION['OFFERS'][$id]['MANUFACTURER'] = $arOffer['MANUFACTURER'];
$_SESSION['OFFERS'][$id]['SIZE'] = $arOffer['SIZE'];
$_SESSION['OFFERS'][$id]['UNISEX'] = $arOffer['UNISEX'];
$_SESSION['OFFERS'][$id]['AGE'] = $arOffer['AGE'];
$_SESSION['OFFERS'][$id]['PICTURE'] = $arOffer['PICTURE'];
$_SESSION['OFFERS'][$id]['THUMBNAIL'] = $arOffer['THUMBNAIL'];
$_SESSION['OFFERS'][$id]['PRICE'] = $arOffer['PRICE'];
$_SESSION['OFFERS'][$id]['OLDPRICE'] = $arOffer['OLDPRICE'];
$_SESSION['OFFERS'][$id]['VENDOR'] = $arOffer['VENDOR'];
$_SESSION['OFFERS'][$id]['URL'] = $arOffer['URL'];
$_SESSION['OFFERS'][$id]['NAME'] = $arOffer['NAME'];
}
/**
* Получаем список всех категорий из xml.
*/
public function AddOffersFromXml($addTo = 'db')
{
$reader = new XMLReader();
$reader->open($_SERVER["DOCUMENT_ROOT"].$this->xmlSiteUrl.$this->xmlFile);
$counter = 0;
while ($reader->read())
{
if ($reader->nodeType == XMLReader::ELEMENT && $reader->localName == 'offers')
{
while ($reader->read())
{
$localName = $reader->localName;
switch ($reader->nodeType)
{
case XMLReader::ELEMENT:
switch ($localName)
{
case 'offer':
$available = $reader->getAttribute('available');
if ($available == 'true')
{
unset($arOffer);
$arOffer = array(
'ID' => '',
'SECTION_UF_ID' => '',
'DESCRIPTION' => '',
'MODEL' => '',
'COLOR' => '',
'COLLECTION' => '',
'EXTERIOR' => '',
'FASTENER' => '',
'SEASONALITY' => '',
'MANUFACTURER' => '',
'SIZE' => '',
'UNISEX' => '',
'AGE' => '',
'PICTURE' => array(),
'THUMBNAIL' => '',
'PRICE' => '',
'OLDPRICE' => '',
'VENDOR' => '',
'URL' => '',
'NAME' =>''
);
}
/*Добавить сессию для удаления*/
break;
case 'param':
if ($available == 'true')
{
$name = $reader->getAttribute('name');
$subChildName = $localName;
}
break;
default:
$subChildName = $localName;
}
break;
case XMLReader::TEXT:
if ($available == 'true')
{
switch ($subChildName)
{
case 'categoryId':
$arOffer['SECTION_UF_ID'] = $reader->value;
break;
case 'description':
$arOffer['DESCRIPTION'] = $reader->value;
break;
case 'model':
$arOffer['MODEL'] = $reader->value;
break;
case 'param':
switch ($name)
{
case 'Цвет':
$arOffer['COLOR'] = $reader->value;
break;
case 'Коллекция':
$arOffer['COLLECTION'] = $reader->value;
break;
case 'Внешний материал':
$arOffer['EXTERIOR'] = $reader->value;
break;
case 'Тип застежки':
$arOffer['FASTENER'] = $reader->value;
break;
case 'Сезонность':
$arOffer['SEASONALITY'] = $reader->value;
break;
case 'Страна-изготовитель':
$arOffer['MANUFACTURER'] = $reader->value;
break;
case 'Размер':
$arOffer['SIZE'] = $reader->value;
break;
case 'Пол':
$arOffer['UNISEX'] = $reader->value;
break;
case 'Возраст':
$arOffer['AGE'] = $reader->value;
break;
}
break;
case 'picture':
$arOffer['PICTURE'][] = $reader->value;
break;
case 'thumbnail':
$arOffer['THUMBNAIL'] = $reader->value;
break;
case 'price':
$arOffer['PRICE'] = $reader->value;
break;
case 'oldprice':
$arOffer['OLDPRICE'] = $reader->value;
break;
case 'vendor':
$arOffer['VENDOR'] = $reader->value;
break;
case 'url':
$arOffer['URL'] = $reader->value;
break;
}
}
break;
case XMLReader::END_ELEMENT:
if ($localName == 'offer')
{
switch ($addTo)
{
case 'session':
//if ($counter < $this->maxAddOffer)
//{
$arOffer['ID'] = $counter;
$this->AddOffer2Session($arOffer);
//}
//else
//{
// break 3;
//}
$counter++;
break;
}
}
break;
}
if ($reader->nodeType == XMLReader::END_ELEMENT && $reader->localName == 'offers')
{
break;
}
}
}
if ($reader->nodeType == XMLReader::END_ELEMENT && $reader->localName == 'offers')
{
break;
}
}
$reader->close();
unset($reader);
}
};
class ClImportConfig
{
public $speed = 0.4;
public $iblockId = 11;
public $projectUrl = '/bitrix/admin/import_xml/';
public $xmlSiteUrl = '/upload/import_xml/';
public $xmlFile = 'lamoda.xml';
public $logFile = 'time_log.html';
public $maxAddCat = 150;
public $maxAddOffer = 150;
public $offset = 50;
public $debugMode = false;
public $beginTime = 0;
public $endTime = 0;
/**
* Вывод отладочной информации
* @param $data
*/
public function pre($data)
{
if ($this->debugMode === true)
{
echo $data;
}
}
/**
* Строка в транслите
* @param $str
* @return $str
*/
function translitIt($str)
{
$str = ClTranslit::transliterate($str);
$str = ClTranslit::asURLSegment($str);
return $str;
}
/**
* Логирование времени выполнения
*/
public function SetTime($param)
{
switch($param)
{
case 'begin';
$this->beginTime = microtime(true);
break;
case 'end':
$this->endTime = microtime(true);
break;
}
}
/**
* Запись лога в файл
* @param $param
*/
public function WriteLog($param, $step, $mode = 'w+')
{
switch ($param)
{
case 'begin':
switch($mode)
{
case 'w':
case 'w+':
unlink($_SERVER["DOCUMENT_ROOT"].$this->projectUrl.$this->logFile);
break;
}
$logStr = '<html><head></head><body><p>';
$logStr .= '============'.date("Y-m-d H:i:s").'==============<br>';
$timeStep = $this->endTime - $this->beginTime;
$logStr .= 'Шаг '.$step.'. Время выполнения: '.$timeStep.' сек.<br>';
break;
case 'end':
$logStr = '=================================================<br>';
$logStr .= '</p></body></html>';
break;
default:
$timeStep = $this->endTime - $this->beginTime;
$logStr .= 'Шаг '.$step.'. Время выполнения: '.$timeStep.' сек.<br>';
}
file_put_contents($_SERVER["DOCUMENT_ROOT"].$this->projectUrl.$this->logFile, var_export($logStr, true), FILE_APPEND | LOCK_EX);
}
/**
* Рестарт массива сессий перед началов выполнения
*/
public function ResetSession()
{
$_SESSION['COUNTER'] = 0;
unset(
$_SESSION['CATS'],
$_SESSION['CATS_WITHOUT_IDS'],
$_SESSION['CATS_PARENT_ID'],
$_SESSION['CATS_WITHOUT_ORPHAN'],
$_SESSION['CATS_COUNT_DB'],
$_SESSION['CATS_COUNT'],
$_SESSION['RESIDUE'],
$_SESSION['CATS_UF_IDS'],
$_SESSION['CAT_IDS'],
$_SESSION['UPDATE'],
$_SESSION['OFFERS'],
$_SESSION['IDS'],
$_SESSION['J'],
$_SESSION['PAGE']
);
}
};
final class ClTranslit{
/**
* Укр/Рус символы
*
* @var array
* @access private
* @static
*/
static private $cyr = array(
'Щ', 'Ш', 'Ч', 'Ц','Ю', 'Я', 'Ж', 'А','Б','В','Г','Д','Е','Ё','З','И','Й','К','Л','М','Н','О','П','Р','С','Т','У','Ф','Х', 'Ь','Ы','Ъ','Э','Є','Ї','І',
'щ', 'ш', 'ч', 'ц','ю', 'я', 'ж', 'а','б','в','г','д','е','ё','з','и','й','к','л','м','н','о','п','р','с','т','у','ф','х', 'ь','ы','ъ','э','є','ї', 'і');
/**
* Латинские соответствия
*
* @var array
* @access private
* @static
*/
static private $lat = array(
'Shh','Sh','Ch','C','Ju','Ja','Zh','A','B','V','G','D','Je','Jo','Z','I','J','K','L','M','N','O','P','R','S','T','U','F','Kh','Y','Y','','E','Je','Ji','I',
'shh','sh','ch','c','ju','ja','zh','a','b','v','g','d','je','jo','z','i','j','k','l','m','n','o','p','r','s','t','u','f','kh','y','y','','e','je','ji', 'i');
/**
* Приватный конструктор класса
* не дает создавать объект этого класса
*
* @access private
*/
private function __construct() {}
/**
* Статический метод транслитерации
*
* @param string
* @return string
* @access public
* @static
*/
static public function transliterate($string, $wordSeparator = '', $clean = false)
{
//$str = iconv($encIn, "utf-8", $str);
for($i=0; $i<count(self::$cyr); $i++)
{
$string = str_replace(self::$cyr[$i], self::$lat[$i], $string);
}
$string = preg_replace("/([qwrtpsdfghklzxcvbnmQWRTPSDFGHKLZXCVBNM]+)[jJ]e/", "\${1}e", $string);
$string = preg_replace("/([qwrtpsdfghklzxcvbnmQWRTPSDFGHKLZXCVBNM]+)[jJ]/", "\${1}y", $string);
$string = preg_replace("/([eyuioaEYUIOA]+)[Kk]h/", "\${1}h", $string);
$string = preg_replace("/^kh/", "h", $string);
$string = preg_replace("/^Kh/", "H", $string);
$string = trim($string);
if ($wordSeparator)
{
$string = str_replace(' ', $wordSeparator, $string);
$string = preg_replace('/['.$wordSeparator.']{2,}/','', $string);
}
if ($clean)
{
$string = strtolower($string);
$string = preg_replace('/[^-_a-z0-9]+/','', $string);
}
//return iconv("utf-8", $encOut, $str);
return $string;
}
/**
* Приведение к УРЛ
*
* @return string
* @access public
* @static
*/
static public function asURLSegment($string)
{
return strtolower(self::transliterate($string, '_', true));
}
}
?>