Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Unable to catch an Exception from Task.Run

I am following this MSDN guide to handle the exceptions within a Task.

This is what I wrote:

var myTask = Task.Run(() =>
    {
        throw new Exception("test");
    });
try
{
    myTask.Wait();
}
catch (Exception e)
{
    return false;
}

I have set a breakpoint within the catch block, but at debug runtime, the code does not reach the breakpoint, and it's giving me:

Exception is unhandled by user code

I have no idea what is going on as I have followed very closely to the example from the MSDN guide. In fact, I copied the example to my project and it's still giving the same problem.

Is there any method I can handle the exception outside the Task? I need to return a boolean value based on the fact if the task throws any Exception or not.

Edit

To make it clearer for some of you, this is a more complete set of codes:

public bool ConnectToService()
{
    try
    {
        // Codes for ServiceHost etc etc, which I'm skipping
        // These codes are already commented out for this test, so they do nothing

        var myTask = Task.Run(() =>
            {
                // Supposed to connect to a WCF service, but just throwing a test exception now to simulate what happens when the service is not running
                throw new Exception("test");
            });
        try
        {
            myTask.Wait();
        }
        catch (Exception e)
        {
            return false;
        }

        return true;
    }

    catch (Exception)
    {
        return false;
    }
}

Caller:

public void DoSomething()
{
    try
    {
        // Other irrelevant stuff
        if (ConnectToService())
        {
            DoAnotherThing();
        }
    }
    catch (Exception)
    {
    }

}

I would also want to point out I have a solution for this, but it's puzzling why an example from MSDN isn't working for me. I would think that my own solution is not elegant, so I'm still looking for a more elegant solution.

Exception taskException = null;
var myTask = Task.Run(() =>
    {
        try
        {
            throw new Exception("test");
        }
        catch (Exception e)
        {
            taskException = e;
        }
    });
try
{
    myTask.Wait();
    if (taskException != null) throw taskException;
}
catch (Exception e)
{
    return false;
}
like image 657
Jai Avatar asked Oct 25 '16 03:10

Jai


2 Answers

When a task is run, any exceptions that it throws are retained and re-thrown when something waits for the task's result or for the task to complete

task.Wait()  Rethrows any exceptions

task.Result  Rethrows any exceptions

As well, your code works correctly

Just press f5 while catching an exception and you will see that will get your point

like image 100
Maxim Avatar answered Nov 15 '22 00:11

Maxim


According to MSDN Task.Run:

Queues the specified work to run on the thread pool and returns a Task object that represents that work.

So You throwing your exception on different thread than you trying to catch it. You should deal with exception on same thread.

Alternatively you can deal with unhandled exceptions in global AppDomain.UnhandledException event.

like image 28
ad1Dima Avatar answered Nov 15 '22 00:11

ad1Dima