我使用IDocumentClient
检索和更新DocumentDB集合中的项目。
检索符合条件的文档列表的代码如下所示:
public static async Task<FeedResponse<T>> GetDocuments<T>(
this IDocumentClient client,
string collection,
Expression<Func<T, bool>> filter)
{
IDocumentQuery<T> query = client.CreateDocumentQuery<T>(GetCollectionUri(collection)).Where(filter)
.AsDocumentQuery();
return await query.ExecuteNextAsync<T>().ConfigureAwait(false);
}
为了针对模拟项列表对上面的代码进行单元测试,我创建了一个模拟类:
public class MockIOrderedQueryable<T> : List<T>, IOrderedQueryable<T>, IDocumentQuery<T>
{
public Expression Expression
{
get
{
var content = this.ToList();
return content.AsQueryable().Expression;
}
}
public IQueryProvider Provider => new MyProvider<T>(this.ToList());
public Task<FeedResponse<TResult>> ExecuteNextAsync<TResult>(CancellationToken token = new CancellationToken())
{
var tmp = new FeedResponse<TResult>((IEnumerable<TResult>)this);
return Task.FromResult(tmp);
}
}
Where
过滤器是IQueryable<T>
上的扩展方法,因此我需要一个如下所示的实现:
public class MyQueryable<T> : IQueryable<T>, IDocumentQuery<T>
{
private readonly List<T> _list;
public MyQueryable(List<T> list)
{
_list = list;
}
public Task<FeedResponse<TResult>> ExecuteNextAsync<TResult>(CancellationToken token = new CancellationToken())
{
var tmp = new FeedResponse<TResult>(_list as List<TResult>);
return Task.FromResult(tmp);
}
}
还有IQueryProvider
的实现,它通过IQueryable
将CreateQuery
实例返回到我原来的模拟类:
public class MyProvider<T> : IQueryProvider
{
private readonly List<T> _list;
public MyProvider(List<T> list)
{
_list = list;
}
public IQueryable<TElement> CreateQuery<TElement>(Expression expression)
{
return new MyQueryable<TElement>(_list as List<TElement>);
}
}
为简洁起见,我省略了抛出NotImplementedException
的方法的代码以及未使用的字段的代码。
这一切看起来都不错,但有一点我无法做到:将Expression
中CreateQuery
传递的真实过滤应用于_list
MyProvider
成员{1}}。我试着调用Invoke
并检索参数,但它没有用。 MockIOrderedQueryable
中返回的表达式可能不是好的(.AsQueryable
列表中的表达式)。我想找到一个lambda Expression<Func<T, bool>>
并在列表中调用它。
任何帮助表示感谢。