1 什么是Servlet?
Servlet是运行在Web服务器上的Java程序,作为来自Web浏览器或者其他HTTP客户端的请求与HTTP服务器上的数据库和应用程序之间的中间层。
Servlet在服务器端只要完成以下任务:
(1)获取客户端浏览器通过HTML表单提交的数据及相关信息。
(2)创建并返回对客户端的动态响应页面。
(3)访问服务器端资源,如文件、数据库。
(4)为JSP页面准备动态数据,与JSP一起协作创建响应页面。
2 Servlet的生命周期
Servlet的生命周期主要由3个过程组成:
(1)init()方法:服务器初始化。首次创建Servlet时才会调用init()方法。要注意的是,init方法用于初始化,而不是创建。
(2)service()方法:初始化完毕,Servlet对象调用该方法响应客户的请求。对于每次请求,Servlet引擎都会调用该方法。该方法声明如下:
public void service(ServletRequest request, ServletResponse response)
其中,request和response对象有Servlet容器创建并传递给service方法,service方法根据HTTP的请求类型,调用相应的doGet()或doPost()方法。Service方法可以被调用多次。
(3)destroy()方法:销毁Servlet对象。
3 Servlet的技术特点:
3.1 有效性
相比传统的CGI程序,Servlet更加有效。主要有两点:
(1)传统CGI对于每一项请求都会启动新进程,而Servlet只是使用Java线程来处理每一项请求,Servlet的开销较小。
(2)传统CGI程序完成请求的处理工作时,就会终止程序,而Servlet在完成响应后仍然保留在内存在中,因此可以在请求之间存储任意复杂的数据。
3.2 方便性
Servlet包含扩展基础结构,能够自动对HTML表单数据进行分析和解码、读取和设置HTTP头、处理C欧凯而、跟踪会话以及实现许多其他类似的高级功能。
3.3 功能强大性
Servlet支持几种常规CGI难以或无法实现的功能。例如,直接与Web服务器对话;多个Servlet之间能共享数据;Servlet还可以保留不同请求的信息。
3.4 可移植性
3.5 安全性
3.6 便宜
4 Servlet和JSP的区别
(1)编程方式不同。Servlet是按照Java规范编写的Java程序,JSP是按照Web规范编写的脚本语言。
(2)编译方式不同。Servlet每次修改后需要重新编译才能运行,JSP被JSP容器编译为Servlet文件。
(3)运行速度不同,由于JSP要被编译成Servlet,所以Servlet被JSP快。
(4)作用不同。JSP 是在Servlet的基础上推出的新技术,但JSP更注重页面的表示,而Servlet则更加注重业务逻辑的实现。
5 Servlet部署
部署描述符文件(web.xml)可配置Servlet的参数,它是Java EE程序的重要组成部分,其主要功能如下:
(1)用于Servlet和Web应用程序的初始化。
(2)Servlet/JSP定义。在Web应用程序中的每个Servlet和预编译的JSP文件都应在部署描述符文件中定义。
(3)MIME类型定义。
(4)安全控制。可以使用部署描述符文件控制对应用程序的访问。
一个部署描述符文件的例子:
<?xml version="1.0" encoding="UTF-8"?>
<web-app
version="3.0"
xmlns="http://java.sun.com/xml/ns/javaee"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_3_0.xsd">
<servlet>
<!-- 指定servlet的名称 -->
<servlet-name>FirstServlet</servlet-name>
<!-- 指定servlet编译生成的.class文件的相对路径,区分大小写 -->
<servlet-class>servlet.FirstServlet</servlet-class>
</servlet>
<!-- 在解析到<url-pattern>中的路径请求时,由<servlet-name>指定的servlet来处理;
<servlet-mapping>用于对<servlet>中指定的servlet映射路径 -->
<servlet-mapping>
<servlet-name>FirstServlet</servlet-name>
<url-pattern>/FirstServlet</url-pattern>
</servlet-mapping>
</web-app>
6 重定向与转发
重定向的功能是将用户从当前页面或者Servlet重定向到另外一个JSP页面或者Servlet;转发的功能是将用户对当前JSP页面或者Servlet对象的请求转发给另外一个JSP页面或者Servlet对象。在Servlet类中可以使用HttpServletResponse类的重定向方法sendRedirect(),以及RequestDispatcher类的转发方法forward()。尽管两者都能让浏览器获得另外一个URL所指向的的资源,但两者的内部运行机制有很大的区别:
(1)forward()只能讲将请求转发给同一个Web应用中的组件;而sendRedirect()不仅可以重定向到当前应用程序中的其他资源,还可以重定向到同一个站点上的其他应用程序中的资源,甚至是使用绝对URL重定向到其他站点的资源。对于相对URL中的“/”,在sendRedirect中表示整个Web站点的根目录,如:http://127.0.0.1/ ,而forward中则表示当前应用程序的根目录:如:http://127.0.0.1/test
(2)调用sendRedirect()方法结束后,浏览器显示URL会变成重定向的目标URL;而forward()会保持原地址不变。
(3)使用sendRedirect的时候,浏览器向目的URL发送一次请求,
目的URL使用sendRedirect响应,返回新的URL地址,然后浏览器再次向新的URL发送请求,新的URL再返回response到浏览器,期间浏览器和服务器端完成了两次请求响应;使用forward的时候,浏览器向目的URL发送请求,目的URL向该请求发送到新的URL,最后由目的URL返回response到浏览器,期间浏览器和服务器只完成了一次请求响应。
(4)无论是forward还是sendRedirect,在调用之前,都不能有内容已经被实际输出到客户端,如果缓冲区已经有了一些内容,这些内容将被从缓冲区中清除。
7 Servlet编程接口
7.1 与Servlet实现相关的接口
7.1.1 Servlet接口
该接口是所有Sevlet类都必须直接或间接实现的接口,它包含以下方法:
(1)public void init(ServletConfig config):用来初始化Servlet。
(2)pubic void service(ServletRequest request, ServletResponse response):处理传来的请求,是运行应用程序逻辑的入口点。
(3)public void destroy():当所有线程结束时,调用此方法,释放Servlet所占资源。
(4)public ServletConfig getServletConfig():返回在init()方法执行时传送给Servlet的ServletConfig对象。
(5)public String getServletInfo():返回一个String类型的对象,包含Servlet信息,如作者、版本号等。
7.1.2 GenericServlet类
GenericServlet类提供了对Servlet接口的基本实现,它是一个抽象类,它的子类需要实现service方法。
public abstract class GenericServlet implements Servlet, ServletConfig, java.io.Serialiable
除了实现覆盖了接口中的方法外,GenericServlet类还包括一些方法:
(1)public void init():用来初始化Servlet,可重写的便捷方法,不必重写init(ServletConfig config),只要重写该方法即可,init(ServletConfig config)将会调用该方法。
(2)public void log(String message):把Servlet的名称和message参数写入到日志中。
(3)public void log(String message, Throwable t):记录Servlet的名称和消息,包括对Throwable异常的跟踪信息。
7.1.3 HttpServlet类
HttpServlet类是针对使用HTTP的Web服务器的Servlet类,提供了Servlet的HTTP实现,是Servlet类的扩展。HttpServlet继承了GenericServlet类,是一个抽象类,但是并没有抽象方法。
HttpServlet类包含以下方法:
(1)protected void doGet(HttpServletRequest request, HttpServletResponse response):处理HTTP get请求。
(2)protected void doPost(HttpServletRequest request, HttpServletResponse response):处理HTTP post请求。
(3)protected void doPut(HttpServletRequest request, HttpServletResponse response):处理HTTP put请求。
(4)protected void doDelete(HttpServletRequest request, HttpServletResponse response):处理HTTP delete请求。
(5)long getLastModified(HttpServletRequest request):返回一个以毫秒为单位的时间,是Servlet上一次被修改以来的时间。默认返回一个负数(-1),表示修改时间未知。
7.2 与ServletConfig配置相关的接口
ServletConfig接口代表了Servlet的配置。由Servlet容器建立的ServletConfig独享,用于初始化期间向Servlet传递信息。Servlet的配置包括Servlet的名字、Servlet的初始化参数和Servlet上下文。主要有以下方法:
(1)public String getServletName():返回一个在Servlet的部署描述符中指定给Servlet的名字。如果Servlet没有定义这个名字,则返回Servlet类的名字。
(2)ServletContext getServletContext():返回与执行的Servlet相联系的ServletContext的应用。
(3)Enumeration getInitParameterNames():返回Servlet初始化参数名称列表。如果没有定义初始化参数,则返回一个空的枚举集合。
(4)public String getInitParameter(String name):返回参数指定的初始化参数值,若不存在则返回null。
7.3 与Servlet异常相关的接口
7.3.1 ServletException类
ServletException是一个通用的异常类,可以被init()、service()、destroy()方法抛出。
7.3.2 UnavailableException类
7.4 与请求和响应相关的接口
7.4.1 HttpServletRequest 接口
该接口的声明如下:
public interface HttpServletRequest extends ServletRequest
该接口包括以下方法:
(1)getCookies()
(2)getSession():如果没有给客户端分配Session,则返回null。
(3)getSession(boolean create):返回和客户端关联的Session,如果create为true且没有给客户端分配Session,则创建一个新的Session并返回;如果create为false且没有给客户端分配Session,则返回null。
(4)getParameter(String name)
(5)getParameterValues(String name):返回请求中名为name的参数值,这个值往往是checkbox或者是select控件提交的,获取的值是一个String数值。
7.4.2 HttpServletResponse接口
该接口的声明如下:
public interface HttpServletResponse extends ServletResponse
该接口包括以下方法:
(1)addCookies()
(2)encodeURL(String URL):使用URL和一个session Id重写这个URL
(3)sendRedirect(String location)
(4)setContentType(String type):设置相应的MIME类型
(5)setCharacterEncoding(String charset):设置响应的字符编码类型
7.5 会话管理
HttpSession接口被Servlet引擎用来实现HTTP客户端和HTTP会话两者之间的关联。Session用来在无状态的HTTP下越过多个请求页面来维持状态和识别用户。使用Session的过程如下:
(1)使用HttpServletRequest中的getSession方法得到或者创建新的Session。
(2)使用HttpSession.setAttribute(name, value)方法来向Session中写入信息。
(3)使用HttpSession.getAttribute(name)来读取Session中一个变量值,要注意的是,读取出来的值的类型为Object,需要进行强制类型转换才能使用。
(4)关闭Session。可以调用session.invalidate()方法关闭Session,但这并不是必须的,应为Servlet引擎会在一段时间之后自动关闭Session。
7.6 Servlet上下文相关
该接口的常用方法有:
(1)getAttribute(String name)
(2)setAttribute(String name, Object obj)
(3)removeAttribute(String name)
参考:《JSP程序设计技术教程(第2版)》 张志锋、甘勇、黄敏等编著