Skip to content

Navigation Menu

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Appearance settings

Commit f527790

Browse filesBrowse files
author
Hugo Hamon
committed
[Security] remove support for defining voters that don't implement the VoterInterface interface.
1 parent 8483564 commit f527790
Copy full SHA for f527790

File tree

8 files changed

+15
-129
lines changed
Filter options

8 files changed

+15
-129
lines changed

‎UPGRADE-4.0.md

Copy file name to clipboardExpand all lines: UPGRADE-4.0.md
+2Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -455,6 +455,8 @@ Security
455455
* The `AccessDecisionManager::setVoters()` method has been removed. Pass the
456456
voters to the constructor instead.
457457

458+
* Support for defining voters that don't implement the `VoterInterface` has been removed.
459+
458460
SecurityBundle
459461
--------------
460462

‎src/Symfony/Bundle/SecurityBundle/CHANGELOG.md

Copy file name to clipboardExpand all lines: src/Symfony/Bundle/SecurityBundle/CHANGELOG.md
+1Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@ CHANGELOG
88
* made `FirewallMap::$container` and `::$map` private
99
* made the first `UserPasswordEncoderCommand::_construct()` argument mandatory
1010
* `UserPasswordEncoderCommand` does not extend `ContainerAwareCommand` anymore
11+
* removed support for voters that don't implement the `VoterInterface`
1112

1213
3.4.0
1314
-----

‎src/Symfony/Bundle/SecurityBundle/DependencyInjection/Compiler/AddSecurityVotersPass.php

Copy file name to clipboardExpand all lines: src/Symfony/Bundle/SecurityBundle/DependencyInjection/Compiler/AddSecurityVotersPass.php
+2-7Lines changed: 2 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -38,19 +38,14 @@ public function process(ContainerBuilder $container)
3838

3939
$voters = $this->findAndSortTaggedServices('security.voter', $container);
4040
if (!$voters) {
41-
throw new LogicException('No security voters found. You need to tag at least one with "security.voter"');
41+
throw new LogicException('No security voters found. You need to tag at least one with "security.voter".');
4242
}
4343

4444
foreach ($voters as $voter) {
4545
$class = $container->getDefinition((string) $voter)->getClass();
4646

4747
if (!is_a($class, VoterInterface::class, true)) {
48-
@trigger_error(sprintf('Using a security.voter tag on a class without implementing the %1$s is deprecated as of 3.4 and will be removed in 4.0. Implement the %1$s instead.', VoterInterface::class), E_USER_DEPRECATED);
49-
}
50-
51-
if (!method_exists($class, 'vote')) {
52-
// in case the vote method is completely missing, to prevent exceptions when voting
53-
throw new LogicException(sprintf('%s should implement the %s interface when used as voter.', $class, VoterInterface::class));
48+
throw new LogicException(sprintf('%s must implement the %s when used as a voter.', $class, VoterInterface::class));
5449
}
5550
}
5651

‎src/Symfony/Bundle/SecurityBundle/Tests/DependencyInjection/Compiler/AddSecurityVotersPassTest.php

Copy file name to clipboardExpand all lines: src/Symfony/Bundle/SecurityBundle/Tests/DependencyInjection/Compiler/AddSecurityVotersPassTest.php
+4-38Lines changed: 4 additions & 38 deletions
Original file line numberDiff line numberDiff line change
@@ -14,16 +14,15 @@
1414
use PHPUnit\Framework\TestCase;
1515
use Symfony\Bundle\SecurityBundle\DependencyInjection\Compiler\AddSecurityVotersPass;
1616
use Symfony\Component\DependencyInjection\ContainerBuilder;
17-
use Symfony\Component\DependencyInjection\Exception\LogicException;
1817
use Symfony\Component\DependencyInjection\Reference;
1918
use Symfony\Component\Security\Core\Authorization\AccessDecisionManager;
2019
use Symfony\Component\Security\Core\Authorization\Voter\Voter;
21-
use Symfony\Component\Security\Core\Tests\Authorization\Stub\VoterWithoutInterface;
2220

2321
class AddSecurityVotersPassTest extends TestCase
2422
{
2523
/**
2624
* @expectedException \Symfony\Component\DependencyInjection\Exception\LogicException
25+
* @expectedExceptionMessage No security voters found. You need to tag at least one with "security.voter".
2726
*/
2827
public function testNoVoters()
2928
{
@@ -71,8 +70,8 @@ public function testThatSecurityVotersAreProcessedInPriorityOrder()
7170
}
7271

7372
/**
74-
* @group legacy
75-
* @expectedDeprecation Using a security.voter tag on a class without implementing the Symfony\Component\Security\Core\Authorization\Voter\VoterInterface is deprecated as of 3.4 and will be removed in 4.0. Implement the Symfony\Component\Security\Core\Authorization\Voter\VoterInterface instead.
73+
* @expectedException \Symfony\Component\DependencyInjection\Exception\LogicException
74+
* @expectedExceptionMessage stdClass must implement the Symfony\Component\Security\Core\Authorization\Voter\VoterInterface when used as a voter.
7675
*/
7776
public function testVoterMissingInterface()
7877
{
@@ -82,40 +81,7 @@ public function testVoterMissingInterface()
8281
->addArgument(array())
8382
;
8483
$container
85-
->register('without_interface', VoterWithoutInterface::class)
86-
->addTag('security.voter')
87-
;
88-
$compilerPass = new AddSecurityVotersPass();
89-
$compilerPass->process($container);
90-
91-
$argument = $container->getDefinition('security.access.decision_manager')->getArgument(0);
92-
$refs = $argument->getValues();
93-
$this->assertEquals(new Reference('without_interface'), $refs[0]);
94-
$this->assertCount(1, $refs);
95-
}
96-
97-
/**
98-
* @group legacy
99-
*/
100-
public function testVoterMissingInterfaceAndMethod()
101-
{
102-
$exception = LogicException::class;
103-
$message = 'stdClass should implement the Symfony\Component\Security\Core\Authorization\Voter\VoterInterface interface when used as voter.';
104-
105-
if (method_exists($this, 'expectException')) {
106-
$this->expectException($exception);
107-
$this->expectExceptionMessage($message);
108-
} else {
109-
$this->setExpectedException($exception, $message);
110-
}
111-
112-
$container = new ContainerBuilder();
113-
$container
114-
->register('security.access.decision_manager', AccessDecisionManager::class)
115-
->addArgument(array())
116-
;
117-
$container
118-
->register('without_method', 'stdClass')
84+
->register('without_interface', 'stdClass')
11985
->addTag('security.voter')
12086
;
12187
$compilerPass = new AddSecurityVotersPass();

‎src/Symfony/Component/Security/CHANGELOG.md

Copy file name to clipboardExpand all lines: src/Symfony/Component/Security/CHANGELOG.md
+2-1Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,8 @@ CHANGELOG
88
You should implement this method yourself in your concrete authenticator.
99
* removed the `AccessDecisionManager::setVoters()` method
1010
* removed the `RoleInterface`
11-
* added a sixth `string $context` argument to`LogoutUrlGenerator::registerListener()`
11+
* removed support for voters that don't implement the `VoterInterface`
12+
* added a sixth `string $context` argument to `LogoutUrlGenerator::registerListener()`
1213

1314
3.4.0
1415
-----

‎src/Symfony/Component/Security/Core/Authorization/AccessDecisionManager.php

Copy file name to clipboardExpand all lines: src/Symfony/Component/Security/Core/Authorization/AccessDecisionManager.php
+4-28Lines changed: 4 additions & 28 deletions
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,6 @@
1313

1414
use Symfony\Component\Security\Core\Authorization\Voter\VoterInterface;
1515
use Symfony\Component\Security\Core\Authentication\Token\TokenInterface;
16-
use Symfony\Component\Security\Core\Exception\LogicException;
1716

1817
/**
1918
* AccessDecisionManager is the base class for all access decision managers
@@ -33,7 +32,7 @@ class AccessDecisionManager implements AccessDecisionManagerInterface
3332
private $allowIfEqualGrantedDeniedDecisions;
3433

3534
/**
36-
* @param iterable|VoterInterface[] $voters An iterator of VoterInterface instances
35+
* @param iterable|VoterInterface[] $voters An array or an iterator of VoterInterface instances
3736
* @param string $strategy The vote strategy
3837
* @param bool $allowIfAllAbstainDecisions Whether to grant access if all voters abstained or not
3938
* @param bool $allowIfEqualGrantedDeniedDecisions Whether to grant access if result are equals
@@ -71,7 +70,7 @@ private function decideAffirmative(TokenInterface $token, array $attributes, $ob
7170
{
7271
$deny = 0;
7372
foreach ($this->voters as $voter) {
74-
$result = $this->vote($voter, $token, $object, $attributes);
73+
$result = $voter->vote($token, $object, $attributes);
7574
switch ($result) {
7675
case VoterInterface::ACCESS_GRANTED:
7776
return true;
@@ -112,7 +111,7 @@ private function decideConsensus(TokenInterface $token, array $attributes, $obje
112111
$grant = 0;
113112
$deny = 0;
114113
foreach ($this->voters as $voter) {
115-
$result = $this->vote($voter, $token, $object, $attributes);
114+
$result = $voter->vote($token, $object, $attributes);
116115

117116
switch ($result) {
118117
case VoterInterface::ACCESS_GRANTED:
@@ -153,7 +152,7 @@ private function decideUnanimous(TokenInterface $token, array $attributes, $obje
153152
$grant = 0;
154153
foreach ($this->voters as $voter) {
155154
foreach ($attributes as $attribute) {
156-
$result = $this->vote($voter, $token, $object, array($attribute));
155+
$result = $voter->vote($token, $object, array($attribute));
157156

158157
switch ($result) {
159158
case VoterInterface::ACCESS_GRANTED:
@@ -177,27 +176,4 @@ private function decideUnanimous(TokenInterface $token, array $attributes, $obje
177176

178177
return $this->allowIfAllAbstainDecisions;
179178
}
180-
181-
/**
182-
* TokenInterface vote proxy method.
183-
*
184-
* Acts as a BC layer when the VoterInterface is not implemented on the voter.
185-
*
186-
* @deprecated as of 3.4 and will be removed in 4.0. Call the voter directly as the instance will always be a VoterInterface
187-
*/
188-
private function vote($voter, TokenInterface $token, $subject, $attributes)
189-
{
190-
if ($voter instanceof VoterInterface) {
191-
return $voter->vote($token, $subject, $attributes);
192-
}
193-
194-
if (method_exists($voter, 'vote')) {
195-
@trigger_error(sprintf('Calling vote() on an voter without %1$s is deprecated as of 3.4 and will be removed in 4.0. Implement the %1$s on your voter.', VoterInterface::class), E_USER_DEPRECATED);
196-
197-
// making the assumption that the signature matches
198-
return $voter->vote($token, $subject, $attributes);
199-
}
200-
201-
throw new LogicException(sprintf('%s should implement the %s interface when used as voter.', get_class($voter), VoterInterface::class));
202-
}
203179
}

‎src/Symfony/Component/Security/Core/Tests/Authorization/AccessDecisionManagerTest.php

Copy file name to clipboardExpand all lines: src/Symfony/Component/Security/Core/Tests/Authorization/AccessDecisionManagerTest.php
-33Lines changed: 0 additions & 33 deletions
Original file line numberDiff line numberDiff line change
@@ -12,11 +12,8 @@
1212
namespace Symfony\Component\Security\Core\Tests\Authorization;
1313

1414
use PHPUnit\Framework\TestCase;
15-
use Symfony\Component\Security\Core\Authentication\Token\TokenInterface;
1615
use Symfony\Component\Security\Core\Authorization\AccessDecisionManager;
1716
use Symfony\Component\Security\Core\Authorization\Voter\VoterInterface;
18-
use Symfony\Component\Security\Core\Exception\LogicException;
19-
use Symfony\Component\Security\Core\Tests\Authorization\Stub\VoterWithoutInterface;
2017

2118
class AccessDecisionManagerTest extends TestCase
2219
{
@@ -141,34 +138,4 @@ protected function getVoter($vote)
141138

142139
return $voter;
143140
}
144-
145-
public function testVotingWrongTypeNoVoteMethod()
146-
{
147-
$exception = LogicException::class;
148-
$message = sprintf('stdClass should implement the %s interface when used as voter.', VoterInterface::class);
149-
150-
if (method_exists($this, 'expectException')) {
151-
$this->expectException($exception);
152-
$this->expectExceptionMessage($message);
153-
} else {
154-
$this->setExpectedException($exception, $message);
155-
}
156-
157-
$adm = new AccessDecisionManager(array(new \stdClass()));
158-
$token = $this->getMockBuilder(TokenInterface::class)->getMock();
159-
160-
$adm->decide($token, array('TEST'));
161-
}
162-
163-
/**
164-
* @group legacy
165-
* @expectedDeprecation Calling vote() on an voter without Symfony\Component\Security\Core\Authorization\Voter\VoterInterface is deprecated as of 3.4 and will be removed in 4.0. Implement the Symfony\Component\Security\Core\Authorization\Voter\VoterInterface on your voter.
166-
*/
167-
public function testVotingWrongTypeWithVote()
168-
{
169-
$adm = new AccessDecisionManager(array(new VoterWithoutInterface()));
170-
$token = $this->getMockBuilder(TokenInterface::class)->getMock();
171-
172-
$adm->decide($token, array('TEST'));
173-
}
174141
}

‎src/Symfony/Component/Security/Core/Tests/Authorization/Stub/VoterWithoutInterface.php

Copy file name to clipboardExpand all lines: src/Symfony/Component/Security/Core/Tests/Authorization/Stub/VoterWithoutInterface.php
-22Lines changed: 0 additions & 22 deletions
This file was deleted.

0 commit comments

Comments
0 (0)
Morty Proxy This is a proxified and sanitized view of the page, visit original site.