這篇文章主要介紹了Django集成OpenLDAP認證的實現,詳細介紹了django-auth-ldap的使用方法,小編覺得挺不錯的,現在分享給大家,也給大家做個參考。一起跟隨小編過來看看吧
本文詳細介紹了django-auth-ldap的使用方法,參數含義,並提供了示例代碼
版本說明
- Django==2.2
- django-auth-ldap==1.7.0
集成過程
Django集成LDAP認證有現成的django-auth-ldap模塊可以使用,本文也主要以這個模塊的使用爲主,先安裝模塊
pip install django-auth-ldap
然後在setting.py全局配置文件中添加如下內容就可以正常使用了:
import ldap from django_auth_ldap.config import LDAPSearch, GroupOfNamesType # Baseline configuration. AUTH_LDAP_SERVER_URI = 'ldap://ldap.ops-coffee.cn' AUTH_LDAP_BIND_DN = 'uid=authz,ou=Public,dc=ops-coffee,dc=cn' AUTH_LDAP_BIND_PASSWORD = 'CzfdX629K7' AUTH_LDAP_USER_SEARCH = LDAPSearch( 'ou=People,dc=ops-coffee,dc=cn', ldap.SCOPE_SUBTREE, '(uid=%(user)s)', ) # Or: # AUTH_LDAP_USER_DN_TEMPLATE = 'uid=%(user)s,ou=People,dc=ops-coffee,dc=cn' AUTH_LDAP_USER_ATTR_MAP = { 'first_name': 'cn', 'last_name': 'sn', 'email': 'mail', } AUTHENTICATION_BACKENDS = ( 'django_auth_ldap.backend.LDAPBackend', 'django.contrib.auth.backends.ModelBackend', )
這裏詳細解釋下上邊配置的含義:
AUTH_LDAP_SERVER_URI: LDAP服務器的地址
AUTH_LDAP_BIND_DN: 一個完整的用戶DN,用來登錄LDAP服務器驗證用戶輸入的賬號密碼信息是否正確
AUTH_LDAP_BIND_PASSWORD: BIND_DN用戶的密碼,這裏我們簡單說明下LDAP的認證邏輯以便更好的理解爲啥需要這兩個配置
Django使用AUTH_LDAP_BIND_DN和AUTH_LDAP_BIND_PASSWORD作爲用戶名和密碼登陸LDAP服務器,根據AUTH_LDAP_USER_SEARCH指定的查詢規則來查找用戶輸入的屬性(即username)的值有沒有,如果查找的條數爲0或者大於1,則返回錯誤,如果查找的條數等於1,則使用查找到的這個條目的DN和用戶輸入的密碼進行匹配驗證,成功則返回成功允許登錄,失敗則不允許登錄
AUTH_LDAP_USER_SEARCH: 可通過LDAP登錄的用戶的範圍,如上配置會去ou=People,dc=ops-coffee,dc=cn下搜索用戶是否存在
其中(uid=%(user)s)'指明瞭作爲Django的username所對應的LDAP的屬性,這裏爲LDAP用戶的uid屬性作爲Django的username
以上配置是在一個OU下查找用戶,當需要在多個OU下搜索用戶時用如下配置:
from django_auth_ldap.config import LDAPSearch, LDAPSearchUnion AUTH_LDAP_USER_SEARCH = LDAPSearchUnion( LDAPSearch( 'ou=Public,dc=ops-coffee,dc=cn', ldap.SCOPE_SUBTREE, '(uid=%(user)s)' ), LDAPSearch( 'ou=PeoPle,dc=ops-coffee,dc=cn', ldap.SCOPE_SUBTREE, '(uid=%(user)s)' ), )
AUTH_LDAP_USER_ATTR_MAP: LDAP中的用戶屬性跟Django後臺用戶屬性的對應關係,當用戶第一次登錄且驗證成功後會將LDAP中對應的用戶屬性寫入到Django的User表中
AUTHENTICATION_BACKENDS: 配置Django的後端認證列表
當Django調用auth.authenticate方法進行驗證時,Django將嘗試AUTHENTICATION_BACKENDS元組中指定的所有認證後端。如果第一個認證方法失敗了,Django將會繼續嘗試下一個,直到所有認證方式都嘗試完成
Django默認的認證後端是django.contrib.auth.backends.ModelBackend,如上配置我們添加了ldap的認證到AUTHENTICATION_BACKENDS中,那麼Django在登錄的時候就會先去LDAP服務器驗證用戶,驗證失敗後再去查詢本地數據庫的User表進行驗證,如果只希望Django驗證LDAP不驗證本地數據庫的話去掉AUTHENTICATION_BACKENDS中的ModelBackend配置即可
其他幾個django-auth-ldap的全局配置參數解釋如下:
AUTH_LDAP_ALWAYS_UPDATE_USER: 是否同步LDAP的修改,默認爲True,即當LDAP中用戶的屬性修改後用戶通過LDAP系統認證時自動同步更新到Django的User表中,如果設置爲False則不自動更新
AUTH_LDAP_CACHE_TIMEOUT: 設置LDAP認證緩存的時間
登錄驗證
上邊的配置沒有問題後就可以通過LDAP系統賬號進行登錄操作了,默認登陸邏輯及前端登錄代碼均無需修改,可以參考github的相關代碼,地址:https://github.com/ops-coffee/demo/tree/master/openldap
高級配置
所謂高級配置這裏主要是說明下django-auth-ldap
中組相關的配置,這需要對LDAP的組有一定的概念,爲了方便理解,接下來我們以實際的例子來說明
假如我們有三個組overmind、kerrigan、admin,配置如下:
# ldapsearch -LLL -x -D "uid=authz,ou=Public,dc=ops-coffee,dc=cn" -w "CzfdX629K7" -b cn=overmind,ou=Group,dc=ops-coffee,dc=cn dn: cn=overmind,ou=Group,dc=ops-coffee,dc=cn cn: overmind member: uid=sre,ou=People,dc=ops-coffee,dc=cn objectClass: groupOfNames objectClass: top
# ldapsearch -LLL -x -D "uid=authz,ou=Public,dc=ops-coffee,dc=cn" -w "CzfdX629K7" -b cn=kerrigan,ou=Group,dc=ops-coffee,dc=cn dn: cn=kerrigan,ou=Group,dc=ops-coffee,dc=cn cn: kerrigan objectClass: groupOfNames objectClass: top member: uid=u1,ou=Public,dc=ops-coffee,dc=cn member: uid=u2,ou=People,dc=ops-coffee,dc=cn
# ldapsearch -LLL -x -D "uid=authz,ou=Public,dc=ops-coffee,dc=cn" -w "CzfdX629K7" -b cn=admin,ou=Group,dc=ops-coffee,dc=cn dn: cn=admin,ou=Group,dc=ops-coffee,dc=cn cn: admin member: uid=u3,ou=Admin,dc=ops-coffee,dc=cn objectClass: groupOfNames objectClass: top
我們需要實現Django集成LDAP認證,且不允許隸屬於kerrigan分組的用戶登錄系統,如果用戶隸屬於admin分組,則需要在登錄Django時給設置爲管理員,接下來的配置將會解釋如何實現該需求
django-auth-ldap中與group有關的配置:
AUTH_LDAP_GROUP_SEARCH = LDAPSearch( 'ou=Group,dc=ops-coffee,dc=cn', ldap.SCOPE_SUBTREE, '(objectClass=groupOfNames)', ) AUTH_LDAP_GROUP_TYPE = GroupOfNamesType(name_attr='cn') # Simple group restrictions # AUTH_LDAP_REQUIRE_GROUP = 'cn=overmind,ou=Group,dc=ops-coffee,dc=cn' AUTH_LDAP_DENY_GROUP = 'cn=kerrigan,ou=Group,dc=ops-coffee,dc=cn' AUTH_LDAP_USER_FLAGS_BY_GROUP = { 'is_superuser': 'cn=admin,ou=Group,dc=ops-coffee,dc=cn', }
以上配置的詳細解釋如下:
AUTH_LDAP_GROUP_SEARCH: 搜索某個ou下的信息,與AUTH_LDAP_USER_SEARCH參數類似,這裏的ou一般指group,例如ou=Group,dc=ops-coffee,dc=cn的組目錄
AUTH_LDAP_GROUP_TYPE: 返回的組的類型,組DN的第一個屬性值,例如組DNcn=overmind,ou=Group,dc=ops-coffee,dc=cn,那麼這裏爲cn
AUTH_LDAP_REQUIRE_GROUP: 設置允許哪些組成員登錄,如果我們只允許overmind組的成員可以登錄系統的話這裏可以設置
AUTH_LDAP_REQUIRE_GROUP = 'cn=overmind,ou=Group,dc=ops-coffee,dc=cn'
AUTH_LDAP_DENY_GROUP: 設置拒絕哪些組成員登錄,如果我們不允許kerrigan組的成員可以登錄系統的話這裏可以設置
AUTH_LDAP_DENY_GROUP = 'cn=kerrigan,ou=Group,dc=ops-coffee,dc=cn'
當我們同時設置了用戶既屬於overmind組又屬於kerrigan組,也就是這個用戶即設置了允許登錄,又設置了拒絕登錄,那麼以拒絕登錄爲準,用戶無法登錄
AUTH_LDAP_USER_FLAGS_BY_GROUP: 根據LDAP的group設置Django用戶的額外屬性,例如我們想要設置LDAP中
admin組具有Django中超級管理員的權限,除了在Django中手動設置外,還可以直接在setting中配置
AUTH_LDAP_USER_FLAGS_BY_GROUP AUTH_LDAP_USER_FLAGS_BY_GROUP = { 'is_superuser': 'cn=admin,ou=Group,dc=ops-coffee,dc=cn', }
當admin組用戶登錄的時候就會自動給用戶的is_superuser屬性設置爲True
至此我們對django-auth-ldap有了一個全面的瞭解,在實際項目集成中可以做到遊刃有餘,如有問題可以參考我github的代碼
踩坑記錄
windowns 10下安裝python-ldap即django-auth-ldap報錯:
c:\users\ops-coffee\appdata\local\temp\pip-install-sec1o036\python-ldap\modules\constants.h(7): fatal error C1083: Cannot open include file: 'lber.h': No such file or directory
error: command 'C:\\Program Files (x86)\\Microsoft Visual Studio 14.0\\VC\\BIN\\x86_amd64\\cl.exe' failed with exit status 2
這個報錯需要手動安裝下whl文件,具體方法爲:
先在這個網站https://www.lfd.uci.edu/~gohlke/pythonlibs/#python-ldap下載對應版本的python-ldap的whl文件
然後使用pip命令安裝whl,注意文件路徑要正確
D:\demo\openldap>python -m pip install python_ldap-3.2.0-cp36-cp36m-win_amd64.whl Processing d:\demo\openldap\python_ldap-3.2.0-cp36-cp36m-win_amd64.whl Requirement already satisfied: pyasn1>=0.3.7 in c:\python36\lib\site-packages (from python-ldap==3.2.0) (0.4.2) Requirement already satisfied: pyasn1-modules>=0.1.5 in c:\python36\lib\site-packages (from python-ldap==3.2.0) (0.2.4) Installing collected packages: python-ldap Successfully installed python-ldap-3.2.0
以上就是本文的全部內容,希望對大家的學習有所幫助,也希望大家多多支持神馬文庫。