Wix 托管引导程序应用程序:通过捆绑将变量传递给 msi

Posted

技术标签:

【中文标题】Wix 托管引导程序应用程序:通过捆绑将变量传递给 msi【英文标题】:Wix Managed bootstrapper Application: Passing variables to msi through bundle 【发布时间】:2017-03-21 02:11:25 【问题描述】:

我在 WPF 中为我的 Wix Bundle 创建了一个自定义 UI,并覆盖了 Bootstrapper 应用程序类,我正在努力处理一个变量,如果需要,我需要从 UI 访问和修改该变量。此变量是引导程序部署的 msi 的安装文件夹路径(字符串)。

我关注了我在许多论坛上找到的内容,但它不起作用,我无法访问此变量。这是我的代码:

Msi 安装程序:

<Product ...>
  <Feature ...
           ConfigurableDirectory="INSTALLFOLDER"
           ...>
</Product>

<Directory Id="TARGETDIR" Name="SourceDir">
  <Directory Id="ProgramFilesFolder">
    <Directory Id="ManufacturerFolder" Name="...">
      <Directory Id="INSTALLFOLDER" Name="!(bind.property.ProductName)"/>
    </Directory>
  </Directory>
</Directory>

捆绑:

<Variable Name="InstallFolder" bal:Overridable="yes" />

<Chain>
      <MsiPackage ...
                  ForcePerMachine="yes"
                  Compressed="no"
                  Visible="no"
                  EnableFeatureSelection="yes"
                  Vital="yes">
        <MsiProperty Name="INSTALLFOLDER" Value="[InstallFolder]" />
      </MsiPackage>
      ...
</Chain>

C# 托管引导程序应用程序:

if (Bootstrapper.Engine.StringVariables.Contains("InstallFolder"))
  installFolder = Bootstrapper.Engine.StringVariables["InstallFolder"];

“installFolder”变量始终为空...我真的不知道我的代码有什么问题。希望可以有人帮帮我。谢谢

编辑:

我按照 Pavel 的建议将 bundle 变量更改为默认值 值,现在即使我仍然无法获得 MSI 返回的值,我 可以将 Bootstrapper.Engine.StringVariables["InstallFolder"] 设置为 值并正确传递给 msi。

【问题讨论】:

【参考方案1】:

这里回答了同样的问题 - Cannot read input from Bootstrapper variable in Managed Bootstrapper Application C#-Code

短版:您还必须通过Bootstrapper.Command.GetCommandLineArgs() 手动解析命令行参数并写入Bootstrapper.Engine.StringVariables["variable"]

【讨论】:

您好,谢谢您的回答,我之前看到了链接,但是当我读取 GetCommandLineArgs() 返回的字符串数组时,它是空的.. 运气好能弄清楚为什么它是空的吗?【参考方案2】:

如果我没记错的话,Burn 变量默认是数字类型的。

所以,请尝试明确指定您的变量类型。也可以指定默认值:

<Variable Name="InstallFolder" Type="string" Value="[ProgramFilesFolder]!(bind.packageName.YourMsiPackageId)" Persisted="yes"/>

如果安装程序在安装过程中需要重新启动,您可能还应该添加 Persisted="yes" 以保留该值。

【讨论】:

您好,谢谢您的回答,但我刚刚试了一下,仍然没有得到msi变量...我只能得到默认值。 您无法从 MSI 包中读取变量。您的 Burn 引导程序运行许多 MSI 和 EXE 包。您可以将 Burn bootstrapper 中的变量传递给包,但反之则不行。 如果您想读取 boostrapper 中的一些信息,您的 MSI 包可以将其存储在系统中的某个位置,例如在注册表项中。然后,您将能够使用标准搜索之一在引导程序中读取它。请参阅wixtoolset.org/documentation/manual/v3/bundle/… 了解更多信息 哦,好的,但我在检测步骤中需要这些信息?是否可以将此值存储在注册表中而无需仅通过运行引导程序来安装 msi? 您的实际工作流程是什么?通常,当我们创建引导程序时,我们会在引导程序本身中定义一些具有默认值的变量。在引导程序的 UI 中,我们可以使用 Bootstrapper.Engine.StringVariables 属性更改它们的值(例如安装路径)。稍后,在应用阶段,这些变量被传递给 MSI 包。如果你只是想初始化【参考方案3】:

好吧,多亏了 Pavel,我现在更了解它的工作原理了:

在 wix 包中,要更改 msi 变量,您需要设置一个默认值,在我的例子中是:

<Variable Name="InstallFolder" Type="string" Value="[INSTALLFOLDER]" Persisted="yes"/>

此默认值对应于 msi 中真正的默认值。有了它,我可以从我的 c# 代码中访问这个变量,并在需要时通过执行以下操作来更改它:

Bootstrapper.Engine.StringVariables["InstallFolder"] = value;

【讨论】:

以上是关于Wix 托管引导程序应用程序:通过捆绑将变量传递给 msi的主要内容,如果未能解决你的问题,请参考以下文章

WiX 引导程序项目参考变量

如何强制卸载损坏的 Wix 捆绑包

自定义 WiX Burn 引导程序用户界面?

无法从另一个托管引导程序应用程序卸载 WiX 托管引导程序应用程序

wix 托管引导程序:回滚失败

托管的 WiX 引导程序包