在命令行上设置公共属性值

问题描述 投票:0回答:1

在 msi 的命令行上设置公共属性值遵循模式

MyInstaller.msi PUBLICPROPERTY="someValue"

这适用于“命令提示符”,即 cmd.exe 和 powershell。

但是

MyInstaller.msi PUBLICPROPERTY=""

在 powershell 中无法按预期工作。我预计它将 PUBLICPROPERTY 设置为 null,但它将 PUBLICPROPERTY 设置为值“CURRENTDIRECTORY =”C:emp \ msi \“”(它确实像 cmd.exe 预期的那样工作)。

为什么 powershell 和 cmd.exe 的行为不同,如何修复?

powershell wix windows-installer parameter-passing quoting
1个回答
4
投票

Windows 上的 PowerShell 必然会在幕后对您的论点执行重新引用

这种不可见的重新引用并不总是按预期工作,例如在本例中。

更新

您可以通过调整您的引用来解决问题

... PUBLICPROPERTY=`"`"  # `-escape the " chars.

... 'PUBLICPROPERTY=""'  # use enclosing '...', so " chars. can be used as-is

请注意,如果您想在参数中包含 PowerShell 变量/表达式的值,则使用

'...'
将不起作用。

此外,在 PSv3+ 中,您可以使用

--%
(停止解析符号)来使 PowerShell 按原样传递剩余参数,就好像您从
cmd.exe
/ 批处理文件调用
(包括环境变量引用的扩展,例如
%OS%
)。

... --% PUBLICPROPERTY=""

同样,您将无法以这种方式在参数中引用 PowerShell 变量或表达式。


至于如果没有上述技术会发生什么:

  • PUBLICPROPERTY="someValue"

     变成

    PUBLICPROPERTY=someValue
    
    

  • PUBLICPROPERTY="some Value"

    ,由于空格,变成了

    "PUBLICPROPERTY=some Value"
    ,即
    整个参数包含在"..."
    中。

PowerShell-

内部诸如PUBLICPROPERTY="someValue"

之类的参数有其引号
stripped:如果将此类参数传递给PowerShell cmdlet或函数,它只会看到PUBLICPROPERTY=someValue

将这样的值传递给

外部程序时,PowerShell会根据情况决定是否需要双引号,但该引用仅应用于整个参数 - "字符的初始位置。丢失了。

因此,

PUBLICPROPERTY="someValue"

变成

PUBLICPROPERTY=someValue
并按原样
传递,因为它
不包含嵌入的空格,因此 PowerShell 不应用双引号。 相比之下,PUBLICPROPERTY="some Value"

会变成

PUBLICPROPERTY=some Value

,并作为
"PUBLICPROPERTY=some Value"
传递,因为空格的存在需要双引号,以便将值保留为单个参数。
请注意,
PowerShell 仅对传递给外部程序的参数应用

双引号

,因为这是唯一可以假定所有程序都能理解的引用样式。 重新引用逻辑随着时间的推移而发生了变化,并且存在 错误,遗憾的是,由于向后兼容性问题,这些错误将继续存在

例如,'3 " of rain'变成了

"3 " of rain"

,即

破碎
,因为
嵌入的
"缺乏转义;解决方法是预见到这一点,并显式执行 PowerShell 应该执行的操作:自动
:将嵌入的 
"
转义为 \",以利于外部程序:
'3 \" of rain'
    

© www.soinside.com 2019 - 2024. All rights reserved.