`

JSP复习笔记——第11章 JSP 构架和MVC设计模式

    博客分类:
  • JSP
阅读更多
11.1 JSP Model I 体系结构  
11.2 JSP Model II 体系结构/MVC设计模式
11.3 使用MVC设计模式改写用户注册程序
    11.3.1 使用serlvet实现Controller层
    11.3.2 使用jsp实现表示层
    11.3.3 使用JavaBean实现模型层
11.3.4 使用JDBC和DAO模式实现数据库层
   11.4 本章小结


JSP + DAO设计模式

使用JSP+JavaBean开发速度快,有一个问题:JSP与JavaBean之间紧密耦合在一起,会对开发及维护造成麻烦。
使用JSP+JavaBean(模式1)开发适用于一次开发完成,而且团队成员较少是使用。
JSP + Servlet + JavaBean
对于模式一JSP与JavaBean之间紧密耦合在一起

分析:
JSP优点,开发前台界面方便,做UI开发容易
Servlet优点:是JAVA程序,安全性高,性能高
Servlet缺点:显示不方便

JavaBean优点:可重复调用,需要接受用户的请求参数,进行相应的处理

问题:
JSP跳转到Servlet可以通过表单或超链接
从Servlet跳转到JSP:使用response对象

Java代码
1.<h1>MVCDEMO</h1>  
2.<!--  
3.<h1><%=request.getAttribute("name")%></h1>  
4.-->  
5.<h1><%=session.getAttribute("name")%></h1>  
6.――――――――― 
<h1>MVCDEMO</h1>
<!--
<h1><%=request.getAttribute("name")%></h1>
-->
<h1><%=session.getAttribute("name")%></h1>
―――――――――


Java代码
1.package org.sky.darkness.servlet ;  
2. 
3.import java.io.* ;  
4.import javax.servlet.* ;  
5.import javax.servlet.http.* ;  
6. 
7.public class MVCServlet extends HttpServlet  
8.{  
9.    public void doGet(HttpServletRequest req,HttpServletResponse resp) throws IOException,ServletException  
10.    {  
11.        this.doPost(req,resp) ;  
12.    }  
13.    public void doPost(HttpServletRequest req,HttpServletResponse resp) throws IOException,ServletException  
14.    {  
15.        // 要传递一个值到mvcdemo.jsp中  
16.    // 要传递的内容只使用一次  
17.    // 一个页面跳转有用,request范围  
18.    // 既然request无法传递,那就扩大范围-session  
19.        // req.setAttribute("name","darkness") ;  
20.req.getSession().setAttribute("name","darkness") ;  
21.        resp.sendRedirect("mvcdemo.jsp");  
22.    }  
23.}; 
package org.sky.darkness.servlet ;

import java.io.* ;
import javax.servlet.* ;
import javax.servlet.http.* ;

public class MVCServlet extends HttpServlet
{
public void doGet(HttpServletRequest req,HttpServletResponse resp) throws IOException,ServletException
{
this.doPost(req,resp) ;
}
public void doPost(HttpServletRequest req,HttpServletResponse resp) throws IOException,ServletException
{
// 要传递一个值到mvcdemo.jsp中
    // 要传递的内容只使用一次
    // 一个页面跳转有用,request范围
    // 既然request无法传递,那就扩大范围-session
// req.setAttribute("name","darkness") ;
req.getSession().setAttribute("name","darkness") ;
resp.sendRedirect("mvcdemo.jsp");
}
};

JSP中两种跳转语句:
四种属性范围:
现在从Servlet中要传递的值只使用一次,如果把此值存放在session范围之中,则此内容只要用户一直与服务器保持连接,则此块内存空间要一直被占用,那么性能会很低。

解决方法:RequestDispatcher接口,是用于由Servlet到JSP进行服务器端跳转的接口

Java代码
1.req.setAttribute("name","darkness") ;  
2.// 与<jsp:forward/>功能相同  
3.req.getRequestDispatcher("mvcdemo.jsp").forward(req,resp); 
req.setAttribute("name","darkness") ;
// 与<jsp:forward/>功能相同
req.getRequestDispatcher("mvcdemo.jsp").forward(req,resp);


Java代码
1.-----------------mvc_login.jsp--------------------------------------  
2.<form action="mvcdemo" method="POST">  
3.输入姓名:<input type="text" name="uname">  
4.<input type="submit" value="提交">  
5.</form> 
-----------------mvc_login.jsp--------------------------------------
<form action="mvcdemo" method="POST">
输入姓名:<input type="text" name="uname">
<input type="submit" value="提交">
</form>


Java代码
1.-----------------MVCServlet.java--------------------------------------  
2.package org.sky.darkness.servlet ;  
3. 
4.import java.io.* ;  
5.import javax.servlet.* ;  
6.import javax.servlet.http.* ;  
7.import org.sky.darkness.bean.MVCCheck ;  
8. 
9.public class MVCServlet extends HttpServlet  
10.{  
11.    public void doGet(HttpServletRequest req,HttpServletResponse resp) throws IOException,ServletException  
12.    {  
13.        this.doPost(req,resp) ;  
14.    }  
15.    public void doPost(HttpServletRequest req,HttpServletResponse resp) throws IOException,ServletException  
16.    {  
17.        String name = req.getParameter("uname") ;  
18.        MVCCheck mc = new MVCCheck() ;  
19.        // 将请求内容设置到mc对象之中  
20.        mc.setName(name) ;  
21.        String path = null ;  
22.        if(mc.isValidate())  
23.        {  
24.            // 保存名字在request范围之中  
25.            req.setAttribute("name",mc.getName()) ;  
26.            path = "mvc_success.jsp" ;  
27.        }  
28.        else 
29.        {  
30.            path = "mvc_failure.jsp" ;  
31.        }  
32.        // 进行跳转  
33.        req.getRequestDispatcher(path).forward(req,resp) ;  
34.    }  
35.};  
36./* 
37.  <servlet> 
38.    <servlet-name>mvc</servlet-name> 
39.    <servlet-class>org.sky.darkness.servlet.MVCServlet</servlet-class> 
40.  </servlet> 
41.  <servlet-mapping> 
42.    <servlet-name>mvc</servlet-name> 
43.    <url-pattern>/mvcdemo</url-pattern> 
44.  </servlet-mapping> 
45.*/ 
-----------------MVCServlet.java--------------------------------------
package org.sky.darkness.servlet ;

import java.io.* ;
import javax.servlet.* ;
import javax.servlet.http.* ;
import org.sky.darkness.bean.MVCCheck ;

public class MVCServlet extends HttpServlet
{
public void doGet(HttpServletRequest req,HttpServletResponse resp) throws IOException,ServletException
{
this.doPost(req,resp) ;
}
public void doPost(HttpServletRequest req,HttpServletResponse resp) throws IOException,ServletException
{
String name = req.getParameter("uname") ;
MVCCheck mc = new MVCCheck() ;
// 将请求内容设置到mc对象之中
mc.setName(name) ;
String path = null ;
if(mc.isValidate())
{
// 保存名字在request范围之中
req.setAttribute("name",mc.getName()) ;
path = "mvc_success.jsp" ;
}
else
{
path = "mvc_failure.jsp" ;
}
// 进行跳转
req.getRequestDispatcher(path).forward(req,resp) ;
}
};
/*
  <servlet>
<servlet-name>mvc</servlet-name>
<servlet-class>org.sky.darkness.servlet.MVCServlet</servlet-class>
  </servlet>
  <servlet-mapping>
<servlet-name>mvc</servlet-name>
<url-pattern>/mvcdemo</url-pattern>
  </servlet-mapping>
*/


Java代码
1.------------------------------------- MVCCheck.java------------------------  
2.package org.sky.darkness.bean ;   
3. 
4.public class MVCCheck  
5.{  
6.    private String name ;  
7. 
8.    public void setName(String name)  
9.    {  
10.        this.name = name ;  
11.    }  
12.    public String getName()  
13. 
14.    {  
15.        return this.name ;  
16.    }  
17.    // 验证  
18.    public boolean isValidate()  
19.    {  
20.        if(this.name==null||"".equals(this.name))  
21.        {  
22.            return false ;  
23.        }  
24.        else 
25.        {  
26.            return true ;  
27.        }  
28.    }  
29.}; 
------------------------------------- MVCCheck.java------------------------
package org.sky.darkness.bean ;

public class MVCCheck
{
private String name ;

public void setName(String name)
{
this.name = name ;
}
public String getName()

{
return this.name ;
}
// 验证
public boolean isValidate()
{
if(this.name==null||"".equals(this.name))
{
return false ;
}
else
{
return true ;
}
}
};


Java代码
1.<%@page contentType="text/html;charset=gb2312"%>  
2.<h1>输入成功!!!</h1>  
3.<h2>欢迎:<%=request.getAttribute("name")%>光临!!!</h2>  
4.<%@page contentType="text/html;charset=gb2312"%>  
5.<h1>输入失败!!!</h1>  
6.<h2><a href="mvc_login.htm">重新登陆</a></h2> 
<%@page contentType="text/html;charset=gb2312"%>
<h1>输入成功!!!</h1>
<h2>欢迎:<%=request.getAttribute("name")%>光临!!!</h2>
<%@page contentType="text/html;charset=gb2312"%>
<h1>输入失败!!!</h1>
<h2><a href="mvc_login.htm">重新登陆</a></h2>



通过以上代码可以发现:
使用MVC开发程序,代码稍微复杂
JSP与JavaBean之间没有什么特别明显的直接关系
而Servlet根据JavaBean返回的内容进行跳转

Servlet中最好只有以下几种代码:
 接收参数
 调用JavaBean
 进行跳转
 有一些简单的逻辑判断


案例-使用mvc+DAO完成用户登陆

Java代码
1.DROP TABLE person ;  
2. 
3.CREATE TABLE person   
4.(  
5.    id varchar(20) not null primary key ,  
6.    name varchar(20) not null ,  
7.    password varchar(20)   
8.) ;  
9. 
10.INSERT INTO person (id,name,password) VALUES ('sky','darkness','wind') ;  
11.INSERT INTO person (id,name,password) VALUES ('cloud','hacker','creaker') ;  
12. 
13.-- 提交事务  
14.commit ; 
DROP TABLE person ;

CREATE TABLE person
(
id varchar(20) not null primary key ,
name varchar(20) not null ,
password varchar(20)
) ;

INSERT INTO person (id,name,password) VALUES ('sky','darkness','wind') ;
INSERT INTO person (id,name,password) VALUES ('cloud','hacker','creaker') ;

-- 提交事务
commit ;



Java代码
1.-----------------login.jsp--------------------------------------------------------------------  
2.<%@page contentType="text/html;charset=gb2312"%>  
3.<%@page import="java.util.*"%>  
4.<html>  
5.<head>  
6.    <title>登陆</title>  
7.</head>  
8.<body>  
9.<center>  
10.    <h1>登陆范例——MVC实现</h1>  
11.    <hr>  
12.    <br>  
13.    <br>  
14.    <!-- 加入更加详细的错误提示 -->  
15.    <%  
16.        if(request.getAttribute("errors")!=null)  
17.        {  
18.            // 有错误,要进行打印输出  
19.            List all = (List)request.getAttribute("errors") ;  
20.            Iterator iter = all.iterator() ;  
21.            while(iter.hasNext())  
22.            {  
23.    %>  
24.                <li><%=iter.next()%>  
25.    <%  
26.            }  
27.        }  
28.    %>  
29.      
30.    <form action="LoginServlet" method="post">  
31.    <table>  
32.        <tr>  
33.            <td colspan="2">用户登陆</td>  
34.        </tr>  
35.        <tr>  
36.            <td>用户名:</td>  
37.            <td><input type="text" name="id" value="${person.id}"></td>  
38.        </tr>  
39.        <tr>  
40.            <td>密&nbsp;&nbsp;码:</td>  
41.            <td><input type="password" name="password" value="${person.password}"></td>  
42.        </tr>  
43.        <tr>  
44.            <td colspan="2">  
45.            <input type="submit" value="登陆">  
46.            <input type="reset" value="重置">  
47.            </td>  
48.        </tr>  
49.    </table>  
50.    </form>  
51.</center>  
52.</body>  
53.</html>  
54.-------------------------LoginServlet.java---------------------------------------------  
55.// 建立MVC中的C,完成JSP+Servlet+JavaBean的开发模式  
56. 
57.package org.sky.darkness.servlet ;  
58. 
59.import java.io.* ;  
60.import java.util.* ;  
61.import javax.servlet.* ;  
62.import javax.servlet.http.* ;  
63.import org.sky.darkness.factory.* ;  
64.import org.sky.darkness.vo.* ;  
65. 
66.public class LoginServlet extends HttpServlet  
67.{  
68.    public void doGet(HttpServletRequest request,HttpServletResponse response) throws IOException,ServletException  
69.    {  
70.        this.doPost(request,response) ;  
71.    }  
72.    public void doPost(HttpServletRequest request,HttpServletResponse response) throws IOException,ServletException  
73.    {  
74.        // 声明一个集合类,用于保存错误信息  
75.        List errors = new ArrayList() ;  
76.        // 完成登陆验证,替换掉login_conf.jsp  
77.        String path = "login.jsp" ;  
78.        // 1、接收请求内容  
79.        String id = request.getParameter("id") ;  
80.        String password = request.getParameter("password") ;  
81.        // 2、进行数据合法性验证,包括是否为空,长度是否满足等  
82.        // 要将接收到的内容设置给PersonVO对象  
83.        PersonVo pv = new PersonVo() ;  
84.        pv.setId(id) ;  
85.        pv.setPassword(password) ;  
86.        pv.setErrors(errors) ;  
87.        // 3、如果合法,则进行数据库验证  
88.        if(pv.invalidate())  
89.        {  
90.            // 数据合法,可以进行数据库验证  
91.            if(DAOFactory.getPersonDAOInstance().isLogin(pv))  
92.            {  
93.                // 用户ID、密码合法  
94.                // 修改跳转路径  
95.                // 保存用户名到request范围之中  
96.                // request.setAttribute("name",pv.getName()) ;  
97.                path = "login_success.jsp" ;  
98.            }  
99.            else 
100.            {  
101.                // 用户ID、密码非法  
102.                errors.add("错误的用户ID及密码!") ;  
103.            }  
104.        }  
105.        // 将错误信息保存  
106.        request.setAttribute("errors",errors) ;  
107.        request.setAttribute("person",pv) ;  
108.        request.getRequestDispatcher(path).forward(request,response) ;  
109.    }  
110.};  
111.-------------------------login_success.jsp---------------------------  
112.<%@page contentType="text/html;charset=gb2312"%>  
113.<html>  
114.<head>  
115.    <title>登陆</title>  
116.</head>  
117.<body>  
118.<center>  
119.    <h1>登陆范例——MVC实现</h1>  
120.    <hr>  
121.    <br>  
122.    <br>  
123.    <h2>登陆成功</h2>  
124.    <h3>欢迎<font color="red" size="15">  
125.        ${person.name}  
126.    </font>光临!!!</h3>  
127.</center>  
128.</body>  
129.</html>  
130.-----------------------------PersonVo.java---------------------  
131.// 只包含setter和getter方法的类  
132. 
133.package org.sky.darkness.vo ;  
134. 
135.import java.util.* ;  
136.public class PersonVo  
137.{  
138.    // 表中所有字段  
139.    private String id ;  
140.    private String name ;  
141.    private String password ;  
142.    // 此属性用于保存全部错误信息  
143.    private List errors ;  
144. 
145.    public boolean invalidate()  
146.    {  
147.        boolean flag = true ;  
148.        // 验证ID  
149.        if(this.id==null||"".equals(this.id))  
150.        {  
151.            flag = false ;  
152.            errors.add("ID不能为空!") ;  
153.        }  
154.        else 
155.        {  
156.            // 进行长度验证:3~10位  
157.            if(this.id.length()<3||this.id.length()>10)  
158.            {  
159.                flag = false ;  
160.                errors.add("ID的长度应为3~10位!") ;  
161.            }  
162.        }  
163.        // 验证密码  
164.        if(this.password==null||"".equals(this.password))  
165.        {  
166.            flag = false ;  
167.            errors.add("密码不能为空!") ;  
168.        }  
169.        else 
170.        {  
171.            // 进行长度验证:3~10位  
172.            if(this.password.length()<3||this.password.length()>10)  
173.            {  
174.                flag = false ;  
175.                errors.add("密码的长度应为3~10位!") ;  
176.            }  
177.        }  
178.        return flag ;  
179.    }  
180. 
181.    public void setErrors(List errors)  
182.    {  
183.        this.errors = errors ;  
184.    }  
185.    public List getErrors()  
186.    {  
187.        return this.errors ;  
188.    }  
189. 
190.    // 生成getter和setter方法  
191.    public void setId(String id)  
192.    {  
193.        this.id = id ;  
194.    }  
195.    public void setName(String name)  
196.    {  
197.        this.name = name ;  
198.    }  
199.    public void setPassword(String password)  
200.    {  
201.        this.password = password ;  
202.    }  
203.    public String getId()  
204.    {  
205.        return this.id ;  
206.    }  
207.    public String getName()  
208.    {  
209.        return this.name ;  
210.    }  
211.    public String getPassword()  
212.    {  
213.        return this.password ;  
214.    }  
215.};  
216.----------------------------------PersonDAO.java----------------------  
217.// 本接口定义本项目中所操作person表的全部方法  
218. 
219.package org.sky.darkness.dao ;  
220. 
221.// 使用PersonVo类  
222.import org.sky.darkness.vo.* ;  
223. 
224.public interface PersonDAO  
225.{  
226.    // 需要一个登陆验证的方法  
227.    public boolean isLogin(PersonVo pv) ;  
228.}  
229.---------------------PersonDAOImpl.java---------------------------------  
230.// 具体实现DAO接口的类  
231. 
232.package org.sky.darkness.daoimpl ;  
233. 
234.// 需要连接数据库  
235.// 需要对VO的内容进行具体的验证  
236.import java.sql.* ;  
237.import org.sky.darkness.dao.* ;  
238.import org.sky.darkness.dbc.* ;  
239.import org.sky.darkness.vo.* ;  
240. 
241.public class PersonDAOImpl implements PersonDAO  
242.{  
243.    public boolean isLogin(PersonVo pv)  
244.    {  
245.        boolean flag = false ;  
246.        // 在此处成具体的数据库验证  
247. 
248.        // 声明一个数据库操作对象  
249.        PreparedStatement pstmt = null ;  
250.        // 声明一个结果集对象  
251.        ResultSet rs            = null ;  
252.        // 声明一个SQL变量,用于保存SQL语句  
253.        String sql              = null ;  
254.        // DataBaseConnection为具体的数据库连接及关闭操作类  
255.        DataBaseConnection dbc  = null ;  
256.        // 连接数据库  
257.        dbc = new DataBaseConnection() ;  
258. 
259.        // 编写SQL语句  
260.        sql = "SELECT name FROM person WHERE id=? and password=?" ;  
261.        try 
262.        {             
263.            // 实例化数据库操作对象  
264.            pstmt = dbc.getConnection().prepareStatement(sql) ;  
265. 
266.            // 设置pstmt的内容,是按ID和密码验证  
267.            pstmt.setString(1,pv.getId()) ;  
268.            pstmt.setString(2,pv.getPassword()) ;  
269. 
270.            // 查询记录  
271.            rs = pstmt.executeQuery() ;  
272.            // 判断是否有记录  
273.            if(rs.next())  
274.            {  
275.                // 如果有记录,则执行此段代码  
276.                // 用户是合法的,可以登陆  
277.                flag = true ;  
278.                pv.setName(rs.getString(1)) ;  
279.            }  
280.            // 依次关闭  
281.            rs.close() ;  
282.            pstmt.close() ;  
283.        }  
284.        catch(Exception e)  
285.        {  
286.            System.out.println(e) ;  
287.        }  
288.        finally 
289.        {  
290.            // 最后一定要保证数据库已被关闭  
291.            dbc.close() ;  
292.        }  
293.        return flag ;  
294.    }  
295.};  
296.-------------------------DAOFactory.java---------------------  
297.// 取得DAO实例的工厂类  
298. 
299.package org.sky.darkness.factory ;  
300. 
301.import org.sky.darkness.dao.* ;  
302.import org.sky.darkness.daoimpl.* ;  
303. 
304.public class DAOFactory  
305.{  
306.    public static PersonDAO getPersonDAOInstance()  
307.    {  
308.        return new PersonDAOImpl() ;  
309.    }  
310.};  
311.---------------------DataBaseConnection.java------------------  
312.// 本类只用于数据库连接及关闭操作  
313.package org.sky.darkness.dbc ;  
314. 
315.import java.sql.* ;  
316. 
317.public class DataBaseConnection  
318.{  
319.    // 属性  
320.    // 定义数据库操作的常量、对象  
321.    // 数据库驱动程序  
322.    private final String DBDRIVER   = "oracle.jdbc.driver.OracleDriver" ;  
323.    // 数据库连接地址  
324.    private final String DBURL      = "jdbc:oracle:thin:@localhost:1521:sky" ;  
325.    // 数据库用户名  
326.    private final String DBUSER     = "scott" ;  
327.    // 数据库连接密码  
328.    private final String DBPASSWORD = "tiger" ;  
329.    // 声明一个数据库连接对象  
330.    private Connection conn         = null ;  
331. 
332.    // 在构造方法之中连接数据库  
333.    public DataBaseConnection()  
334.    {  
335.        try 
336.        {  
337.            // 加载驱动程序  
338.            Class.forName(DBDRIVER) ;   
339.            // 连接数据库  
340.            conn = DriverManager.getConnection(DBURL,DBUSER,DBPASSWORD) ;     
341.        }  
342.        catch (Exception e)  
343.        {  
344.            System.out.println(e) ;  
345.        }  
346.    }  
347. 
348.    // 返回一个数据库连接  
349.    public Connection getConnection()  
350.    {  
351.        /// 返回连接对象  
352.        return this.conn ;  
353.    }  
354. 
355.    // 关闭数据库连接  
356.    public void close()  
357.    {  
358.        try 
359.        {  
360.            this.conn.close() ;           
361.        }  
362.        catch (Exception e)  
363.        {  
364.        }  
365.    }  
366.}; 
分享到:
评论

相关推荐

Global site tag (gtag.js) - Google Analytics