Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Question about FireAndForget #4

Open
fretje opened this issue May 20, 2016 · 2 comments
Open

Question about FireAndForget #4

fretje opened this issue May 20, 2016 · 2 comments

Comments

@fretje
Copy link

fretje commented May 20, 2016

Hi,

I stumbled upon your code, and found that I have a very similar way of doing a FireAndForget as you have in this library. Only, I don't have the body of the Task.Run delegate wrapped into another invokation. So like this:

    public static void FireAndForget(
        Func<Task> task,
        Action<Exception> handle = null)
    {
        Task.Run(async () =>
        {
            try
            {
                await task().ConfigureAwait(false);
            }
            catch (Exception e)
            {
                if (null != handle)
                {
                    handle(e);
                }
            }
        });
    }

I have the above code running fine in production, but am always looking to "harden" it anyways, so I was just wandering: why do you do that? What is the reason of that extra level of invokation?

Also: about the ConfigureAwait... I see that you don't use that. If my understanding about it is right, applying ConfigureAwait(false) means that the synchronisation context doesn't get captured for continuation, which is good here, as we don't need to continue anywhere anyway.

I read somewhere that in library or framework code (I guess this project falls under that category?), ConfigureAwait (false) should almost always be used, as it's more expensive to capture than not to capture, and if you don't need it anyway...

I could be terribly wrong though, as I'm still in the process of wrapping my brain around this whole async/await stuff... Please enlighten me if that's the case ;-)

@tejacques
Copy link
Owner

Hi @fretje,

I'm actually not certain anymore just looking at the code, but I believe it was done to get around a limitation with Task.Run's exception handling. I do recall starting with just an async lambda, but encountering issues, however It's possible that it is not necessary. The ConfigureAwait(false) is a nice addition.

If you'd like to experiment with it and discover anything I'd be interested to know, but I believe you have the right idea here.

@Maly-Lemire
Copy link

Hi,

You should be aware that only the framework 4.6 keep the culture with ConfigureAwait. See http://stackoverflow.com/questions/32097824/configureawaittrue-is-working-only-on-4-6

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants