6
votes

I have started using ConfigureAwait(false) with all the async sql objects.

connection.OpenAsync().ConfigureAwait(false);
cmd.ExecuteNonQueryAsync().ConfigureAwait(false);

But my concern is, Will there be any implications with this approach?.

As this will run on a thread pool which is a separate thread from which it got originated i am not sure about the consequences if we dont run it on a single thread.

Our application is wcf service which will process the 1000's of records parallel.

If some one helps to identity the business scenarios where it could be problem that would be helpful.

Thanks

1
If you don't know how or why to use it, why are you sticking it on everything? - user1228
thinking aloud here (I've never investigated), but I suspect that ambient transactions (aka TransactionScope) would be pretty scuppered if you used ConfigureAwat(false) - but: I haven't actually checked whether they work with aysnc without ConfigureAwait(false) :) - Marc Gravell
I have chosen it because it will give the performance boost on multi core environment - Chandra Mohan
@MarcGravell there is special constructor (starting for .NET 4.5.1) which allows you to tell TransactionScope if it should flow through async continuations or not. But if you don't use this constructor (most cases as of now I think) - it won't flow. I've answered a question couple of days ago when OP used TransactionScope with await without this constructor, which led to surprising results... - Evk
i actually least bother about c# TransactionScope object which i am not using. I am following all stored procedure calls which contains SQL Transaction's with in Store Proc's - Chandra Mohan

1 Answers

8
votes

As a general rule, as long as a region of async operations are self contained and independent, you should be fine using ConfigureAwait(false) - and indeed doing so can be important to reduce overheads and bottlenecks. The library code usually doesn't need to know about the call-context. However, consuming code (such as winforms, MVC, etc) usually needs to get back to the appropriate context, so should not use ConfigureAwait(false). For example:

async Task SomeUXCodeAsync() {
    var data = await GetSomeDataAsync(); // note no ConfigureAwait(false)
    // not shown: use "data"
}
async Task<Foo> GetSomeDataAsync() {
    using(var conn = CreateConnection()) {
        await conn.OpenAsync().ConfigureAwait(false);
        ...
        int result = await cmd.ExecuteNonQueryAsync().ConfigureAwait(false);
        ...
        return ...
    }
}

The above scenario is pretty typical and common, but it is more complex than that - the TransactionScope example from the comments touches on examples where the data related code might need to know about the call context, for example. But nuance aside: as long as the consuming code remembers not to ignore the call context, you'll usually end up back at the right place. Sorry this is a little vague and woolly, but : sadly that's kinda the case generally for the call-context.