使用 WMI 匯出 IIS 6 網站設定

IIS 6 網站要移轉到 Windows 2012 R2 主機,轉換前打算匯出網站完整設定檢視一次,排除過期或廢棄的網站應用程式,另外還想嘗試依據現有設定產生設定網站應用程式與虛擬目錄的自動化 Script,第一步要取得現有網站設定資料。

使用 PowerShell Get-WmiObject -class IISWebVirtualDirSetting -namespace "root/MicrosoftIISv2" -computername "IIS6主機名稱" -authentication 6(參考:Get-WmiObject 參數說明)可列出虛擬目錄及網站應用程式相關設定,要寫程式對匯出資料進行花式應用,轉成 JSON 是首選,而 PowerShell 有個 ConvertTo-Json Cmdlet 可以幫忙。

看似完美對吧?But!天殺的 But 又出現惹~當屬性為物件陣列(如下圖的 HttpCustomHeaders 及 HttpErrors)時,ConvertTo-Json 會轉成"System.Management.ManagementBaseObject"組成的字串陣列,看不出其中內容。

ConvertTo-Json 有個 –Depth 參數指定序列化深度,實測提高到 5 才能看到 HttpErrors 內容:

不過 Depth 提高後,資料結構裡供系統用的 Properties、SystemProperties、Qualifiers、ClassPath 也會被展開,資料變得雜亂仰賴後續過濾簡化。心想橫豎都要寫程式,不如擷取邏輯也自己寫吧!

使用 System.Management.ManagementObjectSearcher 可取回與 Get-WmiObjet 相同的查詢結果,配合 Json.NET LINQ 好用的 JObject、JArray、JValue 動態組裝產生 JSON:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Management;
using System.Text;
using Newtonsoft.Json;
using Newtonsoft.Json.Linq;
 
class IISSettingDumper
{
    public static void Dump()
    {
        ConnectionOptions options = new ConnectionOptions();
        options.Impersonation = System.Management.ImpersonationLevel.Impersonate;
        options.Authentication = AuthenticationLevel.PacketPrivacy;
        ManagementScope scope = new ManagementScope(@"\\.\root\MicrosoftIISv2", options);
        scope.Connect();
        ObjectQuery query = new ObjectQuery("SELECT * FROM IISWebVirtualDirSetting");
        ManagementObjectSearcher searcher = new ManagementObjectSearcher(scope, query);
        ManagementObjectCollection res = searcher.Get();
        JArray pool = new JArray();
        foreach (var m in res)
        {
            JObject jo = new JObject();
            foreach (var p in m.Properties)
            {
 
                if (p.Value is ManagementBaseObject[])
                {
                    var jsonArray = new JArray();
                    var array = (ManagementBaseObject[])p.Value;
                    foreach (var q in array)
                    {
                        var child = new JObject();
                        foreach (var childProp in q.Properties)
                            child.Add(childProp.Name, new JValue(childProp.Value));
                        jsonArray.Add(child);
                    }
                    jo.Add(p.Name, jsonArray);
                }
                else if (p.Value != null && p.Value.GetType().IsArray)
                {
                    var jsonArray = new JArray(p.Value);
                    jo.Add(p.Name, jsonArray);
                }
                else
                {
                    jo.Add(p.Name, new JValue(p.Value));
                }
            }
            pool.Add(jo);
        }
        System.IO.File.WriteAllText("c:\\temp\\VirDirSetting.json", pool.ToString());
        Console.WriteLine(pool.ToString());
    }
}

輸出結果如下,是不是賞心悅目多了?

補充說明:以上做法適用 IIS 6 時代的 WMI 資料規則,如要在 IIS 7+使用,需安裝「IIS 6 Management Compatibility」

【延伸閱讀】
歡迎推文分享:
Published 22 October 2016 01:12 PM 由 Jeffrey
Filed under:
Views: 1,609



意見

沒有意見

你的看法呢?

(必要的) 
(必要的) 
(選擇性的)
(必要的) 
(提醒: 因快取機制,您的留言幾分鐘後才會顯示在網站,請耐心稍候)

5 + 3 =

搜尋

Go

<October 2016>
SunMonTueWedThuFriSat
2526272829301
2345678
9101112131415
16171819202122
23242526272829
303112345
 
RSS
創用 CC 授權條款
【廣告】
twMVC

Tags 分類檢視
關於作者

一個醉心技術又酷愛分享的Coding魔人,十年的IT職場生涯,寫過系統、管過專案, 也帶過團隊,最後還是無怨無悔地選擇了技術鑽研這條路,近年來則以做一個"有為的中年人"自許。

文章典藏
其他功能

這個部落格


Syndication