[Quest ActiveRoles Management Shell for Active Directory] QADProxyAddress命令相關的bug。

This post also be published in English: http://www.cnblogs.com/LarryAtCNBlog/p/3923882.html

稱之爲bug真得好嗎?不過想想也沒錯呀,因爲QADProxyAddress相關的命令基本上都不能用了都。

事情大概是這樣,

我們公司因爲業務以前有很多smtp address,現在大統一要清除AD裏面一些SMTP domain,公司用的是Quest ARServer管理權限,因此實際上我本人雖然身爲管理員,其實權限對AD本身就是一個普通user,所有的操作都必須通過Quest console來實現,很高興的是Quest公司出品了powershell版的console,讓我可以通過命令行來做batch job。

當然,這次的smtp domain清理大行動又落在了我身上,咦~~我爲什麼要說又~

打開ISE,開始碼代碼,其實寫腳本,或者說編程,核心幹活的代碼絕不能排在第一位,logging至少是與其並列,log是當事情幹完之後一旦出問題,唯一能夠拯救世界的東西。

扯遠了,代碼並不複雜,根據project team每次所給我的batch job,我只需要讀該文本,取出user名字,用Get-QADUser的方法從AD裏把該user抓到,然後判斷其ProxyAddresses屬性有沒有匹配到目標domain就好了,沒有匹配到的話,則跳過該user,匹配到的話就提取出匹配項,然後執行Remove-QADProxyAddress命令就行了。這麼簡單想想都有點小激動呢。

代碼寫一半,打算用自己的賬號測試一下Remove-QADProxyAddress這個cmdlet的用法及錯誤返回。

喲,果然what the hell了,心涼一截,這錯兒是怎麼事兒?感覺要被坑呢?

明明通過console UI界面操作,不用每一個type的address都要有一個primary纔對呀,可以直接做纔對呀,果斷搜了一搜,發現如下某人給Dell (沒錯Quest被Dell收購啦) report了同樣的問題,話說Dell沒人管是怎麼事兒?這都快2年了!

http://en.community.dell.com/techcenter/powergui/f/4834/t/19574623.aspx

我公司用的還是ARS 6.7.0, ARS powershell module的相應版本是1.5.1,最新的是ARS 6.8.0,不清楚該bug修復了沒有,無論怎麼樣服務器端要有對應的版本,不然光下載個最近的客戶端也連接不上服務器,會被拒絕。

怎麼辦呢?其實問題很簡單,QADProxyAddress相關的幾個cmdlet在運行的時候都會檢查每個proxy address的type,每種type都要有一個primary,沒設置的話是不行的。而且,就算爲了修正該問題,想對每個type都設一個primary,也是不行。困爲如果同時存在兩種以上的type沒有primary,在糾正其中一個type的時候,會報另外的type沒有primary的錯誤,比如同時有sip和x500兩個type沒有primary,在運行如下命令糾正sip的時候,就會報x500沒有primary,稱爲被坑不爲過呀

怎麼辦怎麼辦,都不要臉地答應人project manager了,現在說做不到不是要丟死人了嗎?

AD賬號本身又沒權限,通過ARS又有該bug,最後想到exchange 2010,我的賬號是有修改mailbox的權限的,看看mailbox上有沒有同樣的屬性先。

於是果斷登上exchange,打開powershell,Get-Mailbox | fl * 一瞅果斷有同樣的屬性。這就是傳說中的救命稻草,趕緊把Y按地上。用Set-Mailbox果然能無視primary修改proxy address,於是腳本改成用exchange powershell執行。於是有了下面的腳本,會讀取Process.list.txt裏的user list,然後從user的address找smtp地址的匹配,找到的話就刪掉,沒有找到就跳過。

. 'D:\Program Files\Microsoft\Exchange Server\v14\bin\RemoteExchange.ps1'
Connect-ExchangeServer -auto

$users = cat '.\Process.list.txt' | ?{$_} | %{$_.Trim()}
$addressToRemove = 'regular expression'

$Date = Get-Date
$strDate = $Date.ToString('yyyy-MM-dd')
$strLogFile = "$strDate.log"

function Add-Log{
    PARAM(
        [String]$Path,
        [String]$Value,
        [String]$Type
    )
    $Type = $Type.ToUpper()
    Write-Host "$((Get-Date).ToString('[HH:mm:ss] '))[$Type] $Value"
    if($Path){
        Add-Content -Path $Path -Value "$((Get-Date).ToString('[HH:mm:ss] '))[$Type] $Value"
    }
}

$Total = $users.Count
Add-Log -Path $strLogFile -Value "Users count: [$Total]" -Type Info

$users | %{$Processed = 0}{
    $Processed++
    Add-Log -Path $strLogFile -Value "Processing: [$Processed/$Total][$_]" -Type Info
    $mailbox = $null
    $mailbox = Get-Mailbox -Identity $_
    if(!$mailbox)
    {
        Add-Log -Path $strLogFile -Value "Failed to get user's mailbox" -Type Error
        return
    }
    Add-Log -Path $strLogFile -Value "All 1: [$(($mailbox.EmailAddresses | %{$_.ProxyAddressString}) -join '], [')]" -Type Info
    $addresses = $mailbox.EmailAddresses | ?{$_.Prefix.DisplayName -eq 'SMTP'} | %{$_.SmtpAddress}
    $addressMatch = $null
    $addressMatch = $addresses -imatch $addressToRemove
    if($addressMatch)
    {
        Add-Log -Path $strLogFile -Value "Matched: [$($addressMatch -join '], [')]" -Type Info
        $mailbox | Set-Mailbox -EmailAddresses @{remove=$addressMatch} -ErrorAction:SilentlyContinue
        if(!$?)
        {
            Add-Log -Path $strLogFile -Value 'Remove address failed, cause:' -Type Error
            Add-Log -Path $strLogFile -Value $Error[0] -Type Error
        }
        $mailbox = Get-Mailbox -Identity $_
        Add-Log -Path $strLogFile -Value "All 2: [$(($mailbox.EmailAddresses | %{$_.ProxyAddressString}) -join '], [')]" -Type Info
    }
    else
    {
        Add-Log -Path $strLogFile -Value "No SMTP address matched, move to next." -Type Info
        return
    }
}
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章