J2EE Servlet 管理机制

2023-05-16

  • Tomcat 9

Servlet 管理机制

(1)Servlet 对象,通过生命周期托管的方式实现单例设计模式

(2) 默认效果是延迟加载

以 Tomcat9 为例,需要在 web.xml 配置文件中为操作资源配置配置八行代码

<servlet>   
    <servlet-name>xxx</servlet-name>
    <servlet-class>controller.XxxController</servlet-class>
</servlet>

<servlet-mapping>
    <servlet-name>xxx</servlet-name>
    <url-pattern>/xxx</url-pattern>
</servlet-mapping>

为什么需要配置两部分,将请求名字与真实类名分开?
因为如果服务器启动时加载全部 Servlet 对象,成本压力非常大,所以采用延迟加载方式。Tomcat 启动时,读取 web.xml 配置文件,获取请求名与真实类名的对应关系;等到需要调用这个类时才生成对象。

(3)Servlet 对象生命周期:

Tomcat9 为了更好的管理对象的产生和销毁,提供了三个方法标识 Servlet 对象的生命周期

  1. init()
    Servlet对象创建的时候调用的,像似构造方法
  2. service()
    执行体
  3. destroy()
    Servlet对象被回收的时候调用的,像 finalize() 方法

如果你在控制层对象中重写了 init() 方法,你会发现该方法是在浏览器请求到该资源的时候才启动,也从侧面印证了Servlet 对象是延迟加载的。

(4)Servlet 加载方式改为立即加载

以 Tomcat9 为例,在 web.xml 配置文件中添加一行内容:

<servlet>   
    ...
    <load-on-startup>优先级</load-on-startup>
</servlet>

<servlet-mapping>
    ...
</servlet-mapping>
  • 优先级:正整数,数字越小,加载越早
  • Tomcat9 在启动时就会读取 web.xml 配置文件,只要配置了 <load-on-startup> 这一行内容,无论优先级数字是大还是小,都是立即加载方式。优先级数字的大小是控制多个 Servlet 对象的立即加载顺序而已

(5)Servlet 对象加载时,可以携带信息

以 Tomcat9 为例,在 web.xml 配置文件中添加以下内容:

<servlet>   
    ...
    <init-param>
		<param-name>key1</param-name>
        <param-value>value1</param-value>
    </init-param>
    ...
    <init-param>
        <param-name>keyN</param-name>
        <param-value>valueN</param-value>
	</init-param>
</servlet>

<servlet-mapping>
    ...
</servlet-mapping>

与此对应的,Servlet 对象生命周期的 init() 方法有一个重载方法读取 Servlet 对象加载时携带的信息

public void init(ServletConfig config){
	
	String value = config.getInitParameter("key");//某一个key对应的value
	
	Enumeration en = config.getInitParameterNames();//获取全部的key
	
	String name = config.getServletName();//获取当前Servlet类名
	
	ServletContext application = config.getServletContext();//获取全局上下文对象,JSP九大内置对象之一
}

(6)Servlet 类的继承关系
在这里插入图片描述
接口 ServletConfig,源码

public interface ServletConfig {
    String getServletName();

    ServletContext getServletContext();

    String getInitParameter(String var1);

    Enumeration<String> getInitParameterNames();
}

接口 Servlet,源码

public interface Servlet {
    void init(ServletConfig var1) throws ServletException;

    ServletConfig getServletConfig();

    void service(ServletRequest var1, ServletResponse var2) throws ServletException, IOException;

    String getServletInfo();

    void destroy();
}

抽象类 GenericServlet,源码

实现三个接口,体现了缺省适配器模式;从接口中继承了全部方法,总共9个,其中8个方法都进行了方法重写(添加具体实现),除了 service() 方法,子类必须重写:

public abstract void service(ServletRequest var1, ServletResponse var2) throws ServletException, IOException;

多了一个 init() 无参的重载方法,

public void init() throws ServletException {}

和两个 log() 方法

public void log(String message) {
	this.getServletContext().log(this.getServletName() + ": " + message);
}

public void log(String message, Throwable t) {
    this.getServletContext().log(this.getServletName() + ": " + message, t);
}

抽象类 HttpServlet

体现了面向对象的编程思想(具体化的说明和体现)肯定是跟HTTP协议有关

  • 添加了很多具体的属性,都与协议有关,比如 get、post 。。。
  • 添加了很多具体的与请求方式对应的方法,比如 doGet、doPost 。。。
  • 添加了几个自己独有的方法,比如 getLastModifer、sendMethodNotAllowed、maybeSetLastModified、getAllDeclaredMethods
  • 实现了 service 方法,并添加了具体实现
    • 方法内部先通过 request.getMethod(); 获取请求的方式 get/post/xxx
    • 找寻对应请求方式的方法执行 doPost 或 doGet 或 doXxx,实际上做事的是处理 HTTP 协议的一个类

我们自己写的 Servlet 类

  1. 自己写一个类
    • 可以继承 HttpServlet
    • 可以继承 GenericServlet,重写service方法,将两个参数转型成HTTP
    • 可以直接实现 Servlet 接口,重写五个方法,init、service、destroy 。。。
  2. 重写方法,可以重写 doPost、doGet、service 。。。
  3. 方法的参数和异常与常规 service 方法一致
  4. 别忘了配置 web.xml 文件
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

J2EE Servlet 管理机制 的相关文章

随机推荐