Home > Installshield, Software Deployment > Installshield Release Configurations: Uninstall not removing shortcuts

Installshield Release Configurations: Uninstall not removing shortcuts

I’m disappointed in you Windows Installer.  You’ve caused me a lot of frustration and wasted time yesterday in my quest to realize ‘best practices’.  However, it looks like you’re not going to do the job you agreed on, so yet again, I’m forced to write a custom action to bend you to my will!

Windows Installer seems to be having trouble uninstalling shortcuts that share the same component GUID between products with differing Upgrade/Product/Package codes.

We’re using Installshield’s release configurations to create two installers of which have their own unique upgrade codes.  This allows us to install both of or products side by side (There’s a start menu entry for both products as well as unique entries within Add/Remove programs).

The problem shows itself when you install both products and then uninstall one of the products.  Some of the shortcuts to our pdf files are not removed for the product that was un-installed.

rwinkler has a decent diagram and explanation:

Start
->product A
–>shortcut component X
–>shortcut component Y

->product B
–>shortcut component X
–>shortcut component Z

If I remove e.g. product A the shortcut to product A remains after uninstallation due to shortcut to component X (component is not shared or permantent). After product A is removed the uninstallation of product B is ok. Still the shortcut of product A is pointing to nowhere.

Another somewhat related post can be found here.

Here’s the relevant entry in the log file:

MSI (s) (E4:AC) [13:20:13:832]: ‘NewShortcut161′ shortcut’s, BT_TOC’ component will not be removed, so that ‘NewShortcut161_F4C5FC901E5D4DBE9F7567B0672E6A5B.exe’ icon will not be removed.MSI (s)

It’s interesting to note that shortcuts extracting the shortcut icon from the .exe resource they are targeting, had no problem uninstalling.  Only shortcuts that make use of Windows Installer’s ICON table exhibit this behavior.

My thoughts:

I hope this is a bug in Windows Installer (tested in v4.5) and can be fixed.  It just seems to me that a component guid should only be associated with the product code and not be system wide.

Workarounds:

  • Embed your shortcut icon in the .exe or other resource. — As I mentioned above, shortcut uninstallation problems were specific to shortcuts making use of the ICON table.
  • Make use of Windows Installer’s RemoveFiles table and add an entry with the InstallMode set to 2.
  • Change the GUID for the component for EACH release. — Since Installshield provides no mechanism for using different component GUIDs for each release, this would be a maintenance nightmare.
  • Use a custom action to manually delete the orphaned shortcuts on uninstall:

I chose to use a custom action and I’ll discuss that in one momento.  Frankly, I’m a little embarrassed for WI because I have to do your job for you.  😉

I’ll give two examples of custom actions that can be scheduled during the Execute Sequence After RemoveShortcuts with a condition of REMOVE=”ALL”.  The first is targeting the specific shortcut using Installscript, with the added bonus of supporting language transforms:


/*------------------------------------------------------------------------*/
/*	Function: RemoveHelpLinks()									  	      */
/*	Descrip: removes the Help Start Menu link for the ProductLanguage	  */
/*------------------------------------------------------------------------*/
export prototype RemoveHelpLinks(HWND);
function RemoveHelpLinks(hMSI)
	STRING szFile, szLinkName, szText, szWhere;
	NUMBER nSize;
begin
	nSize = 256;
	MsiGetProperty(ISMSI_HANDLE,"BT_STARTMENU_NAME",szLinkName,nSize);
	LoadStringFromStringTable("IDS_HELP_TITLE",szText);
	szWhere = FOLDER_PROGRAMS^szLinkName;
	szFile = szWhere+"\\"+szText+".lnk";
	DeleteFile ( szFile );
end;

The second method is using vbscript to blow it all away.  Yes, as Heath Stewart points out, it’s not safe to use vbscript in the installer, but this is relatively low risk in my opinion.  If your’e that concerned, you can replace the DeleteFile() method above with Installscript’s DeleteDir()


' Deletes any start menu entries that didn't get uninstalled with the previous version
'SIGMA-741

Dim fso
Set fso = CreateObject("Scripting.FileSystemObject")

Dim WshShell
Set WshShell = CreateObject("wscript.Shell")

sCurVersion = Session.Property("ARPVERSION")

sStartMenu = WshShell.SpecialFolders("AllUsersStartMenu")
Set oStartMenuFolder = fso.GetFolder(sStartMenu & "\programs")

For Each folder In oStartMenuFolder.SubFolders
	If folder.Name = sCurVersion Then
		LogInfo("Deleting start menu folder: " & folder.Name & vbCr)
		folder.Delete(False)
	End If
Next

'log info into install log
Function LogInfo(msg)
	Dim rec

	Set rec = Session.Installer.CreateRecord(1)
	rec.StringData(0) = msg
	LogInfo = Session.Message(&H04000000, rec)

End Function

Finally, if someone has more to add to this conversation I would be happy to hear your comments.  In researching, I was only able to find others having this problem, but no ‘best practice’ type solutions were given.

Advertisements
  1. Ari
    April 1, 2011 at 4:03 am

    You’re actually breaking component rules when you do this. You have to remember shortcuts are files too, and their directory is the path in the Start menu. Since you’re installing the .lnk file in different directories for the two different products, it breaks component rules, because the component has to be installed and removed all at once. When you uninstall the first product, the component is still installed, so it doesn’t remove any shortcuts. When you uninstall the second product, it knows only about the shortcuts that were installed by the second product, because that’s what’s in its MSI.

    If you want to do this, where the component is shared between products, but each product gets its own different shortcut, you need to put the shortcut into its own component (which would have different component GUID between the two products). You also could simply have the shortcut shared between the products as well, for example:
    Start
    Company Name\
    Shortcut to component X
    Product A\
    Product A specific shortcut
    Product B\
    Product B specific shortcut

    But in the end, it’s not a bug in Windows installer, but a problem in how you organize your components.

    Also, your note about components that use the Icon table — I believe that is an artifact of your having shortcuts in components that don’t contain their target, because when you do this, Installshield will add an entry to the Icon table for you. So I’m guessing that when this happens in your MSIs, you’re ending up with shortcuts in their own component that do follow component rules, and the shortcuts do get uninstalled correctly.

    • Nick Skitch
      April 1, 2011 at 4:27 am

      Hi Ari, I appreciate the feedback, thanks for taking the time to share.

      I can understand that “shortcuts are files too” (I would say “keys”, as in a registry entry, file, shortcut) But, are my files not “files” as well? I would expect they would exhibit the same uninstall problem. My files, like my .lnk files, have a different locations.

      product A: ..\program files\companyName\Product A\file1
      product B: ..\program files\companyName\Product B\file1

      All my files are uninstalled just fine. It’s just the shortcuts that don’t uninstall. Following the description you gave, I would expect that uninstalling Product A, would leave all components that are common with Product B with a different location would NOT uninstall. That’s not what I’m seeing. Also, per your comment, my shortcuts have their own component (no files included in the component)

      As far as I know, we are passing ICE tests. (Maybe I need to be made aware of such validation tests)

      Also, if what you say truly is the case, Installshield has a real problem on their hands with how they use Release Configurations. Installshield would need to maintain a unique list of component GUIDS for each Release Configuration.

      Also, your note about components that use the Icon table — I believe that is an artifact of your having shortcuts in components that don’t contain their target, because when you do this, Installshield will add an entry to the Icon table for you. So I’m guessing that when this happens in your MSIs, you’re ending up with shortcuts in their own component that do follow component rules, and the shortcuts do get uninstalled correctly.

      Quite the opposite. While I agree that Installshield adds an entry to the ICON table if the target is not found in an .exe resource, the shortcuts DO NOT get uninstalled, as you say, if they ‘follow component rules’. That’s the problem.

      I like the comment, but it brings on more questions! haha Again, thank you for sharing.

      -Nick

  2. April 1, 2011 at 1:47 pm

    Ask your developers to embed the icon into the resource from this point forward. Or if you build the resource, add them in yourself (not sure about your leverage to change their code here). Remember KISS methodology 🙂

    -jp

  1. No trackbacks yet.

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s

%d bloggers like this: