Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to exclude files in Wix toolset

Tags:

wix

heat

While harvesting files for heat.exe, I would like to exclude the files with the extension .exe from the input folder since it fetches all the files in the folder at first place.

Below is my code.

    %WIX_PATH%\Heat.exe" dir "%input_folder%" -cg SourceProjectComponents 
    -dr INSTALLLOCATION -scom -sreg -srd -var var.BasePath -gg -sfrag 
    -var var.BasePath -out "%output_folder%\Output.wxs

PS: the input_folder consists of severall .dll and .exe files. hence individual harvesting of the file wasn't possible.

Thanks in advance.

like image 370
codec Avatar asked Jun 26 '17 17:06

codec


People also ask

What is a Wxi file?

File created by the WiX toolset, a Windows installer developing program; contains a top-level container element called, <Include>, which is the root element of the file; similar to header (. H) files used by C++ code. An example of the <Include> root file is below: <Include>

How do I use heat EXE on WiX?

Basically the heat command generates a wxs file with the above component in it. Then all you need to do is to include this component or component group in your main installer. It will then create the registry entries instead of running regasm. The uninstall would then remove these registry entries.


2 Answers

You will need to use an XSLT transform.

Something like this should work for you; Just include -t <Path to the xslt file> in your command line for heat.

This XSLT outputs a new XML file that contains all XML nodes of the input, except if any nodes are <Component> elements with .exe <File> elements.

RemoveExeComponentsTransform.xslt

<?xml version="1.0" encoding="utf-8"?>
<xsl:stylesheet
    xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
    xmlns:wix="http://schemas.microsoft.com/wix/2006/wi"
    xmlns="http://schemas.microsoft.com/wix/2006/wi"

    version="1.0" 
    exclude-result-prefixes="xsl wix"
>

    <xsl:output method="xml" indent="yes" omit-xml-declaration="yes" />

    <xsl:strip-space elements="*" />

    <!--
    Find all <Component> elements with <File> elements with Source="" attributes ending in ".exe" and tag it with the "ExeToRemove" key.

    <Component Id="cmpSYYKP6B1M7WSD5KLEQ7PZW4YLOPYG61L" Directory="INSTALLDIR" Guid="*">
        <File Id="filKUS7ZRMJ0AOKDU6ATYY6IRUSR2ECPDFO" KeyPath="yes" Source="!(wix.StagingAreaPath)\ProofOfPEqualsNP.exe" />
    </Component>

    Because WiX's Heat.exe only supports XSLT 1.0 and not XSLT 2.0 we cannot use `ends-with( haystack, needle )` (e.g. `ends-with( wix:File/@Source, '.exe' )`...
    ...but we can use this longer `substring` expression instead (see https://github.com/wixtoolset/issues/issues/5609 )
    -->
    <xsl:key
        name="ExeToRemove"
        match="wix:Component[ substring( wix:File/@Source, string-length( wix:File/@Source ) - 3 ) = '.exe' ]"
        use="@Id"
    /> <!-- Get the last 4 characters of a string using `substring( s, len(s) - 3 )`, it uses -3 and not -4 because XSLT uses 1-based indexes, not 0-based indexes. -->

    <!-- We can also remove .pdb files too, for example: -->
    <xsl:key
        name="PdbToRemove"
        match="wix:Component[ substring( wix:File/@Source, string-length( wix:File/@Source ) - 3 ) = '.pdb' ]"
        use="@Id"
    />

    <!-- By default, copy all elements and nodes into the output... -->
    <xsl:template match="@*|node()">
        <xsl:copy>
            <xsl:apply-templates select="@*|node()" />
        </xsl:copy>
    </xsl:template>

    <!-- ...but if the element has the "ExeToRemove" key then don't render anything (i.e. removing it from the output) -->
    <xsl:template match="*[ self::wix:Component or self::wix:ComponentRef ][ key( 'ExeToRemove', @Id ) ]" />

    <xsl:template match="*[ self::wix:Component or self::wix:ComponentRef ][ key( 'PdbToRemove', @Id ) ]" />

</xsl:stylesheet>
like image 50
Brian Sutherland Avatar answered Nov 04 '22 13:11

Brian Sutherland


I had the same issue where I had lots of files that I needed to include into the WXS file in a project and I wrote an open source command line application to generate XMLs of directory structure, files and components while ignoring folders, extensions, files etc via a .wixignore file (formatted similar to .gitignore).

You can take a look at the it here.

like image 39
Murat Aykanat Avatar answered Nov 04 '22 11:11

Murat Aykanat