I have a sync method which I'm trying to convert to async. Basically, the code below projects the data into a DTO, and selects rows and orders them based on properties of the DTO. It also gets only a certain 'page' of the data.
return GetDbContext().Items
.ProjectToQueryable<DTO>(automapperConfigProvider)
.Where({expression based on DTO})
.OrderBy({expression based on DTO}).ThenBy(...)
.Skip(skip)
.Take(take)
.ToList();
I tried to convert it like this but it fails on the ToListAsync
.
var query = GetDbContext().Items
.ProjectToQueryable<DTO>(automapperConfigProvider)
.Where({expression based on DTO})
.OrderBy({expression based on DTO}).ThenBy(...)
.Skip(skip)
.Take(take);
return await query.ToListAsync();
The exception I get is:
The source IQueryable doesn't implement IDbAsyncEnumerable. Only sources that implement IDbAsyncEnumerable can be used for Entity Framework asynchronous operations. For more details see http://go.microsoft.com/fwlink/?LinkId=287068.
I'm using EntityFramework, so the link in the exception does not make sense to me.
Has anyone encountered this?
For anyone reading this question, here is how I converted my method to async:
return await GetDbContext().Items
.ProjectTo<DTO>(automapperConfigProvider)
.Where()
.Decompil‌​eAsync()
.OrderBy().ThenBy(...)
.Skip(skip).Take(take)
.ToListAsync();
Basically, I wanted the data server to do all the work in both projecting the dataset to DTO, and performing the query, and then picking only a subset of the result based on paging information.
I explored the UseAsDataSource()
option which Jimmy Bogard mentioned in his comment to Darcy's answer. But I was using an AutoMapper Profile
as a configuration provider for my mapping, and I could not quite figure out how to convert that to an IMapper
to pass to UseAsDataSource()
. So I ended up not doing as Jimmy suggested.
I'm sure there are other ways one could resolve this, but I did it through the code above.
This because ProjectToQueryable<T>
does not implement IDbAsyncEnumerable
.
However there is an async equivalent .ProjectToListAsync<T>();
in the AutoMapper.EF6 package.
Details here: https://github.com/AutoMapper/AutoMapper.EF6