[.NET]續透過WinNT的方式取得電腦中的群組與帳號資訊-變更帳號密碼過期設定及強制修改使用者變更密碼

公司的稽核部門希望,將Windows中的帳號作一次密碼的變更
且加上一些密碼的設定規則,如90天必須更改一次密碼,密碼必須有大小寫英文字母,數字或是特殊字元等等的要求
且當初的帳號在建立時,已經將所有的帳號設定為密碼永久有效的狀態
要處理這樣的情況,一般來說是要進入到Windows,將所有帳號一個一個去作設定,這樣不但花工,也很花時間(帳號一共近100個左右)

http://www.dotblogs.com.tw/maduka/archive/2011/09/12/36008.aspx這篇文章之後

今天早上又接到一個新的需求

原來是公司的稽核部門希望,將Windows中的帳號作一次密碼的變更
且加上一些密碼的設定規則,如90天必須更改一次密碼,密碼必須有大小寫英文字母,數字或是特殊字元等等的要求

由於設定密碼規則是在本機原則中進行設定,所以我就不在這裡說明
反倒是有一個很麻煩的狀況,就是當初的帳號在建立時,已經將所有的帳號設定為密碼永久有效的狀態
要處理這樣的情況,一般來說是要進入到Windows,將所有帳號一個一個去作設定,這樣不但花工,也很花時間(帳號一共近100個左右)

所以,我就把之前的那份程式拿出來作了一點修改

1.於GridView之中顯示帳號密碼的過期狀態以及是否設定為密碼永久有效

要將帳號的密碼狀態變更為已過期,且密碼為永不過期的狀態,需要找出幾個屬性


int intFlag = (int)objChildDE.Properties["UserFlags"].Value;
string strState = (!Convert.ToBoolean(intFlag & 0x2)) ? "" : "停用";
string strExpired = objChildDE.Properties["PasswordExpired"].Value.ToString();                    
string strDONTEXPIRE = (!Convert.ToBoolean(intFlag & 0x10000)) ? "" : "密碼永久有效";

要找出帳號密碼是否已經過期,需要用到"PasswordExpired"這個Properties的值來作判斷,若是1代表已過期,0代表尚未過期
而密碼是否永久有效,則是要將UserFlags的屬性值與0x10000作比對,才能得到在帳號視窗中是否有設定

從上圖可以看出,maduka這個帳號是設定為密碼永久有效的

2.執行帳號的密碼過期修改及修改密碼永久有效的設定

要變更帳號的狀態,其實很簡單,最主要的問題出在,我們只能用WinNT的方式去處理,改用LDAP的話,其實會很簡單


using (DirectoryEntry userEntry = new DirectoryEntry("WinNT://maduka-nb/maduka,user", 登入帳號,登入密碼))
{
    // 先設定帳號密碼不得為永久有效
     int intFlag = (int)userEntry.Properties["UserFlags"].Value;
    if (Convert.ToBoolean(intFlag & 0x10000))
    userEntry.Properties["UserFlags"].Value = (int)userEntry.Properties["UserFlags"].Value - 65536;

    // 設定密碼過期
    userEntry.Invoke("Put", "PasswordExpired", 1);
    userEntry.CommitChanges();
}

MessageBox.Show(strAccount + "重設成功");

從上面的程式可以看的出來,透過DirectoryEntry的方式,找出該使用者帳號的Entry
要設定密碼不為永久有效,只要一樣去判斷與0x10000是否成立,並減去65536的值(0x10000),這樣帳號的密碼永久有效的設定就被取消了
但是取消之後沒有用,所以我們還要再作一個動作,強制密碼過期,這樣使用者在下次登入時,才會要求使用者變更密碼
所以再下面加上Invoke("Put", "PasswordExpired", 1);
設定密碼過期為1
這樣該帳號既為密碼不為永久有效,又同時將該帳號的密碼設定為過期

下面的檔案,是我這次修改的程式,由於公司員工的帳號都是2與4開頭,所以我在批次轉檔的時候,有加入一個判斷,帳號是2或是4開頭才執行
不然會連Administrator及一些系統內建帳號的密碼也改掉就很麻煩了

要批次更改前,請先作一次Get的動作喔,因為批次修改是從GridView中抓取帳號資料的

WindowsAccountGroup.rar