Фактическая имитация FromSql, настроенная для DbQuery<TQuery>
, совпадает с DbSet<TEntity>
, поэтому ссылка OP важна (хотя это реализация всеобщего охвата, если вам нужно соответствовать по sql / параметрам FromSql, вы необходимо выполнить дополнительную настройку макета; предупреждение: быстро становится ужасно).
Вам необходимо смоделировать DbQuery<TQuery>
с запрашиваемой последовательностью, смоделировать провайдер запросов согласно OP-ссылке (расширенной с любым конкретным совпадением, которое вам нужно), а затем назначить макетированный объект DbQuery ОБА DbContext .Query<TQuery>()
метод и свойство DbContext DbQuery<TQuery>
.
С точки зрения насмешек над DbQuery, я использую его для создания:
public static Mock<DbQuery<TQuery>> CreateDbQueryMock<TQuery>(this DbQuery<TQuery> dbQuery, IEnumerable<TQuery> sequence) where TQuery : class {
var dbQueryMock = new Mock<DbQuery<TQuery>>();
var queryableSequence = sequence.AsQueryable();
dbQueryMock.As<IAsyncEnumerableAccessor<TQuery>>().Setup(m => m.AsyncEnumerable).Returns(queryableSequence.ToAsyncEnumerable);
dbQueryMock.As<IQueryable<TQuery>>().Setup(m => m.ElementType).Returns(queryableSequence.ElementType);
dbQueryMock.As<IQueryable<TQuery>>().Setup(m => m.Expression).Returns(queryableSequence.Expression);
dbQueryMock.As<IEnumerable>().Setup(m => m.GetEnumerator()).Returns(queryableSequence.GetEnumerator());
dbQueryMock.As<IEnumerable<TQuery>>().Setup(m => m.GetEnumerator()).Returns(queryableSequence.GetEnumerator());
dbQueryMock.As<IQueryable<TQuery>>().Setup(m => m.Provider).Returns(queryableSequence.Provider);
return dbQueryMock;
}
Затем, если мне нужно поддержать FromSql, я меняю провайдера на макет провайдера запросов (согласно OP, макет, настроенный для CreateQuery):
mock.As<IQueryable<TEntity>>().Setup(m => m.Provider).Returns(queryProviderMock.Object);
В итоге я завернул все это в библиотеку, если вы хотите сэкономить время: https://github.com/rgvlee/EntityFrameworkCore.DbContextBackedMock.Moq