实现编辑、删除与明细信息视图

概述

上篇文章介绍了,在提交表单时对数据的验证规则,在提交的数据合法时,将数据添加到数据库,也就是实现了信息的增加视图。这篇文章将实现查看明细,编辑,删除视图。

实现信息的明细视图

首先,让我们来看一下如何实现一条数据的明细信息视图。为了更好地体会这一功能,首先我们在前文所述的学生信息列表视图(Views文件夹下面的Student文件夹下面的StudentList.cshtml文件)中保留学生信息的姓名、性别、地址、电话、班级等字段。修改后的学生列表视图代码:

@model IEnumerable<Wolfy.FirstMVCProject.Models.Student>

@{
    Layout = null;
}

<!DOCTYPE html>

<html>
<head>
    <meta name="viewport" content="width=device-width" />
    <title>学生信息</title>
</head>
<body>
    <p>
        @Html.ActionLink("添加", "Create")
    </p>
    <table class="table">
        <tr>
            <th>
               姓名
            </th>
            <th>
              性别
            </th>
            <th>
               地址
            </th>

            <th>
               电话
            </th>
            <th>
               删除
            </th>

            <th>
               班级名称
            </th>
            <th></th>
        </tr>

    @foreach (var item in Model) {
        <tr>
            <td>
                @Html.DisplayFor(modelItem => item.stuName)
            </td>
            <td>
                @Html.DisplayFor(modelItem => item.stuSex)
            </td>
            <td>
                @Html.DisplayFor(modelItem => item.stuAddress)
            </td>
            <td>
                @Html.DisplayFor(modelItem => item.stuPhone)
            </td>
            <td>
                @Html.DisplayFor(modelItem => item.Course.className)
            </td>
            <td>
                @Html.ActionLink("编辑", "Edit", new { id=item.stuId }) |
                @Html.ActionLink("详细", "Details", new { id=item.stuId }) |
                @Html.ActionLink("删除", "Delete", new { id=item.stuId })
            </td>

        </tr>
    }

    </table>
</body>
</html>

右键在浏览器中查看

现在学生列表中就只显示每条数据的姓名、性别、地址、电话、班级名称了,如果想查看该条数据的详细信息,需要点击每条数据的“详细”链接,将画面导航到明细数据画面,在该画面中查看这条数据的明细信息。当一条数据的细节信息比较多,而我们只想在该数据的列举清单中显示该数据的几个摘要信息,通过点击链接或按钮的操作来查看数据的细节信息时这种处理方法是比较有用的。

接下来让我们来追加这个明细数据视图。首先打开Student控制器,追加一个返回明细数据视图的Details方法,代码如下所示。

/// <summary>
/// 学生信息详细Action
/// </summary>
/// <param name="id"></param>
/// <returns></returns>
public ActionResult Details(int id)
{
    var student = from s in entity.Student
                  where s.stuId == id
                  select s;
    Student stu = student.FirstOrDefault();
    //查到了该学生的详细
    if (stu != null)
    {
        //找到该学生的信息,则在Details视图中显示,将该学生的信息对象传过去。
        return View("Details",stu);
    }
    else
    {
        //没有查到学生信息明细,则返回学生列表
        return RedirectToAction("StudentList");
    }

}

在Details方法中点击鼠标右键,选择“添加视图”,模型类选择Student,在支架模板中选择“Details”(明细数据),如图所示。

如果要创建中文网站或应用程序,则将默认生成的Details.cshtml文件中有关英文文字修改为中文,修改完毕后该文件中的代码如下所示。

@model Wolfy.FirstMVCProject.Models.Student

@{
    Layout = null;
}

<!DOCTYPE html>

<html>
<head>
    <meta name="viewport" content="width=device-width" />
    <title>Details</title>
</head>
<body>
    <div>
        <h4>Student</h4>
        <hr />
        <dl class="dl-horizontal">
            <dt>
                姓名
            </dt>

            <dd>
                @Html.DisplayFor(model => model.stuName)
            </dd>

            <dt>
              性别
            </dt>

            <dd>
                @Html.DisplayFor(model => model.stuSex)
            </dd>

            <dt>
              生日
            </dt>

            <dd>
                @Html.DisplayFor(model => model.stuBirthdate)
            </dd>

            <dt>
                入学时间
            </dt>

            <dd>
                @Html.DisplayFor(model => model.stuStudydate)
            </dd>

            <dt>
                地址
            </dt>

            <dd>
                @Html.DisplayFor(model => model.stuAddress)
            </dd>

            <dt>
              邮箱
            </dt>

            <dd>
                @Html.DisplayFor(model => model.stuEmail)
            </dd>

            <dt>
              电话
            </dt>

            <dd>
                @Html.DisplayFor(model => model.stuPhone)
            </dd>

            <dt>
               是否删除
            </dt>

            <dd>
                @Html.DisplayFor(model => model.stuIsDel)
            </dd>

            <dt>
               录入时间
            </dt>

            <dd>
                @Html.DisplayFor(model => model.stuInputtime )
            </dd>

            <dt>
               班级
            </dt>

            <dd>
                @Html.DisplayFor(model => model.Course.className)
            </dd>

        </dl>
    </div>
    <p>
        @Html.ActionLink("Edit", "Edit", new { id = Model.stuId }) |
        @Html.ActionLink("Back to List", "StudentList")
    </p>
</body>
</html>

重新运行应用程序,在学生信息列表中点击某个学生的“详细”链接

通过观察地址栏你会发现:http://localhost:4585/Student/Details/9,在url中最后一个9就是学生的id,这个参数是如何传递的呢?

在学生列表视图代码中你会发现类似如下的代码:

  @Html.ActionLink("详细", "Details", new { id=item.stuId }) 

其中id为url中参数的名称,然后我们看一下action方法中的参数也为id,这两者是否必须对应呢?那么,我们修改一下Details方法中的参数名称,测试一下。

将Details方法的参数名改为intI的,然后运行,则会出现如下的信息。

可见,视图中传递的参数名和Action中的参数名必须一样。

实现信息的编辑视图

接下来,让我们来看一下如何实现一个用来修改数据的视图。

首先打开Student控制器,追加一个返回数据修改视图的Edit方法与一个对该视图中的表单提交进行处理的Edit方法,代码如下所示。

public ActionResult Edit(int id)
{
    var student = from s in entity.Student
                  where s.stuId == id
                  select s;
    Student stu = student.FirstOrDefault();

    //查到了该学生的详细
    if (stu != null)
    {
        //外键关系处理
        var course = from c in entity.Course
                     where c.classId == stu.classId
                     select c;
        stu.Course = course.FirstOrDefault();
        //因为学生信息中有班级id的外键,所以在编辑的时候,要指定dropdownlist的数据源
        var courses = from s in entity.Course
                      select s;

        List<SelectListItem> items = new List<SelectListItem>();
        foreach (var item in courses)
        {
            SelectListItem selectListItem = null;
            //当前学生所在的班级被选中
            if (item.classId == stu.classId)
            {
                selectListItem = new SelectListItem() { Text = item.className, Value = item.classId.ToString(), Selected = true };
            }
            else
            {
                selectListItem = new SelectListItem() { Text = item.className, Value = item.classId.ToString() };
            }

            items.Add(selectListItem);
        }
        ViewData["course"] = items;
        //找到该学生的信息,则在Details视图中显示,将该学生的信息对象传过去。
        return View("Edit", stu);
    }
    else
    {
        //没有查到学生信息明细,则返回学生列表
        return RedirectToAction("StudentList");
    }
}
/// <summary>
/// 处理post请求的action方法,也就是修改后提交的数据
/// </summary>
/// <param name="id"></param>
/// <returns></returns>
[HttpPost]
public ActionResult Edit(Student student)
{
    try
    {
        var stu = entity.Student.Find(student.stuId);
        //处理学生所在的班级
        string strCourseId = Request.Form["course"];
        //作为测试,我们只修改性别和班级
        stu.stuSex = student.stuSex;
        stu.classId = Convert.ToInt32(strCourseId);
        entity.Entry<Student>(stu).State = System.Data.Entity.EntityState.Modified;

        int intCount = entity.SaveChanges();
        if (intCount > 0)
        {
            return RedirectToAction("Details", new { id = student.stuId });
        }
        else
        {
            return Content("修改失败");
        }
    }
    catch (Exception)
    {

        return Content("修改失败");
    }
}

这两个Edit方法中,第一个方法将在用户点击外部画面的“编辑”链接时被调用,用来在浏览器中显示数据修改视图,并且在该视图中显示用户选择编辑的数据。第二个Edit方法前面带有一个[HttpPost]标记,负责将修改数据视图中提交的表单数据绑定到一个用模型创建出来的Student对象实例之上(当用户在表单中完成数据修改并点击保存按钮的时候进行提交),在保存数据的过程中如果发生任何错误而导致保存失败的话,则提示修改失败文字信息。

作为测试用,我们只修改性别和班级的信息

接下来让我们来追加该数据修改视图、在Edit方法中点击鼠标右键,选择“添加视图”,模型类选择Student,在支架模板中选择“Edit”(修改数据),如图所示。

如果要创建中文网站或应用程序,则将默认生成的Edit.cshtml文件代码如下所示。

@model Wolfy.FirstMVCProject.Models.Student

@{
    Layout = null;
}

<!DOCTYPE html>

<html>
<head>
    <meta name="viewport" content="width=device-width" />
    <title>Edit</title>
</head>
<body>
    @using (Html.BeginForm("Edit","Student",FormMethod.Post))
    {
        @Html.AntiForgeryToken()

        <div class="form-horizontal">
            <h4>Student</h4>
            <hr />
            @Html.ValidationSummary(true)
            @Html.HiddenFor(model => model.stuId)

            <div class="form-group">
                @Html.LabelFor(model => model.stuName, new { @class = "control-label col-md-2" })
                <div class="col-md-10">
                    @Html.EditorFor(model => model.stuName)
                    @Html.ValidationMessageFor(model => model.stuName)
                </div>
            </div>

            <div class="form-group">
                @Html.LabelFor(model => model.stuSex, new { @class = "control-label col-md-2" })
                <div class="col-md-10">
                    @Html.EditorFor(model => model.stuSex)
                    @Html.ValidationMessageFor(model => model.stuSex)
                </div>
            </div>

            <div class="form-group">
                @Html.LabelFor(model => model.stuBirthdate, new { @class = "control-label col-md-2" })
                <div class="col-md-10">
                    @Html.EditorFor(model => model.stuBirthdate)
                    @Html.ValidationMessageFor(model => model.stuBirthdate)
                </div>
            </div>

            <div class="form-group">
                @Html.LabelFor(model => model.stuStudydate, new { @class = "control-label col-md-2" })
                <div class="col-md-10">
                    @Html.EditorFor(model => model.stuStudydate)
                    @Html.ValidationMessageFor(model => model.stuStudydate)
                </div>
            </div>

            <div class="form-group">
                @Html.LabelFor(model => model.stuAddress, new { @class = "control-label col-md-2" })
                <div class="col-md-10">
                    @Html.EditorFor(model => model.stuAddress)
                    @Html.ValidationMessageFor(model => model.stuAddress)
                </div>
            </div>

            <div class="form-group">
                @Html.LabelFor(model => model.stuEmail, new { @class = "control-label col-md-2" })
                <div class="col-md-10">
                    @Html.EditorFor(model => model.stuEmail)
                    @Html.ValidationMessageFor(model => model.stuEmail)
                </div>
            </div>

            <div class="form-group">
                @Html.LabelFor(model => model.stuPhone, new { @class = "control-label col-md-2" })
                <div class="col-md-10">
                    @Html.EditorFor(model => model.stuPhone)
                    @Html.ValidationMessageFor(model => model.stuPhone)
                </div>
            </div>

            <div class="form-group">
                @Html.LabelFor(model => model.stuIsDel, new { @class = "control-label col-md-2" })
                <div class="col-md-10">
                    @Html.EditorFor(model => model.stuIsDel)
                    @Html.ValidationMessageFor(model => model.stuIsDel)
                </div>
            </div>

            <div class="form-group">
                @Html.LabelFor(model => model.stuInputtime, new { @class = "control-label col-md-2" })
                <div class="col-md-10">
                    @Html.EditorFor(model => model.stuInputtime)
                    @Html.ValidationMessageFor(model => model.stuInputtime)
                </div>
            </div>

            <div class="form-group">
               stuClass
                <div class="col-md-10">
                    @Html.DropDownList("course", String.Empty)
                    @Html.ValidationMessageFor(model => model.classId)
                </div>
            </div>

            <div class="form-group">
                <div class="col-md-offset-2 col-md-10">
                    <input type="submit" value="Save" class="btn btn-default" />
                </div>
            </div>
        </div>
    }

    <div>
        @Html.ActionLink("Back to List", "Index")
    </div>
</body>
</html>

注意,为dropdownlist使用viewdata绑定数据源。 右键在浏览器中查看学生列表,然后选择一条数据进行编辑,如图所示:

修改后结果

实现信息的删除视图

接下来,让我们来看一下如何实现一个用来删除数据的视图。

首先打开Student控制器,追加一个删除数据的方法Delete,代码如下所示。

public ActionResult Delete(int id)
{
    var student = entity.Student.Find(id);
    return View("Delete", student);

}
[HttpPost]
public RedirectToRouteResult Delete(int id, FormCollection collection)
{

    var stu = entity.Student.Find(id);

    //因为score表中存有学生id外键,所以先删除成绩
    var scores = from s in entity.Score
                 where s.stuId == stu.stuId
                 select s;
    foreach (var item in scores)
    {
        entity.Score.Remove(item);
    }

    entity.Student.Remove(stu);
    entity.SaveChanges();
    return RedirectToAction("StudentList");
}
}

这里请注意第一个没有[HttpPost]标记的Delete方法并不会将数据删除,因为如果通过GET请求而删除(或者追加、修改)删除数据的话都会打开一个安全漏洞。

然后在方法上右键,添加视图。

Delete.cshtml代码为:

@model Wolfy.FirstMVCProject.Models.Student

@{
    Layout = null;
}

<!DOCTYPE html>

<html>
<head>
    <meta name="viewport" content="width=device-width" />
    <title>Delete</title>
</head>
<body>
    <h3>Are you sure you want to delete this?</h3>
    <div>
        <h4>Student</h4>
        <hr />
        <dl class="dl-horizontal">
            <dt>
                @Html.DisplayNameFor(model => model.stuName)
            </dt>

            <dd>
                @Html.DisplayFor(model => model.stuName)
            </dd>

            <dt>
                @Html.DisplayNameFor(model => model.stuSex)
            </dt>

            <dd>
                @Html.DisplayFor(model => model.stuSex)
            </dd>

            <dt>
                @Html.DisplayNameFor(model => model.stuBirthdate)
            </dt>

            <dd>
                @Html.DisplayFor(model => model.stuBirthdate)
            </dd>

            <dt>
                @Html.DisplayNameFor(model => model.stuStudydate)
            </dt>

            <dd>
                @Html.DisplayFor(model => model.stuStudydate)
            </dd>

            <dt>
                @Html.DisplayNameFor(model => model.stuAddress)
            </dt>

            <dd>
                @Html.DisplayFor(model => model.stuAddress)
            </dd>

            <dt>
                @Html.DisplayNameFor(model => model.stuEmail)
            </dt>

            <dd>
                @Html.DisplayFor(model => model.stuEmail)
            </dd>

            <dt>
                @Html.DisplayNameFor(model => model.stuPhone)
            </dt>

            <dd>
                @Html.DisplayFor(model => model.stuPhone)
            </dd>

            <dt>
                @Html.DisplayNameFor(model => model.stuIsDel)
            </dt>

            <dd>
                @Html.DisplayFor(model => model.stuIsDel)
            </dd>

            <dt>
                @Html.DisplayNameFor(model => model.stuInputtime)
            </dt>

            <dd>
                @Html.DisplayFor(model => model.stuInputtime)
            </dd>

            <dt>
                @Html.DisplayNameFor(model => model.Course.className)
            </dt>

            <dd>
                @Html.DisplayFor(model => model.Course.className)
            </dd>

        </dl>

        @using (Html.BeginForm("Delete","Student",FormMethod.Post)) {
            @Html.AntiForgeryToken()

            <div class="form-actions no-color">
                <input type="submit" value="Delete" class="btn btn-default" /> |
                @Html.ActionLink("Back to List", "Index")
            </div>
        }
    </div>
</body>
</html>

右键在浏览器中查看学生列表视图,然后选择一条学生信息,单击删除超链接。

点击删除按钮,该条数据将被删除,浏览器中返回显示学生列表页面。

总结

最后,我们添加代码与视图模板来创建了数据的修改视图,删除视图与明细数据视图。一个简单的ASP.NET MVC5项目也算完成了。一个小demo也基本上包括增删改查的操作,接下来,将深入学习一下理论,用理论来支撑之前的实践。