所以我有一个运行ASP.NET Identity 2.0的ASP.NET MVC 5应用程序。一切都很好,但我想重构我的代码,我想知道我当前的实现存在哪些替代方案。让我解释一下。
我的项目根目录中有Controllers,项目的Areas文件夹中有很多。几乎所有这些都继承自BaseController
类,而后者继承自System.Web.Mvc.Controller
。这个BaseController
看起来像这样:
public class BaseController()
{
protected ApplicationUserManager _userManager;
protected ApplicationRoleManager _roleManager;
protected readonly MyDbContext _db = new MyDbContext();
public BaseController()
{
}
public BaseController(ApplicationUserManager um, ApplicationRoleManager rm)
{
UserManager = um;
RoleManager = rm;
}
public ApplicationUserManager UserManager { ... }
public ApplicationRoleManager RoleManager { ... }
#region Utility Methods
// Here are over 60 utility methods that are basically queries on _db
#endregion
}
更多的方法正在进行中,我不禁觉得有一种更好的方法,而不是在逻辑上将它们放在基类中,而不是每个控制器都应该直接继承这样的方法。
将它们移至MyDbContext
(继承IdentityDbContext
)基本上什么也没做,只是将它们移到更适用的文件中。我想象的是MyDbContext
中的每个DbSet都有自定义实用程序方法,但我不知道该怎么做。像下面这样的东西是理想的:
Semester thisSemester = _db.Semesters.GetCurrentSemester();
或
SelectList semesters = _db.Semesters.GetAllSemestersAsSelectList();
两个示例中Semesters
的类型为DbSet<Semester>
。
有人能提供解决方案吗?
答案 0 :(得分:2)
当我看到像...这样的方法时。
_db.Semesters.GetAllSemestersAsSelectList()
...我认为这将是一种扩展方法(除非你有自己的DbSet
实现)。但扩展方法旨在用于真正的通用任务,而不是用于此类特定任务。此外,它要求您可以在任何需要此选择列表的地方访问DbSet
在服务类中执行此操作会更好,因此您可以调用类似
的方法_semesterService.GetAllSemestersAsSelectList()
此服务可能看起来像
class SemesterService : ISemesterService
{
private readonly MyDbContext _context;
/// <summary>
/// Constructor in which an IoC container can inject a context.
/// </summary>
/// <param name="context"></param>
public SemesterService(MyDbContext context)
{
this._context = context;
}
public SelectList GetAllSemestersAsSelectList()
{
return new SelectList(_context.Semesters, "Id", "Name");
}
public Semester GetCurrentSemester()
{
return _context.Semesters.Where(....).FirstOrDefault();
}
}
只是举个例子。
从服务中返回Semesters并在MVC控制器中构建SelectList
可能更好,因此服务层不会对MVC产生依赖。