目录:
- 1.认识Servlet
- 2.编写Servlet
- 3.Servlet的运行机制
- 4.Servlet的生命周期
- 4.1 Servlet生命周期图
- init()方法
- doGet()
- doPost()
- service()
- destroy()方法
- 5.解决“控制台”打印中文乱码问题
- 6.Servlet 和 JSP内置对象 (常用对象)
- 获得out对象
- 获得request 和 response对象
- 获得session对象
- 获得application对象
- 7.设置欢迎页面
- 8.在Servlet中设置/获取参数 :
- 8.1 设置参数
- 8.2 获取参数
- 9.过滤器
- 9.1 过滤器的定义
- 9.2 使用过滤器的三种情况 :
- 情况一
- 情况二
- 情况三
- 9.3 编写过滤器 :
- 编写过滤器的步骤
- 9.4 配置过滤器 :
- 配置 “过滤器” 过滤所有文件
- 配置 “过滤器” 过滤一个或多个Servlet对象/JSP文件
- 配置 “过滤器” 过滤一个或多个文件目录
- 9.5 过滤器的例子
- 过滤器解决中文乱码问题
- 10.异常处理
1.认识Servlet
Servlet 是运行在 Web服务器端 的 Java应用程序,可以生成动态的Web页面,属于客户与服务器响应的 中间层。JSP底层 就是一个Servlet,也可以说 JSP 就是 Servlet。
在运行JSP时,服务器底层 会将 JSP 编译成一一个 Java类,这个类就是 Servlet。
JSP 和 Servlet 都能实现同样的页面效果,不过编写JSP和编写Servlet 相比,前者 ( JSP )的成本低得多。既如此 为什么还要学Servlet?
Servlet属于JSP的底层,学习它有助于了解底层细节;另外,Servlet毕竟是一个Java类,适合纯编程。如果是纯编程,比将Java代码混合在HTML中的JSP要好得多。
2.编写Servlet
编写Servlet的步骤 :
第一步、编写一个类,该类继承 HttpServlet。
public class myServlet extends HttpServlet {}
第二步、重写HttpServlet的 doGet( ) 或 doPost( )方法。 ( 也可以重写HttpServle的其他方法,根据需要来重写。)
public class myServlet extends HttpServlet {@Overrideprotected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {response.setContentType("text/html;charset=gb2312"); //设置HTTP响应的内容类型/*PrintWriter对象可以用于向"客户端浏览器"输出响应数据。通过这个PrintWriter对象,你可以将数据以"文本形式"写入到“HTTP响应”中。*/PrintWriter out = response.getWriter();out.println("欢迎来到本系统!");} }
第三步、配置Servlet。
编写完一个Servlet后还不能直接访问,需要配置Servlet才能通过URL映射到与之对应的Servlet 中,用户才能对它进行访问。
( 配置好Servlet后,客户端浏览器才能通过url/ 网址访问到服务器端的Servlet类)Servlet的配置是通过 web.xml 文件来实现的。web.xml文件位于 “WebRoot/WEB-INF” 下面。
客户端浏览器访问该Servlet的url路径,如客户端浏览器访问 :
http://localhost:8080/servlets/MyServlet 就能访问到 MyServlet.java 类。<?xml version="1.0" encoding="UTF-8"?> <web-app xmlns="http://xmlns.jcp.org/xml/ns/javaee"xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_4_0.xsd"version="4.0"><!-- 配置servlet --><servlet><servlet-name>MyServlet</servlet-name><servlet-class>com.servlets.MyServlet</servlet-class></servlet><servlet-mapping><servlet-name>MyServlet</servlet-name><!--客户端浏览器访问该Servlet的url路径如客户端浏览器访问 :http://localhost:8080/servlets/MyServlet 就能访问到 MyServlet.java类--><url-pattern>/servlets/MyServlet</url-pattern></servlet-mapping></web-app>
<servlet-name>MyServlet</servlet-name>
servlet-name 中的名字用户可以自己命名,不一定要和原文件名一样,但两个servlet-name名字必须要相同。
<url-pattern>/servlets/MyServlet</url-pattern>
url-pattern 也不一定 是Servlet 类的 包路径,只是为方便,一般都用包路径来表示。(可自定义访问Servlet类的 url 路径)
第四步、部署Servlet。如:设置好Tomcat服务器。
第五步、测试Servlet。在浏览器上输入 http://localhost:8080/servlets/MyServlet 即可访问 Servlet。
3.Servlet的运行机制
为Servlet类设置 构造函数,只有 初次运行时,系统才会初始化Servlet / 访问Servlet的构造函数。再次运行Servlet时,不会再访问构造函数 。
( 在Web应用程序中,Servlet类只会在它第一次被访问时初始化 / 访问构造函数。这意味着,当一个请求来到服务器,服务器会判断该Servlet类是否已经被加载。
如果 (构造函数) 没有被加载 ,服务器会加载并初始化该Servlet类,然后处理请求。如果 (构造函数) 有被加载过,服务器会直接使用已经加载和初始化的 (Servlet )实例来处理请求,不会再访问Servlet的构造函数。
Servlet的构造函数只在Servlet类首次被加载和初始化时被调用, 之后的请求不会再访问Servlet的构造函数。 这是Servlet的 生命周期 行为的一部分。 )
public class MyServlet extends HttpServlet {public MyServlet() { //构造函数//Servlet的构造函数,只有Servlet第一次启动时才会访问,之后的请求不会再访问ServletSystem.out.println("MyServlet构造函数");}@Overrideprotected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {//如果"控制台"输出有中文乱码问题,下面有解决方案。System.out.println("MyServlet.doGet函数");} }
访问路径 :
第一次访问Servlet“控制台”打印的信息 :
第二次访问Servlet“控制台”打印的信息 :
第三次访问Servlet“控制台”打印的信息 :
(除第一次访问Servlet会访问构造函数外,之后的请求不会再访问Servlet的构造函数。)
只创建了一个Servlet对象,那么很多用户同时访问的时候会不会造成等待?
实则是不会的。因为Servlet采用的是多线程机制,每一次请求,系统就分配一个线程运行doGet( )函数。但是这样也会带来安全问题,一般来说,不要在Servlet内定义成员变量,除非这些成员变量是所有用户共用的。
4.Servlet的生命周期
4.1 Servlet生命周期图
- 当客户端向Web服务器提出第1次Servlet请求时,Web服务器会实例化一个Servlet,并且调用init( )方法;
(构造函数和 init( )函数只会被访问一次,后续的请求不会再访问这两个函数)- 如果Web服务器中已经存在了一个Servlet实例,将直接使用此实例;然后调用service()方法,service(方法将根据客户端的请求方式来决定调用对应的doXXX0方法;当Servlet从Web服务器中消亡时,Web服务器将会调用Servlet的 destroy() 方法。
init()方法
init()方法 :
- 在Servlet的生命周期中,第一次访问Servlet时,利用构造函数创建Servlet对象后,立即调用init( )方法来进行初始化。构造函数 和 init( )方法都只会在第一次访问时被调用,后续的请求中,两者不会被再次调用。
- init( )方法用于执行一些特定的初始化操作,例如加载配置文件、连接数据库等。
doGet()
- Servlet有两个处理方法之一。
- doGet()在 以 get方式请求Servlet时运行 。常见的get请求方式有 : 链接、get方式表单提交、直接访问Servlet。
doPost()
- Servlet有两个处理方法之一。
- doPost()在 以 post方式请求Servlet时运行。常见的post请求为 :为 post方式表单提交。
service()
- 客户端对Servlet发送一个请求时,服务器端将会开启一个线程,该线程会调用service()方法,
- service()方法会根据收到的客户端请求类型来决定是调用doGet()还是调用doPost()。但一般情况下不用覆盖service()方法,直接使用doGet()与doPost()方法一 样可以达到处理的目的。
destroy()方法
- destroy() 方法在Servlet实例消亡时自动调用。(Servlet消亡时会调用destroy( )方法)
- 在Web服务器运行Servlet实例时会因为一些原因,Servlet对象会消亡。但是在Servlet消亡之前还必须进行某些操作,比如释放数据库连接以节省资源等,这个时候我们就要重写destroy()方法。
5.解决“控制台”打印中文乱码问题
第一步、
第二步、-encoding utf-8
第三步、 -Dfile.encoding=UTF-8 (配置后,要重启tomcat服务器)
每个项目都要在tomcat这么配置,比较麻烦。可通过设置环境变量来解决这个问题。
(配置环境变量后,就不需要每次都在 tomcat里面配置 -Dfile.encoding=UTF-8)第三步的更好的解决替代方案 : 配置环境变量。
JAVA_TOOL_OPTIONS
-Dfile.encoding=UTF-8
6.Servlet 和 JSP内置对象 (常用对象)
- 因为JSP和Servlet等价,在JSP中可以使用内置对象,那么在Servlet中也可以使用内置对象。
- 这里讲述的常用的Servlet 和 JSP内置对象。
获得out对象
JSP中的out对象 对应于Servlet 中的javax.servlet.jsp. JspWriter。通过以下代码可获得out对象。
public void doGet(HttpServletRequest request, HttpServletResponse response)throws ServletExcept ion, IOException {PrintWriter out = response. getWriter();//获得out对象//使用Out对象 }
在默认情况下,out对象是无法打印中文的。因为out对象输出流中有中文却没有设置编码。
public void doGet(HttpServletRequest request, HttpServletResponse response)throws ServletExcept ion, IOException {//设置编码,打印中文response.setContentType("text/html;charset=gb2312");PrintWriter out = response. getWriter();//获得out对象//使用Out对象}
获得request 和 response对象
在Servlet中获得JSP页面中的request对象 和 response对象是很容易的,因为这两个对象已经被作为参数传给了 doXXX( ) 方法。
doXXX( )方法中的 request 和 response 参数就可直接当 request对象、response 对象使用。
public void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {//将request参数当做request对象使用//将response参数当做response对象使用}
获得session对象
session对象对应的是HttpSession接口,在 Servlet 中它可以通过以下代码获得。
public void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {//session对应的是HttpSession接口HttpSession session = request.getSession();//把该session当session对象来使用}
获得application对象
application对象对应的是ServletContext接口,在Servlet中可以通过以下代码获得。
public void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {ServletContext application = this.getServletContext();//把此application当application对象使用}
使用 application 可以实现 服务器内跳转。
ServletContext application = this.getServletContext();RequestDispatcher rd = application.getRequestDispatcher("URL地址");rd.forward(request,response);
由于Servlet和JSP具有同质性,常用的 Servlet内跳转有以下 两种方法:
① 重定向。 (对应JSP隐含对象中的sendRedirect( ))
response.sendRedirect("URL地址");
② 服务器内跳转。(对应JSP隐含对象中的forward( ))
ServletContext application = this.getServletContext(); RequestDispatcher rd = application.getRequestDispatcher("URL地址"); rd.forward(request,response);
(这两种Servlet内的跳转与JSP中提到的跳转都是等效的)
7.设置欢迎页面
在设置完欢迎页面之后,用户登录时输人的URL只需要是该门户网站的虚拟目录就可以自动访问欢迎页面。
可通过在web.xml中设置 “欢迎页面”。
web.xml
<?xml version="1.0" encoding="UTF-8"?> <web-app xmlns="http://xmlns.jcp.org/xml/ns/javaee"xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_4_0.xsd"version="4.0"><welcome-file-list><!-- 所要设定欢迎页面 --><welcome-file>welcome.jsp</welcome-file></welcome-file-list></web-app>
welcome.jsp
<%@ page language="java" import="java.util.*" pageEncoding="gb2312" %> <html> <body> 欢迎来到本系统<br> </body> </html>
web.xml可以同时设置多个欢迎页面 ,web容器默认设置的第一个页面为欢迎页面,如果找不到最前面的页面,Web容器将会依次选择后面的页面作为欢迎页面。
<welcome-file-list><!-- 所要设定欢迎页面 --><!-- 此处添加了多个“欢迎页面,当第一次欢迎页面找不到时,系统会依次向下寻找欢迎页面 --><welcome-file>firstWelcome.jsp</welcome-file><welcome-file>secongdWelcome.jsp</welcome-file></welcome-file-list>
8.在Servlet中设置/获取参数 :
8.1 设置参数
有些和系统有关的信息最好保存在配置文件内,例如系统中的字符编码、数据库连接的信息(driverClassName、url、username、password),在使用这些配置时从配置文件中读,但是读取配置文件的代码必须用户自己来写,比较麻烦。
那么才能比较方便的获得参数? 可在web.xml中设置参数。
设置全局参数 :该参数所有的Servlet都可以访问。
<!--设置全局参数,该参数所有的Servlet都可以访问 --><context-param><param-name>参数名</param-name><param-value>参数值</param-value></context-param>
设置局部参数 :该参数只有对应的Servlet都可以访问。此时设置的参数只在该Servlet中有效,其他的Servlet得不到该参数。
<!--设置局部变量,该参数只有对应的Servlet能访问--><servlet><servlet-name>Servlet名称</servlet-name><servlet-class>类路径</servlet-class><!-- 设置该Servlet对应的变量 : 局部变量 --><init-param><param-name>参数名</param-name><param-value>参数值</param-value></init-param></servlet>
web.xml
<?xml version="1.0" encoding="UTF-8"?> <web-app xmlns="http://xmlns.jcp.org/xml/ns/javaee"xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_4_0.xsd"version="4.0"><!-- 设置全局参数,该参数所有的Servlet都可以访问 --> <context-param><param-name>encoding</param-name><param-value>gb2312</param-value> </context-param><servlet><servlet-name>InitServlet</servlet-name><servlet-class>com.servlets.InitServlet</servlet-class><!-- 设置局部参数 --><init-param><param-name>driverClassName</param-name><param-value>com.mysql.jdbc.Driver</param-value></init-param> </servlet><!-- servlet-mapping --> <servlet-mapping><servlet-name>InitServlet</servlet-name><url-pattern>/servlets/InitServlet</url-pattern> </servlet-mapping><!-- 设置欢迎页面 --> <welcome-file-list><welcome-file>welcome.jsp</welcome-file> </welcome-file-list></web-app>
8.2 获取参数
获取全局参数的方法 :
//获得application对象ServletContext application = this.getServletContext();//获得全局参数application.getInitParameter("参数名称");
获取局部参数的方法 :
this.getInitParameter("参数名");
InitServlet.java
public class InitServlet extends HttpServlet {public void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {//获得application对象ServletContext application = this.getServletContext();//获得全局参数String encoding = application.getInitParameter("encoding");System.out.println("encoding参数是: "+encoding);//获得局部参数String driverClassName = this.getInitParameter("driverClassName");System.out.println("driverClassName的参数是: "+driverClassName);} }
在InitServlet中可以获得web.xml中设置的参数的值,不过,在一般情况下不使用web.xml来设置参数,因为web.xml通常用来设置很基本的Web配置,设置太多参数会使文件过于臃肿。实际用于设置参数的文件与所选取的参数有关。
9.过滤器
9.1 过滤器的定义
- 过滤器 属于一种小巧的、可插入的Web组件,它能够对Web应用程序的前期处理和后期处理进行控制,可以拦截请求和响应,查看、提取或者以某种方式操作正在客户端和服务器之间进行交换的数据。
- 过滤器的doFilter( )函数在Servlet被访问/调用之前被调用(★★★)
9.2 使用过滤器的三种情况 :
以下三种情况遇到的问题可以 过滤器 可以解决。
情况一
为了 解决中文乱码问题,经常需要有如下设置 :
request.setCharacterEncoding("gb2312"); response.setContentType(" text/ html;charset = gb2312");
这是Servlet用来设置编码的,如果Servlet处理方法的最前面没有加入这段代码,则很可能会出现乱码问题。如果是一个大工程,会有很多的Servlet,这样就要写很多重复的代码。同时如果需要换成另外的编码,这也是一件烦琐的事情。
—此时可用 过滤器 来解决
情况二
很多门户网站都会有登录页面,这是为了业务需求,同时也是为了使用户控制更加安全。如果客户没有登录就访问网站的某一受限页面,在很多情况下会引发安全问题。那么应该如何避免这种情况? 在一般情况下可以使用session检查来完成,但是在很多页面上都添加session检查代码会比较烦琐。
—此时可用 过滤器 来解决
情况三
许多网站存在着各种不同的权限,通常只有它的管理员才可以对网站进行维护和修改,一般的普通用户是无法完成该功能的。登录后,网页如何区分是普通用户还是管理员? 如果是每一个页面写一个判断用户类型的代码,这是非常烦琐。
—此时可用 过滤器 来解决
9.3 编写过滤器 :
编写过滤器的步骤
Servlet过滤器可以被当作一个只需要在web. xml文件中配置就可以灵活使用、重用的模块化组件。它能够对JSP、HTML和Servlet文件进行 过滤。
编写过滤器的需要如下两个步骤:
第一步、实现Filter接口。
javax.servlet.Filter;
第二步、实现init()、destroy()、doFilter() 这三个方法。
init():初始化方法, 它表示的是 过滤器初始化时的动作。
//初始化方法 public void init(FilterConfig filterConfig) throws ServletException {};
destroy():消亡方法,它表示的是 过滤器消亡时的动作。
public void destroy() { //消亡方法};
doFilter() : 过滤函数 ,它表示的是 过滤器过滤时的动作。
public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {};
9.4 配置过滤器 :
在 web.xml中配置此过滤器 。可在 过滤器中添加/配置过滤器参数。
过滤器的doFilter( )函数在Servlet被访问/调用之前被调用(★★★)
<!-- 配置过滤器 --> <filter><filter-name>EncodingFilter</filter-name><filter-class>com.filter.EncodingFilter</filter-class><!-- 配置过滤器参数 --><init-param><param-name>paramName</param-name><param-value>paramValue</param-value></init-param> </filter><!-- 访问指定的对象/文件/目录之前都要经过 “过滤器的过滤” --> <filter-mapping><filter-name>EncodingFilter</filter-name><url-pattern>对象/文件/目录的路径</url-pattern> </filter-mapping>
过滤器的配置和Servlet的配置有相似之处。
配置 “过滤器” 过滤所有文件
<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns="http://xmlns.jcp.org/xml/ns/javaee"xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_4_0.xsd"version="4.0"><!-- 配置过滤器 -->
<filter><filter-name>EncodingFilter</filter-name><filter-class>com.filter.EncodingFilter</filter-class>
</filter><!-- 过滤所有文件 -->
<filter-mapping><filter-name>EncodingFilter</filter-name><!-- 访问所有文件之前都要经过 “过滤器的过滤”,*符号代表所有文件 --><url-pattern>/*</url-pattern>
</filter-mapping></web-app>
配置 “过滤器” 过滤一个或多个Servlet对象/JSP文件
<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns="http://xmlns.jcp.org/xml/ns/javaee"xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_4_0.xsd"version="4.0"><!-- 配置过滤器 -->
<filter><filter-name>EncodingFilter</filter-name><filter-class>com.filter.EncodingFilter</filter-class>
</filter><!-- 过滤一个或多个Servlet/JSP文件 -->
<filter-mapping><filter-name>EncodingFilter</filter-name><!-- 访问ServletName1这个Servlet对象之前要先经过 “过滤器的过滤” --><!-- /PATh/ServletName1 为访问该Servlet对象的路径,此时被先Filter过滤一番 --><url-pattern>/PATh/ServletName1( 或JSPName1 )</url-pattern>
</filter-mapping></web-app>
配置 “过滤器” 过滤一个或多个文件目录
<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns="http://xmlns.jcp.org/xml/ns/javaee"xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_4_0.xsd"version="4.0"><!-- 配置过滤器 -->
<filter><filter-name>EncodingFilter</filter-name><filter-class>com.filter.EncodingFilter</filter-class>
</filter><!-- 过滤一个或多个文件目录 -->
<filter-mapping><filter-name>EncodingFilter</filter-name><!-- 其对 PATh1 这个目录进行过滤 --><!-- 访问PATh1这个目录/该目录下的文件 之前要先经过 “过滤器的过滤” --><!-- / : 表示根目录 --><url-pattern>/PATh1/*</url-pattern>
</filter-mapping></web-app>
9.5 过滤器的例子
过滤器解决中文乱码问题
EncodingFilter.java
public class EncodingFilter implements Filter {//初始化方法public void init(FilterConfig filterConfig) throws ServletException {}//消亡方法public void destroy() {}//过滤函数public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {//设置“字符编码”request.setCharacterEncoding("gb2312");chain.doFilter(request,response);} }
web.xml (配置过滤器)
<?xml version="1.0" encoding="UTF-8"?> <web-app xmlns="http://xmlns.jcp.org/xml/ns/javaee"xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_4_0.xsd"version="4.0"><!-- 配置过滤器 --> <filter><filter-name>EncodingFilter</filter-name><filter-class>com.filter.EncodingFilter</filter-class> </filter><!-- 过滤所有文件 --> <filter-mapping><filter-name>EncodingFilter</filter-name><!-- 访问所有文件之前都要经过 “过滤器的过滤”,*符号代表所有文件 --><url-pattern>/*</url-pattern> </filter-mapping><!-- 过滤一个或多个Servlet/JSP文件 --> <filter-mapping><filter-name>EncodingFilter</filter-name> <!-- 访问ServletName1这个Servlet对象之前要先经过 “过滤器的过滤” --> <!-- /PATh/ServletName1 为访问该Servlet对象的路径,此时被先Filter过滤一番 --><url-pattern>/PATh/ServletName1( 或JSPName1 )</url-pattern> </filter-mapping><!-- 过滤一个或多个文件目录 --> <filter-mapping><filter-name>EncodingFilter</filter-name><!-- 其对 PATh1 这个目录进行过滤 --><!-- 访问PATh1这个目录/该目录下的文件 之前要先经过 “过滤器的过滤” --><!-- / : 表示根目录 --><url-pattern>/PATh1/*</url-pattern> </filter-mapping> </web-app>
10.异常处理
在Web应用程序中总会发生各种各样的异常,例如数据库连接失败、0被作为除数、得到的值是空、数组溢出等。如果出现了这些异常,系统不做任何处理显然是不行的。一般情况下都是通过自定义一个公共的error.jsp页面来实现统的异常处理。
error.jsp
<%@ page language="java" pageEncoding="gb2312" isErrorPage="true" %> <html> <head><title>error.jsp</title> </head> <body>对不起,你的操作有误 </body> </html>
web.xml (web.xml中注册该页面)
<!-- 注册error.jsp--> <!-- 其表示由error.jsp来处理所有的异常 --> <error-page><exception-type>java.lang.Exception</exception-type><location>/error.jsp</location> </error-page>
makeErrorTest.jsp
<%@ page language="java" pageEncoding="gb2312" %> <html> <head><title>makeErrorTest.jsp</title> </head> <body> <%String account =(String)session.getAttribute("account");out.print(account.length());//运行该页面,会报一个异常,Servlet容器会自动根据web.xml中的配置找到异常对应的页面//这样所有的Exception就被error.jsp统一处理了 %> </body> </html>