auth權限認證詳細講解
一、總結
一句話總結:四表兩組關系,一個多對多(權限和用戶組之間)(多對多需要3個表),一個一對多(用戶和用戶組之間)
1、實際上使用Auth是需要4張表的(1.會員表 2.認證規則表 3.認證組表 4.認證中間表),這四張表間的圖像化關系是怎樣的?
給用戶組制定訪問規則
會員表(用戶表)---->用戶組表<---->認證規則表(規則表)
認證中間表(規則用戶組表)
2、規則表中控制規則的字段用什么好?
模塊名/控制器名/方法名
【模塊名/控制器名/方法名】或【自定義規則】 字符串類型 這里大家最好按照 模塊名/控制器/方法
3、auth權限驗證的表是給你寫好的,驗證的表的類是否給你寫好了?
官方有的:基於thinkphp5的auth權限認證擴展 - ThinkPHP框架
http://www.thinkphp.cn/extend/873.html
其實就算官方沒有給寫好,自己來寫其實也是非常簡單的
不過官方應該是寫好的,寫好的話省點事,如此而已
4、auth權限驗證中的驗證是如何實現的?
Auth類 check方法
在驗證的時候可以用 MODULE_NAME.'/'.CONTROLLER_NAME.'/'.ACTION_NAME 來自動獲取當前的 模塊名稱/控制器名稱/方法名稱例如:
$auth->check( MODULE_NAME.'/'.CONTROLLER_NAME.'/'.ACTION_NAME, 1 ) );
二、一個小白對auth的理解(轉)
轉自:忘記轉過來的地址了,抱歉抱歉
---恢復內容開始---
PS:最近需要做一個驗證用戶權限的功能,在官方和百度看了下,發現大家都是用auth來做驗證,官方有很多auth的使用教程,但是都不全面,我也提問了幾個關於auth的問題 也沒人來回答我,無奈只好一步步看代碼研究了。本人基礎不好,屬於半路出家的那種,希望我的教程大家不要見笑。 新手純屬無奈之舉。。。
廢話不多開始解密:
首先說下我使用的Thinkphp版本:ThinkPHP3.2.3完整版
auth 翻譯成中文就是認證的意思。
TP的auth類 核心版 是沒有的。完整版才有,這點大家要注意下!
1:首先打開Auth.class.php
文件位置 Thinkphp/Library/Think/Auth.class.php
2:打開Auth類文件之后我們要建Auth認證所需要的3張表了,Auth類中已經給了表所用的字段了 直接復制回來粘貼到 phpmyadmin中運行sql就可以;
Auth所用的張表如下:
//數據庫 /* -- ---------------------------- -- think_auth_rule,規則表, -- id:主鍵,name:規則唯一標識, title:規則中文名稱 status 狀態:為1正常,為0禁用,condition:規則表達式,為空表示存在就驗證,不為空表示按照條件驗證 -- ---------------------------- DROP TABLE IF EXISTS `think_auth_rule`; CREATE TABLE `think_auth_rule` ( `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT, `name` char(80) NOT NULL DEFAULT '', `title` char(20) NOT NULL DEFAULT '', `type` tinyint(1) NOT NULL DEFAULT '1', `status` tinyint(1) NOT NULL DEFAULT '1', `condition` char(100) NOT NULL DEFAULT '', # 規則附件條件,滿足附加條件的規則,才認為是有效的規則 PRIMARY KEY (`id`), UNIQUE KEY `name` (`name`) ) ENGINE=MyISAM DEFAULT CHARSET=utf8; -- ---------------------------- -- think_auth_group 用戶組表, -- id:主鍵, title:用戶組中文名稱, rules:用戶組擁有的規則id, 多個規則","隔開,status 狀態:為1正常,為0禁用 -- ---------------------------- DROP TABLE IF EXISTS `think_auth_group`; CREATE TABLE `think_auth_group` ( `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT, `title` char(100) NOT NULL DEFAULT '', `status` tinyint(1) NOT NULL DEFAULT '1', `rules` char(80) NOT NULL DEFAULT '', PRIMARY KEY (`id`) ) ENGINE=MyISAM DEFAULT CHARSET=utf8; -- ---------------------------- -- think_auth_group_access 用戶組明細表 -- uid:用戶id,group_id:用戶組id -- ---------------------------- DROP TABLE IF EXISTS `think_auth_group_access`; CREATE TABLE `think_auth_group_access` ( `uid` mediumint(8) unsigned NOT NULL, `group_id` mediumint(8) unsigned NOT NULL, UNIQUE KEY `uid_group_id` (`uid`,`group_id`), KEY `uid` (`uid`), KEY `group_id` (`group_id`) ) ENGINE=MyISAM DEFAULT CHARSET=utf8; */
PS:大家自行改成自己所需的表前綴即可;
另外要說的一點是:這3張表 大家可以可以改表名,只要字段包含Auth所需的認證字段也可以。如果你把這3張表改名了,只要在Auth的配置項中改成自己對應的表名即可。
3:3張表建好 先講下這3張表的作用 # (本人理解有限 大家勿噴) (我的表前綴為tp_)
tp_auth_rule # (rule翻譯成中文為【規則】 合起來就是認證規則)
字段概述:
id:這個不必多說 相信大家都懂得 (表主鍵,自增 ,規則ID標識)
name:認證規則 (字段保存的是你需要認證的 【模塊名/控制器名/方法名】或【自定義規則】 字符串類型 這里大家最好按照 模塊名/控制器/方法 來填寫,多個規則之間用,隔開即可,當前規則是按照你的思路來定制的,你也可以填寫一個 admin 或 * 或 guanliyuan 等!字段長度為80,不要超過這個長度就可以)
title:規則描述 這個不多講
type:tinyint類型的,如果type為1, condition字段就可以定義規則表達式。 如定義{score}>5 and {score}<100 表示用戶的分數在5-100之間時這條規則才會通過。(默認為1)
condition:當type為1時,condition字段里面的內容將會用作正則表達式的規則來配合認證規則來認證用戶
tp_auth_group # (group翻譯為中文為 【組】的意思,合起來就是認證組)
字段概述:
id:這個大家都懂得吧(認證組的ID標識,表主鍵 自增)
title:認證組名稱
status:是否開啟 0為關閉 1為開啟 (默認為1 開啟)
rules :規則ID (這里填寫的是 tp_auth_rule里面的規則的ID,下面會給大家演示)
tp_auth_group_access(這個表就倆字段,是規則和組別的中間表)
字段概述:
uid:會員ID (這里填寫是 需要認證的會員ID)
group_id:認證組ID (這里填寫的是 認證組的ID)
Ps:這里跟大家說下我是怎么理解這3張表的關系的:
實際上使用Auth是需要4張表的(1.會員表 2.認證規則表 3.認證組表 4.認證中間表),我表達能力不強,簡單的說下:
a.我在 tp_auth_rule里面添加一個或多個驗證規則用來驗證你的訪問權限
例如:
(Admin/Article/Add)增加文章的權限
(Admin/Article/Edit)修改文章的權限
(Admin/Article/Delete)刪除文章的權限
Ps:這3個規則可以合並成一個規則,合並成一個規則的話就是: (Admin/Article/Add,Admin/Article/Edit,Admin/Article/Delete)!
多個規則用逗號隔開
還有一點:這個規則是80個字節,大家不要超過了; 這個規則你也可以寫成 Article (意思就是擁有所有操作文章的權限)
也可以寫成(Article-Add-Edit-Delete)這樣的 意思是擁有文章的增刪改權限
還可以寫成(Article-Add-Edit)扎樣的 意思是 擁有文章的增加和修改的權限,沒有刪除權限
總之這里的規則你可以按照自己的思路來,很靈活的。這點超級贊!
b.在認證組中 添加2個用戶組(分別是:信息錄入部門、信息審核部門,信息XX部門)
status 默認為就行,默認為1 就是開啟這個認證組
rules 規則ID多個規則用,隔開 例如我現在有4條規則分別是:
id為1: Admin/Article/Add 增加文章的權限
id為2: Admin/Article/Edit 修改文章的權限
id為3: Admin/Article/Delete 刪除文章的權限
id為4: Article-Add-Edit-Delete 擁有文章的增刪改權限
分析下:信息錄入部 需要的是 文章的 增加和修改還有刪除權限,審核部門需要的是 修改和刪除的權限 ,信息xx部門需要所有操作信息的權限
根據分析 :
信息錄入部門的 rules需要的規則為: 1,2,3
信息審核部門需要的是:2,3
信息XX部門需要的是 4
好了,插入數據:
信息錄入部: title:信息錄入部 rules:1,2,3 (插入之后假設ID為1)
信息審核部: title:信息審核部 rules: 2,3 (插入之后建設ID為2)
信息XX部 : title:信息XX部 rules:4 (插入之后建設ID為3)
c.認證中間表中錄入需要認證的會員ID和認證組ID即可
ps:假設我現在有會員表為tp_user
里面有4個會員分別是:
id為1的: 小紅
id為2的: 小明
id為3的: 小張
id為4的: 小李
下面分配權限:
小紅和小明是信息錄入部門的:
那么tp_auth_access如下:
uid為 1 的小紅 所屬認證部為 1(1也就是認證組表中的信息錄入部門,擁有增加、修改、刪除的權限)
uid為 2 的小明 同小紅一個級別(功能一樣)
uid為 3 的小張 所屬認證部為 2 (2也就是認證組表中的信息審核部,擁有修改、刪除的權限)
uid為 4 的小李 所屬認證部為 3 (3也就是認證表中的信息XX部 擁有信息的 增加、修改、刪除的權限)
PS:可能我說的有點繞,但是意思差不多就這樣 嘿嘿! rule表中為所有需要認證的規則條件,group表為部門組,部門的權限為規則表中的規則id,access表為記錄用戶屬於那個部門的! 這樣理解了么?
4:現在開始認證權限吧:
Ps:這里我要糾正一點:我現在用的Thinkphp版本為ThinkPHP3.2.3完整版:在Auth類中有這么一段話:
/**
* 權限認證類
* 功能特性:
* 1,是對規則進行認證,不是對節點進行認證。用戶可以把節點當作規則名稱實現對節點進行認證。
* $auth=new Auth(); $auth->check('規則名稱','用戶id')
* 2,可以同時對多條規則進行認證,並設置多條規則的關系(or或者and)
* $auth=new Auth(); $auth->check('規則1,規則2','用戶id','and')
* 第三個參數為and時表示,用戶需要同時具有規則1和規則2的權限。 當第三個參數為or時,表示用戶值需要具備其中一個條件即可。默認為or
* 3,一個用戶可以屬於多個用戶組(think_auth_group_access表 定義了用戶所屬用戶組)。我們需要設置每個用戶組擁有哪些規則(think_auth_group 定義了用戶組權限)
*
* 4,支持規則表達式。
* 在think_auth_rule 表中定義一條規則時,如果type為1, condition字段就可以定義規則表達式。 如定義{score}>5 and {score}<100 表示用戶的分數在5-100之間時這條規則才會通過。
*/
有問題的是這一句:
2,可以同時對多條規則進行認證,並設置多條規則的關系(or或者and)
$auth=new Auth(); $auth->check('規則1,規則2','用戶id','and');
問題:
Auth類中的check方法一共有 5 個參數
public function check($name, $uid, $type=1, $mode='url', $relation='or')
所以官方類中的 第三個參數填寫and視距上是不起任何作用的!
不知道是不是這樣 哈!。。。。
Ps:在使用auth之前,要先配置下auth所用的配置項:
如果你沒修改auth_rule,auth_group,auth_group_access表名稱的話,只要配置你的會員表即可。在配置項中增加以下配置項:
//Auth配置 'AUTH_CONFIG' => array( // 用戶組數據表名 //'AUTH_GROUP' => 'tp_group', // 用戶-用戶組關系表 //'AUTH_GROUP_ACCESS' => 'tp_group_access', // 權限規則表 //'AUTH_RULE' => 'tp_rule', // 用戶信息表 'AUTH_USER' => 'tp_admin' ),
還要補充一點,會員表中會員ID必須為主鍵!
我現在在Home/Login/Index下做實驗:
先聲明Auth類:
<?php namespace Home\Controller; class LoginController extends \Think\Controller{ public function IndexAction(){ //聲明Auth認證類 $auth = new \Think\Auth(); /* 驗證單個條件 驗證 會員id 為 1 的 小紅是否有 增加信息的權限 check方法中的參數解釋: 參數1:Admin/Article/Add 假設我現在請求 Admin模塊下Article控制器的Add方法 參數2: 1 為當前請求的會員ID */ var_dump( $auth->check( 'Admin/Article/Add', 1 ) ); // boolean true /* 同時驗證多個條件 驗證 會員id 為 1 的小紅是否有增加信息,修改信息 和一個不存在的規則 的權限 參數解釋: 參數1:多條規則同時驗證 , 驗證是否擁有增加、修改、刪除的權限 參數2:當前請求的會員ID ps :XXX是一個不存在的規則為什么會返回真呢? 因為check方法 第5個參數默認為 or 也就是說 多個規則中只要滿足一個條件即為真 */ //var_dump( $auth->check( 'Admin/Article/Add,Admin/Article/Edit,Admnin/Article/Xxx', 1 ) ); // boolean true /* 同時驗證多個條件 並且 都為真 驗證 會員id 為 1 的小紅是否具有 增加 修改 刪除 的權限 參數解釋 參數1:多條規則同時驗證 ,驗證是否擁有 增加 修改 刪除的權限 參數2:當前請求的會員ID 參數3:是否用正則驗證condition中的內容 參數4: 參數5:必須滿足全部規則才通過 */ //var_dump( $auth->check( 'Admin/Article/Add,Admin/Article/Edit,Admin/Article/Xxx', 1, 1, '', 'and' ) ); //boolean false } } ?>
Ps:上面的例子是最基本的認證,當然朋友們可以自己定義自己的驗證規則
下面說一下其他例子:
rule規則表中的name可以寫 *** 或者 admin 或其他字符來代替一個通用驗證規則;
在驗證的時候可以用 MODULE_NAME.'/'.CONTROLLER_NAME.'/'.ACTION_NAME 來自動獲取當前的 模塊名稱/控制器名稱/方法名稱例如:
$auth->check( MODULE_NAME.'/'.CONTROLLER_NAME.'/'.ACTION_NAME, 1 ) );
還有一些我沒了解的使用方法:
例如:
if ($mode=='url' && $query!=$auth ) { parse_str($query,$param); //解析規則中的param $intersect = array_intersect_assoc($REQUEST,$param); $auth = preg_replace('/\?.*$/U','',$auth); if ( in_array($auth,$name) && $intersect==$param ) { //如果節點相符且url參數滿足 $list[] = $auth ; } }
這里的$query!=$anth 不知道怎么用這個,我本地測試的時候在rule規則中增加了一個規則是 test?aa=1&bb=2
在使用auth的時候這樣用可以通過認證:
url中get或者POST必須有這個aa=1&bb=2才會驗證成功,很迷糊這里到底是怎么個情況,有了解的大神希望告知下
$auth->check( 'test' , 1 );
*難道這個 query!=auth 是為了不支持pathinfo的 ?module=home&controller=user&action=login 驗證這樣的?搞不懂。。。*
Ps:你可以寫一個公共方法,把auth認證寫到方法里面 方便調用!
一個小白對auth的理解
---恢復內容結束---