处理管理系统用户和前端网站用户时如何处理用户权限?

时间:2011-09-21 09:10:23

标签: php web-applications authorization acl

任何人都可以推荐一个信息来源或工作示例,说明在与管理系统用户和网站用户同时处理时如何处理访问权限?

我们的代码目前有点像在线商店的大版本,有几名员工使用管理系统管理订单,以及使用该网站的任意数量的客户。管理系统围绕一个访问控制列表(如LiveUser)构建,但有一个相当大的“创可贴”,与一个“虚拟”用户一起担任所有网站用户(所有客户)的角色。

理想情况下,应用程序代码将使用can_place_order()之类的短语来确定用户是否可以执行任务。只要库存水平至少与订单数量一样多,并且他们已经对订单的价值进行支付,客户就可以下订单。只要具有'customer_services'角色,管理员用户就可以下订单。

理想情况下,我们希望扩展系统,以便我们可以让某些注册客户在没有足够库存或支付的情况下下订单,只需生成发票和延期交货。除了许多员工的角色之外,这至少还有两个客户“角色”......

  • 如何使用具有两个单独用户列表的相同权限系统?
  • 或者,如何将明显的两组用户合并为一个列表?

我们正在使用php& MySQL的应用程序,但欢迎任何其他语言模式。

1 个答案:

答案 0 :(得分:4)

我已经尝试了很多不同的权限方案,我只发现了一种让它们工作的方法,几乎​​在所有情况下都满足程序员和客户端。这是为了使它们部分地受数据驱动。

我最近的尝试是这样的:

  1. 每个用户都附加了一个权限对象。在我的情况下,在请求用户时自动创建。 (在我的情况下,不同部分的权限可能不同。因此可能允许用户为Y执行X但不允许执行Z.)
  2. 需要允许的每个页面,代码块或视图都包含一个检查权限对象的if语句。如果该权限也需要担心该部分,则当前相关部分ID将作为数组传入,返回一个新的bool数组以匹配。
  3. 接口不会直接向用户公开这个复杂的混乱,而是使用superadmin接口创建新的用户类型。这些类型带有将为该“类型”用户启用的权限集。不同类型的权限可能会重叠,因此管理员和编辑者都可以“编辑复制”或其他任何内容。
  4. 普通管理界面允许将各个用户设置为不同部分的不同用户类型。因此,一个用户可能是第2部分的管理员,第2,3,4和5部分的编辑器。它们也可以全局设置,它会重载未使用的部分(0)。
  5. 这有许多好处和一个缺点。一,缺点。因为这些密钥直接烘焙到代码中,所以只有superadmin(也称为开发人员)才能访问该界面的该部分。实际上,可能根本不需要接口,因为权限列表应该仅随代码而改变。这里真正的问题是,在运行代码之前,你不会知道标题有什么问题,因为语法会很好。现在,如果这是用C#编写的,这将是一个非常严重的问题。但几乎PHP中的所有东西都不是类型安全的,所以它实际上只是课程的标准。这些值也可以从配置文件加载,甚至可以加入到您构建用户类型的GUI中,尽管这似乎是错误的。

    您从中获得的是能够动态设置新权限类型。您可以相对轻松地重命名这些权限。 (由于系统只使用数字,标题仅用于捕获数字,因此可以在几个地方轻松更改。)并且代码使用起来非常简单。它看起来像这样:

    if($current_user->permissions->can("View Sales Records"))
    {
        //Code to view sales records
    }
    

    或者稍微复杂一点

    $sections = array(1,2,3,4); //Probably really a list of all sections in the system
    $section_permissions = $current_user->permissions->these($sections)->can("Edit Section");
    foreach($sections as $s)
    {
        if($section_permissions[$s])
        {
            // Code for maybe displaying a list of sections to edit or something
        }
    }
    

    链接方法也很简单。 ->these()为这些值设置内部数组,然后返回对象本身的引用。 ->can()然后对该列表进行操作(如果存在),然后取消设置。在我自己的版本中,我还有->any(),它总是返回完整的部分列表,因此我可以检查->any()->can()

    最后,权限对象还包含用户所属类型的列表。这样可以很容易地显示用户列表以及他们具有哪些权限。在我的情况下,我们只使用->types()来访问该列表,并使用ids => names数组。

    简单地忽略不存在的权限标题。它们也以小写形式匹配,并且空格和特殊字符被删除,以帮助减少键入错误的问题。我甚至考虑过进行levenshtein距离检查并选择最接近的比赛。但最终,最好不要依赖类似的东西。 (也许记录错误,但要优雅地选择最接近的匹配。)

    在代码之外和界面中,用户只需要在管理员,编辑,发布者,作家和CEO等人之间相互关联,等等。为不同的组织创建不同的用户类型集也是微不足道的。

    这部分内容可以大量缓存,为完全没有登录的人设置一个基本用户非常容易,而且我还没有遇到基于权限的问题,这个问题对于解决使用这种结构。

    我只希望能和你分享实际代码。我本人并不拥有它,因此不能发布它。