Skip to content

Commit 5d765c6

Browse files
committed
AC-904: PHP Error instead of 404/getting redirected when accessing any directory in <root>/catalog/product/compare/
1 parent 6ace296 commit 5d765c6

File tree

2 files changed

+29
-17
lines changed

2 files changed

+29
-17
lines changed

lib/internal/Magento/Framework/App/Router/ActionList.php

Lines changed: 17 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@
1212
use Magento\Framework\App\State;
1313
use Magento\Framework\App\Utility\ReflectionClassFactory;
1414
use Magento\Framework\Config\CacheInterface;
15+
use Magento\Framework\Exception\FileSystemException;
1516
use Magento\Framework\Module\Dir\Reader as ModuleReader;
1617
use Magento\Framework\Serialize\Serializer\Serialize;
1718
use Magento\Framework\Serialize\SerializerInterface;
@@ -61,7 +62,7 @@ class ActionList
6162
/**
6263
* @var ReflectionClassFactory|null
6364
*/
64-
private $classReflectionFactory;
65+
private $reflectionClassFactory;
6566

6667
/**
6768
* @param CacheInterface $cache
@@ -70,6 +71,10 @@ class ActionList
7071
* @param string $cacheKey
7172
* @param array $reservedWords
7273
* @param SerializerInterface|null $serializer
74+
* @param State|null $state
75+
* @param DirectoryList|null $directoryList
76+
* @param ReflectionClassFactory|null $reflectionClassFactory
77+
* @throws FileSystemException
7378
*/
7479
public function __construct(
7580
CacheInterface $cache,
@@ -78,16 +83,19 @@ public function __construct(
7883
$cacheKey = 'app_action_list',
7984
$reservedWords = [],
8085
SerializerInterface $serializer = null,
86+
State $state = null,
87+
DirectoryList $directoryList = null,
8188
ReflectionClassFactory $reflectionClassFactory = null
8289
) {
8390
$this->reservedWords = array_merge($reservedWords, $this->reservedWords);
8491
$this->actionInterface = $actionInterface;
85-
$objectManager = ObjectManager::getInstance();
86-
$this->serializer = $serializer ?: $objectManager->get(Serialize::class);
87-
$state = $objectManager->get(State::class);
92+
$this->serializer = $serializer ?: ObjectManager::getInstance()->get(Serialize::class);
93+
$state = $state ?: ObjectManager::getInstance()->get(State::class);
94+
$this->reflectionClassFactory = $reflectionClassFactory
95+
?: ObjectManager::getInstance()->get(ReflectionClassFactory::class);
8896

8997
if ($state->getMode() === State::MODE_PRODUCTION) {
90-
$directoryList = $objectManager->get(DirectoryList::class);
98+
$directoryList = $directoryList ?: ObjectManager::getInstance()->get(DirectoryList::class);
9199
$file = $directoryList->getPath(DirectoryList::GENERATED_METADATA)
92100
. '/' . $cacheKey . '.' . 'php';
93101

@@ -105,8 +113,6 @@ public function __construct(
105113
$this->actions = $this->serializer->unserialize($data);
106114
}
107115
}
108-
$this->classReflectionFactory = $reflectionClassFactory ?:
109-
ObjectManager::getInstance()->get(ReflectionClassFactory::class);
110116
}
111117

112118
/**
@@ -119,7 +125,7 @@ public function __construct(
119125
* @return null|string
120126
* @throws ReflectionException
121127
*/
122-
public function get($module, $area, $namespace, $action, $reflectionClass = null)
128+
public function get($module, $area, $namespace, $action)
123129
{
124130
if ($area) {
125131
$area = '\\' . $area;
@@ -139,7 +145,7 @@ public function get($module, $area, $namespace, $action, $reflectionClass = null
139145
)
140146
);
141147
try {
142-
if ($this->validateActionClass($fullPath, $reflectionClass)) {
148+
if ($this->validateActionClass($fullPath)) {
143149
return $this->actions[$fullPath];
144150
}
145151
} catch (ReflectionException $e) {
@@ -153,19 +159,16 @@ public function get($module, $area, $namespace, $action, $reflectionClass = null
153159
* Validate Action Class
154160
*
155161
* @param string $fullPath
156-
* @param ReflectionClass|null $reflectionClass
157162
* @return bool
158163
* @throws ReflectionException
159164
*/
160-
private function validateActionClass(string $fullPath, $reflectionClass): bool
165+
private function validateActionClass(string $fullPath): bool
161166
{
162167
if (isset($this->actions[$fullPath])) {
163168
if (!is_subclass_of($this->actions[$fullPath], $this->actionInterface)) {
164169
return false;
165170
}
166-
if (!$reflectionClass) {
167-
$reflectionClass = $this->classReflectionFactory->create($this->actions[$fullPath]);
168-
}
171+
$reflectionClass = $this->reflectionClassFactory->create($this->actions[$fullPath]);
169172
if ($reflectionClass->isInstantiable()) {
170173
return true;
171174
}

lib/internal/Magento/Framework/App/Test/Unit/Router/ActionListTest.php

Lines changed: 12 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,7 @@
99

1010
use Magento\Framework\App\ActionInterface;
1111
use Magento\Framework\App\Router\ActionList;
12+
use Magento\Framework\App\Utility\ReflectionClassFactory;
1213
use Magento\Framework\Config\CacheInterface;
1314
use Magento\Framework\Module\Dir\Reader;
1415
use Magento\Framework\Serialize\SerializerInterface;
@@ -49,15 +50,22 @@ class ActionListTest extends TestCase
4950
*/
5051
private $reflectionClass;
5152

53+
/**
54+
* @var ReflectionClassFactory|MockObject
55+
*/
56+
private $reflectionClassFactory;
57+
5258
protected function setUp(): void
5359
{
5460
$this->objectManager = new ObjectManager($this);
5561
$this->cacheMock = $this->getMockForAbstractClass(CacheInterface::class);
5662
$this->readerMock = $this->createMock(Reader::class);
5763
$this->serializerMock = $this->getMockForAbstractClass(SerializerInterface::class);
58-
$this->reflectionClass = $this->getMockBuilder(ReflectionClass::class)
64+
$this->reflectionClass = $this->createStub(ReflectionClass::class);
65+
$this->reflectionClassFactory = $this->getMockBuilder(ReflectionClassFactory::class)
5966
->disableOriginalConstructor()
6067
->getMock();
68+
$this->reflectionClassFactory->method('create')->willReturn($this->reflectionClass);
6169
}
6270

6371
public function testConstructActionsCached()
@@ -101,6 +109,7 @@ public function testConstructActionsNoCached()
101109
public function testGet($module, $area, $namespace, $action, $data, $isInstantiable, $expected)
102110
{
103111
$this->reflectionClass->method('isInstantiable')->willReturn($isInstantiable);
112+
104113
$this->cacheMock->expects($this->once())
105114
->method('load')
106115
->willReturn(false);
@@ -114,8 +123,7 @@ public function testGet($module, $area, $namespace, $action, $data, $isInstantia
114123
$module,
115124
$area,
116125
$namespace,
117-
$action,
118-
$this->reflectionClass
126+
$action
119127
));
120128
}
121129

@@ -198,6 +206,7 @@ private function createActionListInstance()
198206
'cache' => $this->cacheMock,
199207
'moduleReader' => $this->readerMock,
200208
'serializer' => $this->serializerMock,
209+
'reflectionClassFactory' => $this->reflectionClassFactory
201210
]
202211
);
203212
}

0 commit comments

Comments
 (0)