2

我正在使用 Entity Framework 访问我的域模型,所有这些都实现了一个接口 (IPublishable),该接口指定属性以指示项目是否已发布。

从前端访问项目时,我总是想过滤掉未发布的项目。所以,每次我写一个查询时,我都在做类似的事情(以下 DbSets Objects1 和 Objects2 都实现了IPublishable

context.Objects1.Where( x => x.IsPublished ...).OrderBy( x => x.Id).ToList()
context.Objects2.Where( x => x.IsPublished ...).First()

理想的情况是,如果我可以将 commonWhere()子句注入到我的 Web 应用程序中的所有查询中,或者是否有一种方法可以编写可以包含在每个查询中的扩展方法。

我尝试为所有 linq 查询创建扩展方法

public static IEnumerable<T> FrontEnd<T>(this DbSet<T> dbSet) where T : class {
  return dbSet.Cast<IPublishable>().Where( x => x.IsPublished ...).Cast<T>();
}

并像这样使用...

context.Objects1.FrontEnd().Where( x => ...).OrderBy(...

但是我收到错误“LINQ to Entities 仅支持转换 EDM 基元或枚举类型”

我是 EF 的新手,所以任何信息都会有很大帮助。谢谢

4

2 回答 2

2

根据评论更新 - 这有效

public static IQueryable<T> FrontEnd<T>(this DbSet<T> dbSet)
    where T : class, IPublishable
{
    return dbSet.Where(x => x.IsPublished);
}

并且可以像这样使用:

context.Objects1.FrontEnd().Where( x => ...).OrderBy(...

您可以尝试以下任一选项:

public static IQueryable<dynamic> FrontEnd(this DbSet<dynamic> dbSet)
{
    return dbSet.Where(x => (x as IPublishable).IsPublished);
}

或者

public static IQueryable<T> FrontEnd<T>(this DbSet<T> dbSet)
    where T : class, IPublishable
{
    return dbSet.Where(x => x.IsPublished);
}

笔记:

第一个选项使用动态,因此第二个选项速度较慢,您必须在对 FrontEnd() 的调用中指定类型,例如

context.Objects1.FrontEnd<Objects1>().Where( x => ...).OrderBy(...
于 2013-07-05T14:14:08.670 回答
0

我认为 LINQ to Entities 不知道如何将强制转换运算符与 SQL 请求相匹配。作为一个建议,你可以尝试这样的事情:

IEnumerable<IPublishable> ReadPublishable(Expression<Func<DomainModelType, bool>> condition)

表达式充当谓词。因此,您将过滤您需要的 IPublishable 对象的谓词传递给 ReadPublishable 函数。我成功地尝试过,但只使用了简单的谓词,所以我不知道如果你使用“is”或“as”运算符是否有效。

于 2013-07-05T13:56:13.807 回答