【问题标题】:Is it possible to have a session within a session?是否可以在会话中进行会话?
【发布时间】:2017-03-16 01:14:09
【问题描述】:

我的程序有 3 种用户类型。员工、人力资源和供应商。每当员工登录时,他/她只能访问该员工可用的页面。

 if( $usr->userLogin() ) {

    echo "Welcome";
     if($usr->user_type == "Vendor") {
       $_SESSION['vend']='set';
      header("Location:Vendor/vendorHome.php");
    }
    else if($usr->user_type == "HR"){
      $_SESSION['hr']='set';
    header("Location:HR/hrHome.php");
}
  else {
    $_SESSION['emp']='set';
    header("Location:Employee/home.php");
  }
}
else {
    echo "Incorrect Username, Password, or User Type. Please Try<a href='index.php'> Again</a>";

在每一页的顶部,我都有这段代码,根据它是否是 3 种类型之一而有所不同。

?php
session_start();
if(!isset($_SESSION['vend'])) #If session is not set, user isn't logged in.
                             #Redirect to Login Page
       {
           header("Location:../index.php");
       }
?>

在编写此应用程序时,这不是问题,直到我意识到如果我将另一个用户添加到任何类型,第二个用户就可以访问第一个用户的页面、信息和数据库中的所有内容。有没有办法根据用户声明第二个会话 ID?我将如何根据用户类型和个人用户本身限制每个用户可用的信息?这甚至可能吗?我不知道每种类型会有多少用户,但我知道会有超过 5 个用户。

**编辑:**感谢您的建议。我将与他们一起改进我的代码。我认为我没有正确解释我的问题。

假设我有 2 个员工类型为“Jack”和“Jill”的用户。 “Jack”浏览了应用程序并添加了一些只有他才能看到或能够编辑和注销的表单。当“吉尔”登录时,她不应该看到任何东西。事实并非如此。 'Jill' 登录,并且能够查看和编辑'Jack' 所能看到的所有内容。 “Jack”和“Jill”都不能访问任何与 HR 或 Vendor 相关的内容。这部分会话变量有效。

【问题讨论】:

  • 您究竟如何存储任何信息?如果您根据会话中的单个值(例如 id)从数据库中提取它,我认为没有问题。而且您的重定向不起作用,因为您在设置标题之前打印了一些东西。
  • 您的数据库是否没有将信息与用户 ID 关联起来?您甚至存储用户 ID 吗?这听起来像是您的应用程序中的设计错误。
  • 也许你应该重新考虑你的数据库结构,在你的情况下,用户类型可以被认为是一个等级,用户可以有多个等级。您可以在表中引入一个包含位标志值的新列。然后你可以做类似$usr-&gt;rank &amp; RANK_VENDOR等的事情。
  • 只是一个观察:永远不要忘记在标头位置之后终止脚本(退出)。
  • 感谢 cmets。 DmitryPonkin,重定向工作。 rogeriolino,我不知道我应该这样做。谢谢你让我知道。 Bytewave,User_ID 是一个无符号自增数。 Xorifelse 我不明白你在问什么。

标签: php mysql session pdo session-variables


【解决方案1】:

对所有用户使用相同的 SESSION 变量会怎样? 喜欢$_SESSION["user_type"]= X;。然后你就可以检查这个变量了。

【讨论】:

    【解决方案2】:

    我不知道是否可以进行多个会话,但您可以先阅读每个网页顶部的 user_type 字段,如果它是正确的用户,它可以保留,否则我应该被重定向到正确的主页。这样,如果用户 HR 键入“Vendor/vendorHome.php”,您在登录时的相同行为可以重定向用户并防止 vendorHome.php 被其他用户阅读。

    始终在 BD 中创建 user_type 字段来过滤您的用户,而不是在会话中。

    【讨论】:

      【解决方案3】:

      我会使用一个会话变量并将其值设置为用户的配置文件:

      if( $usr->userLogin() ) {
      
          echo "Welcome";
           if($usr->user_type == "Vendor") {
             $_SESSION['user_type']='vendor';
            header("Location:Vendor/vendorHome.php");
          }
          else if($usr->user_type == "HR"){
            $_SESSION['user_type']='hr';
          header("Location:HR/hrHome.php");
      }
        else {
          $_SESSION['user_type']='emp';
          header("Location:Employee/home.php");
        }
      }
      

      然后在每个页面中检查用户是否记录了他的用户类型/角色:

      session_start();
      if(!isset($_SESSION['user_type']) or $_SESSION['user_type'] !== 'vendor') // vendor, or hr ... 
             {
                 header("Location:../index.php");
             }
      

      【讨论】:

      • 我第一次尝试这样做时出现了一个问题,这就是我切换到这种方式的原因。
      【解决方案4】:

      你的逻辑结构使用变量的名字作为值,所以你可以做两件事:

      • 设置一个变量来保存所有这些值。

      • 将这些值变量放入一个数组中。

      第一个例子:

      设置:

      $_SESSION['usertype'] = "emp"; 
                            = "hr"; 
                            = "vend";
      

      检查:

      if($_SESSION['usertype'] !== "vend"){
                                          ...
      

      第二个例子:

      设置:

       $_SESSION['usertype']['emp'] = true/false; 
       $_SESSION['usertype']['hr'] = true/false; 
       $_SESSION['usertype']['vend'] = true/false;
      

      检查:

      if(!$_SESSION['usertype']['vend']){
                                         ...
      

      这样做的好处是您可以轻松地将成员设置为同时属于多个类别。


      • 在header 重定向之后,您应该始终使用die 或exit 停止脚本执行
      • 将值设置为布尔值(参见第二个示例)在逻辑上更容易且更具建设性,而不是每次都需要手动检查的手动字符串标志"set"。

      【讨论】:

        【解决方案5】:

        会话变量值已经是用户明智的。因此,如果您为一个用户设置会话变量,则只会为该用户设置它们。任何使用本网站的其他用户都不能拥有其他用户的价值。

        您可能需要在会话中保存用户的 ID 以及您已经保存的用户类型。我还建议将类型保存在一个会话变量中。

        $_SESSION['user'] = // user's id from your db
        $_SESSION['usertype'] = $usr->user_type;
        

        然后简单的在页面顶部包含相同的功能如下

        function validateUser($type) {
            if(empty($_SESSION['usertype']) || $_SESSION['usertype'] != $type)
               header("Location:../index.php");
        }
        

        并且还调用了每一页顶部的函数

        validateUser('vendor'); // and others for each page
        

        还要确保在每个页面的顶部包含具有 validateUser 函数的文件。大概是这样的。

        include('header.php');
        

        至于向不同的用户显示不同的数据,您将使用您在上面保存的会话的用户 ID 并将其(安全地)添加到查询中,以便仅向用户显示他们自己的数据。

        makeDbQuery('SELECT * FROM foo WHERE user_id = ?', [$_SESSION['user']])
        

        上面的查询机制是我想象的,你需要用你自己的来替换它。

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          相关资源
          最近更新 更多