编辑 MSI 数据库






4.77/5 (5投票s)
编辑 MSI 数据库的属性。
摘要
Windows Installer 可高效地安装和配置您的产品和应用程序。我们通常使用 Microsoft Build and Deployment 项目或 InstallShield 等外部工具来创建安装程序。
这些工具中的大多数可能不具备编辑/更新正在生成的安装程序属性的功能。
Orca 是 Microsoft 提供的用于执行这些活动的工具。但是,当需要频繁地在每次构建或每次部署后修改文件时,这项任务会变得很困难。
本文提供了执行此操作的不同方法,首先介绍如何使用 Orca 工具编辑 MSI 数据库。
在我目前的项目中,我们正在使用这种方法,为组织节省了大量时间和成本。这种方法已融入整个组织,帮助所有构建脚本创建者修改他们的 MSI 安装程序。该解决方案是使用 Microsoft 提供的 Orca 工具、用于构建 MSI 的构建脚本以及用于编辑 MSI 元数据的 VB 脚本等实现的。
引言
在一个组织中,当频繁进行构建和部署,同时涉及多个应用程序时,开发人员修改一个或多个 MSI 属性/数据库字段会很麻烦。用于生成部署 MSI 的工具可能没有在构建过程中修改属性的功能。因此,解决方法是在构建完成后修改属性。这对开发人员来说是一项额外的任务。
本文档试图通过提供一种手动、自动地在构建脚本中修改 MSI 数据库值(MSI 属性)的方法来解决上述问题。本文讨论的修改 MSI 属性的方法为涉及多个安装程序的构建过程提供了高度灵活和快速的模式。该方法经过测试和实施。新流程有助于节省构建安装程序和修改安装程序属性的时间。
修改 MSI 属性的必要性
MSI(Microsoft Installer)包含一个由多个表组成的数据库,每个表都有特定的用途。它还包含依赖项/引用的列表等。例如,如果 MSI 安装程序缺少某个引用,通常的方法是重新构建带有适当 MSI 的安装程序。但是,通过适当地修改 MSI 数据库并获取所需的引用,可以实现相同的目标。
另一种情况是需要递增 MSI 中的产品版本。默认情况下,它将是 1.0.0。但是,随着 MSI 的每次新构建,都需要更改它,以便可以跟踪安装的版本。Visual Studio 中的设置和部署项目不提供此功能。
可以使用 Orca 工具手动修改它,但如果每次构建后都需要修改,则会耗费大量时间。如果我们有多个 MSI,则会更加复杂。
开发此方法的需求源于我们遵循迭代交付模式,需要非常频繁地进行构建和增强。我们的项目包含大约 10 个 MSI,每个 MSI 都安装在不同的服务器上。服务器上的部署由不同的组负责,该组对 MSI 属性应包含的内容(包括产品版本)有特定要求。构建工程师在每次构建后修改 10 个 MSI 并修改 MSI 数据库是一项复杂且容易出错的任务,因为我们还必须确保所有 MSI 在每次发布时都使用相同的版本号进行版本控制。
一般的 MSI 编辑过程 | 新方法 |
构建安装程序。使用外部工具 ORCA 修改 MSI 数据库中所需的属性。 | 构建安装程序。所有工作都在构建过程中完成。 |
总而言之,以下是推动此方法的主要因素:
- 由于迭代模式导致的频繁发布。
- 包含许多安装程序的复杂项目。
- 每次构建后的耗时过程。
- 手动修改多个安装程序的属性容易出错。
- 由 TFS 管理员一次性设置,由构建工程师永久构建。
使用 Orca 修改 MSI 属性
Orca 是 Windows Installer SDK 提供的一个 Windows Installer 包编辑器,旨在提供对组成 Windows Installer 包的数据库表的完全访问。虽然 Orca 提供了对 Windows Installer 所有功能的强大访问,但它并不旨在取代功能齐全的包创作环境。Orca.exe 是一个数据库表编辑器,用于创建和编辑 Windows Installer 包和合并模块。该工具提供图形界面来进行验证,突出显示出现验证错误或警告的特定条目。
Orca 可以 此处 免费下载。
启动 Orca 工具并打开您想要编辑的 MSI。
打开后,您会立即发现左侧有很多表,右侧是相关字段。
转到您想要编辑的表和字段,进行编辑并保存文件。
在我们的一种场景中,我们需要更改产品版本。它在 MSI 的属性表中。单击左侧的表,查看右侧的字段。正如您所见,ProductVersion 默认值为 1.0.0。单击该值并将其更改为所需值。保存文件。
自动化过程的详细信息
实施过程
我工作的项目基于 .NET Framework 3.0,使用 C# 作为编程语言,并使用 TFS 作为配置管理。MSI 构建在构建服务器上进行,它会从 TFS 中获取代码。构建过程完成后,输出将如下所示:
- 编译所有代码文件
- 构建所有代码文件并将生成的程序集/文件放置在 Release 文件夹中。
- 压缩 Database 文件夹中的数据库项。
- 使用 Release 文件夹中的程序集/文件生成安装程序,并将它们放置在 MSI 文件夹中。
一旦构建成功,开发人员或构建工程师就需要手动打开每个 MSI 的 Orca 并修改所需的属性。由于我们的项目包含 10 个安装程序,并且我们采用迭代式开发模式,因此我们每周需要执行此操作一次以上。
我设想了一种方法来自动化这个过程,而不是手动打开每个安装程序并进行编辑。
这消除了手动编辑每个 MSI 所需的时间,并消除了过程中的任何人为错误,因为所有安装程序都应该具有相同的 ProductVersion。
下面的子部分将详细介绍配置快速构建过程所需的步骤,并将适用于所有 .NET 版本、语言和版本控制系统。
2. 先决条件
在开始自动化方法之前,我们需要确保我们具备以下先决条件。
- MSI 安装程序已生成。
- Winrunsql.vbs 文件,在本文中附带。此文件包含用于更新指定值的脚本。
3. 准备批处理文件
使用 vbscript 文件,我们可以运行一个修改指定值的命令。
在我们的情况下,命令如下所示:
cscript //nologo "WiRunSql.vbs" "B:\20100903.1\MSI_V\Clinical_2.06.36.msi" "UPDATE Property set Value = '2.06.36' where Property = 'ProductVersion'"
cscript 是运行脚本文件的命令。
请注意,我们指定了 vbscript 文件名/路径
下一个参数是我们想要修改的 MSI 的名称/路径
最后一个参数是常规更新命令,它将更新属性为 ProductVersion 的 Value。
每次执行此操作并确保命令每次都正确是一项艰巨的任务。
因此,更好的方法是创建一个包含所有必需命令的批处理文件。
将上面一行复制到 .bat 文件中。
因此,每当您需要修改此特定属性值时,您需要确保的是版本号正确且 MSI 路径正确。
4. 集成到构建过程中
再次,在构建后从外部运行批处理文件,确保批处理文件中的值正确或用单个字段替换它们,这又是另一项需要遵循的任务。
因此,我最终想将此命令集成到构建脚本中,这样构建工程师除了构建项目之外,什么都不用做。项目构建完成后,MSI 将生成所需的修改值。
项目的服务器构建脚本可在 TFSBuild.proj 文件中找到。
此文件包含 XML 代码来识别解决方案。此文件执行以下活动:
构建每个解决方案并将程序集/文件放置在 Release 文件夹中
借助 .vdproj 文件,从 Release 文件夹中提取程序集/文件,并将它们打包成 MSI。
将 MSI 放置在正确的位置。
MSI 生成后,编写代码以修改 MSI 的数据库属性。
<Exec Command= "cscript //nologo "$(BuildDirectoryPath)\$(TeamProject)\$(BuildType)\Binaries\Release\WiRunSql.vbs" "$(DropLocation)\$(BuildNumber)\MSI\ClinicalServer_$(VersionNumber).msi" "UPDATE Property set Value = '$(VersionNumber)' where Property = 'ProductVersion'""/>
上面的 XML 脚本执行了相同的操作。
<Exec> 指定执行,而 parameter 表示这是一个命令。这意味着运行 parameter 中指定的命令。
请注意,我们正在调用 WiRunSql.vbs。此文件默认情况下在构建服务器上不可用。因此,我们需要将此文件复制到服务器上的 Release 文件夹。
将文件复制到 Release 文件夹的方法:
- 将文件添加到其中一个项目中,构建完成后,文件将被添加到 Release 文件夹。
- 将文件添加到公共 TFS 文件夹中,并在 TFSBuild.proj 文件中将文件复制到 Release 文件夹。
VersionNumber 是 TFSBuild.rsp 文件中指定的数字,它是 TFS 构建过程的一部分。此 VersionNumber 被构建用于版本化程序集。通过这种方式,程序集和安装程序也将与相同的版本号同步,从而消除与版本相关的任何混淆。
5. 构建后
构建成功后,您可以在 MSI 文件夹中找到输出,其中包含已进行所需属性更改的安装程序。
6. 构建工程师需要做什么?
将 WiRunSql.vbs 文件复制到 Release 文件夹,一次性任务。
在 TFS 的构建服务器上进行构建。
找到安装程序并提供给安装团队。
7. 后续步骤
在上述过程中修改 MSI 属性是最快、最安全的方法之一。
4. 面临的挑战
1. 复制 .vbs 文件
WiRunSql.vbs 文件应放置在构建服务器上。但由于是公司服务器,我们无权将文件复制到服务器。另一个放置位置是命令执行所在的文件夹。
这被确定为 Release 文件夹,并在每次构建期间将文件放置在该位置解决了问题。
实际上是将文件放置在分支中的一个文件夹中,并在构建脚本中使用该文件将其复制到 Release 文件夹。
5. 数据样本
表 2 显示了我们应用程序目前拥有的安装程序数量。
安装程序类型 | 安装程序数量 |
MSI | 10 |
下面的表 3 比较了手动和快速构建在最佳和最坏情况下的时间。
最佳情况下的耗时 | 最坏情况下的耗时 | |
手动 MSI 编辑 | 50 分钟。 | 2 小时。 |
自动化方法 | 5 分钟 | 30 分钟 |
与构建集成 | 0 分钟 | 不适用 |
将 MSI 编辑集成到构建过程中后,无需执行任何额外任务。一旦该过程经过测试和验证,它就是万无一失的,不会出现最坏情况。
6. 集成到构建中的优势
以下是我们通过构建脚本获得 MSI 编辑功能的主要优势:
- 无需再担心版本控制。在 TFSBuild.rsp 文件中指定版本,该文件通常用于版本化程序集,构建使用相同的文件来更新版本。
- 无需使用外部工具修改 MSI 数据库。
- 无需执行此活动的额外步骤。
- 对构建文件进行一次性修改即可在整个项目中使用。
7. 成就
目前的构建集成已实施,以解决部署工程师(进而解决客户)长期以来因产品版本延迟交付而面临的痛点。
给安装程序版本化的创新方法在构建和部署过程中节省了大量时间。此外,它使整个过程更加可靠、健壮且不易出错。
由于上述优势,本文提出的方法已分发给不同的团队,收到的反馈非常积极。
8. 致谢
我衷心感谢我的客户,他们提供了我对这种类型构建的见解,我在其基础上进行了改进。我也感谢我的公司提供了一个分享想法的平台。
参考文献
- MSDN。
- “Professional.Team Foundation Server”,Wrox 出版社。