sakrua`s java 世界
struts hibernate spring web2.0 ajax
posts - 0,  comments - 0,  trackbacks - 0

Struts 的MVC

1.Model 1 和Model 2简介

我们在开发Web应用时经常提到的一个概念是Model 1/Model 2,那么到底它是什么意思呢?其实它是对采用JSP技术构成Web应用的不同模型的描述。下面对这个概念做一个简单的介绍。

Model 1

在使用JAVA技术建立Web应用的实例中,由于JSP技术的发展,很快这种便于掌握和可实现快速开发的技术就成了创建Web应用的主要技术。JSP页面中可以非常容易地结合业务逻辑(jsp:useBean)、服务端处理过程(jsp:scriplet)和HTML(<html>),在JSP页面中同时实现显示,业务逻辑和流程控制,从而可以快速地完成应用开发。现在很多的Web应用就是由一组JSP页面构成的。这种以JSP为中心的开发模型我们可以称之为Model 1。

当然这种开发模式在进行快速和小规模的应用开发时,是有非常大的优势,但是从工程化的角度考虑,它也有一些不足之处:

1. 应用的实现一般是基于过程的,一组JSP页面实现一个业务流程,如果要进行改动,必须在多个地方进行修改。这样非常不利于应用扩展和更新。

2. 由于应用不是建立在模块上的, 业务逻辑和表示逻辑混合在JSP页面中没有进行抽象和分离。所以非常不利于应用系统业务的重用和改动。

考虑到这些问题在开发大型的Web应用时必须采用不同的设计模式――这就是Model2

Model 2

Model 2 表示的是基于MVC模式的框架。MVC是Model-View-Controller的简写。"Model" 代表的是应用的业务逻辑(通过JavaBean,EJB组件实现), "View" 是应用的表示面(由JSP页面产生),"Controller" 是提供应用的处理过程控制(一般是一个Servlet),通过这种设计模型把应用逻辑,处理过程和显示逻辑分成不同的组件实现。这些组件可以进行交互和重用。从而弥补了Model 1的不足。

Model 2具有组件化的优点从而更易于实现对大规模系统的开发和管理,但是开发MVC系统比简单的JSP开发要复杂许多,它需要更多的时间学习和掌握。

1. 必须基于MVC组件的方式重新思考和设计应用结构。原来通过建立一个简单的JSP页面就能实现的应用现在变成了多个步骤的设计和实现过程。

2. 所有的页面和组件必须在MVC框架中实现,所以必须进行附加地开发工作。

在开始讲struts 前,我们先了解一下servlet 为什么要看servlet 看到最后就知道了

1、 环境的搭建就pass了

2、 open eclipse and follow me

create new project

clip_image002[5]

新建一个Dynamic Web Project named servlet_Test_project

clip_image0045

clip_image0065

我用的是jdk1.6

接着next ….next完成

转到PackageExplor 我们看一下project 的目录结构

clip_image008[4]

两个jar的环境

clip_image010[4]

源文件目录

clip_image012[4]

输出目录,也就是class的目录了(不多说了,不知道class是什么,学j2se吧)

clip_image014[4]

Web目录

clip_image016[4]

其中jsp等文件放在WebContent目录内(下面两个Web-INF、META-INF除外)

Lib目录为我们工程中用到的jar包的目录

下面为Projct explor下看到的目录结构,我们可以看看他的不同

clip_image018[7]

好,少来费话,新建一个servlet 先

clip_image020[7]

下面看图

clip_image022[5]

包名为sakrua ,lass名为ServletHelloWorld,Superclass 为javax.servlet.http.HttpServlet

只有javax.servlet.http.HttpServlet这个父类吧,到下面再说

接着 你可以点完成,我们next看看有什么

clip_image0244

呵呵 ,好像没有什么,我们点完成(是finish 不要告诉我找不到完成,clip_image026[6]

好,eclipse 为我们已经完成了大部分的代码了,不过我们先不看代码先(习惯先在后了)

我们再看看 Projct explor 有什么不同,不要让我说了,自己能看到的clip_image026[7]

clip_image028[4]

其实这是web.xml文件中的内容,我们去 see see

<?xml version="1.0" encoding="UTF-8"?>
<web-app id="WebApp_ID" version="2.4" xmlns="http://java.sun.com/xml/ns/j2ee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/j2ee http://java.sun.com/xml/ns/j2ee/web-app_2_4.xsd">   
    <display-name>servlet_Test_project</display-name>
    <!--servlet 的-->
    <servlet>
        <description>sakrua 的第一个servlet</description>
        <display-name>ServletHelloWorld</display-name>
        <!-- servlet的名字 -->
        <servlet-name>ServletHelloWorld</servlet-name>
        <!-- servlet 类 -->
        <servlet-class>sakrua.ServletHelloWorld</servlet-class>
    </servlet>
    <servlet-mapping>
        <!-- 跟上面对应的 -->
        <servlet-name>ServletHelloWorld</servlet-name>
        <!-- ie中输入的访问路径 -->
        <url-pattern>/ServletHelloWorld</url-pattern>
    </servlet-mapping>
    <!-- servlet 的 -->
    <!-- 其它的先不理 -->
    <welcome-file-list>
        <welcome-file>index.html</welcome-file>
        <welcome-file>index.htm</welcome-file>
        <welcome-file>index.jsp</welcome-file>
        <welcome-file>default.html</welcome-file>
        <welcome-file>default.htm</welcome-file>
        <welcome-file>default.jsp</welcome-file>
    </welcome-file-list>
</web-app>

应该中国人都看得明

下面我们去看看Servlet 的代码

package sakrua;

import java.io.IOException;
import java.io.PrintWriter;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

 public class ServletHelloWorld extends javax.servlet.http.HttpServlet implements javax.servlet.Servlet {
   static final long serialVersionUID = 1L;
    public ServletHelloWorld() {
        super();
    }      
    protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
    }     
    protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
    }      
}

好我们加点东西上去看看

package sakrua;

import java.io.IOException;
import java.io.PrintWriter;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

 public class ServletHelloWorld extends javax.servlet.http.HttpServlet implements javax.servlet.Servlet {
   static final long serialVersionUID = 1L;
    public ServletHelloWorld() {
        super();
    }      
    protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {

PrintWriter out = response.getWriter();
out.println("<html><head><title>servlet Example by sakrua </title></head><body>");
out.println("<h3><font color=red>servlet is here</font></h3>");
out.println("</body></html>");


    }     
    protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
    }
    public void destroy() {
        System.out.println("It is destroy");
        super.destroy();
    }
    public void init() throws ServletException {
        System.out.println("It is started");
        super.init();
    }                
}

右键选择

clip_image030[4]

在ie看到

clip_image032[4]

Ok !

下面我们具体说一下

Servlet是一个接口,位于 javax.servlet.Servlet,它规定了每个Servlet所必须实现的方法。实际应用时我们需要从 javax.servlet.GenericServlet 和 javax.servlet.http.HttpServlet 两个抽象类继承出自己的Servlet类,并实现所需的功能。这几个类的关系如下(绿色斜体字为抽象类):

clip_image034[4]

上图中,Servlet依赖于ServletRequest和ServletResponse接口,这两个接口负责为Servlet接受和发送信息。 HttpServlet也类似。

Servlet接口

javax.servlet.Servlet接口包含以下的方法:

init()

void init(ServletConfig config) throws ServletException

init方法用于初始化,在Servlet启动时调用。

service()

void service(ServletRequest req, ServiceResponse res) throws ServletException, IOException

Servlet通过这个方法,从req获得客户端请求,处理并生成结果,再通过res发送给客户端。

destroy()

void destroy()

Servlet销毁时执行的方法。

getServletInfo()

String getServletInfo()

将Servlet的信息通过字符串返回。

getServletConfig()

ServletConfig getServletConfig()

获取包含Servlet各种信息的ServletConfig对象。

当某个Servlet第一次被请求时,服务器(Servlet容器)会生成该Servlet并调用它的init()方法,再调用其service()方法处理请求。处理结束后该Servlet会常驻于容器中,下一个请求则不再重新生成Servlet,而是直接调用常驻的Servlet对象的service()方法。服务器停止时,会调用该Servlet的destroy()方法。

因此,在Servlet的一个生命周期中,init()和destroy()仅会被调用一次,而service()则会被调用多次。

―――

好我们又看看这样

package sakrua;

import java.io.IOException;
import java.io.PrintWriter;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

 public class ServletHelloWorld extends javax.servlet.http.HttpServlet implements javax.servlet.Servlet {
   static final long serialVersionUID = 1L;
    public ServletHelloWorld() {
        super();
    }      
    protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        PrintWriter out = response.getWriter();
        out.println("<html><head><title>servlet Example by sakrua </title></head><body>");
        out.println("<h3><font color=red>这就是Servlet 呵呵!</font></h3>");
        out.println("</body></html>");
    }     
    protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
    }
    public void destroy() {
        System.out.println("It is destroy");
        super.destroy();
    }
    public void init() throws ServletException {
        System.out.println("It is started");
        super.init();
    }                
}

看看控制台,所有都ok(close 后才会看到 Is is Destroy)

再看看ie,乱码了!晕

―――

GenericServlet抽象类

javax.servlet.GenericServlet为我们实现了Servlet接口的大部分方法,除了service()方法之外。因此,我们在制作自己的Servlet时,只需要继承GenericServlet并重载service()方法即可。

HttpServlet

HttpServlet继承了GenericServlet,不过它也是一个抽象类,不能直接使用,只能继承它。

HttpServlet中常用的方法有两个:

doGet

void doGet(HttpServletRequest req, HttpServletResponse res) throws ServletException, IOException

当浏览器用GET方式访问时,该方法被调用。

doPost

void doPost(HttpServletRequest req, HttpServletResponse res) throws ServletException, IOException

当浏览器用POST方式访问时,该方法被调用。

这两个函数内部的处理方法基本上与上一节介绍的GenericServlet.service()函数相同。

另外其他的HTTP请求也都有相应的方法:

HTTP请求类别

HttpServlet的方法

GET

doGet()

POST

doPost()

HEAD

doHead()

PUT

doPut()

DELETE

doDelete()

HttpServletRequest

doGet()和doPost()函数的两个参数为 HttpServletRequest和HttpServletResponse对象。

HttpServletRequest接口表示浏览器请求,你可以通过这个类获取浏览器发送到服务器的任何信息。

getParameter

String getParameter(String name)

获取指定变量名name所对应的参数值。该方法实际上为父接口 javax.servlet.ServletRequest的方法。如果是GET请求则获取查询字符串后的参数,POST请求则获取<form>表单中的参数。类似于PHP的$_GET和$_POST数组。

getParameterValues

String[] getParameterValues(String name)

这个方法与getParameter()类似。当你要获取<input type="check">这类会返回多个值的表单属性时,就应当用这个方法。

getMethod

String getMethod()

返回字符串"GET"或"POST"。

getRequestURI

String getRequestURI()

获取请求的URI(不包括查询字符串)。相当于PHP的$_SERVER['REQUEST_URI']。

getServletPath

String getServletPath()

获取Servlet的路径。相当于PHP的$_SERVER['PHP_SELF']。

getPathInfo

String getPathInfo()

获取PathInfo。相当于PHP的$_SERVER['PATH_INFO']。

setCharacterEncoding

void setCharacterEncoding(String new)

设置请求的编码。需要处理汉字时务必要通过该方法设置正确的字符编码,否则将无法正确读取浏览器发过来的文字。

还有好多有用的方法大家可以自己去参考接口文档。

HttpServletResponse

HttpServletResponse接口则用于控制服务器发送给客户端的内容,相当于PHP的echo、header等函数。

setContentType

void setContentType(String type)

设置返回值的类型。通常的HTML内容可设置为"text/html; charset=UTF-8"等,而动态生成的图片则可以设置为"image/gif"等。输出汉字之前,务必要通过该方法指定输出的字符编码。相当于在PHP中写 header("Content-Type: image/gif")。

ServletOutputStream

ServletOutputStream getOutputStream() throws IOException

向客户端发送二进制数据时,需要通过此方法获取输出流。

getWriter

PrintWriter getWriter() throws IOException

向客户端发送文本数据时,需要通过此方法获取输出流。

看到这里应该知道为什么乱码了吧

加上这两句

response.setCharacterEncoding("GBK");

response.setContentType("text/html; charset=GBK");

几乎所有的Web开发语言都支持Session功能,Servlet也不例外。 Servlet/JSP中的Session功能是通过作用域(scope)这个概念来实现的。

作用域分为四种,分别为:

page

在当前页面有效(仅用于JSP中)

request

在当前请求中有效

session

在当前会话中有效

application

在所有应用程序中有效

好,servlet 讲完了,为什么要讲这个呢,我们在以后才会体会到

会到Struts 中,现在,struts 有两个版本 struts 1.x 和struts 2.x , 2 .x 是webwork 的化身,我们现在讲的是1.x .现在来一个struts 的hello world

新建一个同样的工程(如果用myeclipse 有点不一样)

clip_image036[4]

把struts 的这些包copy到lib目录中

下面是step by step

1、修改web.xml文件

<?xml version="1.0" encoding="UTF-8"?>
<web-app id="WebApp_ID" version="2.4" xmlns="http://java.sun.com/xml/ns/j2ee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/j2ee http://java.sun.com/xml/ns/j2ee/web-app_2_4.xsd">
    <display-name>Struts_HelloWorld by sakrua</display-name>
    <!-- the struts config -->
    <servlet>
        <servlet-name>action</servlet-name>
        <servlet-class>org.apache.struts.action.ActionServlet</servlet-class>
        <init-param>
            <param-name>config</param-name>
            <param-value>/WEB-INF/struts-config.xml</param-value>
        </init-param>
        <load-on-startup>2</load-on-startup>
    </servlet>

    <!-- Standard Action Servlet Mapping -->
    <servlet-mapping>
        <servlet-name>action</servlet-name>
        <url-pattern>*.do</url-pattern>
    </servlet-mapping>
    <!-- end struts config -->
    <welcome-file-list>
        <welcome-file>index.html</welcome-file>
        <welcome-file>index.htm</welcome-file>
        <welcome-file>index.jsp</welcome-file>
        <welcome-file>default.html</welcome-file>
        <welcome-file>default.htm</welcome-file>
        <welcome-file>default.jsp</welcome-file>
    </welcome-file-list>
</web-app>

看不了没,跟servlet 是不是有点相似昵,以后我们会看到更加清楚(struts 的本质,你可以自己想想)

看到这里我们要有一个struts-config.xml文件, Now 我们来写一个

<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE struts-config PUBLIC
          "-//Apache Software Foundation//DTD Struts Configuration 1.3//EN"
          "http://struts.apache.org/dtds/struts-config_1_3.dtd">

<struts-config>
    <form-beans>
        <form-bean name="helloWorldForm" type="org.helloWorld.struts.form.HelloWorldForm"></form-bean>
    </form-beans>
    <action-mappings>
        <action path="/hello" name="helloWorldForm" type="org.helloWorld.struts.action.HelloWorldAction">
            <forward name="success" path="/helloworld/success.jsp"></forward>
            <forward name="fail" path="/helloworld/fail.jsp"></forward>
        </action>
    </action-mappings>
    <message-resources parameter="org.helloWorld.struts.resource.ApplicationResources"></message-resources>
</struts-config>

好,我们来看看这个XML文件,我们发现有<form-bean>和<action>现在我们先不理what is this

我们看到type中都有一个类,我们先来完成这个类

clip_image038[4]

从ActionForm 类中继成

package org.helloWorld.struts.form;

import javax.servlet.http.HttpServletRequest;

import org.apache.struts.action.ActionErrors;
import org.apache.struts.action.ActionForm;
import org.apache.struts.action.ActionMapping;

/**
 * struts helloworld 的action form
 * @author sakrua
 * email :winds8@gmail.com  msn:wind_s8@hotmail.com
 * 2007年11月5日
 */
public class HelloWorldForm extends ActionForm {

    private static final long serialVersionUID = -3372095237053639793L;

    //一个javabean 从ActionForm继成
    //用户名
    private String userName;
    //想说的话
    private String worldToSay;
/*
    //validate
    public ActionErrors validate(ActionMapping mapping,
            HttpServletRequest request) {
        ActionErrors errors = new ActionErrors();
        //暂时我们不理这个,以后再说
        if(userName.equals("")){
        }
        if(worldToSay.equals("")){
        }
        return super.validate(mapping, request);
    }
*/
    //下面为set get function
    public String getUserName() {
        return userName;
    }

    public void setUserName(String userName) {
        this.userName = userName;
    }

    public String getWorldToSay() {
        return worldToSay;
    }

    public void setWorldToSay(String worldToSay) {
        this.worldToSay = worldToSay;
    }
}

下面是action

package org.helloWorld.struts.action;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.apache.struts.action.Action;
import org.apache.struts.action.ActionForm;
import org.apache.struts.action.ActionForward;
import org.apache.struts.action.ActionMapping;
import org.helloWorld.struts.form.HelloWorldForm;
/**
 * struts helloworld 的action form
 * @author sakrua
 * email :winds8@gmail.com  msn:wind_s8@hotmail.com
 * 2007年11月5日
 */
public class HelloWorldAction extends Action {

    private static final String FAIL ="fail";
    private static final String SUCCESS ="success";
    //action中所有的请求都会由这个函数处理
    public ActionForward execute(ActionMapping mapping, ActionForm form,
            HttpServletRequest request, HttpServletResponse response)
            throws Exception {
        //从actionForm 中取数据
        HelloWorldForm helloWorldForm =(HelloWorldForm)form;
        String userName = helloWorldForm.getUserName();
        String worldToSay = helloWorldForm.getWorldToSay();
        //如果没有协作输入转到错误页面
        if(userName.equals("")||worldToSay.equals("")){
            return mapping.findForward(FAIL);
        }
        //转到成功页面
        return mapping.findForward(SUCCESS);
    }

}

还有两个jsp

Index.jsp

<?xml version="1.0" encoding="UTF-8" ?>
<%@ page language="java" contentType="text/html; charset=UTF-8" pageEncoding="UTF-8"%>

<%@ taglib uri="http://struts.apache.org/tags-bean" prefix="bean" %>
<%@ taglib uri="http://struts.apache.org/tags-html" prefix="html" %>

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8" />
<title>Welcome you to use this demo</title>
</head>
<body>

<html:form action="/hello">
请输入你的用户名:   
<html:text property="userName"></html:text><br />
请输入你想说的话:
<html:textarea property="worldToSay"></html:textarea><br />
<html:submit value="submit"></html:submit>
</html:form>

</body>
</html>

Fail.jsp

<?xml version="1.0" encoding="UTF-8" ?>
<%@ page language="java" contentType="text/html; charset=UTF-8" pageEncoding="UTF-8"%>
<%@ taglib uri="http://struts.apache.org/tags-bean" prefix="bean" %>
<%@ taglib uri="http://struts.apache.org/tags-html" prefix="html" %>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8" />
<title>请输入完整的信息</title>
</head>
<body>
<bean:message key="helloWorld.userNameRequire"/><br />
<bean:message key="helloWorld.worldToSayRequire"/><br />
<a href="index.jsp" >转到转入页面</a>
</body>
</html>

Success.jsp

<?xml version="1.0" encoding="UTF-8" ?>
<%@ page language="java" contentType="text/html; charset=UTF-8" pageEncoding="UTF-8"%>
<%@ taglib uri="http://struts.apache.org/tags-bean" prefix="bean" %>
<%@ taglib uri="http://struts.apache.org/tags-html" prefix="html" %>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8" />
<title>Welcome you <bean:write name="helloWorldForm" property="userName" /></title>
</head>
<body>
<bean:write name="helloWorldForm" property="userName" /> 你想对我们说的是<bean:write name="helloWorldForm" property="worldToSay" />
</body>
</html>

好写完了

打开ie输入http://localhost:8080/Struts_HelloWorld/

clip_image040[4]

clip_image042[4]

正常运行中

在这个过程中我们做了什么呢,我们已经完成了我们的第一个struts 程序(废话)

具体做了什么 

To be continued

posted on 2007-11-08 22:39 风の使者 阅读(267) 评论(0)  编辑  收藏 所属分类: struts

<2025年7月>
293012345
6789101112
13141516171819
20212223242526
272829303112
3456789

留言簿

文章分类

文章档案

搜索

  •  

最新评论