回滚到以前版本的 WiX 捆绑安装程序
Rollback to previous version of WiX bundle installer
我有带有两个 msi 包的 WiX 包:A 和 B。首先,我成功安装了包版本 1.0.0.0。
然后我正在安装 MajorUpgrade 版本 2.0.0.0。包 A 成功升级。包 B 升级失败并开始回滚。
我将 msi 包升级定义为:
<MajorUpgrade AllowSameVersionUpgrades="yes" Schedule="afterInstallInitialize" DowngradeErrorMessage="A newer version of [ProductName] is already installed." />
包 B 恢复到版本 1.0.0.0。包 A 卷支持删除。因此,捆绑包仍处于不一致状态。
如果更新失败,我需要将整个包恢复到版本 1.0.0.0。可能吗?
没有标准的方法来完成它,因为 multi-MSI WiX 不支持交易。
我找到了适合我的解决方法。我使用 Custom Bootstrapper Application,因此我可以在 C# 代码中处理失败事件。如果您使用 WiX 标准引导程序应用程序 (WiXStdBA),它不会帮助您。
如果更新失败,我会在静默修复模式下从 Windows Package Cache 调用之前的捆绑包安装程序。它恢复以前的状态。
下一段代码表达思路:
Bootstrapper.PlanRelatedBundle += (o, e) => { PreviousBundleId = e.BundleId; };
Bootstrapper.ApplyComplete += OnApplyComplete;
private void OnApplyComplete(object sender, ApplyCompleteEventArgs e)
{
bool updateFailed = e.Status != 0 && _model.InstallationMode == InstallationMode.Update;
if (updateFailed)
{
var registryKey = string.Format("SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall\{0}", VersionManager.PreviousBundleId);
RegistryKey key = RegistryKey.OpenBaseKey(RegistryHive.LocalMachine, RegistryView.Registry32).OpenSubKey(registryKey)
?? RegistryKey.OpenBaseKey(RegistryHive.LocalMachine, RegistryView.Registry64).OpenSubKey(registryKey);
if (key != null)
{
string path = key.GetValue("BundleCachePath").ToString();
var proc = new Process();
proc.StartInfo.FileName = path;
proc.StartInfo.Arguments = "-silent -repair";
proc.Start();
proc.WaitForExit();
}
}
}
我有带有两个 msi 包的 WiX 包:A 和 B。首先,我成功安装了包版本 1.0.0.0。 然后我正在安装 MajorUpgrade 版本 2.0.0.0。包 A 成功升级。包 B 升级失败并开始回滚。
我将 msi 包升级定义为:
<MajorUpgrade AllowSameVersionUpgrades="yes" Schedule="afterInstallInitialize" DowngradeErrorMessage="A newer version of [ProductName] is already installed." />
包 B 恢复到版本 1.0.0.0。包 A 卷支持删除。因此,捆绑包仍处于不一致状态。
如果更新失败,我需要将整个包恢复到版本 1.0.0.0。可能吗?
没有标准的方法来完成它,因为 multi-MSI WiX 不支持交易。
我找到了适合我的解决方法。我使用 Custom Bootstrapper Application,因此我可以在 C# 代码中处理失败事件。如果您使用 WiX 标准引导程序应用程序 (WiXStdBA),它不会帮助您。
如果更新失败,我会在静默修复模式下从 Windows Package Cache 调用之前的捆绑包安装程序。它恢复以前的状态。
下一段代码表达思路:
Bootstrapper.PlanRelatedBundle += (o, e) => { PreviousBundleId = e.BundleId; };
Bootstrapper.ApplyComplete += OnApplyComplete;
private void OnApplyComplete(object sender, ApplyCompleteEventArgs e)
{
bool updateFailed = e.Status != 0 && _model.InstallationMode == InstallationMode.Update;
if (updateFailed)
{
var registryKey = string.Format("SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall\{0}", VersionManager.PreviousBundleId);
RegistryKey key = RegistryKey.OpenBaseKey(RegistryHive.LocalMachine, RegistryView.Registry32).OpenSubKey(registryKey)
?? RegistryKey.OpenBaseKey(RegistryHive.LocalMachine, RegistryView.Registry64).OpenSubKey(registryKey);
if (key != null)
{
string path = key.GetValue("BundleCachePath").ToString();
var proc = new Process();
proc.StartInfo.FileName = path;
proc.StartInfo.Arguments = "-silent -repair";
proc.Start();
proc.WaitForExit();
}
}
}