權(quán)限管理(RBAC新解)

轉(zhuǎn)自:http://www.thinksaas.cn/group/topic/150841/
原文地址:http://www.katasoft.com/blog/2011/05/09/new-rbac-resource-based-access-control

本文討論以角色概念進(jìn)行的權(quán)限管理策略及主要以基于角色的機(jī)制進(jìn)行權(quán)限管理是遠(yuǎn)遠(yuǎn)不夠的。同時(shí)我將討論一種我認(rèn)為更好的權(quán)限管理方式污桦。

什么是角色

當(dāng)說到程序的權(quán)限管理時(shí)亩歹,人們往往想到角色這一概念。角色是代表一系列可執(zhí)行的操作或責(zé)任的實(shí)體,用于限定你在軟件系統(tǒng)中能做什么捆憎、不能做什么舅柜。用戶帳號(hào)往往與角色相關(guān)聯(lián),因此躲惰,一個(gè)用戶在軟件系統(tǒng)中能做什么取決于與之關(guān)聯(lián)的各個(gè)角色致份。

例如,一個(gè)用戶以關(guān)聯(lián)了”項(xiàng)目管理員”角色的帳號(hào)登錄系統(tǒng)础拨,那這個(gè)用戶就可以做項(xiàng)目管理員能做的所有事情――如列出項(xiàng)目中的應(yīng)用氮块、管理項(xiàng)目組成員、產(chǎn)生項(xiàng)目報(bào)表等诡宗。
從這個(gè)意義上來說滔蝉,角色更多的是一種行為的概念:它表示用戶能在系統(tǒng)中進(jìn)行的操作。

基于角色的訪問控制(Role-Based Access Control)

既然角色代表了可執(zhí)行的操作這一概念塔沃,一個(gè)合乎邏輯的做法是在軟件開發(fā)中使用角色來控制對(duì)軟件功能和數(shù)據(jù)的訪問蝠引。你可能已經(jīng)猜到,這種權(quán)限控制方法就叫基于角色的訪問控制(Role-Based Access Control)蛀柴,或簡(jiǎn)稱為RBAC螃概。

有兩種正在實(shí)踐中使用的RBAC訪問控制方式:隱式(模糊)的方式和顯示(明確)的方式。
今天依舊有大量的軟件應(yīng)用是使用隱式的訪問控制方式鸽疾。但我肯定的說吊洼,顯示的訪問控制方式更適合于當(dāng)前的軟件應(yīng)用。

隱式的訪問控制

前面提到制肮,角色代表一系列的可執(zhí)行的操作冒窍。但我們?nèi)绾沃酪粋€(gè)角色到底關(guān)聯(lián)了哪些可執(zhí)行的操作呢?

答案是:目前的大多數(shù)應(yīng)用豺鼻,你并能不明確的知道一個(gè)角色到底關(guān)聯(lián)了哪些可執(zhí)行操作综液。可能你心里是清楚的(你知道一個(gè)有”管理員”角色的用戶可以鎖定用戶帳號(hào)拘领、進(jìn)行系統(tǒng)配置意乓;一個(gè)關(guān)聯(lián)了”消費(fèi)者”這一角色的用戶可在網(wǎng)站上進(jìn)行商品選購(gòu))樱调,但這些系統(tǒng)并沒有明確定義一個(gè)角色到底包含了哪些可執(zhí)行的行為约素。

拿”項(xiàng)目管理員”來說,系統(tǒng)中并沒有對(duì)”項(xiàng)目管理員”能進(jìn)行什么樣的操作進(jìn)行明確定義笆凌,它僅是一個(gè)字符串名詞圣猎。開發(fā)人員通常將這個(gè)名詞寫在程序里以進(jìn)行訪問控制。例如乞而,判斷一個(gè)用戶是否能查看項(xiàng)目報(bào)表送悔,程序員可能會(huì)編碼如下:

代碼塊1. 隱式地基于角色的權(quán)限控制:

if (user.hasRole("Project Manager")){
    //show the project report button
} else {
    //don't show the button
}

在上面的示例代表中,開發(fā)人員判斷用戶是否有”項(xiàng)目管理員”角色來決定是否顯示查看項(xiàng)目報(bào)表按鈕。請(qǐng)注意上面的代碼欠啤,它并沒有明確語(yǔ)句來定義”項(xiàng)目管理員”這一角色到底包含哪些可執(zhí)行的行為荚藻,它只是假設(shè)一個(gè)關(guān)聯(lián)了項(xiàng)目管理員角色的用戶可查看項(xiàng)目報(bào)表,而開發(fā)人員也是基于這一假設(shè)來寫 if/else 語(yǔ)句洁段。

脆弱的權(quán)限策略

像上面的權(quán)限訪問控制是非常脆弱的应狱。一個(gè)極小的權(quán)限方面的需求的變動(dòng)都可能導(dǎo)致上面的代碼需要重新修改。

舉例來說祠丝,假如某一天這個(gè)開發(fā)團(tuán)隊(duì)被告知:“哦疾呻,順便說一下,我們需要一個(gè)’部門管理員’角色写半,他們也可以查看項(xiàng)目報(bào)表岸蜗。請(qǐng)做到這一點(diǎn)〉”

這種情況下璃岳,開發(fā)人員需要找到上面的代碼塊并將其修改為:

代碼塊2. 修改過的隱式的基于角色的權(quán)限控制:

if (user.hasRole("Project Manager") || user.hasRole("Department Manager")) {
    //show the project report button
} else {
    //don't show the button
}

隨后,開發(fā)人員需要更新他的測(cè)試用例悔捶、重新編譯系統(tǒng)矾睦,還可能需要重走軟件質(zhì)量控制(QA)流程,然后再重新部署上線炎功。這一切僅僅是因?yàn)橐粋€(gè)微小的權(quán)限方面的需求變動(dòng)枚冗!

后面如果需求方又回來告訴你說我們又有另一個(gè)角色可查看報(bào)表,或是前面關(guān)于”部門管理員可查看報(bào)表”的需求不再需要了蛇损,豈不把人累死了赁温。

如果需求方要求動(dòng)態(tài)地創(chuàng)建、刪除角色以便他們自己配置角色淤齐,又該如何應(yīng)對(duì)呢股囊?

像上面的情況,這種隱式的(靜態(tài)字符串)形式的基于角色的訪問控制方式難以滿足需求更啄。理想的情況是如果權(quán)限需求變動(dòng)不需要修改任何代碼稚疹。怎樣才能做到這一點(diǎn)呢?

顯式地訪問控制:更好的選擇

從上面的例子我們看到祭务,當(dāng)權(quán)限需求發(fā)生變動(dòng)時(shí)内狗,隱式的權(quán)限訪問控制方式會(huì)給程序開發(fā)帶來沉重的負(fù)擔(dān)。如果能有一種方式在權(quán)限需求發(fā)生變化時(shí)不需要去修改代碼就能滿足需求那就好了义锥。理解的情況是柳沙,即使是正在運(yùn)行的系統(tǒng),你也可以修改權(quán)限策略卻又不影響最終用戶的使用拌倍。當(dāng)你發(fā)現(xiàn)某些錯(cuò)誤的或危險(xiǎn)的安全策略時(shí)赂鲤,你可以迅速地修改策略配置噪径,同時(shí)你的系統(tǒng)還能正常使用,而不需要重構(gòu)代碼重新部署系統(tǒng)数初。

怎樣才能達(dá)到上面的理想效果呢找爱?我們可以通過顯式的(明確的)界定我們?cè)趹?yīng)用中能做的操作來進(jìn)行。

回顧上面隱式的權(quán)限控制的例子泡孩,思考一下這些代碼最終的目的缴允,想一下它們最終是要做什么樣的控制?

從根本上說珍德,這些代碼最終是在保護(hù)資源(項(xiàng)目報(bào)表)练般,是要界定一個(gè)用戶能對(duì)這些資源進(jìn)行什么樣的操作(查看/修改)。當(dāng)我們將權(quán)限訪問控制分解到這種最原始的層次锈候,我們就可以用一種更細(xì)粒度(更富有彈性)的方式來表達(dá)權(quán)限控制策略薄料。

我們可以修改上面的代碼塊,以基于資源的語(yǔ)義來更有效地進(jìn)行權(quán)限訪問控制:

代碼塊3. 顯式的權(quán)限控制:

if (user.isPermitted("projectReport:view:12345")) {
    //show the project report button
} else {
    //don't show the button
}

上面的例子中泵琳,我們可明確地看到我們是在控制什么摄职。不要太在意冒號(hào)分隔的語(yǔ)法,這僅是一個(gè)例子获列,重點(diǎn)是上面的語(yǔ)句明確地表示了“如果當(dāng)前用戶允許查看編號(hào)為12345的項(xiàng)目報(bào)表谷市,則顯示項(xiàng)目報(bào)表按鈕”。也就是說击孩,我們明確地說明了一個(gè)用戶帳號(hào)可對(duì)一個(gè)的資源實(shí)例進(jìn)行的具體的操作迫悠。

為什么說這種方式更好

上面最后的示例代碼塊與前面的代碼的主要區(qū)別:最后的代碼塊是基于什么是受保護(hù)的, 而不是誰(shuí)可能有能力做什么巩梢〈葱梗看似簡(jiǎn)單的區(qū)別,但后者對(duì)系統(tǒng)開發(fā)及部署有著深刻的影響:

  • 更少的代碼重構(gòu):我們是基于系統(tǒng)的功能(系統(tǒng)的資源及對(duì)資源的操作)來進(jìn)行權(quán)限控制括蝠,而相應(yīng)來說鞠抑,系統(tǒng)的功能需求一旦確定下來后,一段時(shí)間內(nèi)對(duì)它的改動(dòng)相應(yīng)還是比較少的忌警。只是當(dāng)系統(tǒng)的功能需求改變時(shí)搁拙,才會(huì)涉及到權(quán)限代碼的改變。例如上面提到的查看項(xiàng)目報(bào)表的功能法绵,顯式的權(quán)限控制方式不會(huì)像傳統(tǒng)隱式的RBAC權(quán)限控制那樣因不同的用戶/角色要進(jìn)行這個(gè)操作就需要重構(gòu)代碼箕速;只要這個(gè)功能存在,顯式的方式的權(quán)限控制代碼是不需要改變的礼烈。
  • 更直觀:保護(hù)資源對(duì)象弧满、控制對(duì)資源對(duì)象的操作(對(duì)象及對(duì)象的行為),這樣的權(quán)限控制方式更符合人們的思想習(xí)慣此熬。正因?yàn)榉线@種直觀的思維方式,面向?qū)ο蟮木庉嬎枷爰癛EST通信模型變得非常成功。
  • 更有彈性:上面的示例代碼中沒有寫死哪些用戶犀忱、組或角色可對(duì)資源進(jìn)行什么操作募谎。這意味著它可支持任何安全模型的設(shè)計(jì)。例如阴汇,可以將操作(權(quán)限)直接分配給用戶 数冬,或者他們可以被分配到一個(gè)角色,然后再將角色與用戶關(guān)聯(lián)搀庶,或者將多個(gè)角色關(guān)聯(lián)到組(group)上拐纱,等等。你完全可以根據(jù)應(yīng)用的特點(diǎn)定制權(quán)限模型哥倔。
  • 外部安全策略管理:由于源代碼只反映資源和行為秸架,而不是用戶、組和角色咆蒿,這樣資源/行為與用戶东抹、組、角色的關(guān)聯(lián)可以通過外部的模塊或?qū)S霉ぞ呋蚬芾砜刂婆_(tái)來完成沃测。這意味著在權(quán)限需求變化時(shí)缭黔,開發(fā)人員并不需要花費(fèi)時(shí)間來修改代碼,業(yè)務(wù)分析師甚至最終用戶就可以通過相應(yīng)的管理工具修改權(quán)限策略配置蒂破。
  • 可在運(yùn)行環(huán)境做修改:因?yàn)榛谫Y源的權(quán)限控制代碼并不依賴于行為的主體(如組馏谨、角色、用色)附迷,你并沒有將行為的主體的字符名詞寫在代碼中田巴,所以你甚至可以在程序運(yùn)行的時(shí)候通過修改主體能對(duì)資源進(jìn)行的操作這樣一些方式,通過配置的方式就可應(yīng)對(duì)權(quán)限方面需求的變動(dòng)挟秤,再也不需要像隱式的RBAC方式那樣需要重構(gòu)代碼壹哺。
RBAC新解:Resource-Based Access Control

對(duì)于上面列出的諸多好處,我重點(diǎn)要說是這種顯式的機(jī)制帶給我們的富有彈性的權(quán)限模型艘刚。

如果你仍想保留或模擬傳統(tǒng)的基于角色的權(quán)限訪問控制管宵,你可以將權(quán)限(可執(zhí)行的操作)直接分配給某個(gè)角色。這種情況下攀甚,你依舊是在使用基于角色的權(quán)限訪問控制方式(不同之處在于你需要明確地界定角色中的權(quán)限箩朴,而不是傳統(tǒng)的使用角色字符串隱式地進(jìn)行權(quán)限控制)。

但在這種新的模型下秋度,已不必再局限于角色了炸庞。你可以將權(quán)限直接分配給用戶、組或其它你覺得可以的對(duì)象荚斯。

因?yàn)樯厦骘@式地埠居、基于資源的權(quán)限訪問控制的諸多好處查牌,或許可以給RBAC一個(gè)新的定義:“Resource-Based Access Control”。只是我的一個(gè)想法:)

現(xiàn)實(shí)世界的例子:Apache Shiro

如果你好奇現(xiàn)實(shí)世界有沒有被多個(gè)系統(tǒng)使用的基于資源的權(quán)限控制框架滥壕,你可以了解一下Apache Shiro纸颜。它是一個(gè)java平臺(tái)的現(xiàn)代權(quán)限管理框架。通過它的權(quán)限(Permission)概念绎橘,Shiro很好地支持基于資源的權(quán)限訪問控制胁孙。

當(dāng)然,并不需要借用Shiro來理解本文所說的一些概念称鳞,但Shiro對(duì)理解本文所討論的概念及示例有一定的幫助涮较。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個(gè)濱河市冈止,隨后出現(xiàn)的幾起案子狂票,更是在濱河造成了極大的恐慌,老刑警劉巖靶瘸,帶你破解...
    沈念sama閱讀 211,884評(píng)論 6 492
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件苫亦,死亡現(xiàn)場(chǎng)離奇詭異,居然都是意外死亡怨咪,警方通過查閱死者的電腦和手機(jī)屋剑,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 90,347評(píng)論 3 385
  • 文/潘曉璐 我一進(jìn)店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來诗眨,“玉大人唉匾,你說我怎么就攤上這事〗吵” “怎么了巍膘?”我有些...
    開封第一講書人閱讀 157,435評(píng)論 0 348
  • 文/不壞的土叔 我叫張陵,是天一觀的道長(zhǎng)芋簿。 經(jīng)常有香客問我峡懈,道長(zhǎng),這世上最難降的妖魔是什么与斤? 我笑而不...
    開封第一講書人閱讀 56,509評(píng)論 1 284
  • 正文 為了忘掉前任肪康,我火速辦了婚禮,結(jié)果婚禮上撩穿,老公的妹妹穿的比我還像新娘磷支。我一直安慰自己,他們只是感情好食寡,可當(dāng)我...
    茶點(diǎn)故事閱讀 65,611評(píng)論 6 386
  • 文/花漫 我一把揭開白布雾狈。 她就那樣靜靜地躺著,像睡著了一般抵皱。 火紅的嫁衣襯著肌膚如雪善榛。 梳的紋絲不亂的頭發(fā)上辩蛋,一...
    開封第一講書人閱讀 49,837評(píng)論 1 290
  • 那天,我揣著相機(jī)與錄音锭弊,去河邊找鬼堪澎。 笑死擂错,一個(gè)胖子當(dāng)著我的面吹牛味滞,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播钮呀,決...
    沈念sama閱讀 38,987評(píng)論 3 408
  • 文/蒼蘭香墨 我猛地睜開眼剑鞍,長(zhǎng)吁一口氣:“原來是場(chǎng)噩夢(mèng)啊……” “哼!你這毒婦竟也來了爽醋?” 一聲冷哼從身側(cè)響起蚁署,我...
    開封第一講書人閱讀 37,730評(píng)論 0 267
  • 序言:老撾萬榮一對(duì)情侶失蹤,失蹤者是張志新(化名)和其女友劉穎蚂四,沒想到半個(gè)月后光戈,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 44,194評(píng)論 1 303
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡遂赠,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 36,525評(píng)論 2 327
  • 正文 我和宋清朗相戀三年久妆,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片跷睦。...
    茶點(diǎn)故事閱讀 38,664評(píng)論 1 340
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡筷弦,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出抑诸,到底是詐尸還是另有隱情烂琴,我是刑警寧澤,帶...
    沈念sama閱讀 34,334評(píng)論 4 330
  • 正文 年R本政府宣布蜕乡,位于F島的核電站奸绷,受9級(jí)特大地震影響,放射性物質(zhì)發(fā)生泄漏层玲。R本人自食惡果不足惜号醉,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 39,944評(píng)論 3 313
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望称簿。 院中可真熱鬧扣癣,春花似錦、人聲如沸憨降。這莊子的主人今日做“春日...
    開封第一講書人閱讀 30,764評(píng)論 0 21
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽(yáng)授药。三九已至士嚎,卻和暖如春呜魄,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背莱衩。 一陣腳步聲響...
    開封第一講書人閱讀 31,997評(píng)論 1 266
  • 我被黑心中介騙來泰國(guó)打工爵嗅, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留,地道東北人笨蚁。 一個(gè)月前我還...
    沈念sama閱讀 46,389評(píng)論 2 360
  • 正文 我出身青樓睹晒,卻偏偏與公主長(zhǎng)得像,于是被迫代替她去往敵國(guó)和親括细。 傳聞我的和親對(duì)象是個(gè)殘疾皇子伪很,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 43,554評(píng)論 2 349

推薦閱讀更多精彩內(nèi)容