概念
本质
Servlet是按照Servlet规范编写的Java类
作用
Servlet带给我们最大的作用就是能够处理浏览器带来HTTP请求,并返回一个响应给浏览器,从而实现浏览器和服务器的交互
启动
Servlet不是从命令行启动的,而是由包含Java虚拟机的Web服务器进行加载
运行
- Servlet是基于Java技术的Web组件,由容器管理并产生动态的内容
- Servlet与客户端通过Servlet容器实现的请求/响应模型进行交互
- Servlet是由服务器调用的, 运行在服务器端
Servlet 任务
读取
- 读取客户端(浏览器)发送的显式的数据。
这包括网页上的 HTML 表单,或者也可以是来自 applet 或自定义的 HTTP 客户端程序的表单。 - 读取客户端(浏览器)发送的隐式的 HTTP 请求数据。
这包括 cookies、媒体类型和浏览器能理解的压缩格式等等。
处理
- 处理数据并生成结果。这个过程可能需要访问数据库,执行 RMI 或 CORBA 调用,调用 Web 服务,或者直接计算得出对应的响应。
返回
- 发送显式的数据(即文档)到客户端(浏览器)。
该文档的格式可以是多种多样的,包括文本文件(HTML 或 XML)、二进制文件(GIF 图像)、Excel 等。 - 发送隐式的 HTTP 响应到客户端(浏览器)。
这包括告诉浏览器或其他客户端被返回的文档类型(例如 HTML),设置 cookies 和缓存参数,以及其他类似的任务。
创建Servlet
Servlet 创建有三种方式。
1. 实现 Servlet 接口
因为是实现 Servlet 接口,所以我们需要实现接口里的方法。
public class ServletDemo1 implements Servlet {
//当Servlet第一次被创建对象时执行该方法,该方法在整个生命周期中只执行一次
public void init(ServletConfig arg0) throws ServletException {
System.out.println("----init-");---
}
//对客户端响应的方法,该方法会被执行多次,每次请求该servlet都会执行该方法
public void service(ServletRequest arg0, ServletResponse arg1)
throws ServletException, IOException {
System.out.println("hello");
}
//当Servlet被销毁时执行该方法
public void destroy() {
System.out.println("----destroy----");
}
public ServletConfig getServletConfig() {
return null;
}
public String getServletInfo() {
return null;
}
}
2. 继承 GenericServlet 类
它实现了 Servlet 接口除了 service 的方法,不过这种方法我们极少用。
public class ServletDemo2 extends GenericServlet {
3. 继承 HttpServlet 方法
public class ServletDemo3 extends HttpServlet {
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp)
throws ServletException, IOException {
System.out.println("hello get");
}
@Override
protected void doPost(HttpServletRequest req, HttpServletResponse resp)
throws ServletException, IOException {
System.out.println("hello post");
doGet(req,resp);
}
}
创建 Servlet 的第三种方法,也是我们经常用的方法。
Servlet生命周期
Servlet 生命周期可被定义为从创建直到毁灭的整个过程。
Servlet 遵循的过程
- Servlet 通过调用 init () 方法进行初始化。
- Servlet 调用 service() 方法来处理客户端的请求。
- Servlet 通过调用 destroy() 方法终止(结束)。
- 最后,Servlet 是由 JVM 的垃圾回收器进行垃圾回收的。
生命周期方法
init()
- 只调用一次
init()
被设计成只调用一次。它在第一次创建 Servlet 时被调用,在后续每次用户请求时不再调用。因此,它是用于一次性初始化。 - 调用时机
Servlet 默认创建于用户第一次调用对应于该 Servlet 的 URL 时,但是也可以指定 Servlet 在服务器第一次启动时被加载。 - 线程
当用户调用一个 Servlet 时,就会创建一个 Servlet 实例,每一个用户请求都会产生一个新的线程,适当的时候移交给 doGet 或 doPost 方法。init() 方法简单地创建或加载一些数据,这些数据将被用于 Servlet 的整个生命周期。
定义如下:
public void init() throws ServletException {
// 初始化代码...
}
service() 方法
service() 方法是执行实际任务的主要方法。Servlet 容器(即 Web 服务器)调用 service() 方法来处理来自客户端(浏览器)的请求,并把格式化的响应写回给客户端。
每次服务器接收到一个 Servlet 请求时,服务器会产生一个新的线程并调用服务。service() 方法检查 HTTP 请求类型(GET、POST、PUT、DELETE 等),并在适当的时候调用 doGet、doPost、doPut,doDelete 等方法。
下面是该方法的特征:
public void service(ServletRequest request,
ServletResponse response)
throws ServletException, IOException{
}
service() 方法由容器调用,service 方法在适当的时候调用 doGet、doPost、doPut、doDelete 等方法。
所以不用对 service() 方法做任何动作,只需要根据来自客户端的请求类型来重写 doGet() 或 doPost()
destroy() 方法
destroy() 方法只会被调用一次,在 Servlet 生命周期结束时被调用。destroy() 方法可以让您的 Servlet 关闭数据库连接、停止后台线程、把 Cookie 列表或点击计数器写入到磁盘,并执行其他类似的清理活动。
在调用 destroy() 方法之后,servlet 对象被标记为垃圾回收
public void destroy() {
// 终止化代码...
}
架构图
下图显示了一个典型的 Servlet 生命周期方案。
- 第一个到达服务器的 HTTP 请求被委派到 Servlet 容器。
- Servlet 容器在调用 service() 方法之前加载 Servlet。
- 然后 Servlet 容器处理由多个线程产生的多个请求,每个线程执行一个单一的 Servlet 实例的 service() 方法。
![](https://img.haomeiwen.com/i11861611/2ee30a27604e98a3.jpg)
Servlet的生命周期可以被归纳为以下几步:
- 装载Servlet,这一项操作一般是动态执行的。然而,Servlet通常会提供一个管理的选项,用于在Servlet启动时强制装载和初始化特定的Servlet
- Server创建一个Servlet
实例
- Server调用Servlet的
init()
- 一个客户端请求到达Server
- Server创建一个请求对象
- Server创建一个响应对象
- Server激活Servlet的
service()
,传递请求和响应对象作为参数 -
service()
获得关于请求对象的信息,处理请求,访问其他资源,获得需要的信息 -
service()
使用响应对象的方法。将响应传回Server,最终到达客户端。Service方法可能激活其他方法以处理请求。如doGet,doPost或其他程序员自己开发的方法 - 对于更多的客户端请求,Server创建新的请求和响应对象,仍然激活此servlet的
service()
,将这两个对象作为参数传递给它,如此重复以上的循环,但无需再次调用init方法,Servlet一般只初始化一次 - 当Server不再需要Servlet时,比如当Server要关闭时,Server调用Servlet的
destroy()
简单总结:
只要访问Servlet,service()就会被调用。
init()只有第一次访问Servlet的时候才会被调用。
destroy()只有在Tomcat关闭的时候才会被调用。
参考文章
菜鸟教程Servlet 生命周期
网友评论