Models文件下的模型因为和数据库紧密关联,最好不要直接作为视图和控制器中间的传递媒介,不然如果想在显示时添加某些字段,会变动数据库表的结构。
因此,可以创建一个专门用于视图和控制器传递数据的模型ViewModel,也叫视图模型。
在项目根目录下创建一个名为ViewModels的文件夹,并在ViewModels文件夹下创建视图模型类MajorViewModel。
MajorViewModel视图模型类的字段和Major模型类中的属性一样,有Id和Name。
代码如下:
public class MajorViewModel
{
public Guid Id { get; set; }
[Display(Name = "专业名称")]
public string Name { get; set; } = string.Empty;
}
其中,[Display(Name = "专业名称")]
表示当视图中在可能出现Name属性的含义的地方,将显示专业名称字样。
在Add.cshtml中,将指定模型修改为MajorViewModel。
由于MajorViewModel处于StuInfoManaSys.ViewModels命名空间下,因此还需要修改命名空间。
代码如下:
@using StuInfoManaSys.ViewModels
@model MajorViewModel
对于之后的功能,如果每一个视图中都去指定命名空间,显得非常繁琐,因此可以将@using StuInfoManaSys.ViewModels
这一指令移步到**_ViewImports.cshtml**中。
现在可以将label标签中的文本删除,并添加asp-for属性,代码如下:
<label asp-for="Name" class="label"></label>
label中的asp-for会根据模型中属性的**[Display]特性将label的文本设置为Display中的Name属性,例如,在MajorViewModel中,Name的Display的Name**属性是专业名称,因此,它会将专业名称这几个字填充到label中充当文本。
回到控制器中,现在Add动作接收的参数类型已经又Major变为MajorViewModel了,代码如下:
[HttpPost]
public IActionResult Add(MajorViewModel model)
{
majorRepo.Insert(model);
return RedirectToAction("Index");
}
但是,简单地将参数类型修改并不解决问题,因为Insert方法并不接收MajorViewModel类型的数据,它只接收Major类型的数据,因此还需要将MajorViewModel类型的数据转换为Major类型的数据。
最终代码如下:
[HttpPost]
public IActionResult Add(MajorViewModel model)
{
Major major = new Major()
{
Name = model.Name,
};
majorRepo.Insert(major);
return RedirectToAction("Index");
}