我需要在远程计算机上运行ps1脚本。该脚本将传递一个表示文件名的参数。我尝试了很多很多种不同的组合和方法来将参数传递给脚本块,但是在尝试支持脚本名称和/或文件名中的空格时,我总是遇到一个错误或另一个。
注意:最终结果将使用-ComputerName
Invoke-Command参数在 REMOTE 计算机上运行脚本,但为了简单起见并测试了所有示例在本地运行。
给出示例“远程”脚本
#processFile.ps1
$args[0] # Just outputs the first parameter passed
如果名称
中没有空格,则以下情况有效$cmd = ".\processFile.ps1"
$fn = "someFile.csv"
$sb = [ScriptBlock]::Create("$cmd $fn")
Invoke-Command -ScriptBlock $sb
# Outputs the correct
someFile.csv
但是,以下操作不起作用
$cmd = ".\processFile.ps1"
$fn = "some File.csv"
$sb = [ScriptBlock]::Create("$cmd $fn")
Invoke-Command -ScriptBlock $sb
# Outputs the incorrect
some
显然,文件名参数需要转义并作为“some File.csv”传递。这可以通过以下方式完成:
$cmd = ".\processFile.ps1"
$fn = "some File.csv"
$sb = [ScriptBlock]::Create("$cmd `"$fn`"") # Notice the escape $fn parameter
Invoke-Command -ScriptBlock $sb
# Outputs the correct
some File.csv
但是,当我尝试将此空间支持扩展到脚本名称时,一切都崩溃了。以下失败
$cmd = ".\processFile.ps1"
$fn = "some File.csv"
$sb = [ScriptBlock]::Create("`"$cmd`" `"$fn`"") # Notice the attempt to escape both parameters
有以下异常
Exception calling "Create" with "1" argument(s): "Unexpected token 'some File.csv' in expression or statement."
我尝试过的所有东西,以及许多不同的方法,都产生了类似的东西。我似乎无法让两个参数都被转义。 (实际上,问题不仅仅是我无法逃避第一个参数。我的一些尝试包括嵌套引号,单引号,[ScriptBlock] :: Create,{},$ executionContext等。< / p>
答案 0 :(得分:6)
试试这个:
$sb = [ScriptBlock]::Create(@"
&'$cmd' '$fn'
"@)
答案 1 :(得分:4)
对于任何对mjolinor接受的答案感到困惑的人,你需要补充:
. $sb
让它实际运行脚本块。
此外,更简单的语法对我来说更具可读性:
$cmd = @"
&'$cmd' '$fn'
"@
Invoke-Expression $cmd