搜索SO和其他所有地方,包括目录服务编程书的.net开发人员指南 - 没有运气。
我正在尝试创建一个简单的密码重置网页,允许用户更改其密码。代码的更改密码部分工作正常。对于用户,我还希望在他们当前的密码将在下一个到期时显示。
使用上面提到的书中的示例代码我能够获得所有代码设置但是,返回的属性总是等于Long.MinValue,因此不能反转为正数,加上这意味着它没有找到合适的域名设置。
是否有人在Windows 2008或R2域环境中获取密码过期的示例代码或参考,其中每个用户的密码策略可能不同?
已更新以包含代码
获取策略对象的构造函数:
public PasswordExpires()
{
//Get Password Expiration
Domain domain = Domain.GetCurrentDomain();
DirectoryEntry root = domain.GetDirectoryEntry();
using (domain)
using (root)
{
this.policy = new DomainPolicy(root);
}
}
域策略构造器:
public DomainPolicy(DirectoryEntry domainRoot)
{
string[] policyAttributes = new string[] {
"maxPwdAge", "minPwdAge", "minPwdLength",
"lockoutDuration", "lockOutObservationWindow",
"lockoutThreshold", "pwdProperties",
"pwdHistoryLength", "objectClass",
"distinguishedName"
};
//we take advantage of the marshaling with
//DirectorySearcher for LargeInteger values...
DirectorySearcher ds = new DirectorySearcher(
domainRoot,
"(objectClass=domainDNS)",
policyAttributes,
SearchScope.Base
);
SearchResult result = ds.FindOne();
//do some quick validation...
if (result == null)
{
throw new ArgumentException(
"domainRoot is not a domainDNS object."
);
}
this.attribs = result.Properties;
}
调用此方法以获取密码到期时间:
public TimeSpan MaxPasswordAge
{
get
{
string val = "maxPwdAge";
if (this.attribs.Contains(val))
{
long ticks = GetAbsValue(
this.attribs[val][0]
);
if (ticks > 0)
return TimeSpan.FromTicks(ticks);
}
return TimeSpan.MaxValue;
}
}
代码在这里失败,因为它无法转换Long.MinValue,它不应该首先出现
private long GetAbsValue(object longInt)
{
return Math.Abs((long)longInt);
}
这是调试器输出和值。根据MSDN站点,溢出异常是由最小值引起的。我的数字与minvalue的例子匹配。
答案 0 :(得分:2)
存储密码到期时间,如果lastPwdSet - maxPwdAge < DateTime.UtcNow
为真,则密码已过期。因此,如果您在一周前设置了密码,但密码将在10天后过期,则左侧将为(DateTime.UtcNow - 7) - (-10)
,或DateTime.UtcNow - 7 + 10
或DateTime.UtcNow + 3
,且不小于{ {1}},因此您的密码不会过期。
这意味着将maxPwdAge设置为long.MinValue将有效地为您提供数千年的密码到期时间。因此,如果您收到DateTime.UtcNow
,则您的政策会说密码不会过期。你应该只是寻找那个值并正确对待它,可能是这样的:
long.MinValue
另外,我应该指出,这些值以100纳秒的增量存储,因此您应该期望数十亿的值。