12

我显然不知道我在做什么。

我终于让这个 PowerShell 命令工作了。但我无法弄清楚它为什么会起作用。

我关心的是最后的 "" 字符:

    &"C:\Program Files\IIS\Microsoft Web Deploy\msdeploy.exe" `
    -verb:sync `
    -source:contentPath="$build_directory\deploy" `
    -dest:contentPath="$server_temp_directory,computerName=$server,username=$server_username,password=$server_password" `
    -verbose `
    -postSync=runCommand="powershell -NoLogo -NoProfile -Command $server_temp_directory\remotetasks.ps1 Deploy""

为什么我需要双双引号?

我的 IDE (PowerGUI) 说该行没有正确结束,但这是我可以使命令按需要运行的唯一方法。

是什么,我 - 和 IDE - 不知道在 PowerShell 中引用?


echoargs 的一些输出:

如果我运行:

echoargs -postSync=runCommand="powershell -NoLogo -NoProfile -Command $server_temp_directory\remotetasks.ps1 Deploy""

我得到:

Arg 0 is <-postSync=runCommand=powershell -NoLogo -NoProfile -Command \remotetasks.ps1 Deploy>

如果我在没有双双引号的情况下运行,我会得到:

Arg 0 is <-postSync=runCommand=powershell>
Arg 1 is <-NoLogo>
Arg 2 is <-NoProfile>
Arg 3 is <-Command>
Arg 4 is <\remotetasks.ps1>
Arg 5 is <Deploy>

需要注意的另一件事是,上述命令仅在使用 = 而不是:最后一个参数时才有效。

这不起作用:

-postSync:runCommand="powershell -NoLogo -NoProfile -Command $server_temp_directory\remotetasks.ps1 Deploy""

我试过这样的数组解决方案:

$arguments = @("-verb:sync",
               "-source:contentPath=$build_directory\deploy",
               "-dest:contentPath=$server_temp_directory,computerName=$server,username=$server_username,password=$server_password",
               "-verbose",
               "-postSyncOnSuccess:runCommand=powershell -Command $server_temp_directory\remotetasks.ps1 Deploy")
&"C:\Program Files\IIS\Microsoft Web Deploy\msdeploy.exe" $arguments

我仍然得到同样的错误:

错误:无法识别的参数 '"-postSyncOnSuccess:runCommand=powershell -Command c:\temp\kslog\remotetasks.ps1 Deploy"'。所有参数必须以“-”开头。

我在这里做错了什么新事情吗?

4

3 回答 3

11

这是一个臭名昭著的问题。票“执行需要引号和变量的命令实际上是不可能的”是投票最多的错误:https ://connect.microsoft.com/PowerShell/Feedback

您也可以找到一些解决方法。但我建议您将所有参数组合为一个数组,并使用&运算符调用该数组的本机命令。查看答案和示例: 使用 PowerShell 从包含空格的目录中运行 EXE 文件从 Powershell 执行存储在变量中的命令

我没有与您合作msdeploy.exe,也无法为您的案例提供一些演示代码。但是我将这种方法很好地应用于许多其他棘手的本机命令。请尝试一下,让我们知道结果。

PS 从技术上讲,这并不完全是您问题的答案,但我认为您仍在寻找一种实用的方法,因此它仍然可能会有所帮助。

于 2010-10-08T12:28:05.080 回答
3

我终于找到了如何做到这一点。这是一个示例脚本:

$src = 'C:\sandbox\Test Folder\A'
$dest = 'C:\sandbox\Test Folder\B'
$msdeploy = Get-Command 'C:\Program Files (x86)\IIS\Microsoft Web Deploy V3\msdeploy.exe'
$command = "& `$msdeploy --% -verb:sync -source:contentPath=""$src"" -dest:contentPath=""$dest"""
$sb = $ExecutionContext.InvokeCommand.NewScriptBlock($command)
& $sb
于 2013-08-08T15:06:34.820 回答
1

这里的问题之一是 PowerShell 无法处理在基于 cmd 的 msdeploy 中表达的“程序文件”之间的空白转换。

这是一个非常基本的解决方案,并利用了过时的 DOS 限制,但可以使用以下非空白引用来代替:

\Program Files\ ... \Progra~1\
\Program Files (x86)\ ... \Progra~2\

这很蹩脚,但它有效。

您还可以创建一个调用 cmd 并执行您的命令的函数。此示例还假设您尝试调用的内容(msdeploy 等)在路径中。

function PushToTarget() {
     cmd.exe /C $("msdeploy.exe -verb:sync -source:apphostconfig=yourwebapp-dev -dest:archivedir=d:\backup")
}
于 2013-02-13T20:42:15.837 回答