当前位置:首页 > CMS教程 > Thinkphp > 列表

thinkPHP3.2使用RBAC实现权限管理的实现

发布:smiling 来源: PHP粉丝网  添加日期:2021-12-12 15:40:12 浏览: 评论:0 

这篇文章主要介绍了thinkPHP3.2使用RBAC实现权限管理的实现,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧。

在thinkphp3.2中自己集成了RBAC来实现权限管理,RBAC实现类在项目中地址为:ThinkPHP/Librar/Org/Util/Rbac.class.php,其中集成了我们所需的权限管理操作

一:表设计

在thinkPHP的Rbac的的Rbac.class.php文件中一共提供了4张表,还有一张用户表需要你自己去建

如下是我所建的和权限相关的sql

其中的wj_为表前缀,改成你项目中的表前缀

1:权限表:

  1. CREATE TABLE IF NOT EXISTS `wj_access` ( 
  2.  `role_id` SMALLINT(6) UNSIGNED NOT NULL COMMENT '角色ID'
  3.  `node_id` SMALLINT(6) UNSIGNED NOT NULL COMMENT '节点ID'
  4.  `level` TINYINT(1) NOT NULL COMMENT '深度'
  5.  `module` VARCHAR(50) DEFAULT NULL COMMENT '模块'
  6.  KEY `groupId` (`role_id`), 
  7.  KEY `nodeId` (`node_id`) 
  8. ) ENGINE=MYISAM DEFAULT CHARSET=utf8 COMMENT='权限表'

2:节点表:

  1. CREATE TABLE IF NOT EXISTS `wj_node` ( 
  2.  `id` SMALLINT(6) UNSIGNED NOT NULL AUTO_INCREMENT COMMENT '节点ID'
  3.  `nameVARCHAR(20) NOT NULL COMMENT '节点名称'
  4.  `title` VARCHAR(50) DEFAULT NULL COMMENT '节点标题'
  5.  `status` TINYINT(1) DEFAULT '0' COMMENT '状态 0禁用 1启用'
  6.  `remark` VARCHAR(255) DEFAULT NULL COMMENT '描述'
  7.  `sort` SMALLINT(6) UNSIGNED DEFAULT NULL COMMENT '排序'
  8.  `pid` SMALLINT(6) UNSIGNED NOT NULL COMMENT '父级节点'
  9.  `level` TINYINT(1) UNSIGNED NOT NULL COMMENT '深度'
  10.  PRIMARY KEY (`id`), 
  11.  KEY `level` (`level`), 
  12.  KEY `pid` (`pid`), 
  13.  KEY `status` (`status`), 
  14.  KEY `name` (`name`) 
  15. ) ENGINE=MYISAM DEFAULT CHARSET=utf8 COMMENT='节点表'

3:用户角色表:

  1. CREATE TABLE IF NOT EXISTS `wj_role` ( 
  2.  `id` SMALLINT(6) UNSIGNED NOT NULL AUTO_INCREMENT COMMENT '角色ID'
  3.  `nameVARCHAR(20) NOT NULL COMMENT '角色名称'
  4.  `pid` SMALLINT(6) DEFAULT NULL '父级ID'
  5.  `status` TINYINT(1) UNSIGNED DEFAULT NULL COMMENT '状态 0禁用 1启用'
  6.  `remark` VARCHAR(255) DEFAULT NULL COMMENT '备注'
  7.  PRIMARY KEY (`id`), 
  8.  KEY `pid` (`pid`), 
  9.  KEY `status` (`status`) 
  10. ) ENGINE=MYISAM DEFAULT CHARSET=utf8 COMMENT='用户角色表'

4:用户角色关联表:

  1. CREATE TABLE IF NOT EXISTS `wj_role_user` ( 
  2.  `role_id` MEDIUMINT(9) UNSIGNED DEFAULT NULL COMMENT '角色ID'
  3.  `user_id` CHAR(32) DEFAULT NULL COMMENT '用户ID'
  4.  KEY `group_id` (`role_id`), 
  5.  KEY `user_id` (`user_id`) 
  6. ) ENGINE=MYISAM DEFAULT CHARSET=utf8 COMMENT='用户角色关联表'

5:用户表:

  1. CREATE TABLE IF NOT EXISTS `wj_user` ( 
  2.  `user_id` INT(11) UNSIGNED NOT NULL AUTO_INCREMENT COMMENT '用户ID'
  3.  `username` VARCHAR(50) NOT NULL COMMENT '用户名'
  4.  `passwordVARCHAR(100) NOT NULL COMMENT '密码'
  5.  `create_time` INT(10) DEFAULT NULL COMMENT '创建时间'
  6.  `update_time` INT(10) DEFAULT NULL COMMENT '更新时间'
  7.  `status` INT(1) DEFAULT NULL COMMENT '状态 0禁用 1启用'
  8.  PRIMARY KEY (`user_id`) 
  9. ) ENGINE=MYISAM DEFAULT CHARSET=utf8 COMMENT='用户表'

二:关于权限操作的常用配置:

你可以在config.php文件的数组中增加:

// 加载扩展配置文件

'LOAD_EXT_CONFIG' => 'user',

这样的话我们就可以将我们的所有权限配置放置在config.php同级的user.php文件中,user.php文件配置如下:

  1. <?php 
  2. /** 
  3.  * 用户权限配置文件 
  4.  */ 
  5. return array
  6.   // 是否需要认证 
  7.   'USER_AUTH_ON' => true, 
  8.   // 认证类型 1 登录认证 2 实时认证 
  9.   'USER_AUTH_TYPE' => 1, 
  10.   // 后台用户认证SESSION标记 
  11.   'USER_AUTH_KEY' => 'wjAuthId'
  12.   // 默认认证网关 
  13.   'USER_AUTH_GATEWAY' => '?m=Admin&c=Login&a=index'
  14.   // RBAC_DB_DSN 数据库连接DSN 
  15.   // 角色表名称,C('DB_PREFIX')表示前缀 
  16.   'RBAC_ROLE_TABLE' => C('DB_PREFIX') . 'role'
  17.   // 用户角色关联表名称 
  18.   'RBAC_USER_TABLE' => C('DB_PREFIX') . 'role_user'
  19.   // 权限表名称 
  20.   'RBAC_ACCESS_TABLE' => C('DB_PREFIX') . 'access'
  21.   // 节点表名称 
  22.   'RBAC_NODE_TABLE' => C('DB_PREFIX') . 'node'
  23.   // 默认验证数据表模型 
  24.   'USER_AUTH_MODEL' => 'User'
  25.   // 超级管理员的SESSION标记 
  26.   'ADMIN_AUTH_KEY' => 'wjAdministrator'
  27.   // 默认需要认证模块 
  28.   'REQUIRE_AUTH_MODULE' => ''
  29.   // 默认需要认证操作 
  30.   'REQUIRE_AUTH_ACTION' => ''
  31.   // 默认无需认证模块 
  32.   'NOT_AUTH_MODULE' => 'Public'
  33.   // 默认无需认证操作 
  34.   'NOT_AUTH_ACTION' => ''
  35.   // 是否开启游客授权访问 
  36.   'GUEST_AUTH_ON' => false, 
  37.   // 游客的用户ID 
  38.   'GUEST_AUTH_ID' => 0, 
  39.   // 后台用户名的SESSION标记 
  40.   'BACK_LOGIN_NAME' => 'loginBackName'
  41.   // 后台角色的SESSION标记 
  42.   'BACK_USER_ROLE' => 'bakcUserRole'
  43.   // 后台角色ID的SESSION标记 
  44.   'BACK_ROLE_ID' => 'backRoleId'
  45.   // 后台用户登录时间的SESSION标记 
  46.   'BACK_ONLINE_TIME' => 'backOnlineTime'
  47.   // 后台在线间隔时间,以分钟为单位 
  48.   'ONLINE_INTERVAL' => 180, 
  49.   //退出登录的URL 
  50.   'LOGOUT_URL' => '/test'
  51. ); 

三:关于权限操作的常用方法:

1:Rbac::saveAccessList($authId=null);

缓存权限列表,在这个方法可以传递空值的前提是:你在用户登录操作的时候要在 $_SESSION[C('USER_AUTH_KEY')] 中把用户的id保存下来,然后这里会将用户所对应的角色拥有的权限都保存在$_SESSION['_ACCESS_LIST']中

2:Rbac::checkAccess()

判断用户访问的模块和方法是否需要权限认证

3:Rbac::AccessDecision()

断用户是否有访问权限的,即检测当前项目模块操作 是否在$_SESSION['_ACCESS_LIST']数组中,也就是说 在 $_SESSION['_ACCESS_LIST'] 数组中$_SESSION'_ACCESS_LIST''当前控制器'是否存在。如果存在表示有权限 否则返回flase

4:Rbac::checkLogin();

判断用户是否登录,如果未登录则跳转到指定路径

5:Rbac::getAccessList($authId)

通过查询数据库 返回权限列表 $_SESSION['_ACCESS_LIST']的值

6:Rbac::authenticate($map, $model='')

传入查询用户的条件和用户表的MODEL 返回数组包含用户的信息,如果不传model值的话使用配置项中的USER_AUTH_MODEL

四:权限管理简单实现实例:

1:登录:

  1. //获取传递的用户名和密码 
  2. $username = I('post.username'); 
  3. $password = I('post.password'); 
  4. //生成认证条件 
  5. $map = array(); 
  6. $map['username'] = $username
  7. $map['status'] = array('eq', 1); 
  8. //判断是否存在此用户 
  9. $authInfo = Rbac::authenticate($map); 
  10. if (!$authInfo) { 
  11.   $this->error('账号不存在'); 
  12. if ($authInfo['password'] != md5($password)) { 
  13.   $this->error('密码错误'); 
  14. $user_id = $authInfo['user_id']; 
  15. $role_user = new Model(); 
  16. $role = $role_user->Table(C("RBAC_USER_TABLE"))->alias("user")->where("user_id=" . $user_id)->join(C("RBAC_ROLE_TABLE") . " as role ON role.id=user.role_id")->field("id,name")->find(); 
  17. if (emptyempty($role)) { 
  18.   $this->error('此用户无对应的角色,无法登录'); 
  19. //后台角色ID的SESSION标记 
  20. session(C('BACK_ROLE_ID'), $role['id']); 
  21. //后台角色的SESSION标记 
  22. session(C('BACK_USER_ROLE'), $role['name']); 
  23. //后台用户认证SESSION标记 
  24. session(C('USER_AUTH_KEY'), $authInfo['user_id']); 
  25. //后台用户名的SESSION标记 
  26. session(C('BACK_LOGIN_NAME'), $authInfo['username']); 
  27. //后台用户登录时间的SESSION标记 
  28. session(C('BACK_ONLINE_TIME'), time()); 
  29. //判断用户角色是否为超级管理员 
  30. if ($role['id'] == '1') { 
  31.   //超级管理员将超级管理员的SESSION标记设置为true 
  32.   session(C('ADMIN_AUTH_KEY'), true); 
  33. // 缓存访问权限 
  34. Rbac::saveAccessList(); 
  35. $this->success('登录成功', U('Index/index')); 

2:登录成功后的权限校验:

  1. //验证是否登录 
  2. Rbac::checkLogin(); 
  3. // 用户权限检查 
  4. if (Rbac::checkAccess() && !Rbac::AccessDecision()) { 
  5.   // 没有权限 清除登录session 并抛出错误 
  6.   if (C('RBAC_ERROR_PAGE')) { 
  7.     // 定义权限错误页面 
  8.     redirect(C('RBAC_ERROR_PAGE')); 
  9.   } else { 
  10.     if (C('GUEST_AUTH_ON')) { 
  11.       //开启游客访问 
  12.     } 
  13.     // 提示错误信息 
  14.     $this->error(L('_VALID_ACCESS_')); 
  15.   } 
  16. //自动退出功能,判断后台用户登录时间的SESSION标记是否超时 
  17. if (session(C('BACK_ONLINE_TIME')) + C('ONLINE_INTERVAL') * 60 < time()) { 
  18.   if (session('?' . C('USER_AUTH_KEY'))) { 
  19.     session('[destroy]'); 
  20.     if (isset($_COOKIE[session_name()])) { 
  21.       setcookie(session_name(), '', time() - 3600, '/'); 
  22.     } 
  23.     session_destroy(); 
  24.   } 
  25.   $this->error('超时请重新登录', U('Login/index')); 
  26. else { 
  27.   session(C('BACK_ONLINE_TIME'), time()); 

根据如上就可以实现用户角色的权限管理。

Tags: thinkPHP3 2 RBAC权限管理

分享到: