Автоматизация задач Group Policy Management Console
Оснастка Group Policy Management Console (GPMC) консоли Microsoft Management Console (MMC), появившаяся в Windows Server 2003, представляет собой исключительно полезный инструмент. С помощью данного средства можно через единый интерфейс выполнять большую часть работ, связанных с управлением групповыми политиками. Более того, при установке данного компонента также устанавливаются несколько COM-объектов, с помощью которых многие работы можно автоматизировать. В статье "Управление объектами групповой политики с помощью сценариев" (http://www.osp.ru/text/302/3154185/) речь шла о том, с чего следует начинать, чтобы научиться работать с этими объектами. Указанная статья, а также те материалы, ссылки на которые приводятся в разделе "Список литературы", помогут понять основные принципы автоматизации задач, связанных с политиками. Затем можно переходить к использованию COM-объектов GPMC для решения более серьезных задач, таких как программируемый поиск объектов групповой политики (GPO), поиск всех диапазонов управления (Scope of Management – SOM) для какого-либо GPO, а также поиск всех объектов SOM в дереве Active Directory (AD).
Простой поиск всех GPO
Для того чтобы использовать сценарии, описанные в статье "Управление объектами групповой политики с помощью сценариев", необходимо знать глобальный уникальный идентификатор (GUID) в AD того объекта GPO, к которому требуется подключиться. Та часть GPO, которая хранится в AD, имеет отличительное имя (DN), которое может выглядеть, например, следующим образом: cn={myguid}, cn=policies, cn=system, dc=mydomain, dc=mycorp, dc=com, где {myguid} соответствует идентификатору GUID. Теоретически использовать GUID несложно, поскольку объекты GPO обычно не меняются после того, как они были настроены администратором. Однако как быть в том случае, когда мы не хотим в явном виде задавать GUID в сценарии? Или если нужно определить, какие объекты GPO существуют в AD или какие GPO связаны с определенным объектом SOM? В таких случаях поиск можно автоматизировать с помощью GPMC.
В Листинге 1 показан пример сценария SearchAndReport.vbs, с помощью которого в заданном домене выполняется поиск всех существующих объектов GPO, как привязанных (linked), так и не привязанных к дереву AD. В начале сценария объявляется константа DOMAIN, содержащая имя домена, в котором будет выполняться поиск. Соответственно, если вы захотите использовать SearchAndReport.vbs в своей инфраструктуре, потребуется заменить значение mydomain.mycorp.com именем соответствующего домена из вашей сети. То же касается и всех констант из рассмотренных здесь сценариев. Их значения следует поменять на те, которые соответствуют актуальным значениям вашего дерева AD.
Во фрагменте кода, отмеченного в Листинге 1 меткой A, для создания ссылки на объект GPM используется функция VBScript CreateObject. Далее с помощью метода GetDomain объекта GPM с константой DOMAIN в качестве аргумента создается объект GPMDomain, соответствующий используемому в примере домену. С помощью объекта GPMDomain можно создавать, опрашивать и восстанавливать объекты GPO, а также выполнять поиск объектов SOM в заданном домене. Кроме того, для того чтобы создать ссылку на объект GPMSearchCriteria, я использовал метод CreateSearchCriteria объекта GPM. Данный объект можно использовать для задания критериев поиска. В рассматриваемом случае я не указываю никаких критериев поиска. Иными словами, объект GPMSearchCriteria имеет "пустое" значение, поэтому в результате поиска будут возвращены данные обо всех GPO, существующих в данном домене.
Теперь, когда в нашем распоряжении есть все необходимые объекты, можно запускать процедуру поиска. Как видно из фрагмента Листинга 1, обозначенного меткой B, здесь используется вызов метода SearchGPOs объекта GPMDomain с пустым объектом GPMSearchCriteria, передаваемым в качестве параметра. В результате выполнения метода SearchGPOs возвращается объект GPMGPOCollection, содержащий все GPO данного домена. Затем эта коллекция обрабатывается обычным образом. Сначала с помощью свойства Count объекта GPMGPOCollection мы получаем количество объектов GPO в данной коллекции и отображаем полученное значение командой Echo. Затем перебираем элементы коллекции с помощью цикла For Each...Next. Для каждого GPO отображается его GUID, дружественное отображаемое имя (friendly display name) и имя DN. При этом и GUID, и DN являются уникальными, поскольку в каждом из них содержится GUID. Что касается отображаемого имени, то оно в общем случае уникальным не является.
Поиск объектов SOM для отдельного GPO
Как видно из файла SearchAndReport.vbs, организовать поиск всех имеющихся в домене GPO достаточно просто. Теперь рассмотрим более сложный случай. Предположим, нам нужно найти в дереве AD все те домены и организационные подразделения (OU), к которым привязан какой-либо объект GPO. Иначе говоря, мы хотим найти для отдельного объекта GPO все соответствующие объекты SOM для доменов и OU. В Листинге 2 показан сценарий FindSOMsforGPO.vbs, который может быть использован в данном случае. В этом сценарии поиск основывается на известном объекте GPO, идентификатор GUID которого определяется константой. В сценарии FindSOMsforGPO.vbs идентификатор GUID соответствует идентификатору объекта Default Domain Policy, который одинаков для всех доменов Windows 2003 Server и Windows 2000 Server. Запустив FindSOMsforGPO.vbs с данным значением GUID, можно получить информацию обо всех доменах и OU, к которым привязан объект Default Domain Policy.
Теперь давайте обсудим, как работает сценарий FindSOMsforGPO.vbs. Как показано в Листинге 2 во фрагменте кода с меткой A, здесь создается ссылка на объект GPM, а затем, с помощью вызова метода GetDomain данного объекта, создается объект GPMDomain. Далее, вызывая метод GetGPO объекта GPMDomain с константой GUID в качестве аргумента, находим GPO, соответствующий Default Domain Policy.
Затем нужно определить, имеются ли в данном домене какие-либо объекты SOM, которые используют то же значение GUID, которое задается константой GUID. Для этого можно вызвать метод SearchSOMs объекта GPMDomain и получить объект GPMSOMCollection, который представляет собой коллекцию объектов SOM. Методу SearchSOMs в качестве параметра указывается объект GPMSearchCriteria. Однако если в качестве параметра будет передан пустой объект GPMSearchCriteria, как это делается в примере Листинга 1, то в результате мы получим список всех объектов SOM для данного домена, а это не то, что нам нужно, поскольку мы хотим найти только те SOM-объекты, которые соответствуют конкретному объекту GPO. Поэтому если нужно, чтобы процедура поиска возвратила только интересующие нас объекты SOM, то необходимо задать в объекте GPMSearchCriteria критерий, определяющим нужный нам объект GPO.
Как показано в Листинге 2 (фрагмент с меткой B), сначала создается объект GPMSearchCriteria, аналогично тому, как это делалось в примере Листинга 1. После этого в данный объект добавляется критерий, для чего используется метод Add объекта GPMSearchCriteria.
Синтаксис вызова метода Add, описанный в библиотеке Microsoft Developer Network (MSDN) Library, кажется с виду сложным, однако на самом деле использовать этот метод достаточно просто. Для добавления нового критерия используем следующий синтаксис:
Add(SearchProperty,SearchOperator, Value)
Здесь SearchProperty и Value определяют, соответственно, имя и значение искомого свойства, а с помощью SearchOperator задается тот оператор, который будет применяться в процессе поиска. В методе Add используются операторы, позволяющие найти свойство, которое содержит (opContains), не содержит (opNotContains), равно (opEquals) или не равно (opNotEquals) заданной величине (value). Допустим, если нужно найти в домене тот объект GPO, который имеет заданное значение GUID, это описывается следующим образом:
gpoID opEquals GUID
Другими словами, выполняется поиск свойства gpoID, значение которого равно значению константы GUID. При задании критериев поиска очень удобно то, что когда поисковый метод объекта GPM получает в качестве параметра объект GPMSearchCriteria, таким образом точно определяется, какие именно критерии можно использовать. Этот сдерживающий фактор очень помогает. В данном случае я хочу использовать метод SearchSOMs для поиска в домене объектов SOM, и при этом мне нужно ограничить круг поиска идентификатором GUID интересующего меня объекта GPO. В соответствии с описанием метода SearchSOMs объекта GPMDomain, приведенном в документации "Group Policy Management Console Reference" (http://msdn.microsoft.com/library/default.asp?url=/library/enus/gpmc/gpmc/group_policy_management_console_reference.asp), при поиске может использоваться только свойство somLinks. Согласно описанию метода Add объекта GPMSearchCriteria, при работе с поисковым свойством somLinks может использоваться только оператор поиска opContains, причем значение (value) в данном случае должно быть объектом GPMGPO. Таким образом, нужно задать такой критерий, который предписывает, что ссылки SOM (somLinks) должны содержать (opContains) интересующий меня GPO.
Итак, как показано во фрагменте кода, обозначенном меткой В, сначала создается пустой объект GPMSearchCriteria, после чего для добавления критерия используется метод Add. Как уже упоминалось ранее в данной статье, метод Add имеет три параметра: SearchProperty, SearchOperator и Value. Поскольку значения параметров SearchProperty и SearchOperator представляют собой постоянные величины – соответственно, somLinks и opContains – вместо того, чтобы жестко задавать их в коде сценария, я передаю их динамически в виде двух соответствующих констант. Как объяснялось ранее в статье "Управление объектами групповой политики с помощью сценариев", для использования динамической передачи констант необходимо сначала подключиться к объекту GPMConstants. После установки этого соединения и создания ссылки через переменную gpmConstants в качестве параметра SearchProperty задается значение gpmConstants.SearchPropertySOMLinks, а в качестве параметра SearchOperator – значение gpmConstants.SearchOpContains. Что касается параметра Value, то здесь я просто указываю переменную gpmGPO, поскольку она содержит ссылку на тот объект GPO, к которому я собираюсь подключиться. И, наконец, я применяю метод SearchSOMs, результаты выполнения которого передаются переменной с именем colDOUSOMs, которая является объектом GPMSOMCollection. В переменной colDOUSOMs содержится коллекция объектов SOM, соответствующая домену и тем его OU, на которые ссылаются интересующие меня GPO. Во фрагменте кода, обозначенном в Листинге 2 меткой C, сначала выводится количество объектов SOM, а затем отображается путь к каждому из них.
Организация поиска всех объектов SOM
А теперь рассмотрим, как можно организовать поиск, не ограничиваясь только обнаружением объектов SOM, соответствующих домену и OU для какого-то конкретного GPO, а находить и выводить перечень всех сайтов доменов и OU дерева AD, к которым привязаны объекты GPO. Как нам уже известно, для того чтобы получить список всех имеющихся объектов GPO, можно применить метод SearchGPOs объекта GPMDomain, задав в качестве аргумента пустой объект GPMSearchCriteria. Поскольку объект GPMSearchCriteria также может использоваться с методом SearchSites объекта GPMSitesContainer и методом SearchSOMs объекта GPMDomain, логично было бы предположить, что можно таким же образом использовать в этих методах пустой объект GPMSearchCriteria и получить, соответственно, перечень всех объектов SOM, относящихся к сайтам или перечень всех объектов SOM, относящихся к доменам и OU. Однако, хотя это и не очевидно, данные методы подобным образом работать не будут. Если объект GPMSearchCriteria используется с методами SearchSites и SearchSOMs, необходимо обязательно задавать критерий, в противном случае будет выдано сообщение об ошибке.
Сформировать список всех сайтов, доменов и OU в дереве AD, к которым привязаны объекты GPO, можно двумя способами. Во-первых, можно проанализировать содержимое AD с помощью сценария, такого как ListSOMPolicyTree.wsf. При установке GPMC данный файл помещается в каталог C:program filesgpmcscripts. Во-вторых, можно воспользоваться показанным в Листинге 3 сценарием FindAllSOMs.vbs, с помощью которого получить перечень всех объектов GPO, а затем найти для них объекты SOM.
Сценарий FindAllSOMs.vbs начинается с установки соединения с объектами GPMDomain и GPMConstants. Затем получаем объект GPMGPOCollection, содержащий предназначенную для дальнейшего просмотра коллекцию GPO. Это реализуется при помощи того же кода, что и в сценарии SearchAndReport.vbs. Однако в отличие от SearchAndReport.vbs, в сценарии FindAllSOMs.vbs выполняется полная очистка переменной gpmSearchCriteria, которой присваивается значение "Nothing" (см. фрагмент кода с меткой A в Листинге 3). Очистка переменной сделана для того, чтобы сценарий мог повторно использовать ее в дальнейшем. Конечно, процедура полной очистки переменной перед ее повторным использованием не является обязательным требованием, однако подобный подход упрощает процесс модифицирования сценария, если в дальнейшем возникнет такая необходимость.
Итак, коллекция GPO получена, теперь выполняется ее обработка с помощью цикла For Each...Next. Внутри цикла после вывода данных по текущему GPO создается один объект GPMSearchCriteria, записываю его в очищенную переменную gpmSearchCriteria и задаю критерий, указывающий на текущий объект GPO. В результате я могу применить метод SearchSOMs объекта GPMDomain и сформировать для данного GPO коллекцию объектов SOM. После повторной очистки переменной gpmSearchCriteria (для подготовки перехода к следующему элементу коллекции в ходе цикла), выполняется отображение данных для каждого отдельного объекта SOM. Обратите внимание, что в отличие от сценария FindSOMsforGPO.vbs, здесь отображается не путь к каждому из объектов SOM, а его имя.
Как видно из фрагмента кода, обозначенного меткой B (см. Листинг 3), далее определяется – чем является данный объект SOM: сайтом, доменом или OU. Для этого я использую конструкцию Select Case и объект GPMConstants. После того как тип объекта определен, Select Case отображает его вслед за именем объекта SOM.
И, наконец, с помощью метода Path объекта GPMSOM находим путь к каждому объекту SOM, а затем, используя метод GetGPOLinks объекта GPMSOM, выявляем привязки к GPO для каждого объекта SOM. Каждая связь представлена соответствующим идентификатором GUID, кроме этого я включил сюда порядок связей (т.е. указываю порядок, в котором задействуются эти связи). В целях улучшения восприятия выводимой информации используется форматирование текста с помощью перехода на другую строку с возвратом каретки (vbCrLf) и табуляции (vbTab).
Приведенный в Листинге 3 сценарий лучше запускать через cscript.exe из командной строки. При этом прокрутка выводимого текста выполняется намного более эффективно.
Запуск сценариев и дальнейшие эксперименты
Итак, теперь вам известно, как можно с помощью сценариев выполнять простые и несколько более сложные процедуры поиска через GPMC. Если вы собираетесь использовать три рассмотренных здесь сценария, тогда в них нужно соответствующим образом изменить значения констант. Далее можно запускать эти сценарии из окна командной строки с помощью следующих команд:
cscript.exe SearchAndReport.vbscscript.exe FindSOMsforGPO.vbscscript.exe FindAllSOMs.vbs
В дополнение к изложенному выше я настоятельно рекомендую вам ознакомиться с документом "Group Policy Management Console Reference" и начать экспериментировать с созданием своих сценариев для организации поиска через GPMC, а также для автоматизации других задач, связанных с политиками.
Список литературы
СТАТЬЯ WINDOWS IT PRO/RE
Алистер Лоу-Норрис, "Управление объектами групповой политики с помощью сценариев",
http://www.osp.ru/text/302/3154185/
СТАТЬИ MICROSOFT
"Enterprise Management with the Group Policy Management Console"
http://www.microsoft.com/windowsserver2003/gpmc
"Group Policy Management Console Reference"
КНИГА
Robbie Allen and Alistair G. Lowe-Norris, Active Directory, 2nd edition, "Chapter 7: Profiles and Group Policy Primer" and "Chapter 10: Designing Organization-Wide Group Policies" (O'Reilly and Associates, 2003)
ЛИСТИНГ 1: SearchAndReport.vbs
Const DOMAIN = "mydomain.mycorp.com"
Dim gpm, gpmDomain, gpmGPO, gpmSearchCriteria, colGPOs
' BEGIN CALLOUT A
Set gpm = CreateObject("GPMGMT.GPM")
Set gpmDomain = gpm.GetDomain (DOMAIN, "", 0)
Set gpmSearchCriteria = gpm.CreateSearchCriteria
' END CALLOUT A
' BEGIN CALLOUT B
Set colGPOs = gpmDomain.SearchGPOs(gpmSearchCriteria)
' END CALLOUT B
WScript.Echo "There are " & colGPOs.Count & " GPOs in the domain"
For Each gpmGPO in colGPOs
WScript.Echo gpmGPO.ID _
& vbCrLf & vbTab & gpmGPO.DisplayName _
& vbCrLf & vbTab & gpmGPO.Path
Next
ЛИСТИНГ 2. FindSOMsforGPO.vbs
Const GUID = "{31B2F340-016D-11D2-945F-00C04FB984F9}"
Const DOMAIN = "mydomain.mycorp.com"
Dim gpm, gpmDomain, gpmGPO, gpmSearchCriteria
Dim gpmConstants, colDOUSOMs, gpmSOM
‘ BEGIN CALLOUT A
Set gpm = CreateObject("GPMGMT.GPM")
Set gpmDomain = gpm.GetDomain(DOMAIN, "", 0)
Set gpmGPO = gpmDomain.GetGPO(GUID)
‘ END CALLOUT A
‘ BEGIN CALLOUT B
Set gpmSearchCriteria = gpm.CreateSearchCriteria
Set gpmConstants = gpm.GetConstants
gpmSearchCriteria.Add gpmConstants.SearchPropertySOMLinks, _
gpmConstants.SearchOpContains, gpmGPO
Set colDOUSOMs = gpmDomain.SearchSOMs(gpmSearchCriteria)
‘ END CALLOUT B
' BEGIN CALLOUT C
WScript.Echo "GPO is: " & GUID
WScript.Echo "There are " & colDOUSOMs.Count " domain & OU SOMs for the GPO."
For Each gpmSOM in colDOUSOMs
WScript.Echo gpmSOM.Path
Next
' END CALLOUT C
ЛИСТИНГ 3: FindAllSOMs.vbs
Const DOMAIN = "mydomain.mycorp.com"
Dim gpm, gpmDomain, gpmGPO, gpmSearchCriteria, colGPOs
Dim gpmConstants, colDOUSOMs, gpmSOM, gpmGPOLink
Dim colGPOLinks
Set gpm = CreateObject("GPMGMT.GPM")
Set gpmDomain = gpm.GetDomain (DOMAIN, "", 0)
Set gpmConstants = gpm.GetConstants
Set gpmSearchCriteria = gpm.CreateSearchCriteria
Set colGPOs = gpmDomain.SearchGPOs(gpmSearchCriteria)
‘ BEGIN CALLOUT A
Set gpmSearchCriteria = Nothing
‘ END CALLOUT A
WScript.Echo "There are " & colGPOs.Count & " GPOs in the domain"
For Each gpmGPO in colGPOs
WScript.Echo gpmGPO.ID _
& vbCrLf & vbTab & gpmGPO.DisplayName _
& vbCrLf & vbTab & gpmGPO.Path
Set gpmSearchCriteria = gpm.CreateSearchCriteria
gpmSearchCriteria.Add _
gpmConstants.SearchPropertySOMLinks, _
gpmConstants.SearchOpContains, gpmGPO
Set colDOUSOMs = _
gpmDomain.SearchSOMs(gpmSearchCriteria)
Set gpmSearchCriteria = Nothing
WScript.Echo vbCrLf & vbTab & "There are " & _
colDOUSOMs.Count " domain & OU SOMs."
For Each gpmSOM in colDOUSOMs
‘ BEGIN CALLOUT B
Select Case gpmSOM.Type
Case Constants.SOMSite
WScript.Echo vbCrLf & vbTab & _
gpmSOM.Name & " (Site)"
Case Constants.SOMDomain
WScript.Echo vbCrLf & vbTab & _
gpmSOM.Name & " (Domain)"
Case Constants.SOMOU
WScript.Echo vbCrLf & vbTab & _
gpmSOM.Name & " (OU)"
End Select
‘ END CALLOUT B
colGPOLinks = gpmSOM.GetGPOLinks
WScript.Echo vbCrLf & vbTab & vbTab & gpmSOM.Path
For Each gpmGPOLink in colGPOLinks
WScript.Echo vbCrLf & vbTab & vbTab & _
gpmGPOLink.GPOID
WScript.Echo vbCrLf & vbTab & vbTab & _
gpmGPOLink.SOMLinkOrder
Next
Next