.net Core console app - exit signal has a hard stop time

1.7k Views Asked by At

I have a number of console apps that need to be built that all run "Jobs". They will be long running processes - never ended, and they continually do work.

With that in mind, I'm hoping to build a generic way to host these jobs. Each will be a console app, but rather than using something like Console.Read() to stop the console app finishing, I was going to use ManualResetEventSlim to block the process from finishing.

I've come up with a generic interface that each console app will implement and then it can be run in a common way. As follows:

public interface IHostedProcess
{
    void Starting();
    void Run();
    void Stopping();
}

This means I can implement a common way to host processes with a start, run and stop method:

public class ProcessHost
{
    ManualResetEventSlim keepAliveEvent = new ManualResetEventSlim();

    public void Run(IHostedProcess hostedProcess)
    {
        hostedProcess.Starting();

        AssemblyLoadContext.Default.Unloading += async ctx =>
        {
            hostedProcess.Stopping();
            keepAliveEvent.Set();
        };

        hostedProcess.Run();
        keepAliveEvent.Wait();
    }
}

And a simple example of a class that implements the IHostedProcess interface and can be run in the console app:

public class MyHostedProcess : IHostedProcess
{
    public void Starting()
    {
        Console.WriteLine("Job starting");

        // Call my custom code here...
    }

    public void Run()
    {
        Console.WriteLine("Job running");

        // Call my custom code here...
    }

    public void Stopping()
    {
        Console.WriteLine("Job stopping1");

        // Call my custom code here...
    }
}

Leaving my console app code looking like this:

public static void Main(string[] args)
{
    try
    {
        var mp = new MyHostedProcess();

        var ph = new ProcessHost();
        ph.Run(mp);
    }
    catch (Exception e)
    {
        Console.WriteLine("Something went wrong! " + e.Message);
        throw;
    }
}

Output is as follows:

enter image description here

Then click the "X" to stop the process:

enter image description here

And we see the "stopping" message:

enter image description here

So this all works fine up until a certain point - when I try to carry out a long running shut down process in MyHostedProcess.Stopping it seems to have a hard shut down and not wait until that process is finished. Example, modify the "Stopping" process to this:

public void Stopping()
{
    Console.WriteLine("Job stopping first");

    // Call my custom code here...
    Thread.Sleep(20000); // Doesnt seem to wait this long...
    Console.WriteLine("Job stopping second"); // Never see this!
}

I never see "Job stopping second" output as the console app seems to hard stop after 10 seconds or so. What am I doing wrong? How to I handle the shutdown more gracefully and guarantee I can complete any shutdown work before the app closes? Maybe there is a way to do this "out of the box" that I've missed?

Thanks for any pointers in advance!

0

There are 0 best solutions below