我们正在将安装程序从Visual Studio Installer项目(* .vdproj)升级到WiX安装程序 . 从我们的用户角度来看,我们希望尽可能无缝地进行此转换 . 即如果他们的软件版本是使用* .vdproj版本中的MSI安装的,那么使用WiX版本中的MSI进行的v2.0安装应该覆盖/删除旧版本并继续正常运行 .
我们遇到的问题是原始的* .vdproj安装程序将软件安装为“ALLUSERS = false”,而现在使用WiX我们想使用InstallScope =“perMachine”(即“ALLUSERS = true”) .
我们使用自举的WiX安装程序,其中链中的第一个元素处理.Net Framework安装(如果需要),第二个元素是我们产品的MSI安装程序 .
<MajorUpgrade DowngradeErrorMessage="A newer version of ... is already installed." />
<Upgrade Id="{UPGRADE-CODE-OF-OLD-INSTALLER}">
<UpgradeVersion OnlyDetect="no" Property="OTHER_STUFF_FOUND" Minimum="0.0.0" />
</Upgrade>
如果我们在新的WiX安装程序中设置InstallScope =“perUser”,那么这将按预期工作,但是如果我们设置InstallScope =“perMachine”,则卸载失败并记录此错误:
MSI (c) (04:10) [23:18:49:626]: FindRelatedProducts: current install is per-machine. Related install for product '{PRODUCT-CODE-OF-OLD-INSTALLER}' is per-user. Skipping...
经过一些研究后,我们了解到这是一个已知问题,并且由于Microsoft安装程序阻止了上下文切换(即从perUser到perMachine),因此无法像上面所述那样简单地解决问题 .
问题是:我们如何以稳健的方式处理此升级?目前我们没有可行的解决方案 .
我可以想到几个选项,但想看看人们是否有更好的答案,关于哪个选项最好的建议,或者关于如何实施这些列出的方法之一的建议:
-
使用自定义操作手动卸载旧软件或向用户发出警告,以手动卸载旧版本并终止安装 . 如果我们知道旧安装程序的升级代码,我们应该能够搜索注册表以查看是否安装了旧软件?当我看着re
-
我可以使用另一个以InstallScope = "perUser"运行的WiX MSI安装程序,并且全权负责删除旧安装吗?
-
我找到了这个解决方案[3],但是因为我们使用的是Bootstrapped安装程序,我们的MSI项目中的标签没有被执行所以它对我们不起作用 .
-
将我们的新WiX安装程序更改为"perUser"并在未来的某个时间处理此问题(不是理想的解决方案)
关于卸载旧的perUser安装 . 如果与最初用于每用户安装的用户相比,登录的用户不同,那么可能会出现问题?这里有什么问题我们应该注意吗?
UPDATE
我已经尝试使用CustomAction的方法,我使用升级代码调用 MsiEnumRelatedProducts
以查看我们的软件的先前版本是否已安装,然后调用
msiexec /X {PRODUCT-CODE-FOUND-USING-MsiEnumRelatedProducts} \q
卸载旧版本 . 但是,这不起作用,因为MSI似乎使用Mutex锁来确保一次只能执行一个MSI操作 .
1 回答
我会回答我自己的问题 .
最后,我使用以下代码创建了一个CustomInstallerAction:
并在WiX安装程序中添加以下内容: