如何基于Python建設企業(yè)認證和權限控制平臺
原創(chuàng)【51CTO.com原創(chuàng)稿件】企業(yè)內網(wǎng),建立在企業(yè)內部,為員工提供信息的共享和交流,為業(yè)務提供運營和管理的支撐,已是當今企業(yè)信息化建設必不可少的一個項目。隨著企業(yè)的規(guī)模越來越大,業(yè)務越來越廣,系統(tǒng)建設就顯得尤為重要。
統(tǒng)一認證系統(tǒng)是企業(yè)內網(wǎng)系統(tǒng)建設的基礎,主要實現(xiàn)用戶管理、身份認證、權限管理和單點登錄等功能,以解決企業(yè)內網(wǎng)系統(tǒng)建設過程中用戶定義模糊、用戶身份組織零亂、交叉權限管理和應用系統(tǒng)出口多樣性等棘手的問題。
基于此,五阿哥運維技術團隊基于Python建設了統(tǒng)一認證(BUC:Back User Center)和權限控制(ACL:Access Control List)平臺,這個系統(tǒng)技術架構圖如下:
一、 系統(tǒng)的功能
1.用戶管理
在企業(yè)中,每個用戶都有一個唯一的賬號進行登錄,用戶的賬號和個人身份信息(包含姓名、郵件等公共屬性)會集中保存在內網(wǎng)統(tǒng)一認證系統(tǒng)里。但對于同一個用戶在外部系統(tǒng)中的賬號,如微信、釘釘、Tower等第三方系統(tǒng),統(tǒng)一認證系統(tǒng)也可以通過定時同步或實時查詢等方式獲取到用戶的信息。
2.安全管理
對于保存在企業(yè)內網(wǎng)中的用戶賬號進行認證是比較方便的,對于保存在外部系統(tǒng)中的用戶賬號,可以通過定時同步或實時驗證等方式來驗證用戶的鑒權,最終統(tǒng)一以唯一的身份使用戶登錄進入系統(tǒng)。
同時,企業(yè)內部存在多個不同的業(yè)務應用,以所有應用均接入統(tǒng)一認證平臺為基礎,各個業(yè)務系統(tǒng)的用戶認證采用單點登錄認證模式,一次登錄即可在各個業(yè)務子系統(tǒng)中完成自動認證并獲得相關授權。
3.應用管理
不同的業(yè)務系統(tǒng)會對用戶進行不同的角色劃分,不同的角色又會劃分出細粒度的權限。角色權限在統(tǒng)一認證系統(tǒng)中保存,在一個地方就可以完成用戶授權信息的設定。
4.系統(tǒng)接入
支持各種技術棧的系統(tǒng)接入,包含Java和Python等,其中各技術棧的SDK可以在Github項目中找到。
5.三方應用
第三方應用,包含郵箱,VPN,無線等直接進行SSO登錄。
6.系統(tǒng)監(jiān)控
對系統(tǒng)運行、操作、會話進行監(jiān)控,保障在受到外部或者內部攻擊時,能夠及時發(fā)現(xiàn),進行實例回溯。
7.系統(tǒng)審計
對平臺所有操作進行審計,在出現(xiàn)系統(tǒng)權限錯亂或者安全問題的時候,對平臺操作進行審計。
二、 系統(tǒng)架構設計
1.接口設計
企業(yè)內網(wǎng)的統(tǒng)一認證平臺建議基于B/S模式設計,后端使用Django框架以快速開發(fā),用DB+LDAP方式完成用戶各類信息的存儲,保障存儲和查詢效率。 統(tǒng)一認證的核心問題是鑒權中心和各子系統(tǒng)之間的通信接口問題,用戶認證接口協(xié)議可以基于標準化HTTP/HTTPS方式實現(xiàn),并對外提供不同語言的SDK(如Python CAS庫、Java Web過濾器等),使得第三方業(yè)務系統(tǒng)的接入不完全依賴于特定的開發(fā)環(huán)境。
2.安全設計
對于接入系統(tǒng),認證中心接口協(xié)議調用采用HTTPS傳輸?shù)姆绞剑ㄐ虐踩珕栴}將轉化到HTTPS傳輸?shù)陌踩詥栴}上,而對于HTTPS通道的攻擊,可以由單獨的網(wǎng)絡掃描模塊專門負責監(jiān)控。
對于統(tǒng)一認證和SSO接口參數(shù)的信息安全,一方面網(wǎng)站可采用專有加密算法對參數(shù)內容進行加密,另一方面,可以采用IP認證策略來保證對接口雙方的信任,系統(tǒng)通過通道安全和信息加密雙保險的措施來保證統(tǒng)一認證體系的接口安全。
同時系統(tǒng)配有全方面的應用監(jiān)控和訪問日志的審計,當機器發(fā)生異常情況或日志審計檢測到有可疑入侵行為時,會自動以多種方式通知到運維工程師和相關負責人。
三、 BUC使用技術和實現(xiàn)
1.用戶管理
通常在企業(yè)中,每個用戶擁有一個唯一的身份標識,即用戶名。同時用戶在其他內網(wǎng)或外部應用也存在著對應的用戶,如果能使用同一個用戶身份最為方便;獨立的用戶可以通過關聯(lián)不同的系統(tǒng)的用戶使之對外呈現(xiàn)為一個用戶。用戶可以在不同的應用系統(tǒng)中使用,這一切的基礎是有一個中央的系統(tǒng)來保存和管理這些用戶。常見的解決方案有Windows活動目錄和LDAP。
(1)Windows活動目錄域服務
使用 Active Directory(R) 域服務 (AD DS) 服務器角色,可以創(chuàng)建用于用戶和資源管理的可伸縮、安全及可管理的基礎機構,并可以提供對啟用目錄的應用程序(如 Microsoft(R) Exchange Server)的支持。
圖-1:AD的功能,來自微軟的介紹
AD DS 提供了一個分布式數(shù)據(jù)庫,該數(shù)據(jù)庫可以存儲和管理有關網(wǎng)絡資源的信息,以及啟用了目錄的應用程序中特定于應用程序的數(shù)據(jù)。 運行 AD DS 的服務器稱為域控制器。 管理員可以使用 AD DS 將網(wǎng)絡元素(如用戶、計算機和其他設備)整理到層次內嵌結構。內嵌層次結構包括 Active Directory 林、林中的域以及每個域中的組織單位 (OU)。
域模式的最大好處就是單一的網(wǎng)絡登錄能力,用戶只要在域中有一個賬戶,就可以在整個網(wǎng)絡中漫游。活動目錄服務增強了信任關系,擴展了域目錄樹的靈活性。活動目錄把一個域作為一個完整的目錄,域之間能夠通過一種基于Kerberos認證的可傳遞的信任關系建立起樹狀連接,從而使單一賬戶在該樹狀結構中的任何地方都有效,這樣在網(wǎng)絡管理和擴展時就比較輕松。
同時,活動目錄服務把域又詳細劃分成組織單元。組織單元是一個邏輯單元,它是域中一些用戶和組、文件與打印機等資源對象的集合。組織單元中還可以再劃分下級組織單元,下級組織單元能夠繼承父單元的訪問許可權。每一個組織單元可以有自己單獨的管理員并指定其管理權限,它們都管理著不同的任務,從而實現(xiàn)了對資源和用戶的分級管理。活動目錄服務通過這種域內的組織單元樹和域之間的可傳遞信任樹來組織其信任對象,為動態(tài)活動目錄的管理和擴展帶來了極大的方便。
(2)LDAP技術
輕型目錄存取協(xié)定(英文:Lightweight Directory Access Protocol,縮寫:LDAP)是一個開放的,中立的,工業(yè)標準的應用協(xié)議,通過IP協(xié)議提供訪問控制和維護分布式信息的目錄信息。
目錄服務在開發(fā)內部網(wǎng)和與互聯(lián)網(wǎng)程序共享用戶、系統(tǒng)、網(wǎng)絡、服務和應用的過程中占據(jù)了重要地位。例如,目錄服務可能提供了組織有序的記錄集合,通常有層級結構,例如公司電子郵件目錄。同理,也可以提供包含了地址和電話號碼的電話簿。
圖-2:LDAP目錄樹圖示,來自網(wǎng)絡
LDAP協(xié)議是跨平臺的和標準的協(xié)議,因此應用程序就不用為LDAP目錄放在什么樣的服務器上操心了。實際上,LDAP得到了業(yè)界的廣泛認可,因為它是Internet的標準。廠商都很愿意在產品中加入對LDAP的支持,因為他們根本不用考慮另一端(客戶端或服務端)是怎么樣的。
LDAP服務器可以是任何一個開放源代碼或商用的LDAP目錄服務器(或者還可能是具有LDAP界面的關系型數(shù)據(jù)庫),因為可以用同樣的協(xié)議、客戶端連接軟件包和查詢命令與LDAP服務器進行交互。
與LDAP不同的是,如果軟件廠商想在軟件產品中集成對DBMS的支持,那么通常都要對每一個數(shù)據(jù)庫服務器單獨定制。不像很多商用的關系型數(shù)據(jù)庫,你不必為LDAP的每一個客戶端連接或許可協(xié)議付費。大多數(shù)的LDAP服務器安裝起來很簡單,也容易維護和優(yōu)化。
(3)用戶管理實踐
根據(jù)國內企業(yè)辦公網(wǎng)絡的實際情況,用戶計算機通常為Windows系統(tǒng),通通接入到Windows活動目錄中進行管理。而且Windows活動目錄兼容LDAP協(xié)議,我們使用活動目錄作為統(tǒng)一保存用戶信息的中央系統(tǒng),再通過LDAP協(xié)議使用程序訪問域控制器將用戶信息同步到統(tǒng)一認證服務器中。
圖-3:企業(yè)內部系統(tǒng)基本結構
由上圖架構所示,一方面常見的辦公系統(tǒng)(如代碼倉庫、Wiki等)自身即支持LDAP認證,通過配置Windows AD中的目錄/用戶搜索規(guī)則即完成對登錄用戶的認證;另一方面自行開發(fā)的業(yè)務系統(tǒng)通過中央認證服務器提供的接口間接的對Windows AD進行登錄用戶的認證,即一個用戶,一套密碼,在多個系統(tǒng)中都可使用。
- # auth.py
- class ActiveDirectoryAuthenticationBackEnd:
- def authenticate(self, username, password, request=None):
- if not username or not password:
- return None
- try:
- # 建立同域控的連接
- server = Server(settings.AD_SERVER_NAME, use_ssl=True)
- # 驗證用戶使用的用戶名和密碼
- conn = Connection(server, "%s\\%s" % (settings.AD_DOMAIN, username), password, auto_bind=True, authentication=NTLM)
- # 認證通過,返回系統(tǒng)中注冊的用戶,不存在則創(chuàng)建
- user = conn.bound and self.get_or_create_user(username, conn) or None
- return user
- except LDAPBindError:
- return None
- def get_or_create_user(self, username, conn=None):
- try:
- user = User.objects.get(username=username)
- except User.DoesNotExist:
- if conn is None:
- return None
- # 從域控向中央認證系統(tǒng)中同步注冊一個新用戶
- if conn.search(USER_BASE_DN, "(sAMAccountName=%s)" % username, SUBTREE, attributes=["sn", "givenName"]):
- result = conn.response[0]["attributes"]
- user = User(username=username)
- user.first_name = result["givenName"]
- user.last_name = result["sn"]
- user.email = "%s@%s" % (username, settings.AD_EMAIL_HOST)
- user.save()
- else:
- return None
- return user
2.身份認證
(1)通過外部應用認證
外部應用,如即時通訊軟件釘釘?shù)龋@些應用存有單獨的一套用戶憑證,通過應用提供的免登服務,將應用中的用戶與統(tǒng)一認證服務器中的用戶進行一一對應,當用戶在外部應用中登錄后,自動獲得在企業(yè)內應用的已登錄狀態(tài)。
(2)通過TOTP動態(tài)驗證碼認證
OTP (One-Time Password) ,一次性密碼,也稱動態(tài)口令。它是使用密碼技術實現(xiàn)在客戶端和服務器之間共享秘密的一種認證技術,是一種強認證技術,是增強目前靜態(tài)口令認證的一種非常方便的技術手段,是一種重要的雙因素認證技術。
TOTP (Time-base One-Time Password) ,基于時間的一次性密碼,也稱時間同步的動態(tài)密碼。當在一些用戶不方便輸入密碼或者忘記密碼的場景中,我們可以使用TOTP進行認證。服務器和用戶各自保管共同的密鑰,通過比對基于時間分片與哈希計算出的動態(tài)數(shù)字驗證碼即可完成對用戶身份的認證。主流實現(xiàn)為Google Authenticator(Google身份驗證器),阿里的身份寶也兼容該算法。
圖-4:TOTP算法圖示
(3)雙因子認證
雙因子認證(Two-Factor Authentication)是指結合密碼以及實物(信用卡、SMS手機、令牌或指紋等生物標志)兩種元素對用戶進行認證的方法。
圖-5:動態(tài)驗證碼流程圖示
結合上面使用的TOTP驗證碼,對于安全級別較高的應用或資源路徑、或是系統(tǒng)探測到風險較高的操作時,即可以對用戶重定向至雙因子認證頁面,進一步保障系統(tǒng)安全。
3.單點登錄
主要實現(xiàn)方式:
(1)共享 cookie
利用同一域名下的cookie共享為基礎,將session id寫入共享cookie,在實現(xiàn)了后臺session共享存儲和訪問后,不同的應用之間即實現(xiàn)了單點登錄。
(2)Broker-based (基于經(jīng)紀人)
在一個基于經(jīng)紀人的 SSO 解決方案中,有一個集中的認證和用戶帳號管理的服務器。經(jīng)紀人能被用于進一步請求的電子的身份存取。中央數(shù)據(jù)庫的使用減少了管理的代價,并為認證提供一個公共和獨立的"第三方"。例如 Kerberos 、 Sesame 、 IBM KryptoKnight (憑證庫思想 ) 等。
(3)Agent-based(基于代理人)
在這種解決方案中,有一個自動地為不同的應用程序認證用戶身份的代理程序。這個代理程序需要設計有不同的功能。比如,它可以使用口令表或加密密鑰來自動地將認證的負擔從用戶移開。代理人被放在服務器上面,在服務器的認證系統(tǒng)和客戶端認證方法之間充當一個 " 翻譯 " ,例如 SSH 等。
(4)Token-based
口令認證,比如 FTP 、郵件服務器的登錄認證,這是一種簡單易用的方式,實現(xiàn)一個口令在多種應用當中使用。
- 基于網(wǎng)關
- 基于 SAML
- Ticket-based(基于票據(jù))
4.BUC實踐
在我們的內網(wǎng)應用中,最終選擇了CAS協(xié)議作為單點登錄的方案。CAS(Central Authentication Service)是 Yale 大學發(fā)起的一個企業(yè)級的、開源的項目,旨在為 Web 應用系統(tǒng)提供一種可靠的單點登錄解決方法。CAS開始于2001年,并在2004年12月正式成為JA-SIG的一個項目。
CAS的主要特點有:
- 開源
- 支持多種認證機制:Active Directory、JAAS、JDBC、LDAP、X.509等
- 安全策略:使用票據(jù)(Ticket)來實現(xiàn)支持的認證協(xié)議
- 支持授權:可以決定哪些服務可以請求和驗證服務票據(jù)
- 提供高可用性
- 支持多種客戶端及SDK: Java, .Net,PHP,Python,nodejs 等
- 服務端也有多種語言實現(xiàn)
(1)登錄驗證流程
圖-6:用戶、CAS客戶端、服務端三方交互過程
- # urls.py
- # 在配置文件中將/cas 路徑掛載至根路徑,即可通過/cas/login來訪問中央認證頁面,后臺的認證過程會通過已有的認證服務進行
- urlpatterns = [
- ……
- url(r"^cas/", include("mama_cas.urls", namespace="cas")),
- ……
- ]
(2)安全擴展
當CAS服務端完成了對用戶和CAS客戶端的驗證之后,CAS服務端將驗證后的用戶信息傳輸給CAS客戶端(目標應用),同時也可根據(jù)配置返回該應用下的附屬用戶信息,如用戶擁有的該應用下的角色、權限和屬性。目標應用根據(jù)服務器返回的用戶信息進一步檢查用戶可訪問的資源,適當?shù)恼故緲I(yè)務視圖。
- # settings.py
- MAMA_CAS_SERVICES = [
- {
- 'SERVICE': '.*',
- 'CALLBACKS': [
- 'base.cas_callbacks.user_profile_attributes',
- 'security.cas_callbacks.user_security_attributes',
- # 按需加入回調函數(shù)
- ]
- }
- ]
- # user_profile_attributes
- # 返回用戶的基本信息
- def user_profile_attributes(user, service):
- return {
- “username”: get_username(user),
- “name”: get_display_name(user)
- }
- # user_security_attributes.py
- # 返回用戶在該業(yè)務/服務中擁有的角色、權限和訪問路徑信息
- def user_security_attributes.py(user, service):
- return {
- “roles”: get_roles(service, user),
- “permissions”: get_permissions(service, user),
- “urls”: get_urls(service, user)
- }
四、ACL使用技術和實現(xiàn)
在現(xiàn)代企業(yè),尤其是互聯(lián)網(wǎng)企業(yè)中,產品業(yè)務繁多,對數(shù)據(jù)安全、訪問控制都提出了很高的要求,基于用戶組織結構、匯報線等傳統(tǒng)的分組模式已經(jīng)無法適應和滿足多變的互聯(lián)網(wǎng)扁平化管理模式的需要,因此我們選擇了基于角色和權限的動態(tài)分組來設計和實現(xiàn)企業(yè)中不用應用可以共享的安全訪問管理系統(tǒng)。
1.權限
權限是針對資源和操作層面的最小安全訪問控制單元,例如:
- 按資源分,可以設置訪問設備A、訪問設備B等。
- 按操作分,可以設置讀取文件,寫入文件等。
例-1:權限分類示意圖
2.角色
角色是針對應用使用者來設置的,可分為管理員、技術人員,普通用戶等,也可按區(qū)域分為華北員工、華南員工等。
角色是一系列權限的集合,擁有某角色的用戶即應當自動擁有該角色下包含的權限。
圖-7:角色與權限關系示意圖
3.屬性
屬性是針對用戶層面下設置的獨立的安全設置,用來擴展和實現(xiàn)更細粒度的自定義安全設置數(shù)據(jù),如將可訪問數(shù)據(jù)細化到數(shù)據(jù)庫中的表、數(shù)據(jù)表中的行、列上。
得益于JSON的兼容性,可以很靈活的存儲下這些自定義的結構化數(shù)據(jù)。
例-2:用戶屬性示意圖
4.ACL實踐
1.數(shù)據(jù)庫建模
依模型圖可以看出,一個應用可劃分多個角色、權限、路徑和屬性,其中角色又可包含同應用下的權限和路徑。一個用戶對應一個ACL,通過將不同的控制單元授予用戶,即可完成用戶的訪問控制配置。
2.配套功能設計
為了使訪問控制的整套機制良好的運轉起來,相關輔助和配套的功能也是不可缺少的,這里列舉一些我們已經(jīng)投入使用的功能:
(1) 應用授權的分級、分組管理
不用業(yè)務應用的負責人可以分別對自己負責的業(yè)務進行授權管理,不會產生沖突和越權。
(2)應用菜單可見性、可訪問性的集成
業(yè)務應用中的各子功能可以和預先設置的權限一對一或一對多映射,具有相應權限的用戶才可以訪問和使用相應的功能,前后臺設置保持同步。
(3)應用下角色權限申請?zhí)峤弧⑹跈嘧兏⑹跈嗤瓿傻茸詣踊鞒?/strong>
基本的權限審批流減小了業(yè)務應用負責人和使用者之間的溝通成本,同時也記錄了權限獲取的記錄,為日后的安全審計提供了可查的數(shù)據(jù)。
(4)應用訪問日志收集、分析、審計、報警等
應用訪問日志記錄了更為詳細的用戶訪問和操作記錄,為安全審計提供了更完備的數(shù)據(jù)支持,同時也支持以一定的邏輯來分析和發(fā)現(xiàn)潛在的安全泄露風險。
五、總結
本文總結介紹了針對企業(yè)內網(wǎng)門戶的統(tǒng)一用戶管理、認證和授權管理的系統(tǒng)的組成部分和常見實現(xiàn)方法。使用開源CAS產品搭建的統(tǒng)一身份認證系統(tǒng)和定制化開發(fā)的安全訪問控制系統(tǒng)在企業(yè)內網(wǎng)平臺上得到了很好地實踐和應用,各部門的業(yè)務系統(tǒng)也已穩(wěn)定接入并使用,目前運行良好。隨著系統(tǒng)規(guī)模和業(yè)務的增長,這一套平臺仍可能會面臨新的問題和挑戰(zhàn),這也使得我們在收集用戶反饋的同時不斷的進行重構和增強,以保障企業(yè)業(yè)務的穩(wěn)定發(fā)展。
項目地址:
https://github.com/cangelzz/cas-demo-django-server
https://github.com/cangelzz/cas-demo-flask-client
https://github.com/cangelzz/cas-demo-java-client
作者簡介:
程曉飛,高級全棧開發(fā)工程師 。2016年加入五阿哥鋼鐵電商平臺(wuage.com),曾供職于知名500強外企,精通Python,Java等多種編程語言及軟件開發(fā)技術,在企業(yè)內部Web系統(tǒng)、自動化工具開發(fā)方面有多年經(jīng)驗。
最后給自己代個鹽~~歡迎大家有空時翻下我牌子(知乎專欄“開發(fā)運維”https://zhuanlan.zhihu.com/idevops),看看之前的文章,再點個贊唄,順便關注下。
【51CTO原創(chuàng)稿件,合作站點轉載請注明原文作者和出處為51CTO.com】

































