Movatterモバイル変換


[0]ホーム

URL:


Skip to content

Navigation Menu

Sign in
Appearance settings

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

Sign up
Appearance settings

Commit02904b3

Browse files
committed
minor#11653 Fixing docs about switch_user and custom voters (weaverryan)
This PR was merged into the 4.2 branch.Discussion----------Fixing docs about switch_user and custom voters@nicolas-grekas caught this. We need to use a custom attribute, instead of relying on `ROLE_ALLOWED_TO_SWITCH`. Otherwise, it's possible for the `RoleVoter` to say "Yes! This person *does* have `ROLE_ALLOWED_TO_SWITCH`"... but then your custom voter is never called, which would then say "Wait, no, they should not". A bit of an edge case - but this strategy gives the user 100% control, which is generally what we want with voters: only 1 voter should vote, not multiple.Was introduced originally in 4.1.Commits-------3f2e67d Fixing docs about switch_user and custom voters
2 parents31d14b3 +3f2e67d commit02904b3

File tree

1 file changed

+76
-25
lines changed

1 file changed

+76
-25
lines changed

‎security/impersonating_user.rst‎

Lines changed: 76 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -190,25 +190,81 @@ also adjust the query parameter name via the ``parameter`` setting:
190190
Limiting User Switching
191191
-----------------------
192192

193-
If you need more control over user switching, but don't require the complexity
194-
of a full ACL implementation, you can use a security voter. For example, you
195-
may want to allow employees to be able to impersonate a user with the
196-
``ROLE_CUSTOMER`` role without giving them the ability to impersonate a more
197-
elevated user such as an administrator.
193+
If you need more control over user switching, you can use a security voter. First,
194+
configure ``switch_user`` to check for some new, custom attribute. This can be
195+
anything, but *cannot* start with ``ROLE_`` (to enforce that only your voter will)
196+
be called:
198197

199-
Create the voter class::
198+
..configuration-block::
199+
200+
..code-block::yaml
201+
202+
# config/packages/security.yaml
203+
security:
204+
# ...
205+
206+
firewalls:
207+
main:
208+
# ...
209+
switch_user:{ role: CAN_SWITCH_USER }
210+
211+
..code-block::xml
212+
213+
<!-- config/packages/security.xml-->
214+
<?xml version="1.0" encoding="UTF-8"?>
215+
<srv:containerxmlns="http://symfony.com/schema/dic/security"
216+
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
217+
xmlns:srv="http://symfony.com/schema/dic/services"
218+
xsi:schemaLocation="http://symfony.com/schema/dic/services
219+
https://symfony.com/schema/dic/services/services-1.0.xsd">
220+
<config>
221+
<!-- ...-->
222+
223+
<firewallname="main">
224+
<!-- ...-->
225+
<switch-userrole="CAN_SWITCH_USER" />
226+
</firewall>
227+
</config>
228+
</srv:container>
229+
230+
..code-block::php
231+
232+
// config/packages/security.php
233+
$container->loadFromExtension('security', [
234+
// ...
235+
236+
'firewalls' => [
237+
'main'=> [
238+
// ...
239+
'switch_user' => [
240+
'role' => 'CAN_SWITCH_USER',
241+
],
242+
],
243+
],
244+
]);
245+
246+
Then, create a voter class that responds to this role and includes whatever custom
247+
logic you want::
200248

201249
namespace App\Security\Voter;
202250

203251
use Symfony\Component\Security\Core\Authentication\Token\TokenInterface;
204252
use Symfony\Component\Security\Core\Authorization\Voter\Voter;
253+
use Symfony\Component\Security\Core\Security;
205254
use Symfony\Component\Security\Core\User\UserInterface;
206255

207256
class SwitchToCustomerVoter extends Voter
208257
{
258+
private $security;
259+
260+
public function __construct(Security $security)
261+
{
262+
$this->security = $security;
263+
}
264+
209265
protected function supports($attribute, $subject)
210266
{
211-
return in_array($attribute, ['ROLE_ALLOWED_TO_SWITCH'])
267+
return in_array($attribute, ['CAN_SWITCH_USER'])
212268
&& $subject instanceof UserInterface;
213269
}
214270

@@ -220,34 +276,29 @@ Create the voter class::
220276
return false;
221277
}
222278

223-
if (in_array('ROLE_CUSTOMER', $subject->getRoles())
224-
&&$this->hasSwitchToCustomerRole($token)) {
279+
// you can still check for ROLE_ALLOWED_TO_SWITCH
280+
if ($this->security->isGranted('ROLE_ALLOWED_TO_SWITCH')) {
225281
return true;
226282
}
227283

228-
return false;
229-
}
284+
// check for any roles you want
285+
if ($this->security->isGranted('ROLE_TECH_SUPPORT')) {
286+
return true;
287+
}
230288

231-
private function hasSwitchToCustomerRole(TokenInterface $token)
232-
{
233-
foreach ($token->getRoles() as $role) {
234-
if ($role->getRole() === 'ROLE_SWITCH_TO_CUSTOMER') {
235-
return true;
236-
}
289+
/*
290+
* or use some custom data from your User object
291+
if ($user->isAllowedToSwitch()) {
292+
return true;
237293
}
294+
*/
238295

239296
return false;
240297
}
241298
}
242299

243-
To enable the new voter in the app, register it as a service and
244-
:doc:`tag it</service_container/tags>` with the ``security.voter``
245-
tag. If you're using the
246-
:ref:`default services.yaml configuration<service-container-services-load-example>`,
247-
this is already done for you, thanks to:ref:`autoconfiguration<services-autoconfigure>`.
248-
249-
Now a user who has the ``ROLE_SWITCH_TO_CUSTOMER`` role can switch to a user who
250-
has the ``ROLE_CUSTOMER`` role, but not other users.
300+
That's it! When switching users, your voter now has full control over whether or
301+
not this is allowed. If your voter isn't called, see:ref:`declaring-the-voter-as-a-service`.
251302

252303
Events
253304
------

0 commit comments

Comments
 (0)

[8]ページ先頭

©2009-2025 Movatter.jp