PowerShell, Get-LiveJournal: параметры скрипта, ч.1 (param и $args)

Mar 12, 2023 13:28

Окружение: операционная система «Windows 10», программа-оболочка «PowerShell» версии 7, скрипт «Get-LiveJournal».

При написании скрипта «Get-LiveJournal» мне пришлось довольно много времени потратить на обдумывание работы с параметрами скрипта.

Способы получения параметров

Вообще, в скриптах для программы-оболочки «PowerShell» параметры можно получить, как минимум, двумя способами: с помощью выражения param (подробнее) или из встроенной переменной-массива $args (подробнее). Следует иметь в виду, что при совмещении этих способов во встроенную переменную-массив $args попадают только параметры, которые пользователь скрипта передает сверх параметров, принимаемых через выражение param. Например:

скрипт «test.ps1»

param($user)
$user
$args[0]
запускаем скрипт из программы-оболочки:

PS C:\> .\test "первый" "второй"
первый
второй

Как видно из блоков кода выше, в первый элемент (с индексом 0) встроенной переменной-массива $args попал второй параметр. Первый параметр в данном случае во встроенную переменную-массив $args не попал, он попал в переменную (параметр) $user в скрипте.

У каждого из этих двух способов есть свои преимущества и недостатки. С помощью выражения param можно создать параметры любого вида, который может быть в программе-оболочке «PowerShell». Вообще, разных видов параметров довольно много, я не буду описывать их все в этом посте. Но меня очень привлекает возможность создавать именованные параметры. Например, для скрипта, приведенного выше, $user - это именованный параметр, то есть скрипт можно вызвать так:

PS C:\> .\test -User "первый"
первый
или так:

PS C:\> .\test "второй" -User "первый"
первый
второй

У именованных параметров два плюса. Во-первых, в примерах, показывающих порядок запуска скрипта, имена параметров, указанные в составе команды, сами по себе уже дают представление о назначении определенных параметров (то есть именованные параметры обладают свойством самодокументирования). Во-вторых, именованные параметры (в отличие от позиционных) легко можно менять местами, что показано в примере выше.

Недостаток выражения param

У выражения param есть и недостаток: на этот механизм навешано слишком много лишнего. Например, если пользователь скрипта укажет лишние параметры, я хочу предупредить его об этом. Поэтому сначала я написал что-то вроде следующего:

скрипт «test.ps1»

param($user)
if ($args.Length -gt 0) {
Write-Error "Нужен только один параметр!"
}
запускаем скрипт из программы-оболочки:

PS C:\> .\test "первый" "второй"
Write-Error: Нужен только один параметр!

Вроде, всё работает так, как и планировалось. Однако, позже мне понадобилось добавить к скрипту атрибут CmdletBinding, что можно сделать, только если в скрипте присутствует выражение param. Вот что при этом получилось:

скрипт «test.ps1»

[CmdletBinding()] param($user)
if ($args.Length -gt 0) {
Write-Error "Нужен только один параметр!"
}
запускаем скрипт из программы-оболочки:

PS C:\> .\test "первый" "второй"
test.ps1: A positional parameter cannot be found that accepts argument 'второй'.

Как видно из блоков кода выше, моё предупреждение о лишних параметрах было заменено встроенным предупреждением о том же. С одной стороны, это хорошо: теперь я могу убрать свой код с предупреждением о лишних параметрах и тем самым сократить текст скрипта. С другой стороны, мое предупреждение было на русском языке и оно было более понятным.

В итоге мне пришлось пока что смириться в этом случае с таким встроенным предупреждением (может, в будущем я когда-нибудь сумею найти удобное мне решение). Я могу, конечно, выкинуть выражение param и пользоваться получением параметров через встроенную переменную-массив $args, но тогда мне придется отказаться от именованных параметров и от возможностей, предоставляемых атрибутом CmdletBinding (я расскажу об этом в одном из следующих постов).

Продолжение следует...

Инструмент, Образование, Программирование

Previous post Next post
Up