-s при использовании Start-Job в powershell

Я пытаюсь вызвать Start-Job в PowerShell. Когда я это делаю, он создает фоновую оболочку PowerShell со следующими аргументами:

C:\Windows\System32\WindowsPowerShell\v1.0\powershell.exe -Version 5.0 -s -NoLogo -NoProfile -EncodedCommand [encoded command I want to run in base64]

Однако команда powershell, похоже, никогда не завершается, какую бы команду я ей ни отправлял.

Я попытался создать экземпляр PowerShell следующим образом:

powershell.exe -s

И это также, похоже, создает экземпляр, который кажется замороженным, не выполняющим и не выполняющим никаких действий. Просматривая онлайн, я не могу найти никаких ссылок на аргумент -s.

Кто-нибудь знает, для чего он нужен или как от него избавиться, чтобы мои стартовые вакансии работали правильно?

Изменить: возможно, что -s является сокращением для -sta, но моя команда не зависает с помощью -sta, но использует -s.

Edit2: С тех пор я обнаружил, что -s - это сокращение для -ServerMode, по-видимому, вариант Legacy Powershell 2.0. Понятия не имею, почему это добавляется при использовании Start-Job.

Edit3: Я использую следующую команду:

$deploymentsJobs += Start-Job -InitializationScript { SomeSmallFunction } (AnotherFunction) -ArgumentList  $arg1, $arg2, $arg3}

person Ghi102    schedule 26.07.2017    source источник
comment
Я ценю это, @ Ghi102   -  person mklement0    schedule 09.03.2019


Ответы (1)


tl; dr:

  • Параметр -s является ожидаемой частью командной строки, используемой для запуска фонового задания через новый процесс PowerShell - он переводит новый процесс в серверный режим, который требуется для связи с вызывающим процессом в фоновом режиме. управление работой.

    • It is not a legacy option, but it isn't documented either, because it is only meant to be used internally by PowerShell.
  • Учитывая, что все, что вы описываете, соответствует ожиданиям, проблема, скорее всего, связана с конкретными командами, которые вы запускаете через -InitializationScript и в основном блоке сценария (подразумеваемый аргумент -ScriptBlock).


Как вы обнаружили, Start-Job вызов порождает powershell -s -NoLogo -NoProfile вызов за кулисами (обнаруживаемый с помощью диспетчера задач).
То есть создается новый процесс PowerShell для запускать команды в фоновом режиме.

Параметр -EncodedCommand с командной строкой в ​​кодировке Base64 присутствует только в том случае, если вы вызвали Start-Process с параметром -Initialization - основной блок скрипта ((подразумеваемый) аргумент -ScriptBlock) не передается через командную строку (см. ниже).

-s используется внутри PowerShell - всегда - для вызова фоновых заданий, а -s, как вы также обнаружили, является псевдонимом для переключателя -servermode. (Учитывая, что задокументирован только -STA, можно было бы ожидать, что -s будет сокращением от -STA, но это не так).
-s / -servermode - это деталь реализации, используемая только самой PowerShell, т.е. почему это не задокументировано.

nbsp; a> в исходном коде PowerShell Core на GitHub показывает, как строится командная строка для фонового процесса.

Серверный режим - это режим, в котором должен находиться фоновый процесс, чтобы взаимодействовать с вызывающим процессом через его стандартные потоки (stdin, stdout, stderr) : То есть команда для выполнения в фоновом режиме отправляется фоновому процессу через его поток stdin, а фоновый процесс сообщает о своих выводах через потоки stdout и stderr. [1]

Обратите внимание, что сериализация / десериализация на основе XML происходит во время этого межпроцессного взаимодействия с использованием той же инфраструктуры, что и PowerShell удаленного взаимодействия - см. этот ответ для получения дополнительной информации.


[1] Охад Шнайдер указывает, что можно случайно нарушить эту связь, если основной блок сценария содержит такие команды, как Start-Process -NoNewWindow с консольной программой, которые напрямую записывают поток stdout фонового процесса - см. этот ответ.

person mklement0    schedule 26.07.2017