您好,JK。 顺便说一下,当收到您所提出的问题时,我们躲到了桌子下面并装作不在,为此请接受我们的道歉;每当收到与日期和 Active Directory 相关的问题时,我们都会有点紧张。 这是因为,Active Directory 使用许多不同的方法来存储日期和时间,有些方法特别古怪。 例如,LastLogon 时间被存储为 Large Integer 值,表示 1601 年 1 月 1 日 0 时与用户上次登录到域时之间所经过的秒数。 (我们不骗你。) VBScript 不能直接处理 Large Integer 值;因此我们需要使用包括高等数学、转换算法以及完全不切实际的想法在内的各种方法来将 Large Integer 值转换为 VBScript 能够处理的值。 尽管如此,我们实际上未能得到日期和时间,而只是一个可通过较为复杂的数学变换最终转换为日期和时间的值。
然而,幸运的是,我们无需使用量子力学或巫术即可确定用户帐户的过期时间。 这并不意味着可为我们指出帐户过期时间的 AccountExpirationDate 属性没有多少奇特之处,而是这些奇特之处至少非常易于解决。
让我们看看可为我们指出 Ken Myer 用户帐户过期时间的脚本:
On Error Resume Next
Set objUser = GetObject("LDAP://cn=MyerKen,ou=Finance,dc=fabrikam,dc=com")
dtmAccountExpiration = objUser.AccountExpirationDate
If Err.Number = -2147467259 OR dtmAccountExpiration = #1/1/1970# Then
WScript.Echo "This account has no expiration date."
Else
WScript.Echo "Account expiration date: " & objUser.AccountExpirationDate
End If
首先,您可能注意到了脚本中的第一行: On Error Resume Next。 通常,示例脚本中不包含错误处理;尽管错误处理在进行实际脚本编写时非常重要,但它常常会使示例脚本(即用于教学而非立即实际使用的脚本)中的要点变得模糊。 不过,在本例中,必须有错误处理;因为如果没有为帐户指定过期日期,将会出错。 如果没有预料到并捕获该错误,脚本将失败。 因此,我们以 On Error Resume Next 作为开始;从而使得脚本在遇到没有过期日期的帐户时将继续运行。
在第 2 行中,绑定到 Active Directory 中的 Ken Myer 帐户;接下来将 AccountExpirationDate 的值存储到变量 dtmAccountExpiration 中。 此时可能会出错: 如果用户帐户没有指定的过期日期,将生成错误号 -2147467259。 需要检查是否发生了该错误。
还需要检查 AccountExpirationDate 的另外一个奇特功能。 在 Active Directory 中,可配置用户帐户,使其永不过期;如果进行了此操作,AccountExpirationDate 将被设置为 1970 年 1 月 1 日。(是的,这是一种可确保帐户不过期的奇特方法。) 如果返回表示帐户没有设置过期日期的错误号 -2147467259,则意味着帐户未过期。 不过,如果返回的帐户过期日期为 1970 年 1 月 1 日,则也表示帐户未过期。 因此,我们需要使用 If-Then 语句来检查这两种可能情况:
If Err.Number = -2147467259 OR dtmAccountExpiration = #1/1/1970# Then
正如您所看到的,如果错误号 (Err.Number) 等于 -2147467259 或者帐户过期日期为 1970 年 1 月 1 日 (1/1/1970),将回显一条消息,指出帐户没有过期日期;否则回显过期日期。 这很离奇,但很有效,至少我们不必躲到桌子下面去了。 (尽管那并非全损失: 当我们在桌子下面时,我们发现了钉书器、一束纸夹以及另外一半三明治。)