Async methods in the generic class Repository.Pattern.Ef6.Repository<TEntity>

Oct 6, 2015 at 1:21 PM

The generic class Repository.Pattern.Ef6.Repository<TEntity> has the following asynchronous functions:
  • FindAsync
  • DeleteAsync
  • SelectAsync
Is there a need for a async insert method?
  • InsertAsync
Or could the same be achieved by using the existing insert functions:
  • Insert
  • InsertRange
  • InsertGraphRange
  • InsertOrUpdateGraph
Togheter with UoW class Repository.Pattern.Ef6.UnitOfWork.SaveChangesAsync
Oct 14, 2015 at 6:53 AM
Hi Marva00,

I've just been looking at the Async calls in SelectAsync, after reading

I would say that FindAsync is a 'true async' method, as it calls the EF async FindAsync. And as DeleteAsync calls FindAsync, the same logic applies.

InerstAsync, isn't necessary. Insert is 'only' updating internal state of objects. The SaveChangesAsync is where the real Async benefit comes into play.

BUT, back to my SelectAsync point.

I'd comment that (@lelong37 do you agree?) that SelectAsync's use of Task.Run is 'fake async' and could (according to Stephen Cleary's article) harm performance on ASP.NET implementations if you use it.


The pertienent quote is :

"There are (at least) four efficiency problems introduced as soon as you use await with Task.Run in ASP.NET:
•Extra (unnecessary) thread switching to the Task.Run thread pool thread. Similarly, when that thread finishes the request, it has to enter the request context (which is not an actual thread switch but does have overhead).
•Extra (unnecessary) garbage is created. Asynchronous programming is a tradeoff: you get increased responsiveness at the expense of higher memory usage. In this case, you end up creating more garbage for the asynchronous operations that is totally unnecessary.
•The ASP.NET thread pool heuristics are thrown off by Task.Run “unexpectedly” borrowing a thread pool thread. I don’t have a lot of experience here, but my gut instinct tells me that the heuristics should recover well if the unexpected task is really short and would not handle it as elegantly if the unexpected task lasts more than two seconds.
•ASP.NET is not able to terminate the request early, i.e., if the client disconnects or the request times out. In the synchronous case, ASP.NET knew the request thread and could abort it. In the asynchronous case, ASP.NET is not aware that the secondary thread pool thread is “for” that request. It is possible to fix this by using cancellation tokens, but that’s outside the scope of this blog post.