Detect when MSI finish

  • Thread starter Alhambra Eidos Desarrollo
  • Start date
A

Alhambra Eidos Desarrollo

Hi all, misters,

I have Windows App .net 2.0 + vs 2005. My form launch several MSI's
(app1.msi, app2.msi).

I try launch MSI using Process.Start.

I need know when detect MSI executable has finished ? Perphaps, I launch MSI
and wait it until finish.

Any suggestions or sample code source ??

Thanks in advance, greetings.
 
C

Ciaran O''Donnell

I think when you launch the MSI you need to launch MSEExec which is the
program that actually runs the install. You should then be able to pass
parameters as to which MSI and then WaitForExit on the process object.
 
A

Alhambra Eidos Desarrollo

Thanks all,

One potential problem is that this version of WaitForExit() will wait
forever if the process never finishes, for example if it hangs.

Any suggestions for resolves this problem ?? Any good sample code about it ?

Thanks.
 
A

Alhambra Eidos Desarrollo

need know when detect MSI executable has finished ? Perphaps, I launch MSI
and wait it until finish.


Can do this:



Dim process as Process = Process.Start( "C:\.........blah.exe" )
process.WaitForExit()




In forums, Bart Read says (in C# forums):

One potential problem is that this version of WaitForExit() will wait
forever if the process never finishes, for example if it hangs. Obviously,
you'd hope that wouldn't happen with the MSIs you're running, but just in
case, it might be worth taking into account. Also I haven't at all considered
what might happen if the MSI exits with a failure code (non-zero exit code).
Process also implements IDisposable, so once you're done with the object you
should call Dispose().

This sample takes these things into account:

using ( Process process = Process.Start( "C:\.....blah.exe" ) )
{
process.WaitForExit( 30000 ); // Give process 30 seconds to execute (for
example)
// - this is probably far too short for
running your MSIs
if ( process.HasExited )
{
if ( process.ExitCode == 0 ) // Success
{
HandleSuccess();
}
else
{
HandleFailure();
}
}
else
{
try
{
// You might also want to kill the process, although with an MSI
this is not a good idea because you're almost
// certainly going to leave your system in an inconsistent
state. Anyway, if you do want to kill the process:
process.Kill();

// Maybe display timeout message or throw exception indicating
timeout.
}
catch ( InvalidOperationException ) // Thrown by Kill(); indicates
process has already exited
{
// Same code as above reproduced here for illustrative purposes
only (should be separate method).
if ( process.ExitCode == 0 ) // Success
{
HandleSuccess();
}
else
{
HandleFailure();
}
}
catch ( Win32Exception w32e ) // Thrown by Kill() if, e.g., process
can't be terminated
{
// Do exception handling: e.g. display error to user, or wrap
and rethrow
}
}
}

That's probably enough to be going on with, however if you're distributing
your application to a very large number of peope and you don't really like,
or trust using (like me), then you might want to do the following, which is a
little more foolproof (some people don't like this idiom though):

Process process = null;
try
{
process = Process.Start( "C:\.....blah.exe" );
process.WaitForExit( 30000 ); // Give process 30 seconds to execute (for
example)
// - this is probably far too short for
running your MSIs
if ( process.HasExited )
{
if ( process.ExitCode == 0 ) // Success
{
HandleSuccess();
}
else
{
HandleFailure();
}
}
else
{
try
{
// You might also want to kill the process, although with an MSI
this is not a good idea because you're almost
// certainly going to leave your system in an inconsistent
state. Anyway, if you do want to kill the process:
process.Kill();

// Maybe display timeout message or throw exception indicating
timeout.
}
catch ( InvalidOperationException ) // Thrown by Kill(); indicates
process has already exited
{
// Same code as above reproduced here for illustrative purposes
only (should be separate method).
if ( process.ExitCode == 0 ) // Success
{
HandleSuccess();
}
else
{
HandleFailure();
}
}
catch ( Win32Exception w32e ) // Thrown by Kill() if, e.g., process
can't be terminated
{
// Do exception handling: e.g. display error to user, or wrap
and rethrow
}
}

process.Dispose(); // If this throws an exception you'll know about it;
whereas if another exception is thrown
// elsewhere this idiom means that an exception
thrown by Dispose() won't mask it.
process = null;
}
finally
{
if ( process != null )
{
try { process.Dispose(); } catch ( Exception ) {}
}
}

Any good solution about it ? I think is better use another Thread, but for
me the problem is how kill the process if MSI hangs or fails ??



Please, MVPs or Microsoft developers, which is the better solution or
solutions for this issue ???



I want to do good practice !!!


Any suggestions or good sample code source about it??

Thanks in advance, greetings
 
F

Family Tree Mike

Well, I said handle the Process.Exited event. If it doesn't occur in 24
hours, you could kill it.

"Alhambra Eidos Desarrollo"
 
C

Ciaran O''Donnell

WaitForExit has an overload which takes a number of milliseconds to return
after if the process hasnt exited and returns a bool to say whether it
finished in time or not.

e.g

bool didItFinishBeforeTimeout = process.WaitForExit(1000);
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Top