I have two MSI applications (app1.msi and app2.msi) that share the same set of registry values. Both MSI are referencing a dll which contains all custom actions and stuff. I am using WiX 3.8. These registry values are custom for the solution.
I need to find a way for the uninstall process to ONLY remove the registry values if both applications are removed. Right now, whenever I remove either app1 or app2 the registry values are removed, leaving the other application unusable unless I uninstall and re-install.
Any ideas as to how to solve this problem?
This is a very common question. The problem is that both your MSI setups think they "own" the file and registry keys in question so they happily remove them on uninstall - this is obviously clear. Now what to do about it?
The solution is generally to use the same component GUID to install the registry keys / file in both setups. Effectively this means that the component is registered as a shared component. MSI's built-in mechanism to do this is "merge modules" (you can build merge modules with WiX). You should also be able to use WiX include files - though I have to admit that I have never taken the time to actually try it. Essentially this would entail putting a single component in a WiX source file that is then included by both setups, something like this (using the preprocessor feature in WiX): How to include wxi file into wxs?.
Once the same component GUID is used in both MSI file, the reference count for it will be 2 when both products are installed. When one product is uninstalled the reference count will be reduced to 1 and the component will hence not be uninstalled. Once it reaches 0 when the second product is uninstalled, it will be uninstalled (unless it is marked as a permanent component).
Understanding component reference counting is key to understanding MSI. There is an answer here that might help if you take the time to read it thoroughly (I think I recommend this - please give it a once-over):
Change my component GUID in wix? (please do read this answer, see if it still makes sense).
And now a further complication: having deployed your old MSI files "in the wild" means that setting a stable component GUID from now on will not necessarily help to sort out the problem since your old MSI being uninstalled as you install your new MSI still thinks it "owns" the registry key when it is being uninstalled - and hence will delete it. The problem is only solved when both your setups "know" that the component is shared and its registry keys should be left alone.
Before I elaborate this, are these MSI file live? As in published in the wild, or are you still in development?
To get ahead of myself: if you can change the location of the registry key (For example from HKLM\Software\Company\MyProduct
to HKLM\Software\Company\NewProduct
- which is usually not possible) and then also set a new component GUID for it, then you should be "de-coupled" from the sins of the past and your new MSI files should share the component properly.
With all that being said, I want to ask if these registry settings are in HKCU or in HKLM? It is generally not recommended to write settings to HKCU form MSI setups - you should rather populate HKCU when your application is first launched. This approach can solve a lot of hard deployment problems - or prevent them from ever existing.