Issue #3375276 by DieterHolvoet: 4xx HTTP code theme suggestions are not applied if a node is set as 4xx path

merge-requests/4470/head
Lauri Eskola 2023-07-24 23:29:04 +03:00
parent 5ac5a2b6c3
commit c7bde64317
No known key found for this signature in database
GPG Key ID: 382FC0F5B0DF53F8
2 changed files with 35 additions and 19 deletions

View File

@ -37,6 +37,7 @@ use Drupal\Core\StreamWrapper\StreamWrapperManager;
use Drupal\Core\Url; use Drupal\Core\Url;
use GuzzleHttp\Exception\TransferException; use GuzzleHttp\Exception\TransferException;
use Symfony\Component\HttpFoundation\RedirectResponse; use Symfony\Component\HttpFoundation\RedirectResponse;
use Symfony\Component\HttpKernel\Exception\HttpExceptionInterface;
/** /**
* Disabled option on forms and settings. * Disabled option on forms and settings.
@ -306,15 +307,11 @@ function system_theme_suggestions_page(array $variables) {
$path_args = explode('/', trim(\Drupal::service('path.current')->getPath(), '/')); $path_args = explode('/', trim(\Drupal::service('path.current')->getPath(), '/'));
$suggestions = theme_get_suggestions($path_args, 'page'); $suggestions = theme_get_suggestions($path_args, 'page');
$http_error_suggestions = [ $supported_http_error_codes = [401, 403, 404];
'system.401' => 'page__401', $exception = \Drupal::requestStack()->getCurrentRequest()->attributes->get('exception');
'system.403' => 'page__403', if ($exception instanceof HttpExceptionInterface && in_array($exception->getStatusCode(), $supported_http_error_codes, TRUE)) {
'system.404' => 'page__404',
];
$route_name = \Drupal::routeMatch()->getRouteName();
if (isset($http_error_suggestions[$route_name])) {
$suggestions[] = 'page__4xx'; $suggestions[] = 'page__4xx';
$suggestions[] = $http_error_suggestions[$route_name]; $suggestions[] = 'page__' . $exception->getStatusCode();
} }
return $suggestions; return $suggestions;

View File

@ -5,10 +5,10 @@ namespace Drupal\KernelTests\Core\Theme;
use Drupal\Core\Extension\ModuleExtensionList; use Drupal\Core\Extension\ModuleExtensionList;
use Drupal\Core\Path\CurrentPathStack; use Drupal\Core\Path\CurrentPathStack;
use Drupal\Core\Path\PathMatcherInterface; use Drupal\Core\Path\PathMatcherInterface;
use Drupal\Core\Routing\RouteMatchInterface;
use Drupal\Core\Theme\Registry; use Drupal\Core\Theme\Registry;
use Drupal\Core\Utility\ThemeRegistry; use Drupal\Core\Utility\ThemeRegistry;
use Drupal\KernelTests\KernelTestBase; use Drupal\KernelTests\KernelTestBase;
use Symfony\Component\HttpKernel\Exception\HttpExceptionInterface;
/** /**
* Tests the behavior of the ThemeRegistry class. * Tests the behavior of the ThemeRegistry class.
@ -192,6 +192,26 @@ class RegistryTest extends KernelTestBase {
], $suggestions, 'Found expected page node suggestions.'); ], $suggestions, 'Found expected page node suggestions.');
} }
/**
* Tests page theme suggestions for 200 responses.
*/
public function test200ThemeSuggestions() {
$path_matcher = $this->prophesize(PathMatcherInterface::class);
$path_matcher->isFrontPage()->willReturn(FALSE);
\Drupal::getContainer()->set('path.matcher', $path_matcher->reveal());
$path_current = $this->prophesize(CurrentPathStack::class);
$path_current->getPath()->willReturn('/node/123');
\Drupal::getContainer()->set('path.current', $path_current->reveal());
$suggestions = \Drupal::moduleHandler()->invokeAll('theme_suggestions_page', [[]]);
$this->assertSame([
'page__node',
'page__node__%',
'page__node__123',
], $suggestions);
}
/** /**
* Data provider for test40xThemeSuggestions(). * Data provider for test40xThemeSuggestions().
* *
@ -200,9 +220,9 @@ class RegistryTest extends KernelTestBase {
*/ */
public function provider40xThemeSuggestions() { public function provider40xThemeSuggestions() {
return [ return [
['system.401', 'page__401'], [401, 'page__401'],
['system.403', 'page__403'], [403, 'page__403'],
['system.404', 'page__404'], [404, 'page__404'],
]; ];
} }
@ -211,19 +231,18 @@ class RegistryTest extends KernelTestBase {
* *
* @dataProvider provider40xThemeSuggestions * @dataProvider provider40xThemeSuggestions
*/ */
public function test40xThemeSuggestions($route, $suggestion) { public function test40xThemeSuggestions(int $httpCode, string $suggestion): void {
/** @var \Drupal\Core\Path\PathMatcherInterface $path_matcher */
$path_matcher = $this->prophesize(PathMatcherInterface::class); $path_matcher = $this->prophesize(PathMatcherInterface::class);
$path_matcher->isFrontPage()->willReturn(FALSE); $path_matcher->isFrontPage()->willReturn(FALSE);
\Drupal::getContainer()->set('path.matcher', $path_matcher->reveal()); \Drupal::getContainer()->set('path.matcher', $path_matcher->reveal());
/** @var \Drupal\Core\Path\CurrentPathStack $path_current */
$path_current = $this->prophesize(CurrentPathStack::class); $path_current = $this->prophesize(CurrentPathStack::class);
$path_current->getPath()->willReturn('/node/123'); $path_current->getPath()->willReturn('/node/123');
\Drupal::getContainer()->set('path.current', $path_current->reveal()); \Drupal::getContainer()->set('path.current', $path_current->reveal());
/** @var \Drupal\Core\Routing\RouteMatchInterface $route_matcher */
$route_matcher = $this->prophesize(RouteMatchInterface::class); $exception = $this->prophesize(HttpExceptionInterface::class);
$route_matcher->getRouteName()->willReturn($route); $exception->getStatusCode()->willReturn($httpCode);
\Drupal::getContainer()->set('current_route_match', $route_matcher->reveal()); \Drupal::requestStack()->getCurrentRequest()->attributes->set('exception', $exception->reveal());
$suggestions = \Drupal::moduleHandler()->invokeAll('theme_suggestions_page', [[]]); $suggestions = \Drupal::moduleHandler()->invokeAll('theme_suggestions_page', [[]]);
$this->assertSame([ $this->assertSame([