第8章 JavaServer Pages (JSP)

第8章 JavaServer Pages (JSP)

8.1 JSP与Servlet的关系:
JSP是Servlet更高级别的扩展,通过JSP可以让开发人员把普通的Java代码镶嵌到HTML页面中,最终JSP文件会通过Web服务器的Web容器编译成一个Servlet,用来处理各种请求。

8.2 JSP与Servlet的关系:
从根本上来说JSP就是Servlet,因为JSP在Web服务中运午的时候,就是先转化成Sevlet,再调用转化后Servlet的方法,把输出的动态HTML内容返回给客户的浏览器。

JSP的头标签:
<%@page language="java" contentType="text/html";charset="UTF-8">

8.4 JSP内部运行机制:
1.当浏览器向Web服务器发出请求,要求调用JSP页面的时候,Web服务器会根据请求文件的“.jsp”扩展名知道浏览器请求的是一个JSP文件。
2.Web服务器把这个请求传递给Web容器,Web容器会把请求的JSP文件转化成Servlet的源文件,同时对源文件进行编译,生成转化后的Servle的Class文件。
转化和编译的过程发生在这个JSP文件第一次被浏览器请求的进候。第一次调用花费更多的时间才能看到输出的内容。
Tomcat就保留了这些临时生成的Servlet源文件和class文件,这些文件保存在tomcat根目录下的work目录下。在work目录下,可 以查看每个Web应用中JSP文件所生成的Servlet源文件和编译后的class文件。

浏览器在调用JSP文件时,Servlet容器会把浏览器的请求和对浏览器的回应封装成HttpServletRequest和HttpServletResponse对象,同时调用对应的生成Servlet中的_jspService()方法,把这两个对象作为参数传递到_jspService()方法中,_jspService()方法执行后给浏览器返回HTML内容。

jspInit()方法:
只在JSP页面初始化的时候进行调用。

jspDestroy()方法:
在JSP页面被Servlet容器销毁的时候调用。

_jspService(HttpServletRequest request, HttpServletResponse response)方法:
该方法只能同Servlet容器在转化JSP为Servlet的时候,由Servlet容器来重写。

JSP生成的Servlet继承了org.apache.jasper.runtime.HttpJspBase类,而这个类是Tomcat为了简化编程,直接实现了HttpJspPage接口,从设计上分析,这里可以认为使用了缺少适配设计模式。

JSP转化Servlet图:
.jsp - HttpJspBase - (interface)HttpJspPage - (interface)JspPage - (interface)Servlet

8.5 JSP语法:
8.5.2 指定(Directive)标记:
JSP指令用来设置与整个jsp页面相关的属性,它并不直接产生任何可见的输出,而只是告诉引擎如何处理其余JSP页面。
一、page指令
功能:设定整个JSP网页的属性和相关功能。
语法:
标签元素:

page指令元素的属性:

language="language" 指定JSP Container要用什么语言来编译JSP网页。目前只可以使用Java语言,不过不排除增加其它语言。默认值为Java。

extends="className" 定义此JSP页面产生的Servlet是继承自哪个父类。必须为实现HttpJspPage接口的类。JSP规范对不完全理解其隐意的情况下使用此属性提出警告。

import="importList" 定义此JSP页面可以使用哪些Java API。用逗号分隔列出一个或多个全质类名。此列表用于在生成的java servlet中创建相应的导入语句。以下包是自动包含的,不必被指出:java.lang.*;java.servlet.*;java.servlet.jsp.*;java.servlet.htt.*

buffer="none|size in kb" 指定输出流缓存的大小。有效值是nkb或没有。缺省为8kb。

authflush="true|false":决定输出流的缓冲区是否要自动清除。当值为true时缓存满时将被自动刷新,当值为false时,缓冲区满会抛出溢出异常。缺省值为true。

isThreadSafe="true" 此JSP页面能处理来自多个线程的同步请求,此值为true,否则为false,生成的servlet表明它实现了SingleThreadMode接口。SingleThreadMode已经声明不赞成使用(deprecate)

info="text" 表示此JSP页面的相关信息,由getServletInfo()方法返回的。

isErrorPage="true|false" 如果此页面被用作处理异常错误的页面,则为true。在这种情况下,页面可被指定为另一页面page指令元素中errorPage属性的取值。指定此属性为true将使exception隐含变量对此页面可用。缺省值为false。

errorPage="error_url" 表示如果发生异常错误,网页会被重新指向一个URL页面。错误页面必须在其page指令元素中指定isErrorPage="true"

contentType="ctinfo" 表示将在生成servlet中使用的MIME类型和可选字符解码。

pageEncoding="ctinfo" 表示JSP页面的编码方式。

isELIgnored="true|false" 表示是否在此JSP网页中执行或忽略EL表达式。如果为true时JSP Container将忽略EL表达式。

JSP 语法
<%@ page
[ language="java" ]
[ extends="package.class" ]
[ import="{package.class | package.*}, ..." ]
[ session="true | false" ]
[ buffer="none | 8kb | sizekb" ]
[ autoFlush="true | false" ]
[ isThreadSafe="true | false" ]
[ info="text" ]
[ errorPage="relativeURL" ]
[ contentType="mimeType [ ;charset=characterSet ]" | "text/html ; charset=ISO-8859-1" ]
[ isErrorPage="true | false" ]
%>
例子
<%@ page import="java.util.*, java.lang.*" %>
<%@ page buffer="5kb" autoFlush="false" %>
<%@ page errorPage="error.jsp" %>

二、include指令
功能:在JSP编译时插入包含一个文件。包含的过程是静态的,包含的文件可以是JSP、HTML、文本或是Java程序。
语法:
标签元素:
注意:include指令元素和动作元素主要有两个方面的不同点。
1.include指令是静态包含,执行时间是在编译阶段执行,引入的内容为静态文要,在编译成servlet时就和包含者融合到一起。所以file不能是一个变量,也不能在file后接任何参数。
2.include行为是动态包含,执行时间是在请求阶段执行,引入的内容在执行页面时被请求时动态生成再包含到页面中。

<%@ include file=“filename” %>如果直接以文件名开头,指的是正在使用的JSP文件所在的路径,如果以/开头,指的是正在使用的JSP文件上下的路径关系.

三、taglib指令

功能:使用标签库定义新的自定义标签,在JSP页面中启用定制行为。
语法:
标签元素:

uri="tagLibraryURI" 标签库描述器的URI,主要是说是tagLibrary的存放位置。
prefix="tagPrefix" 用于标识在页面后面部分使用定制标签的唯一前缀。

<%@ taglib uri="URIToTagLibrary" prefix="tagPrefix" %>

如<%@ taglib uri="http://www.jspcentral.com/tags" prefix="public" %>
// 这里的URI指的是标签库定义文件(*.tld文件)中定义的URI
prefix(前缀)相当于标签库的一个别名.

8.5.3 声明(Declaration)标记
jsp的声明标记,可以用来声明标量和方法,格式如下(前面的三个符号——尖括号,百分号和感叹号都连续的,不空格):
<%!
private int i = 0;
private String getName(){……}
%>
也可以用来定义jspInit()和jspDestroy()方法。

8.5.4 Scriptlet标记
<%
//java code
%>

8.5.5 表达式(Expression)标记:
<%="expression"%>

8.7 JSP动作(action)
8.7.1 <jsp:include>动作:

使用include动作代码片段:
<jsp:include page="/header.jsp" />
包含其他页面同时还可以传递参数:
<jsp:include page="/header.jsp">
<jsp:param name="author" value="pilou.com">
</jsp:include>
page属性的属性值也可以是一个表达式的值,属性值只能使用相对路径。“/”指是页面所属的Web应用的根目录。
flush="true | false",如果页面的输出内容是有缓冲的,flush属性值决定是否flush。该属性的默认值为false。
通过param标记可以在包含其他JSP页面的时候传递一个或多个的参数,name属性设定参数名,ualue属性设定参数值。使用include动作的JSP页面,通过request.getParameter("name");获得被包含文件传递的参数值。

<%@ include file=""%>与<jsp:include page=""/>区别
1. include指令标记读入指定页面的内容并把这些内容和原来的页面融合到一起。这个过程发生在JSP转化成Servlet的阶段,最终所合成的JSP文件被Servlet容器转化成servlet。如果一个JSP页面使用include指令包含了另一个JSP页面,最终也只产生一个Servlet的JAVA源文件和一个class文件。
使用<jsp:include>动作包含其他JSP页面,其本质是调用了被包含文件所转化的Servlet对象的jspService()方法。也就是说,所被包含的JSP文件也对应有生成的Servlet源文件和class文件。如果一个JSP页面使用include动作包含了另一个JSP页面,一共会产生两个Servlet源文件和两个class文件。

8.7.2 <jsp:forward>动作
使用forward动作的代码片段:
<jsp:forward page="/register.jsp" />
转向同时还可以传递参数:
<jsp:forward page="/register.jsp">
<jsp:param name="author" value="pilou.com" />
</jsp:forward>

page属性值表示转向后的页面地址,只能使用相对地址,“/”指是页面所属的Web应用的根目录。
通过param标记可以在转向到其他JSP页面的时候,传递一个或者多个的参数,name属性设定参数名,value属性设定参数值。转向后的JSP页面,可以通过request.getParameter("name1")获得传递的参数。
使用<jsp:forward>动作转向,和下面Servlut中常用的转向代转是完全等同的:
RequestDispatcher rd = request.getRequestDispatcher("/register.jsp");
rd.forward(request, response);

8.8 JSP内置对象
8.8.1 out对象:
<%out.print("welcome to www.pilou.com");%>

8.8.2 request对象:
request的类型为javax.servlet.http.HttpServletRequest,request对象封装客户端发出的请求,有关客户端请求的信息,都可以通过request对象获得。例如:请求头、请求方法、请求的参数等内容。总之request对象的用法和Servlet中的HttpServlitRequest对象的用法一样:
<%out.println(request.getParameters("username"));%>

8.8.3 response对象
response对象类型为javax.servlet.http.HttpServletResponse,response对象封装对客户端响应的内容,利用它来设定一些要返回给客户的信息。response对象的用法和Servlet中的HttpServletResponse对象的用法一样。
使用response对象的代码片段:
response.sendRedirect("http://www.sina.com");
上面代码的作用是转向到http://www.sina.com

8.8.4 session对象:
session对象的类型为HttpSession,用法和Servlet中的用法完全一样。在一次会话中,我们访问同一个Web应用中的Servlet和JSP页面时,所使用的session对象是同一个会
话对象。
<%
session.setAttribute("sebsit", "http://www.sina.com");
out.println(session.getAttribute("website"));
%>

8.8.5 application对象:
application对象的类型是javax.servlet.ServletContext,通过application对象可以获得和当前Web应用相关的信息。

1.传递参数:
通过application对象可以保存跨用户的共享数据,通过application对象保存的数据内容,所有的用户都可以共享使用。如果把session对象比喻成个人专有的手机,可以由专属个人在任何地点接打电话,那么application对象就相当于公共电话,任何人都可以接打这同一个电话。
<%
application.setAttribute("website", "http://www.pilou.com");
out.println(application.getAttribute("website"));
%>

2.设置context初始参数:
通过web.xml的设置为Servlet设置专门的参数,然后可以通过ServlitConfig对象的getInitParameter()方法获取参数值。实际上还可以通过web.xml,为一个Web应用中所有的Servlet和JSP页面设置共享的初始参数值。
<%
out.println("Contextk中设置的初始参数值:");
out.println(application.getInitParameter("website"));
%>

3.使用log()方法记录日志:
同时,还可以在JSP页面中,使用application对象提供的log()方法,实现日志记录的功能,在Tomcat服务器中,记录的日志都保存在tomcat根目录的logs目录下。日志内容分成不同文件进行记录,例如2010年3月2日的日志内容会记录到localhost_log.2010-03-02.txt文件中。
JSP页面中使用log()方法的代码片段:
<%application.log("pilou is here");%>

8.8.6 page对象:
page对象代表的是当前所在的JSP页面,其作用等同于Java编程中this关键字的作用。

8.8.7 pageContext对象
pageContext对象类型是javax.servlet.jsp.PageContext,其他内置对象都自动的被加入至pageContext对象中,可以通过它来获得其他JSP内置对象,例如:getRequest()方法可以获得ServletRequest对象,getServletConfig()可以获得ServletConfig对象,getSession()可以取得HttpSession对象等等。它的主要作用在于提供单一接口,以管理其他的对象(HttpSession, ServletContext, ServletConfig, ServletRequest, ServletResponse 等)。

8.8.8 exception对象:
exception是JSP页面中可以专门集中处理违例的内置对象,通过page指令的设定,Web应用中所有JSP页面所发生的违例都可以由指定的JSP页面处理,这个指定的JSP页面中就可以使用exception内置对象处理转发过来的违例。
使用page指令时,设定errorPage属性指定专门处理违例的JSP页面,而专门处理违例的JSP页面页面,而专门处理违例的JSP页面则设定isErrorPage属性为true。专门处理违例的JSP页面中使用这个内置的exception对象。
<%
exception.printStackTrace(new PrintWriter(out));
%>
<%=exception%>代码只能显示简单的违例信息,而exception.printStackTrace(new PrintWriter(out));可以显示发生违例的堆栈信息。

8.8.9 config对象:
config对象的类型为javax.servlet.ServletConfig,它是可以获取Servlet设定信息的对象,与Servlet中的ServletConfig对象用法一致。

8.11.3 设置web.xml
Web服务器自已定义的错误信息都不够人性化,在Web编程中Web服务器显示错误信息的页面是可以进行自定义的,自定义的页面通过web.xml文件进行设定:
<error-page>
  <error-code>404</error-code>
  <location>/error404.html</location>
</error-page>
<error-page>
  <error-code>500</error-code>
  <location>/error500.html</location>
</error-page>
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值