SetTitle("Миграция"); if ($_REQUEST['go']) { CModule::IncludeModule("forum"); // ошибки будут фиксироваться в лог файле и выводиться пользователю в iframe define('LOG_FILENAME',$_SERVER["DOCUMENT_ROOT"].'/log.txt'); // $BREAK_POINT - метка в которой хранится позиция с которой // будет начинаться следующий шаг минрации if ($_REQUEST['break_point']) $BREAK_POINT = $_REQUEST['break_point']; else @unlink(LOG_FILENAME); if ($_REQUEST['START']) $START = $_REQUEST['START']; // Функция миграции групп пользователей, // пользователи выгружаются пока не будет импортирован последний // На последнем шаге функции MigrateUserGroups устанавливается $START = 'Users' // и скрипт переходит к функции MigrateUsers if (!$START) MigrateUserGroups($BREAK_POINT); if ($START == 'Users') MigrateUsers($BREAK_POINT); if ($START == 'ForumGroups') MigrateForumGroups($BREAK_POINT); if ($START == 'Forums') MigrateForums($BREAK_POINT); if ($START == 'Topics') MigrateTopics($BREAK_POINT); if ($START == 'Posts') MigratePosts($BREAK_POINT); // Форма которая отпраляет запрос для запуска нового шага // Отправка формы реализуется яваскриптом // В запросе хранится метка break_point и метка START if ($BREAK_POINT && !defined('END')) {?>
Идет импорт ...

"; if (file_exists(LOG_FILENAME)) echo $iframe; } else { global $DB; // создаем таблицу для хранения данных авторизации пользователей, // полученных методом кодирования паролей в MyBB(см. задача №3) $DB -> Query("CREATE TABLE IF NOT EXISTS old_user ( LOGIN varchar(60) NOT NULL, PASSWORD varchar(64) NOT NULL, SALT varchar(64) NOT NULL, PRIMARY KEY (LOGIN));" ); // Эта форма запускает сам скрипт echo"
"; } // Далее пройдемся по самим функциям переноса разных объектов. // Начнем с групп пользователей. // Тут все просто. function MigrateUserGroups($ID) { global $BREAK_POINT, $START, $TEXT; // подключение к БД вынес в отдельную функцию $link = ConnectDb(); if (!$ID) $ID=0; // один шаг = одна запись в из таблицы групп пользователей в MyBB $step = 1; // получаем одну запись из таблицы mybb_usergroups, // где ID больше чем ID на котором завершился прошлый шаг выполнения этой функции $query ="SELECT * FROM mybb_usergroups where gid > $ID LIMIT $step"; $resUserGroups = mysql_query($query , $link) or die("Invalid query: " . mysql_error()); // устанавливаем флаг окончания работы функции MigrateUserGroups в true $bFinish = true; $ObGroup = new CGroup; while ($userGroup = mysql_fetch_assoc($resUserGroups)) { // пока $bFinish!=true на следующем шаге будет выполняться MigrateUserGroups $bFinish = false; $arFields = Array( "ACTIVE" => "Y", "C_SORT" => 100, "NAME" => $userGroup['title'], "DESCRIPTION" => $userGroup['description'], "STRING_ID" => $userGroup['gid']//сюда записываем id из старой БД(см. задача №2) ); $GID = $ObGroup->Add($arFields); if (strlen($ObGroup -> LAST_ERROR)>0) { //записываем в файл log.txt ошибки, которые будут выводится во фрейме AddMessage2Log($ObGroup -> LAST_ERROR); } //запоминаем id группы с которого будет начинаться следующий шаг $BREAK_POINT = $userGroup['gid']; } // Если заходили в цикл while ($userGroup = mysql_fetch_assoc($resUserGroups)), // то $bFinish = false; // Если не заходили в цикл, то группы закончились, $bFinish = true, переходим к функции MigrateUsers if ($bFinish) { //если все группы пользователей импортированы, //то переходим к выгрузке самих пользователей $START = 'Users'; $BREAK_POINT = 0; } else $TEXT = "Импортируется группа пользователей: $BREAK_POINT"; } //Далее пользователи: function MigrateUsers($ID) { global $BREAK_POINT, $START, $TEXT, $DB; $link = ConnectDb(); $ObUser = new CUser; // один шаг = 100 записей $step = 100; $query ="SELECT * FROM mybb_users where uid > $ID and username != 'admin' LIMIT $step"; $resUsers = mysql_query($query , $link) or die("Invalid query: " . mysql_error()); $bFinish = true; while ($user = mysql_fetch_assoc($resUsers)) { $bFinish = false; $avatarPath = substr($user['avatar'], 1, strlen($user['avatar'])); // получаем новые id групп пользователей по старому id в MyBB, хранящемуся в STRING_ID(см. задача №2) $obGroups = CGroup::GetList(($by="ID"), ($order="desc"), array('STRING_ID' => $user['usergroup'])); while ($arGroup=$obGroups->GetNext()) : $groupId[] = $arGroup['ID']; endwhile; $arFields = Array( "XML_ID" => $user['uid'],//сюда записываем id из старой БД(см. задача №2) "LOGIN" => $user['username'], "PASSWORD" => $user['password'], "CONFIRM_PASSWORD" => $user['password'], "ACTIVE" => "Y", "NAME" => $user['username'], "SECOND_NAME" => '', "LAST_NAME" => '', "EMAIL" => $user['email'], "LAST_LOGIN" => ConvertTimeStamp($user['lastactive'],"FULL"), "LAST_ACTIVITY_DATE" => ConvertTimeStamp($user['lastactive'],"FULL"), "LID" => 's1', "GROUP_ID" => $groupId,//записываем актуальные id групп пользователей "PERSONAL_ICQ" => !$user['icq'] ? '' : $user['icq'], "PERSONAL_PHOTO" => CFile::MakeFileArray('/home/blablabla/'.$avatarPath), ); $UID = $ObUser->Add($arFields); //Если, при добавлении пользователя, возникла ошибка, то пишем её в log.txt if (strlen($ObUser->LAST_ERROR)>0) { AddMessage2Log($ObUser->LAST_ERROR); } //иначе добавляем пользователя форума else { $arFields = Array( "USER_ID" => $UID, "DESCRIPTION" => $user['usertitle'], "IP_ADDRESS" => $user['lastip'], "AVATAR" => CFile::MakeFileArray('/home/blablabla/'.$avatarPath), "NUM_POSTS" => $user['postnum'], "LAST_POST" => $user['lastpost'], "LAST_VISIT" => ConvertTimeStamp($user['lastvisit'],"FULL"), "DATE_REG" => ConvertTimeStamp($user['regdate'],"FULL"), "REAL_IP_ADDRESS" => $user['lastip'], "SIGNATURE" => $user['signature'], ); if (!CForumUser::Add($arFields)) { $e = $GLOBALS['APPLICATION']->GetException(); if ($e && $str = $e->GetString()) AddMessage2Log("Ошибка: ".$str); else AddMessage2Log("Неизвестная ошибка"); } // Добавляем в таблицу old_user данные авторизации //закодированные алгоритмом MyBB(см. задача № 3) $DB->Insert("old_user", array( "LOGIN" => "'".$DB->ForSQL($user['username'])."'", "PASSWORD" => "'".$DB->ForSQL($user['password'])."'", "SALT" => "'".$DB->ForSQL($user['salt'])."'", ) ); } $BREAK_POINT = $user['uid']; } if ($bFinish) { $START = 'ForumGroups'; $BREAK_POINT = 0; } else $TEXT = "Группы пользователей импортированы.
Импортируется пользователь: $BREAK_POINT"; } //Перенос групп форумов function MigrateForumGroups($ID) { global $BREAK_POINT, $START, $TEXT; $link = ConnectDb(); $step = 1; // группы форумов и сами форумы хранятся в MyBB в одной таблице // отличаются они значением в поле type, для групп форумов type = 'c' $query = "SELECT * from mybb_forums where fid > $ID and type = 'c' LIMIT $step"; $resForumGroups = mysql_query($query , $link) or die("Invalid query: " . mysql_error()); $arSysLangs = array(); $arGroupForumsId = array(); // Получам языки сайта $ObLangs = CLanguage::GetList($by="lid", $order="desc", Array()); while($lang = $ObLangs->Fetch()) { $arSysLangs[] = $lang['LID']; } $bFinish = true; while ($forumGroup = mysql_fetch_assoc($resForumGroups)) { $bFinish = false; for ($i = 0; $i $arSysLangs[$i], "NAME" => $forumGroup['name'], "DESCRIPTION" => $forumGroup['description'], ); $arFields["XML_ID"] = $forumGroup['fid']; } $FGID = CForumGroup::Add($arFields); if (!$FGID) { $e = $GLOBALS['APPLICATION']->GetException(); if ($e && $str = $e->GetString()) AddMessage2Log("Ошибка: $str"); else AddMessage2Log("Неизвестная ошибка"); } $BREAK_POINT = $forumGroup['fid']; } if ($bFinish) { $START = 'Forums'; $BREAK_POINT = 0; } else $TEXT = "Группы пользователей импортированы
Пользователи импортированы
Импортируется группа $BREAK_POINT форума"; } //Перенос форумов function MigrateForums($ID) { global $BREAK_POINT, $START, $TEXT; $link = ConnectDb(); $step = 5; // группы форумов и сами форумы хранятся в MyBB в одной таблице // отличаются они значением в поле type, для форумов type = 'f' $query = "SELECT * from mybb_forums where fid > $ID and type = 'f' LIMIT $step" ; $resForums = mysql_query($query , $link) or die("Invalid query: " . mysql_error()); $Sites = CSite::GetList(); while ($Site = $Sites->Fetch()) { $arSites[$Site['LID']] = '/forum/index.php?PAGE_NAME=message&FID=#FORUM_ID#&TID=#TOPIC_ID#&MID=#MESSAGE_ID#'; } $bFinish = true; while ($forum = mysql_fetch_array($resForums)) { $bFinish = false; // Получаем новые id групп пользователей, по старым, хранящимся в XML_ID (см. задача №2) // Стандартно не работает фильтрация групп форумов по xml_id // Нужно в \bitrix\modules\forum\classes\general\forum_new.php // для функции CForumGroup::GetList(строка 2014) добавить case "XML_ID": $obForumGroup = CForumGroup::GetList(array(), array('XML_ID' => $forum['pid'])); $forumGroup=$obForumGroup->GetNext(); $forumGroupId = $forumGroup['ID']; $arFields = Array( "ACTIVE" => "Y", "NAME" => $forum['name'], "DESCRIPTION" => $forum['description'], "FORUM_GROUP_ID" => $forumGroupId, "SITES" => $arSites, "TOPICS" => $forum['threads'], "POSTS" => $forum['posts'], "LAST_POSTER_ID" => $forum['lastposteruid'], "LAST_POSTER_NAME" => $forum['lastposter'], "LAST_MESSAGE_ID" => $forum['lastpost'], "XML_ID" => $forum['fid'] ); if (!CForumNew::Add($arFields)) { $e = $GLOBALS['APPLICATION']->GetException(); if ($e && $str = $e->GetString()) AddMessage2Log("Ошибка: ".$str); else AddMessage2Log("Неизвестная ошибка"); } $BREAK_POINT = $forum['fid']; } if ($bFinish) { $START = 'Topics'; $BREAK_POINT = 0; } else $TEXT = "Группы пользователей импортированы
Пользователи импортированы
Группы форумов импортированы
Импортируется форум: $BREAK_POINT"; } //Перенос тем форумов function MigrateTopics($ID) { global $BREAK_POINT, $START, $TEXT; $link = ConnectDb(); $step = 100; $query = "SELECT * from mybb_threads where tid > $ID LIMIT $step" ; $resTopics = mysql_query($query , $link) or die("Invalid query: " . mysql_error()); $bFinish = true; while ($topic = mysql_fetch_assoc($resTopics)) { $bFinish = false; $obForum = CForumNew::GetList(array(), array('XML_ID' => $topic['fid'])); $forum=$obForum->GetNext(); $forumId = $forum['ID']; $obUser = CUser::GetList(($by="ID"), ($order="desc"), array('XML_ID' => $topic['uid']), array('FIELDS' => array('ID'))); $user=$obUser->GetNext(); $userId = $user['ID']; $obLastPoster = CUser::GetList(($by="ID"), ($order="desc"), array('XML_ID' => $topic['lastposteruid']), array('FIELDS' => array('ID'))); $lastPoster = $obLastPoster->GetNext(); $lastPosterId = $lastPoster['ID']; $arFields = Array( "XML_ID" => $topic["tid"], "TITLE" => $topic["subject"], "STATE" => $topic["closed"] === 0 ? 'N' : 'Y', "USER_START_ID" => $userId, "USER_START_NAME" => $topic["username"], "START_DATE" => ConvertTimeStamp($topic["dateline"],"FULL"), "POSTS" => $topic["replies"], "VIEWS" => $topic["views"], "FORUM_ID" => $forumId, "APPROVED" => 'Y', "LAST_POSTER_ID" => $lastPosterId, "LAST_POSTER_NAME" => $topic["lastposter"], "LAST_POST_DATE" => ConvertTimeStamp($topic["lastpost"],"FULL"), ); if (!CForumTopic::Add($arFields)) AddMessage2Log("Ошибка и мпорта топика"); $BREAK_POINT = $topic['tid']; } if ($bFinish) { $START = 'Posts'; $BREAK_POINT = 0; } else $TEXT = "Группы пользователей импортированы
Пользователи импортированы
Группы форумов импортированы
Форумы импортированы
Импортируется топик: $BREAK_POINT"; } // Перенос сообщений в темах форумов function MigratePosts($ID) { global $BREAK_POINT, $START, $TEXT; $link = ConnectDb(); $step = 100; $query = "SELECT * from mybb_posts where pid > $ID LIMIT $step" ; $resPosts = mysql_query($query , $link) or die("Invalid query: " . mysql_error()); $bFinish = true; while ($post = mysql_fetch_assoc($resPosts)) { $bFinish = false; $obForum = CForumNew::GetList(array(), array('XML_ID' => $post['fid'])); $forum=$obForum->GetNext(); $forumId = $forum['ID']; $obTopic = CForumTopic::GetList(array(), array('XML_ID' => $post['tid'])); $topic=$obTopic->GetNext(); $topicId = $topic['ID']; $obUser = CUser::GetList(($by="ID"), ($order="desc"), array('XML_ID' => $post['uid']), array('FIELDS' => array('ID'))); $user=$obUser->GetNext(); $userId = $user['ID']; $arFields = Array( "AUTHOR_ID" => $userId, "AUTHOR_NAME" => $post["username"], "AUTHOR_IP" => $post["ipaddress"], "USE_SMILES" => 'Y', "POST_DATE" => ConvertTimeStamp($post["dateline"],"FULL"), "POST_MESSAGE" => $post["message"], "FORUM_ID" => $forumId, "TOPIC_ID" => $topicId, "APPROVED" => 'Y', ); if (!CForumMessage::Add($arFields)) { $e = $GLOBALS['APPLICATION']->GetException(); if ($e && $str = $e->GetString()) AddMessage2Log("Ошибка: $str"); else AddMessage2Log("Неизвестная ошибка"); } $BREAK_POINT = $post['pid']; } if ($bFinish) { //define('END', true); для завершения миграции define('END', true); $TEXT = "Группы пользователей импортированы
Пользователи импортированы.
Группы форумов импортированы.
Форумы импортированы.
Топики импортированы.
Посты импортированы.
Миграция завершена"; } else $TEXT = "Группы пользователей импортированы
Пользователи импортированы.
Группы форумов импортированы.
Форумы импортированы.
Топики импортированы.
Импортируется пост: $BREAK_POINT"; } //функция для подключения к БД MyBB function ConnectDb() { $link = mysql_connect('localhost:31006', 'root', '', true); mysql_query("SET NAMES 'utf-8'", $link); $db_selected = mysql_select_db('sitemanager', $link); if (!$db_selected) { echo('Ошибка подключения к БД'); die(); } return ($link); } ?>