Утверждение отчетов WSUS для группы

9

Я пытаюсь найти способ создания отчета WSUS об обновлениях, которые были утверждены для группы компьютеров A, которые не были утверждены для одной или нескольких других групп. Кроме того, табличный отчет, в котором перечислены статус утверждения для каждого обновления и каждой группы, так что он может быть обработан, чтобы извлечь то, что мне нужно. Похоже, в самом WSUS такого отчета нет, или, по крайней мере, я не могу его найти, поэтому сценарий для создания такого отчета был бы весьма желательным.

Джон Гарденье
источник
На какой версии Windows работает ваш WSUS?
Nate
@Nate, это WSUS 3.2.7600.226, работающий на 64-битной машине Server 2008 R2 Standard.
Джон Гарденье
Я думаю, что у меня есть решение для вас, дайте мне несколько, и я подтвердлю
Нейт

Ответы:

8

Этот скрипт powershell делает именно то, что было в вашем первоначальном запросе. Изучите одну группу компьютеров и найдите обновления, не утвержденные для одной или нескольких других групп компьютеров.

Примечание. Вам нужно будет выполнить это либо на сервере WSUS, либо на компьютере, на котором установлены средства администрирования WSUS.

конфигурация

Задайте $targetComputerGroupдля группы компьютеров, которую вы хотите использовать в качестве базовой линии. Укажите $CheckForMissingимена групп или групп, для которых вы хотите узнать, были ли они утверждены. Примечание: чтобы сделать кратные просто кома отдельно ("Group1, Group2")

$serverName="localhost"
$targetComputerGroup="BaselineGroup"
$checkForMissing="MissingGroup1,MissingGroup2"

[void][reflection.assembly]::LoadWithPartialName("Microsoft.UpdateServices.Administration")
$wsus=[Microsoft.UpdateServices.Administration.AdminProxy]::getUpdateServer($serverName,$false)
$computerGroup=$wsus.GetComputerTargetGroups()|ForEach-Object -Process {if ($_.Name -eq $targetComputerGroup) {$_}}
$UpdateScope=New-Object Microsoft.UpdateServices.Administration.UpdateScope
$UpdateScope.ApprovedStates="Any"
$updateScope.ApprovedComputerTargetGroups.Add($computerGroup)
$Approvals = $wsus.GetUpdateApprovals($UpdateScope)

#At this point we have all of the updates assigned to the $targetComputerGroup

$report= @()
write-host "Querying for all Updates approved for $targetComputerGroup"

foreach ($Approval in $approvals) {
   $record=""|Select-Object ComputerGroup,UpdateName, UpdateID
   $record.ComputerGroup=$wsus.GetComputerTargetGroup($Approval.ComputerTargetGroupID).Name
   $record.UpdateName=$wsus.GetUpdate($Approval.UpdateID).Title
   $record.UpdateID=$wsus.GetUpdate($Approval.UpdateID).ID.UpdateID
   $report +=$record
   }

#Now group the results by UpdateName
$GR=$report|group -Property UpdateName

$CheckForMissing=$CheckForMissing.Split(",")

 foreach ($entry in $gr) {
    $groups=@()
    foreach ($g in $entry.Group) {
        $groups += $g.ComputerGroup
        }
    foreach ($missing in $checkForMissing) {
        if ($groups -Contains $missing) {}
        else{
            New-Object PSObject -Property @{
            Name = $entry.Name
            UpdateID = $entry.Group[0].UpdateID
            GroupMissing = $missing
            }
        }
    }
}

После завершения у вас будет вывод как: введите описание изображения здесь

Если вместо вывода на экран вы хотите экспортировать список в CSV, замените нижнюю часть следующим кодом:

   $CheckForMissing=$CheckForMissing.Split(",")
   $CSVdata=@()
     foreach ($entry in $gr) {
        $groups=@()
        foreach ($g in $entry.Group) {
            $groups += $g.ComputerGroup
            }
        foreach ($missing in $checkForMissing) {
            if ($groups -Contains $missing) {}
            else{
                $CSVdata += New-Object PSObject -Property @{
                Name = $entry.Name
                UpdateID = $entry.Group[0].UpdateID
                GroupMissing = $missing
                }
            }
        }
    }
 $CSVdata|Export-Csv "FILENAME.CSV"
Nate
источник
Оно работает! Вы знаете, как остановить усечение вывода? Кстати, я не могу присудить награду еще 9 часов.
Джон Гарденье
1
Усечение - это функция форматирования PowerShell для экрана. Я обновил ответ с примером вывода в файл CSV, чтобы вы могли получить полные значения.
Nate
Отлично, так как CSV очень подходит для моих нужд. Отсюда я могу передать его в Perl, где, по крайней мере, я знаю, что делаю. Очень признателен.
Джон Гарденье
7

Можно «просто» подключиться к базе данных WSUS и выполнить запросы к ней:

  1. Запустите SQL Management Studio с повышенными привилегиями.
  2. Подключитесь к \\.\pipe\MSSQL$MICROSOFT##SSEE\sql\queryиспользованию Windows Authentication .

Эти таблицы, кажется, представляют интерес для вашего вопроса:

  • tbUpdate
    Содержит информацию об отдельных обновлениях

  • tbTargetGroup
    Содержит информацию обо всех группах компьютеров

  • tbDeployment
    Содержит информацию о том, какие обновления были одобрены для каких групп компьютеров.

Однако представляется целесообразным использовать уже существующее представление vUpdateApprovalдля получения большей части информации, которую вы ищете, поскольку это представление уже переводит ActionIDстолбец из tbDeploymentдругих вещей.

Представление vUpdateApproval, однако, не включает легко читаемые заголовки для обновлений. Названия обычно читаются из tbLocalizedProperty. Для того, чтобы сделать его проще для нас, есть еще один вид: vUpdate.

На самом деле у меня нет нужных данных в нашей базе данных WSUS для построения правильного запроса, который бы соответствовал вашему первому запросу (и я не достаточно уверен, чтобы создавать его вслепую). Итак, вот подход для вашего вторичного запроса. Если я не испортил, он выдает список всех обновлений и состояние утверждения для всех групп.

SELECT
    aUpdate.UpdateId,
    aUpdate.DefaultTitle,
    aGroup.Name as GroupName,
    aApproval.Action as Action
FROM
    PUBLIC_VIEWS.vUpdate AS aUpdate INNER JOIN
    PUBLIC_VIEWS.vUpdateApproval AS aApproval ON aUpdate.UpdateId = aApproval.UpdateId LEFT JOIN
    dbo.tbTargetGroup as aGroup ON aGroup.TargetGroupID = aApproval.ComputerTargetGroupId
;

Который производит этот вывод на нашем немецком SBS:

введите описание изображения здесь

Для нашего SBS с его 5 группами по умолчанию это дает 121558 строк результата за ~ 26 с. Поэтому, если вы хотите поэкспериментировать с запросом, рекомендуется изменить первую строку на SELECT TOP 1000время тестирования.

Я также нашел время, чтобы обернуть все это в сценарий PowerShell:

# Where to connect to
$dataSource        = "\\.\pipe\MSSQL`$MICROSOFT##SSEE\sql\query"
$connectionTimeout = 30

# The query we want to perform against the WSUS database
$query = @"
    SELECT TOP 10
        aUpdate.UpdateId,
        aUpdate.DefaultTitle,
        aGroup.Name as GroupName,
        aApproval.Action as Action
    FROM
        PUBLIC_VIEWS.vUpdate AS aUpdate INNER JOIN
        PUBLIC_VIEWS.vUpdateApproval AS aApproval ON aUpdate.UpdateId = aApproval.UpdateId LEFT JOIN
        dbo.tbTargetGroup as aGroup ON aGroup.TargetGroupID = aApproval.ComputerTargetGroupId
"@
$queryTimeout = 120

# Construct the connection string
$connectionString = "Data Source={0};Integrated Security=True;Connect Timeout={1};Database=SUSDB" -f $dataSource,$connectionTimeout

# Open the connection to the SQL server
$connection = New-Object System.Data.SqlClient.SQLConnection
$connection.ConnectionString = $connectionString
$connection.Open()

# Construct our SQL command
$sqlCommand = New-Object system.Data.SqlClient.SqlCommand( $query, $connection )
$sqlCommand.CommandTimeout = $queryTimeout

# Retrieve the data from the server
$dataSet     = New-Object system.Data.DataSet
$dataAdapter = New-Object system.Data.SqlClient.SqlDataAdapter( $sqlCommand )
[void]$dataAdapter.fill( $dataSet )

# Clean up
$connection.Close()

# Output result
$dataSet.Tables

Обратите внимание, что в этот скрипт включено SELECT TOP 10ограничение, позволяющее избежать затопления вашей оболочки во время тестирования.

Der Hochstapler
источник
Это, безусловно, что-то для расследования. Возможно, есть модуль Perl для взаимодействия с MS SQL Server.
Джон Гарденье
@JohnGardeniers: я добавил скрипт PowerShell, который выполняет запрос. К сожалению, мои знания Perl еще хуже :)
Der Hochstapler
Это хорошая отправная точка, но я должен выяснить, как остановить усеченный вывод.
Джон Гарденье
@JohnGardeniers: по умолчанию PowerShell отображает возвращаемые объекты. Вы можете запустить скрипт, как myscript.ps1 | flполучить другой (не усеченный) вывод.
Der Hochstapler
Я решил наградить вас за ваши усилия, но вам придется ждать 24 часа. Система не позволит мне немедленно получить награду.
Джон Гарденье