学习ASP.NET MVC 编程系列目录

学习ASP.NET MVC(一)——我的第一个ASP.NET MVC应用程序

学习ASP.NET MVC(二)——我的第一个ASP.NET MVC 控制器

学习ASP.NET MVC(三)——我的第一个ASP.NET MVC 视图

学习ASP.NET MVC(四)——我的第一个ASP.NET MVC 实体对象

学习ASP.NET MVC(五)——我的第一个ASP.NET MVC CURD页面

学习ASP.NET MVC(六)——我的第一个ASP.NET MVC 编辑页面

学习ASP.NET MVC(七)——我的第一个ASP.NET MVC 查询页面

学习ASP.NET MVC(八)——“Code First Migrations ”工具

学习ASP.NET MVC(九)——“Code First Migrations ”工具使用示例

学习ASP.NET MVC(十)——排序

学习ASP.NET MVC(十一)——分页

在本篇文章中,我将添加一个新的查询页面(SearchIndex),可以按书籍的种类或名称来进行查询。这个新页面的网址是http://localhost:36878/Book/ SearchIndex。该页面中用一个下拉框来显示种类,用一文本框让用户输入书籍的名称。当用户在点击“查询”按钮之后,页面会被刷新,显示用户的查询结果。控制器会根据用户提交查询参数,由动作方法(Action Motehd)去解析用户提交的参数值,并使用这些值来查询数据库。

第一步,创建SearchIndex查询页面
            首先,在BookController中添加一个SearchIndex动作方法。该方法将返回一个包含HTML表单的视图。代码如下:

public ActionResult SearchIndex(string searchString)
{ var books = from m in db.Books
select m; if (!String.IsNullOrEmpty(searchString))
{ books = books.Where(s => s.Name.Contains(searchString)); }
return View(books);
}

上面SearchIndex方法代码中的第一行如下面,其作用是创建一个LINQ查询从数据库中筛选相应的书籍数据:

           var books = from m in db.Books
select m;

这一句表示查询已经建立,但是尚未对数据存储区中的数据进行筛选。 
       如果“searchString”参数变量中有一个字符串,则这个“books”查询语句将以“searchString”参数变量的值做为查询条件进行筛选相应的书籍数据,如下面的代码:

   if (!String.IsNullOrEmpty(searchString))
{
books = books.Where(s => s.Name.Contains(searchString)); }

上面代码中的s =>s.Title代码是一个Lambda表达式。 Lambda 表达式用在基于方法的 LINQ 查询中,作为诸如 Where 和 Where 等标准查询运算符方法的参数。  例如上面的代码中使用的方法。LINQ查询时未执行它们的定义,或者当他们通过调用一个方法进行修改,或在排序时进行修改。相反,查询执行的延迟,这意味着一个表达式的计算被延迟,直到其变量实际上的迭代结束或者可以调用的方法(ToList方法)被调用。在SearchIndex这个页面中,查询是在SearchIndex视图下执行。

接下来,我们来制作一个SearchIndex视图,以将这个查询界面呈现给用户看。在Visual Studio中的BookController文件中右键单击里面的SearchIndex方法,在弹出菜单中单击“添加视图”菜单。在添加视图对话框中,指定你要一个Book对象传递给视图模板作为它的模型类。在支架模板列表中,选择列表,然后单击“添加”。如下图。

当单击“添加”按钮,将创建一个Views\Book\ SearchIndex.cshtml视图模板。因为你选择了列表中的支架模板列表中,Visual Studio会自动生成(搭建)的视图中的一些默认的标记。基架创建一个HTML表单。它检查Book类和创建的代码来呈现为类的每个属性<label>元素。下面的清单显示生成的创建视图:

@model IEnumerable<MvcApplication1.Models.Book>

@{

    ViewBag.Title = "书籍查询";

}

<h2>书籍查询</h2>
<p> @Html.ActionLink("Create New", "Create") </p> <table>
<tr>
<th>
@Html.DisplayNameFor(model => model.Category) </th> <th> @Html.DisplayNameFor(model => model.Name) </th>
<th>
@Html.DisplayNameFor(model => model.Numberofcopies) </th>
<th>
@Html.DisplayNameFor(model => model.AuthorID) </th> <th> @Html.DisplayNameFor(model => model.Price) </th>
<th>
@Html.DisplayNameFor(model => model.PublishDate) </th> <th></th> </tr> @foreach (var item in Model) { <tr> <td> @Html.DisplayFor(modelItem => item.Category) </td> <td> @Html.DisplayFor(modelItem => item.Name) </td> <td> @Html.DisplayFor(modelItem => item.Numberofcopies) </td> <td> @Html.DisplayFor(modelItem => item.AuthorID) </td> <td> @Html.DisplayFor(modelItem => item.Price) </td> <td> @Html.DisplayFor(modelItem => item.PublishDate) </td> <td> @Html.ActionLink("Edit", "Edit", new { id=item.BookID }) | @Html.ActionLink("Details", "Details", new { id=item.BookID }) | @Html.ActionLink("Delete", "Delete", new { id=item.BookID }) </td> </tr> }
</table>

按F5, 运行该应用程序,并使用浏览器导航到/Book/ SearchIndex。在URL后面会追加一个查询字符串,如“?searchString=sql”。提交之后,符合条件的书籍数据将显示。如下图。

第三,修改SearchIndex查询方法
        我们也可以修改SearchIndex方法的参数,传入一个命名参数“ID”,这个“ID”参数将匹配在Global.asax文件中的缺省路由设置中的{id}占位符。路由设置如下:

{controller}/{action}/{id}

原来SearchIndex方法如下所示:

public ActionResult SearchIndex(string searchString)
{ var books = from m in db.Books select m; if (!String.IsNullOrEmpty(searchString)) { books = books.Where(s => s.Name.Contains(searchString)); } return View(books);
}

修改后的SearchIndex方法将如下所示:

public ActionResult SearchIndex(string id)
{ string searchString = id;
var books = from m in db.Books
select m; if (!String.IsNullOrEmpty(searchString))
{ books = books.Where(s => s.Name.Contains(searchString)); } return View(books);
}

现在,您可以把查询条件“书籍名称”作为路由数据(URL中的一段字符),而不是作为查询字符串值。如下图。

       第三,添加“书籍名称”查询条件
     通过上面的学习,我们实现了数据查询功能。但是我们不能希望普通用户也能像我们一样,会在URL中添加查询条件。当需要进行查询时,自己去修改URL中的查询条件内容来进行书籍查询。所以,需要添加一个查询页面,方便普通用户输入相应的查询条件,根据查询条件去查询书籍。

一、改变SearchIndex方法的签名,并通过路由绑定到ID参数上,让SearchIndex方法接受一个名为“searchString”字符串作为参数。代码如下:

public ActionResult SearchIndex(string searchString)
{ var books = from m in db.Books select m; if (!String.IsNullOrEmpty(searchString)) { books = books.Where(s => s.Name.Contains(searchString)); }
return View(books); }

二、打开Views\Book\ SearchIndex.cshtml文件,在@Html.ActionLink("Create New", "Create")的位置处,添加一个文本框与一个查询按钮。内容如下:

@using (Html.BeginForm())
{ <p> 书籍名称: @Html.TextBox("SearchString")<br /> <input type="submit" value="查询" /></p> }

下面的代码显示了Views\Book\ SearchIndex.cshtml文件的一部分与增加的筛选标记。

@Model IEnumerable<MvcApplication1.Models.Book>

@{
ViewBag.Title = "书籍查询";
} <h2>书籍查询</h2>
@using (Html.BeginForm()) { <p> 书籍名称: @Html.TextBox("SearchString")<br /> <input type="submit" value="查询" /></p> }

这个Html.BeginForm辅助方法创建了一个<form>标签。当用户通过单击“查询”按钮提交表单时,Html.BeginForm辅助方法将会把这个Form中的内容提交给控制器,同时刷新页面。
       三、按F5,运行该应用程序,并在“书籍名称”文本框中输入“sql”,然后点击“查询”按钮,进行书籍查询。如下图。

还有不需要重载SearchIndex的HttpPost的方法。因为该方法不改变应用程序的状态,只是是用来查询数据。 
       你可以象下面一样把[HttpPost]加在SearchIndex方法的上面。在添加了[HttpPost]之后,浏览器将首先调用匹配HttpPost的SearchIndex方法。HttpPost的SearchIndex方法运行结果如下图。

[HttpPost] 

public string SearchIndex(FormCollection fc, string searchString)
{ return "<h3> From [HttpPost]SearchIndex: " + searchString + "</h3>"; }

然而,即使添加了SearchIndex的HttpPost版本的方法。假设一下如下场景,你想把某个查询结果发给你的朋友,你又想只发一个特定链接给朋友,让他们可以查询查看相同的一个查询结果。请注意,如果是相同的查询结果,一个为HTTP POST请求,另一个为相同的URL GET请求(例如本地主机:XXXXX /图书/ SearchIndex ) 。则HTTP POST请求在URL本身没有带查询参数的情况下,是无法看到查询结果的。如果只是一个URL,这就意味着你与朋友们永远不能看到相同的查询结果。
        你应该使用以下的解决方案,使用BeginForm的重载方法,指定POST请求应该在URL中添加的相应的查询参数信息 ,它应该被路由到SearchIndex方法的HTTPGET版本。使用下面的代码替换现有参数的BeginForm方法将:如下图。

   @using (Html.BeginForm("SearchIndex", "book", FormMethod.Get))


       现在,当你点击“查询”按钮时,URL中将包含查询条件的字符串。查询请求也将去请求HTTPGET的 SearchIndex操作方法,即使你有一个HttpPost的SearchIndex方法。如下图。

第三,添加“书籍种类”查询方法
      第一步,删除代码中HttpPost版本的SearchIndex方法。

第二步,添加新的查询功能。在页面中添加一个“书籍种类”的查询条件,让用户可以通过“书籍种类”查询到相关书籍。用下面的代码替换SearchIndex方法:

   public ActionResult SearchIndex(string Category, string searchString)
{ var cateLst = new List<string>();
var cateQry = from d in db.Books orderby d.Category select d.Category; cateLst.AddRange(cateQry.Distinct()); ViewBag.category = new SelectList(cateLst); var books = from m in db.Books select m; if (!String.IsNullOrEmpty(searchString))
{
books = books.Where(s => s.Name.Contains(searchString)); } if (string.IsNullOrEmpty(Category)) return View(books); else {
return View(books.Where(x => x.Category == Category));
}
}

这个新的SearchIndex方法增加了一个新的查询条件,即Category。代码的前几行创建一个List对象从数据库中查询“书籍种类”,并将查询到的结果添加到List对象中。

下面的代码是通过一个LINQ查询从数据库把所有书籍种类都查了出来。

var cateQry = from d in db.Books

                           orderby d.Category

                           select d.Category;

以下代码的作用是使用泛型List集合的AddRange方法所有书籍类型添加到列表中。 (如果没有DISTINCT修饰符,会将相同的类型增加到列表中 - 例如,MS,SAP将会被我们添加两次)。

 cateLst.AddRange(cateQry.Distinct());

然后,该代码存储在ViewBag对象流派列表。

  ViewBag.category = new SelectList(cateLst);

下面的代码演示如何检查Category参数。如果它不是空的,该代码进一步限制了书的查询所选择的书限制到指定的种类。

 if (string.IsNullOrEmpty(Category))

                return View(books);
else
{
return View(books.Where(x => x.Category == Category));
}

          第四,在SearchIndex查询页面中添加“书籍种类”查询条件 
          添加一个HTML样式的下拉列表框(DropDownList)到Views\Book\ SearchIndex.cshtml文件中,放在“书籍名称”文本框的前面。已完成的代码如下所示:

<p> 

     @using (Html.BeginForm("SearchIndex","book",FormMethod.Get)){     

         <p>书籍种类: @Html.DropDownList("category", "All")   

           书籍名称: @Html.TextBox("SearchString")   

         <input type="submit" value="查询" /></p> 

        } 

</p>

按F5,运行这个应用程序,在浏览器中浏览/Book/ SearchIndex这个地址。就可以按“书籍种类”、“书籍名称”进行书籍信息查询。如下图1,图2。
 

图1

图2
 在本篇中学习如何创建一个新的查询操作方法和视图,让用户通过书籍名称和书籍类型来进行查询。

学习ASP.NET MVC(七)——我的第一个ASP.NET MVC 查询页面的更多相关文章

  1. 学习ASP.NET MVC(一)——我的第一个ASP.NET MVC应用程序

    学习ASP.NET MVC系列: 学习ASP.NET MVC(一)——我的第一个ASP.NET MVC应用程序 学习ASP.NET MVC(二)——我的第一个ASP.NET MVC 控制器 学习ASP ...

  2. 学习ASP.NET MVC(三)——我的第一个ASP.NET MVC 视图

    今天我将对前一篇文章中的示例进行修改,前一篇文章中并没有用到视图,这次将用到视图.对于前一个示例中的HelloWorldController类进行修改,使用视图模板文件生成HTML响应给浏览器. 一. ...

  3. 7、ASP.NET MVC入门到精通——第一个ASP.NET MVC程序

    本系列目录:ASP.NET MVC4入门到精通系列目录汇总 开发流程 新建Controller 创建Action 根据Action创建View 在Action获取数据并生产ActionResult传递 ...

  4. ASP.NET MVC入门到精通——第一个ASP.NET MVC程序

    开发流程 新建Controller 创建Action 根据Action创建View 在Action获取数据并生产ActionResult传递给View. View是显示数据的模板 Url请求→Cont ...

  5. 初入码田--ASP.NET MVC4 Web应用之创建一个空白的MVC应用程序

    初入码田--ASP.NET MVC4 Web应用开发之一  实现简单的登录 初入码田--ASP.NET MVC4 Web应用开发之二 实现简单的增删改查 2016-07-29 在此之前,需要一台电脑( ...

  6. ASP.NET没有魔法——开篇-用VS创建一个ASP.NET Web程序

    为什么写这一系列文章? 本系列文章基于ASP.NET MVC,在ASP.NET Core已经发布2.0版本,微服务漫天的今天为什么还写ASP.NET?. 答:虽然现在已经有ASP.NET Core并且 ...

  7. 学习ASP.NET MVC(四)——我的第一个ASP.NET MVC 实体对象

    今天我将根据数据库中的表结构添加一些类.这些类将成为这个ASP.NET MVC应用程序中“模型”的一部分.       我们使用Entity Framework(实体框架)来定义和使用这些模型类,并且 ...

  8. 学习ASP.NET MVC(六)——我的第一个ASP.NET MVC 编辑页面

    在上一文章中由Entity Framework(实体框架)去实现了对数据库的CURD操作.在本篇文章中,主要是调试修改自动生成的动作方法和视图,以及调试编辑功能与编辑功能的Book控制器. 首先,在V ...

  9. 学习ASP.NET MVC(五)——我的第一个ASP.NET MVC CURD页面

    在上一篇文章中我们已经创建了实体类,在这一篇文章中,我将创建一个新的控制器类——BookController,使用BookController对Books表中的数据进行CURD操作的方法,并使用视图模 ...

随机推荐

  1. android shader 用法

    转自 http://blog.csdn.net/abcdef314159 http://blog.csdn.net/aigestudio/article/details/41799811 Shader ...

  2. scrapy-1.2.1安装失败之解决方法

    前几天重装了win10 64位系统,安装了python-3.5,但是用pip安装scrapy模块时出现如下错误: 看起来是lxml安装的时候出错了,于是先pip install lxml,出现了和上面 ...

  3. CSS 自定义字体

    移动端如何兼容UI给的字体 [toc] 移动端的默认字体 IOS 默认中文字体是Heiti SC 默认英文字体是Helvetica 默认数字字体是HelveticaNeue Android 默认中文字 ...

  4. Python Charts库的使用

    博客园格式不太好看,可以去本人CSDN博客 http://blog.csdn.net/ashic/article/details/52598664 http://nbviewer.jupyter.or ...

  5. Java获取Web服务器文件

    Java获取Web服务器文件 如果获取的是服务器上某个目录下的有关文件,就相对比较容易,可以设定死绝对目录,但是如果不能设定死绝对目录,也不确定web服务器的安装目录,可以考虑如下两种方式: 方法一: ...

  6. 【转载】Bandits for Recommendation Systems (Part I)

    [原文链接:http://engineering.richrelevance.com/bandits-recommendation-systems/.] [本文链接:http://www.cnblog ...

  7. NPIO 导出记录

    http://www.cnblogs.com/qingyuan/archive/2012/11/08/2760034.html http://www.cnblogs.com/gaoshuai/arch ...

  8. 解决ie8(及其以下)不支持getElementsByClassName的问题

    这篇技术笔记与大家分享的是:解决IE8(及以下)不支持getElementsByClassName的方法.如果有说错的地方,麻烦留言告诉我,我及时更正,一来是更新一下我的认知,二来也是不要误导的他人, ...

  9. 彻底理解ThreadLocal一

    synchronized这类线程同步的机制可以解决多线程并发问题,在这种解决方案下,多个线程访问到的,都是同一份变量的内容.为了防止在多线程访问的过程中,可能会出现的并发错误.不得不对多个线程的访问进 ...

  10. ajax跟取后台 josn 之 josn理解

    json是一种轻量级的数据交换格式,是 JavaScript 原生格式,是理想的数据交换格式. 1.json对象json对象以“{”开始 , 以“}”结束,每个“名称”后跟一个“:”(冒号),‘名:值 ...