成人国产在线小视频_日韩寡妇人妻调教在线播放_色成人www永久在线观看_2018国产精品久久_亚洲欧美高清在线30p_亚洲少妇综合一区_黄色在线播放国产_亚洲另类技巧小说校园_国产主播xx日韩_a级毛片在线免费

資訊專欄INFORMATION COLUMN

Yii2的RBAC實現(xiàn)

xiaoxiaozi / 1003人閱讀

摘要:一的前期準(zhǔn)備的權(quán)限管理需要知道怎么給用戶分配角色,給角色分配權(quán)限,以權(quán)限來精細(xì)化需要的操作,判斷是否有權(quán)限來操作這一步,達到管理權(quán)限的目的。若沒有則渲染不顯示數(shù)據(jù)提交更新相應(yīng)的修改或者增加。

一、RBAC的前期準(zhǔn)備

RBAC的權(quán)限管理需要知道怎么給用戶分配角色,給角色分配權(quán)限,以權(quán)限來精細(xì)化需要的操作,判斷是否有權(quán)限來操作這一步,達到管理權(quán)限的目的。
先展示下要達到的效果 :

左邊為三劍客:用戶、角色、權(quán)限;
下面為測試頁面
二、RBAC的數(shù)據(jù)表
用戶表用的是yii2-admin中migration里面的用戶表

create table `user`
(
    `id` int(11) NOT NULL AUTO_INCREMENT PRIMARY KEY,
    `username` varchar(32) NOT NULL,
    `auth_key` varchar(32) NOT NULL,
    `password_hash` varchar(256) NOT NULL,
    `password_reset_token` varchar(256),
    `email` varchar(256) NOT NULL,
    `status` integer not null default 1,
    `created_at` integer not null,
    `updated_at` integer not null,
    KEY `email` (`email`)

)ENGINE=InnoDB DEFAULT CHARSET=utf8;
CREATE TABLE `role` (
  `id` int(11) unsigned NOT NULL AUTO_INCREMENT,
  `name` varchar(50) NOT NULL DEFAULT "" COMMENT "角色名稱",
  `status` tinyint(1) NOT NULL DEFAULT "1" COMMENT "狀態(tài) 1:有效 0:無效",
  `updated_time` timestamp NOT NULL DEFAULT "0000-00-00 00:00:00" COMMENT "最后一次更新時間",
  `created_time` timestamp NOT NULL DEFAULT "0000-00-00 00:00:00" COMMENT "插入時間",
  PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COMMENT="角色表";

CREATE TABLE `permission` (
  `id` int(11) unsigned NOT NULL AUTO_INCREMENT,
  `title` varchar(50) NOT NULL DEFAULT "" COMMENT "權(quán)限名稱",
  `urls` varchar(1000) NOT NULL DEFAULT "" COMMENT "json 數(shù)組",
  `status` tinyint(1) NOT NULL DEFAULT "1" COMMENT "狀態(tài) 1:有效 0:無效",
  `updated_time` timestamp NOT NULL DEFAULT "0000-00-00 00:00:00" COMMENT "最后一次更新時間",
  `created_time` timestamp NOT NULL DEFAULT "0000-00-00 00:00:00" COMMENT "插入時間",
  PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COMMENT="權(quán)限詳情表";


CREATE TABLE `user_role` (
  `id` int(11) unsigned NOT NULL AUTO_INCREMENT,
  `uid` int(11) NOT NULL DEFAULT "0" COMMENT "用戶id",
  `role_id` int(11) NOT NULL DEFAULT "0" COMMENT "角色ID",
  `created_time` timestamp NOT NULL DEFAULT "0000-00-00 00:00:00" COMMENT "插入時間",
  PRIMARY KEY (`id`),
  KEY `uid` (`uid`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COMMENT="用戶角色表";



CREATE TABLE `role_permisson` (
  `id` int(11) unsigned NOT NULL AUTO_INCREMENT,
  `role_id` int(11) NOT NULL DEFAULT "0" COMMENT "角色id",
  `permission_id` int(11) NOT NULL DEFAULT "0" COMMENT "權(quán)限id",
  `created_time` timestamp NOT NULL DEFAULT "0000-00-00 00:00:00" COMMENT "插入時間",
  PRIMARY KEY (`id`),
  KEY `role_id` (`role_id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COMMENT="角色權(quán)限表";

三、視圖渲染部分。
將準(zhǔn)備好的頁面放到views層,在models層建立和表相對應(yīng)的文件
文件結(jié)構(gòu):
models層:

view層:

四、邏輯部分:
以角色的增加和修改、給角色增加權(quán)限為例:
1、RoleController代碼:

where([ "status" => 1 ])->orderBy(["id"=>SORT_DESC])->all();
        return $this->render("index",["roles"=>$roles]);
    }
   /*
    *方法講解:
    *編輯+新增
    *1、如果能獲取到角色的id。則從數(shù)據(jù)庫取出數(shù)據(jù)來渲染。若沒有則渲染不顯示數(shù)據(jù)
    *2、提交更新相應(yīng)的修改或者增加。同樣以id來區(qū)分
    *3、新增方法簡化還可用load()方法
    */
    public function actionEdit(){
        if (Yii::$app->request->isPost){
            //這個request方法是封裝的獲取參數(shù)的方法在后面的BaseController里面可以找到
            $id = $this->request("id",0);
            $name = $this->request("name","");
            $date_now = date("Y-m-d H:i:s");
            //驗證參數(shù)TODO:

            $role = Role::find()->where([ "id" => $id ])->one();
            if( $role ){//編輯動作
                $role = $role;
            }else{//添加動作
                $role = new Role();
                $role->status = 1;
                $role->created_time = $date_now;
            }
            $role->name = $name;
            $role->updated_time = $date_now;

            $res = $role->save(0);
            if ($res){
                return $this->redirect("/role/index");
            }
        }
        $id = $this->request("id",0);
        $role = [];
        if( $id ){
            $role = Role::find()->where([ "id" => $id ])->one();
        }
        return $this->render("edit",[
            "role" => $role
        ]);

    }
    /*
    *最重要的一步:展示權(quán)限和該角色已經(jīng)擁有的權(quán)限
    */
    public function actionSet(){
        if (Yii::$app->request->isPost){
                //實現(xiàn)保存選中權(quán)限的邏輯
            $id = $this->request("id",0);
            $permission_ids = $this->request("permission_ids",[]);

            //驗證參數(shù)TODO:

            //取出所有已分配給指定角色的權(quán)限
            $role_permission_list = RolePermission::find()->where([ "role_id" => $id ])->asArray()->all();
            $assign_permission_ids = array_column( $role_permission_list,"permission_id" );
            /**
             * 找出刪除的權(quán)限
             * 假如已有的權(quán)限集合是A,界面?zhèn)鬟f過得權(quán)限集合是B
             * 權(quán)限集合A當(dāng)中的某個權(quán)限不在權(quán)限集合B當(dāng)中,就應(yīng)該刪除
             * 使用 array_diff() 計算補集
             */
            $delete_permission_ids = array_diff( $assign_permission_ids,$permission_ids );
            if( $delete_permission_ids ){
                RolePermission::deleteAll([ "role_id" => $id,"permission_id" => $delete_permission_ids ]);
            }

            /**
             * 找出添加的權(quán)限
             * 假如已有的權(quán)限集合是A,界面?zhèn)鬟f過得權(quán)限集合是B
             * 權(quán)限集合B當(dāng)中的某個權(quán)限不在權(quán)限集合A當(dāng)中,就應(yīng)該添加
             * 使用 array_diff() 計算補集
             */
            $new_permission_ids = array_diff( $permission_ids,$assign_permission_ids );
            if( $new_permission_ids ){
                foreach( $new_permission_ids as $permission_id  ){
                    $role_permission = new RolePermission();
                    $role_permission->role_id = $id;
                    $role_permission->permission_id = $permission_id;
                    $role_permission->created_time = date("Y-m-d H:i:s");
                    $role_permission->save( 0 );
                }
            }
            return $this->redirect("/role/index");
        }
        $id = $this->request("id",0);
        //驗證數(shù)據(jù)TODO:
        $role = Role::find()->where([ "id" => $id ])->one();
        
        //取出所有的權(quán)限
        $permissions = Permission::find()->where([ "status" => 1 ])->orderBy( [ "id" => SORT_DESC ])->all();
       
       

        //取出所有已分配的權(quán)限
        $role_permission= RolePermission::find()->where([ "role_id" => $id ])->asArray()->all();
        
        $role_permission_ids = array_column( $role_permission,"permission_id" );
        return $this->render("set",[
            "role" => $role,
            "permissions" => $permissions,
            "role_permission_ids" => $role_permission_ids
        ]);

    }
}

2、由于基礎(chǔ)的增加改查都會編寫。在這里寫set模板渲染
set.php在view中的role目錄,代碼如下:

">
">

給三劍客增加、修改、刪除的核心代碼已經(jīng)結(jié)束
五、基礎(chǔ)控制器的編寫:
實現(xiàn)辨別是否有權(quán)限訪問要訪問的頁面
BaseController

checkLoginStatus();
        if ( !$login_status && !in_array( $action->uniqueId,$this->allowAllAction )  ) {
            
            $this->redirect( "/site/login" );//返回到登錄頁面
            
            return false;
        }
  
        // *
        //  * 判斷權(quán)限的邏輯是
        //  * 取出當(dāng)前登錄用戶的所屬角色,
        //  * 在通過角色 取出 所屬 權(quán)限關(guān)系
        //  * 在權(quán)限表中取出所有的權(quán)限鏈接
        //  * 判斷當(dāng)前訪問的鏈接 是否在 所擁有的權(quán)限列表中
         
        //判斷當(dāng)前訪問的鏈接 是否在 所擁有的權(quán)限列表中
       
        if( !$this->checkPrivilege( $action->getUniqueId() ) ){
            $this->redirect( "/test/forbidden");

            return false;
        }
        return true;
    }

    //檢查是否有訪問指定鏈接的權(quán)限
    public function checkPrivilege( $url ){
        //如果是超級管理員 也不需要權(quán)限判斷,這里可以根據(jù)自己需要更改
        if( Yii::$app->user->identity->id == 1 ){
            return true;
        }

        //有一些頁面是不需要進行權(quán)限判斷的
        if( in_array( $url,$this->ignore_url ) ){
            return true;
        }

        return in_array( $url, $this->getRolePrivilege( ) );
    }

    /*
    * 獲取某用戶的所有權(quán)限
    * 取出指定用戶的所屬角色,
    * 在通過角色 取出 所屬 權(quán)限關(guān)系
    * 在權(quán)限表中取出所有的權(quán)限鏈接
    */
    public function getRolePrivilege($uid = 0){
        if( !$uid){
            $uid = Yii::$app->user->identity->id;
        }

        if( !$this->privilege_urls ){
            $role_ids = UserRole::find()->where([ "uid" => $uid ])->select("role_id")->asArray()->column();
            if( $role_ids ){
                //在通過角色 取出 所屬 權(quán)限關(guān)系
                $permission_ids = RolePermission::find()->where([ "role_id" =>  $role_ids ])->select("permission_id")->asArray()->column();
                //在權(quán)限表中取出所有的權(quán)限鏈接
                $list = Permission::find()->where([ "id" => $permission_ids ])->all();
                $urls = [];
                if( $list ){
                    foreach( $list as $_item  ){
                        $tmp_urls = @json_decode(  $_item["urls"],true );
                        $urls[] = $tmp_urls;
                    }
                        $this->privilege_urls = array_merge( $this->privilege_urls,$urls );
                }
            }
        }
        return $this->privilege_urls ;
    }


    //驗證登錄是否有效,返回 true or  false
    protected function checkLoginStatus(){
        if (Yii::$app->user->isGuest){
            return false;
        }       
        return true;
    }
    public  function request($key, $def = false) {
        $result = $def;
        if(isset($key)) {
            $request = Yii::$app->getRequest();
            if($request->isGet) {
                $result = $request->get($key, $def);
            }else if($request->isPost) {
                $result = $request->post($key, $def);
            }
        }
        return $result;
    }
}

整體代碼沒有準(zhǔn)備,如有需要可以留言,準(zhǔn)備后會將鏈接寫在這里。

文章版權(quán)歸作者所有,未經(jīng)允許請勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。

轉(zhuǎn)載請注明本文地址:http://systransis.cn/yun/25601.html

相關(guān)文章

  • Yii2 restful接口方式開發(fā),權(quán)限控制(yii2-rest-rbac)

    摘要:根據(jù)修改,只是方式,這個相當(dāng)于的版本。適合用于前后端分離項目,方式提供接口,實現(xiàn)對接口的權(quán)限控制。 根據(jù)yii2-admin(https://github.com/mdmsoft/yi...)修改,yii2-admin只是web方式,這個相當(dāng)于yii2-admin的rest版本。適合用于前后端分離項目,rest方式提供接口,實現(xiàn)對接口的權(quán)限控制。項目地址:https://github....

    whataa 評論0 收藏0
  • yii2搭建完美后臺并實現(xiàn)rbac權(quán)限控制實例教程

    摘要:利用渲染后臺模板后臺的模板我們采用利用插播一曲是一個完全響應(yīng)管理模板?;诳蚣?,易定制模板。適合多種屏幕分辨率,從小型移動設(shè)備到大型臺式機。內(nèi)置了多個頁面,包括儀表盤郵箱日歷鎖屏登錄及注冊錯誤錯誤等頁面。 作者:白狼 出處:http://www.manks.top/yii2_fra... 本文版權(quán)歸作者,歡迎轉(zhuǎn)載,但未經(jīng)作者同意必須保留此段聲明,且在文章頁面明顯位置給出原文連接,否則保...

    neu 評論0 收藏0
  • RBAC筆記

    摘要:例如,系統(tǒng)中某個用戶辭職了,只需要將系統(tǒng)中該用戶的角色授權(quán)撤銷即可。 Q0.有哪些概念需要知道? 一些概念的具體定義如下 用戶(user): 和計算機系統(tǒng)交互的人(在許多設(shè)計方案中,單個用戶可能擁有多個登錄標(biāo)識(ID),這些標(biāo)識可能同時處于活躍狀態(tài),但身份驗證機制可以使多個標(biāo)識匹配到某個具體的人,即用戶對于計算機系統(tǒng)來說具有唯一性) 主體(subject): 一個代表用戶行為的計算機...

    ZweiZhao 評論0 收藏0
  • Yii2系列教程五:簡單用戶權(quán)限管理

    摘要:原文來自上一篇文章講了用戶的注冊,驗證和登錄,這一篇文章按照約定來說說之中的用戶和權(quán)限控制。探尋上面的一些列設(shè)置和代碼更改,已經(jīng)實現(xiàn)了一小部分的用戶控制登錄的用戶才能發(fā)表。 原文來自: https://jellybool.com/post/programming-with-yii2-user-access-controls 上一篇文章講了用戶的注冊,驗證和登錄,這一篇文章按照...

    livem 評論0 收藏0
  • Yii2-admin插件用法

    摘要:一安裝下載安裝二配置這里記得用單引號而不是雙引號在配置文件中用對整個項目規(guī)則限制配置完后取消這個這里是允許訪問的三創(chuàng)建數(shù)據(jù)庫上面的命令會在數(shù)據(jù)庫創(chuàng)建表和表。相關(guān)表或者執(zhí)行里的語句四地址欄加上訪問即可出現(xiàn) 一、安裝 https://github.com/mdmsoft/yii2-admin 下載安裝: composer require mdmsoft/yii2-admin 2.x-dev...

    chaos_G 評論0 收藏0

發(fā)表評論

0條評論

最新活動
閱讀需要支付1元查看
<