1

I have a basic setup project in Visual Studio 2010, and I am struggling with setting up custom actions. I have 3 Installer classes in a separate assembly.

The 3 classes do the following things:

  • Check for parameters to allow for unattended installation with licensing information (overrides the Install method)
  • Remove a previous installation of the software (installed with an NSIS installer, uses the BeforeInstall event)
  • Stop the program if it is running, using the BeforeInstall event

The problem is the last one, it seems the BeforeInstall event is never triggered. I've tried to make it create a file on disk, and displaying a MessageBox. It never triggers.

The "Primary output from SetupActions" has been added to the "Install" section in the Custom Actions editor. My Installer classes all have [RunInstaller(true)].

Code that does not work:

[RunInstaller(true)]
public partial class InstallerStopProgram : System.Configuration.Install.Installer
{
    public InstallerStopProgram()
    {
        InitializeComponent();
    }

    private void InstallerStopProgram_BeforeInstall(object sender, InstallEventArgs e)
    {
        MessageBox.Show("This is never displayed during the install");
    }
}
Vegard Larsen
  • 12,827
  • 14
  • 59
  • 102

3 Answers3

2

Problem with this approach is that you want to run something before installation and that something resides in the dll/exe that gets onto the target machine only as a part of installation. So unless installation is done, you will not have your BeforeInstall code on the disk to run (and then you can make it run only as post install).

To my knowledge, what you want to achieve is not possible VS 2010 setup project. Perhaps, you should use Wix (or NSIS)!

VinayC
  • 47,395
  • 5
  • 59
  • 72
  • Unfortunately my project has issues with NSIS that are to cumbersome to explain here. Is there any way to run any sort of code using a VS Setup that runs before the installation has started? – Vegard Larsen Jan 14 '11 at 10:52
  • I am not expert at this but this needs to be done at bootstrapping stage - perhaps by custom pre-requisite: see http://jcrawfor74.wordpress.com/2008/02/27/bootstrap-manifest-generator-how-to-custom-pre-requisites/ for how to have custom pre-requisite. – VinayC Jan 14 '11 at 12:25
  • @VinayC How to uninstall an application during the installation of my msi file and remove unwanted folder.Can you please look into this http://stackoverflow.com/questions/26688869/do-some-action-before-application-install-in-c-sharp – user2681579 Nov 11 '14 at 06:52
0

You don't need to migrate to WiX, but you can do it if you use WiX at some extent.

First you'll have to transfer you C# code to a WiX Custom Action.

Then you'll embed this Custom Action into the MSI using the following JScript code:

var installer = WScript.CreateObject("WindowsInstaller.Installer");
var filespec = WScript.Arguments(0);
var msiOpenDatabaseModeTransact = 1;
var msiViewModifyAssign         = 3;
var database = installer.OpenDatabase(filespec, msiOpenDatabaseModeTransact);

var sqlQuery = "SELECT `Name`,`Data` FROM Binary";
var view = database.OpenView(sqlQuery);
var record = installer.CreateRecord(2);
record.StringData(1) = "myAction";
view.Execute(record);
var binaryPath = WScript.ScriptFullName.replace(WScript.ScriptName, "SetupAction.CA.dll");
record.SetStream(2, binaryPath);
view.Modify(msiViewModifyAssign, record);
Execute("INSERT INTO `CustomAction` (`Action`, `Type`, `Source`, `Target`)  VALUES ('myActionId', 1, 'myAction', 'MySimpleAction')");
Execute("INSERT INTO `InstallUISequence` (`Action`, `Sequence`)  VALUES ('myActionId', 26)");
database.Commit();

function Execute(sql) {
    view = database.OpenView(sql);
    view.Execute();
    view.Close();
}
Jader Dias
  • 162
  • 1
  • 9
0

VinacC is correct above. To do this correctly, this needs to be done prior to File Costing. A bootstrapper would be a good place to do it. You want to get the machine cleaned of the old NSIS version before Windows Installer starts looking at what needs to be done to get to the latest version.

Christopher Painter
  • 54,556
  • 6
  • 63
  • 100