From 1506516dc3178c10a3bace2a9d7b52a975973706 Mon Sep 17 00:00:00 2001 From: Nathaniel Catchpole Date: Thu, 4 Oct 2018 19:30:49 +0100 Subject: [PATCH] Issue #2875276 by huzooka, ion.macaria, cestmoi, catch: Breadcrumbs disappears when starting with front-page after cache rebuild (for anonymous user) --- .../src/Functional/NodeTranslationUITest.php | 1 + .../system/src/PathBasedBreadcrumbBuilder.php | 2 +- .../Menu/BreadcrumbFrontCacheContextsTest.php | 91 +++++++++++++++++++ .../PathBasedBreadcrumbBuilderTest.php | 27 ++++-- 4 files changed, 113 insertions(+), 8 deletions(-) create mode 100644 core/modules/system/tests/src/Functional/Menu/BreadcrumbFrontCacheContextsTest.php diff --git a/core/modules/node/tests/src/Functional/NodeTranslationUITest.php b/core/modules/node/tests/src/Functional/NodeTranslationUITest.php index 513c074932..54d9c73038 100644 --- a/core/modules/node/tests/src/Functional/NodeTranslationUITest.php +++ b/core/modules/node/tests/src/Functional/NodeTranslationUITest.php @@ -27,6 +27,7 @@ class NodeTranslationUITest extends ContentTranslationUITestBase { 'url.path.parent', 'url.query_args:_wrapper_format', 'user.roles', + 'url.path.is_front', // These two cache contexts are added by BigPipe. 'cookies:big_pipe_nojs', 'session.exists', diff --git a/core/modules/system/src/PathBasedBreadcrumbBuilder.php b/core/modules/system/src/PathBasedBreadcrumbBuilder.php index ebc5df0b75..261ae32a24 100644 --- a/core/modules/system/src/PathBasedBreadcrumbBuilder.php +++ b/core/modules/system/src/PathBasedBreadcrumbBuilder.php @@ -144,7 +144,7 @@ public function build(RouteMatchInterface $route_match) { // Add the url.path.parent cache context. This code ignores the last path // part so the result only depends on the path parents. - $breadcrumb->addCacheContexts(['url.path.parent']); + $breadcrumb->addCacheContexts(['url.path.parent', 'url.path.is_front']); // Do not display a breadcrumb on the frontpage. if ($this->pathMatcher->isFrontPage()) { diff --git a/core/modules/system/tests/src/Functional/Menu/BreadcrumbFrontCacheContextsTest.php b/core/modules/system/tests/src/Functional/Menu/BreadcrumbFrontCacheContextsTest.php new file mode 100644 index 0000000000..9027209467 --- /dev/null +++ b/core/modules/system/tests/src/Functional/Menu/BreadcrumbFrontCacheContextsTest.php @@ -0,0 +1,91 @@ +drupalPlaceBlock('system_breadcrumb_block'); + + $user = $this->drupalCreateUser(); + + $this->drupalCreateContentType([ + 'type' => 'page', + ]); + + // Create a node for front page. + $node_front = $this->drupalCreateNode([ + 'uid' => $user->id(), + ]); + + // Create a node with a random alias. + $this->nodeWithAlias = $this->drupalCreateNode([ + 'uid' => $user->id(), + 'type' => 'page', + 'path' => '/' . $this->randomMachineName(), + ]); + + // Configure 'node' as front page. + $this->config('system.site') + ->set('page.front', '/node/' . $node_front->id()) + ->save(); + + \Drupal::cache('render')->deleteAll(); + } + + /** + * Validate that breadcrumb markup get the right cache contexts. + * + * Checking that the breadcrumb will be printed on node canonical routes even + * if it was rendered for the page first. + */ + public function testBreadcrumbsFrontPageCache() { + // Hit front page first as anonymous user with 'cold' render cache. + $this->drupalGet(''); + $web_assert = $this->assertSession(); + // Verify that no breadcrumb block presents. + $web_assert->elementNotExists('css', '.block-system-breadcrumb-block'); + + // Verify that breadcrumb appears correctly for the test content + // (which is not set as front page). + $this->drupalGet($this->nodeWithAlias->path->alias); + $breadcrumbs = $this->assertSession()->elementExists('css', '.block-system-breadcrumb-block'); + $crumbs = $breadcrumbs->findAll('css', 'ol li'); + $this->assertTrue(count($crumbs) === 1); + $this->assertTrue($crumbs[0]->getText() === 'Home'); + } + +} diff --git a/core/modules/system/tests/src/Unit/Breadcrumbs/PathBasedBreadcrumbBuilderTest.php b/core/modules/system/tests/src/Unit/Breadcrumbs/PathBasedBreadcrumbBuilderTest.php index a24313f4af..b07f31f62f 100644 --- a/core/modules/system/tests/src/Unit/Breadcrumbs/PathBasedBreadcrumbBuilderTest.php +++ b/core/modules/system/tests/src/Unit/Breadcrumbs/PathBasedBreadcrumbBuilderTest.php @@ -151,7 +151,7 @@ public function testBuildOnFrontpage() { $breadcrumb = $this->builder->build($this->getMock('Drupal\Core\Routing\RouteMatchInterface')); $this->assertEquals([], $breadcrumb->getLinks()); - $this->assertEquals(['url.path.parent'], $breadcrumb->getCacheContexts()); + $this->assertEquals(['url.path.is_front', 'url.path.parent'], $breadcrumb->getCacheContexts()); $this->assertEquals([], $breadcrumb->getCacheTags()); $this->assertEquals(Cache::PERMANENT, $breadcrumb->getCacheMaxAge()); } @@ -168,7 +168,7 @@ public function testBuildWithOnePathElement() { $breadcrumb = $this->builder->build($this->getMock('Drupal\Core\Routing\RouteMatchInterface')); $this->assertEquals([0 => new Link('Home', new Url(''))], $breadcrumb->getLinks()); - $this->assertEquals(['url.path.parent'], $breadcrumb->getCacheContexts()); + $this->assertEquals(['url.path.is_front', 'url.path.parent'], $breadcrumb->getCacheContexts()); $this->assertEquals([], $breadcrumb->getCacheTags()); $this->assertEquals(Cache::PERMANENT, $breadcrumb->getCacheMaxAge()); } @@ -203,7 +203,11 @@ public function testBuildWithTwoPathElements() { $breadcrumb = $this->builder->build($this->getMock('Drupal\Core\Routing\RouteMatchInterface')); $this->assertEquals([0 => new Link('Home', new Url('')), 1 => new Link('Example', new Url('example'))], $breadcrumb->getLinks()); - $this->assertEquals(['url.path.parent', 'user.permissions'], $breadcrumb->getCacheContexts()); + $this->assertEquals([ + 'url.path.is_front', + 'url.path.parent', + 'user.permissions', + ], $breadcrumb->getCacheContexts()); $this->assertEquals([], $breadcrumb->getCacheTags()); $this->assertEquals(Cache::PERMANENT, $breadcrumb->getCacheMaxAge()); } @@ -254,7 +258,12 @@ public function testBuildWithThreePathElements() { new Link('Example', new Url('example')), new Link('Bar', new Url('example_bar')), ], $breadcrumb->getLinks()); - $this->assertEquals(['bar', 'url.path.parent', 'user.permissions'], $breadcrumb->getCacheContexts()); + $this->assertEquals([ + 'bar', + 'url.path.is_front', + 'url.path.parent', + 'user.permissions', + ], $breadcrumb->getCacheContexts()); $this->assertEquals(['example'], $breadcrumb->getCacheTags()); $this->assertEquals(Cache::PERMANENT, $breadcrumb->getCacheMaxAge()); } @@ -281,7 +290,7 @@ public function testBuildWithException($exception_class, $exception_argument) { // No path matched, though at least the frontpage is displayed. $this->assertEquals([0 => new Link('Home', new Url(''))], $breadcrumb->getLinks()); - $this->assertEquals(['url.path.parent'], $breadcrumb->getCacheContexts()); + $this->assertEquals(['url.path.is_front', 'url.path.parent'], $breadcrumb->getCacheContexts()); $this->assertEquals([], $breadcrumb->getCacheTags()); $this->assertEquals(Cache::PERMANENT, $breadcrumb->getCacheMaxAge()); } @@ -325,7 +334,7 @@ public function testBuildWithNonProcessedPath() { // No path matched, though at least the frontpage is displayed. $this->assertEquals([0 => new Link('Home', new Url(''))], $breadcrumb->getLinks()); - $this->assertEquals(['url.path.parent'], $breadcrumb->getCacheContexts()); + $this->assertEquals(['url.path.is_front', 'url.path.parent'], $breadcrumb->getCacheContexts()); $this->assertEquals([], $breadcrumb->getCacheTags()); $this->assertEquals(Cache::PERMANENT, $breadcrumb->getCacheMaxAge()); } @@ -373,7 +382,11 @@ public function testBuildWithUserPath() { $breadcrumb = $this->builder->build($this->getMock('Drupal\Core\Routing\RouteMatchInterface')); $this->assertEquals([0 => new Link('Home', new Url('')), 1 => new Link('Admin', new Url('user_page'))], $breadcrumb->getLinks()); - $this->assertEquals(['url.path.parent', 'user.permissions'], $breadcrumb->getCacheContexts()); + $this->assertEquals([ + 'url.path.is_front', + 'url.path.parent', + 'user.permissions', + ], $breadcrumb->getCacheContexts()); $this->assertEquals([], $breadcrumb->getCacheTags()); $this->assertEquals(Cache::PERMANENT, $breadcrumb->getCacheMaxAge()); } -- GitLab