首页 > 解决方案 > Symfony4 SwitchUserSubscriber 不区分两个用户

问题描述

在我的 S4 应用程序中,我需要超级用户的切换用户“功能”。我有一个带有自动完成功能的表单输入来搜索用户(仅适用于 ROLE_SUPERADMIN),但我想禁止用户冒充自己。我已经实现了这个事件订阅者,但是对于 $currentUser 和 $targetUser,它返回相同的身份(目标身份)。我哪里错了?

<?php

namespace App\EventSubscriber;

use Symfony\Component\EventDispatcher\EventSubscriberInterface;
use Symfony\Component\Security\Core\Exception\UnsupportedUserException;
use Symfony\Component\Security\Http\Event\SwitchUserEvent;

class SwitchUserSubscriber implements EventSubscriberInterface
{
    public function onSecuritySwitchUser(SwitchUserEvent $event)
    {
        $currentUser = $event->getToken()->getUser();
        $targetUser = $event->getTargetUser();

        if($currentUser->getUsername() == $targetUser->getUsername()){
            throw new UnsupportedUserException("You can't impersonate yourself");
        }
    }

    public static function getSubscribedEvents()
    {
        return [
           'security.switch_user' => 'onSecuritySwitchUser',
        ];
    }
}

有没有更好的方法来实现这一目标?

标签: phpsymfonysymfony4

解决方案


好的找到解决方案,阅读代码注释进行解释

namespace App\EventSubscriber;

use Symfony\Component\EventDispatcher\EventSubscriberInterface;
use Symfony\Component\Security\Core\Exception\UnsupportedUserException;
use Symfony\Component\Security\Http\Event\SwitchUserEvent;
use Symfony\Component\Security\Core\Role\SwitchUserRole;

class SwitchUserSubscriber implements EventSubscriberInterface
{
    /**
     * @param SwitchUserEvent $event
     */
    public function onSecuritySwitchUser(SwitchUserEvent $event)
    {

        // Current user initialized to null
        $currentUser = null;
        // Gets all the roles in switching phase
        $roles = $event->getToken()->getRoles();
        // Cycles between roles
        foreach($roles as $role) {
            // SwitchUserRole it's a role of the impersonating user
            // The if statement doesn't happen in switch exit
            if ($role instanceof SwitchUserRole) {
                // Recupera l'uente
                $currentUser = $role->getSource()->getUser();
            }
        }

        // Impersonated user
        $targetUser = $event->getTargetUser();
        // If you wann be yourself raises an exception
        if(null !== $currentUser && ($currentUser->getUsername() == $targetUser->getUsername())){
            throw new UnsupportedUserException("You can't impersnate yourself");
        }
    }

    public static function getSubscribedEvents()
    {
        return [
           'security.switch_user' => 'onSecuritySwitchUser',
        ];
    }
}

推荐阅读