joseph / rbac
此包提供了一种灵活的方式,可以将基于角色的权限添加到Laravel 4
Requires
- php: >=5.3.0
- illuminate/support: 4.1.*
- laravelbook/ardent: 2.4.*
Requires (Dev)
- illuminate/database: 4.x
- mockery/mockery: 0.7.2
- zizaco/factory-muff: dev-master
This package is not auto-updated.
Last update: 2024-09-28 17:12:28 UTC
README
Rbac是rbac的副本,根据我的需求进行了修改,提供了一种灵活的方式,可以将基于角色的权限添加到Laravel4。
所需设置
在composer.json
文件的require
键中添加以下内容
"joseph/rbac": "v1.0"
运行Composer更新命令
$ composer update
在config/app.php
中,将'Joseph\Rbac\RbacServiceProvider'
添加到$providers
数组末尾
'providers' => array( 'Illuminate\Foundation\Providers\ArtisanServiceProvider', 'Illuminate\Auth\AuthServiceProvider', ... 'Joseph\Rbac\RbacServiceProvider', ),
在config/app.php
的末尾添加'Rbac' => 'Joseph\Rbac\RbacFacade'
到$aliases
数组
'aliases' => array( 'App' => 'Illuminate\Support\Facades\App', 'Artisan' => 'Illuminate\Support\Facades\Artisan', ... 'Rbac' => 'Joseph\Rbac\RbacFacade', ),
配置
将属性值设置到config/auth.php
。这些值将被rbac用于引用正确的用户表和模型。
用户与角色之间的关系
现在生成Rbac迁移
$ php artisan rbac:migration
它将生成<timestamp>_rbac_setup_tables.php
迁移。您现在可以使用Artisan migrate命令运行它
$ php artisan migrate
迁移后,将出现两个新表:包含现有角色及其权限的roles
表和表示User
和Role
之间多对多关系的assigned_roles
表。
模型
创建一个Role模型,参考app/models/Role.php
中的示例
<?php use Joseph\Rbac\RbacRole; class Role extends RbacRole { }
Role
模型有一个主要属性:name
和permissions
。name
,正如你可以想象的,是角色的名称。例如:"Admin"、"Owner"、"Employee"。permissions
字段已被弃用,建议使用权限表。你不再使用它。它是一个数组,在模型保存时会自动序列化和反序列化。此数组应包含Role
的权限名称。例如:array( "manage_posts", "manage_users", "manage_products" )
。
创建一个Permission模型,参考app/models/Permission.php
中的示例
<?php use Joseph\Rbac\RbacPermission; class Permission extends RbacPermission { }
Permission
模型有两个属性:name
和display_name
。name
,正如你可以想象的,是权限的名称。例如:"Admin"、"Owner"、"Employee"、"can_manage"。显示名称是权限字符串的观众友好版本。"Admin"、"Can Manage"、"Something Cool"。
接下来,在你的现有User
模型中使用HasRole
特质。例如
<?php use Joseph\Rbac\HasRole; class User extends Eloquent /* or ConfideUser 'wink' */{ use HasRole; // Add this trait to your user model ...
这将实现与Role
的关系,并在你的User
模型中启用以下方法:roles
、hasRole( $name )
、can( $permission )
和ability($roles, $permissions, $options)
。
别忘了运行composer autoload
$ composer dump-autoload
现在你可以开始了。
用法
概念
让我们首先创建以下Role
和Permission
$owner = new Role; $owner->name = 'Owner'; $owner->save(); $admin = new Role; $admin->name = 'Admin'; $admin->save();
创建完这两个角色后,让我们将它们分配给用户。多亏了HasRole
特质,这将变得非常简单
$user = User::where('username','=','Joseph')->first(); /* role attach alias */ $user->attachRole( $admin ); // Parameter can be an Role object, array or id. /* OR the eloquent's original: */ $user->roles()->attach( $admin->id ); // id only
现在我们只需要向这些角色添加权限。
$managePosts = new Permission; $managePosts->name = 'manage_posts'; $managePosts->display_name = 'Manage Posts'; $managePosts->save(); $manageUsers = new Permission; $manageUsers->name = 'manage_users'; $manageUsers->display_name = 'Manage Users'; $manageUsers->save(); $owner->perms()->sync(array($managePosts->id,$manageUsers->id)); $admin->perms()->sync(array($managePosts->id));
现在我们可以通过简单地执行来检查角色和权限
$user->hasRole("Owner"); // false $user->hasRole("Admin"); // true $user->can("manage_posts"); // true $user->can("manage_users"); // false
你可以在每个User
中有任意多的Role
,反之亦然。
可以使用强大的 ability
函数进行更高级的检查。它接受三个参数(角色、权限、选项)。roles
是要检查的角色集合。permissions
是要检查的权限集合。任一角色或权限变量可以是逗号分隔的字符串或数组。
$user->ability(array('Admin','Owner'), array('manage_posts','manage_users')); //or $user->ability('Admin,Owner', 'manage_posts,manage_users');
这将检查用户是否具有提供的任何角色和权限。在这种情况下,它会返回 true,因为用户是管理员并且具有 manage_posts 权限。
第三个参数是选项数组。
$options = array( 'validate_all' => true | false (Default: false), 'return_type' => boolean | array | both (Default: boolean) );
validate_all
是一个布尔标志,用于设置是否检查所有值都为 true,或者如果至少匹配一个角色或权限则返回 true。
return_type
指定返回布尔值、检查值的数组或同时返回两者(在数组中)。
下面是一个示例输出。
$options = array( 'validate_all' => true, 'return_type' => 'both' ); list($validate,$allValidations) = $user->ability(array('Admin','Owner'), array('manage_posts','manage_users'), $options); // Output var_dump($validate); bool(false) var_dump($allValidations); array(4) { ['role'] => bool(true) ['role_2'] => bool(false) ['manage_posts'] => bool(true) ['manage_users'] => bool(false) }
简写语法路由过滤器
要按权限或角色过滤路由,可以在您的 app/filters.php
中调用以下代码
// Only users with roles that have the 'manage_posts' permission will // be able to access any route within admin/post. Rbac::routeNeedsPermission( 'admin/post*', 'manage_posts' ); // Only owners will have access to routes within admin/advanced Rbac::routeNeedsRole( 'admin/advanced*', 'Owner' ); // Optionally the second parameter can be an array of permissions or roles. // User would need to match all roles or permissions for that route. Rbac::routeNeedsPermission( 'admin/post*', array('manage_posts','manage_comments') ); Rbac::routeNeedsRole( 'admin/advanced*', array('Owner','Writer') );
这两种方法都接受第三个参数。如果第三个参数为 null,则禁止访问的返回将为 App::abort(403)
。否则,将返回第三个参数。因此,您可以像这样使用它
Rbac::routeNeedsRole( 'admin/advanced*', 'Owner', Redirect::to('/home') );
进一步,这两种方法都接受第四个参数。它默认为 true,并检查所有给定角色/权限。如果将其设置为 false,则函数只有在所有角色/权限对用户都失败时才会失败。对于希望允许多个组访问的应用程序非常有用。
// If a user has `manage_posts`, `manage_comments` or both they will have access. Rbac::routeNeedsPermission( 'admin/post*', array('manage_posts','manage_comments'), null, false ); // If a user is a member of `Owner`, `Writer` or both they will have access. Rbac::routeNeedsRole( 'admin/advanced*', array('Owner','Writer'), null, false ); // If a user is a member of `Owner`, `Writer` or both, or user has `manage_posts`, `manage_comments` they will have access. // You can set the 4th parameter to true then user must be member of Role and must has Permission. Rbac::routeNeedsRoleOrPermission( 'admin/advanced*', array('Owner','Writer'), array('manage_posts','manage_comments'), null, false);
路由过滤器
可以通过在 Facade 中使用 can
和 hasRole
方法简单地使用 Rbac 角色权限在过滤器中。
Route::filter('manage_posts', function() { if (! Rbac::can('manage_posts') ) // Checks the current user { return Redirect::to('admin'); } }); // Only users with roles that have the 'manage_posts' permission will // be able to access any admin/post route. Route::when('admin/post*', 'manage_posts');
使用过滤器检查角色
Route::filter('owner_role', function() { if (! Rbac::hasRole('Owner') ) // Checks the current user { App::abort(404); } }); // Only owners will have access to routes within admin/advanced Route::when('admin/advanced*', 'owner_role');
如你所见,Rbac::hasRole()
和 Rbac::can()
检查用户是否登录,然后检查他是否有角色或权限。如果用户未登录,返回值也将为 false
。
故障排除
如果在执行迁移时遇到类似于以下错误的错误
SQLSTATE[HY000]: General error: 1005 Can't create table 'laravelbootstrapstarter.#sql-42c_f8' (errno: 150) (SQL: alter table `assigned_roles` add constraint assigned_roles_user_id_foreign foreign key (`
user_id`) references `users` (`id`)) (Bindings: array (
))
那么很可能是您的用户表中的 id
列与 assigned_roles
中的 user_id
列不匹配。确保两者都是 INT(10)
。
名称保存有问题。
RbacRole
的 name
有一个长度限制,该限制在 RbacRole 类 的规则变量中设置。
您可以通过更改您的角色模型来调整它。
<?php use Joseph\Rbac\RbacRole; class Role extends RbacRole { /** * Ardent validation rules * * @var array */ public static $rules = array( 'name' => 'required|between:4,255' ); }
许可协议
Rbac 是免费软件,根据 MIT 许可协议分发
附加信息
如有任何问题,请随时联系我或在 这里 提问
如有任何问题,请 在此处报告