HttpServlet的生命周期是什么?

基本上,servlet的实例有多长? 我有点猜测它是会话范围。 但是,我想它可能有某种超时或垃圾收集来删除旧实例。

  • 应用程序启动时(在servlet容器上部署)或首次访问时创建servlet(取决于load-on-startup设置)
  • 实例化servlet时,调用servlet的init()方法
  • 然后servlet(它的唯一实例)处理所有请求(由多个线程调用其service()方法)。 这就是为什么不建议在其中进行任何同步,并且应该避免servlet的实例变量
  • 取消部署应用程序时(servlet容器停止),将调用destroy()方法。

生命周期定义良好,并通过Servlet的init,service和destroy方法中公开的生命周期方法公开。

而且,尽管这里还有其他内容,但这是您可以依赖的规范。 基本上,您可以获得这三种方法,并保证Servlet不是线程安全的。 可以通过一个或多个请求同时访问单个servlet。

规范中没有任何内容将servlet限制为容器的一个实例,如果容器决定,它可以获取请求,创建servlet,调用它的init,然后服务,然后销毁方法,并将其设置为垃圾收集。

单个容器具有可能不同的实现。

大多数容器都会创建一个实例。 但规范并不保证,所以你不应该依赖它。

此外,请考虑像Google App Engine这样的东西。 GAE是非常积极的,不断到期并关闭整个没有流量的网络应用程序。 如果你有一个轻松旅行的网站,你可以很好地期望整个应用程序启动,初始化它的所有服务,初始化任何加载启动servlet,执行请求,然后关闭所有内容。 因此,在GAE上,为了保持任何表面性能,您必须拥有非常快速的应用程序启动。

因此,简单地说,您可以依赖的是规范所说的内容。 单个容器可以提供不同的运行时间体验。

只要应用程序执行,Servlet就会存在。

servlet不绑定到会话,它是一个服务对象,在需要时由容器实例化,并且通常在webapp的整个生命周期中保持活动状态。 它通常响应来自多个客户端(和会话)的请求,甚至是并发请求。 这正是您的servlet代码必须是线程安全的原因,并且您永远不会在servlet字段中存储与请求或会话相关联的一些数据。

servlet生命周期可以定义为从创建到销毁的整个过程。 以下是servlet遵循的路径

  • 通过调用init()方法初始化servlet。
  • servlet调用service()方法来处理客户端的请求。
  • 通过调用destroy()方法终止servlet。
  • 最后,servlet被JVM的垃圾收集器垃圾收集。

更多这里..

http://www.dzone.com/links/r/java_ee_servlets_life_cycle.html

当我记得正确的servlet在Servlet容器(例如Tomcat)中作为单例生存时。 我不确定第一个实例是否是惰性的,这意味着Servlet只在需要时才构造,但我猜测可以在相应的Servlet Container的Classloader源中检查它。 Servlet的生命周期结束,当Servlet容器关闭时,它会调用destroy()方法。 您可以通过设置断点或登录相应的init()destroy()方法以及构造函数来轻松检查,然后检查代码何时在调试器/日志文件中执行。

希望有所帮助。

参考文献: Tomcat的Classloader howto

servlet(它的唯一实例)将以每个客户端的单独单线程的方式处理n个请求,即克服CGI限制的地方

只要取消部署应用程序或关闭servletConatiner,servlet对象就会存在于服务器端机器的堆中,servlet对象不会死亡。

从技术上讲:servletcontainer持有servletobject,servletobject持有servletConfig对象

Servletcontainer只能调用其生命周期的3个方法1)init()2)service()3)destroy()

实际上Servlet可能随时被销毁和重建! 所以其他答案有点描述整个生命周期,但错过了这个重要的细节。 从servlet规范:

servlet容器不需要在任何特定时间段内加载servlet。 对于servlet容器的生命周期(可能是几天,几个月或几年),或者介于两者之间的任何时间量,servlet实例可以在servlet容器中保持活动状态一段时间。

[…]

在servlet实例上调用destroy方法后,容器可能不会将其他请求路由到该servlet实例。 如果容器需要再次启用servlet,则必须使用servlet类的新实例。

在Tomcat上运行的典型servlet的生命周期可能如下所示:

1.Tomcat通过其中一个连接器接收客户端的请求。

2.Tomcat将此请求映射到适当的Engine以进行处理。 这些引擎包含在其他元素中,例如主机和服务器,这些元素限制了Tomcat搜索正确引擎的范围。

3.一旦请求被映射到适当的servlet,Tomcat就会检查是否已加载该servlet类。 如果没有,Tomcat将servlet编译为Java字节码,该字节码可由JVM执行,并创建servlet的实例。

4.Tomcat通过调用其init方法初始化servlet。 servlet包含能够读取Tomcat配置文件并相应地执行操作的代码,以及声明它可能需要的任何资源,以便Tomcat可以以有序,可管理的方式创建它们。

5.一旦初始化了servlet,Tomcat就可以调用servlet的服务方法来处理请求,该请求将作为响应返回。

6.在servlet的生命周期中,Tomcat和servlet可以通过使用监听器类进行通信,监听器类监视servlet以进行各种状态更改。 Tomcat可以以各种方式检索和存储这些状态更改,并允许其他servlet访问它们,从而允许状态在单个或多个用户会话的跨度内由给定上下文的各个组件进行维护和访问。 实现此function的一个示例是电子商务应用程序,该应用程序记住用户已添加到购物车的内容并能够将此数据传递到结帐流程。

7.Tomcat调用servlet的destroy方法来平滑地删除servlet。 此操作由正在侦听的状态更改触发,或者由传递给Tomcat的外部命令触发,以取消部署servlet的Context或关闭服务器。

参考:

https://www.mulesoft.com/tcat/tomcat-servlet

 life cycle of servlet > 1) load the class. 2) instantiate the servlet. 3) servlet container construct the servlet config interface. 4) container call the init() and pass the servlet config object. 5) httpRequest and httpResponse object created. 6) container call the service() and pass the httpRequest and httpResponse object as argument. 7) process the service method.and if have any other request then follow the step 4 again. 8) other wise container call the distroy(). 

servlet的容器​​连接到Web服务器,该服务器侦听特定端口号上的HTTP或HTTPS请求(端口8080通常在开发期间使用,端口80在生产中使用)。 当客户端(具有Web浏览器的用户)发送HTTP请求时,servlet容器会创建新的HttpServletRequestHttpServletResponse对象(针对每个新请求),并将它们传递给任何已定义的Filter链,最终传递给Servlet实例。

在filter的情况下,调用doFilter()方法。 当其代码调用chain.doFilter(request, response) ,请求和响应将继续执行下一个filter,或者如果没有剩余filter则命中servlet。

在servlet的情况下,调用service()方法(由多个线程用于不同的请求)。 默认情况下,此方法根据request.getMethod()确定要调用哪个doXxx()方法。 如果servlet中没有确定的方法,则在响应中返回HTTP 405错误。

请求对象提供对HTTP请求的所有信息的访问,例如其标题和正文。 响应对象提供了以您希望的方式控制和发送HTTP响应的function,例如,允许您设置标头和正文(通常使用JSP文件中生成的HTML内容)。 提交并完成HTTP响应后,请求和响应对象都将被回收并重新使用。