Servlet初识

Mr.he...大约 5 分钟JavaWebServlet

1. Servlet入门

1.1 概念

Servlet(server applet)是运行在服务器端的小程序。

  • Servlet就是一个接口,定义了Java类被浏览器访问到(tomcat识别)的规则;
  • 使用时需要自定义一个类来实现Servlet接口,复写Servlet接口的方法。

动态资源:不同的人访问的资源可能不一样。

1.2 快速入门

  1. 创建一个JavaWEB项目
  2. 定义一个类,实现Servlet接口,代码为public class ServletDemo1 implements Servlet
  3. 覆写接口中的抽象方法
  4. 配置Servlet,在web.xml中配置Servlet,并映射虚拟路径。
  5. 启动Tomcat服务器,并访问相应虚拟路径;

1.3 执行原理

  1. 当服务器接收到客户端浏览器的请求后,会解析请求URL路径,获取访问的Servlet的资源路径;
  2. 查找web.xml文件,是否有对应的<url-pattern>标签体内容;
  3. 如果有,则再找到对应的<servlet-class>全类名;
  4. tomcat会将字节码文件加载进内存,并且创建其对象;
  5. 调用其方法。

1.4. Servlet的生命周期

Servlet中的生命周期主要有Servlet被创建时执行一次的init方法,提供服务的service方法和正常关闭服务器时执行一次的destroy方法。

1.4.1 init方法

被创建时执行init方法,只执行一次,Servlet默认情况下,第一次被访问时,Servlet被创建。

  • 可以在web.xml中的<servlet>标签下配置执行Servlet的创建时机。
    1. 第一次被访问时,创建; <load-on-startup>的值为负数
    2. 在服务器启动时,创建。 <load-on-startup>的值为0或正整数
    <servlet>
        <servlet-name>demo1</servlet-name>
        <servlet-class>hek.web.servlet.ServletDemo1</servlet-class>
        <load-on-startup>-1</load-on-startup>
    </servlet>

Servlet的init方法,只执行一次,说明一个Servlet在内存中只存在一个对象,Servlet是单例的。

  1. 多个用户同时访问时,可能存在线程安全问题。
  2. 解决方法:尽量不要在Servlet中定义成员变量。即使定义了成员变量,也不要对修改值

1.4.2 service方法

提供服务时执行service方法,可执行多次。

  • 每次访问Servlet时,Service方法都会被调用一次。

1.4.3 destroy方法

被销毁时执行destroy方法,只执行一次。

  1. 服务器关闭时,Servlet被销毁。
  2. 只有服务器正常关闭时,才会执行destroy方法。
  3. destroy方法在Servlet被销毁之前执行,一般用于释放资源。

1.5 Servlet的注解配置

Servlet3.0以上支持注解配置。可以不需要web.xml了。

1.5.1 使用步骤

  1. 创建JavaEE项目,选择Servlet的版本3.0以上,不创建web.xml;
  2. 定义一个类,实现Servlet接口
  3. 复写Servlet的方法
  4. 在类上使用@WebServlet注解,进行配置,代码@WebServlet("/资源路径")

资源路径必须加上反斜线,不然会报错。

1.5.2 实现原理

WebServlet的注解中对XML的配置给了默认值,可根据自己的需求进行传入参数,默认传入的为资源路径。

@Target({ElementType.TYPE})
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface WebServlet {
String name() default "";//相当于<Servlet-name>

String[] value() default {};//代表urlPatterns()属性配置

String[] urlPatterns() default {};//相当于<url-pattern>,这也是默认传入值

int loadOnStartup() default -1;//相当于<load-on-startup>

WebInitParam[] initParams() default {};

boolean asyncSupported() default false;

String smallIcon() default "";

String largeIcon() default "";

String description() default "";

String displayName() default "";
}

默认传入的是虚拟目录路径。

2. Servlet进阶

在入门阶段学习了Serlet的概念、使用步骤、执行原理、生命周期、注解配置。现在学习更多的Servlet的知识。

2.1 Servlet的体系结构

Servlet -- 接口
	|
GenericServlet -- 抽象类
	|
HttpServlet  -- 抽象类

2.1.1 GenericServlet

将Servlet接口中其他的方法做了默认空实现,只将service()方法作为抽象方法,将来定义Servlet类时,可以继承GenericServlet,实现service()方法即可。

了解即可,真正开发时不用这种方式。

2.1.2 HttpServlet

对http协议的一种封装,简化操作。

2.1.2.1 使用步骤
  1. 定义类继承HttpServlet
  2. 复写doGet/doPost方法
//为保持简介已去掉导包代码
@WebServlet("/demo")
public class ServletDemo extends HttpServlet {
    @Override
    protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        System.out.println("doPost...");
    }

    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        System.out.println("doGet...");
    }
}
  1. 使用doGet方法,默认情况下直接访问该路径就是get请求,触发该方法。
  2. 使用doPost方法,最简单的方式为建立一个表单页面(login.html),然后访问表单的路径(/login.html),使用post方法将信息提交到/demo路径下。
<!-- web目录下的login.html 表单-->
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>login</title>
</head>
<body>
<form action="/demo" method="post">
    <input type="text">
    <button type="submit">提交</button>
</form>
</body>
</html>

2.2 Servlet访问路径

一个Servlet可以定义多个访问路径 ,如@WebServlet({"/d4","/dd4","/ddd4"}),然后可以通过其中的任意一个路径进行访问到该资源。

2.2.1 路径定义规则

  1. /xxx:路径匹配
  2. /xxx/xxx:多层路径,目录结构
  3. *.do:扩展名匹配