Once you’ve learnt the basics of using WiX to create msi installers, one of the more sophisticated techniques to master is the Remember Property pattern.

With this pattern, you provide commandline properties to your installer for the first installation that are persisted in the registry for later reuse, by an upgrade or a repair.

WiX’s benevolent dictator, Rob Mensching has an excellent post “The WiX toolset’s ‘Remember Property’ pattern” which goes into some detail on how to do this right.

However, that post is a few years old, and requires a minor hack in the form of a CustomAction.

I wondered if there was a better way to solve the problem, with more recent versions of WiX - and I found that there was.

Here’s a working example for a “SERVER” property, though note that I’m not showing all of the installer, just the elements necessary.

First we have a simple declaration to mark our property as secure.

<Property Id="SERVER"
          Secure="yes"/>

In theory we don’t need this, but in practice I found my msi didn’t upgrade property when deployed through SCCM without this. YMMV.

Next we have a second property - in my case distinguished by the “P.” prefix - into which we load any value previously stored in the registry.

<Property Id="P.SERVER">
  <RegistrySearch Id="S.SERVER"
                  Root="HKLM"
                  Key="SOFTWARE\Niche Software\[ProductName]"
                  Name="Server"
                  Type="raw"
                  Win64="$(var.Win64)"/>
</Property>

If we didn’t get a value for SERVER passed on the commandline, we want to overwrite it with the value loaded from the registry, if any.

<SetProperty Id="SERVER"
             Value="[P.SERVER]"
             After="AppSearch">NOT(SERVER)</SetProperty>

Finally, we store the value we used in the registry, so that we can reload it next time our installer is activated:

<RegistryValue Root="HKLM"
               Key="SOFTWARE\Niche Software\[ProductName]"
               Name="Server"
               Value="[SERVER]"
               Type="string"/>

This last element needs to be part of a component that gets installed, preferably one that’s conditional on SERVER being defined. All the other elements can nest directly under your master <Product> element.

Even though I’ve used this to good effect in several installers so far, there are sure to be ways this can be improved.

Comments

blog comments powered by Disqus
Next Post
Blink Estimation  11 Aug 2013
Prior Post
Why attend a user group meeting?  12 May 2013
Related Posts
Browsers and WSL  31 Mar 2024
Factory methods and functions  05 Mar 2023
Using Constructors  27 Feb 2023
An Inconvenient API  18 Feb 2023
Method Archetypes  11 Sep 2022
A bash puzzle, solved  02 Jul 2022
A bash puzzle  25 Jun 2022
Improve your troubleshooting by aggregating errors  11 Jun 2022
Improve your troubleshooting by wrapping errors  28 May 2022
Keep your promises  14 May 2022
Archives
August 2013
2013