ZF2以管理员身份切换用户会话

时间:2015-05-05 07:29:48

标签: php authentication zend-framework2

我有一个应用程序,有两个用户角色(成员和管理员)。管理员可以查看所有用户的列表。现在,管理员应该有可能以另一个用户身份登录,以便像用户一样查看应用程序。

在不失去管理员状态的情况下切换用户的最佳解决方案是什么?

1 个答案:

答案 0 :(得分:0)

我为我的一些网络应用程序开发了这个解决方案,并且完美无瑕。让我们从假设一些事实开始:

  1. 您在数据库中保存用户密码哈希
  2. 用户需要输入他的电子邮件和密码才能登录。
  3. 我开发了一个AdminController,我可以从中看到列表中的每个用户,并且在该控制器内部有一个动作调用“loginasAction”,它接收来自URL的参数(阅读下面的代码):

    public function loginasAction() {
        $params = $this->params()->fromQuery();
        //this is the email of the user we want to log in as
        $user=$params['loginas'];
        //the current session data
        $userSession = new Container('appData');
        //a new session container built for the ocassion
        $adminSession = new Container('adminData');
        //save your admin user session as "originalUser" in the new session container,
        //because the original one is going to be cleared
        $adminSession->originalUser = $userSession->user;
    
        //retrieve the user data and asave it into the new session container too
        $userModel = new UserModel();
        $user= $userModel->getUser($user);
        $adminSession->clientAdmin = $clientAdmin;
        //redirect to my LogController Login action.
        return $this->redirect()->toRoute('login', array(), array('query' => array('loginas' => '')));
    }
    

    让我们看一下Login操作中的内容:

    //check if it comes form admin panel
    $params = $this->params()->fromQuery();
    if (isset($params['loginas'])) {
        $adminSession = new Container('adminData');
        if (isset($adminSession->userToLog)) {
            //let's use the destination user to log in as
            $user = $adminSession->userToLog;
            unset($adminSession->userToLog);
            //clear previous user session
            $session = new Container('appData');
            $session->getManager()->getStorage()->clear('appData');
            //log new user and redirect
            //userSession is a function that save the user data 
            //in my appData container session in the way I need it
            $this->userSession($user);
            //since I have loged in the user, we can redirect ourselves to home page
            return $this->redirect()->toRoute('home');
        }
    }
    

    现在,我们与 appData 容器会话与我们使用的管理员用户“管理员用户”进行了用户和 adminData 容器会话。

    我们如何回到我们的管理员用户?

    我的登录操作可以从名为“loguotas”的URL中读取参数,在这种情况下,我们将检查是否在 adminData 会话容器中保存了管理会话。在这种情况下,我们将清除当前的 appData 会话,并保存我们在流程开始时保存的 adminData 用户,即我们的管理员用户。

    //check if it is an admin user that want to return to view clients list
    if (isset($params['logoutas'])) {
        $adminSession = new Container('adminData');
        if (isset($adminSession->originalUser)) {
            $originalUser = $adminSession->originalUser;
            //clean sessions
            $session = new Container('appData');
            $session->getManager()->getStorage()->clear();
            //log in original user and redirect
            $this->userSession($originalUser);
            return $this->redirect()->toRoute('admin');
        }
    }
    

    这不容易也不复杂,但你需要坐下来思考几分钟。我希望这能为您提供良好的服务,或者至少为您的网络应用提供一个起点。