Запрашивать ввод пользователя в PowerShell - PullRequest
189 голосов
/ 18 ноября 2011

Я хочу попросить пользователя ввести серию входных данных, включая пароль и имя файла.

У меня есть пример использования host.ui.prompt, который кажется разумным, но я не могу понять, откуда это возвращается.

Есть ли лучший способ получить пользовательский ввод в PowerShell?

Ответы [ 4 ]

291 голосов
/ 18 ноября 2011

Read-Host - это простая опция для получения ввода строки от пользователя.

$name = Read-Host 'What is your username?'

Чтобы скрыть пароли, вы можете использовать:

$pass = Read-Host 'What is your password?' -AsSecureString

Чтобы преобразовать пароль в обычный текст:

[Runtime.InteropServices.Marshal]::PtrToStringAuto(
    [Runtime.InteropServices.Marshal]::SecureStringToBSTR($pass))

Что касается типа, возвращаемого $host.UI.Prompt(), если вы запустите код по ссылке, размещенной в комментарии @ Christian, вы можете узнать тип возвращаемого значения, указав в нем Get-Member (например, $results | gm). В результате получается словарь, в котором ключом является имя FieldDescription объекта, используемого в приглашении. Чтобы получить доступ к результату для первой подсказки в связанном примере, введите: $results['String Field'].

Чтобы получить доступ к информации без вызова метода, оставьте скобки выключенными:

PS> $Host.UI.Prompt

MemberType          : Method
OverloadDefinitions : {System.Collections.Generic.Dictionary[string,psobject] Pr
                    ompt(string caption, string message, System.Collections.Ob
                    jectModel.Collection[System.Management.Automation.Host.Fie
                    ldDescription] descriptions)}
TypeNameOfValue     : System.Management.Automation.PSMethod
Value               : System.Collections.Generic.Dictionary[string,psobject] Pro
                    mpt(string caption, string message, System.Collections.Obj
                    ectModel.Collection[System.Management.Automation.Host.Fiel
                    dDescription] descriptions)
Name                : Prompt
IsInstance          : True

$Host.UI.Prompt.OverloadDefinitions даст вам определение (я) метода. Каждое определение отображается как <Return Type> <Method Name>(<Parameters>).

74 голосов
/ 23 ноября 2011

Использование привязки параметров определенно является подходящим способом. Это не только очень быстро писать (просто добавьте [Parameter(Mandatory=$true)] над вашими обязательными параметрами), но это также единственная опция, которую вы не будете ненавидеть позже.

Подробнее ниже:

[Console]::ReadLine явно запрещено правилами FxCop для PowerShell. Зачем? Поскольку он работает только в PowerShell.exe, а не в PowerShell ISE , PowerGUI и т. Д.

Read-Host очень просто плохая форма. Read-Host неконтролируемо останавливает сценарий для запроса пользователя, что означает, что у вас никогда не будет другого сценария, который включает сценарий, использующий Read-Host.

Вы пытаетесь запросить параметры.

Вы должны использовать атрибут [Parameter(Mandatory=$true)] и правильный ввод, чтобы запросить параметры.

Если вы используете это для [SecureString], появится запрос на ввод поля пароля. Если вы используете это для типа учетных данных ([Management.Automation.PSCredential]), появится диалоговое окно учетных данных, если параметр отсутствует. Строка станет просто старым текстовым полем. Если вы добавите HelpMessage к атрибуту параметра (то есть [Parameter(Mandatory = $true, HelpMessage = 'New User Credentials')]), он станет текстом справки для приглашения.

14 голосов
/ 16 февраля 2014

Поместите это вверху вашего скрипта.Это заставит скрипт запросить у пользователя пароль.Полученный пароль можно затем использовать в другом месте вашего скрипта с помощью $ pw .

   Param(
     [Parameter(Mandatory=$true, Position=0, HelpMessage="Password?")]
     [SecureString]$password
   )

   $pw = [Runtime.InteropServices.Marshal]::PtrToStringAuto([Runtime.InteropServices.Marshal]::SecureStringToBSTR($password))

Если вы хотите отладить и увидеть значение пароля, который вы только чточитать, использовать:

   write-host $pw
3 голосов
/ 23 ноября 2014

В качестве альтернативы вы можете добавить его в качестве параметра скрипта для ввода как части выполнения скрипта

 param(
      [Parameter(Mandatory = $True,valueFromPipeline=$true)][String] $value1,
      [Parameter(Mandatory = $True,valueFromPipeline=$true)][String] $value2
      )
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...