Symfony UserVoter 获取当前登录的用户代替 url 中的用户
Symfony UserVoter gets current logged in User in place of User in the url
在显示用户操作中,我想检查登录用户是否有权查看该用户。所以我创建了一个 UserVoter。
但是当我尝试使用注释将 url 中定义的用户传递给投票者时,我使用 $subject
和 $token->getUser()
获得了登录用户
如果我在操作中更改我的 var 名称,它工作正常($user -> $foo)。
你知道我怎样才能不更改我的 var 名称吗?
控制器:
/**
* Finds and displays a user entity.
*
* @Method("GET")
* @Route("/{id}/", name="authenticated_user_show", requirements={"id": "\d+"})
* @ParamConverter("user", class="AppBundle:User")
* @Security("is_granted('SHOW', user)")
*/
public function showAction(User $user)
{
选民:
protected function voteOnAttribute($attribute, $subject, TokenInterface $token)
{
$user = $token->getUser();
if (!$user instanceof User) {
// the user must be logged in; if not, deny access
return false;
}
if ($user->hasRole(User::ROLE_SUPER_ADMIN)) {
// if super admin, can do everything
return true;
}
// you know $subject is an User object, thanks to supports
/** @var User $userSubject */
$userSubject = $subject;
switch ($attribute) {
case self::SHOW:
return $this->canShow($userSubject, $user);
case self::EDIT:
return $this->canEdit($userSubject, $user);
}
throw new \LogicException('This code should not be reached!');
}
private function canShow(User $userSubject, User $user) : bool
{
if ($user->getClient() === $userSubject->getClient()) {
// if they are in the same client
return true;
}
return false;
}
private function canEdit(User $userSubject, User $user, TokenInterface $token) : bool
{
if (
$this->decisionManager->decide($token, [User::ROLE_ADMIN]) &&
$user->getClient() === $userSubject->getClient()
) {
// if the user and the admin belong to the same client
return true;
} elseif (
$this->decisionManager->decide($token, [User::ROLE_MANAGER]) &&
$this->userManager->hasEstablishmentInCommon($user, $userSubject)
) {
// if the user and the manager are linked to the same establishment
return true;
}
return false;
}
假设您不想查看已登录的用户,我会认为您可能与安全注释上下文中的变量发生冲突:
https://symfony.com/doc/current/bundles/SensioFrameworkExtraBundle/annotations/security.html
安全注释可以访问以下变量:
- token:当前安全令牌
- user:当前用户对象
- request:请求实例
- roles:用户角色;和所有要求
属性。
要修复,请更改用户名以避免冲突。
/**
* Finds and displays a user entity.
*
* @Method("GET")
* @Route("/{id}/", name="authenticated_user_show", requirements={"id":
"\d+"})
* @ParamConverter("showUser", class="AppBundle:User")
* @Security("is_granted('SHOW', showUser)")
*/
public function showAction(User $showUser)
在显示用户操作中,我想检查登录用户是否有权查看该用户。所以我创建了一个 UserVoter。
但是当我尝试使用注释将 url 中定义的用户传递给投票者时,我使用 $subject
和 $token->getUser()
如果我在操作中更改我的 var 名称,它工作正常($user -> $foo)。
你知道我怎样才能不更改我的 var 名称吗?
控制器:
/**
* Finds and displays a user entity.
*
* @Method("GET")
* @Route("/{id}/", name="authenticated_user_show", requirements={"id": "\d+"})
* @ParamConverter("user", class="AppBundle:User")
* @Security("is_granted('SHOW', user)")
*/
public function showAction(User $user)
{
选民:
protected function voteOnAttribute($attribute, $subject, TokenInterface $token)
{
$user = $token->getUser();
if (!$user instanceof User) {
// the user must be logged in; if not, deny access
return false;
}
if ($user->hasRole(User::ROLE_SUPER_ADMIN)) {
// if super admin, can do everything
return true;
}
// you know $subject is an User object, thanks to supports
/** @var User $userSubject */
$userSubject = $subject;
switch ($attribute) {
case self::SHOW:
return $this->canShow($userSubject, $user);
case self::EDIT:
return $this->canEdit($userSubject, $user);
}
throw new \LogicException('This code should not be reached!');
}
private function canShow(User $userSubject, User $user) : bool
{
if ($user->getClient() === $userSubject->getClient()) {
// if they are in the same client
return true;
}
return false;
}
private function canEdit(User $userSubject, User $user, TokenInterface $token) : bool
{
if (
$this->decisionManager->decide($token, [User::ROLE_ADMIN]) &&
$user->getClient() === $userSubject->getClient()
) {
// if the user and the admin belong to the same client
return true;
} elseif (
$this->decisionManager->decide($token, [User::ROLE_MANAGER]) &&
$this->userManager->hasEstablishmentInCommon($user, $userSubject)
) {
// if the user and the manager are linked to the same establishment
return true;
}
return false;
}
假设您不想查看已登录的用户,我会认为您可能与安全注释上下文中的变量发生冲突:
https://symfony.com/doc/current/bundles/SensioFrameworkExtraBundle/annotations/security.html 安全注释可以访问以下变量:
- token:当前安全令牌
- user:当前用户对象
- request:请求实例
- roles:用户角色;和所有要求 属性。
要修复,请更改用户名以避免冲突。
/**
* Finds and displays a user entity.
*
* @Method("GET")
* @Route("/{id}/", name="authenticated_user_show", requirements={"id":
"\d+"})
* @ParamConverter("showUser", class="AppBundle:User")
* @Security("is_granted('SHOW', showUser)")
*/
public function showAction(User $showUser)