![](/img/trans.png)
[英]unlocking Locked user accounts on Active Directory using Python ldap module
[英]Detect if an Active Directory user account is locked using LDAP in Python
我正在使用 python 的 ldap 模块验证用户登录。 当登录失败时,我得到一个 ldap.INVALID_CREDENTIALS 登录,但这可能是因为密码错误或帐户被锁定。 帐户在第 3 次尝试后被锁定。
我想检测到该帐户已被锁定并将其报告给沮丧的用户,而不是相同的“无效登录”消息。
搜索我找到的解决方案:
我应该用来查找锁定用户的 LDAP 查询是:
(&(objectClass=user)(lockoutTime>=1))
或者对于特定用户:
(&(objectClass=user)(sAMAccountName=jabberwocky)(lockoutTime>=1))
但这不起作用,查询每次都没有返回结果。
lockoutTime
中的零值意味着它没有被锁定。 所以,你应该试试这个。
(&(objectClass=user)(!lockoutTime=0))
实际上,上述查询仍然不是 100% 正确的。 如果您从 MSDN 阅读细则,Microsoft 建议您将Lockout-Time
属性添加到Lockout-Duration
属性,然后将其与当前时间进行比较。 那是因为有一个叫做锁定时间的东西。 一旦锁定时间结束,用户将自动解锁。 Lockout-Duration
中的零表示帐户将永远锁定,直到管理员将其解锁。
请参阅这篇MSDN 文章
此属性值仅在帐户登录成功时重置。 这意味着该值可能不为零,但帐户未被锁定。 要准确判断账户是否被锁定,必须在该时间上加上Lockout-Duration,与当前时间进行比较,考虑当地时区和夏令时。
lockoutTime
是一个<not set>
属性,所以最简单的方法是使用:
(&(objectClass=user)(lockoutDuration=*)))
对于非空条目。
更新:
但是,当密码过期、需要更改密码等时,也会设置此值。
所以需要过滤:
UserPrincipal userPrincipal = new UserPrincipal(context);
bool isLocked = userPrincipal.IsAccountLockedOut();
获取用户因违反密码策略而被锁定的情况,例如错误输入密码 5 次。
我还找到了这个属性标志列表: How to use the UserAccountControl flags
SCRIPT 0x0001 1
ACCOUNTDISABLE 0x0002 2
HOMEDIR_REQUIRED 0x0008 8
LOCKOUT 0x0010 16
PASSWD_NOTREQD 0x0020 32
PASSWD_CANT_CHANGE 0x0040 64
ENCRYPTED_TEXT_PWD_ALLOWED 0x0080 128
TEMP_DUPLICATE_ACCOUNT 0x0100 256
NORMAL_ACCOUNT 0x0200 512
INTERDOMAIN_TRUST_ACCOUNT 0x0800 2048
WORKSTATION_TRUST_ACCOUNT 0x1000 4096
SERVER_TRUST_ACCOUNT 0x2000 8192
DONT_EXPIRE_PASSWORD 0x10000 65536
MNS_LOGON_ACCOUNT 0x20000 131072
SMARTCARD_REQUIRED 0x40000 262144
TRUSTED_FOR_DELEGATION 0x80000 524288
NOT_DELEGATED 0x100000 1048576
USE_DES_KEY_ONLY 0x200000 2097152
DONT_REQ_PREAUTH 0x400000 4194304
PASSWORD_EXPIRED 0x800000 8388608
TRUSTED_TO_AUTH_FOR_DELEGATION 0x1000000 16777216
PARTIAL_SECRETS_ACCOUNT 0x04000000 67108864
您必须使用0x002
对属性userAccountControl
进行二进制与运算。 为了获得所有锁定(即禁用)的帐户,您可以使用
(&(objectClass=user)(userAccountControl:1.2.840.113556.1.4.803:=2))
对于操作员1.2.840.113556.1.4.803
请参阅LDAP 匹配规则
此外,我发现 lockoutTime 并不能保证 AD 中的所有用户(至少在我们的配置中),但会在达到锁定尝试失败次数时创建。 因此,在检查锁定帐户时,还需要检查 None 或等效项。
使用此查询以获得最佳结果,
Get-ADUser -LDAPFilter "(&(objectCategory=Person)(objectClass=User)(lockoutTime>=1))" -Properties LockedOut
(&(objectClass=user)(&(lockoutTime=*)(!(lockoutTime=0))))
将返回作为用户的对象,并且具有名为 lockoutTime 的 present 属性,该属性不等于 0。
像这样做:
def islocked(self, user, basedn, conn):
search_filter = "(&(objectCategory=Person)(objectClass=User)(lockoutTime>=1))"
search_attribute = ["sAMAccountName"]
try:
conn.search(basedn,
search_filter,
attributes=search_attribute)
results = conn.entries
except ldap3.core.exceptions.LDAPException as e:
print(e)
lockedaccounts = [x['sAMAccountName'] for x in results]
lockedaccounts = [str(x) for x in lockedaccounts]
lockedaccounts = [x for x in lockedaccounts]
if user in lockedaccounts:
return True
else:
return False
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.