Skip to content

Commit a12d705

Browse files
ENGCOM-6995: Fix #20309 - URL Rewrites redirect loop #26902
- Merge Pull Request #26902 from Bartlomiejsz/magento2:feature/fix_20309_url_rewrites_redirect_loop - Merged commits: 1. 684b951 2. 0fd6fd3
2 parents 0d3defe + 0fd6fd3 commit a12d705

File tree

7 files changed

+428
-306
lines changed

7 files changed

+428
-306
lines changed

app/code/Magento/UrlRewrite/Controller/Router.php

Lines changed: 42 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -3,15 +3,22 @@
33
* Copyright © Magento, Inc. All rights reserved.
44
* See COPYING.txt for license details.
55
*/
6+
declare(strict_types=1);
7+
68
namespace Magento\UrlRewrite\Controller;
79

10+
use Magento\Framework\App\Action\Forward;
811
use Magento\Framework\App\Action\Redirect;
12+
use Magento\Framework\App\ActionFactory;
913
use Magento\Framework\App\ActionInterface;
1014
use Magento\Framework\App\Request\Http as HttpRequest;
1115
use Magento\Framework\App\RequestInterface;
1216
use Magento\Framework\App\Response\Http as HttpResponse;
17+
use Magento\Framework\App\ResponseInterface;
18+
use Magento\Framework\App\RouterInterface;
1319
use Magento\Framework\Exception\NoSuchEntityException;
1420
use Magento\Framework\UrlInterface;
21+
use Magento\Store\Model\StoreManagerInterface;
1522
use Magento\UrlRewrite\Controller\Adminhtml\Url\Rewrite;
1623
use Magento\UrlRewrite\Model\UrlFinderInterface;
1724
use Magento\UrlRewrite\Service\V1\Data\UrlRewrite;
@@ -21,10 +28,10 @@
2128
*
2229
* @SuppressWarnings(PHPMD.CouplingBetweenObjects)
2330
*/
24-
class Router implements \Magento\Framework\App\RouterInterface
31+
class Router implements RouterInterface
2532
{
2633
/**
27-
* @var \Magento\Framework\App\ActionFactory
34+
* @var ActionFactory
2835
*/
2936
protected $actionFactory;
3037

@@ -34,7 +41,7 @@ class Router implements \Magento\Framework\App\RouterInterface
3441
protected $url;
3542

3643
/**
37-
* @var \Magento\Store\Model\StoreManagerInterface
44+
* @var StoreManagerInterface
3845
*/
3946
protected $storeManager;
4047

@@ -49,17 +56,17 @@ class Router implements \Magento\Framework\App\RouterInterface
4956
protected $urlFinder;
5057

5158
/**
52-
* @param \Magento\Framework\App\ActionFactory $actionFactory
59+
* @param ActionFactory $actionFactory
5360
* @param UrlInterface $url
54-
* @param \Magento\Store\Model\StoreManagerInterface $storeManager
55-
* @param \Magento\Framework\App\ResponseInterface $response
61+
* @param StoreManagerInterface $storeManager
62+
* @param ResponseInterface $response
5663
* @param UrlFinderInterface $urlFinder
5764
*/
5865
public function __construct(
59-
\Magento\Framework\App\ActionFactory $actionFactory,
66+
ActionFactory $actionFactory,
6067
UrlInterface $url,
61-
\Magento\Store\Model\StoreManagerInterface $storeManager,
62-
\Magento\Framework\App\ResponseInterface $response,
68+
StoreManagerInterface $storeManager,
69+
ResponseInterface $response,
6370
UrlFinderInterface $urlFinder
6471
) {
6572
$this->actionFactory = $actionFactory;
@@ -84,23 +91,41 @@ public function match(RequestInterface $request)
8491
);
8592

8693
if ($rewrite === null) {
87-
//No rewrite rule matching current URl found, continuing with
88-
//processing of this URL.
94+
// No rewrite rule matching current URl found, continuing with
95+
// processing of this URL.
8996
return null;
9097
}
98+
99+
$requestStringTrimmed = ltrim($request->getRequestString(), '/');
100+
$rewriteRequestPath = $rewrite->getRequestPath();
101+
$rewriteTargetPath = $rewrite->getTargetPath();
102+
$rewriteTargetPathTrimmed = ltrim($rewriteTargetPath, '/');
103+
104+
if (preg_replace('/\?.*/', '', $rewriteRequestPath) === preg_replace('/\?.*/', '', $rewriteTargetPath) &&
105+
(
106+
!$requestStringTrimmed ||
107+
!$rewriteTargetPathTrimmed ||
108+
strpos($requestStringTrimmed, $rewriteTargetPathTrimmed) === 0
109+
)
110+
) {
111+
// Request and target paths of rewrite found without query params are equal and current request string
112+
// starts with request target path, continuing with processing of this URL.
113+
return null;
114+
}
115+
91116
if ($rewrite->getRedirectType()) {
92-
//Rule requires the request to be redirected to another URL
93-
//and cannot be processed further.
117+
// Rule requires the request to be redirected to another URL
118+
// and cannot be processed further.
94119
return $this->processRedirect($request, $rewrite);
95120
}
96-
//Rule provides actual URL that can be processed by a controller.
121+
// Rule provides actual URL that can be processed by a controller.
97122
$request->setAlias(
98123
UrlInterface::REWRITE_REQUEST_PATH_ALIAS,
99-
$rewrite->getRequestPath()
124+
$rewriteRequestPath
100125
);
101-
$request->setPathInfo('/' . $rewrite->getTargetPath());
126+
$request->setPathInfo('/' . $rewriteTargetPath);
102127
return $this->actionFactory->create(
103-
\Magento\Framework\App\Action\Forward::class
128+
Forward::class
104129
);
105130
}
106131

app/code/Magento/UrlRewrite/Model/Storage/DbStorage.php

Lines changed: 9 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -138,17 +138,22 @@ private function extractMostRelevantUrlRewrite(string $requestPath, array $urlRe
138138
{
139139
$prioritizedUrlRewrites = [];
140140
foreach ($urlRewrites as $urlRewrite) {
141+
$urlRewriteRequestPath = $urlRewrite[UrlRewrite::REQUEST_PATH];
142+
$urlRewriteTargetPath = $urlRewrite[UrlRewrite::TARGET_PATH];
141143
switch (true) {
142-
case $urlRewrite[UrlRewrite::REQUEST_PATH] === $requestPath:
144+
case rtrim($urlRewriteRequestPath, '/') === rtrim($urlRewriteTargetPath, '/'):
145+
$priority = 99;
146+
break;
147+
case $urlRewriteRequestPath === $requestPath:
143148
$priority = 1;
144149
break;
145-
case $urlRewrite[UrlRewrite::REQUEST_PATH] === urldecode($requestPath):
150+
case $urlRewriteRequestPath === urldecode($requestPath):
146151
$priority = 2;
147152
break;
148-
case rtrim($urlRewrite[UrlRewrite::REQUEST_PATH], '/') === rtrim($requestPath, '/'):
153+
case rtrim($urlRewriteRequestPath, '/') === rtrim($requestPath, '/'):
149154
$priority = 3;
150155
break;
151-
case rtrim($urlRewrite[UrlRewrite::REQUEST_PATH], '/') === rtrim(urldecode($requestPath), '/'):
156+
case rtrim($urlRewriteRequestPath, '/') === rtrim(urldecode($requestPath), '/'):
152157
$priority = 4;
153158
break;
154159
default:

0 commit comments

Comments
 (0)