python + ldap을 사용하여 Active Directory에 대한 인증


89

Python + LDAP를 사용하여 AD에 대해 어떻게 인증합니까? 나는 현재 python-ldap 라이브러리를 사용하고 있으며 그것이 생산하는 것은 눈물뿐입니다.

간단한 쿼리를 수행하기 위해 바인딩 할 수도 없습니다.

import sys
import ldap


Server = "ldap://my-ldap-server"
DN, Secret, un = sys.argv[1:4]

Base = "dc=mydomain,dc=co,dc=uk"
Scope = ldap.SCOPE_SUBTREE
Filter = "(&(objectClass=user)(sAMAccountName="+un+"))"
Attrs = ["displayName"]

l = ldap.initialize(Server)
l.protocol_version = 3
print l.simple_bind_s(DN, Secret)

r = l.search(Base, Scope, Filter, Attrs)
Type,user = l.result(r,60)
Name,Attrs = user[0]
if hasattr(Attrs, 'has_key') and Attrs.has_key('displayName'):
  displayName = Attrs['displayName'][0]
  print displayName

sys.exit()

이것을 실행하면 myusername@mydomain.co.uk password username두 가지 오류 중 하나가 발생합니다.

Invalid Credentials -사용자 인증 정보를 잘못 입력하거나 의도적으로 잘못 사용하면 인증에 실패합니다.

ldap.INVALID_CREDENTIALS : { 'info': '80090308 : LdapErr : DSID-0C090334, 주석 : AcceptSecurityContext 오류, 데이터 52e, vece', 'desc': '잘못된 자격 증명'}

또는

ldap.OPERATIONS_ERROR : { 'info': '00000000 : LdapErr : DSID-0C090627, 설명 :이 작업을 수행하려면 연결에서 성공적인 바인드를 완료해야합니다., 데이터 0, vece', 'desc': '작업 오류 '}

제대로 바인딩하려면 무엇을 놓치고 있습니까?

페도라와 창에서 동일한 오류가 발생합니다.


2
"... 그리고 그것이 생산하는 것은 눈물뿐입니다." 않는 눈물이 곰 또는 맥주와 운율?
philshem

답변:


47

나는 놓치고 있었다

l.set_option(ldap.OPT_REFERRALS, 0)

초기화에서.


3
이 버그의 근본 원인은 초기 응답에 조회가 있고 Windows LDAP 코드가 조회 서버에 자격 증명을 보내지 않기 때문입니다. kerberos 자격 증명을 사용한 경우 작동합니다.
schlenk

2
나는 다른 증상이 있었지만 동일한 옵션이 내 문제를 해결했습니다. 블로그 게시물에서 요약 : chaverma.com/blog/index.php/2013/06/…
Chris

관련이 있는지 확실하지 않지만 동일한 문제가 있었고 1729의 솔루션이 무언가를 수행 한 것 같습니다. 그러나 때로는 LDAP 서버가 잘못된 자격 증명에 즉시 응답합니다. 잠시 후 진정되고 다시 작동합니다.
Nitay 2014 년

29

pywin32 사용에 개방적이라면 Python에서 Win32 호출을 사용할 수 있습니다. 이것은 CherryPy 웹 서버에서 수행하는 작업입니다.

import win32security
token = win32security.LogonUser(
    username,
    domain,
    password,
    win32security.LOGON32_LOGON_NETWORK,
    win32security.LOGON32_PROVIDER_DEFAULT)
authenticated = bool(token)

3
간단하고 깨끗합니다! 감사!
alexroat 2013 년

이 솔루션은 제한적인 NTLM 기업 프록시 뒤에서 Python Flask 애플리케이션에서 저에게 효과적이었습니다. 다른 LDAP 기반 옵션은 작동하지 않습니다.
Gigaflop

7

그것은 나를 위해 일했습니다. l.set_option (ldap.OPT_REFERRALS, 0) 은 ActiveDirectory에 액세스하는 열쇠였습니다. 또한 스크립트를 끝내기 전에 연결을 끊으려면 "con.unbind ()"를 추가해야한다고 생각합니다.


8
로부터 파이썬 - LDAP 문서 : 인스턴스의 LDAPObject에 의해 반환됩니다 initialize(). LDAP 개체가 삭제되면 연결이 자동으로 바인딩 해제되고 닫힙니다.
Søren Løvborg

연결이 아니라 세션을 닫습니다.
Romulus

5

여기 저에게 맞는 간단한 코드가 있습니다.

import ldap  # run 'pip install python-ldap' to install ldap module.
conn = ldap.open("ldaphost.company.com")
conn.simple_bind_s("myuser@company.com", "mypassword")

이것은 이전 답변을 기반으로합니다 .


1
더 이상 작동하지 않습니다. 다음을 받게됩니다.AttributeError: module 'ldap' has no attribute 'open'
Josh Correia

3

예를 들어 Centrify Express가 설치되어 실행되는 경우처럼 Kerberos를 설치하고 AD와 통신하는 경우 python-kerberos를 사용할 수 있습니다. 예

import kerberos
kerberos.checkPassword('joe','pizza','krbtgt/x.pizza.com','X.PIZZA.COM')`

True를 반환합니다. 사용자 'joe'는 Kerberos 영역 X.PIZZA.COM에서 암호 'pizza'를 가지고 있습니다. (일반적으로 후자는 AD 도메인의 이름과 동일 할 것이라고 생각합니다.)


2

DN이 문제를 해결하지 않는다는 @Johan Buret에 대한 귀하의 의견을 보았지만, 그 점을 살펴보아야한다고 생각합니다.

예를 들어 AD의 기본 관리자 계정 DN은 다음과 같습니다. cn = Administrator, cn = Users, dc = mydomain, dc = co, dc = uk-시도해보십시오.


2

우수한 ldap3 튜토리얼을 기반으로 :

>>> from ldap3 import Server, Connection, ALL, NTLM
>>> server = Server('server_name_or_ip', get_info=ALL)
>>> conn = Connection(server, user="user_name", password="password", auto_bind=True)
>>> conn.extend.standard.who_am_i()
>>> server.info

Python3에서 위의 작업을 수행했지만 Python 2와 호환되어야합니다.


1

나는 추가하려고했다

l.set_option (ldap.OPT_REFERRALS, 0)

그러나 오류 대신 Python이 멈추고 더 이상 응답하지 않습니다. 검색 쿼리를 잘못 작성하고있을 수 있습니다. 검색의 기본 부분은 무엇입니까? 간단한 바인드를 위해 DN과 동일한 것을 사용하고 있습니다 (아 l.simple_bind, 대신 해야했습니다 l.simple_bind_s).

import ldap
local = ldap.initialize("ldap://127.0.0.1")
local.simple_bind("CN=staff,DC=mydomain,DC=com")
#my pc is not actually connected to this domain 
result_id = local.search("CN=staff,DC=mydomain,DC=com", ldap.SCOPE_SUBTREE, "cn=foobar", None)
local.set_option(ldap.OPT_REFERRALS, 0)
result_type, result_data = local.result(result_id, 0)

AD LDS를 사용하고 있으며 인스턴스가 현재 계정에 등록되어 있습니다.


1

나는 같은 문제가 있었지만 암호 인코딩에 관한 것이 었습니다.

.encode('iso-8859-1')

문제를 해결했습니다.


0

고유 이름을 사용하여 시스템에 로그온하십시오. "CN=Your user,CN=Users,DC=b2t,DC=local" AD를 포함한 모든 LDAP 시스템에서 작동해야합니다.


0

나를 위해 트릭 simple_bind_s()을 변경했습니다 bind().

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.