0

我正在寻求有关如何使我的 MVC 代码更高效的帮助,因为我在我的 Create GET 和 POST 操作中重用了相同的代码,这违反了 MVC 的 DRY 原则。

具体来说,我正在使用 EntityFramework 并有一个控制器,该控制器使用以下代码填充 ViewModel:

public ActionResult Create()
    {

        var fileManagers = from x in db.UserProfiles
                            select x;

        var estimators = from x in db.UserProfiles
                                select x;

        var projectManagers = from x in db.UserProfiles
                            select x;

        var jobStatuses = from x in db.JobStatuses
                            select x;           

        JobViewModel viewModel = new JobViewModel
        {
            Job = new Job(),
            FileManagers = fileManagers.Select(x => new SelectListItem
            {
                Value = x.UserName,
                Text = x.FirstName + " " + x.LastName
            }).ToList(),
            Estimators = estimators.Select(x => new SelectListItem
            {
                Value = x.UserName,
                Text = x.FirstName + " " + x.LastName
            }).ToList(),
            ProjectManagers = projectManagers.Select(x => new SelectListItem
            {
                Value = x.UserName,
                Text = x.FirstName + " " + x.LastName
            }).ToList()
        };

        return View(viewModel);
    }

在我的 POST 函数中,我正在检查模型的有效性,然后如果模型无效,则再次写出相同的代码以重新填充我的 ViewModel,这在http://的 ASP.NET 音乐教程中显示www.asp.net/mvc/tutorials/mvc-music-store/mvc-music-store-part-5

    [HttpPost]
    [ValidateAntiForgeryToken]
    public ActionResult Create(Job job, string action)
    {

        if (ModelState.IsValid)
        {
            db.Jobs.Add(job);
            db.SaveChanges();
            return RedirectToAction("Index");
        }

        var fileManagers = from x in db.UserProfiles
                           select x;

        var estimators = from x in db.UserProfiles
                         select x;

        var projectManagers = from x in db.UserProfiles
                              select x;

        var jobStatuses = from x in db.JobStatuses
                          select x;

        JobViewModel viewModel = new JobViewModel
        {
            Job = job,
            FileManagers = fileManagers.Select(x => new SelectListItem
            {
                Value = x.UserName,
                Text = x.FirstName + " " + x.LastName
            }).ToList(),
            Estimators = estimators.Select(x => new SelectListItem
            {
                Value = x.UserName,
                Text = x.FirstName + " " + x.LastName
            }).ToList(),
            ProjectManagers = projectManagers.Select(x => new SelectListItem
            {
                Value = x.UserName,
                Text = x.FirstName + " " + x.LastName
            }).ToList()
        };

        return View(viewModel);

    }

有人可以建议一个更好的方法吗?最好不要添加单独的 ORM 层,因为项目很小。

4

2 回答 2

3

只需将所有重用的代码放在一个方法中,然后从两个操作方法中调用,例如

  public ActionResult Create()
        {

            return View(createViewModel(new Job()));
        }

        [HttpPost]
        [ValidateAntiForgeryToken]
        public ActionResult Create(Job job, string action)
        {

            if (ModelState.IsValid)
            {
                db.Jobs.Add(job);
                db.SaveChanges();
                return RedirectToAction("Index");
            }            

            return View(createViewModel(job));
        }

        private JobViewModel createViewModel(Job job)
        {
            var fileManagers = from x in db.UserProfiles
                               select x;

            var estimators = from x in db.UserProfiles
                             select x;

            var projectManagers = from x in db.UserProfiles
                                  select x;

            var jobStatuses = from x in db.JobStatuses
                              select x;

            JobViewModel viewModel = new JobViewModel
            {
                Job = job,
                FileManagers = fileManagers.Select(x => new SelectListItem
                {
                    Value = x.UserName,
                    Text = x.FirstName + " " + x.LastName
                }).ToList(),
                Estimators = estimators.Select(x => new SelectListItem
                {
                    Value = x.UserName,
                    Text = x.FirstName + " " + x.LastName
                }).ToList(),
                ProjectManagers = projectManagers.Select(x => new SelectListItem
                {
                    Value = x.UserName,
                    Text = x.FirstName + " " + x.LastName
                }).ToList()
            };

            return viewModel;
        }

反正我就是这样做的,省去两次输入相同的东西

于 2013-09-04T04:50:05.197 回答
2

好吧,看到您为模型中的每个组使用相同的用户集,这有点简单:

var users = db.UserProfiles
.ToArray()
.Select(x => new SelectListItem
{
    Value = x.UserName,
    Text = x.FirstName + " " + x.LastName
});

var jobStatuses = from x in db.JobStatuses
                  select x;

JobViewModel viewModel = new JobViewModel
{
    Job = job,
    FileManagers = users.ToList(),
    Estimators = users.ToList(),
    ProjectManagers = users.ToList()
};

如果您将其用作表单模型,您还可以像这样创建模型:

var viewModel = new JobViewModel
{
    Job = job,
    FileManagers = new SelectList(users, "Value", "Text", model.FileManager),
    Estimators = new SelectList(users, "Value", "Text", model.Estimator),
    ProjectManagers = new SelectList(users, "Value", "Text", model.ProjectManager)
};

当然,假设各种列表是SelectLists 并且您具有与每个角色的选定用户相对应的字符串模型属性。假设您想要一种填充选择列表的方法,您可以执行以下操作:

[HttpGet]
public ActionResult YourActionName()
{
    var model = new JobViewModel
    {
        Job = job,
        FileManager = "some value",
        Estimator = "some value",
        ProjectManager = "some value"
    };

    PopulateModel(model);

    return View(model);
}

[HttpPost]
public ActionResult YourActionName(JobViewModel model)
{
    if(ModelState.IsValid)
    {
        // do something...
        return RedirectToAction("your success action");
    }

    PopulateModel(model);

    return View(model);
}

private void PopulateModel(JobViewModel model)
{
    model.FileManagers = new SelectList(users, "Value", "Text", model.FileManager);
    model.Estimators = new SelectList(users, "Value", "Text", model.Estimator);
    model.ProjectManagers = new SelectList(users, "Value", "Text", model.ProjectManager);
}
于 2013-09-04T05:01:45.663 回答