Creating Installation Components



Creating Installation Components

When you deploy an application, you may want to take certain customized actions during the installation process. Some examples of customized actions include registering a Windows service with the Service Control Manager, registering a serviced component with COM+ Explorer, creating a database, installing event logs, installing performance counters, and so on.

The .NET Framework provides you with an Installer class to help you perform customized installation actions such as those mentioned above. The Installer class is defined in the System.Configuration.Install namespace.

Understanding the Installer Class

The System.Configuration.Install.Installer class works as a base class for all the custom installers in the .NET Framework. Some of the important members of the Installer class that I will discuss in this chapter are listed in Figure.

Figure Important members of the Installer Class

Member Name

Type

Description

Commit

Method

The code in the Commit() method is executed if the Install() method executes successfully.

Install

Method

Performs the specified actions during an application's installation.

Installers

Property

Collection of Installer objects that are needed for this Installer instance to successfully install a component.

Rollback

Method

If the Install() method fails for some reason, the code in the Rollback() method is called to undo any custom actions performed during the Install method.

Uninstall

Method

Performs the specified actions when a previously installed application is uninstalled.

You can derive a class from the Installer class and override the methods given in Figure to perform any custom actions.

If you want the derived installer class to execute when an assembly is installed, whether by using setup projects or by using the Installer Tool (installutil.exe), then you need to decorate the class with the RunInstaller attribute set to true:


[RunInstaller(true)]

The installer classes provide the infrastructure for making installation a transactional process. If an error is encountered during the Install() method, the Rollback() method tracks back all the changes and undoes them to leave the machine in the same clean state as it was before the process of installation started. The Rollback() method must know the order in which the installation steps were performed and exactly what changes were made so that it can undo those changes in the proper order.

Similarly, when an application is uninstalled, the Uninstall() method of the Installer class is called. The responsibility of the Uninstall() method is again to undo the changes done by the installation process so that the machine is left as clean as if the program had never been installed on it.

A question arises: How does the Install() method communicate its installation information to the Rollback() and Uninstall() methods? This question becomes even more interesting when you see that the Install() and Uninstall() methods are not called in the same process. Install() is called when the application is installed, whereas Uninstall() is called when the application is uninstalled. These two events might be separated by several days and computer restarts.

The Install() method communicates the installation state by persisting it in a file with the extension .InstallState. This file is placed in the installation directory of the application. The Installer class makes this file available to each of the Install(), Commit(), Rollback(), and Uninstall() methods by passing an IDictionary object to the contents of this file. Content in the .InstallState file is used by the Rollback() and Uninstall() methods to perform the required cleanup operation.

Predefined Installation Components

The .NET Framework provides five predefined installation components. Each of these installation components as listed in Figure is associated with a specific server component.

Predefined Installation Components

Installer Name

Description

EventLogInstaller

Enables you to install and configure a custom event log. This class belongs to the System.Diagnostics namespace.

MessageQueueInstaller

Enables you to install and configure a message queue. This class belongs to the System.Messaging namespace.

PerformanceCounterInstaller

Enables you to install and configure a custom performance counter. This class belongs to the System.Diagnostics namespace.

ServiceInstaller

Enables you to install a Windows service contained in a Windows service application. This class does work specific to the Windows service with which it is associated. The ServiceInstaller class belongs to the System.ServiceProcess namespace.

ServiceProcessInstaller

Enables you to install a Windows service application. This class does work common to all Windows services in an executable. The ServiceProcessInstaller class belongs to the System.ServiceProcess namespace.

Visual Studio .NET does not automatically add an installer for a server component, but it's easy to add one. For example, if you create a new Windows service project and access the Properties window for the project, you see a link as shown in Figure to add predefined installer classes for the Windows service in the project.

28. You can add a predefined installer for a server component by clicking on the Add Installer hyperlink in the Properties window.

graphics/10fig28.jpg

Clicking on the Add Installer link adds an instance of the predefined installation component to a class named ProjectInstaller in your project. You can add as many instances of the installation components to the ProjectInstaller class as you need. Each instance of a predefined installation component is set with properties that help in re-creating that object on the production machine. All the installation components are added to the Installers collection of the ProjectInstaller class. When you compile the project to build an EXE or a DLL file, the ProjectInstaller class is now part of the output assembly. The ProjectInstaller class has the RunInstaller attribute set to true, so at the time of installation, the ProjectInstaller class takes the responsibility of installing all the predefined installation components in an assembly.

You'll learn how to use predefined installation components to install a Windows service in a forthcoming section, "Deploying a Windows Service."

Custom Installation Components

You can also add a custom installer class to a project to perform custom actions during installation, such as compiling the code to a native image or creating a database on a target computer. These installer classes are compiled with your project and are then added to the deployment project as custom actions that are run at the end of the installation. You need to do the following to create a custom installer class:

  1. Inherit a class from the Installer class.

  2. Makes sure that the RunInstaller attribute is set to true in the derived class.

  3. Override the Install(), Commit(), Rollback(), and Uninstall() methods to perform any custom actions.

  4. In the setup project, use the Custom Actions Editor to invoke this derived class to do the required processing.

  5. If needed, pass arguments from the Custom Actions Editor to the custom Installer class by using the CustomActionData property.

You'll learn how to use the preceding steps to create a custom installer class in a forthcoming section, "Deploying a Serviced Component."

Deploying an Assembly Containing the Installation Components

You can deploy an assembly containing installation components in one of the following two ways:

  • By Using the Setup and Deployment Project Templates— To deploy an application that consists of installation components, you create a setup package by using the Setup and Deployment Project templates as you would do normally. But this time, you use the Custom Actions Editor to deploy the resources specified by the installer class. At the time of deployment, the setup program executes the ProjectInstaller class as a part of its custom installation action to create component resources. Step-by-Step 13.17 shows you how.

  • By Using the Installer Tool (installutil.exe)— You can also use the command line Installer Tool (installutil.exe) to install the assemblies that contain additional component resources. To install the resources contained in an assembly named Assembly1.dll, you can use the following form of the installutil.exe command:

    
    installutil.exe Assembly1.dll
    
    

    You can also install resources contained in multiple assemblies together, like

    
    installutil.exe Assembly1.dll Assembly2.dll Assembly3.dll
    
    

    If you instead want to launch the uninstaller for installation classes stored in an assembly, you use the /u or /uninstall option with the command, like

    
    installutil.exe /u Assembly1.dll
    
    

EXAM TIP

Installer Tool (installutil.exe) Performs Installations in a Transactional Manner If you are installing components from multiple assemblies by using the installutil.exe command, be aware that if any assembly fails to install, installutil.exe rolls back the installations of all other assemblies. However, the process of uninstallation is not transactional.


I already discussed using the Installer tool (installutil.exe) in Chapter 6, "Windows Services." In the following section, I'll use Visual Studio .NET setup and deployment projects to install the installation components.