不拖控件ASP.NET——NVelocity(2)

    上节课我们讲述了NVelocity的简单应用,但是没有和数据库打交道,这次我们来和数据库连接实现人员的增删改查。

  1.      上篇博客回顾

    链接:http://blog.csdn.net/u010955843/article/details/42528761

    开讲之前,我们先来回顾上一节课讲的内容,主要是两个页面,一个是一般处理程序的页面,另一个是渲染后的模板。

    ?  机制

    上篇博客中我们建立一个person类,并且在一般处理程序中对其进行了赋值,之后交给了模板(html)进行数据填充,渲染成html页,之后生成的纯html文本返回给一般处理程序将,一般处理程序将其返回给浏览器进行解析,并且显示。     

    ?  好处

    实现了数据和逻辑和界面的分离:数据给了模板(一般由html担当),最后一般处理程序拿到渲染html进行输出;模板不管数据来源,只是知道表格中需要设置几行几列;一般处理程序只是取数据,传给模板,不管模板会把数据渲染成什么样子的,也就是各自只是负责自己的那一块就可以了

  2.      与数据库连接实现人员增删改查

    上节课我们只是在一般处理程序中写的数据源对象,那么在传统web开发NVelocity如何数据库进行交互的呢,我们先来介绍程序编写的步骤。

    ?  建立数据库并且建表

     可以自己定,我们的库为CRUDTest,表明为Persons

技术分享

    设置Id为自增的,我们可以手动输入几条记录

    ?  CommonHelper

    和上次一样,我们首先下载NVelocity的DLL,之后将其添加到建立的相应项目下,直接拖进项目下面即可,之后添加对它的引用即可。

    上次我们是将模板写在一个一般处理程序中,但是我们知道这样的只是适用一个或者少数的处理程序,要是想要达到模板的复用或者方便的使用,我们可以将其进行封装,放到一个类中即可,这样实现了方法的复用。

    我们知道这里只是有两个参数不一样,即将渲染的模板,另一个是将要填充模板的文件或者数据。

    具体代码如下:

<strong><span style="font-family:Microsoft YaHei;font-size:14px;">using NVelocity;
using NVelocity.App;
using NVelocity.Runtime;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;

//using NVelocity;using NVelocity.App;using NVelocity.Runtime;必须引入的
//这个类用于封装Nvelocity模板的渲染
namespace yinqingmuban
{
    public class commonHelper
    {
        /// <summary>
        /// 用data数据填充templateName模板,渲染生成html返回
        /// </summary>
        /// <param name="templateName">模板名字</param>
        /// <param name="data">填充模板数据</param>
        /// <returns></returns>
        public static string RenderHtml(string templateName, object data)
        {
            VelocityEngine vltEngine = new VelocityEngine();
            vltEngine.SetProperty(RuntimeConstants.RESOURCE_LOADER, "file");
            vltEngine.SetProperty(RuntimeConstants.FILE_RESOURCE_LOADER_PATH, System.Web.Hosting.HostingEnvironment.MapPath("~/templates"));//模板文件所在的文件夹,我们遵从上次讲的我们还是放在templates这个文件夹中,自己也可以新建别的名字的
            vltEngine.Init(); //引擎初始化

            VelocityContext vltContext = new VelocityContext(); 
            vltContext.Put("Data", data);//设置参数,在模板中可以通过$data来引用

            Template vltTemplate = vltEngine.GetTemplate(templateName);//渲染的html模板
            System.IO.StringWriter vltWriter = new System.IO.StringWriter();
            vltTemplate.Merge(vltContext, vltWriter);

            string html = vltWriter.GetStringBuilder().ToString();
            return html;
        }
    }
}</span></strong>

    ?  Sqlhelper

    相信大家都学过三层,这里不再做过多的介绍。封装了一系列的增删改查的方法,并且建立了数据库的里连接。这里不再展示了

    ?  配置文件

    用于配置连接数据库的字符串,这样便于我们灵活更换数据库,而不用于更改代码内部。

<strong><span style="font-family:Microsoft YaHei;font-size:14px;"><connectionStrings>
  <add name="conStr" connectionString="data source=.;database=CRUDTest;uid=sa;pwd=123456;"/>
</connectionStrings></span></strong>

    ?  人员显示的一般处理程序(personlist.ashx)

这里主要是读取数据,然后把它渲染到html页上进行输出。

<strong><span style="font-family:Microsoft YaHei;font-size:14px;">using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Data;

namespace yinqingmuban
{
    /// <summary>
    /// personlist 的摘要说明
    /// </summary>
    public class personlist : IHttpHandler
    {

        public void ProcessRequest(HttpContext context)
        {
            context.Response.ContentType = "text/html";
            //context.Response.Write("Hello World");
            DataTable dt = sqlHelper.ExecuteDataTable("select * from Persons");
            //DataTable不是集合,所以无法foreach遍历,DataTable的Rows属性
            //代表表格中的数据行的集合(DataRow的集合),一般传递DataRowCollection
            //给模板方便遍历
            string html = commonHelper.RenderHtml("personlist.html", dt.Rows);

            context.Response.Write(html);
        }

        public bool IsReusable
        {
            get
            {
                return false;
            }
        }
    }
}</span></strong>

    ?  建立人员列表的渲染模板(personlist.html)

<strong><span style="font-family:Microsoft YaHei;font-size:14px;"><!DOCTYPE html>
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8"/>
    <title></title>
</head>
<body>
    <!-- 人员的操作处理,增删改查 -->
    <a href="personEdit.ashx?Action=AddNew">新增人员</a>
    <!--//变量data中的每一行,并且输入每一行中的每一列的字段值-->
    <table>
        <thead>
            <tr><td>删除</td><td>编辑</td><td>姓名</td><td>年龄</td><td>邮箱</td></tr>
        </thead>
        <tbody>
            #foreach($person in $Data)
            <tr><td><a href="personEdit.ashx?Action=Delete&Id=$person.Id">删除</a></td><td><a href="personEdit.ashx?Action=Edit&Id=$person.Id">编辑</a></td><td>$person.Name</td><td>$person.Age</td><td>$person.Email</td></tr>
            #end
        </tbody>
    </table>
</body>
</html>
</span></strong>

    ?  对列表进行增删改(personEdit.ashx)

<strong><span style="font-family:Microsoft YaHei;font-size:14px;">using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Data.SqlClient;
using System.Data;
namespace yinqingmuban
{
    /// <summary>
    /// personEdit 的摘要说明
    /// </summary>
    public class personEdit : IHttpHandler
    {

        public void ProcessRequest(HttpContext context)
        {
            context.Response.ContentType = "text/html";
            //PersonEdit.ashx?action=AddNew
            //PersonEdit.ashx?action=Edit&Id=3
            string action = context.Request["action"];
            if (action == "AddNew")
            {
                //判断是否含有Save并且等于true,如果是的话就说明是点击【保存】按钮请求来的
                bool save = Convert.ToBoolean(context.Request["Save"]);
                if (save)//是保存
                {
                    string name = context.Request["Name"];
                    int age = Convert.ToInt32(context.Request["Age"]);
                    string email = context.Request["Email"];
                   
                    sqlHelper.ExecuteNonQuery("Insert into Persons(Name,Age,Email) values(@Name,@Age,@Email)", new SqlParameter("@Name", name)
                        , new SqlParameter("@Age", age)
                        , new SqlParameter("@Email", email));
                    context.Response.Redirect("personlist.ashx");//保存成功返回列表页面
                }
                else
                {
                    //string html = CommonHelper.RenderHtml("PersonEdit.htm", new { Name = "", Age = 20, Email = "@rupeng.com" });
                    //定义匿名对象  Action可能与数据库中字段重复,建议分开,相关和无关的字段;New一个匿名类型,等于在一个匿名类中又创建一个匿名类,
                    var data = new { Action = "AddNew", Person = new { Name = "", Age = 20, Email = "@rupeng.com" } };
                    //进行渲染  
                    string html = commonHelper.RenderHtml("personEdit.html", data);
                    context.Response.Write(html);
                }
            }
            else if (action == "Edit")
            {
                //判断是否含有Save并且等于True,如果是的话说明点击了保存按钮  
                bool save = Convert.ToBoolean(context.Request["Save"]);
                if (save)
                {
                    //所有的信息服务器端尽量不要记,尽量通过客户端传递  
                    //服务器是一个健忘症(无状态),服务器只认识Request中的信息  
                    long id = Convert.ToInt64(context.Request["Id"]);
                    string name = context.Request["Name"];
                    int age = Convert.ToInt32(context.Request["Age"]);
                    string email = context.Request["Email"];
                    sqlHelper.ExecuteNonQuery("update Persons set Name=@Name,Age=@Age,Email=@Email where Id=@Id", new SqlParameter("@Id", id), new SqlParameter("@Name", name), new SqlParameter("@Age", age), new SqlParameter("@Email", email));
                    context.Response.Redirect("personlist.ashx");
                }
                else
                {
                    long id = Convert.ToInt64(context.Request["Id"]);
                    DataTable dt = sqlHelper.ExecuteDataTable("select * from Persons where Id=@Id", new SqlParameter("@Id", id));
                    if (dt.Rows.Count <= 0)
                    {
                        context.Response.Write("没有找到Id=" + id + "的数据");
                    }
                    else if (dt.Rows.Count > 1)
                    {
                        context.Response.Write("找到多条Id=" + id + "的数据");
                    }
                    else
                    {
                        DataRow row = dt.Rows[0];
                        var data = new { Action = "Edit", Person = row };
                        string html = commonHelper.RenderHtml("personEdit.html", data);
                        context.Response.Write(html);
                    }
                }  
     
            }
            else if (action == "Delete")  
            {  
                long id = Convert.ToInt64(context.Request["Id"]);  
                sqlHelper.ExecuteNonQuery("delete from Persons where Id=@Id", new SqlParameter("@Id",id));  
                context.Response.Redirect("personlist.ashx");  
             }  
            else   
            {  
                context.Response.Write("Action参数错误!");  
            }  

           
            }

        public bool IsReusable
        {
            get
            {
                return false;
            }
        }
    }
}</span></strong>

?  建立人员增删改的渲染模板(personEdit.html)

<strong><span style="font-family:Microsoft YaHei;font-size:14px;"><!DOCTYPE html>
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8"/>
    <title>
        #if($Data.Action=="AddNew")
        新增用户
        #else
        编辑用户$Data.Person.Name
        #end
    </title>
    
</head>
<body>
    <form action="personEdit.ashx" method="post">
        <!--<input type="hidden" name="Action" value="AddNew" />-->
        <input type="hidden" name="Action" value="$Data.Action" />
        <input type="hidden" name="Save" value="true" />
        #if($Data.Action=="Edit")
        <input type="hidden" name="Id" value="$Data.Person.Id" />
        #end

        <table style="background-color:blueviolet">
            <tr><td>姓名:</td><td><input type="text" name="Name" value="$Data.Person.Name" /></td></tr>
            <tr><td>年龄:</td><td><input type="text" name="Age" value="$Data.Person.Age" /></td></tr>
            <tr><td>邮箱:</td><td><input type="text" name="Email" value="$Data.Person.Email" /></td></tr>
            <tr><td></td><td><input type="submit" value="保存" /></td></tr>
        </table>
    </form>
</body>
</html>
</span></strong>

    ?  效果

    列表显示
技术分享
    点击新增人员
技术分享
    点击编辑
技术分享

    通过隐藏字段来实现想要的结果,在实现增删改的页面我们用了隐藏字段,隐藏字段是服务器端控件,这样我们在服务器端可以通过隐藏字段的name来获得其相应的值,主要是因为关于一些操作这些是不要用户可以看到的,只是程序需要看到,故而做成了隐藏字段。

    至此我们就实现与数据库的交互,出现的效果自己可以写写代码看一下啊。

  3.      总结

    这样总算完美了,不然总是觉得少了些什么,自己最近时间紧,一直没有写这篇与数据库交互的博客,在mvc中同样存在一个引擎Razor,我们称之为视图引擎,希望在这篇博客的基础能够激起你对引擎探究的好奇心,自己去看看和研究吧,相信你会感兴趣的。


郑重声明:本站内容如果来自互联网及其他传播媒体,其版权均属原媒体及文章作者所有。转载目的在于传递更多信息及用于网络分享,并不代表本站赞同其观点和对其真实性负责,也不构成任何其他建议。