关于实体框架,有很长时间以来一直困扰着我.
去年我为使用EF的客户编写了一个大型应用程序.在开发过程中,一切都很顺利.
我们八月发货了.但几周后我开始在生产服务器上看到奇怪的内存泄漏.运行几天后,我的ASP.NET MVC 4进程占用了机器的所有资源(8 GB).这不好.我在网上搜索,看到你应该在一个using()块中包围所有的EF查询和操作,以便可以处理上下文.
在一天中,我重构了我要使用的所有代码using(),这解决了我的问题,因为这个过程依赖于稳定的内存使用.
我首先没有围绕我的查询的原因是我从Visualofite中包含的Microsofts自己的脚手架开始了我的第一个控制器和存储库,这些没有使用包围它的查询,而是它具有DbContext作为实例变量的控制器本身.
首先:如果处理上下文非常重要(某些事情不会很奇怪,dbconnection需要关闭等等),微软可能应该在他们的所有示例中都有这个!
现在,我已开始与我在我的后脑勺所有学习收获一个新的大项目工作,我一直在试用的.NET 4.5和EF 6的新功能async和await.EF 6.0具有所有这些异步方法(例如SaveChangesAsync,ToListAsync等等).
public Task<tblLanguage> Post(tblLanguage language)
{
using (var langRepo = new TblLanguageRepository(new Entities()))
{
return langRepo.Add(RequestOrganizationTypeEnum, language);
}
}
Run Code Online (Sandbox Code Playgroud)
在课堂上TblLanguageRepo:
public async Task<tblLanguage> Add(OrganizationTypeEnum requestOrganizationTypeEnum, tblLanguage language)
{
...
await Context.SaveChangesAsync();
return langaugeDb;
}
Run Code Online (Sandbox Code Playgroud)
但是,当我现在在一个using()块中包含我的语句时,我得到异常DbContext was disposed,在查询能够返回之前.这是预期的行为.查询运行async,using块在查询之前完成.但是在使用ef 6的async和await函数时,我应该如何以适当的方式处理我的上下文?
请指出我正确的方向.
是using()需要EF 6?为什么微软自己的例子从未有过这样的特色?如何正确使用异步功能并处理上下文?
我对ASP.NET MVC应用程序中实体框架上下文的期望生命周期有一些疑问.是不是最好尽可能在最短的时间内保持上下文?
请考虑以下控制器操作:
public ActionResult Index()
{
IEnumerable<MyTable> model;
using (var context = new MyEntities())
{
model = context.MyTable;
}
return View(model);
}
Run Code Online (Sandbox Code Playgroud)
上面的代码将不起作用,因为在视图呈现页面时,实体框架上下文已超出范围.其他人如何构建上面的代码?
坦率地说,我是C#和Asp.net MVC的新手.我也不知道asp.net Web应用程序如何在IIS和ASP.NET框架后面实际工作.
我对我必须在我的asp.net mvc应用程序中声明DbContext(或从DbContext派生的任何类)字段的决定感到困惑.
我有两个选择:
global.asax,以便所有控制器都可以使用它.你能解释哪一个是正确的吗?确实需要更详细的解释.
我在通过 DbContext.Add(...) 方法添加新实体时遇到问题。在 DbContext.SaveChanges() 上,我收到 DbUpdateConcurrencyException。我正在尝试插入数据库。我是该应用程序的唯一开发人员,运行本地主机,并且数据库表是原始的。没有用户。只有我。
尽管它很相似,但这并没有帮助:
Entity Framework 6 DbUpdateConcurrencyException When Adding New Rows To Database
我每个请求使用一个 DbContext。像这样:
ASP.NET MVC 中每个请求一个 DbContext(没有 IOC 容器)
我正在注销实体框架生成的sql语句,如下所示:
https ://stackoverflow.com/a/20751723/2088914
这是模型(代码优先,带有迁移)。当我发帖时,我只提供同事、角色、分配者和已删除标志。行 id 自动设置为 0,因为我没有从客户端提供它,并且日期也是默认值,然后我在服务器上填充它 - 所有预期的内容:
public class Permission {
[Column("row_id")]
[DatabaseGenerated(DatabaseGeneratedOption.Identity)]
public int RowId { get; set; }
[Key]
[StringLength(10)]
[Column("associate_nt_id", Order = 0)]
[Required]
public string AssociateNtId { get; set; }
[Key]
[Column("role_name", Order = 1)]
[StringLength(50)]
[Required]
public string RoleName { get; set; }
[Key]
[Column("eff_ts", Order = 2)] …Run Code Online (Sandbox Code Playgroud) c# sql-server entity-framework asp.net-web-api entity-framework-6
我有一个处理所有数据库操作的类.我已经读过,最好将多个DataContext实例用于不同的读/写/更新/删除操作,而不是一个长时间使用的DataContext实例.
这意味着在数据库上执行读/写/更新/删除的每个函数都需要这样做:
public int GetSomeID(string name)
{
using (XXDataContext context = new XXDataContext(connStr))
{
...
}
}
public int GetAnotherID(string name)
{
using (XXDataContext context = new XXDataContext(connStr))
{
...
}
}
public void WriteSomething(string text)
{
using (XXDataContext context = new XXDataContext(connStr))
{
...
}
}
Run Code Online (Sandbox Code Playgroud)
反对只在构造函数中使用this()并将上下文作为私有成员变量可用于每个函数调用.
保持每个函数调用创建一个新的DataContext的功能,是否可以使用()在其他地方移动它,所以不是每个函数都必须包含这一行?
我有一个类包含几个为我的MVC应用程序定制的常用方法,我在几个地方使用.这是一些例子:
private MyEntities db = new MyEntities();
public List<SelectListItem> GetLocationList()
{
var query =
db.v_LocationsAlphabetical.OrderByDescending(x => x.Category).ThenBy(x => x.LocationName).ToList()
.Select(x => new SelectListItem
{
Value = x.LocationID.ToString(),
Text = x.LocationName
});
return (query).ToList();
}
public IEnumerable<SelectListItem> GetStates()
{
var query = db.States.Select(x => new SelectListItem
{
Value = x.Abbr,
Text = x.Name
});
return(query);
}
public List<Person> GetPeople()
{
var query = db.Person.OrderBy(m => m.LastName).ThenBy(m => m.FirstName).ToList();
return (query);
}
Run Code Online (Sandbox Code Playgroud)
这些方法中的每一个都调用数据库来获取数据,我想知道是否需要为每个方法添加一个dispose.如果没有,为什么?谢谢.
我试图找出导致此错误的原因,我列出了我的代码中的一些相关区域,希望有助于解决我的问题.
配方实体的成员集合如下所示:
public virtual IList<Member> Members { get; set; }
Run Code Online (Sandbox Code Playgroud)
这是成员实体上的Recipes集合:
public virtual IList<Recipe> Recipes { get; set; }
Run Code Online (Sandbox Code Playgroud)
我在创建DbContext时执行以下操作,以便在单独的表中建立多对多关系
protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
// have to specify these mappings using the EF Fluent API otherwise I end up with
// the foreign key fields being placed inside the Recipe and Member tables, which wouldn't
// give a many-to-many relationship
modelBuilder.Entity<Recipe>()
.HasMany(r => r.Members)
.WithMany(m => m.Recipes)
.Map(x => {
x.ToTable("Cookbooks"); // using a mapping table for a …Run Code Online (Sandbox Code Playgroud) 我在这里找到stackoverflow上的帖子之后设置了我的DbContext模型.
这是目前的设置......
public static class DbContext
{
public static MyDbContext Db
{
get
{
if (!HttpContext.Current.Items.Contains("_db"))
{
HttpContext.Current.Items.Add("_db", new MyDbContext());
}
return HttpContext.Current.Items["_db"] as MyDbContext;
}
}
}
Run Code Online (Sandbox Code Playgroud)
上下文在end_request上的global.asax中处理,如下所示:
void Application_EndRequest(object sender, EventArgs e)
{
var db = (MyDbContext)HttpContext.Current.Items["_db"];
if (db != null)
db.Dispose();
}
Run Code Online (Sandbox Code Playgroud)
这样,在我的系统中,我可以访问Db DbContext.Db.xxxx
到目前为止,一切都在本地运行,但是,我还没有在生产环境中测试过多个用户.
我的顾虑...
我在stackoverflow上阅读了这篇文章,现在让我担心多个用户访问静态上下文可能存在数据问题.这应该关注我还是我的安装方式好吗?
c# ×8
asp.net-mvc ×2
using ×2
.net ×1
asp.net ×1
asynchronous ×1
database ×1
datacontext ×1
dbcontext ×1
idisposable ×1
sql ×1
sql-server ×1