使用標準取用者監視和回應事件

您可以使用已安裝 的標準取用者類別 ,根據作業系統中的事件來執行動作。 標準取用者是已註冊的簡單類別,而且會定義永久取用者類別。 每個標準取用者會在收到事件通知之後採取特定動作。 例如,您可以定義 ActiveScriptEventConsumer 的實例,以在電腦上的可用磁碟空間與指定的大小不同時執行腳本。

WMI 會將標準取用者編譯成相依于作業系統的預設命名空間,例如:

  • 在 Windows Server 2003 中,所有標準取用者預設都會編譯為 「Root\Subscription」命名空間。

注意

如需每個 WMI 類別專屬的預設命名空間和作業系統,請參閱每個類別主題的和一節。

 

下表列出並描述 WMI 標準取用者。

標準取用者 描述
ActiveScriptEventConsumer 在收到事件通知時執行腳本。 如需詳細資訊,請參閱 根據事件執行腳本
LogFileEventConsumer 在收到事件通知時,將自訂字串寫入文字記錄檔。 如需詳細資訊,請參閱 根據事件寫入記錄檔
NTEventLogEventConsumer 將特定訊息記錄至應用程式事件記錄檔。 如需詳細資訊,請參閱 根據事件記錄至 NT 事件記錄檔。
SMTPEventConsumer 每次將事件傳遞至電子郵件訊息時,都會使用 SMTP 傳送電子郵件訊息。 如需詳細資訊,請參閱根據事件傳送Email
CommandLineEventConsumer 當事件傳遞至本機系統時,啟動進程。 可執行檔必須位於安全的位置,或使用強式存取控制清單保護, (ACL) ,以防止未經授權的使用者以不同的可執行檔取代可執行檔。 如需詳細資訊,請參閱 根據事件從命令列執行程式

 

下列程式描述如何使用標準取用者來監視和回應事件。 請注意,Managed 物件格式 (MOF) 檔案、腳本或應用程式的程式相同。

使用標準取用者監視和回應事件

  1. 使用 MOF 預處理器命令 #pragma命名空間,在 MOF 檔案中指定命名空間。 在腳本或應用程式中,在連線至 WMI 的程式碼中指定命名空間。

    下列 MOF 程式碼範例示範如何指定 root\subscription 命名空間。

    #pragma namespace ("\\\\.\\root\\subscription")
    

    大部分 的內部事件 都與 root\cimv2 命名空間中類別實例的變更相關聯。 不過,系統登錄提供者會在 root\default 命名空間中引發RegistryKeyChangeEvent之類的登錄事件。

    取用者可以藉由在__EventFilter事件查詢EventNamespace屬性中指定命名空間,以包含位於其他命名空間的事件類別。 每個命名空間都有內 建事件 類別,例如 __InstanceOperationEvent

  2. 建立並填入標準取用者類別的實例。

    這個實例在 Name 屬性中可能有唯一的值。 您可以重複使用相同的名稱來更新現有的取用者。

    InsertStringTemplates 包含要插入 EventType中所指定事件中的文字。 您可以使用常值字串或直接參考屬性。 如需詳細資訊,請參閱 使用標準字串範本SELECT 語句進行事件查詢

    針對支援插入字串且沒有相關聯文字的事件記錄檔使用現有的來源。

    下列 MOF 程式碼範例示範如何使用現有的 WSH 來源,以及 8 的 EventID 值。

    instance of NTEventLogEventConsumer as $Consumer
    {
        Name = "RunKeyEventlogConsumer";
        SourceName = "WSH";               
        EventID = 8;
        // Warning                              
        EventType = 2;
        // One string supplies the entire message          
        NumberOfInsertionStrings = 1;             
        // the %Hive% and %KeyPath% are properties of
        // the RegistryKeyChangeEvent instance 
        InsertionStringTemplates = 
            {"The key %Hive%\\%RootPath% has been modified."
            "Check if the change is intentional"};
    };
    
  3. 建立 __EventFilter 實例,並定義事件的查詢。

    在下列範例中,篩選準則會監視註冊啟動程式的登錄機碼。 監視此登錄機碼可能很重要,因為未經授權的程式可以在機碼下註冊本身,這會導致電腦開機時啟動。

    instance of __EventFilter as $Filter
    {
    Name = "RunKeyFilter";
    QueryLanguage = "WQL"; 
    Query = "Select * from RegistryTreeChangeEvent"
        " where (Hive = \"HKEY_LOCAL_MACHINE\" and "
        "RootPath = \"Software\\\\Microsoft\\\\Windows"
        "\\\\CurrentVersion\\\\Run\")";
    
    // RegistryTreeChangeEvents only fire in root\default namespace
    EventNamespace = "root\\default";                       
    };
    
  4. 識別要監視及建立事件查詢的事件。

    您可以檢查是否有使用的內部或外來事件。 例如,使用登錄提供者的 RegistryTreeChangeEvent 類別來監視系統登錄的變更。

    如果類別不存在描述您需要監視的事件,則必須建立自己的事件提供者,並定義新的外來事件類別。 如需詳細資訊,請參閱 撰寫事件提供者

    在 MOF 檔案中,您可以定義篩選和取用者的 別名 ,以提供簡單的方式來描述實例路徑。

    下列範例示範如何定義篩選和取用者的 別名

    instance of __EventFilter as $FILTER
    instance of LogFileEventConsumer as $CONSUMER
    
  5. 建立 __FilterToConsumerBinding 的實例,以建立篩選和取用者類別的關聯。 這個實例會判斷當發生符合指定篩選的事件時,必須發生取用者所指定的動作。 __EventFilter__EventConsumer__FilterToConsumerBindingCreatorSID 屬性中必須有相同的個別安全性識別碼 (SID) 。 如需詳細資訊,請參閱 使用邏輯取用者系結事件篩選

    下列範例示範如何依物件路徑識別實例,或使用別名做為物件路徑的簡短運算式。

    instance of __EventFilter as $FILTER
    instance of NTEventLogEventConsumer as $CONSUMER
    

    下列範例會使用別名將篩選系結至取用者。

    instance of __FilterToConsumerBinding
    {
        Filter = $FILTER;
        Consumer = $CONSUMER;
    
    };
    

    您可以將一個篩選系結至數個取用者,這表示發生比對事件時,必須採取數個動作;或者,您可以將一個取用者系結至數個篩選準則,這表示當符合其中一個篩選準則的事件發生時,必須採取動作。

    系統會根據取用者和事件的條件採取下列動作:

    • 如果其中一個永久取用者失敗,其他要求事件接收通知的取用者。
    • 如果卸載事件,WMI 會 引發__EventDroppedEvent
    • 如果您訂閱此事件,它會傳回已卸載的事件,而 __EventConsumer 的參考代表失敗的取用者。
    • 如果取用者失敗,WMI 會 引發__ConsumerFailureEvent,其中可能包含 ErrorCodeErrorDescriptionErrorObject 屬性中的詳細資訊。

    如需詳細資訊,請參閱 使用邏輯取用者系結事件篩選

範例

下列範例顯示 NTEventLogEventConsumer實例的 MOF。 編譯此 MOF 之後,任何嘗試在登錄路徑中建立、刪除或修改值 ,HKEY_LOCAL_MACHINE\ Software\Microsoft\Windows\CurrentVersion\Run 會記錄應用程式事件記錄檔中來源 「WSH」 的專案。

#pragma namespace ("\\\\.\\root\\subscription")
 
instance of __EventFilter as $Filter
{
    Name = "RunKeyFilter";
    QueryLanguage = "WQL";
    Query = "Select * from RegistryTreeChangeEvent"
            " where (Hive = \"HKEY_LOCAL_MACHINE\" and "
            "KeyPath = \"Software\\\\Microsoft\\\\Windows"
            "\\\\CurrentVersion\\\\Run\")";

    // RegistryTreeChangeEvents only fire
    // in root\default namespace
    EventNamespace = "root\\default";   
};
 
instance of NTEventLogEventConsumer as $Consumer
{
    Name = "RunKeyEventlogConsumer";
    SourceName = "WSH";               
    EventID = 8;
    EventType = 2;                            // Warning
    Category = 0;
    NumberOfInsertionStrings = 1;

    // the %Hive% and %KeyPath% are properties
    // of the RegistryKeyChangeEvent instance 
    InsertionStringTemplates = {"The key %Hive%\\%RootPath% "
        "has been modified. Check if the change is intentional"};
};
 

// Bind the filter to the consumer
instance of __FilterToConsumerBinding
{
    Filter = $Filter;
    Consumer = $Consumer;
};

安全地接收事件