diff --git a/typo3/sysext/rtehtmlarea/Classes/Hook/Install/DeprecatedRteProperties.php b/typo3/sysext/rtehtmlarea/Classes/Hook/Install/DeprecatedRteProperties.php index a9442e1e63117fa8999e8a8084d5f9bcd558311b..6fbe1845939cabecb42aeb9c5bf05f322502d30c 100644 --- a/typo3/sysext/rtehtmlarea/Classes/Hook/Install/DeprecatedRteProperties.php +++ b/typo3/sysext/rtehtmlarea/Classes/Hook/Install/DeprecatedRteProperties.php @@ -14,6 +14,10 @@ namespace TYPO3\CMS\Rtehtmlarea\Hook\Install; * The TYPO3 project - inspiring people to share! */ +use Doctrine\DBAL\DBALException; +use TYPO3\CMS\Core\Database\ConnectionPool; +use TYPO3\CMS\Core\Utility\GeneralUtility; +use TYPO3\CMS\Core\Utility\StringUtility; use TYPO3\CMS\Install\Updates\AbstractUpdate; /** @@ -102,7 +106,7 @@ class DeprecatedRteProperties extends AbstractUpdate { $result = false; - $pages = $this->getPagesWithDeprecatedRteProperties($dbQueries, $customMessages); + $pages = $this->getPagesWithDeprecatedRteProperties($customMessages); $pagesCount = count($pages); $deprecatedProperties = ''; $deprecatedRteProperties = array_merge($this->replacementRteProperties, $this->useInsteadRteProperties); @@ -165,7 +169,7 @@ class DeprecatedRteProperties extends AbstractUpdate public function performUpdate(array &$dbQueries, &$customMessages) { $customMessages = ''; - $pages = $this->getPagesWithDeprecatedRteProperties($dbQueries, $customMessages); + $pages = $this->getPagesWithDeprecatedRteProperties($customMessages); if (empty($customMessages)) { $pagesCount = count($pages); if ($pagesCount) { @@ -176,7 +180,7 @@ class DeprecatedRteProperties extends AbstractUpdate if (empty($customMessages)) { // If all pages were updated, we query again to check if any deprecated properties are still present. if (count($updateablePages) === $pagesCount) { - $pagesAfter = $this->getPagesWithDeprecatedRteProperties($dbQueries, $customMessages); + $pagesAfter = $this->getPagesWithDeprecatedRteProperties($customMessages); if (empty($customMessages)) { if (!empty($pagesAfter)) { $customMessages = 'Some deprecated Page TSconfig properties were found. However, the wizard was unable to automatically replace all the deprecated properties found. Some properties will have to be replaced manually.'; @@ -198,29 +202,66 @@ class DeprecatedRteProperties extends AbstractUpdate /** * Gets the pages with deprecated RTE properties in TSconfig column * - * @param array $dbQueries Pointer where to insert all DB queries made, so they can be shown to the user if wanted * @param string $customMessages Pointer to output custom messages * @return array uid and inclusion string for the pages with deprecated RTE properties in TSconfig column */ - protected function getPagesWithDeprecatedRteProperties(&$dbQueries, &$customMessages) + protected function getPagesWithDeprecatedRteProperties(&$customMessages) { - $fields = 'uid, TSconfig'; - $table = 'pages'; - $where = ''; - $db = $this->getDatabaseConnection(); + $queryBuilder = GeneralUtility::makeInstance(ConnectionPool::class)->getQueryBuilderForTable('pages'); + $queryBuilder->getRestrictions()->removeAll(); + + $isMySQL = StringUtility::beginsWith($queryBuilder->getConnection()->getServerVersion(), 'MySQL'); + + $constraints = []; foreach (array_merge($this->replacementRteProperties, $this->useInsteadRteProperties, $this->doubleReplacementRteProperties) as $deprecatedRteProperty => $_) { - $where .= ($where ? ' OR ' : '') . '(TSconfig LIKE BINARY ' . $db->fullQuoteStr('%RTE.%' . $deprecatedRteProperty . '%', 'pages') . ' AND TSconfig NOT LIKE BINARY ' . $db->fullQuoteStr('%RTE.%' . $deprecatedRteProperty . 's%', 'pages') . ')' . LF; - } - $res = $db->exec_SELECTquery($fields, $table, $where); - $dbQueries[] = str_replace(LF, ' ', $db->debug_lastBuiltQuery); - if ($db->sql_error()) { - $customMessages = 'SQL-ERROR: ' . htmlspecialchars($db->sql_error()); + // MySQL needs the non-standard BINARY modifier to ensure case sensitive comparisons with LIKE + if ($isMySQL) { + $constraints[] = $queryBuilder->expr()->andX( + $queryBuilder->expr()->comparison( + $queryBuilder->quoteIdentifier('TSconfig'), + 'LIKE BINARY', + $queryBuilder->createNamedParameter( + '%RTE.%' . $queryBuilder->escapeLikeWildcards($deprecatedRteProperty) . '%' + ) + ), + $queryBuilder->expr()->comparison( + $queryBuilder->quoteIdentifier('TSconfig'), + 'NOT LIKE BINARY', + $queryBuilder->createNamedParameter( + '%RTE.%' . $queryBuilder->escapeLikeWildcards($deprecatedRteProperty) . 's%' + ) + ) + ); + } else { + $constraints[] = $queryBuilder->expr()->andX( + $queryBuilder->expr()->like( + 'TSconfig', + $queryBuilder->createNamedParameter( + '%RTE.%' . $queryBuilder->escapeLikeWildcards($deprecatedRteProperty) . '%' + ) + ), + $queryBuilder->expr()->notLike( + 'TSconfig', + $queryBuilder->createNamedParameter( + '%RTE.%' . $queryBuilder->escapeLikeWildcards($deprecatedRteProperty) . 's%' + ) + ) + ); + } } - $pages = array(); - while ($row = $db->sql_fetch_assoc($res)) { - $pages[] = $row; + + try { + return $queryBuilder + ->select('uid', 'TSconfig') + ->from('pages') + ->orWhere(...$constraints) + ->execute() + ->fetchAll(); + } catch (DBALException $e) { + $customMessages = 'SQL-ERROR: ' . htmlspecialchars($e->getPrevious()->getMessage()); } - return $pages; + + return []; } /** @@ -235,7 +276,7 @@ class DeprecatedRteProperties extends AbstractUpdate $deprecatedProperties = explode(',', '/' . implode('/,/((RTE\\.(default\\.|config\\.[a-zA-Z0-9_\\-]*\\.[a-zA-Z0-9_\\-]*\\.))|\\s)', array_keys($this->replacementRteProperties)) . '/'); $replacementProperties = explode(',', '$1' . implode(',$1', array_values($this->replacementRteProperties))); $updatedPageTSConfig = preg_replace($deprecatedProperties, $replacementProperties, $page['TSconfig']); - if ($updatedPageTSConfig == $page['TSconfig']) { + if ($updatedPageTSConfig === $page['TSconfig']) { unset($pages[$index]); } else { $pages[$index]['TSconfig'] = $updatedPageTSConfig; @@ -253,18 +294,17 @@ class DeprecatedRteProperties extends AbstractUpdate */ protected function updatePages($pages, &$dbQueries, &$customMessages) { - $db = $this->getDatabaseConnection(); + $queryBuilder = GeneralUtility::makeInstance(ConnectionPool::class)->getQueryBuilderForTable('pages'); foreach ($pages as $page) { - $table = 'pages'; - $where = 'uid =' . $page['uid']; - $field_values = array( - 'TSconfig' => $page['TSconfig'] - ); - $db->exec_UPDATEquery($table, $where, $field_values); - $dbQueries[] = str_replace(LF, ' ', $db->debug_lastBuiltQuery); - if ($db->sql_error()) { - $customMessages .= 'SQL-ERROR: ' . htmlspecialchars($db->sql_error()) . LF . LF; + try { + $queryBuilder->update('pages') + ->where($queryBuilder->expr()->eq('uid', (int)$page['uid'])) + ->set('TSconfig', $queryBuilder->quote($page['TSconfig']), false) + ->execute(); + } catch (DBALException $e) { + $customMessages .= 'SQL-ERROR: ' . htmlspecialchars($e->getPrevious()->getMessage()) . LF . LF; } + $dbQueries[] = str_replace(LF, ' ', $queryBuilder->getSQL()); } } } diff --git a/typo3/sysext/rtehtmlarea/Classes/Hook/Install/RteAcronymButtonRenamedToAbbreviation.php b/typo3/sysext/rtehtmlarea/Classes/Hook/Install/RteAcronymButtonRenamedToAbbreviation.php index cbe2a94e357bd91f4fd84764a1c068aa6e77d30f..e97fdf4ad314decd31399404e9b4082cab1cf933 100644 --- a/typo3/sysext/rtehtmlarea/Classes/Hook/Install/RteAcronymButtonRenamedToAbbreviation.php +++ b/typo3/sysext/rtehtmlarea/Classes/Hook/Install/RteAcronymButtonRenamedToAbbreviation.php @@ -14,6 +14,10 @@ namespace TYPO3\CMS\Rtehtmlarea\Hook\Install; * The TYPO3 project - inspiring people to share! */ +use Doctrine\DBAL\DBALException; +use TYPO3\CMS\Core\Database\ConnectionPool; +use TYPO3\CMS\Core\Utility\GeneralUtility; +use TYPO3\CMS\Core\Utility\StringUtility; use TYPO3\CMS\Install\Updates\AbstractUpdate; /** @@ -37,7 +41,7 @@ class RteAcronymButtonRenamedToAbbreviation extends AbstractUpdate { $result = false; - $pages = $this->getPagesWithDeprecatedRteProperties($dbQueries, $customMessages); + $pages = $this->getPagesWithDeprecatedRteProperties($customMessages); $pagesCount = count($pages); $description = '<p>The RTE "acronym" button is deprecated and replaced by the "abbreviation" button since TYPO3 CMS 7.0.</p>' . LF . '<p>Page TSconfig currently includes the string "acronym" on <strong>' . strval($pagesCount) . ' pages</strong> (including deleted and hidden pages).</p>' . LF; if ($pagesCount) { @@ -78,7 +82,7 @@ class RteAcronymButtonRenamedToAbbreviation extends AbstractUpdate public function performUpdate(array &$dbQueries, &$customMessages) { $customMessages = ''; - $pages = $this->getPagesWithDeprecatedRteProperties($dbQueries, $customMessages); + $pages = $this->getPagesWithDeprecatedRteProperties($customMessages); if (empty($customMessages)) { $pagesCount = count($pages); if ($pagesCount) { @@ -103,26 +107,37 @@ class RteAcronymButtonRenamedToAbbreviation extends AbstractUpdate /** * Gets the pages with deprecated RTE properties in TSconfig column * - * @param array $dbQueries Pointer where to insert all DB queries made, so they can be shown to the user if wanted * @param string $customMessages Pointer to output custom messages * @return array uid and inclusion string for the pages with deprecated RTE properties in TSconfig column */ - protected function getPagesWithDeprecatedRteProperties(&$dbQueries, &$customMessages) + protected function getPagesWithDeprecatedRteProperties(&$customMessages) { - $db = $this->getDatabaseConnection(); - $fields = 'uid, TSconfig'; - $table = 'pages'; - $where = 'TSconfig LIKE BINARY ' . $db->fullQuoteStr('%acronym%', 'pages'); - $res = $db->exec_SELECTquery($fields, $table, $where); - $dbQueries[] = str_replace(LF, ' ', $db->debug_lastBuiltQuery); - if ($db->sql_error()) { - $customMessages = 'SQL-ERROR: ' . htmlspecialchars($db->sql_error()); + $queryBuilder = GeneralUtility::makeInstance(ConnectionPool::class)->getQueryBuilderForTable('pages'); + $queryBuilder->getRestrictions()->removeAll(); + + $isMySQL = StringUtility::beginsWith($queryBuilder->getConnection()->getServerVersion(), 'MySQL'); + if ($isMySQL) { + $whereClause = $queryBuilder->expr()->comparison( + $queryBuilder->quoteIdentifier('TSconfig'), + 'LIKE BINARY', + $queryBuilder->createNamedParameter('%acronym%') + ); + } else { + $whereClause = $queryBuilder->expr()->like('TSconfig', $queryBuilder->createNamedParameter('%acronym%')); } - $pages = array(); - while ($row = $db->sql_fetch_assoc($res)) { - $pages[] = $row; + + try { + return $queryBuilder + ->select('uid', 'TSconfig') + ->from('pages') + ->where($whereClause) + ->execute() + ->fetchAll(); + } catch (DBALException $e) { + $customMessages = 'SQL-ERROR: ' . htmlspecialchars($e->getPrevious()->getMessage()); } - return $pages; + + return []; } /** @@ -135,7 +150,7 @@ class RteAcronymButtonRenamedToAbbreviation extends AbstractUpdate { foreach ($pages as $index => $page) { $updatedPageTSConfig = str_replace('acronym', 'abbreviation', $page['TSconfig']); - if ($updatedPageTSConfig == $page['TSconfig']) { + if ($updatedPageTSConfig === $page['TSconfig']) { unset($pages[$index]); } else { $pages[$index]['TSconfig'] = $updatedPageTSConfig; @@ -153,18 +168,17 @@ class RteAcronymButtonRenamedToAbbreviation extends AbstractUpdate */ protected function updatePages($pages, &$dbQueries, &$customMessages) { - $db = $this->getDatabaseConnection(); + $queryBuilder = GeneralUtility::makeInstance(ConnectionPool::class)->getQueryBuilderForTable('pages'); foreach ($pages as $page) { - $table = 'pages'; - $where = 'uid =' . $page['uid']; - $field_values = array( - 'TSconfig' => $page['TSconfig'] - ); - $db->exec_UPDATEquery($table, $where, $field_values); - $dbQueries[] = str_replace(LF, ' ', $db->debug_lastBuiltQuery); - if ($db->sql_error()) { - $customMessages .= 'SQL-ERROR: ' . htmlspecialchars($db->sql_error()) . LF . LF; + try { + $queryBuilder->update('pages') + ->where($queryBuilder->expr()->eq('uid', (int)$page['uid'])) + ->set('TSconfig', $queryBuilder->quote($page['TSconfig']), false) + ->execute(); + } catch (DBALException $e) { + $customMessages .= 'SQL-ERROR: ' . htmlspecialchars($e->getPrevious()->getMessage()) . LF . LF; } + $dbQueries[] = str_replace(LF, ' ', $queryBuilder->getSQL()); } } }