在ASP.NET Core中使用DI的控制器构造函数上分配持久对象

时间:2018-04-24 07:34:36

标签: angular asp.net-core-mvc object-persistence

所以也许有几种方法来表达这个问题,但这很清楚。我有一个与我的web项目(基于Angular2和Asp.Net Core构建)分开的常规类库,并且必须在整个Web应用程序生命周期中保持其“核心对象”状态。我的问题是这样的对象类访问数据库,我不得不使用DI来从Angular2应用程序访问正确的DBContext。

private Building building = null;
public AddDoorController(AutoListDbContext context) {
    building = new Building(context);
}

但是,我必须坚持building状态,但是从目前为止我可以收集的内容,服务器端类来促进状态持久性(例如HttpContextTempData等)在构造函数的范围内不可用。我希望保留这个数据服务器端,当然必须有办法解决它,不存在吗?

1 个答案:

答案 0 :(得分:1)

EF上下文是(并且应该是)请求范围的。这意味着您只能通过请求/瞬态范围将它们注入其他内容。由于上下文是在应用程序的生命周期中多次创建和销毁的,因此您无法将其注入到单一范围的对象中,该对象只会被创建一次。

如果你有一个绝对必须有权访问上下文的单例,你可以注入IServiceCollection并使用服务定位器模式,即:

var context = services.GetService<MyContext>();

但是,每次访问上下文时都需要执行此操作。换句话说,不要将其保存到实例变量或字段,因为它将在某个时刻处置。一般来说,应该避免服务定位器模式,因为它可能会导致各种各样的问题,但有时你无法做出选择。

尽管如此,你很可能实际上需要一个单身人士。像HttpContext这样的东西不再是ASP.NET Core中的静态。如果您需要访问HttpContext,则只需注入IHttpContextAccessor即可。顾名思义,这可以让您访问当前的HttpContext实例。

此外,需要在请求之间保持持久化的状态应该持久化,即实际保存到某种持久性存储,如SQL Server或Redis。在这方面,您可以设置distributed cache,然后使用它来保持对象状态,因为分布式缓存(配置时)将使用SQL Server或Redis作为支持。这也可以让你避免使用单例作用域,因为你总是可以随时从分布式缓存中检索对象。