Servlet的继承关系:
Servlet接口介绍:
1、init方法在容器启动时被容器(如:Tomcat)调用(当 load-on-startup 设置为负数或者不设置时会在Servlet第一次用到时才被调用),只会调用一次。
2、getServletConfig 方法用于获取ServletConfig。
3、service方法用于具体处理一个请求。
4、getServletInfo方法可以获取一些Servlet相关的信息,如 作者、版权等,这个方法需要自己实现,默认返回空字符串。
5、destory 主要用于在Servlet销毁(一般指关闭服务器)时释放一些资源,也只会调用一次。
init方法被调用时会接收到一个ServletConfig类型的参数,是容器传进去的。Servlet-config 顾名思义指的是Servlet的配置,我们在web.xml中定义Servlet时通过init-param标签置的参数就是通过SevletConfig来保存的。
Web程序和容器的关系
![](/qrcode.jpg)
我们都知道程序的唯一入口是main方法,有没有发现我们编写的Web程序中是不需要写main方法的,没有main方法的JavaWeb程序为什么以运行? 其实,Web程序单独是不能运行的,只有放到容器中才能运行。容器是有main方法的,容器读取web程序的web.xml文件,通过反射的方式实例化Servlet、Filter、Listener等。虽然我们实例化Servlet、Filter、Listener等,但是我们并不知道这些类中方法是干什么的,为了解决这个问题,采用了面向接口编程的方式,Servlet.jar是容器和Web程序沟通的桥梁,Servlet.jar 包中定义了许多接口。我们会发现 容器中会有Servlet.jar这个包,我们开发项目时也会有这个jar包,但是我们发布的项目却不要包该jar包,因为容器中已经有了,如果包含可能会发生版本冲突的问题。
Tomcate中Servlet的init方法是在org.apache.catelina.core.standardWrapper的initServlet方法中调用的initServlet方法中调用的,ServletConfig传入的是StandardWrapper自身的面类StandardWrapperFacade(ServletConfig的实现类)。在web项目引入的jar包中是找不到StandardWrapperFacade类的,因为这些类在Tomcat中。在调试时是无法进入到Tomcat容器中的jar包的。所以我们要手动的将tomcat目录下的catalina.jar包导入到我们项目里。如果是maven引入要注意引入的版本,解压catalina.jar,打开MANIFEST.MF文件,Implementation-Version就是版本号。
<dependency>
<groupId>org.apache.tomcat</groupId>
<artifactId>tomcat-catalina</artifactId>
<version>8.5.12</version>
</dependency>
ServletConfig接口介绍:
1、getServletName 用于获取Servlet的名字,也就是我们在web.xml中定义的servlet-name。
2、getInitParameter 方法用于获取init-param配置的参数;
3、getInitParameterNames用于获取配置的所有init-param的名称集合。
4、getServletContext非常重要,他的返回值ServletContext代表的是我们这个应用本身,既然ServletContext代表应用本身,那么ServletContext里面设置的参数就可以被当前应用的所有Servlet共享了。我做项目的时候都知道参数可以保存在Session中,也可以保存在Application中。而后者很多时候就是保存在了ServletContext中。
实例:
web.xml:
<context-param>
<param-name>company</param-name>
<param-value>xiaoMi</param-value>
</context-param>
<servlet>
<servlet-name>userServlet</servlet-name>
<servlet-class>servletTest.UserServlet</servlet-class>
<init-param>
<param-name>name</param-name>
<param-value>xiaoHong</param-value>
</init-param>
<init-param>
<param-name>sex</param-name>
<param-value>female</param-value>
</init-param>
<load-on-startup>1</load-on-startup>
</servlet>
<servlet-mapping>
<servlet-name>userServlet</servlet-name>
<url-pattern>/user</url-pattern>
</servlet-mapping>
Servlet:
public class UserServlet extends HttpServlet {
@Override
public void init(ServletConfig config) throws ServletException {
Enumeration enumeration = config.getInitParameterNames();//获取参名称集合
while (enumeration.hasMoreElements()) {//遍历
String name = enumeration.nextElement().toString();
String value = config.getInitParameter(name);//获取值
System.out.println("name=" + name + ";value=" + value);
}
String servletName = config.getServletName();
System.out.println("servletName=" + servletName);
System.out.println("--------------servletContext----------------");
ServletContext servletContext = config.getServletContext();
Enumeration enumeration1= servletContext.getInitParameterNames();
while (enumeration1.hasMoreElements()) {//遍历
String name = enumeration1.nextElement().toString();
String value = servletContext.getInitParameter(name);//获取值
System.out.println("name=" + name + ";value=" + value);
}
}
}
结果:
name=sex;value=female
name=name;value=xiaoHong
servletName=userServlet
--------------servletContext----------------
name=company;value=xiaoMi
上面通过context-param配置的company配置到了ServletContext中,而通过servlet下的init-param配置的sex和name配置到了ServletConfig中。