我有一个Controller操作(Controller通过JMSDiExtraBundle将$this->securityContext
设置为$this->get('security.context')
:
$user = $this->securityContext->getToken()->getUser();
$groupRepo = $this->getDoctrine()->getRepository('KekRozsakFrontBundle:Group');
if ($this->securityContext->isGranted('ROLE_ADMIN') === false) {
$myGroups = $groupRepo->findByLeader($user);
} else {
$myGroups = $groupRepo->findAll();
}
当我登录dev
环境并检查分析器时,我可以看到我已授予ROLE_ADMIN
角色,但我仍然可以获得已过滤的分组列表。
我在Controller和Symfony的RoleVoter.php
中添加了一些调试代码。我的控制器中的令牌($this->securityContext->getToken()
)和RoleVoter.php
中的令牌的字符串表示相同,但当我使用$token->getRoles()
时,我得到两个不同的数组。
我的用户和角色通过用户和角色实体存储在数据库中。这是我发现的错误还是我做错了什么?
答案 0 :(得分:4)
终于明白了。一分钟前,一个朦胧的想法让我大吃一惊。问题是由我自己的RoleHierarchyInterface
实施引起的。我最初的想法是复制Symfony自己的,但是从ORM而不是security.yml
加载它。但正因为如此,我必须完全重写buildRoleMap()
函数。差异如下:
private function buildRoleMap()
{
$this->map = array();
$roles = $this->roleRepo->findAll();
foreach ($roles as $mainRole) {
$main = $mainRole->getRole();
- $this->map[$main] = array();
+ $this->map[$main] = array($main);
foreach ($mainRole->getInheritedRoles() as $childRole) {
$this->map[$main][] = $childRole->getRole();
// TODO: This is one-level only. Get as deep as possible.
// BEWARE OF RECURSIVE NESTING!
foreach ($childRole->getInheritedRoles() as $grandchildRole) {
$this->map[$main][] = $grandchildRole->getRole();
}
}
}
}
答案 1 :(得分:0)
此案例 - 角色已设置并显示在Symfony的分析器中,但isGranted
返回false - 当角色名称不以前缀 ROLE _ 开头时可能会发生。
错误的角色名称:USER_TYPE_ADMIN
更正角色名称:ROLE_USER_TYPE_ADMIN