Startup.Auth.cs //我在这里添加了我的DbContext
// Configure the db context, user manager and signin manager to use a single instance per request
app.CreatePerOwinContext(ProjectPlannerContext.Create);
app.CreatePerOwinContext<ApplicationUserManager>(ApplicationUserManager.Create);
app.CreatePerOwinContext<ApplicationSignInManager>(ApplicationSignInManager.Create);
在 AccountController.cs 中,我想创建一个服务实例,需要 UnitOfWork 实例来执行数据库相关的操作。所以这是代码:
public AccountController()
{
contactManager = new ContactManager(UnitOfWork);
}
其中 UnitOfWork 是这样定义的属性:
public UnitOfWork UnitOfWork
{
get
{
if (unitOfWork == null)
{
//Here the HttpContext is NULL
unitOfWork = new UnitOfWork(HttpContext.GetOwinContext().Get<ProjectPlannerContext>());
}
return unitOfWork;
}
}
我应用了一个全局授权过滤器,所以当我运行应用程序时,首先要做的是登录到网站(这将导致对AccountController的登录方法的请求 - 并给出一个错误对象引用而不是设置为实例,因为在控制器构造函数中调用了UnitOfWork。
对我来说奇怪的是,如果我在构造函数中注释contactManager行,则在登录时Asp.NET MVC使用如下定义的 SignInManager :
public ApplicationSignInManager SignInManager
{
get
{
return _signInManager ?? HttpContext.GetOwinContext().Get<ApplicationSignInManager>();
}
private set
{
_signInManager = value;
}
}
这完全有效,我可以注册(对象引用错误不会抛出),并在数据库中看到我的用户被插入。 所以我的问题是为什么会发生这种情况,以及如果不在构造函数中如何初始化我的服务?
如果我定义 UnitOfWork ,实际上有解决方法:
public UnitOfWork UnitOfWork
{
get
{
if (unitOfWork == null)
{
unitOfWork = new UnitOfWork(ProjectPlannerContext.Create());
}
return unitOfWork;
}
}
但这意味着我应该在每个Controller中创建数据库上下文..
最佳做法/解决方案是什么?
答案 0 :(得分:2)
我最终实现了将从其他控制器派生的BaseController,这里是示例:
public abstract class BaseController : Controller
{
public virtual UnitOfWork UnitOfWork
{
get
{
return unitOfWork;
}
}
protected override void Initialize(RequestContext requestContext)
{
base.Initialize(requestContext);
if (unitOfWork == null)
{
unitOfWork = new UnitOfWork(HttpContext.GetOwinContext().Get<ProjectPlannerContext>());
}
}
#region Private members
private UnitOfWork unitOfWork;
#endregion
}
需要额外服务的AccountController(IContactManager):
public class AccountController : BaseController
{
public AccountController()
{
}
protected override void Initialize(RequestContext requestContext)
{
base.Initialize(requestContext);
contactManager = new ContactManager(UnitOfWork);
}
public ActionResult CreateContact(string firstName, string lastName, string email)
{
ContactModel contact = contactManager.Create(firstName, lastName, email);
return JsonNet(new { contact = contact });
}
#region Private members
private IContactManager contactManager;
#endregion
}