关于Servlet的学习我觉得明白如下两张图就能够基本就能入门,犹如打通任督二脉,下面将按Servlet—GenericServlet—HttpServlet的顺序来记录他们之间的联系及相关内容。以下内容为个人学习记录,如有不对还请指正。
Servlet接口
Servlet的运行流程
- ServletRequest由Servlet容器来管理
- 当客户请求到来时,容器创建一个ServletRequest对象,封装请求数据
- 同时创建- -个ServletResponse对象,封装响应数据
- 这两个对象将被容器作为service()方法的参数传递给Servlet
- Servlet利用ServletRequest对象获取客户端发来的请求数据
- 完成逻辑,利用ServletResponse对象发送响应数据。
知道了Servlet的运行流程,那一个Servlet的具体实现又是怎么样的呢?要知道一个人我们要先去了解他的一生,同样的了解Servlet也是如此,一个Servlet的生命周期如下图。
整个的运作过程都是通过一些方法实现的,具体的内容我们去源码里寻找答案。以下为Servlet接口的源码
package javax.servlet;
import java.io.IOException;
public interface Servlet {
public void init(ServletConfig config) throws ServletException;
public ServletConfig getServletConfig();
public void service(ServletRequest req, ServletResponse res)
public String getServletInfo();
public void destroy();
这五个抽象方法体现了一个Servlet的生命周期,但是看着这里还是有点抽象,那么试着编写一个简单的Servlet
import java.io.IOException;
import java.io.PrintWriter;
import javax.servlet.Servlet;
import javax.servlet.ServletConfig;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.annotation.WebServlet;
@WebServlet(name = "MyServlet", urlPatterns = {
"/my" })
public class MyServlet implements Servlet {
private transient ServletConfig servletConfig;
@Override
public void init(ServletConfig servletConfig)
throws ServletException {
this.servletConfig = servletConfig;
}
@Override
public ServletConfig getServletConfig() {
return servletConfig;
}
@Override
public String getServletInfo() {
return "My Servlet";
}
@Override
public void service(ServletRequest request,
ServletResponse response) throws ServletException,
IOException {
String servletName = servletConfig.getServletName();
response.setContentType("text/html");
PrintWriter writer = response.getWriter();
writer.print("<html><head></head>"
+ "<body>Hello from " + servletName
+ "</body></html>");
}
@Override
public void destroy() {
//如果连接了数据库等等这里就断开关闭数据库
}
}
那么其中ServletConfig又是什么?ServletRequest和ServletResponse又是些什么呢?初次看这段代码可能不是很理解,但是没关系,通过下面的自主学习你就能完全理解。
ServletRequest和ServletResponse接口
ServletRequest和ServletResponse这里是根据Http协议传递的内容,用键值对的形式存储的,记住键值对这个概念!!!如果对这里完全没有印象可以参考我之前的一篇文章中对HTTP基础知识的一些补充https://blog.csdn.net/weixin_44164333/article/details/104580476,ServletRequest的常用方法有如下内容(只是主要常用,不完全):
Parameter是Http协议传递的值,这里的Attribute则与客户端无关。服务器端接收后产生的一个Request对象,可能在各个不同的Servlet间传递而进行必要的处理,这时我们可以在Servlet A中通过setAttribute(String name,Object)方法存储一些信息,然后在Servlet B中通过getAttribute(String name)方法,取出相关的Object对象,进行一些处理。由于本文是为了讲解3个接口的联系,所以在这些问题上不详说。
Parameter和Attribute可参考https://www.cnblogs.com/bigbigbigo/p/10052178.html
Header和Path Elements参考https://blog.csdn.net/handsome_boy_wsq/article/details/82822186
https://blog.csdn.net/weixin_41547486/article/details/81266697
https://blog.csdn.net/weixin_43453386/article/details/83792682?depth_1-utm_source=distribute.pc_relevant.none-task&utm_source=distribute.pc_relevant.none-task(请按我链接顺序阅读学习,这些文章我都阅读了,觉得对理解有很大帮助,于是按理解顺序排列推荐)
ServletResponse的常见使用方法参考https://www.cnblogs.com/youngchaolin/p/11533181.html
其实遇到一些不知道的API(方法或接口)可以去查官方API文档。
ServletConfig接口
ServletConfig顾名思义代表当前Servlet在web.xml中的配置信息
String getServletName() – 获取当前Servlet在web.xml中配置的名字
在Servlet的配置文件中,可以使用一个或多个标签为servlet配置一些初始化参数。
当servlet配置了初始化参数后,web容器在创建servlet实例对象时,会自动将这些初始化参数封装到ServletConfig对象中,并在调用servlet的init方法时,将ServletConfig对象传递给servlet。进而,程序员通过ServletConfig对象就可以得到当前servlet的初始化参数信息。
这样做的好处是:如果将数据库信息、编码方式等配置信息放在web.xml中,如果以后数据库的用户名、密码改变了,则直接很方便地修改web.xml就行了,避免了直接修改源代码的麻烦。
String getInitParameter(String name) – 获取当前Servlet指定名称的初始化参数的值
Enumeration getInitParameterNames() – 获取当前Servlet所有初始化参数的名字组成的枚举
ServletContext getServletContext() – 获取代表当前web应用的ServletContext对象
ServletContext接口
ServletContext是什么?
从下面图示可以看出WEB容器在启动时,它会为每个WEB应用程序都创建一个对应的ServletContext对象,它代表当前web应用。
ServletConfig对象中维护了ServletContext对象的引用,开发人员在编写servlet时,可以通过ServletConfig.getServletContext方法获得ServletContext对象。
由于一个WEB应用中的所有Servlet共享同一个ServletContext对象,因此Servlet对象之间可以通过ServletContext对象来实现通讯。
有如下常用方法,详细参考https://www.cnblogs.com/qianguyihao/p/4140877.html
Servlet接口到这里已经有大致的了解了,知识体系已经差不多成功搭建。
注意今天所说的这些全部都是接口!!方法返回的是接口的实现类对象,实现类由Tomcat提供,在这你所见到的接口,自己没有写过它的实现类,它的实现类由Tomcat提供。如:Servlet是接口,我们只写该类,并没有实例化,是Tomcat提供的实例化对象。
下一篇文章将记录GenericServlet和HTTPServlet接口是如何从Servlet演变封装而来的。
文末附上API使用方法:https://blog.csdn.net/wenzhi20102321/article/details/52431519