Заметки о Windows и других программных продуктах Microsoft...

CMD или PowerShell ?

CMD или PowerShell ?

Командная строка долгое время является неотъемлемой частью Windows, и за это время для нее было создано множество различных утилит. PowerShell задумывался в том числе и как альтернатива командной строке, однако сможет ли он полностью заменить ее ?

Для примера я взял наиболее распространенные утилиты командной строки, применяемые в администрировании, и попробовал подобрать им замену в PowerShell. Вот что из этого получилось.

Ping

На замену утилите ping в PowerShell пришел командлет Test-Connection, входящий в состав модуля Microsoft.PowerShell.Management. Для примера пропингуем сервер SRV3 командой:

Test-Connection -ComputerName SRV3

Можно указать для проверки сразу несколько серверов, например перечислив их через запятую:

Test-Connection -ComputerName SRV3, SRV4

или считав из файла:

Test-Connection -ComputerName (Get-Content serverlist.txt)

Еще командлет умеет запускать проверку сразу с нескольких точек. Например, для проверки сервера SRV4 с локального компьютера и с сервера SRV3 воспользуемся следующей командой:

Test-Connection -Source localhost, SRV3 -ComputerName SRV4

Параметр -Source появился только в PS 3.0. В некоторых случаях очень удобно, однако при его использовании может понадобится ввести учетные данные:

Test-Connection -Source localhost, SRV3 -ComputerName SRV4 -Credential Contoso\administrator

командлет Test-Connection

 

Примечание. Командлет использует класс Win32_PingStatus, поэтому для проверки соединения можно воспользоваться командой Get-WmiObject Win32_PingStatus, ее действие аналогично команде Test-Connection.

Tracert

Следующее средство, обычно применяемое после ping — это трассировка с помощью утилиты tracert. В PowerShell для этих целей можно задействовать командлет Test-NetConnection из модуля NetTCPIP. Не смотря на похожее название, по функционалу он довольно сильно отличается от предыдущего командлета, хотя включает в себя и его возможности. Кроме проверки TCP соединения вывод может включать в себя список IP интерфейсов, разрешение DNS-имен (DNS lookup), правила IPsec и проверку возможности установления соединения. В самом простом варианте команда выглядит так:

Test-NetConnection -ComputerName ya.ru

Для пошагового вывода в стиле tracert можно сделать так:

Test-NetConnection -ComputerName ya.ru -TraceRoute

Также можно указать определенный порт и сделать детализованный вывод:

Test-NetConnection -ComputerName ya.ru -Port 80 -InformationLevel Detailed

командлет Test-NetConnection

IPConfiig

Первое, для чего используют Ipconfig — это просмотр сетевых настроек. В PowerShell для этих целей можно воспользоваться командлетом Get-NetIPConfiguration. Так для подробного вывода настроек для всех сетевых интерфейсов (аналог ipconfig /all) введем команду:

Get-NetIPConfiguration -All -Detailed

командлет Get-NetIPConfiguration

 

Для операций с клиентом DNS воспользуется командлетами PowerShell из модуля DNSClient. Для очистки содержимого локального кеша DNS вместо ipconfig /flushdns выполним команду Clear-DnsClientCache, для перерегистрации вместо ipconfig /registerdns — команду Register-DnsClient. Вывести содержимое кеша (ipconfig /displaydns) можно командой Get-DnsClientCache. Также можно выводить не все содержимое кеша, а посмотреть только определенную запись, например:

Get-DnsClientCache -Entry www.bing.ru

командлет Get-DNSClientCache

Nslookup

Для проверки DNS имен вместо nslookup можно воспользоваться командлетом Resolve-DnsName, входящий в состав модуля DNSClient. Синтаксис у них похожий, например:

Resolve-DnsName -Name SRV3

Можно указать тип записи (A, PTR, SRV), указать, откуда брать данные и выбрать определенный DNS-сервер, отличный от дефолтного:

Resolve-DnsName -Name SRV3 -Type A -DNSOnly -Server 192.168.0.1

командлет Resolve-DNSName

Netstat

Утилита Netstat — еще один инструмент сетевой диагностики, показывающий сетевые подключения. Заменим ее командлетом Get-NetTCPConnection. Следующая команда выведет все подключения к интернету, имеющие статус установленных (Established):

Get-NetTCPConnection -State Established -AppliedSettings Internet | ft -auto

командлет Get-NetTcpConnection

Route

Для управления маршрутизацией вместо утилиты Route воспользуемся несколькими командлетами из модуля NetTCPIP. Для примера попробуем добавить новый постоянный маршрут до сети 172.16.0.0 с маской 255.255.0.0 и шлюзом 192.168.0.1 для интерфейса с номером 3. Вот так это можно сделать с помощью Route:

Route -p add 172.16.0.0 mask 255.255.0.0 192.168.0.1 -if 3

А вот так при использовании PowerShell:

New-NetRoute -DestinationPrefix ″172.16.0.0/16″ -InterfaceIndex 3 -NextHop 192.168.0.1

Для просмотра таблицы маршрутизации вместо route print возьмем командлет Get-NetRoute.  Выведем все маршруты для протокола IPv4 командой:

Get-NetRoute -AddressFamily IPv4 | ft -auto

New-NetRoute и Get-NetRoute

 

В PS 4.0 появился интересный командлет Find-NetRoute, с помощью которого можно вывести маршрут для одного конкретного  IP-адреса, например:

Find-NetRoute -RemoteAddress 10.0.0.1

Для удаления маршрута (вместо route delete) также есть отдельный командлет Remove-NetRoute, например:

Remove-NetRoute -DestinationPrefix ″172.16.0.0/16″ -InterfaceIndex 3 -NextHop 192.168.0.1 -Confirm:$false

Для изменения уже созданного маршрута вместо route change можно воспользоваться связкой Remove-NetRoute&New-NetRoute.

Netsh

Утилита Netsh (Network shell) предназначена для выполнения различных задач по настройке сети. Поскольку функционал ее достаточно широк, для сравнения возьмем одну из типичных задач по настройке сетевого интерфейса.  Предположим, нам необходимо проверить настройки сетевого интерфейса, и если включен DHCP — отключить его и настроить статическую адресацию. С помощью netsh это будет выглядеть следующим образом:

Netsh interface IPv4 show addresses
Netsh interface IP set address ″Ethernet″ static 192.168.0.11 255.255.255.0 192.168.0.1
Netsh interface IP add DNSServers ″Ethernet″ 8.8.8.8

И тоже самое, но уже с помощью PowerShell:

Get-NetIPAddress -InterfaceIndex 3 -AddressFamily IPv4
Set-NetIPInterface -InterfaceIndex 3 -Dhcp disabled
New-NetIPAddress -InterfaceIndex 3 -IPAddress 192.168.0.11 -PrefixLength 24 -DefaultGateway 192.168.0.1
Set-DNSClientServerAddress -InterfaceIndex3 -ServerAddresses (″8.8.8.8″)

изменение сетевых настроек из PowerShell

 

Что интересно, для изменения сетевых настроек придется их удалить и создать заново. Например IP-адрес можно изменить так:

Remove-NetIPAddress -InterfaceIndex 3 -IPAddress 192.168.0.11 -PrefixLength 24 -DefaultGateway 192.168.0.1 -Confirm:$false
New-NetIPAddress -InterfaceIndex 3 -IPAddress 192.168.0.12 -PrefixLength 24 -DefaultGateway 192.168.0.1 -Confirm:$false

изменение IP-адреса из powerShell

 

Примечание. Для изменения IP-адреса логично было бы воспользоваться специально предназначенным для этого командлетом Set-NetIPAddress, но не тут-то было 🙂 При попытке изменить настройки этот командлет стабильно выдает ошибку. Как выяснилось, этот командлет не может изменить сам IP-адрес, а только некоторые его свойства.

Gpupdate и Gpresult

Для обновления групповых политик вместо Gpupdate в модуле GroupPolicy есть командлет Invoke-GPUpdate. Синтаксис у них практически один и тот же, например принудительное обновление политик пользователя выполняется командой:

Gpupdate /target:user /force
Invoke-GPUpdate -Target user -force

Ну и посмотреть результирующие политики вместо Gpresult можно командлетом Get-GPResultantSetOfPolicy. Осуществить вывод результатов в HTML-файл можно командой:

Get-GPResultantSetOfPolicy -ReportType Html -Path C:\gpo.html

командлет Invoke-GPUpdate

CMD vs PowerShell

Как видите, PowerShell вполне в состоянии заменить большинство утилит командной строки. Однако остается еще один вопрос —  зачем это нужно.

В достоинства PowerShell, на мой взгляд, можно записать более структурированный вывод результатов, которые к тому-же можно обрабатывать — фильтровать, сортировать и изменять формат вывода. Кроме того, результатом выполнения команд PowerShell являются объекты, которые можно сохранять в переменные, передавать по конвейеру и т.п. Это очень удобно при написании скриптов.

Из недостатков — большинство описанных в статье команд требуют PowerShell 3.0, а некоторые вообще есть только в четвертой версии. Также некоторые командлеты (напр. Set-NetIPAddress) работают криво не совсем так, как должны.

Ну а на стороне CMD проверенный временем функционал, который есть в любой версии Windows. Кроме того, для простых задач администрирования cmd использовать привычнее, а где-то и удобнее.

Итак, что же лучше — CMD или PowerShell ? Не знаю как вы, а я не готов однозначно ответить на этот вопрос. Впрочем, ничто не мешает нам пользоваться и тем и другим.

 
 
Комментарии

А еще, по ощущениям, Powershell работает гораздо медленнее, особенно со всем, что касается сетевых подключений.

Алексей

Добрый день. А почему некоторые вышеперечисленные команды в PS v 3 не выполняются? Например на Resolve-DnsName -Name ya.ru PS пишет «Имя «Resolve-DnsName» не распознано как имя командлета, функции, файла сценария….».

Возможно не подгрузился нужный модуль. Попробуйте перед запуском команду Import-Module DNSClient.

Алексей

Import-Module DNSClient
Import-Module : Указанный модуль «DNSClient» не был загружен, так как ни в одном из каталогов модулей не был обнаружен действительный файл модуля.
строка:1 знак:1
+ Import-Module DNSClient
+ ~~~~~~~~~~~~~~~~~~~~~~~
+ CategoryInfo : ResourceUnavailable: (DNSClient:String) [Import-Module], FileNotFoundException
+ FullyQualifiedErrorId : Modules_ModuleNotFound,Microsoft.PowerShell.Commands.ImportModuleCommand

….причем песня одинакова что на 7-ке, что на 2008 Server-е