InstallAnywhere offers merge module support to facilitate parallel development, code sharing, and reuse. Unlike Windows Installer merge modules, InstallAnywhere merge modules can be integrated into InstallAnywhere projects in four ways: Design-Time, Build-Time, Install-Time, and Dynamic. The way the merge module is integrated affects how projects are coded and determines some aspects of how the installation functions at run-time. The goal of this article is to talk a bit out what merge modules are, how to write them, and how to use them.
What Is a Merge Module?
Merge modules are distinct groups of installation functionality that are packaged into a single package. They can be thought of as “plug and play” type functionality where, if they are written properly, they deliver a complete set of functionality in a package that can be included in one or more product installations. Conceptually they are like a USB device: once you plug it into the computer, the complete set of functionality is available, and when removed the functionality is completely removed. Similarly, when a merge module is included in an installation project, the result of running the built installation will be delivery of the contents of the merge module, as well as those in the installation project itself. If removed from the project, all of the functionality contained within is removed from the project.
Merge modules can contain anything a normal installation project can contain, like actions in Pre- and Post-Install tasks (including panels, consoles, etc…), actions in the Install and Uninstall tasks, and actions in Pre- and Post-Uninstall (including panels, consoles, etc…). Which of these actions will be visible or executed is determined by the merge module type designation when it is integrated into the installation project that consumes it.
Developing Merge Modules
From a development standpoint a merge module starts out as any other installation project. Designating the project as a merge module occurs in the Build task where the format of the output is specified. For testing purposes, you can even build the project as both a merge module and as an installation project that can be run independently on its own. This allows for testing of the merge module functionality outside any other installation project so it can be fully debugged before including it in any projects.
All merge module projects can be coded the same way and the distinction of which type they are is determined at integration time with the product installation that delivers them. In fact, the same merge module can be included in different projects as different types depending on what you intend as the developer. This is rare, but the flexibility does exist for those times where it may be desirable. That being said, it does help to understand how the merge module will be consumed to allow you to make coding choices, so you probably want to consider that before getting too far in your implementation.
Communication of variable values can take place between the merge module and the project which consumes it, and this is done via Advertised Variables. The consuming project can set variables within the merge module and the merge module can in turn set variable values within the consuming project. Merge modules advertise their variables too so that at import time they can be seen from the consuming project via the Edit Variables view that is unique for each type of merge module.
Using Merge Modules
As an InstallAnywhere developer, how do you know which type to choose? Let’s go through the types and how their behaviors differ.
Design-Time Merge Modules
Design-Time merge modules are imported in the Modules section under the Organization task. They are imported a single time during development of your installation project and can be thought of like taking a copy of the merge module content at import time and inserting the actions within it into the appropriate tasks within your installation project.
Once the merge module has been imported, there are no ties to the original merge module project, so any changes to it will only be included into new projects that import it.
After the Design-Time merge module has been imported, the actions from it can be moved around within your project to put them into the order that you desire. The actions are independent and can be acted upon independently. You can even organize them under action groups and assign rules to them.
Build-Time Merge Modules
Build-time merge modules are included via the Install Merge Module action in the Installation task. They are included in such a way that there is a reference to them in the consuming project, but they are streamed into the installation package at build-time. There is some control in the Install Merge Module action over whether the Pre-Install and Post-Install tasks are included in the run time functionality as well.
Although Pre-Install and Post-Install tasks can be included with Build-Time merge modules, the merge module will be installed silently so all Panels, Consoles, and Show Message actions will be ignored at run time.
Install-Time Merge Modules
Install-Time merge modules are included via the Install Merge Module action in the Installation task very similarly to Build-Time merge modules. They are also included in so that there is a reference to them in the consuming project, but instead of being streamed into the installation package at build-time, a reference to a directory is provided so that the project will know where to find the merge module at run time.
When the Install-Time merge module action is used in this way, the referenced directory is searched and all InstallAnywhere merge modules located in that directory will run in alphabetical order. As with Build-Time merge modules, there is some control in the Install Merge Module action over whether the Pre-Install and Post-Install tasks are included as well.
Although Pre-Install and Post-Install tasks can be included with Install-Time merge modules, the merge module will be installed silently so all Panels, Consoles, and Show Message actions will be ignored.
Dynamic Merge Modules
Dynamic merge modules are imported in the Modules section under the Organization task. They are imported an initial time when they are included in the project, but they are re-imported each time the installation is built or closed and opened again. This is the type of merge module that is the most like a Windows Installer Merge Module in how it is integrated with its consuming projects.
The author of the consuming project can chose whether or not to include Pre-Install and Post-Install actions from the merge module. Unlike Build-Time merge modules, a Dynamic merge module’s Pre-Install and Post-Install actions are grouped in a single action within the consuming project’s Pre-Install and Post-Install tasks. The actions within the merge module can be visible within the single group, but cannot be expanded or edited from the consuming project. The Installation tasks of the merge module are included in the Installation task of the consuming project, but as a single item that cannot be expanded or viewed via the consuming project. The single group can be moved as a single entity, but the separate actions within it cannot be split apart.
Merge modules can add a lot of flexibility to the way you code your projects. They can allow multiple developers to work on a project simultaneously, and can facilitate easy code sharing and reuse across multiple projects so give them a try!
For tips on creating professional, reliable installations that make a favorable first impression for your products, see Robert Dickau's white paper Best Practices for Building Multi-Platform Installers