深入解析yii权限分级式访问控制的实现(非RBAC法)


Posted in PHP onJune 13, 2013

yii framework 提供了2套权限访问系统,一套是简单的filter(过滤器)模式,另一套是复杂全面的RBAC模式,我这里要讲的是第一套(因为我也刚刚学到这里)。如 果你有研究过YII官方的demo blog,一定知道,比如,由gii自动生成的user模块,自动附带了简单的filter权限分配功能,具体细节请参照blog手册的“用户验证”一章 节,以及yii官方指南的“验证和授权”一章节。(注意,我这里所指的模块,只是我个人对与user有关的文件的统称,与yii文件系统的模块 (module)含义不同。)
关于权限分配的文件大多在controllers里,比如打开UserController.php文件你会看到2个类函数。

public function filters() 
     { 
      return array( 
       'accessControl',               // 实现CRUD操作的访问控制。 
       'postOnly + delete', 
         ); 
     }  public function accessRules()              //这里就是访问规则的设置。 
     { 
      return array( 
         array('allow',              // 允许所有用户执行index,view动作。 
           'actions'=>array('index','view'), 
           'users'=>array('*'), <span></span>           
           ),                    
         array('allow',             // 只允许经过验证的用户执行create, update动作。 
            'actions'=>array('create','update'), 
            'users'=>array('@'),       // @号指所有注册的用户 
             ), 
         array('allow',             // 只允许用户名是admin的用户执行admin,delete动作 
             'actions'=>array('admin','delete'), 
             'users'=>array('admin'), 
             ),                   //admin就是指用户名是admin的用户,以硬编码的形式分配用户权限。 
             array('deny',           // 拒绝所有的访问。 
             'users'=>array('*'), 
             ), 
         ); 
     }

关于更多的访问规则的设定请参照官方文件http://www.yiiframework.com/doc/api/1.1/CAccessControlFilter
好了,现在要开始按照我们自己的需求设置适合自己的权限分配了。我们希望filter访问控制模式能更完美一点,按照常识,我们希望它能按照数据库里user表里不同级别用户,实行不同的授权,而不是用硬编码的形式控制。

回到demo blog,我先对数据库的tbl_user表做修改,在原来的基础上加上role一项。对原来的用户信息记录添加role的value为"管理员"或"一般用户"。
然后依次执行以下3个步骤:
1. 创建组件WebUser,它是对CWebUser的扩展。
2. 修改config/main.php文件。
3.修改accessRules()。
具体细节如下:
1.WebUser.php 组件代码:

<strong><?php  // this file must be stored in: 
 // protected/components/WebUser.php 
 class WebUser extends CWebUser { 
   // Store model to not repeat query. 
   private $_model; 
   // Return first name. 
   // access it by Yii::app()->user->first_name 
   function getFirst_Name(){ 
     $user = $this->loadUser(Yii::app()->user->id); 
     return $user->first_name; 
   } 
   // This is a function that checks the field 'role' 
   // in the User model to be equal to 1, that means it's admin 
   // access it by Yii::app()->user->isAdmin() 
   function isAdmin(){ 
     $user = $this->loadUser(Yii::app()->user->id); 
     if ($user==null) 
         return 0; 
     else 
         return $user->role == "管理员"; 
   } 
   // Load user model. 
   protected function loadUser($id=null) 
     { 
         if($this->_model===null) 
         { 
             if($id!==null) 
                 $this->_model=User::model()->findByPk($id); 
         } 
         return $this->_model; 
     } 
 } 
 ?></strong>

2.在config/main.php找到如下代码,添加标红色的代码。
   'components'=>array(
        'user'=>array(
            // enable cookie-based authentication
            'allowAutoLogin'=>true,
             'class'=>'WebUser',
        ),

3.找到需要更改权限的controller类,对accessRules()函数做修改,比如对前文的accessRules()函数做如下修改:
public function accessRules()  //这里就是访问规则的设置。     { 
     return array( 
         array('allow',                     // 允许所有用户执行index,view动作。 
             'actions'=>array('index','view'), 
             'users'=>array('*'),         //*号标识所有用户包括注册的、没注册的、一般的、管理员级的 
         ), 
         array('allow',                      // 只允许经过验证的用户执行create, update动作。 
             'actions'=>array('create','update'), 
             'users'=>array('@'),       // @号指所有注册的用户 
         ), 
         array('allow',                     // 只允许用户名是admin的用户执行admin,delete动作 
             'actions'=>array('admin','delete'), 
             'expression'=>'yii::app()->user->isAdmin()', 
             //这样只有标识为“管理员”的用户才能访问admin,delete动作 
         ), 
         array('deny',  // 拒绝所有的访问。 
             'users'=>array('*'), 
         ), 
     );

工作完成!
PHP 相关文章推荐
php访问查询mysql数据的三种方法
Oct 09 PHP
php入门之连接mysql数据库的一个类
Apr 21 PHP
php计算两个日期时间差(返回年、月、日)
Jun 19 PHP
Yii框架调试心得--在页面输出执行sql语句
Dec 25 PHP
ThinkPHP文件缓存类代码分享
Apr 22 PHP
WordPress中获取所使用的模板的页面ID的简单方法
Dec 31 PHP
thinkPHP使用pclzip打包备份mysql数据库的方法
Apr 30 PHP
yii2利用自带UploadedFile实现上传图片的示例
Feb 16 PHP
laravel如何开启跨域功能示例详解
Aug 31 PHP
PHP共享内存使用与信号控制实例分析
May 09 PHP
PHP笛卡尔积实现算法示例
Jul 30 PHP
php封装的pdo数据库操作工具类与用法示例
May 08 PHP
PHP 基于Yii框架中使用smarty模板的方法详解
Jun 13 #PHP
关于PHP二进制流 逐bit的低位在前算法(详解)
Jun 13 #PHP
php读取二进制流(C语言结构体struct数据文件)的深入解析
Jun 13 #PHP
基于PHP Socket配置以及实例的详细介绍
Jun 13 #PHP
深入php socket的讲解与实例分析
Jun 13 #PHP
PHP数据类型的总结分析
Jun 13 #PHP
如何用C语言编写PHP扩展的详解
Jun 13 #PHP
You might like
PHP中Memcache操作类及用法实例
2014/12/12 PHP
PHP实现删除字符串中任何字符的函数
2015/08/11 PHP
解决php-fpm.service not found问题的办法
2017/06/06 PHP
thinkPHP框架中执行原生SQL语句的方法
2017/10/25 PHP
JavaScript中Math对象方法使用概述
2014/01/02 Javascript
jQuery之选项卡的简单实现
2014/02/28 Javascript
jQuery使用之标记元素属性用法实例
2015/01/19 Javascript
jQuery实现多级联动下拉列表查询框
2016/01/18 Javascript
JS面向对象编程详解
2016/03/06 Javascript
SWFUpload多文件上传及文件个数限制的方法
2016/05/31 Javascript
JS实现页面数据无限加载
2016/09/13 Javascript
基于chosen插件实现人员选择树搜索自动筛选功能
2016/09/24 Javascript
ajax前台后台跨域请求处理方式
2018/02/08 Javascript
详解微信小程序实现WebSocket心跳重连
2018/07/31 Javascript
10行代码实现微信小程序滑动tab切换
2018/12/28 Javascript
简单两步使用node发送qq邮件的方法
2019/03/01 Javascript
详解使用React.memo()来优化函数组件的性能
2019/03/19 Javascript
Async/Await替代Promise的6个理由
2019/06/15 Javascript
vue项目中锚点定位替代方式
2019/11/13 Javascript
vue 将多个过滤器封装到一个文件中的代码详解
2020/09/05 Javascript
python发布模块的步骤分享
2014/02/21 Python
深入解析Python编程中super关键字的用法
2016/06/24 Python
python 实现红包随机生成算法的简单实例
2017/01/04 Python
Python实现文件信息进行合并实例代码
2018/01/17 Python
python3 打开外部程序及关闭的示例
2018/11/06 Python
Python函数递归调用实现原理实例解析
2020/08/11 Python
css3实现一款模仿iphone样式的注册表单
2013/03/20 HTML / CSS
印度在线购物网站:Paytmmall
2019/07/24 全球购物
函授教育个人学习的自我评价
2013/12/31 职场文书
秦兵马俑教学反思
2014/02/07 职场文书
一年级评语大全
2014/04/23 职场文书
大学生活动总结模板
2014/07/02 职场文书
应届毕业生自荐信
2015/03/04 职场文书
2015年度个人教学工作总结
2015/05/20 职场文书
报案材料怎么写
2015/05/25 职场文书
python scipy 稀疏矩阵的使用说明
2021/05/26 Python