Servlet基础之API

Servlet API

1. 概述

Servlet API 是你的 Java Web 程序与 Servlet 容器(例如,Tomcat)之间的『约定』。

注意
Servlet 容器有且不仅只有 Tomcat 一种。后续内容就不再强调 Servlet 容器和 Tomcat 之间的关系,但凡提到 Tomcat 容器的场景,使用其它的 Servlet 容器也是可以的。

这个约定归结起来就是,Tomcat 将 Servlet 类载入内存,并由 Tomcat 调用 Servlet 对象的具体的方法这些方法所需的参数也是由 Tomcat 准备并传入的

简单来说就是一句话,你按照某种特定规则写好代码『放在这里等着』Tomcat 来调用。

Servlet 技术的核心是 Servlet 接口:

Servlet 接口
└── GenericServlet 抽象类
    └── HttpServlet 

你的 Servlet 类必须直接或间接实现的 Servlet 接口。通常,我们是继承 HttpServlet,从而间接实现 Servlet 接口。

// 直接实现 Servlet 接口
public class AServlet implements Servlet { ... }

// 间接实现 Servlet 接口
public class BServlet extends GenericServlet { ... }

// 间接实现 Servlet 接口
public class CServlet extends HttpServlet { ... }

2. 相关对象概述

在 web 项目运行期间,每个 Servlet 类最多只能有一个对象。它们都是『单例』的,它们都是(被动地)由 Tomcat 创建的。

如果你是直接实现的 Servlet 接口, Tomcat 在调用你的 Servlet 的 .service 方法时,会传入两个参数:

  • ServletRequest 其中封装了当前的 HTTP 请求,因此,Servlet 开发人员不必解析和操作原始的 HTTP 数据。

  • ServletResponse 表示对当前用户的 HTTP 响应,它使得将响应发回给用户变得十分容易。

如果你是间接实现的 Servlet 接口,本质上也是如此。

ServletRequest 和 ServletResponse 对象是『多实例』的。

对于每一个 WebApp,Tomcat 还会创建一个 ServletContext 实例,它也是『单例』的。这个对象中中封装了上下文的环境详情。

每个 Servlet 实例也都有一个封装 Servlet 配置的 ServletCongfig ,Servlet 和 ServletConfig 是『一一对应』的。

总结:一个 WebApp 在运行时,有:

  • 1 个 ServletContext 实例

  • N 个 Servlet 实例 (取决于 Servlet 类的数量)

  • N 个 ServletConfig 实例 (取决于 Servlet 类的数量)

  • 任意个 HTTPRequest / HTTPResponse 实例 (取决于用户请求的次数)

3. Servlet 接口

Servlet 接口中定义了 5 个方法:

#方法说明
1.init在 Servlet 第一次被请求时,被 Servlet 容器调用。
Tomcat 调用 .init 时,容器会传入一个 ServletConfig 对象。
2.service在每次用户发起请求时,被容器调用。
Tomcat 调用 .service 时,容器会传入代表用户请求和相应的 HTTPRequest 对象和 HTTPResponse 对象。
3.destroy在销毁 Servlet 时,被 Tomcat 调用。一般发生在卸载 WebApp 或关闭容器时。
4.getServletInfo这个方法返回一个用于描述 Servlet 的字符串。
5.getServlet这个方法用于返回由 Servlet 传给 .init 方法的 ServletConfig 对象。

.init.service.destroy 方法是 Servlet 的生命周期方法,另外两个方法是非生命周期方法。

4. GenericServlet 抽象类

GenericServlet 抽象类实现了 Servlet 接口,它为这些方法提供了默认的实现,并新增了一个 servletConfig 实例变量,用于在 init() 方法中将容器传入的 ServletConfig 对象保存起来。

5. HTTPServlet 类

HTTPServlet 在其父类 GenericServlet 的基础上进一步简化了实现了 Servlet 接口的工作。

HTTPServlet 有两个特性是 GenericServlet 所不具备的:

  1. 不用 Override service() 方法,而是 Override doGet() 或者 doPost() 方法。

  2. 使用 HttpServletRequest/HttpServletResponse,而非 ServletRequest/ServletResponse。

6. ServletRequest 和 HTTPServletRequest

每当 Tomcat 调用你的 Servlet 的 service 方法时,它都会创建一对新的 Request 和 Response 对象传入其中。

Tomcat 何时会调用你的Servlet 的 service 方法?

getParameter() 方法是 ServletRequest 中最常用的方法,该方法用于从 Request 对象中获取请求参数的值。

除了 getParameter() 外,类似用于获取请求参数的值的方法还有:

  • getParameterNames()

  • getParameterMap()

  • getParameterValues()

7. HttpServletRequest

由于我们更长使用的是 HTTPServlet 类,而不是 Servlet 接口,因此,我们更多地是接触并使用 HttpServletRequest,而不是 ServletRequest 。

HTTPServletRequest 实现并扩展了 ServletRequest 接口。

HttpServletRequest 扩展的常用方法有:

  • Stirng getRequestURL( )

  • Stirng getRequestURI( )

  • Stirng getContextPath( )

  • String getMethod( )

  • Cookie[] getCookies( )

  • HttpSession getSession( )

8. ServletResponse 和 HTTPServletResponse

Tomcat 在调用你的 Servlet 的 service() / doGet() / doPost() 方法时,除了会传入要给 Request 对象,还会传入一个 Response 对象:ServletResponse / HttpServletResponse

ServletResponse 隐藏了向浏览器发送响应的复杂过程。

在 ServletResponse 所有的方法中,最常用的方法之一是 getWriter() 方法,它返回一个可以向客户端发送文本的 java.io.PrintWriter 对象。默认情况下,PrintWriter 对象使用 ISO-8859-1 编码。

注意
有另外的一个向浏览器发送数据的方法叫 getOutputStream(),但这个方法是用于发送二进制数据的。因此大多数情况下使用的是 getWriter(),而非 getOutPutStream()。不要调用错了方法。

大多数情况下,你的 Servlet 通过 Tomcat 向客户端发送响应数据应该是一个 HTML 格式的字符串。

在发送这个 HTML 格式字符串前,应该先调用 setContentType() 方法,设置响应的内容类型,并将 text/html 作为参数传入。这是告诉浏览器,所发送给它的数据内容是 HTML 格式内容。

HTTPServletResponse 实现并扩展了 ServletResponse 接口。它所扩展的常用的方法有:

  • void addCookie ( Cookie cookie )

  • void sendRedirect ( String location )

9. ServletConfig 和 ServletContext

当 Tomcat 创建出你的 Servlet 的单例对象后,它会调用你的 Servlet 的 init() 方法,并传入一个 ServletConfig 对象。

ServletConfig 对象中封装这由 @WebServlet 注解或者 部署描述符 传给 Servlet 的配置信息。

这样传入的每一条信息就叫做 初始化参数,一个初始化参数由 key 和 value 组成。

@WebServlet(name="HelloServlet",
            urlPatterns = {"/hello.do"},
            initParams = {
                @WebInitParam(name="author", value="ben"),
                @WebInitParam(name="email", value = "hemiao3000@126.com")
})

为了获得 Servlet 的初始化参数,可以从容器传给 Servlet 的 ServletConfig 对象中调用 getInitParameter() 方法来获得。


ServletContext 代表着 WebbApp。每个 WebApp 只有一个 ServletContext 对象。

通过调用 ServletConfig 实例的 getServletContext() 方法,可以获得该 Servlet 所属的 WebApp 的 ServietContext 对象。

10. 部署描述符

在 servlet 3.0 之前,不支持注解的形式来配置 servlet,而是在 web.xml 中使用配置描述符。

<servlet>
  <servlet-name>HelloServlet</servlet-name>
  <servlet-class>HelloServlet</servlet-class>
  <init-param>
    <param-name>author</param-name>
    <param-value>ben</param-value>
  </init-param>
  <init-param>
    <param-name>email</param-name>
    <param-value>hemiao3000@126.com</param-value>
  </init-param>
</servlet>

<servlet-mapping>
  <servlet-name>HelloServlet</servlet-name>
  <url-pattern>/HelloWorld/hello.do</url-pattern>
</servlet-mapping>
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值