Reputation: 6528
I am trying to understand which approach is the best to take when executing multiple database calls. I am having lots of screens that contain the same pattern:
Some screens have only one database call, and some screen have multiple database calls.
A typical database call
private Task<List<Product>> GetProductsAsync()
{
TaskCompletionSource<List<Product>> tcs = new TaskCompletionSource<List<Product>>();
TaskEx.Run(() => tcs.SetResult(Repository.GetAllProducts()));
return tcs.Task;
}
usage on screen with single call
// an event handler,can be marked as async void
public override async void OnActivated()
{
base.OnActivated();
ProductList = await GetProductsAsync();
}
usage on screen with multiple calls
// an event handler,can be marked as async void
public override async void OnActivated()
{
base.OnActivated();
ProductList = await GetProductsAsync();
CustomerList = await GetCustomersAsync();
OtherList = await GetOthersAsync();
}
As you can see, current implementation will spawn multiple threads from thread pool on screen with multiple calls. Is this a correct approach?
Another approach is to retrieve all data in one Task, but that would result in retrieving an array of lists in tcs.Result, which is kind of unclear what is being retrieved (from the point of code readability).
Do you thing that executing each database call in its own thread is correct approach, and if not what is your suggestion?
Upvotes: 1
Views: 2372
Reputation: 116636
When you're using async-await
all calls may run on different threads, but not necessarily at the same time (concurrently). In your case all calls are sequential, so you're not hitting the DB concurrently.
About having concurrent calls to the DB, it depends on the db itself. Most databases can handle multiple calls concurrently, especially on different tables. It could however increase contention if the concurrent operations use the same locks. It could go either way, but in most cases concurrent calls to a database is a good thing.
About GetProductsAsync
why are you using TaskCompletionSource instead of:
private Task<List<Product>> GetProductsAsync()
{
return Task.Run(() => Repository.GetAllProducts());
}
Upvotes: 1