9

问题

我有一个 MSI,它在安装期间创建和启动 Windows 服务,并在卸载期间停止和删除该服务。这在自行安装和卸载时工作正常,但在升级时,会显示Files in Use对话框(仅在 Vista 及更高版本上,由于新的Restart Manager),表明该服务正在使用中。

背景

Files in Use对话框在InstallExecute序列期间由InstallValidate自定义操作显示,该操作安排在RemoveExistingProducts自定义操作之前;这意味着之前的版本尚未卸载,因此应显示“正在使用的文件”对话框。

MSDN 文档指出必须在InstallValidate操作之后安排RemoveExistingProducts操作,并且我目前在InstallValidate操作之后立即安排了RemoveExistingProducts操作。

潜在解决方案

我想将RemoveExistingProducts自定义操作重新安排到InstallValidate自定义操作之前,以便之前的安装有机会在显示“正在使用的文件”对话框之前停止并删除该服务。我尝试重新安排这些操作,它似乎可以正常工作,没有不良副作用(尽管日志仍然表明InstallValidate操作在RemoveExistingProducts操作之前执行),但我很犹豫是否使用此解决方案,因为它违反了 MSDN 文档,并且可能会有我还没有看到的不利影响。

有没有人试过这个?我能想到的唯一其他选择是让新安装停止旧安装的服务,但这是不可取的,因为它要求安装具有有关它可以升级的所有旧安装的信息(停止此特定服务可能涉及更多不仅仅是简单地调用服务管理器来停止它)。

4

4 回答 4

6

我实施了问题中概述的潜在解决方案,将RemoveExistingProducts安排在InstallValidate之前。我还没有看到任何问题,但我会在安装得到更多使用后再次发布。

更新

我们的安装已经使用了一段时间,我没有注意到任何不良影响。

于 2010-02-16T15:13:10.447 回答
2

它已经内置在 MSI / Windows Installer 中……唯一的问题是 .NET 安装程序类不使用 MSI“服务安装”功能。实际发生的情况是 MSI 正在尝试安装文件并使用刚刚复制的文件运行自定义命令(这就是 Visual Studio 放入 MSI 的所有内容)。

要解决它,您可以使用 ORCA 编辑 MSI 并将以下行添加到ServiceControl表:

1   ServiceName 170     1   C__489628C5CC1144CB47F43E8BE7F3F31D

您可以从 FILES 表中查找的组件 ID ...我刚刚选择了主 EXE 文件的组件 ID。170 是一个位图,告诉 Windows 安装程序在安装和卸载时停止和删除服务。

这将为 .NET 安装程序添加服务扫清道路,您可以在通过自定义命令安装服务后使用 ServiceController 启动服务。

于 2011-04-07T04:58:05.307 回答
0

一个潜在的问题是,如果用户在 InstallValidate 期间取消(例如,由于没有足够的磁盘空间或正在使用的文件)或在安装期间取消,回滚行为是什么。理想情况是应用程序状态与之前相同(例如安装了之前的应用程序)。您可能会放弃排序,尽管回滚可能是您可以不用的功能。

于 2010-01-28T22:24:00.190 回答
0

我认为这将在不违反 MSDN 文档的情况下为您提供帮助,并避免将来出现任何问题。设置条件“已安装或 PREVIOUSVERSIONSINSTALLED”,您也可以很好地升级,因为在 FindRelatedProducts 期间的 InstallValidate 操作之前设置了属性 PREVIOUSVERSIONSINSTALLED。我不知道为什么,但是属性 PREVIOUSVERSIONSINSTALLED 没有记录在 MSDN 中,但它确实存在并且对我很有帮助。

于 2013-12-20T20:31:20.117 回答