在 php 应用程序中实现基于角色的访问控制


Implementing Roles based access control in php application

我一直在为我的大学开发一个PHP应用程序,该应用程序需要基于角色的访问控制。我遵循的方法是为每个角色创建一个单独的MySQL用户。因此,每个角色都有一个单独的数据库用户。这些数据库用户中的每一个都对角色所需的最小表集具有特权。

现在,我的问题是这是否是处理基于角色的应用程序的正确方法。我之所以产生这种怀疑,是因为现在是时候让系统上线(使用 GoDaddy 托管)时,我发现他们不允许创建具有表特定权限的用户。事实上,他们甚至不允许直接通过SQL脚本创建用户(系统上的角色创建涉及通过执行SQL命令的php脚本创建用户)。

因此,我现在在想我的方法是否实际上是正确的方法。实现这种基于角色的系统的标准方法是什么?

这是我的第一个现场项目,所以我在实际交付一个真正的项目方面没有太多经验。

除非您不是主机托管商,否则您可能不希望通过脚本动态创建数据库用户。想想吧:

数据库用户是与您的应用程序交互而不是与最终用户交互的组件。

因此,请坚持为您的应用程序使用一个数据库,并使用专用表来构建您的 ACL。您的数据库架构可能如下所示:

users( id:pk, name )
roles( id:pk, name )
permissions( id:pk, key, description )
permission_role( permission_id:fk, role_id:fk )
role_user( role_id:fk, user_id:fk )

你在这里基本上有三件事:

  • 用户:没什么特别的。只是一个可以通过其 id 唯一定义的用户
  • 权限
  • :基本上只是一个密钥存储,将在脚本中查询以检查权限
  • 角色:用户和权限之间的粘合剂。用户所属的角色总和及其权限将定义允许用户执行的操作和不可以执行的操作的全部内容。

这是基本设置。其他表只是将各个部分连接在一起的帮助表。

您的代码处理其余部分。 设置一个(或更好的)类来完成繁重的工作。然后将 ACL 的实例传递给 User 类(当然也可以使用其他实现。见帖子底部)。

<?php 
class Acl implements AclInterface {
    public function hasPermissionTo( $action )
    {
        // Query DB and check if a record exists
        // in the role_user table where the 
        // user_id matches with the current user
        // and join the role_id with `roles` and then
        // with `permission_role` to see if the user
        // is permitted to perform a certain action
    }
}
class User {
    protected $acl;
    public function __construct( AclInterface $acl )
    {
        $this->acl = $acl;
    }
    public function hasPermissionTo( $action )
    {
        return $this->acl->hasPermissionTo( $action );
    }
}

你应该得到基本的概念。实际实施取决于您。您可能需要考虑的事项:

  • 您希望 ACL 成为User的一部分还是独立组件?
  • 您希望如何将当前用户传递给 ACL?是要将当前用户的实例传递给 ACL,还是仅将用户 ID 传递给 ACL?

这些问题取决于你喜欢什么和你的架构。祝您编码愉快!