[TASK] Remove site caches if page is created on top level 17/58017/4
authorChristian Kuhn <lolli@schwarzbu.ch>
Thu, 23 Aug 2018 22:02:32 +0000 (00:02 +0200)
committerAnja Leichsenring <aleichsenring@ab-softlab.de>
Mon, 27 Aug 2018 19:15:13 +0000 (21:15 +0200)
The patch fixes a fatal php scenario if a page is created
on root level. The data handler now flushes site caches if that
happens and unsets the SiteMatcher singleton so it is forced
to be recalculated if re-used in current request.

Change-Id: Ie54f70b1bbfaaf1f6302f4e6b14abcf6af4c310f
Resolves: #85985
Releases: master
Reviewed-on: https://review.typo3.org/58017
Tested-by: TYPO3com <no-reply@typo3.com>
Reviewed-by: Wouter Wolters <typo3@wouterwolters.nl>
Tested-by: Wouter Wolters <typo3@wouterwolters.nl>
Reviewed-by: Anja Leichsenring <aleichsenring@ab-softlab.de>
Tested-by: Anja Leichsenring <aleichsenring@ab-softlab.de>
typo3/sysext/core/Classes/Hooks/SiteDataHandlerCacheHook.php

index 4baa5d8..0c1a207 100644 (file)
@@ -19,10 +19,13 @@ namespace TYPO3\CMS\Core\Hooks;
 use TYPO3\CMS\Core\Cache\CacheManager;
 use TYPO3\CMS\Core\Cache\Frontend\FrontendInterface;
 use TYPO3\CMS\Core\DataHandling\DataHandler;
+use TYPO3\CMS\Core\Routing\SiteMatcher;
 use TYPO3\CMS\Core\Utility\GeneralUtility;
 
 /**
- * Whenever a sys_domain or sys_language record is modified, the Site Handling caches should be flushed.
+ * When a sys_domain or sys_language record is modified, the Site Handling caches should be flushed.
+ * Also, if pages on root level are changed, site handling caches need flush.
+ *
  * @internal
  */
 class SiteDataHandlerCacheHook
@@ -38,9 +41,15 @@ class SiteDataHandlerCacheHook
      */
     public function processDatamap_afterDatabaseOperations(string $status, string $table, $recordId, array $updatedFields, DataHandler $dataHandler)
     {
-        if ($table === 'sys_domain' || $table === 'sys_language') {
+        if ($table === 'sys_domain'
+            || $table === 'sys_language'
+            || ($status === 'new' && $table === 'pages' && (int)$updatedFields['pid'] === 0)
+        ) {
             $this->getCache()->remove('pseudo-sites');
             $this->getCache()->remove('legacy-domains');
+            // After evicting caches, we need to make sure these are re-initialized within the
+            // current request if needed. Easiest solution is to purge the SiteMatcher singleton.
+            GeneralUtility::removeSingletonInstance(SiteMatcher::class, GeneralUtility::makeInstance(SiteMatcher::class));
         }
     }