How do I install a Windows Installer Patch?

Consider a scenario where a single file in the application has undergone a change, and this file needs to be replaced in all the machines where it is Installed. In such a situation, it doesn’t make sense in creating a new package and deploy the same. Also, if we have any configuration file which the user has modified for his customization, re-installing the package will also replace those files. Hence, we will need to find a way to replace only that file.., without reinstalling the application package. That is where a patch comes into picture. 

Keeping it simple, a patch is basically the file from which changes to an already installed application is done. Also, a Patch can be installed individually, if the previous MSI already exists in the system. A windows Installer Patch file, will usually have an extension of .msp.
 
How to Install a Patch
 
When you run the patch Silent/unattended, the dialogs are not displayed and the required property like REINSTALL are not set. Hence, we will need to define this in the command line for Patch Installation.

Msiexec /p ABC10_v1.msp REINSTALL=ALL REINSTALLMODE=omus

Also, double-clicking the .MSP file will patch an existing installation as well as the locally cached copy of the MSI database because the dialogs are run and they in turn set REINSTALL and REINSTALLMODE properties.

Advantages of Using Patches:

  1. A patch can contain an entire file or only the file bits necessary to update part of the file. This will enable the user to download an upgrade patch that is much smaller than the installation package for the entire product.
  2. Create and install patches that can be uninstalled singly, and in any order, without having to uninstall and reinstall the entire application and other patches.
  3. Skip actions associated with specific tables that are unmodified by the patch. This can significantly reduce the time required to install the patch
  4. An update using a patch can preserve a user customization of the application through the upgrade.

4 comments

  1. This is what Kim replied in WiX discussion Thread

    “This is possible using msidb which is part of the Windows Installer Development Tools.

    I think you will need to do the following:
    – extract cab file using “msidb -x”
    – replace the file in the cabinet
    – delete the cab file from the msi using “msidb -k”
    – add the changed cabinet back using “msidb -a”

    If you do not know the name of the stream you can use a tool like InstEdit to find out.”

  2. This is what Saascha replied in WiX discussion Thread (replacing one single file)

    Assuming you don't mind having an external CAB file, it's not too hard… here's a (simplified) script that I'm using to permit end-users to customize a configuration file prior to deployment. The example code modifies the MSI (which is fine for testing), however our production code creates a copy, modifies it, generates an MST against the original and finally removes the copy.

    This code doesn't actually “replace” the original file, but adds a second copy which gets installed instead.

    Const MSI_SOURCE = “application.msi”
    Const FILE_REPLACE = “config.xml”

    Dim filesys, installer, database, view
    Dim objFile, size, result, objCab

    Set filesys=CreateObject(“Scripting.FileSystemObject”)
    Set installer = CreateObject(“WindowsInstaller.Installer”)
    Set database = installer.OpenDatabase (MSI_SOURCE, 1)

    Set objFile = filesys.GetFile(FILE_REPLACE) size = objFile.Size

    objCab.CreateCab “config.cab”, False, False, False objCab.AddFile FILE_REPLACE, filesys.GetFileName(FILE_REPLACE) objCab.CloseCab

    Set view = database.OpenView (“SELECT LastSequence FROM Media WHERE DiskId = 1”) view.Execute

    Set result = view.Fetch
    seq = result.StringData(1) + 1 ' Sequence for new configuration file

    Set view = database.OpenView (“INSERT INTO Media (DiskId, LastSequence, Cabinet) VALUES ('2', '” & seq & “', 'config.cab')”) view.Execute

    Set view = database.OpenView (“UPDATE File SET FileSize = ” & size & “, Sequence = ” & seq & ” WHERE File = '” & LCase(FILE_REPLACE) & “'”) view.Execute

Leave a Reply

Your email address will not be published. Required fields are marked *