Skip to content

Commit 08832fe

Browse files
committed
fix(security): allow multiple Security attributes when applicable
1 parent e532750 commit 08832fe

File tree

2 files changed

+47
-1
lines changed

2 files changed

+47
-1
lines changed

src/Symfony/Component/Security/Core/Authorization/TraceableAccessDecisionManager.php

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -54,7 +54,7 @@ public function decide(TokenInterface $token, array $attributes, mixed $object =
5454
$this->accessDecisionStack[] = $accessDecision;
5555

5656
try {
57-
return $accessDecision->isGranted = $this->manager->decide($token, $attributes, $object, $accessDecision);
57+
return $accessDecision->isGranted = $this->manager->decide($token, $attributes, $object, $accessDecision, $allowMultipleAttributes);
5858
} finally {
5959
$this->strategy = $accessDecision->strategy;
6060
$currentLog = array_pop($this->currentLog);

src/Symfony/Component/Security/Core/Tests/Authorization/TraceableAccessDecisionManagerTest.php

Lines changed: 46 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,12 +11,14 @@
1111

1212
namespace Symfony\Component\Security\Core\Tests\Authorization;
1313

14+
use PHPUnit\Framework\MockObject\MockObject;
1415
use PHPUnit\Framework\TestCase;
1516
use Symfony\Component\Security\Core\Authentication\Token\TokenInterface;
1617
use Symfony\Component\Security\Core\Authorization\AccessDecisionManager;
1718
use Symfony\Component\Security\Core\Authorization\AccessDecisionManagerInterface;
1819
use Symfony\Component\Security\Core\Authorization\TraceableAccessDecisionManager;
1920
use Symfony\Component\Security\Core\Authorization\Voter\VoterInterface;
21+
use Symfony\Component\Security\Core\Exception\InvalidArgumentException;
2022
use Symfony\Component\Security\Core\Tests\Fixtures\DummyVoter;
2123

2224
class TraceableAccessDecisionManagerTest extends TestCase
@@ -276,4 +278,48 @@ public function testCustomAccessDecisionManagerReturnsEmptyStrategy()
276278

277279
$this->assertEquals('-', $adm->getStrategy());
278280
}
281+
282+
public function testThrowsExceptionWhenMultipleAttributesNotAllowed()
283+
{
284+
$accessDecisionManager = new AccessDecisionManager();
285+
$traceableAccessDecisionManager = new TraceableAccessDecisionManager($accessDecisionManager);
286+
/** @var TokenInterface&MockObject $tokenMock */
287+
$tokenMock = $this->createMock(TokenInterface::class);
288+
289+
$this->expectException(InvalidArgumentException::class);
290+
$traceableAccessDecisionManager->decide($tokenMock, ['attr1', 'attr2']);
291+
}
292+
293+
/**
294+
* @dataProvider allowMultipleAttributesProvider
295+
*/
296+
public function testAllowMultipleAttributes(array $attributes, bool $allowMultipleAttributes)
297+
{
298+
$accessDecisionManager = new AccessDecisionManager();
299+
$traceableAccessDecisionManager = new TraceableAccessDecisionManager($accessDecisionManager);
300+
/** @var TokenInterface&MockObject $tokenMock */
301+
$tokenMock = $this->createMock(TokenInterface::class);
302+
303+
$isGranted = $traceableAccessDecisionManager->decide($tokenMock, $attributes, null, null, $allowMultipleAttributes);
304+
305+
$this->assertFalse($isGranted);
306+
}
307+
308+
public function allowMultipleAttributesProvider(): \Generator
309+
{
310+
yield [
311+
['attr1'],
312+
false,
313+
];
314+
315+
yield [
316+
['attr1'],
317+
true,
318+
];
319+
320+
yield [
321+
['attr1', 'attr2', 'attr3'],
322+
true,
323+
];
324+
}
279325
}

0 commit comments

Comments
 (0)