null

Windows PowerShell: Получаем список установленных программ.

Доброго всем времени суток.
Не так давно увлёкся Windows PowerShell.
Скриптов за это время скопилось не мало, в следствии чего, в данном блоге, я решил запустить цикл статей, содержащих, пожалуй, самые полезные из них. И так:

##############################################################################
#                                                                            #
#        Получение списка всех установленных програмных продуктов  на        #
#                    Системе Windows используя PoSh.                         #
#                                                                            #
#         Ver.1.0                                                            #
#         Tested OS: Windows 10                                              #
#         Tested PowerShell: 5.0.10240.16384                                 #
#                                                                            #
#         Author: Patrahin Nikita                                            #
#         e-mail: Nikita.Patrahin@tune-it.ru                                 #
#                                                                            #
##############################################################################

Write-Output ("`n`t`Приступаю к анализу системы...`n")	
Write-Output ("`n`---------------------------------------------------------")

#Объявляем функцию содержащую способ вывода и сорт. по свойству DisplayName.
function Grid-Output

{
    param (
    <#
      Объявляем, что наличие массива элементов указанного ниже для работы 
      данной функции явлется строго обязательным
    #>
     [Parameter (Mandatory = $true)] 
        [Array] $Massive             
    )

    <#
      Сортируем вывод по свойству DisplayName, далее указываем формат вывода 
      GridView
    #>
    $Massive |sort-object -property DisplayName | Out-GridView
}

<#
  Получаем объекты из реестра.
 
  На данном этапе из реестра мы получ. объекты типа: 
  System.MarshalByRefObject.RegistryKey (Microsoft.Win32.RegistryKey)
  Отдельный объект для этих целей был создан потому что: 
    
    1.Возможно данный объект, в последующем, необходимо будет изменить. 
      Скорее всего даже на функцию анализирующую массивы 
      элементов описанных ниже, формируя единый массив: 
       1.1: $soft = Get-WmiObject -Class Win32_Product
       1.2: $soft32 = gci "HKLM:\SOFTWARE\Wow6432Node\Microsoft\Windows\CurrentVersion\Uninstall"
       1.3: $soft64 = gci "HKLM:\SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall"

       В связи с этим мы изолируем его для упрощения последующих модификаций. 

    2. Улучшает читабельность кода. 
#>
[array]$RegUnistValues = Get-ChildItem HKLM:\SOFTWARE\Wow6432Node\Microsoft\Windows\CurrentVersion\Uninstall

<#
  Генерируем объекты Automation.PSCustomObject для каждого свойства полученных ранее объектов Win32.RegistryKey 
  Более подр. информацию по Get-ItemProperty можно почитать тут: 
  https://technet.microsoft.com/ru-ru/library/hh849851.aspx 
#>
[String]$temp = 'Здесь будут временно содержаться значения' 
[Array]$temp = $RegUnistValues | ForEach-object {(Get-ItemProperty Microsoft.PowerShell.Core\Registry::$_)}

<# 
   Создаём запрос на активацию фильтра.
   Для этого мы генерируем popup запрос вывод которого записываем в объект $result.
   
   object.Popup(strText,[nSecondsToWait],[strTitle],[nType]) в данном случае имеет следующие параметры:
   
   strText = "Активировать фильтрацию столбцов?" / Текст запроса
   nSecondsToWait = 10 / время ожидания ответа от пользователя
   strTitle =  "Question" / Не обязательное значение. Данная строка будет отображаться в сообщения.
   nType = 4+32 / Типы кнопок во всплывающем сообщении. В данном случае :
        4 = Сочетание кнопок "Да" и "Нет"
        32 = Рисунок знака вопроса в сообщении

        Более подробную информацию можно взять тут: 
        https://msdn.microsoft.com/en-us/library/x83z1d9f(v=vs.84).aspx
#>
$shell = new-object -comobject "WScript.Shell"
$result = $shell.popup("Активировать фильтрацию столбцов?",10,"Question",4+32) 

<# 
  Используем оператор Switch для анализа знчений объект $result 
  (ВНИМАНИЕ!! использование данного оператору в больших проектах с .Net объектами неприемлимо
  и считается дурным тоном, так как сильно затрудняет читабильность кода. Аналогов в данном 
  случае я, к сожалению, не нашёл)
  В данном случае объект $result у нас может иметь 3 варианта:
    
    1. -1 : если в popup окне пользователь не нажал ни одну кнопку, и окно было закрыто по Тайм-Ауту.
    2.  6 : если в popup окне пользователь нажал "Да"
    3.  7 : если в popup окне пользователь нажал "Нет" 

    Соответственно, в зависимости от значения $result выполняется сценарий.
    P.S.: значение -1 и все остальные возможные значения исключая 6 и 7 у меня перекрывает сценарий: Default.
    Сделано на случай если $result вернёт вместо значения ошибку. 
#>

Switch ($result) {

	6 { 
        Write-Output ("`n`t`Фильтр активирован.`n")

        <# 
            В данном конкретном случае меня интересовали свойста DisplayName, DIsplayVersion, PSChildName.
            Однако никто не запрещает выбрать самостоятельно. Напоминаю, что все доступные свойтсва объекта 
            можно получить: $тут_будет_указан_объект_свойства_которого_хотим_посмотреть | Get-Member
                        
            В это конкретном случае $temp | Get-Member
            Далее выбираем из свойств NoteProperty, указываем через запятую после Select-Object -Property. 
            Выбранные нами свойства будут являться заголовками столбцов при выводе. 
        #>
        #вывод полученных данных с помощью ранее написанной функции Grid-Output
        Grid-Output -Massive ($temp | Select-Object -Property DisplayName, DIsplayVersion, PSChildName) 
        	
	}

	7 {
        Write-Output ("`n`t`Фильтр отключен.`n")
        #вывод полученных данных с помощью ранее написанной функции Grid-Output#
        Grid-Output -Massive $temp 
        
    }
    
	Default {
                Write-Output ("`n`t`Время на подтверждение активации фильтра истекло. Фильтр отключен.`n") 
                #вывод полученных данных с помощью ранее написанной функции Grid-Output
                Grid-Output -Massive $temp
    
    }

}

#Обнуляем значение, дабы не оставлять после себя артефактов со значениями реестра.
[String]$RegUnistValues = 'Здесь содержались значения реестра' 
[String]$temp = 'Здесь временно содержались значения' 

Write-Output ("`n`t`Запрос успешно обработан.`n") 
Write-Output ("`n`---------------------------------------------------------") 
Write-Output ("`n`t`Работа скрипта завершена.`n") 

<# 
  Блокируем автоматическое закрытие окна PowerShell после выполнения скрипта. В данном конкретном случае, 
  мне необходимо было сделать именно таким образом, однако правильнее будет запустить скрипт с ключом: 
  powershell.exe -NoExit -command c:\myscript.ps1 
  Ибо вносить для этого отдельные изменения в сценарий не рекомендуется. 
#> 
$host.ui.RawUI.ReadKey(6)|out-null

 
 
Назад