从类型中获取DbSet

我正在尝试为MVC 6应用程序创建通用表查看器/编辑器。

我目前正在使用

Context.GetEntityTypes(); 

给我一个表格列表。

现在我需要获取特定类型的数据。 我目前的实施是:

 // On my context public IQueryable GetDbSetByType(string fullname) { Type targetType = Type.GetType(fullname); var model = GetType() .GetRuntimeProperties() .Where(o => o.PropertyType.IsGenericType && o.PropertyType.GetGenericTypeDefinition() == typeof(DbSet) && o.PropertyType.GenericTypeArguments.Contains(targetType)) .FirstOrDefault(); if (null != model) { return (IQueryable)model.GetValue(this); } return null; } 

在我的控制器中使用此代码

 [HttpGet("{requestedContext}/{requestedTable}/data")] public IActionResult GetTableData(string requestedContext, string requestedTable) { var data = Request.Query; var context = GetContext(requestedContext); if (context == null) { return new ErrorObjectResult("Invalid context specified"); } var entity = context.GetEntity(requestedTable); if (entity == null) { return new ErrorObjectResult("Invalid table specified"); } var set = context.GetDbSetByType(entity.ClrType.AssemblyQualifiedName); if (set == null) { return new ErrorObjectResult("Invalid table specified - DbSet could not be found"); } var start = Convert.ToInt32(data["start"].ToString()); var count = Convert.ToInt32(data["length"].ToString()); var search = data["search[value]"]; return new ObjectResult(set.Skip(start).Take(count)); } 

实际上,这将返回长度count和位置start 。 但是,我无法对IQueryable的特定属性执行查询。

问题是:

  1. 这似乎是一件微不足道的事情,所以我几乎可以肯定我错过了一些东西 – 这一定很容易做到。
  2. 如果不是1,那么我如何将我的object set转换回DbSet以便我可以执行查询? 如果我设置断点并检查我可以看到我的所有数据都坐在那里。

注意:这是EF7

附加信息:

  1. requestedTable是完全限定类型EG: .Models.Shared.Users

编辑(2016/5/5)

我最后只是用简单的SQL来做这件事 – 如果有人设法让这个工作,请告诉我!

通过使用generics方法并使用DbContext.Set()这将更简单。 您可以在运行时创建generics方法,如下所示:

 public IActionResult GetTableData(string requestedContext, string requestedTable) { var context = GetContext(requestedContext); if (context == null) { return new ErrorObjectResult("Invalid context specified"); } var entity = context.GetEntity(requestedTable); if (entity == null) { return new ErrorObjectResult("Invalid table specified"); } var boundMethod = s_getTableDataMethodInfo.MakeGenericMethod(entity.ClrType); return boundMethod.Invoke(this, new object[] { context }) as IActionResult; } private static readonly MethodInfo s_getTableDataMethodInfo = typeof(MyController).GetTypeInfo().GetDeclaredMethod("GetTableDataForEntity"); private IActionResult GetTableDataForEntity(DbContext context) where TEntity : class { var data = Request.Query; var start = Convert.ToInt32(data["start"].ToString()); var count = Convert.ToInt32(data["length"].ToString()); var search = data["search[value]"]; return new ObjectResult(context.Set().Skip(start).Take(count)); }