无需依赖,简单的PHP访问控制列表。

0.1.0 2015-05-04 16:21 UTC

This package is auto-updated.

Last update: 2024-09-05 02:59:29 UTC


README

这是一个简单、无需依赖(使用中)的用户/登录/cookie管理,角色和用户级访问控制系统。

这是一个非常简单、易于使用的用户系统,可以扩展到任何目的。

ACL组件基于Nette\Security,而Nette\Security本身基于Zend_Acl。

安装

您可以克隆存储库并直接操作文件,但已为composer配置了所有内容,这使得操作变得简单。

composer require gburtini/acl

使用方法

使用此包有三个部分。

  • 实现针对您的用例的认证器
  • 开发访问控制列表。
  • 集成用户类。

每个部分都可以根据您的用例是复杂还是简单。

认证器是一个实现了->authenticate($username, $password[, $roles])方法的类,验证用户名和密码(如果指定,则请求的角色),并返回用户的唯一标识符以及属于他的角色集合,格式为['id' => 123, 'roles' => ['administrator']]。在Authenticator.php中提供了一些关于如何编写良好的认证系统的注释。为了演示目的,SimpleAuthenticator.php提供了一个SimpleAuthenticator。

<?php
  class SimpleAuthenticator extends Authenticator {
    private $users;

    public function __construct($userpasses) {
      $this->users = $userpasses;
    }

    public function authenticate($user, $password, $roles=null) {
      if($this->users[$user] === $password)
        return ['id' => $user, 'roles' => $roles];  // in reality, you want to pick/confirm roles for this user.
      return false;
    }
  }

这不是一个好的认证器,因为它给予用户他们请求的任何角色(注意请求角色是可选的,您可以忽略该参数,只需返回此用户的有效角色列表即可),并将用户名和密码完整且明文存储。更好的认证器将与您的用户表或其他数据存储交互。

开发访问控制列表需要使用ACL类。以下是一个示例。

$acl = new ACL();
$acl->addRole("administrator");
$acl->addRole("manager");
$acl->addRole("client");
$acl->addRole("guest");
// or, $acl->addRole("administrator", ["manager"]);, indicating that administrator inherits manager's permissions.

$acl->addResource("files");
$acl->addResource("client_lists");

$acl->deny("guest", ["files", "client_lists"]);
$acl->allow(['administrator', 'manager'], ['files', 'client_lists'], ['read', 'write'], function($acl, $testing_role, $testing_resource, $testing_privilege) {
// this function is an assertion that returns true/false if the rule should apply.
$arguments = $acl->getQueriedOtherArguments();
if($arguments['user_id'] == 4)  // we can pass in user ID and indeed file/list ID via the other arguments system.
  return false;
}));

注意,您可以调用serialize()方法来获取可存储在数据库中的$acl对象版本。有关继承和角色/资源如何工作的更多信息,Nette\Security和Zend_Acl文档几乎可以直接应用于此代码。

最后,要集成用户类以将其全部连接起来。我们可以使用内置的用户,或者扩展它以提供我们自己的功能(特别是存储除标识符以外的用户信息)。在此演示中,我们将使用提供的用户类(在User.php中)。

// provide HMAC and AES keys... note that as of PHP 5.6 invalid length AES keys are not acceptable.
// we use the WordPress Secret Key API to generate the HMAC key: https://api.wordpress.org/secret-key/1.1/salt/
// if you wish and trust me, you can generate keys here: http://giuseppe.ca/aes.php - pass ?size=12 to force a particular size (bytes) output key.
$user = new User('SNgsHsd#T$DaN R*Ol~O6z+a+[v}@3)6%-X0nHH|%#ag+hYV 5f|zs}6;T|wM?3+', 'ALPHb92wzIamFw39VHLTiv6rY8i6EiEU8Plghvbhu547iPlgqlHSy76F');
$user->setAuthenticator(new SimpleAuthenticator([
  'johnny' => 'apples33d',
  'thelma' => 'J!JHndmTivE'
]));
$user->setExpiration("30 days");
$user->setACL($acl);  // from our previous set up
// if the user is not signed in, his only role is 'guest' and his ID is null.
// but you can check with $user->isLoggedIn(), $user->whoAmI() or $user->roles()

// if the user has a login stored in his cookies, he will be already authenticated. If he weren't, you can try to authenticate him with $user->login($username, $password); -- this will throw an exception if the login fails.

if($user->can("files", "view", 1)) {
    echo "I'm allowed to view file #1";
}

完成了。这就是整个系统。

注意:选择强密钥非常重要。我的网站提供了一些代码,如果您信任我和我的服务器不会受到损害,则可以为您生成密钥(注意:您不应该这样做,在理想情况下,您应该检查并运行代码),本质上它并不比调用openssl_random_pseudo_bytes更复杂。

$key =  openssl_random_pseudo_bytes($length_bytes, $boolean);
if($boolean === false) die("This is not a good key. Something bad happened.");

未来工作

有很多事情可以做,但没有我立即需要的事情。欢迎提交拉取请求。

  • 将所有异常转换为抛出不同的类,以便可以干净地捕获原因。
  • 实现一些其他认证器和用户类。
  • 记录如何扩展用户类以进行您的实现。
  • 验证并提取User.php中所需的加密,将其放入其自己的依赖包。
  • 与gburtini/Hooks集成,以便在用户实例上发生事件。
  • 记录此文件中(README.md)的每个方法。
  • 添加“令牌认证”系统,允许生成临时(基于正则表达式或角色)认证。例如,用于在密码恢复系统中更改密码。

为了简化,我希望将以下内容保留在包之外,但这将对许多用户很有价值。

  • 用户存储功能(包括用户权限在内的用户信息写入数据库)。
  • 进一步的用户身份功能(目前,User类旨在扩展以提供这些功能)。

许可协议

由于代码的部分部分来自New BSD许可的代码,我们遵循了这一精神,并且此包本身也根据New BSD许可发布。

新颖贡献。版权(c)2015 Giuseppe Burtini。

Zend_Acl原始代码。版权(c)2005-2015,Zend Technologies USA, Inc. 保留所有权利。

重新分发和使用源代码和二进制形式,无论是否修改,只要满足以下条件。

  • 源代码的重新分发必须保留上述版权声明、本条件列表和以下免责声明。
  • 二进制形式的重新分发必须复制上述版权声明、本条件列表和以下免责声明在随附的文档和其他材料中。
  • 未经具体事先书面许可,不得使用Zend Technologies USA, Inc.或Giuseppe Burtini的名称或任何贡献者的名称来认可或推广由此软件派生出的产品。

本软件由版权所有者和贡献者提供“现状”且不承担任何明示或暗示的保证,包括但不限于适销性和特定用途的适用性保证。在任何情况下,版权所有者或贡献者不应对任何直接、间接、偶然、特殊、示范性或后果性的损害(包括但不限于替代商品或服务的采购;使用、数据或利润的损失;或业务中断)承担责任,无论这种损害是由何种原因造成的,无论是在合同、严格责任还是侵权(包括疏忽或其他)责任,即使在被告知可能发生此类损害的情况下。