一文了解 Servlet
1.什么是 Servlet
Servlet(Server Applet
)是 Java Servlet 的简称,称为 小服务程序 或 服务连接器,用 Java 编写的服务器端程序,具有独立于平台和协议的特性,主要功能在于交互式地浏览和生成数据,生成动态 Web 内容。
狭义的 Servlet 是指 Java 语言实现的一个接口,广义的 Servlet 是指任何实现了这个 Servlet 接口的类,一般情况下,人们将 Servlet 理解为后者。Servlet 运行于支持 Java 的应用服务器中。从原理上讲,Servlet 可以响应任何类型的请求,但绝大多数情况下 Servlet 只用来扩展基于 HTTP 协议的 Web 服务器。
- Servlet 是 Java 提供的一门动态 Web 资源开发技术。
- Servlet 是 JavaEE 规范之一,其实就是一个接口,将来我们需要定义 Servlet 接口,并由 Web 服务器运行 Servlet。
2.Servlet 快速入门
创建 Web 项目,导入 Servlet 依赖坐标。
<dependencies>
<dependency>
<groupId>javax.servlet</groupId>
<artifactId>javax.servlet-api</artifactId>
<version>3.1.0</version>
<scope>provided</scope>
</dependency>
</dependencies>
创建:定义一个类,实现 Servlet 接口,并重写接口中的所有方法,并在 service
方法中输入一句话。
public class Demo01 implements Servlet {
@Override
public void init(ServletConfig servletConfig) throws ServletException {
}
@Override
public ServletConfig getServletConfig() {
return null;
}
@Override
public void service(ServletRequest servletRequest, ServletResponse servletResponse) throws ServletException, IOException {
System.out.println("hello");
}
@Override
public String getServletInfo() {
return null;
}
@Override
public void destroy() {
}
}
配置:在类上使用 @WebServlet 注解,配置该 Servlet 的访问路径。
@WebServlet("/demo01")
访问:启动 Tomcat,浏览器输入URL,访问该 Servlet。
3.Servlet 生命周期
Servlet 生命周期就是 Servlet 从创建到销毁的过程。
我们做一个简单的测试。
@WebServlet("/demo01")
public class Demo01 implements Servlet {
@Override
public void init(ServletConfig servletConfig) throws ServletException {
System.out.println("初始化方法");
}
@Override
public void service(ServletRequest servletRequest, ServletResponse servletResponse) throws ServletException, IOException {
System.out.println("hello");
}
@Override
public void destroy() {
System.out.println("销毁方法");
}
分别在 init
方法、service
方法、destroy
方法输出语句。运行时发现 init
方法调用一次,之后通过不断刷新,会重复调用 service
方法,直至关掉服务器调用 destroy
方法。
这样我们发现,只有访问网页,Servlet 才会进行初始化,那如何在服务器启动的时候就加载 Servlet。
解决方法:为注解添加参数。
@WebServlet(value = "/demo01", loadOnStartup = 1)
- 负整数:第一次访问时创建 Servlet 对象。
- 0 0 0 或正整数:服务器启动时创建 Servlet 对象,数字越小优先级越高。
4.Servlet 体系结构
大部分开发 B/S 架构的 Web 项目,都是针对 HTTP 协议,所以我们自定义 Servlet,会继承 HttpServlet。
@WebServlet("/demo03")
public class Demo3 extends HttpServlet {
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
System.out.println("这是demo3,doGet");
}
@Override
protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
System.out.println("demo3 doPost");
}
}
要想发送一个 GET 请求,请求该 Servlet,只需要通过浏览器发送 http://localhost:8080/web-demo/demo3
,就能看到 doGet 方法被执行了。
要想发送一个 POST 请求,请求该 Servlet,单单通过浏览器是无法实现的,这个时候就需要编写一个 form
表单来发送请求,在 webapp
下创建一个 a.html
页面,内容如下:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>get & post</title>
</head>
<body>
<h1>GET</h1>
<form action="login" method="get">
用户:<input type="text" name="username"><br>
密码:<input type="password" name="password"><br>
<input type="submit" value="登录">
</form>
<form action="login" method="post">
用户:<input type="text" name="username"><br>
密码:<input type="password" name="password"><br>
<input type="submit" value="登录">
</form>
</body>
</html>
启动测试,即可看到 doPost 方法被执行了。
5.urlPatern 配置
Servlet 类编写好后,要想被访问到,就需要配置其访问路径(urlPattern
)。
@WebServlet(value = "/demo01", loadOnStartup = 1)
一个 Servlet,可以配置多个 urlPattern
。
5.1 urlPattern 配置规则
5.1.1 精确匹配
/**
配置路径
*/
@WebServlet(value = "/order/demo04")
访问路径:localhost:9999/Tomcat_war_exploded/order/demo04
5.1.2 目录匹配
/**
配置路径
*/
@WebServlet(value = "/order/*")
访问路径:localhost:9999/Tomcat_war_exploded/order/任意
。
表示 order
目录下的所有路径都能够访问。
5.1.3 扩展名匹配
/**
配置路径
*/
@WebServlet(value = "*.do")
访问路径:localhost:9999/Tomcat_war_exploded/order/任意.do
5.1.4 任意匹配
/**
配置路径
*/
@WebServlet(value = "/*")
访问路径:localhost:9999/Tomcat_war_exploded/任意
5.2 访问优先级
- 前缀匹配高于后缀匹配
- 匹配原则:最佳匹配原则,哪个接近就访问哪个
- 优先级顺序:精确匹配
>
目录匹配>
任意匹配>
后缀匹配
6.XML 编写 Servlet
Servlet 从 3.0 版本后开始支持使用注解配置,3.0 版本前只支持 XML 配置文件的配置方法。
6.1 编写 Servlet 类
public class demo5 extends HttpServlet {
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
System.out.println("这是demo5,doGet");
}
@Override
protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
System.out.println("这是demo5, doPost");
}
}
6.2 在 web.xml 中配置该 Servlet
<!--给serlvet取名字-->
<servlet>
<servlet-name>demo5</servlet-name>
<servlet-class>org.example.servlet.demo5</servlet-class>
</servlet>
<!--根据servlet名字配置路径-->
<servlet-mapping>
<servlet-name>demo5</servlet-name>
<url-pattern>/demo5</url-pattern>
</servlet-mapping>
这种配置方式和注解比起来,确实麻烦很多,所以建议大家使用注解来开发。但是大家要认识上面这种配置方式,因为并不是所有的项目都是基于注解开发的。