PowerShell Invoke-Command with FilePath 在本地计算机上 - 模糊参数错误?

PowerShell Invoke-Command with FilePath on local computer - vague parameters error?

我想 运行 使用 Invoke-Command 在本地计算机上的文件中创建一个脚本,这样我就可以使用 -ArgumentList 传递参数。我遇到了一个我不明白的错误,所以我简化了我的命令。当我这样做时:

Invoke-Command -FilePath 'getprocess.ps1'

getprocess.ps1的内容是:

Get-Process

我收到的错误信息是:

Invoke-Command : Parameter set cannot be resolved using the specified named parameters.

At line:1 char:1

+ Invoke-Command -FilePath 'getprocess.ps1'

+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

+ CategoryInfo : InvalidArgument: (:) [Invoke-Command], ParameterBindingException

+ FullyQualifiedErrorId : AmbiguousParameterSet,Microsoft.PowerShell.Commands.InvokeCommandCommand

我对这条错误消息感到困惑。这是什么意思?我如何让它工作?

我真的不能在本地使用 invoke-command。当您尝试 运行 远程 PC 上的命令时,您会用到它。

例如,您可能想要 运行 像这样的东西:

invoke-Command -ComputerName REMOTE-PC -Credentials $credential -Scriptblock {Get-Process}

该错误基本上是在告诉您需要填写更多与该命令相关的参数。

尝试 运行ning Get-Help Invoke-Command 查看有关命令的一些信息以及如何 运行 它。

虽然错误消息没有说清楚,但 -FilePath 参数使得 -ComputerName 参数成为必需参数。要明确定位本地计算机,请使用 -ComputerName localhost.

Invoke-Command -FilePath 'getprocess.ps1' -ComputerName localhost

您必须有一个计算机名。

$parameters = @{
    ComputerName = '255.255.255.255'
    FilePath = 'getprocess.ps1'
    Credential = 'Domain01\User01'
}

invoke-command @parameters

使用您的 IP :) 要允许您还必须包含 -credential

如果不行...invoke-expression 可能是一个半合适的测试替代品,直到您准备好在远程机器上调用命令。

tl;博士:

  • 通常,不要将 Invoke-Command 用于 local 调用 - 虽然技术上可行,但只有需要这样做的一个特定用例(见下文)。

  • 相反,直接调用脚本:

.\getprocess.ps1

注意:与 cmd.exe 不同,PowerShell 在设计上需要 .\ 才能执行位于 当前目录 中的可执行文件。也就是说,为了避免在当前目录而不是 $env:Path 中列出的目录中意外执行可执行文件,作为一项安全功能,PowerShell 要求您发出在当前目录中执行某些内容的意图信号 (.) 明确地。

对于 script blocks ({ ... }), use &, the call operator(例如,& { Get-Date })。

仅出于句法原因,您情境还需要&用于脚本文件路径,如果它们被指定作为 引用 路径(例如,& '.\getprocess.ps1')and/or 如果路径涉及 变量引用(例如,
& $HOME\getprocess.ps1).

(另外,. ,在两种情况下都需要dot-sourcing operator才能直接执行脚本[block] 在调用者的范围内 而不是在子范围内)。


请注意,您可以在技术上将脚本块传递给 Invoke-Command(参数 -ScriptBlock)与调用本地脚本相结合:

# The script block positionally binds to the -ScriptBlock parameter.
# This is essentially the more expensive equivalent of:
#     & .\getprocess.ps1
Invoke-Command { .\getprocess.ps1 }

较慢,并且与 直接 调用 相比没有任何优势。 然而,有一个可以想象的用例:

如果脚本 不是 一个 advanced script 并且您想利用 Invoke-Command 的流输出收集 common parameters, such as -ErrorVariable(如果被调用的脚本或函数高级的,它支持这些常用参数本身)。

# Invoke locally and collect errors in $errs
Invoke-Command { .\getprocess.ps1 } -ErrorVariable errs

警告:至少从 PowerShell 7.2 开始,Invoke-Command 不会 common -ErrorAction parameter 应用于错误在脚本块中出现,因此它不能用于控制错误处理;例如,-ErrorAction Stop 对脚本块中的命令没有影响。


至于你试过的:

确实,正如您指出的 -FilePath 必须
结合 -ComputerName 参数
(不幸的是,错误消息是如此笼统)。

参数-FilePath目的是复制本地脚本的内容*.ps1 文件) 到 远程 计算机执行 那里。也就是说,它是一种方便的机制,可以执行在远程机器上(仅)在本地可用的脚本代码。

虽然 您可以通过 -ComputerName localhost(或者更简洁地说,通过 -ComputerName . / -cn .)从技术上将本地计算机作为目标,但这相当于本地电话:

每当指定 -ComputerName - 即使使用 -ComputerName localhost - 使用 PowerShell 的 远程处理基础设施 ,它有主要影响

  • 目标计算机 - 即使是本地计算机 - 必须设置为 PowerShell 远程处理 - 请参阅 about_Remote_Requirements

  • 如果您专门针对本地计算机,则您必须 运行 在 提升的 会话中(运行 作为管理员)。

  • 执行会比直接(本地)调用慢很多。

  • 假设涉及通过 PowerShell 的基于 XML 的序列化基础结构的跨进程封送处理,输入和输出数据的类型保真度可能会丢失 - 请参阅


也就是说,如果目的是在本地测试脚本的远程执行,并且您的本地计算机设置为远程处理目标,然后使用 -ComputerName localhost (-ComputerName . / -cn .) 非常有意义,因为 PowerShell 的远程处理基础结构随后以与真正远程调用相同的方式参与。

但是请注意,此类“环回远程处理”调用需要 elevation(运行 作为管理员)。

您可以像这样在本地 运行,但您必须处于管理员(提升的)提示符下。很高兴能够 运行 它作为测试。

invoke-command localhost getprocess.ps1

你实际上也可以做一种奇怪的并行形式:

invoke-command localhost,localhost,localhost getprocess.ps1