将OData Queryable与存储库一起使用?

时间:2013-03-08 13:33:44

标签: c# asp.net-web-api odata iqueryable

我有这个存储库方法:

public IQueryable<TModel> GetAll()
{
    using (var context = new DatabaseContext())
    {
        return context.Set<TModel>().AsQueryable();
    }
}

其中TModel是艺术家模型..无论如何

然后我在我的控制器中执行此操作:

// GET api/artist
[Queryable]
public IQueryable<ArtistModel> Get()
{
    return _repo.GetAll().AsQueryable();
}

现在..如果我要更改存储库方法以返回List并为我的结果添加.ToList ..那么这将很有效。但是无论什么OData查询进来..我仍然会首先执行“获取所有查询”..将它们转换为列表然后我将对该列表执行我的OData查询..

这似乎是完全错误的..我想要做的是确保OData查询在我尝试从数据库中获取数据的同时执行..所以我只得到非常具体的结果匹配查询..而不是后来被查询的大量数据..

现在我遇到了DbContext在使用之外被处理掉的问题..但我仍然需要关闭DbContext以及某些地方,有些如何...

有什么想法吗?

2 个答案:

答案 0 :(得分:2)

您可以通过多种方式启用可查询的Web API,

  1. [Queryable]属性放在您的操作上。您的操作可以返回以下内容之一 - IEnumerable<T>IQueryable<T>HttpResponseMessage,内容为ObjectContent<IQueryable<T>>ObjectContent<IEnumerable<T>>Task<IQueryable<T>>,{{ 1}},Task<IEnumerable<T>>具有与之前相同的限制。

  2. 通过Task<HttpResponseMessage>启用全局查询。这样可以查询返回configuration.EnableQuerySupport()

  3. 的所有方法
  4. 按照here使用IQueryable<T>并自行手动应用查询。

  5. 关于ODataQueryOptions<T>处理问题,我们以一种懒惰的方式很晚地评估查询 - 当格式化程序将响应写入流时。因此,您不应在行动中处置DbContext。而是将它与控制器一起配置,即覆盖控制器的DbContext方法并将其丢弃。 Web API负责控制器的生命周期,并在请求完成处理后处理控制器。此外,您也可以使用Dispose方法,在请求处理完毕后处理任何资源。

答案 1 :(得分:1)

web api的可查询扩展的最新版本有点令人困惑,因为它与以前的版本有很大的不同。在新版本中,您需要显式启用可查询支持或使用新的查询选项类。 See this

编辑:有些代码,因为我现在在办公桌

public IQueryable<TModel> GetAll(ODataQueryOptions opts)
    {
        var db = _repo.GetAll();
        return (IQueryable<TModel>) opts.ApplyTo(db);
    }