YII2框架RBAC 实例运用
来源:互联网 发布:电脑该网络存储 编辑:程序博客网 时间:2024/06/06 01:36
YII2框架RBAC 自己开发(权限控制)实例运用
1、首先说一下什么是RBAC
基于角色的访问控制(Role-Based Access Control),作为传统访问控制(自主访问,强制访问)的有前景的受到广泛的关注,在RBAC中,权限与角色相关联,用户通过角色的成员得到这些角色的权限。这就极大地简化了权限的管理。在一个组织中,角色是为了完成各种工作而创造,用户则依据他的责任和资格来被指派响应的角色,用户可以很容易地从一个角色被指派到另一个角色。角色可依新的需求和系统的合并并赋予新的权限,而权限也可根据需要而从某角色中回收。角色与角色的关系可以建立起来以囊括更广泛的客观情况。
2、测试中我们可以做一个简单的登录,将用户名和id存入到session中,方便以后的使用
3、yii框架中的权限分配
我们在学习PHP的过程中应该对TP框架中的RBAC很熟悉,其实框架之间的内容大多数都是相同的,下面让我们来看一下yii框架中的RBAC。
配置RBAC
在开始定义授权数据和执行存取检查之前,需要先配置应用组件yii/base/Application::authManager。yii提供了两套授权管理器;yii/rbac/phpManager和yii/rbac/DbManager。牵着使用PHP脚本存放授权数据,而后者使用数据库存放授权数据。如果你的应用不要求大量的动态角色和权限管理,你可以考虑使用前者。
下面是两个文件的位置
配置在frontend/backend文件夹,config文件夹下main.php
或者
有关yii2使用RBAC地址:http://www.yiifans.com/forum.php?mod=viewthread&tid=11244
我们此时用自己的方法套用YII2框架实现RBAC
RBAC实现思路:
所需表:用户表
角色表
用-角派生表
节点表
节-角的派生表
大致步骤:
1、首先根据用户id 查询用-角派生表 查出角色id
2、在根据角色id 查询 节-角派生表 查出改角色对应节点id 中的控制器和方法
3、再用当前的的控制器和方法进行比对 如果没有就权限给出提示
难点:表关系的处理、查询语句、以及节点赋权时 多选框 点击一级其余子级选中、点击子级父级选中
笔者运用的ACE后台模板
效果展示:
节点列表
角色列表
角色节点赋权
用户角色赋权
代码实例:
common控制器
<?phpnamespace frontend\controllers;header("content-type:text/html;charset=utf-8");use Yii;use yii\base\InvalidParamException;use yii\web\BadRequestHttpException;use yii\web\Controller;use yii\filters\VerbFilter;use yii\filters\AccessControl;use common\models\LoginForm;use frontend\models\PasswordResetRequestForm;use frontend\models\ResetPasswordForm;use frontend\models\SignupForm;use frontend\models\ContactForm;use yii\db\Query;class CommonController extends Controller{ /** * @param \yii\base\Action $action * @return bool * @throws BadRequestHttpException */ public function beforeAction($action){ $session=\Yii::$app->session; $user_session=$session->get('user'); //判断是否有登录session if(!isset($user_session)){ echo "<script>alert('请先登录');location.href='index.php?r=login/login'</script>";die; } //设置超级管理员 if($user_session=="admin"){ return true; } //判断权限 $ctl=Yii::$app->controller->id; //获取当前访问的控制器 $action=Yii::$app->controller->action->id; //获取当前访问的方法 //当访问后台是首页权限是公共的 if($ctl=="admin" && $action=="index"){ return true; } $id_session=$session->get('id'); //接到用户登录时存的id $sql="select rn.node_id,n.controller,n.action from role_node as rn left join node as n on rn.node_id=n.node_id where role_id in(SELECT role_id from user_role where user_id=$id_session) group by rn.node_id"; $rows=Yii::$app->db->createCommand($sql)->queryAll(); //查询出该角色的权限 if($rows){ foreach($rows as $key => $val){ if($val['controller']==$ctl && $val['action']==$action){ return true; } } echo "<script>alert('抱歉,您的权限不够');location.href='index.php?r=admin/index'</script>"; return false; }else{ echo "<script>alert('抱歉,您的权限不够');location.href='index.php?r=admin/index'</script>"; } if (!parent::beforeAction($action)) { return false; } return true; }}用户控制器
<?phpnamespace frontend\controllers;use Yii;use yii\web\Controller;use yii\db\Query;use yii\data\Pagination;class UsersController extends CommonController{ public $layout = 'admin'; /**显示页面 * @return void */ public function actionShow(){ $query = new Query(); //查询出所有的数据 $userList = $query->from('user')->where(['is_delete'=>0])->all(); //统计数据个数 $count = count($userList); //实例化分页类 $pagination = new Pagination(['totalCount' => $count]); $pagination->setPageSize(2 ); $data = $query->offset($pagination->offset)->limit($pagination->limit)->all(); return $this->render('show', ['data' => $data, 'pagination' => $pagination,]); } /** * 删除 * @return void */ public function actionDel() { $db = Yii::$app->db; $id = Yii::$app->request->get('user_id'); $res = $db->createCommand()->update('user',['is_delete'=>1],['user_id'=>$id])->execute(); if($res) { echo "<script>alert('删除成功');location.href='index.php?r=users/show'</script>"; }else{ echo "<script>alert('删除失败');location.href='index.php?r=users/show'</script>"; } } /** *添加 * @return void */ public function actionAdd(){ $request = YII::$app->request; if($request->isPost) { $user_name = $request->post('user_name'); $user_pwd = $request->post('user_pwd'); $user_time=date("Y-m-d H:i:s",time()); $res=Yii::$app->db->createCommand()->insert('user', ['user_name' => $user_name,'user_pwd'=>$user_pwd,'user_time'=>$user_time])->execute(); if($res){ echo "<script>alert('添加成功');location.href='index.php?r=users/show'</script>"; }else{ echo "<script>alert('添加失败');location.href='index.php?r=users/show'</script>"; } }else{ return $this->render('add'); } } /** * 修改数据 * @return void */ public function actionUpda() { $request = YII::$app->request; if($request->isPost){ $user_name=$request->post('user_name'); $user_pwd=$request->post('user_pwd'); $user_id=$request->post('user_id'); $res=Yii::$app->db->createCommand()->update('user', ['user_name' => $user_name,'user_pwd'=>$user_pwd], "user_id = $user_id")->execute(); if($res){ echo "<script>alert('修改成功');location.href='index.php?r=users/show'</script>"; }else{ echo "<script>alert('修改失败');location.href='index.php?r=users/show'</script>"; } } if($request->get('user_id')){ $id=$request->get('user_id'); $data = Yii::$app->db->createCommand("SELECT * FROM user WHERE user_id=$id")->queryOne(); return $this->render('upda', ['userInfo' => $data]); } } /**用户角色赋权 * @return string * @throws \yii\db\Exception */ public function actionAuthority(){ $request = YII::$app->request; $db = Yii::$app->db; if($request->isPost){ $request->post(); $role_ids= $request->post('role_id'); $user_id= $request->post('user_id'); //查询派生表中数据 $sql="select * from user_role where user_id=$user_id"; $user_role=Yii::$app->db->createCommand($sql)->queryAll(); if($user_role){ //删除派生表中原有数据 $re=Yii::$app->db->createCommand()->delete('user_role', "user_id = $user_id")->execute(); //判断是否接到值 if($role_ids){ foreach($role_ids as $v){ $res=Yii::$app->db->createCommand()->insert('user_role', ['user_id' => $user_id,'role_id'=>$v])->execute(); } if($res){ echo "<script>alert('角色赋权成功');location.href='index.php?r=users/show'</script>";die; }else{ echo "<script>alert('角色赋权失败');location.href='index.php?r=users/show'</script>";die; } }else{ echo "<script>alert('清除所有角色');location.href='index.php?r=users/show'</script>";die; } }else{ if($role_ids){ foreach($role_ids as $v){ $res=Yii::$app->db->createCommand()->insert('user_role', ['user_id' => $user_id,'role_id'=>$v])->execute(); } if($res){ echo "<script>alert('角色赋权成功');location.href='index.php?r=users/show'</script>";die; }else{ echo "<script>alert('角色赋权失败');location.href='index.php?r=users/show'</script>";die; } }else{ echo "<script>alert('清除所有角色');location.href='index.php?r=users/show'</script>";die; } } } if($request->isGet){ //查询角色表 $query = new Query(); //查询出所有的数据 $roleList = $query->from('role')->where(['is_delete'=>0])->all(); $user_id = Yii::$app->request->get('user_id'); //查询用户拥有角色 $sql="select * from user_role where user_id=$user_id"; $user_role=Yii::$app->db->createCommand($sql)->queryAll(); $arr=array(); foreach($user_role as $v){ $arr[]=$v['role_id']; } //前台多选框选中字段添加 foreach($roleList as $k=>$val){ if(in_array($val['role_id'],$arr)){ $roleList[$k]['check']="check"; }else{ $roleList[$k]["check"]="false"; } } return $this->render('authority',['roleList'=>$roleList,'user_id'=>$user_id,'user_role'=>$user_role]); } }}角色控制器
<?phpnamespace frontend\controllers;use Yii;use yii\web\Controller;use yii\db\Query;use yii\data\Pagination;class RoleController extends CommonController{ public $layout = 'admin'; public function actionShow(){ $query = new Query(); //查询出所有的数据 $userList = $query->from('role')->where(['is_delete'=>0])->all(); //统计数据个数 $count = count($userList); //实例化分页类 $pagination = new Pagination(['totalCount' => $count]); $pagination->setPageSize(2 ); $data = $query->offset($pagination->offset)->limit($pagination->limit)->all(); return $this->render('show', ['data' => $data, 'pagination' => $pagination,]); } /** * 删除 * @return void */ public function actionDel() { $db = Yii::$app->db; $id = Yii::$app->request->get('role_id'); $res = $db->createCommand()->update('role',['is_delete'=>1],['role_id'=>$id])->execute(); if($res) { echo "<script>alert('删除成功');location.href='index.php?r=role/show'</script>"; }else{ echo "<script>alert('删除失败');location.href='index.php?r=role/show'</script>"; } } /** * 修改数据 * @return [type] [description] */ public function actionUpda() { $request = YII::$app->request; if($request->isPost){ $role_name=$request->post('role_name'); $role_desc=$request->post('role_desc'); $role_start=$request->post('role_start'); $role_id=$request->post('role_id'); $res=Yii::$app->db->createCommand()->update('role', ['role_name' => $role_name,'role_desc'=>$role_desc,'role_start'=>$role_start], "role_id = $role_id")->execute(); if($res){ echo "<script>alert('修改成功');location.href='index.php?r=role/show'</script>"; }else{ echo "<script>alert('修改失败');location.href='index.php?r=role/show'</script>"; } } if($request->get('role_id')){ $id=$request->get('role_id'); $data = Yii::$app->db->createCommand("SELECT * FROM role WHERE role_id=$id")->queryOne(); return $this->render('upda', ['roleInfo' => $data]); } } /**添加角色 * @return string * @throws \yii\db\Exception */ public function actionAdd(){ $request = YII::$app->request; if($request->isPost){ $role_name=$request->post('role_name'); $role_desc=$request->post('role_desc'); $role_start=$request->post('role_start'); $role_time=date("Y-m-d H:i:s",time()); $res=Yii::$app->db->createCommand()->insert('role', ['role_name' => $role_name,'role_desc'=>$role_desc,'role_start'=>$role_start,'role_time'=>$role_time])->execute(); if($res){ echo "<script>alert('添加成功');location.href='index.php?r=role/show'</script>"; }else{ echo "<script>alert('添加失败');location.href='index.php?r=role/show'</script>"; } }else{ return $this->render('add'); } } /**角色节点赋权 * @return string * @throws \yii\db\Exception */ public function actionAuthority(){ $request = YII::$app->request; if($request->isPost){ $request->post(); $node_ids= $request->post('node_id'); $role_id= $request->post('role_id'); //查询派生表中数据 $sql="select * from role_node where role_id=$role_id"; $role_node=Yii::$app->db->createCommand($sql)->queryAll(); if($role_node){ //删除派生表中原有数据 $re=Yii::$app->db->createCommand()->delete('role_node', "role_id = $role_id")->execute(); //判断是否接到值 if($node_ids){ foreach($node_ids as $v){ $res=Yii::$app->db->createCommand()->insert('role_node', ['role_id' => $role_id,'node_id'=>$v])->execute(); } if($res){ echo "<script>alert('节点赋权成功');location.href='index.php?r=role/show'</script>";die; }else{ echo "<script>alert('节点赋权失败');location.href='index.php?r=role/show'</script>";die; } }else{ echo "<script>alert('清除所有节点');location.href='index.php?r=role/show'</script>";die; } }else{ if($node_ids){ foreach($node_ids as $v){ $res=Yii::$app->db->createCommand()->insert('role_node', ['role_id' => $role_id,'node_id'=>$v])->execute(); } if($res){ echo "<script>alert('节点赋权成功');location.href='index.php?r=role/show'</script>";die; }else{ echo "<script>alert('节点赋权失败');location.href='index.php?r=role/show'</script>";die; } }else{ echo "<script>alert('清除所有节点');location.href='index.php?r=role/show'</script>";die; } } } if($request->isGet){ $id = Yii::$app->request->get('role_id'); //查询出所有节点 $query = new Query(); //查询出所有的数据 $nodeList = $query->from('node')->all(); $nodeLists=$this->sort_a($nodeList); //查询出派生表中角色所定义的节点id $role_node= Yii::$app->db->createCommand("SELECT * FROM role_node where role_id=$id")->queryAll(); //循环两个数组将角色对应的节点增加选中字段 $arr=array(); foreach($role_node as $v){ $arr[]=$v['node_id']; } foreach($nodeLists as $k=>$val){ if(in_array($val['node_id'],$arr)){ $nodeLists[$k]['check']="check"; }else{ $nodeLists[$k]['check']="false"; } } return $this->render('authority',['nodeLists'=>$nodeLists,'role_id'=>$id]); } } /** 递归 * @param 列表数据 * @param int 父类id * @param int 间隔 * @return array */ public function sort_a($res,$sid=0,$level=0){ static $arr=array(); foreach($res as $key=>$val){ if($val['parent_id']==$sid){ $val['level']=str_repeat(" ",$level); $arr[]=$val; $this->sort_a($res,$val['node_id'],$level+1); } } return $arr; }}
节点控制器
<?phpnamespace frontend\controllers;use Yii;use yii\web\Controller;use yii\db\Query;use yii\data\Pagination;class NodeController extends CommonController{ public $layout = 'admin'; public function actionShow(){ $query = new Query(); //查询出所有的数据 $nodeList = $query->from('node')->all(); $nodeLists=$this->sort_a($nodeList); return $this->render('show', ['data' => $nodeLists]); } /** 递归 * @param 列表数据 * @param int 父类id * @param int 间隔 * @return array */ public function sort_a($res,$sid=0,$level=0){ static $arr=array(); foreach($res as $key=>$val){ if($val['parent_id']==$sid){ $val['level']=str_repeat(" ",$level); $arr[]=$val; $this->sort_a($res,$val['node_id'],$level+1); } } return $arr; } /** * 删除 * @return void */ public function actionDel() { $db = Yii::$app->db; $id = Yii::$app->request->get('node_id'); $sql="select * from node where parent_id = $id"; $data = Yii::$app->db->createCommand("$sql")->queryAll(); if($data){ echo "<script>alert('该目录下有子类不能删除');location.href='?r=node/show';</script>";die; } $res=Yii::$app->db->createCommand()->delete('node', "node_id = $id")->execute(); if($res) { echo "<script>alert('删除成功');location.href='index.php?r=node/show'</script>"; }else{ echo "<script>alert('删除失败');location.href='index.php?r=node/show'</script>"; } } /** * 修改数据 * @return void */ public function actionUpda() { $request = YII::$app->request; if($request->isPost){ $node_title=$request->post('node_title'); $controller=$request->post('controller'); $action=$request->post('action'); $parent_id=$request->post('parent_id'); $node_id=$request->post('node_id'); $res=Yii::$app->db->createCommand()->update('node', ['node_title' => $node_title,'controller'=>$controller,'action'=>$action,'parent_id'=>$parent_id], "node_id = $node_id")->execute(); if($res){ echo "<script>alert('修改成功');location.href='index.php?r=node/show'</script>"; }else{ echo "<script>alert('修改失败');location.href='index.php?r=node/show'</script>"; } } if($request->get('node_id')){ $query = new Query(); //查询出所有的数据 $nodeList = $query->from('node')->all(); $nodeLists=$this->sort_a($nodeList); $id=$request->get('node_id'); $data = Yii::$app->db->createCommand("SELECT * FROM node WHERE node_id=$id")->queryOne(); return $this->render('upda', ['nodeInfo' => $data,'nodelist'=>$nodeLists]); } } /**节点添加 * @return string * @throws \yii\db\Exception */ public function actionAdd(){ $query = new Query(); //查询出所有的数据 $nodeList = $query->from('node')->all();// print_R($nodeList);exit; $nodeLists=$this->sort_a($nodeList); $request = YII::$app->request; if($request->isPost){// print_r( $request->post());exit; $node_title=$request->post('node_title'); $controller=$request->post('controller'); $action=$request->post('action'); $parent_id=$request->post('parent_id'); $res=Yii::$app->db->createCommand()->insert('node', ['node_title' => $node_title,'controller'=>$controller,'action'=>$action,'parent_id'=>$parent_id])->execute(); if($res){ echo "<script>alert('添加成功');location.href='index.php?r=node/show'</script>"; }else{ echo "<script>alert('添加失败');location.href='index.php?r=node/show'</script>"; } }else{ return $this->render('add',['nodelist'=>$nodeLists]); } }}
显示页面就不一一展示了,笔者只将用户赋角和角色赋节点两个页面展示
1、用户赋角
<div class="main-content"> <div class="breadcrumbs" id="breadcrumbs"> <script type="text/javascript"> try{ace.settings.check('breadcrumbs' , 'fixed')}catch(e){} </script> <ul class="breadcrumb"> <li> <i class="icon-home home-icon"></i> <a href="#">角色授权</a> </li> <li class="active">控制台</li> </ul><!-- .breadcrumb --> <div class="nav-search" id="nav-search"> <form class="form-search"> <span class="input-icon"> <input type="text" placeholder="Search ..." class="nav-search-input" id="nav-search-input" autocomplete="off" /> <i class="icon-search nav-search-icon"></i> </span> </form> </div><!-- #nav-search --> </div> <div class="page-content"> <div class="page-header"> <h1> 权限管理功能 <small> <i class="icon-double-angle-right"></i> 角色授权 </small> </h1> </div> <!-- /.page-header --> <!-- 添加HTML --> <center> <table> <form action="?r=users/authority" method="post" > <tr> <td>角色:</td> <td class="input-group input-group-sm"> <span class="input-group-addon">@</span> <?php foreach($roleList as $v){;?> <input type="checkbox" name="role_id[]" value="<?php echo $v['role_id'] ;?>"<?php if($v['check']=='check'){ ?>checked="checked" <?php } ;?>/><?php echo $v['role_name'] ;?> <?php };?> </td> </tr> <tr> <td> <input type="hidden" name="user_id" value="<?php echo $user_id ;?>"/> </td> <td><input type="submit" value="submit"></td> </tr> </form> </table> </center> </div><!-- /.page-content --></div><!-- /.main-content -->2、角色赋节点
<div class="main-content"> <div class="breadcrumbs" id="breadcrumbs"> <script type="text/javascript"> try{ace.settings.check('breadcrumbs' , 'fixed')}catch(e){} </script> <ul class="breadcrumb"> <li> <i class="icon-home home-icon"></i> <a href="#">节点授权</a> </li> <li class="active">控制台</li> </ul><!-- .breadcrumb --> <div class="nav-search" id="nav-search"> <form class="form-search"> <span class="input-icon"> <input type="text" placeholder="Search ..." class="nav-search-input" id="nav-search-input" autocomplete="off" /> <i class="icon-search nav-search-icon"></i> </span> </form> </div><!-- #nav-search --> </div> <div class="page-content"> <div class="page-header"> <h1> 权限管理功能 <small> <i class="icon-double-angle-right"></i> 节点授权 </small> </h1> </div> <!-- /.page-header --> <!-- 添加HTML --> <center> <table> <form action="?r=role/authority" method="post" > <tr> <td>节点:</td> <td class="input-group input-group-sm"> <span class="input-group-addon">@</span> <?php foreach($nodeLists as $v){;?> <input type="checkbox" class="node" name="node_id[]" id="<?php echo $v['node_id'] ;?>" parent_id="<?php echo $v['parent_id'] ;?>" value="<?php echo $v['node_id'] ;?>"<?php if($v['check']=='check'){ ?>checked="checked" <?php } ;?>/><?php echo $v['node_title'] ;?> <?php };?> </td> </tr> <tr> <td> <input type="hidden" name="role_id" value="<?php echo $role_id ;?>"/> </td> <td><input type="submit" value="submit"></td> </tr> </form> </table> </center> </div><!-- /.page-content --></div><!-- /.main-content --><script src="assets/js/jquery1.8.3.js"></script><script> $(function(){ //上、下级选中 $(".node").click( function(){ var _this=$(this).val(); var _parent=$(this).attr("parent_id") if(this.checked){ $(".node").each(function(){ if($(this).attr("parent_id")==_this){ $(this).prop("checked",true) } if(_parent==$(this).val()){ $(this).prop("checked",true) } }) }else { $(".node").each(function () { if ($(this).attr("parent_id") == _this) { $(this).prop("checked", false) } if (_parent == $(this).val()) { $(this).prop("checked", false) } }) } } ) })</script>
- YII2框架RBAC 实例运用
- YII2框架RBAC 自己开发(权限控制)实例运用
- Yii2 RBAC
- Yii2-权限控制RBAC-实例篇(三)
- yii2框架中写的原生的rbac权限
- YII2.0框架(五) RBAC基于角色的权限控制源码透析yii\rbac\DbManager
- Yii2 使用十三 RBAC
- yii2 rbac 详解
- YII2 RBAC用法
- yii2自带rbac
- yii2-rbac权限设置
- YII2 学习笔记-- RBAC
- yii2.0Rbac操作
- rbac框架
- yii2-rbac及yii2-admin可视化管理
- YII2-RBAC-Plus-安装篇
- yii2.0 rbac权限控制
- Yii2 rbac权限控制详解
- 排序五 归并排序
- HTML的 table 设计
- HTTPS的安全保护
- openstack安装
- 网址
- YII2框架RBAC 实例运用
- JPA @MappedSuperclass注解的使用说明
- 严重: Compilation error org.eclipse.jdt.internal.compiler.classfmt.ClassFormatException
- C#学习之路一
- C 语言资源大全总结--各种框架各种开源库,c开发必备
- python 文件名相关
- ubuntu 配置tftp 服务器
- 细说Nginx系列-- events参数说明
- Android ANR & WatchDog