assign('from_version', InstallCore::getStoredData('update_from_version'));
$this->assign('convert_versions', $this->aVersionConvert);
}
public function process()
{
set_time_limit(0);
/**
* Коннект к серверу БД
*/
if (!$oDb = $this->getDBConnection(InstallConfig::get('db.params.host'), InstallConfig::get('db.params.port'),
InstallConfig::get('db.params.user'), InstallConfig::get('db.params.pass'), true)
) {
return false;
}
/**
* Выбираем БД
*/
if (!@mysqli_select_db($oDb, InstallConfig::get('db.params.dbname'))) {
return $this->addError(InstallCore::getLang('db.errors.db_query'));
}
$this->setDbParams(array(
'prefix' => InstallConfig::get('db.table.prefix'),
'engine' => InstallConfig::get('db.tables.engine'),
));
$sVersion = InstallCore::getRequestStr('from_version');
/**
* Проверяем наличие конвертора
* Конвертор представляет собой отдельный метод вида converFrom_X1_Y1_Z1_to_X2_Y2_Z2
*/
$sMethod = 'convertFrom_' . str_replace('.', '_', $sVersion) . '_to_' . str_replace('.', '_', VERSION);
if (!method_exists($this, $sMethod)) {
return $this->addError(InstallCore::getLang('steps.updateVersion.errors.not_found_convert'));
}
InstallCore::setStoredData('update_from_version', $sVersion);
/**
* Запускаем конвертор
*/
return call_user_func_array(array($this, $sMethod), array($oDb));
}
/**
* Конвертор версии 2.0.0 в 2.0.1
*
* @param $oDb
*
* @return bool
*/
public function convertFrom_2_0_0_to_2_0_1($oDb)
{
/**
* Запускаем SQL патч
*/
$sFile = 'sql' . DIRECTORY_SEPARATOR . 'patch_2.0.0_to_2.0.1.sql';
list($bResult, $aErrors) = array_values($this->importDumpDB($oDb, InstallCore::getDataFilePath($sFile), array(
'engine' => InstallConfig::get('db.tables.engine'),
'prefix' => InstallConfig::get('db.table.prefix'),
'skip_fk_errors' => true
)));
if ($bResult) {
return true;
}
return $this->addError(join('
', $aErrors));
}
/**
* Конвертор версии 1.0.3 в 2.0.0
*
* @param $oDb
*
* @return bool
*/
public function convertFrom_1_0_3_to_2_0_0($oDb)
{
/**
* Запускаем SQL патч
*/
$sFile = 'sql' . DIRECTORY_SEPARATOR . 'patch_1.0.3_to_2.0.0.sql';
list($bResult, $aErrors) = array_values($this->importDumpDB($oDb, InstallCore::getDataFilePath($sFile), array(
'engine' => InstallConfig::get('db.tables.engine'),
'prefix' => InstallConfig::get('db.table.prefix'),
'check_table' => 'cron_task',
'skip_fk_errors' => true
)));
if ($bResult) {
/**
* Проверяем необходимость конвертировать таблицу плагина Page
*/
if ($this->dbCheckTable("prefix_page")) {
$sFile = 'sql' . DIRECTORY_SEPARATOR . 'patch_page_1.3_to_2.0.sql';
list($bResult, $aErrors) = array_values($this->importDumpDB($oDb, InstallCore::getDataFilePath($sFile),
array(
'engine' => InstallConfig::get('db.tables.engine'),
'prefix' => InstallConfig::get('db.table.prefix'),
'check_table_field' => array('prefix_page', 'id'),
'skip_fk_errors' => true
)));
if (!$bResult) {
return $this->addError(join('
', $aErrors));
}
}
/**
* Конвертируем опросы
* Сначала проверяем необходимость конвертации опросов
*/
if ($this->dbCheckTable("prefix_topic_question_vote")) {
$iPage = 1;
$iLimitCount = 50;
$iLimitStart = 0;
while ($aTopics = $this->dbSelect("SELECT t.*, c.topic_extra FROM prefix_topic as t, prefix_topic_content as c WHERE topic_type = 'question' and t.topic_id = c.topic_id LIMIT {$iLimitStart},{$iLimitCount}")) {
$iPage++;
$iLimitStart = ($iPage - 1) * $iLimitCount;
/**
* Топики
*/
foreach ($aTopics as $aTopic) {
$aPollData = @unserialize($aTopic['topic_extra']);
if (!isset($aPollData['answers'])) {
continue;
}
/**
* Создаем опрос
*/
$aFields = array(
'user_id' => $aTopic['user_id'],
'target_type' => 'topic',
'target_id' => $aTopic['topic_id'],
'title' => htmlspecialchars($aTopic['topic_title']),
'count_answer_max' => 1,
'count_vote' => isset($aPollData['count_vote']) ? $aPollData['count_vote'] : 0,
'count_abstain' => isset($aPollData['count_vote_abstain']) ? $aPollData['count_vote_abstain'] : 0,
'date_create' => $aTopic['topic_date_add'],
);
if ($iPollId = $this->dbInsertQuery('prefix_poll', $aFields)) {
foreach ($aPollData['answers'] as $iAnswerIdOld => $aAnswer) {
/**
* Создаем вариант ответа
*/
$aFields = array(
'poll_id' => $iPollId,
'title' => htmlspecialchars($aAnswer['text']),
'count_vote' => htmlspecialchars($aAnswer['count']),
'date_create' => $aTopic['topic_date_add'],
);
if ($iAnswerId = $this->dbInsertQuery('prefix_poll_answer', $aFields)) {
/**
* Получаем список кто голосовал за этот вариант
*/
if ($aVotes = $this->dbSelect("SELECT * FROM prefix_topic_question_vote WHERE topic_id = '{$aTopic['topic_id']}' AND answer = '{$iAnswerIdOld}' ")) {
foreach ($aVotes as $aVote) {
/**
* Добавляем новый факт голосования за вариант
*/
$aFields = array(
'poll_id' => $iPollId,
'user_id' => $aVote['user_voter_id'],
'answers' => serialize(array($iAnswerId)),
'date_create' => $aTopic['topic_date_add'],
);
$this->dbInsertQuery('prefix_poll_vote', $aFields);
}
}
}
}
/**
* Добавляем факты голосования воздержавшихся
*/
/**
* Получаем список кто голосовал за этот вариант
*/
if ($aVotes = $this->dbSelect("SELECT * FROM prefix_topic_question_vote WHERE topic_id = '{$aTopic['topic_id']}' AND answer = -1 ")) {
foreach ($aVotes as $aVote) {
/**
* Добавляем новый факт воздержания
*/
$aFields = array(
'poll_id' => $iPollId,
'user_id' => $aVote['user_voter_id'],
'answers' => serialize(array()),
'date_create' => $aTopic['topic_date_add'],
);
$this->dbInsertQuery('prefix_poll_vote', $aFields);
}
}
}
/**
* Меняем тип топика
*/
$this->dbQuery("UPDATE prefix_topic SET topic_type = 'topic' WHERE topic_id ='{$aTopic['topic_id']}'");
/**
* Убираем лишние данные из topic_extra
*/
unset($aPollData['answers']);
unset($aPollData['count_vote_abstain']);
unset($aPollData['count_vote']);
$sExtra = mysqli_escape_string($this->rDbLink, serialize($aPollData));
$this->dbQuery("UPDATE prefix_topic_content SET topic_extra = '{$sExtra}' WHERE topic_id ='{$aTopic['topic_id']}'");
}
}
/**
* Удаляем старые таблицы
*/
if (!$this->getErrors()) {
$this->dbQuery('DROP TABLE prefix_topic_question_vote');
}
}
/**
* Конвертируем топик-ссылки
*/
$iPage = 1;
$iLimitCount = 50;
$iLimitStart = 0;
while ($aTopics = $this->dbSelect("SELECT t.*, c.topic_extra, c.topic_text, c.topic_text_short, c.topic_text_source FROM prefix_topic as t, prefix_topic_content as c WHERE topic_type = 'link' and t.topic_id = c.topic_id LIMIT {$iLimitStart},{$iLimitCount}")) {
$iPage++;
$iLimitStart = ($iPage - 1) * $iLimitCount;
/**
* Топики
*/
foreach ($aTopics as $aTopic) {
$aData = @unserialize($aTopic['topic_extra']);
if (!isset($aData['url'])) {
continue;
}
/**
* Переносим ссылку в текст топика
*/
$sUrl = $aData['url'];
if (strpos($sUrl, '://') === false) {
$sUrl = 'http://' . $sUrl;
}
$sUrl = htmlspecialchars($sUrl);
$sTextAdd = "\n
{$sUrl}";
$aTopic['topic_text'] .= $sTextAdd;
$aTopic['topic_text_short'] .= $sTextAdd;
$aTopic['topic_text_source'] .= $sTextAdd;
unset($aData['url']);
$sExtra = mysqli_escape_string($this->rDbLink, serialize($aData));
$sText = mysqli_escape_string($this->rDbLink, $aTopic['topic_text']);
$sTextShort = mysqli_escape_string($this->rDbLink, $aTopic['topic_text_short']);
$sTextSource = mysqli_escape_string($this->rDbLink, $aTopic['topic_text_source']);
$this->dbQuery("UPDATE prefix_topic_content SET topic_extra = '{$sExtra}', topic_text = '{$sText}', topic_text_short = '{$sTextShort}', topic_text_source = '{$sTextSource}' WHERE topic_id ='{$aTopic['topic_id']}'");
/**
* Меняем тип топика
*/
$this->dbQuery("UPDATE prefix_topic SET topic_type = 'topic' WHERE topic_id ='{$aTopic['topic_id']}'");
}
}
/**
* Конвертируем топик-фотосеты
*/
if ($this->dbCheckTable("prefix_topic_photo")) {
$iPage = 1;
$iLimitCount = 50;
$iLimitStart = 0;
while ($aTopics = $this->dbSelect("SELECT t.*, c.topic_extra, c.topic_text, c.topic_text_short, c.topic_text_source FROM prefix_topic as t, prefix_topic_content as c WHERE topic_type = 'photoset' and t.topic_id = c.topic_id LIMIT {$iLimitStart},{$iLimitCount}")) {
$iPage++;
$iLimitStart = ($iPage - 1) * $iLimitCount;
/**
* Топики
*/
foreach ($aTopics as $aTopic) {
$aData = @unserialize($aTopic['topic_extra']);
if (!isset($aData['main_photo_id'])) {
continue;
}
/**
* Получаем фото
*/
if ($aPhotos = $this->dbSelect("SELECT * FROM prefix_topic_photo WHERE topic_id = '{$aTopic['topic_id']}' ")) {
$aMediaItems = array();
foreach ($aPhotos as $aPhoto) {
/**
* Необходимо перенести изображение в media и присоеденить к топику
*/
$sFileSource = $this->convertPathWebToServer($aPhoto['path']);
/**
* Формируем список старых изображений для удаления
*/
$sMask = pathinfo($sFileSource,
PATHINFO_DIRNAME) . DIRECTORY_SEPARATOR . pathinfo($sFileSource,
PATHINFO_FILENAME) . '_*';
$aFilesForRemove = array();
if ($aPaths = glob($sMask)) {
foreach ($aPaths as $sPath) {
$aFilesForRemove[$sPath] = $sPath;
}
}
if ($oImage = $this->createImageObject($sFileSource)) {
$iWidth = $oImage->getSize()->getWidth();
$iHeight = $oImage->getSize()->getHeight();
if ($this->resizeImage($oImage, 1000)) {
if ($sFileSave = $this->saveImage($oImage, $sFileSource, '_1000x')) {
unset($aFilesForRemove[$sFileSave]);
}
}
if ($oImage = $this->createImageObject($sFileSource)) {
if ($this->resizeImage($oImage, 500)) {
if ($sFileSave = $this->saveImage($oImage, $sFileSource, '_500x')) {
unset($aFilesForRemove[$sFileSave]);
}
}
}
if ($oImage = $this->createImageObject($sFileSource)) {
if ($this->cropImage($oImage, 1) and $this->resizeImage($oImage, 100)) {
if ($sFileSave = $this->saveImage($oImage, $sFileSource, '_100x100crop')) {
unset($aFilesForRemove[$sFileSave]);
}
}
}
if ($oImage = $this->createImageObject($sFileSource)) {
if ($this->cropImage($oImage, 1) and $this->resizeImage($oImage, 50)) {
if ($sFileSave = $this->saveImage($oImage, $sFileSource, '_50x50crop')) {
unset($aFilesForRemove[$sFileSave]);
}
}
}
/**
* Добавляем запись в медиа
*/
$aDataMedia = array(
'image_sizes' => array(
array(
'w' => 1000,
'h' => null,
'crop' => false,
),
array(
'w' => 500,
'h' => null,
'crop' => false,
),
array(
'w' => 100,
'h' => 100,
'crop' => true,
),
array(
'w' => 50,
'h' => 50,
'crop' => true,
),
),
);
if ($aPhoto['description']) {
$aDataMedia['title'] = htmlspecialchars($aPhoto['description']);
}
$aFields = array(
'user_id' => $aTopic['user_id'],
'type' => 1,
'target_type' => 'topic',
'file_path' => '[relative]' . str_replace(dirname(dirname(INSTALL_DIR)), '',
$sFileSource),
'file_name' => pathinfo($sFileSource, PATHINFO_FILENAME),
'file_size' => filesize($sFileSource),
'width' => $iWidth,
'height' => $iHeight,
'date_add' => $aTopic['topic_date_add'],
'data' => serialize($aDataMedia),
);
if ($iMediaId = $this->dbInsertQuery('prefix_media', $aFields)) {
/**
* Добавляем связь медиа с топиком
*/
$aFields = array(
'media_id' => $iMediaId,
'target_id' => $aTopic['topic_id'],
'target_type' => 'topic',
'date_add' => $aTopic['topic_date_add'],
'data' => '',
);
if ($iMediaTargetId = $this->dbInsertQuery('prefix_media_target', $aFields)) {
$sFileWeb = InstallConfig::get('path.root.web') . str_replace(dirname(dirname(INSTALL_DIR)),
'',
$sFileSource);
$aMediaItems[$iMediaId] = $sFileWeb;
}
}
/**
* Удаляем старые
*/
foreach ($aFilesForRemove as $sFileRemove) {
@unlink($sFileRemove);
}
}
}
/**
* Добавляем в начало текста топика вывод фотосета
*/
$sCodeRender = '';
$sCodeSource = '';
if ($aMediaItems) {
$sCodeSource = '