From: Marcel Werk Date: Sun, 2 Aug 2020 21:46:01 +0000 (+0200) Subject: Added support for multilingual files X-Git-Tag: 5.3.0_Beta_1~6^2~1 X-Git-Url: https://git.stricted.de/?a=commitdiff_plain;h=e5ffd5d29a858e9a51209e2499e85e37a149fda7;p=GitHub%2FWoltLab%2Fcom.woltlab.wcf.exporter.git Added support for multilingual files Closes #44 --- diff --git a/files/lib/system/exporter/WBB4xExporter.class.php b/files/lib/system/exporter/WBB4xExporter.class.php index dcf21b6..9b4e3e6 100644 --- a/files/lib/system/exporter/WBB4xExporter.class.php +++ b/files/lib/system/exporter/WBB4xExporter.class.php @@ -2347,12 +2347,17 @@ class WBB4xExporter extends AbstractExporter { } /** - * Exports filebase files. + * Exports filebase files from 5.2-. * * @param integer $offset * @param integer $limit */ public function exportFilebaseFiles($offset, $limit) { + if (version_compare($this->getPackageVersion('com.woltlab.filebase'), '5.3.0 Alpha 1', '>=')) { + $this->exportFilebaseFiles53($offset, $limit); + return; + } + // get file ids $fileIDs = []; $sql = "SELECT fileID @@ -2364,7 +2369,6 @@ class WBB4xExporter extends AbstractExporter { while ($row = $statement->fetchArray()) { $fileIDs[] = $row['fileID']; } - if (empty($fileIDs)) return; // get tags @@ -2399,55 +2403,125 @@ class WBB4xExporter extends AbstractExporter { $statement = $this->database->prepareStatement($sql); $statement->execute($conditionBuilder->getParameters()); while ($row = $statement->fetchArray()) { - $additionalData = []; - if ($row['languageCode']) $additionalData['languageCode'] = $row['languageCode']; - if (isset($tags[$row['fileID']])) $additionalData['tags'] = $tags[$row['fileID']]; - - $data = [ - 'userID' => $row['userID'], - 'username' => $row['username'], + $contents[$row['languageCode'] ?: ''] = [ 'subject' => $row['subject'], - 'message' => $row['message'], - 'time' => $row['time'], 'teaser' => $row['teaser'], - 'website' => $row['website'], - 'enableHtml' => $row['enableHtml'], - 'enableComments' => $row['enableComments'], - 'isDisabled' => $row['isDisabled'], - 'isDeleted' => $row['isDeleted'], - 'ipAddress' => $row['ipAddress'], - 'deleteTime' => $row['deleteTime'], - 'isCommercial' => $row['isCommercial'], - 'isPurchasable' => $row['isPurchasable'], - 'price' => $row['price'], - 'currency' => $row['currency'], - 'totalRevenue' => (isset($row['totalRevenue']) ? $row['totalRevenue'] : 0), - 'purchases' => $row['purchases'], - 'licenseName' => (isset($row['licenseName']) ? $row['licenseName'] : ''), - 'licenseURL' => (isset($row['licenseURL']) ? $row['licenseURL'] : ''), - 'downloads' => $row['downloads'], - 'isFeatured' => $row['isFeatured'], - 'lastChangeTime' => $row['lastChangeTime'], + 'message' => $row['message'], + 'tags' => $tags[$row['fileID']] ?? [], ]; - // file icon - if (!empty($row['iconHash'])) { - $data['iconHash'] = $row['iconHash']; - $data['iconExtension'] = $row['iconExtension']; - $additionalData['iconLocation'] = $this->getFilebaseDir() . 'images/file/' . substr($row['iconHash'], 0, 2) . '/' . $row['fileID'] . '.' . $row['iconExtension']; + $this->exportFilebaseFilesHelper($row, $contents, $categories[$row['fileID']] ?? [$row['categoryID']]); + } + } + + /** + * Exports filebase files from 5.3+. + * + * @param integer $offset + * @param integer $limit + */ + public function exportFilebaseFiles53($offset, $limit) { + // get file ids + $fileIDs = []; + $sql = "SELECT fileID + FROM filebase".$this->dbNo."_file + WHERE fileID BETWEEN ? AND ? + ORDER BY fileID"; + $statement = $this->database->prepareStatement($sql); + $statement->execute([$offset + 1, $offset + $limit]); + while ($row = $statement->fetchArray()) { + $fileIDs[] = $row['fileID']; + } + if (empty($fileIDs)) return; + + // get file contents + $fileContents = $fileContentIDs = []; + $conditionBuilder = new PreparedStatementConditionBuilder(); + $conditionBuilder->add('fileID IN (?)', [$fileIDs]); + $sql = "SELECT file_content.*, language.languageCode + FROM filebase".$this->dbNo."_file_content file_content + LEFT JOIN wcf".$this->dbNo."_language language + ON (language.languageID = file_content.languageID) + " . $conditionBuilder; + $statement = $this->database->prepareStatement($sql); + $statement->execute($conditionBuilder->getParameters()); + while ($row = $statement->fetchArray()) { + $fileContents[$row['fileID']][$row['languageCode'] ?: ''] = $row; + $fileContentIDs[] = $row['fileContentID']; + } + + // get tags + $tags = $this->getTags('com.woltlab.filebase.file', $fileContentIDs); + + // get files + $sql = "SELECT * + FROM filebase".$this->dbNo."_file + ".$conditionBuilder; + $statement = $this->database->prepareStatement($sql); + $statement->execute($conditionBuilder->getParameters()); + while ($row = $statement->fetchArray()) { + $contents = []; + if (isset($fileContents[$row['fileID']])) { + foreach ($fileContents[$row['fileID']] as $languageCode => $fileContent) { + $contents[$languageCode ?: ''] = [ + 'subject' => $fileContent['subject'], + 'teaser' => $fileContent['teaser'], + 'message' => $fileContent['message'], + 'tags' => $tags[$fileContent['fileContentID']] ?? [], + ]; + } } - if (version_compare($this->getPackageVersion('com.woltlab.filebase'), '3.0.0 Alpha 1', '<')) { - // 2.x - if (isset($categories[$row['fileID']])) $additionalData['categories'] = $categories[$row['fileID']]; + $this->exportFilebaseFilesHelper($row, $contents, [$row['categoryID']]); + } + } + + protected function exportFilebaseFilesHelper(array $row, array $contents = [], array $categories = []) { + $additionalData = [ + 'contents' => $contents, + ]; + + $data = [ + 'userID' => $row['userID'], + 'username' => $row['username'], + 'time' => $row['time'], + 'website' => $row['website'], + 'enableHtml' => $row['enableHtml'], + 'enableComments' => $row['enableComments'], + 'isDisabled' => $row['isDisabled'], + 'isDeleted' => $row['isDeleted'], + 'ipAddress' => $row['ipAddress'], + 'deleteTime' => $row['deleteTime'], + 'isCommercial' => $row['isCommercial'], + 'isPurchasable' => $row['isPurchasable'], + 'price' => $row['price'], + 'currency' => $row['currency'], + 'totalRevenue' => (isset($row['totalRevenue']) ? $row['totalRevenue'] : 0), + 'purchases' => $row['purchases'], + 'licenseName' => (isset($row['licenseName']) ? $row['licenseName'] : ''), + 'licenseURL' => (isset($row['licenseURL']) ? $row['licenseURL'] : ''), + 'downloads' => $row['downloads'], + 'isFeatured' => $row['isFeatured'], + 'lastChangeTime' => $row['lastChangeTime'], + ]; + + // file icon + if (!empty($row['iconHash'])) { + $data['iconHash'] = $row['iconHash']; + $data['iconExtension'] = $row['iconExtension']; + $additionalData['iconLocation'] = $this->getFilebaseDir() . 'images/file/' . substr($row['iconHash'], 0, 2) . '/' . $row['fileID'] . '.' . $row['iconExtension']; + } + + if (!empty($categories)) { + if (count($categories) == 1) { + $data['categoryID'] = reset($categories); } else { - // 3.0+ - $data['categoryID'] = $row['categoryID']; + $additionalData['categories'] = $categories; } - - ImportHandler::getInstance()->getImporter('com.woltlab.filebase.file')->import($row['fileID'], $data, $additionalData); } + + ImportHandler::getInstance()->getImporter('com.woltlab.filebase.file')->import($row['fileID'], $data, $additionalData); } /** @@ -2464,38 +2538,112 @@ class WBB4xExporter extends AbstractExporter { * @param integer $limit */ public function exportFilebaseFileVersions($offset, $limit) { - $sql = "SELECT * + if (version_compare($this->getPackageVersion('com.woltlab.filebase'), '5.3.0 Alpha 1', '>=')) { + $this->exportFilebaseFileVersions53($offset, $limit); + return; + } + + $sql = "SELECT file_version.*, language.languageCode + FROM filebase".$this->dbNo."_file_version file_version + LEFT JOIN filebase".$this->dbNo."_file file + ON (file.fileID = file_version.fileID) + LEFT JOIN wcf".$this->dbNo."_language language + ON (language.languageID = file.languageID) + WHERE file_version.versionID BETWEEN ? AND ? + ORDER BY file_version.versionID"; + $statement = $this->database->prepareStatement($sql); + $statement->execute([$offset + 1, $offset + $limit]); + while ($row = $statement->fetchArray()) { + $contents[$row['languageCode'] ?: ''] = [ + 'description' => $row['description'], + ]; + + $this->exportFilebaseFileVersionsHelper($row, $contents); + } + } + + /** + * Exports filebase file versions from 5.3+. + * + * @param integer $offset + * @param integer $limit + */ + public function exportFilebaseFileVersions53($offset, $limit) { + // get version ids + $versionIDs = []; + $sql = "SELECT versionID FROM filebase".$this->dbNo."_file_version WHERE versionID BETWEEN ? AND ? ORDER BY versionID"; $statement = $this->database->prepareStatement($sql); $statement->execute([$offset + 1, $offset + $limit]); while ($row = $statement->fetchArray()) { - $fileLocation = ''; - if (empty($row['downloadURL'])) { - $fileLocation = $this->getFilebaseDir() . 'files/' . substr($row['fileHash'], 0, 2) . '/' . $row['versionID'] . '-' . $row['fileHash']; + $versionIDs[] = $row['versionID']; + } + if (empty($versionIDs)) return; + + // get version contents + $versionContents = []; + $conditionBuilder = new PreparedStatementConditionBuilder(); + $conditionBuilder->add('versionID IN (?)', [$versionIDs]); + $sql = "SELECT version_content.*, language.languageCode + FROM filebase".$this->dbNo."_file_version_content version_content + LEFT JOIN wcf".$this->dbNo."_language language + ON (language.languageID = version_content.languageID) + " . $conditionBuilder; + $statement = $this->database->prepareStatement($sql); + $statement->execute($conditionBuilder->getParameters()); + while ($row = $statement->fetchArray()) { + $versionContents[$row['versionID']][$row['languageCode'] ?: ''] = $row; + } + + // get versions + $sql = "SELECT * + FROM filebase".$this->dbNo."_file_version + " . $conditionBuilder; + $statement = $this->database->prepareStatement($sql); + $statement->execute($conditionBuilder->getParameters()); + while ($row = $statement->fetchArray()) { + $contents = []; + if (isset($versionContents[$row['versionID']])) { + foreach ($versionContents[$row['versionID']] as $languageCode => $versionContent) { + $contents[$languageCode ?: ''] = [ + 'description' => $versionContent['description'], + ]; + } } - ImportHandler::getInstance()->getImporter('com.woltlab.filebase.file.version')->import($row['versionID'], [ - 'fileID' => $row['fileID'], - 'versionNumber' => $row['versionNumber'], - 'description' => $row['description'], - 'filename' => $row['filename'], - 'filesize' => $row['filesize'], - 'fileType' => $row['fileType'], - 'fileHash' => $row['fileHash'], - 'uploadTime' => $row['uploadTime'], - 'downloads' => $row['downloads'], - 'downloadURL' => (isset($row['downloadURL']) ? $row['downloadURL'] : ''), - 'isDisabled' => $row['isDisabled'], - 'isDeleted' => $row['isDeleted'], - 'deleteTime' => $row['deleteTime'], - 'ipAddress' => $row['ipAddress'], - 'enableHtml' => $row['enableHtml'] - ], ['fileLocation' => $fileLocation]); + $this->exportFilebaseFileVersionsHelper($row, $contents); } } + protected function exportFilebaseFileVersionsHelper(array $row, array $contents = []) { + $additionalData = [ + 'contents' => $contents, + 'fileLocation' => '', + ]; + if (empty($row['downloadURL'])) { + $additionalData['fileLocation'] = $this->getFilebaseDir() . 'files/' . substr($row['fileHash'], 0, 2) . '/' . $row['versionID'] . '-' . $row['fileHash']; + } + + ImportHandler::getInstance()->getImporter('com.woltlab.filebase.file.version')->import($row['versionID'], [ + 'fileID' => $row['fileID'], + 'versionNumber' => $row['versionNumber'], + 'filename' => $row['filename'], + 'filesize' => $row['filesize'], + 'fileType' => $row['fileType'], + 'fileHash' => $row['fileHash'], + 'uploadTime' => $row['uploadTime'], + 'downloads' => $row['downloads'], + 'downloadURL' => (isset($row['downloadURL']) ? $row['downloadURL'] : ''), + 'isDisabled' => $row['isDisabled'], + 'isDeleted' => $row['isDeleted'], + 'deleteTime' => $row['deleteTime'], + 'ipAddress' => $row['ipAddress'], + 'enableHtml' => $row['enableHtml'] + ], $additionalData); + } + /** * Counts filebase file comments. */ diff --git a/files/lib/system/exporter/XF2xExporter.class.php b/files/lib/system/exporter/XF2xExporter.class.php index 2d45d64..b1b609e 100644 --- a/files/lib/system/exporter/XF2xExporter.class.php +++ b/files/lib/system/exporter/XF2xExporter.class.php @@ -1532,18 +1532,23 @@ class XF2xExporter extends AbstractExporter { $statement = $this->database->prepareStatement($sql); $statement->execute($conditionBuilder->getParameters()); while ($row = $statement->fetchArray()) { - $additionalData = []; - if (isset($tags[$row['resource_id']])) $additionalData['tags'] = $tags[$row['resource_id']]; + $additionalData = [ + 'contents' => [ + '' => [ + 'subject' => $row['title'], + 'teaser' => $row['tag_line'], + 'message' => self::fixBBCodes($row['message'] ?? ''), + 'tags' => $tags[$row['resource_id']] ?? [], + ], + ], + ]; $data = [ 'userID' => $row['user_id'], 'categoryID' => $row['resource_category_id'], 'username' => $row['username'], - 'subject' => $row['title'], - 'message' => self::fixBBCodes($row['message'] ?? ''), 'time' => $row['resource_date'], 'lastChangeTime' => $row['last_update'], - 'teaser' => $row['tag_line'], 'enableHtml' => 0, 'isDisabled' => $row['resource_state'] == 'moderated' ? 1 : 0, 'isDeleted' => $row['resource_state'] == 'deleted' ? 1 : 0, @@ -1614,12 +1619,18 @@ class XF2xExporter extends AbstractExporter { $statement = $this->database->prepareStatement($sql); $statement->execute(['resource_version', $offset + 1, $offset + $limit]); while ($row = $statement->fetchArray()) { - $fileLocation = ''; + $additionalData = [ + 'fileLocation' => '', + 'contents' => [ + '' => [ + 'description' => '', + ], + ], + ]; $data = [ 'fileID' => $row['resource_id'], 'versionNumber' => $row['version_string'], - 'description' => '', 'filename' => $row['filename'], 'downloadURL' => $row['download_url'], 'uploadTime' => $row['release_date'], @@ -1636,9 +1647,10 @@ class XF2xExporter extends AbstractExporter { $data['filesize'] = filesize($fileLocation); $data['fileType'] = FileUtil::getMimeType($fileLocation) ?: 'application/octet-stream'; $data['fileHash'] = sha1_file($fileLocation); + $additionalData['fileLocation'] = $fileLocation; } - ImportHandler::getInstance()->getImporter('com.woltlab.filebase.file.version')->import($row['resource_version_id'], $data, ['fileLocation' => $fileLocation]); + ImportHandler::getInstance()->getImporter('com.woltlab.filebase.file.version')->import($row['resource_version_id'], $data, $additionalData); } }