-
-
Notifications
You must be signed in to change notification settings - Fork 9.6k
Core User class returning roles as strings instead of Role objects #13037
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Comments
hi, where in your code are you calling getRoles()? |
As in stack trace, I'm not calling it:
EDIT: Anyway, it doesn't even matter, the DIC code created in the security extension seems wrong or I am missing something? |
I would exclude code is wrong, but.. can you explain more your setup please?
|
I don't have the source right now but I can give some copy-paste from Security component The extension code: $definition = $container->setDefinition($id, new DefinitionDecorator('security.user.provider.in_memory'));
foreach ($config['users'] as $username => $user) {
$userId = $id.'_'.$username;
$container
->setDefinition($userId, new DefinitionDecorator('security.user.provider.in_memory.user'))
->setArguments(array($username, (string) $user['password'], $user['roles']))
;
$definition->addMethodCall('createUser', array(new Reference($userId)));
} Core User class defined:
constructor just setts that array of strings while the interface requires array of I will try to create a test for that but from the code it's obvious that it's a bug, correct me if I'm wrong. |
Please post a copy of your AdminAccessVoter. It looks like that class is calling something on Line 65 that's invoking the RoleHierarchy. The RoleHierarchy object stores the hierarchy as all role strings, but expects the $roles array argument via ->getReachableRoles($roles) to all be RoleInterface objects, which they should be if that list is coming from the Security Token.
When each Voter goes to make a voting decision in its vote() method, it has arguments of the Security Token, an object being voted on and a list of attributes being voted on. If a Voter needs the list of roles for the current user, it should only use Token->getRoles(), which returns an array of objects implementing RoleInterface. So how do those RoleInterface ( When a Token is created (at least if it extends AbstractToken), it is supplied the User object. The User->getRoles() list is iterated, each converted into RoleInterface objects then stored with the Token, which is then stored in the TokenStorage (previously SecurityContext < 2.6). |
It's quite simple: protected function isGranted($attribute, $object, $user = null)
{
$decision = self::ACCESS_ABSTAIN;
if ($user instanceof UserInterface) {
$roles = $this->roleHierarchy->getReachableRoles($user->getRoles());
foreach ($roles as $role) {
if ($role->getRole() === Role::ROLE_ADMIN) {
$decision = self::ACCESS_GRANTED;
break;
}
}
}
return $decision;
} Still I don't understand why created |
What I've found in documentation is:
So the issue seems to be the docblock of |
IMO it would be nice to create some TODO to unify access to roles across the codebase, as everywhere we require to use |
@turneliusz have a look at #11742 it's on the list
|
The user is allowed to return strings since the very beginning of Symfony actually. This is a mistake in the phpdoc. |
When executing this piece of code:
I get the following error: "Error: Call to a member function getRole() on string". Because Symfony is treating strings as role objects on Symfony/Component/Security/Core/Role/RoleHierarchy.php.
Shouldn't the code be changed to something like
|
This PR was merged into the 2.3 branch. Discussion ---------- Fixed the phpDoc of UserInterface | Q | A | ------------- | --- | Bug fix? | yes | New feature? | no | BC breaks? | no | Deprecations? | no | Tests pass? | yes | Fixed tickets | #13037 | License | MIT | Doc PR | - #13037 is the original issue ... which was tried to be fixed in #13146 ... which was closed without merging it. Commits ------- 8e2a33e Fixed the phpDoc of UserInterface
Hey, this commit does not solve the issue as role objects are still being treated as strings in the RoleHierarchy.php file. I've implemented the patch on my side (the phpDoc change) and the "Error: Call to a member function getRole() on string" persists. |
@CMatias Can you please show the complete stack trace of that error and a way to reproduce your issue? |
@CMatias Closing here as I now understand your issue which is related to how you use the |
This issue stood with us for a long time. As we upgraded to 2.8 the new way of voting with decisionManager no longer required us to do that fix. Sorry and thanks for the help. |
I'm using Symfony 2.6
for that the container looks like:
which is triggering an exception Call to a member function getRole() on a non-object:
as Core User code looks like:
UserInterface::getRoles()
defines:Am I doing something wrong or it's a bug?
The text was updated successfully, but these errors were encountered: