Управління виведенням команд у PowerShell – повний посібник для тих, хто бажає ефективно працювати з командною оболонкою PowerShell та впевнено керувати виведенням результатів команд. Використання команд у PowerShell дозволяє взаємодіяти з операційною системою, виконувати завдання та отримувати результати. Проте, іноді виведення може бути перевантаженим або складним для аналізу. В цьому посібнику ми розглянемо різні підходи до управління виведенням команд, такі як фільтрація, сортування, збереження результатів у файл, а також використання потоків виведення. Ви дізнаєтесь про різноманітні опції та функції, які дозволять вам легко знаходити необхідну інформацію, контролювати виведення та зберігати дані для використання.
Незалежно від вашого досвіду з PowerShell, цей посібник допоможе вам оптимізувати вашу роботу з командами, полегшить аналіз результатів та підвищить вашу продуктивність при роботі з цією потужною командною оболонкою. Працюючи в оболонці PowerShell, ми поки що не замислювалися, яким чином система формує рядки тексту, які виводяться на екран в результаті виконання тієї чи іншої команди (нагадаємо, що командлети PowerShell повертають .NET об’єкти, які, як правило, не знають, як відображати себе на екрані). Насправді PowerShell має базу даних (набір XML-файлів), що містить модулі форматування за умовчанням для різних типів .NET-об’єктів. Ці модулі визначають, які властивості об’єкта відображаються під час виведення та у якому форматі: списку чи таблиці. Розташовуються модулі форматування в каталозі, де встановлено PowerShell (шлях до цього каталогу зберігається в змінному оточенні $pshome), переглянути їх список можна за допомогою наступної команди: PS С:\> Get-Childltam $PSHCME/*format*
Працюючи в PowerShell, ми ще не замислювалися про те, як система генерує рядки тексту, які відображаються в результаті виконання тієї чи іншої команди (нагадаємо, що командлети PowerShell повертають . NET об’єкти, які зазвичай не вміють відображати себе на екрані).
По суті, PowerShell має базу даних (набір, який містить форматувальники за замовчуванням для різних . НЕТТО-06ЕкТ0Б. Ці модулі визначають, які властивості об’єкта відображаються на виході і в якому форматі: списки і таблиці. Форматувальники розташовуються в директорії, де встановлена PowerShell (шлях до цього каталогу зберігається в змінній середовища $PSHOME), переглянути їх список можна за допомогою наступної команди:
PS С:\> Get-Childltam $PSHCME/*format* Каталог: С:\Windows\System32\WindowsPowerShell\vl.О Mode LastWriteTime Length Name -а--- 07.12.2019 12:10 12825 Certificate.format.pslxml -а--- 07.12.2019 12:10 4994 Diagnostics.Format.pslxml -а--- 07.12.2019 12:10 138013 DotNetTypes.format.pslxml -а--- 07.12.2019 12:10 10112 Event.Format.pslxml -а--- 07.12.2019 12:10 25306 FileSystem.format.pslxml -а--- 07.12.2019 12:10 91655 Help.format.pslxml -а--- 07.12.2019 12:10 138625 HelpV3.format.pslxml -а--- 07.12.2019 12:10 206468 PowerShellCore.format.pslxml -а--- 07.12.2019 12:10 4097 PowerShellTrace.format.pslxml -а--- 07.12.2019 12:10 8458 Registry.format.pslxml -а--- 07.12.2019 12:10 16598 WSMan.Format.pslxml
Коли об’єкт досягає кінця конвеєра, PowerShell визначає його тип і шукає його в списку об’єктів, для яких встановлено правило форматування. Якщо цей тип зустрічається в списку, до об’єкта застосовується відповідна форма; якщо ні, PowerShell просто відображає властивості цього . НЕТТО-06РКТА.
Ви також можете явно встановити правила форматування для командлетів і, як і інші консольні програми, перенаправити ці дані на файл, принтер або на порожній пристрій.
У традиційних оболонках команди і утиліти самі форматують вихід. Деякі команди (наприклад, dir в інтерпретаторі cmd.exe) дозволяють налаштувати вихідний формат за допомогою спеціальних ключових параметрів.
У PowerShell результат відформатовано чотирма спеціальними командлетами формату (табл. 6.1). Це спрощує навчання, оскільки вам не потрібно запам’ятовувати інструменти та параметри форматування для інших команд (решта командлетів не форматують вивід).
Як зазначалося раніше, якщо жоден з командлетів Format явно не вказано, використовується formatter за замовчуванням, який визначається типом даних, що відображаються. Наприклад, під час запуску командлета Get-Service виводом за замовчуванням є таблиця з трьома стовпцями (Status, Name і Disp1ayName):
DisplayName)* PS С:\> Get-Service Status Name DisplayName Stopped Alerter Running ALG Stopped AppMgmt Stopped aspnet state Running Ati HotKey Poller Running Audiosrv Running BITS Оповещатель Служба шлюза уровня приложения Управление приложениями ASP.NET State Service Ati HotKey Poller Windows Audio Фоновая интеллектуальная служба пер... Running Browser Обозреватель компьютеров Stopped cisvc Служба индексирования Stopped ClipSrv Сервер папки обмена Stopped clr optimizatio.. . .NET Runtime Optimization Service v Stopped COMSysApp Системное приложение COM+ Running CryptSvc Службы криптографии Running DcomLaunch Запуск серверных процессов DCOM Running Dhcp DHCP-клиент
Щоб змінити формат виводу, його потрібно передати до відповідного командлета Fornat. Наприклад, за допомогою командлета Format-List у наведеній нижче команді буде перелічено такі команди:
PS С:\> Get-Service | Format-List Name DisplayName Status DependentServices ServicesDependedOn CanPauseAndContinue : Alerter : Оповещатель : Stopped : {} : {LanmanWorkstation} : False CanShutdown : False CanStop ServiceType : False : Win32ShareProcess Name DisplayName Status DependentServices ServicesDependedOn CanPauseAndContinue CanShutdown : ALG : Служба шлюза уровня приложения : Running : {} : {} : False : False CanStop ServiceType : True : Win320wnProcess
Як бачимо, під час використання формату списку відображається більше відомостей про кожну службу, ніж формат таблиці (замість трьох стовпців даних про кожну службу у форматі списку відображається дев’ять рядків даних). Однак це не означає, що командлет списку форматів отримує додаткові відомості про служби. Ця інформація міститься в об’єктах, повернутих командою Get-Service, але типовий командлет Fomat-Tab1e відкидає її, оскільки вона не може відображати більше трьох стовпців. Під час форматування виводу за допомогою командлетів Format-List і Fonnat-Tab1e можна вказати імена властивостей об’єкта, які потрібно відобразити (нагадаємо, що список властивостей об’єкта можна переглянути в командлеті Get-Member). Наприклад:
PS С:\> Get-Service | Format-List Name, Status, CanStop Name : Alerter Status : Stopped CanStop : False Name : ALG Status : Running CanStop : True Name : AppMgmt Status : Stopped CanStop : False Вывести все имеющиеся у объектов свойства можно с помощью параметра *, например: PS С:\> Get-Service Format-List * Name CanPauseAndContinue CanShutdown CanStop DisplayName Dependentservices MachineName ServiceName ServicesDependedOn ServiceHandle Status ServiceType Site Container Name CanPauseAndContinue CanShutdown Alerter False False True Оповещатель {} Alerter {LanmanWorkstation} SafeServiceHandle Running Win32ShareProcess : ALG : False : False
В оболонці PowerShell є кілька командлетів, за допомогою яких можна керувати виведенням даних. Ці командлети починаються зі слова Out, їх список можна побачити так:
PS С:\> Get-Command out-* | Format-Table Name Name Out-Default Out-File Out-GridView Out-Host Out-Null Out-Printer Out-String
За замовчуванням вивід передається командлету 0ut-Defau1t, який, у свою чергу, делегує всю роботу відображення рядків командлету 0ut-Host. Щоб зрозуміти цей механізм, слід мати на увазі, що архітектура PowerShell має на увазі відмінність між самим ядром оболонки (інтерпретатором команд) і хост-додатком, що використовує це ядро. В принципі, в якості хоста може виступати будь-який додаток, що реалізує ряд спеціальних інтерфейсів, що дозволяють правильно інтерпретувати інформацію, отриману від PowerShell. У нашому випадку хост – це консольне вікно (термінал), в якому ми працюємо з оболонкою, а командлет 0utHost передає вихідну інформацію в це вікно.
Параметр -Paging командлета Out-Host, аналогічний команді інтерпретатора cmd.exe дозволяє організувати посторінкове відображення інформації, наприклад:
PS С:\> Get-Help Get-Process -Full | Out-Host -Paging ИМЯ Get-Process ОПИСАНИЕ Отображает процессы, выполняющиеся на локальном компьютере. СИНТАКСИС Get-Process [[-name] <string[]>] [<CommonParameters>] <ПРОБЕЛ> следующая страница; <CR> следующая строка; Q выход
Як уже згадувалося, PowerShell підтримує перенаправлення стандартного потоку вихідних команд у текстові файли за допомогою стандартних операторів > та >>. Наприклад, наступна команда відобразить вміст кореневого каталогу c:\ до текстового файлу d:\dir c.txt (якщо цей файл існував, його буде перезаписано):
PS C:\> реж. C:\ > d:\dir c.txt
Якщо потрібно перенаправити вихід команди на файл в режимі додавання (зі збереженням попереднього вмісту цього файлу), слід скористатися оператором >>:
PS DXR з:\ >> d: \dxr c.txt
Крім операторів перенаправлення > і >>, PowerShell також має командлет під назвою 0utFile, який також дозволяє направляти вихід в текстовий файл замість вікна консолі. При цьому командлет 0ut-Fi1e має кілька додаткових параметрів, за допомогою яких можна більш гнучко управляти виводом: задати тип кодування файлів, задати довжину вихідних рядків в символах і вибрати режим перезапису файлів (табл. 6.2).
Наприклад, наведена нижче команда збереже в довідці.txt файл докладної версії вбудованої довідки для командлета Get-Process в Windows-кодировке:
PS С:\Users\andrv> Get-Help Get-Process -Detailed | Out-File -FilePath .\help.txt -Encoding "Default"
Можна друкувати дані безпосередньо на принтері за допомогою командлета Out-Printer. При цьому друк може виконуватися або на принтері за замовчуванням (для цього не потрібні спеціальні параметри), або на довільному принтері (в цьому випадку коротке ім’я принтера потрібно вказувати як значення параметра -Name). Наприклад:
PS C:\script> Get-Process | Out-Printer -Name "Xerox Phaser 3500 PCL 6"
Використовуйте командлет 0ut-Nu11, щоб скасувати будь-які вхідні дані. Це може бути корисно для придушення відображення непотрібної інформації, отриманої як побічний ефект виконання команди. Наприклад, при створенні каталогу командою mkdir відображається його вміст:
PS С:\> mkdir klop Каталог: Microsoft.PowerShell.Core\FileSystem::С:\ Mode LastWriteTime Length Name d--- 26.05.2020 15:01 klop Если мы не желаем видеть эту информацию, то результат выполнения команды mkdir нужно передать по конвейеру командлету Out-Null: PS С:\> mkdir klop | Out-Null PS C:\> Как видим, в этом случае никаких сообщений на экран не выводится.
За допомогою командлета 0ut-GridView, як і з Fornat-Table, можна відображати дані в табличному вигляді, але не в тому ж вікні консолі, а в окремому діалоговому вікні з графічним інтерфейсом.
Наприклад, запустіть таку команду:
ps C: \> Get-Process Out-GridView
При цьому інформація про процеси буде доступна в окремому вікні (Мал . 6.1)
У рядку заголовка цього вікна відображається виконана команда PowerShell, а при необхідності можна змінити заголовок, вказавши параметр -Tit1e:
PS С:\> Get-Process | Out-GridView -Title ’’Process”
Відображувану таблицю можна відсортувати за значеннями будь-якого стовпця, натиснувши на його назву. Також можна фільтрувати рядки за різними умовами за допомогою конструктора фільтрів (Мал 6.2).
Табличний вигляд даних, що генеруються Out-GridView, є інтерактивним і може бути змінений безпосередньо в самій таблиці. Більше того, результуючий набір рядків, отриманий за допомогою сортування, фільтрації та виділення, можна знову повернути до PowerShell, натиснувши OK, і надіслати далі вниз. Для цього потрібно вказати –PassThru. Наприклад:
PS С:\> Get-Process 1 Out-GridView -Title "Процессы" -PassThru | Format-Table Id, ProcessName
Id ProcessName 836 wininit 12412 WINWORD
У цьому прикладі рядки (об’єкти) з наступного вікна передано командлету Format-Table
Рядки, які потрібно повернути в конвеєр PowerShell з діалогового вікна, повинні бути виділені в поданні таблиці (за замовчуванням повертається тільки перший рядок).
Тут підтримуються стандартні комбінації:
<Ctrl>+<A> для введення всіх рядків;
Утримуйте <Shift> та стрілки вгору або вниз, щоб вибрати суміжний діапазон рядків;
Утримуйте <Ctrl> і клацніть, щоб додати окремі рядки
PowerShell має стандартний командлет під назвою ConvertTo-Htm1, який можна використовувати для відображення результатів ваших команд. Наприклад, давайте використаємо Get-PSDrive, щоб отримати список дисків PowerShell і перетворити список у HTML:
PS С:\Users\andrv> Get-PSDrive I ConvertTo-Html <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN” "http://www.w3.org/TR/xhtmll/DTD/xhtmll-strict.dtd"> <html xmlns="http://www.w3.org/1999/xhtml"> 118 Часть I. Знакомимся с PowerShell <head> <title>HTML TABLE</title> </headxbody> <table> <colgroupxcol/xcol/xcol/xcol/xcol/xcol/xcol/xcol/xcol/xcol/x/colgroup> <trxth>Used</thxth>Free</thxth>CurrentLocation</thxth>Name</thxth>Provider </thxth>Root</thxth>Description</thxth>MaximumSize</thxth>Credential</th> <th>DisplayRoot</thx/tr> <trxtdx/tdxtdx/tdxtdx/tdxtd>Alias</tdxtd>Microsoft. PowerShell. Core\ Alias</tdxtdx/tdxtd>HwcK, содержащий представление псевдонимов, сохраненное в состоянии сеанса. </tdxtdx/tdxtd>System.Management .Automation. PSCredential</tdxtdx/tdx/tr> <trxtdx/tdxtdx/tdxtdx/tdxtd>WSMan</tdxtd>Microsoft.WSMan. Management\ WSMan</tdxtdx/tdxtd>KopeHb хранилища конфигурации WsMan.</tdxtdx/td> <td>System. Management .Automation. PSCredential</tdxtdx/tdx/tr> </table> </bodyx/html>
Як бачимо, на виході виходить коректний HTML-документ з таблицею, оформленою за допомогою тега <tabie>. Цей висновок можна надіслати в HTML-файл і відкрити цей файл у браузері (рис. 6.4) за допомогою командлета invoke-item:
PS С:\Users\andrv> Get-PSDrive | ConvertTo-Html | Out-File psdrives.html PS C:\Users\andrv> Invoke-Item .\psdrives.html
Параметр -As List дозволяє змінювати зовнішній вигляд таблиці – властивості кожного об’єкту будуть оформлені у вигляді списку (Мал . 6.5), як при форматуванні виводу за допомогою Fomat-List:
PS С:\Users\andrv> Get-PSDrive | ConvertTo-Html -As List | Out-File psdrives. html PS C:\Users\andrv> Invoke-Item .\psdrives.html
За допомогою додаткових параметрів можна задати текст заголовка до і після таблиці:
PS С:\Users\andrv> Get-PSDrive | ConvertTo-Html -Title ’’Отчет о дисках PowerShell" -PreContent "<р>Текст до таблицы</р>" -PostContent "Текст после таблицы" | Out-File .\psdrives.html
При необходимости к формируемому HTML-документу можно подключить внешний CSS-файл, путь к которому указывается в качестве значения параметра -cssUri. Если в convertTo-HTML указан параметр -Fragment, то в HTML-разметке будет сгенерирована только таблица с данными (тег <tabie>): PS С:\Users\andrv> Get-PSDrive | ConvertTo-Html -Fragment <table> <colgroupxcol/xcol/xcol/xcol/xcol/xcol/xcol/xcol/xcol/xcol/x/colgroup> <trxth>Used</thxth>Free</thxth>CurrentLocation</thxth>Name</thxth>Provider </thxth>Root</thxth>Description</thxth>MaximumSize</thxth>Credential</th> <th>DisplayRoot</thx/tr> <trxtdx/tdxtdx/tdxtdx/tdxtd>Alias</tdxtd>Microsoft. PowerShell. Core\ Alias</tdxtdx/tdxtd>JJncK, содержащий представление псевдонимов, сохраненное в состоянии сеанса. </tdxtdx/tdxtd>System.Management .Automation. PSCredential </tdxtdx/tdx/tr> </table>
На додаток до стандартного потоку виводу 0utput, через який об’єкти передаються від командлета до командлета, PowerShell підтримує ще кілька потоків.
Наявність декількох неперетинних ланцюжків не захаращує основний потік помилками або іншими додатковими повідомленнями — командлети отримують в якості вхідних даних лише потрібні структуровані об’єкти.
Можна записувати дані в різні потоки за допомогою відповідних командлетів за допомогою дієслова Write: Write-Output, Write-Error, Write-Warning, WriteVerbose, Write-Debug і Write-Information.
Наприклад, напишемо нове повідомлення в потік помилок:
PS С:\Users\andrv> Write-Error -Message "Произошла ошибка" Write-Error -Message "Произошла ошибка" : Произошла ошибка + Categoryinfo : NotSpecified: (:) [Write-Error], WriteErrorException + FullyQualifiedErrorld : Microsoft.PowerShell.Commands.WriteErrorException
Це автоматично згенерувало об’єкт з інформацією про помилки та помістило його в потік помилок (більш детально про виявлення та обробку помилок ми поговоримо в PowerShell у главі 10). Відомості про помилки з потоку помилок також відображаються та виділяються червоним кольором.
Інформація з потоку Verbose відображається в консолі і виділяється жовтим тільки в тому випадку, якщо при виклику команди вказано параметр -Verbose:
PS С: \Users\andrv> Write-Verbose -Message "Сообщение из потока Verbose" PS С:\Users\andrv> Write-Verbose -Message "Сообщение из потока Verbose" -Verbose ПОДРОБНО: Сообщение из потока Verbose Поведение (в частности, режим вывода на экран сообщений) команд write-* зависит от значений нескольких системных переменных: PS С:\Users\andrv> $ErrorActionPreference Continue PS C:\Users\andrv> $DebugPreference SilentlyContinue PS C:\Users\andrv> $VerbosePreference SilentlyContinue PS C: \Users\andrv> $InforrnationPreference SilentlyContinue
Якщо значення змінної Si1entlyContinue, то інформація з відповідного потоку не дублюється на екрані. Для додаткових потоків PowerShell також підтримується перенаправлення на файл або на стандартний вихідний потік 0utput.
Перенаправити дані з потоку в файл можна за допомогою тих же операторів > і >>, яким передує числовий номер потоку. Наприклад:
PS С:\Users\andrv> Write-Error -Message "Произошла ошибка" 2> error.txt PS С:\Users\andrv> Get-Content .\error.txt Write-Error -Message "Произошла ошибка" 2> error.txt : Произошла ошибка + Categoryinfo : NotSpecified: (:) [Write-Error], WriteErrorException + FullyQualifiedErrorld : Microsoft.PowerShell.Commands.WriteErrorException PS C: \Users\andrv> Write-Warning -Message "Сообщение из потока Warning" 3> l.txt PS C:\Users\andrv> Get-Content .\l.txt Сообщение из потока Warning Также с помощью оператора *> можно перенаправить в один файл все данные из всех потоков. Например, выполним блок кода, в котором идет запись в потоки Output, warning и Error, и перенаправим данные из всех этих потоков в файл streams.txt: PS С:\Users\andrv> & { Write-Output "Данные из Output" » Write-Warning "Данные из Warning" » Write-Error "Данные из Error" » } *> streams.txt PS С:\Users\andrv> Get-Content .\streams.txt Данные из Output Данные из Warning Write-Output "Данные из Output" Write-Warning "Данные из Warning" Write-Error "Данные из Error" : Данные из Error строка:1 знак:1 + & { Write-Output "Данные из Output" + Categoryinfo : NotSpecified: (:) [Write-Error], WriteErrorException + FullyQualifiedErrorld : Microsoft.PowerShell.Commands.WriteErrorException
Ви можете перенаправити дані з потоку з номером n n на стандартний вихідний потік 0utput, який має номер 1, використовуючи Наприклад, спробуємо зберегти дані з потоку Verbose:
PS С:\Users\andrv> $message = Write-Verbose -Message "Подробное сообщение" -Verbose ПОДРОБНО: Подробное сообщение Проверим значение переменной $message: PS С:\Users\andrv> $message Как видим, в $message ничего не записалось, т. к. оператор присваивания получает данные ИЗ ВЫХОДНОГО потока Output, а не ИЗ потока Verbose. Перенаправим теперь поток verbose с номером 4 в выходной поток output (номер 1): PS С:\Users\andrv> $message = Write-Verbose -Message "Подробное сообщение" -Verbose 4>&1 После ЭТОГО переменная $message будет иметь ТИП System.Management.Automation. verboseRecord, в ней будет содержаться наше сообщение: PS С:\Users\andrv> $message ПОДРОБНО: Подробное сообщение PS С:\Users\andrv> $message.getType().fullName System.Management.Automation.VerboseRecord
PowerShell використовує внутрішню систему форматування, яка визначає зовнішній вигляд і вміст інформації про об’єкти, яка відображається на екрані. Правила форматування можна встановити явно за допомогою командлетів
За замовчуванням дані відображаються на екрані, за допомогою командлетів 0ut-* вихід можна перенаправити на файл, на принтер або на порожній пристрій. Використовуйте командлет Out-GridView для відображення таблиці даних в окремому діалоговому вікні графічного інтерфейсу.
Результат команд можна відформатувати за допомогою ConvertTo-HTM1.
PowerShell підтримує кілька незалежних потоків для виведення на них додаткової інформації, яка не потрібна в основному потоці, що забезпечує потік об’єктів по конвеєру. Дані з цих додаткових потоків можна перенаправляти до файлу або до стандартного потоку виводу 0utput.
Дякуємо нашій команді волонтерів за надану інформацію з відкритих джерел.