I need to run some VSTOs after they been installed. Everything I tried came out negative.
One example:
<Property Id="runcmd">start</Property>
<CustomAction Id="RunOutlookVSTO"
Property="runcmd"
Execute="deferred"
Return="asyncNoWait"
ExeCommand="[SourceDir]Outlook2010AddIn.vsto">
</CustomAction>
<InstallExecuteSequence>
<Custom Action="RunOutlookVSTO"
After="PublishProduct">NOT INSTALLED</Custom>
</InstallExecuteSequence>
Error: No reaction.
Second example: replace start with cmd
Error: No reaction.
Third example: Replace start with msiexec and msiexec /i
Error: msiexec help screen and "did not find any msi to exec"
Fourth example: <Custom action id="RunOutlookVSTO" etc>
Error: Does not understand custom at compile.
EDIT:
Seems to be a bit of a confusion, just to be clear - yes I tried the registry key, and it is being ignored by the Office applications (Outlook, Word, Excel).
<RegistryKey Action="none" Root="HKLM" Key="SOFTWARE\Microsoft\Office\14.0\User Settings\">
<RegistryKey Id="CreateVSTOOutlook" Action="createAndRemoveOnUninstall"
Key="OUR.Outlook2010AddIn\Create\Software\Microsoft\Office\Outlook\Addins\OUR.Outlook2010AddIn">
<RegistryValue Id="CmdLineOutlook" Name="CommandLineSafe" Value="1" Type="integer"></RegistryValue>
<RegistryValue Id="descOutlook" Name="Description" Value="Tilføjelsesprogram til Outlook 2010" Type="string"></RegistryValue>
<RegistryValue Id="nameOutlook" Name="FriendlyName" Value="Outlook 2010 AddIn" Type="string"></RegistryValue>
<RegistryValue Id="LoadOutlook" Name="LoadBehavior" Value="3" Type="integer"></RegistryValue>
<RegistryValue Id="manifestOutlook" Name="Manifest" Value="[INSTALLDIR]OUR.Outlook2010AddIn.vsto|vstolocal" Type="string"></RegistryValue>
</RegistryKey>
</RegistryKey>
Any ideas what I could try next?
Vsto addins are not standalone programs you can execute. They are dll's that get loaded and then called by the respective office programs through a special bootstrapper.
In your case starting OUTLOOK should load the addin (if it's registered properly). And nothing else will.
-- EDIT --
The .vsto file extension gets associated with the VstoInstaller.exe which is the program you try to run. Note that the vsto file is not a program and as such can't be executed/run. It is a configuration file that is understood by the vstoinstaller (program).
For a default installation VSTOInstaller.exe can be found in
C:\Program Files\Common Files\microsoft shared\VSTO\10.0\VSTOInstaller.exe
it has a /help switch but the install syntax is:
VSTOInstaller.exe /i \servername\foldername\AddIn.vsto
for more info see this msdn link
Related
Firstly I should clarify that I am a novice and have been struggling to understand the WIX formatting, but by cobbling together examples found on-line, I now have the files installing fine so I next need to register my DLL.
I used the example here as a starting point: How to deploy a SharpShell-based shell extension via WiX? but it seems that the SharpShell tool srm.exe may not be getting called at installation.
If I manually call srm.exe as follows, it works as hoped i.e. the DLL is registered and my shell extension works.
srm install MyExtension.dll -codebase
I can also see that the registration has been successful via the Server Manager application that comes with SharpShell.
I can also manually uninstall with the following - not that this is particularly relevant to my problem but it at least confirms that the manual methods work:
srm uninstall MyExtension.dll
Here is a fragment of my WXS file. When I run the resultant MSI, the files are installed but the DLL is not being registered; confirmed via SharpShell's Server Manager. Where am I going wrong?
</Component>
<Component Id="SRMexe" Guid="C17BB61F-6471-46F9-AA87-2D14D2456632">
<File Id='srm' Name='srm.exe' DiskId='1' Source='..\MyExtension\packages\SharpShellTools.2.2.0.0\lib\srm.exe' KeyPath='yes'>
</File>
</Component>
<!-- TODO: Insert files, registry keys, and other resources here. -->
<!-- </Component> -->
</ComponentGroup>
</Fragment>
<Fragment>
<CustomAction Id="InstallShell" FileKey="srm"
ExeCommand='install "[INSTALLFOLDER]\MyExtension.dll" -codebase'
Execute="deferred" Return="check" Impersonate="no" />
<CustomAction Id="UninstallShell" FileKey="srm"
ExeCommand='uninstall "[INSTALLFOLDER]\MyExtension.dll"'
Execute="deferred" Return="check" Impersonate="no" />
<InstallExecuteSequence>
<Custom Action="InstallShell"
After="InstallFiles">
NOT Installed
</Custom>
<Custom Action="UninstallShell"
Before="RemoveFiles">
(NOT UPGRADINGPRODUCTCODE) AND (REMOVE="ALL")
</Custom>
</InstallExecuteSequence>
</Fragment>
It doesn't look like you have any references to the Fragment with the CustomAction definitions so they are not linked into your final output MSI.
Add a CustomActionRef from your Product element to create the reference.
I am really new using WIX, my only experience to build a complete install was with INNO, and WIX has been decided the way to go for an MSI
The installation includes a bunch of examples and templates, 427 files, which seems crazy to enumerate even with an utility like HEAT.EXE
So we went for a self-extracting utility. WIX install includes this custom utility and the compressed cabinet file, and then that extracts files and folders via custom action.
Problem is when we try to delete the compressed file and the extractor utility. I haven't found the way to delete them after the extraction takes place. RemoveFile seems to not work, and deleting the file within the extraction utility fires the self-healing mechanism in every run of the application.
Leaving the files in the install is dangerous, it is 200MB and it would reset all the installed examples if user runs the self-extraction utility by accident.
If it is of use, the WIX snippet in charge of this is like that:
<Fragment>
<ComponentGroup Id="App_Files">
<Component Id="cmp_Files_Dat" Directory="INSTALLCOMMONFOLDER" Guid="{8BFED6C2-4D4F-48BB-xxxx-C171F624C90B}">
<File Id="fil_Files_Dat" Source="appfiles\files.dat" />
<RemoveFile Id="rem_Files_Dat" Name="files.dat" On="install" />
</Component>
<Component Id="cmp_UnpackFiles_exe" Directory="INSTALLCOMMONFOLDER" Guid="{5722B5E0-C6E8-4C71-yyyy-61EC0ACA0D72}">
<File Id="fil_UnpackFiles_exe" Source="appfiles\UnPackFiles.exe" Checksum="yes" />
<RemoveFile Id="rem_UnpackFiles_exe" Name="UnPackFiles.exe" On="install" />
</Component>
</ComponentGroup>
<CustomAction Id="action_UnPackFiles" FileKey="fil_UnpackFiles_exe" ExeCommand="[INSTALLCOMMONFOLDER]" Execute="commit" Return="check" Impersonate="no" />
<InstallExecuteSequence>
<Custom Action="action_UnPackFiles" After="InstallFiles" > NOT (REMOVE="ALL") </Custom>
</InstallExecuteSequence>
</Fragment>
The net result of the code above leaves the files, does not remove them.
Thanks in advance
Josep
I get an error when I try to use a custom action to add a really long registry value before uninstall.
<CustomAction Id="InsertValue" Return="check" Execute="deferred" Impersonate="no" Directory="INSTALLDIR" ExeCommand=""reg add HKEY_CURRENT_USER\Software\Intel\Display\igfxcui\HotKeys" /v 9530 /t REG_BINARY /d <REALLY LONG HEXADECIMAL VALUE>"/>
The value is deleted on install and I need to write it back during uninstall but the value is longer than 255 characters so it is giving me a string overflow error.
What other options do I have to write such long values into the registry?
Try this code. This is the correct way to write to registries from wix.
<RegistryKey Root="HKCU"
Key="SOFTWARE\Intel\Display\igfxcui\HotKeys">
<RegistryValue Name="9530"
Action="write"
Value="LONG HEXADECIMAL VALUE"
Type="binary"
KeyPath="yes" />
</RegistryKey>
You should write this between a component tag.
I am trying to understand how my setup.msi inserts registry values when installing it. In Orca editor I am seeing like this,
After installing the msi, in the log file I am seeing like this,
MSI (s) (A8:B4) [16:27:28:674]: Executing op: ComponentRegister(ComponentId={45667B7F-9DC7-43B7-BE9E-3215ED1B1985},KeyPath=02:\SOFTWARE\myCompany\MySolution\Plugins\MyProduct\ProductCode,State=3,,Disk=1,SharedDllRefCount=0,BinaryType=0)
I want to do the reverse engineering of this mechanism, can any one help me to understand this? I want to recreate the same using WIX, so I just tried like below
<Component Id="RegistryEntries" Guid="*">
<RegistryKey Root="HKLM"
Key="Software\Microsoft\MyCompany"
Action="createAndRemoveOnUninstall">
<RegistryValue Type="string" Name="MyApp" Value="[INSTALLLOCATION]" KeyPath="yes"/>
<RegistryValue Type="string" Name="Configuration Files" Value="[INSTALLLOCATIONCONFIG]"/>
<RegistryValue Type="string" Name="Configuration Files1" Value="[INSTALLLOCATIONCONFIG1]"/>
</RegistryKey>
</Component>
When I built the msi and if edit it Orca, I am seeing like below,
What should I do to get the msi as shown in the previous image?
MSI expresses registry data in the Registry table. During the installation, the system determines which features and components are being installed therefore which registry adds, updates and deletes to perform. The actual work is carried out by the WriteRegistryValues and RemoveRegistryValues actions.
It is not a best practice to "execute a reg file" during an installation because it's out of process and MSI can't manage the changes. Instead use the WiX Heat tool to harvest the contents of the registry file into wix xml source for inclusion in your installer.
I've been working on a WIX .net project that needs to update a Microsoft registry entry to work correctly. While testing the logic, I found it difficult to debug the WIX components that updates the registry via the MSiexec.exe command line /log options. To verify the correct behaviour, I had to check the registry value manually. How do I force the WIX project to log the registry search and update logic from the following fragment in the MSI log output?
<util:RegistrySearch Id="Office2013RegistySearch"
Root="HKLM"
Key="SOFTWARE\Microsoft\Office\15.0\Access Connectivity Engine\Engines\Excel"
Value="TypeGuessRows"
Variable="Office2013GuessRowsx86Exist"
Win64="no"
Result="exists" />
<Component Id="Office2013GuessRowsx86RegComponent" Guid="CFE579F9-292A-4777-A671-B5E8E330B1A0" Win64="no">
<Condition>Office2013GuessRowsx86Exists</Condition>
<RegistryKey Root="HKLM"
Key="SOFTWARE\Microsoft\Office\15.0\Access Connectivity Engine\Engines\Excel" ForceDeleteOnUninstall="no">
<RegistryValue Type="integer" Name="TypeGuessRows" Value="0"/>
</RegistryKey>
</Component>
Try use full log
msiexec /i "dotnetproject.msi" /L*v "log.log"
or add <Property Id="MsiLogging" Value="voicewarmup"/> (for full log too)