Skip to content

Commit 08a218c

Browse files
committed
bug #34218 [Security] Fix SwitchUserToken wrongly deauthenticated (chalasr)
This PR was merged into the 4.4 branch. Discussion ---------- [Security] Fix SwitchUserToken wrongly deauthenticated | Q | A | ------------- | --- | Branch? | 4.4 | Bug fix? | yes | New feature? | no | Deprecations? | no | Tickets | Fix #34202 | License | MIT | Doc PR | - Commits ------- e47b31c [Security] Fix SwitchUserToken wrongly deauthenticated
2 parents 0c784d2 + e47b31c commit 08a218c

File tree

2 files changed

+40
-2
lines changed

2 files changed

+40
-2
lines changed

src/Symfony/Component/Security/Core/Authentication/Token/AbstractToken.php

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -318,9 +318,12 @@ private function hasUserChanged(UserInterface $user): bool
318318
}
319319

320320
$userRoles = array_map('strval', (array) $user->getRoles());
321-
$rolesChanged = \count($userRoles) !== \count($this->getRoleNames()) || \count($userRoles) !== \count(array_intersect($userRoles, $this->getRoleNames()));
322321

323-
if ($rolesChanged) {
322+
if ($this instanceof SwitchUserToken) {
323+
$userRoles[] = 'ROLE_PREVIOUS_ADMIN';
324+
}
325+
326+
if (\count($userRoles) !== \count($this->getRoleNames()) || \count($userRoles) !== \count(array_intersect($userRoles, $this->getRoleNames()))) {
324327
return true;
325328
}
326329

src/Symfony/Component/Security/Core/Tests/Authentication/Token/SwitchUserTokenTest.php

Lines changed: 35 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,7 @@
1414
use PHPUnit\Framework\TestCase;
1515
use Symfony\Component\Security\Core\Authentication\Token\SwitchUserToken;
1616
use Symfony\Component\Security\Core\Authentication\Token\UsernamePasswordToken;
17+
use Symfony\Component\Security\Core\User\UserInterface;
1718

1819
class SwitchUserTokenTest extends TestCase
1920
{
@@ -38,4 +39,38 @@ public function testSerialize()
3839
$this->assertSame('provider-key', $unserializedOriginalToken->getProviderKey());
3940
$this->assertEquals(['ROLE_ADMIN', 'ROLE_ALLOWED_TO_SWITCH'], $unserializedOriginalToken->getRoleNames());
4041
}
42+
43+
public function testSetUserDoesNotDeauthenticate()
44+
{
45+
$impersonated = new class() implements UserInterface {
46+
public function getUsername()
47+
{
48+
return 'impersonated';
49+
}
50+
51+
public function getPassword()
52+
{
53+
return null;
54+
}
55+
56+
public function eraseCredentials()
57+
{
58+
}
59+
60+
public function getRoles()
61+
{
62+
return ['ROLE_USER'];
63+
}
64+
65+
public function getSalt()
66+
{
67+
return null;
68+
}
69+
};
70+
71+
$originalToken = new UsernamePasswordToken('impersonator', 'foo', 'provider-key', ['ROLE_ADMIN', 'ROLE_ALLOWED_TO_SWITCH']);
72+
$token = new SwitchUserToken($impersonated, 'bar', 'provider-key', ['ROLE_USER', 'ROLE_PREVIOUS_ADMIN'], $originalToken);
73+
$token->setUser($impersonated);
74+
$this->assertTrue($token->isAuthenticated());
75+
}
4176
}

0 commit comments

Comments
 (0)
pFad - Phonifier reborn

Pfad - The Proxy pFad of © 2024 Garber Painting. All rights reserved.

Note: This service is not intended for secure transactions such as banking, social media, email, or purchasing. Use at your own risk. We assume no liability whatsoever for broken pages.


Alternative Proxies:

Alternative Proxy

pFad Proxy

pFad v3 Proxy

pFad v4 Proxy