Sequencing issue when reading an ini file with Wix - wix

I have to read an ini file with Wix. This ini file is created by the installer itself by a custom action (an exe file generates the ini file).
Problem:AppSearch (where the ini file is read) is the first step of the InstallUISequence.
Even if I call the CA before AppSearch, I get an error because when I try to read the ini file, it is not created yet..(Return="asyncWait" in the CA).
Here is the call:
<InstallUISequence>
<Custom Action="LaunchCA" Before="AppSearch" />
</InstallUISequence>
Is there a solution? Thanks!

Windows Installer INI searches support only files in C:\Windows folder. So using a search is not feasible.
Instead, you can try using a custom action (custom code written by you) to read the file. I assume you want to save the result in some installer properties. So your custom action will need to receive the installation handle.

So, what you need is to access the data in that generated INI file, right? Do you control the way that EXE outputs the data?
If you do, you can make that data to be dumped not to INI file, but to the custom MSI table instead. Later on, your CA to read the contents of the INI file doesn't have to wait for it to gets created and you'll get rid of the AppSearch dependency.

Related

WIX installer: Use property value to place a file

I've read a property from the registry, and that property has been set properly (I'm using this to check the property value)
<CustomAction Id="Test" Script="vbscript">
<![CDATA[MsgBox Session.Property("MYEXTRAFILESFOLDER")]]>
</CustomAction>
Now I'm just trying to drop a few files into that folder. I can't figure out how to make a File element target a specific directory.
As I get you don't need to change taget path in general but only put some files to specific folder. Easiest way is to create custom action.
Add custom action as described
In InstallExecuteSequence set After=InstallFiles or After=InstallFinalize (to make sure that your files from installer will be copied already)
In custom action read you path from registry
Get you install path using TARGETDIR
Move files from TargetDir to your registry dir
Another option is
Create custom action as described
In custom action read you path from registry
Get file stream from installer and write it to folder
Also this can be an option too. But I don't know how it works exactly

Wix property evaluation

How to use FileSearch result as condition in Component section.
I want to get something like this:
<Property Id=\"CONFIG_XML_EXISTS\">
<DirectorySearch Id="CheckForConfigXml" Path="[INSTALLDIR]\">'
<FileSearch Id="ConfigXmlSearch" Name="config.xml" />
</DirectorySearch>
</Property>
...
<Component Id="c_DefaultConfig.xml" Guid="{1AAB0AFD-B763-4A55-8585-B0AD4D8CE23C}">
<File Id="f_default_config.xml"
Name="default-config.xml"
Source="$(var.SourceRoot)\config.xml"/>
<Condition>CONFIG_XML_EXISTS</Condition>
</Component>
I don't know why but property wix doesn't want to evaluate CONFIG_XML_EXISTS.
Because that search happens very early in the install, the most likely reason is that INSTALLDIR has no value. You haven't said whether you're doing a fresh install or an upgrade, so it's not clear where you think it might be getting its value from.
I'd also point out that the purpose of that source code is apparently to prevent the install of a file if there is one there already, so:
If INSTALLDIR turns out to be the application folder (typically program files) where your files are installed then users can usually change this location, so it's not clear the file is going to be where you expect it to be.
The file overwrite rules prevent incoming files from overwriting modified data files (modify date > creation date) so if that config file has been changed it won't be overwritten and you don't need to do the check.
In your comment you say "My installer must create file config.xml only if there is no such file in target(install) directory. If such file exists, my installer must create file with name template.xml". I think that perhaps the easiest way to do this is in the application after the install has finished, or possibly in a custom action after all the files have been installed. There seems to be no good way to do this before the install because INSTALLDIR is unpredictable. I've seen this kind of problem solved by installing the XML files to (say) User's Application Data, and after the files are installed then the application or a custom action can see what files are there (or not) and get them from User's Application Data.

Create file in installation folder using WiX custom action

I try to create a wix installer that has the need to create a file in the programme folder after Installation. For doing so, I have created a custom action, but I now have the following problem:
In order to write the file, I need to know the installation directory from session["INSTALLDIR"], which is only available if the action is executed "immediate".
However, if i run "immediate" after "install files", the target directory does not yet exist. If I run "deferred", it exists, but i cannot access session["INSTALLDIR"].
If I run "immediate" after "InstallFinalize", I can get the variable and the directory exists, but I am not elevated and hence not allowed to write the file.
What is the correct combination for writing a file to the installation directory?
You need to use CustomActionData to access property values from a deferred CA. You need something like this
or
another answer
Beyond using a built in extension for custom actions instead of writing your own, the next level would be how can I move complexity / custom actions out of the installer?
One thought is to write it to the registry instead. Another thought is for the application reading the value to be able to determine installation directory on it's own. One possibility is reflection to get the location another possibility is to query the MSI API for where the product is installed.

WiX: Copy a file from local folder to installation folder

I'm using a WiX setup project to build an MSI package.
I want the MSI, to do a copy of the given file during the installation to the installation folder from the one, where the .msi file is running from.
I read on WiX a bit, and what I found is the <CopyFile... /> element supposed to do that.
Appreciate your help.
Actually I've figured out what the issue is.
The problem is that the SourceDirectory of the CopyFile element supposed to point to the Directory tag id.
Instead, I've used SourceProperty attribute of the CopyFlie tag, and also defined a Property separately, which made the use of the CopyFile element correct.
So it worked.

Open txt file in wix when clicking btn

I have a wix project to which I added a custom window that checks the dependencies needed to run the app. This window comes up right after the License Agreement. Everything works fine, the dependencies are checked through custom actions and in case they are not fulfilled hyperlinks to official websites appear if the windows installer is above version5.
In case of a lower version I would like to click on a btn "Show dependencies" and to show the txt file with the links. I have the custom action below that open notepad and the property that contains the file.
Code:
<Property Id="FXDEP" Value="$(sys.CURRENTDIR)\Resources\Files\FxDependencies.txt" />
<Property Id='NOTEPAD'>NOTEPAD.EXE</Property>
<CustomAction Id='LaunchDependencies' Property='NOTEPAD' ExeCommand='[FXDEP]' Return='asyncNoWait' />
The problem is that on the dev machine it works since it finds the path, but on other of course it fails.
How should I tell wix to maintain this file and open it?
I tried putting the file into
<Binary Id="FxDependencies.txt" SourceFile="$(sys.CURRENTDIR)\Resources\Files\FxDependencies.txt" />
but the custom action does not recognize it.
You seem to be trying to open the file that resides in the source of your installation. You use the same values for FxDependencies.txt and FXDEP.
Your text file with dependencies resides in Binary table of the installer, to use it you have to extract it into a temporary directory, and then launch Notepad to display it.
To do it, you would have to write several custom actions:
The first CA extract the file into a temporary directory, and saves the path into a property, FXDEPTEMPPATH.
The second CA uses FXDEPTEMPPATH to display it in Notepad.
Another option is to write a small application (.exe) that would contain your FxDependencies.txt, in resources for example. You add this .exe into Binary table of MSI, and launch it instead of Notepad from the installer. In this case MSI will automatically extract the exe into a temporary directory and start it. In your application you create a new text file in temporary directory, by extracting the information from resources, and then launch Notepad to display it.
Edit: There's a number of ways to read a file from the Binary table. See these links for examples:
BinaryWrite from Msiext.
Reading from the Binary Table based on WiX source code.
Streaming a File from the Binary Table.
Write the code yourself:
Open a database view of the active database with MsiGetActiveDatabase and MsiDatabaseOpenView;
Read the binary stream with MsiRecordReadStream.
I would suggest you to create folder in custom action.
So,
Validate pre-requisites
Check windows installer version
If version is less than 5, call a custom action to create folder ($(sys.CURRENTDIR)\Resources\Files\)
Then on button click you can call the custom action to launch txt file