0%

HTTP协议详解

  • HTTP协议详解、HttpServlet源码分析

2.HTTP

2.1 ★★★HTTP协议详解

2.1.1 HTTP协议

  • 什么是协议?

    • 协议实际上是某些人,或者某些组织提前制定好的一套规范,大家都按照这个规范来,这样可以做到沟通无障碍。
    • 协议就是一套规范,就是一套标准。由其他人或其他组织来负责制定的。
    • 我说的话你能听懂,你说的话,我也能听懂,这说明我们之间是有一套规范的,一套协议的,这套协议就是:中国普通话协议。我们都遵守这套协议,我们之间就可以沟通无障碍。
  • 什么是 HTTP 协议?

    • HTTP 协议:是 W3C 制定的一种超文本传输协议。(通信协议:发送消息的模板提前被制定好。)
      • W3C(World Wide Web Consortium):
        • 万维网联盟组织
        • 负责制定标准的:HTTP、HTML4.0、HTML5、XML、DOM 等规范都是 W3C 制定的。
        • 万维网之父:蒂姆·伯纳斯·李
      • 什么是超文本?
        • 超文本说的就是:不是普通文本,比如流媒体:声音、视频、图片等。
        • HTTP协议支持:不但可以传送普通字符串,同样支持传递声音、视频、图片等流媒体信息。
      • 这种协议游走在 B 和 S 之间。B 向 S 发数据要遵循 HTTP 协议,S 向 B 发数据同样需要遵循 HTTP 协议。这样 B 和 S 才能解耦合。
    • 什么是解耦合?
      • B 不依赖 S。
      • S 也不依赖 B。
    • B/S 表示:B/S 结构的系统(浏览器访问 WEB服务器的系统)
      • 浏览器WEB服务器 发送数据,叫做:请求(request
      • WEB服务器浏览器 发送数据,叫做:响应(response
    • HTTP协议包括:
      • 请求协议:浏览器 向 WEB服务器 发送数据的时候,这个发送的数据需要遵循一套标准,这套标准中规定了发送的数据具体格式。
      • 响应协议:WEB服务器 向 浏览器 发送数据的时候,这个发送的数据需要遵循一套标准,这套标准中规定了发送的数据具体格式。
    • HTTP协议就是提前制定好的一种消息模板。
      • 不管你是哪个品牌的 浏览器,都是这么发。
      • 不管你是哪个品牌的 WEB服务器,都是这么发。
      • FF浏览器 可以向 Tomcat发送请求,也可以向 Jetty服务器发送请求。浏览器不依赖具体的服务器品牌。
      • WEB服务器也不依赖具体的浏览器品牌。可以是FF浏览器,也可以是Chrome浏览器,可以是IE,都行。

2.1.2 HTTP的请求协议

  • HTTP 的请求协议(B –> S)

    • HTTP 的请求协议包括:4 部分

      • 请求行
        • 包括三部分:
          • 第一部分:请求方式(7种)
            • get(常用的)
            • post(常用的)
            • delete
            • put
            • head
            • options
            • trace
          • 第二部分:URI
            • 什么是 URI? 统一资源标识符。代表网络中某个资源的名字。但是通过 URI 是无法定位资源的。
            • 什么是 URL?统一资源定位符。代表网络中某个资源,同时,通过 URL 是可以定位到该资源的。
            • URI 和 URL 什么关系,有什么区别?
          • 第三部分:HTTP协议版本号
      • 请求头
        • 请求的主机
        • 主机的端口
        • 浏览器信息
        • 平台信息
        • cookie等信息
      • 空白行
        • 空白行是用来区分“请求头”和“请求体”
      • 请求体
        • 向服务器发送的具体数据
    • 怎么查看的协议内容?

      • 使用浏览器:F12。然后找到network,通过这个面板可以查看协议的具体内容。
    • HTTP 请求协议的具体报文:GET 请求:

      1
      2
      3
      4
      5
      6
      7
      8
      9
      10
      11
      12
      13
      14
      15
      16
      17
      18
      GET /servlet05/getServlet?username=lucy&userpwd=1111 HTTP/1.1        请求行
      Host: localhost:8080 请求头
      Connection: keep-alive
      sec-ch-ua: "Google Chrome";v="95", "Chromium";v="95", ";Not A Brand";v="99"
      sec-ch-ua-mobile: ?0
      sec-ch-ua-platform: "Windows"
      Upgrade-Insecure-Requests: 1
      User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/95.0.4638.54 Safari/537.36
      Accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3;q=0.9
      Sec-Fetch-Site: same-origin
      Sec-Fetch-Mode: navigate
      Sec-Fetch-User: ?1
      Sec-Fetch-Dest: document
      Referer: http://localhost:8080/servlet05/index.html
      Accept-Encoding: gzip, deflate, br
      Accept-Language: zh-CN,zh;q=0.9
      空白行
      请求体
    • HTTP 请求协议的具体报文:POST 请求:

      1
      2
      3
      4
      5
      6
      7
      8
      9
      10
      11
      12
      13
      14
      15
      16
      17
      18
      19
      20
      21
      22
      POST /servlet05/postServlet HTTP/1.1                                 请求行
      Host: localhost:8080 请求头
      Connection: keep-alive
      Content-Length: 25
      Cache-Control: max-age=0
      sec-ch-ua: "Google Chrome";v="95", "Chromium";v="95", ";Not A Brand";v="99"
      sec-ch-ua-mobile: ?0
      sec-ch-ua-platform: "Windows"
      Upgrade-Insecure-Requests: 1
      Origin: http://localhost:8080
      Content-Type: application/x-www-form-urlencoded
      User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/95.0.4638.54 Safari/537.36
      Accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3;q=0.9
      Sec-Fetch-Site: same-origin
      Sec-Fetch-Mode: navigate
      Sec-Fetch-User: ?1
      Sec-Fetch-Dest: document
      Referer: http://localhost:8080/servlet05/index.html
      Accept-Encoding: gzip, deflate, br
      Accept-Language: zh-CN,zh;q=0.9
      空白行
      username=lisi&userpwd=123 请求体

2.1.3 HTTP的响应协议

  • HTTP 的响应协议(S –> B)

    • HTTP 的响应协议包括:4 部分

      • 状态行

        • 三部分组成:

          • 第一部分:协议版本号(HTTP/1.1)

          • 第二部分:状态码(HTTP协议中规定的响应状态号。不同的响应结果对应不同的号码)

            • 200 表示请求响应成功,正常结束。
            • 404 表示访问的资源不存在,通常是因为要么是你路径写错了,要么是路径写对了,但是服务器中对应的资源并没有启动成功。总之 404 错误是前端错误。
            • 405 表示前端发送的请求方式与后端请求的处理方式不一致时发生:
              • 比如:前端是 POST 请求,后端的处理方式按照 get 方式进行处理时,发生 405。
              • 比如:前端是 GET 请求,后端的处理方式按照 post 方式进行处理时,发生 405。
            • 500 表示服务器端的程序出现了异常。一般会认为是服务器端的错误导致的。

            4 开始的,一般是浏览器端的错误导致的。

            5 开始的,一般是服务器端的错误导致的。

          • 第三部分:状态的描述信息

            • ok 表示正常成功结束。
            • not found 表示资源找不到。
      • 响应头

        • 响应的内容类型
        • 响应的内容长度
        • 响应的时间
      • 空白行

        • 用来分隔“响应头”和“响应体”的。
      • 响应体

        • 响应体就是响应的正文,这些内容是一个长的字符串,这个字符串被浏览器渲染,解释并执行,最终展示出效果。
    • HTTP 响应协议的具体报文:

      1
      2
      3
      4
      5
      6
      7
      8
      9
      10
      11
      12
      13
      14
      15
      16
      HTTP/1.1 200 ok                                     				状态行
      Content-Type: text/html;charset=UTF-8 响应头
      Content-Length: 160
      Date: Mon, 08 Nov 2021 13:19:32 GMT
      Keep-Alive: timeout=20
      Connection: keep-alive
      空白行
      <!doctype html> 响应体
      <html>
      <head>
      <title>from get servlet</title>
      </head>
      <body>
      <h1>from get servlet</h1>
      </body>
      </html>

★思考

  • 怎么向服务器发送 GET 请求,怎么向服务器发送 POST 请求?

    • 到目前为止,只有一种情况可以发送 POST 请求:使用 form 表单,并且 form 标签中的 method 属性值为:method="post"
    • 其他所有情况一律都是 GET 请求:
      • 在浏览器地址栏上直接输入 URL,敲回车,属于 get 请求。
      • 在浏览器上直接点击超链接,属于 get 请求。
      • 使用 form 表单提交数据时,form 标签中没有写 method 属性,默认就是 get。或者使用 form 的时候,form 标签中 method 属性值为:method="get"
  • GET 请求和 POST 请求有什么区别?

    • GET 请求:
      • GET 请求发送数据的时候,数据会挂在 URI 的后面,并且在 URI 后面添加一个“?”,”?“后面是数据。这样会导致发送的数据回显在浏览器的地址栏上(**GET 请求在“请求行”上发送数据**)。
      • GET 请求只能发送普通的字符串,并且发送的字符串长度有限制,不同的浏览器限制不同,这个没有明确的规范。
      • GET 请求无法发送大数据量。
      • GET 请求在 W3C 中是这样说的:**GET 请求比较适合从服务器端获取数据**。
      • GET 请求是安全的,GET 请求是绝对安全的。为什么?因为 GET 请求只是为了从服务器上获取数据,不会对服务器造成威胁。
      • GET 请求支持缓存
    • POST 请求:
      • POST 请求发送数据的时候,在请求体当中发送,不会回显到浏览器的地址栏上。也就是说 POST 发送的数据,在浏览器地址栏上看不到(**POST 在“请求体”当中发送数据**)。
      • POST 请求可以发送任何类型的数据,包括普通字符串,流媒体等信息:视频、声音、图片。
      • POST 请求可以发送大数据量,理论上没有长度限制。
      • POST 请求在 W3C 中是这样说的:**POST 请求比较适合向服务器端传送数据**。
      • POST 请求是危险的。为什么?因为 POST 请求是向服务器提交数据,如果这些数据通过后门的方式进入到服务器当中,服务器是很危险的。另外 POST 是为了提交数据,所以一般情况下拦截请求的时候,大部分会选择拦截(监听) POST 请求。
      • POST 请求不支持缓存POST 是用来修改服务器端的资源的)。
        • POST 请求之后,服务器“响应的结果”不会被浏览器缓存起来,因为这个缓存没有意义。
  • GET 请求和 POST 请求如何选择,什么时候使用 GET 请求,什么时候使用 POST 请求?

    • 怎么选择 GET 请求和 POST 请求呢?衡量标准是什么呢?要看你这个请求是想获取服务器端的数据,还是想向服务器发送数据。如果你是想从服务器上获取资源,建议使用 GET 请求,如果你这个请求是为了向服务器提交数据,建议使用 POST 请求。
    • 大部分的 form 表单提交,都是 POST 方式,因为 form 表单中要填写大量的数据,这些数据是收集用户的信息,一般是需要传给服务器,服务器将这些数据保存/修改等。
    • 如果表单中有敏感信息,还是建议使用 POST 请求,因为 GET 请求会回显敏感信息到浏览器地址栏上。(例如:密码信息)
    • 做文件上传,一定是 POST 请求,因为要传的数据不是普通文本。
    • 其他情况都可以使用 GET 请求。
  • 不管你是 GET 请求还是 POST 请求,发送的请求数据格式是完全相同的,只不过位置不同,格式都是统一的:

    • name=value&name=value&name=value&name=value
    • name 是什么?
      • 以 form 表单为例:form 表单中 input 标签的 name。
    • value 是什么?
      • 以 form 表单为例:form 表单中 input 标签的 value。

2.2 模板设计模式

  • 什么是设计模式?

    • 某类相似问题的固定的解决方案(可以被重复使用)。
  • 什么是模板设计模式?

    • 在模板类的模板方法当中定义核心算法骨架,具体的实现步骤可以延迟到子类当中完成。
      • 模板类通常是一个抽象类,模板类当中的模板方法定义核心算法,这个方法通常是 final 的(但也可以不是 final 的)。
      • 模板类当中的抽象方法就是不确定实现的方法,这个不确定怎么实现的事交给子类去做。

    注:在“Java笔记”中有关于“模板设计模式”的阐述。

2.3 ★★★HttpServlet源码分析

  • HttpServlet 类是专门为 HTTP 协议准备的,比 GenericServlet 更加适合 HTTP 协议下的开发。

    • HttpServlet 在哪个包下?
      • jakarta.servlet.http.HttpServlet
  • 到目前为止我们接触了 servlet 规范中哪些接口?

    • jakarta.servlet.Servlet 核心接口(接口)
    • jakarta.servlet.ServletConfig Servlet 配置信息接口(接口)
    • jakarta.servlet.ServletContext Servlet 上下文接口(接口)
    • jakarta.servlet.ServletRequest Servlet 请求接口(接口)
    • jakarta.servlet.ServletResponse Servlet 响应接口(接口)
    • jakarta.servlet.ServletException Servlet 异常(类)
    • jakarta.servlet.GenericServlet 标准通用的 Servlet 类(抽象类)
  • http 包下都有哪些类和接口呢?

    • jakarta.servlet.http.HttpServlet (HTTP 协议专用的 Servlet 类,抽象类)
    • jakarta.servlet.http.HttpServletRequest (HTTP 协议专用的请求对象)
    • jakarta.servlet.http.HttpServletResponse (HTTP 协议专用的响应对象)
  • HttpServletRequest 对象(简称 request 对象)中封装了什么信息?

    • 封装了请求协议的全部内容。
    • Tomcat服务器(WEB服务器)将“请求协议”中的数据(GET、POST请求数据)全部解析出来,然后将这些数据全部封装到 request 对象当中了。
    • 也就是说,我们只要面向 HttpServletRequest,就可以获取请求协议中的数据。
  • HttpServletResponse 对象是专门用来响应 HTTP 协议到浏览器的。

  • HttpServlet 源码分析:

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    67
    68
    69
    70
    71
    72
    73
    74
    75
    76
    77
    78
    79
    80
    81
    82
    83
    84
    85
    86
    87
    88
    89
    90
    91
    92
    93
    94
    95
    96
    97
    98
    99
    100
    101
    102
    103
    104
    105
    package com.f.javaweb.servlet;

    import jakarta.servlet.ServletException;
    import jakarta.servlet.http.HttpServlet;
    import jakarta.servlet.http.HttpServletRequest;
    import jakarta.servlet.http.HttpServletResponse;

    import java.io.IOException;
    import java.text.MessageFormat;

    /**
    * @author fzy
    * @date 2023/11/23 21:44
    * 根据创建的Servlet对象的生命周期来分析HttpServlet源码
    */
    public class HelloServlet extends HttpServlet {
    // 通过无参数构造方法创建对象
    /*
    public HelloServlet() {
    }
    */

    // 没有提供init方法,那么必然执行父类HttpServlet的init方法
    // HttpServlet类中没有init方法,会继续执行GenericServlet类中的init方法
    // 这里的init方法是 init()

    // 没有提供service方法,那么必然执行父类HttpServlet的service方法
    // 这里的service方法是 service(ServletRequest req, ServletResponse res)
    // 而不是 service(HttpServletRequest req, HttpServletResponse resp)
    // 而在HttpServlet的service(ServletRequest req, ServletResponse res)中,结尾会调用service(HttpServletRequest req, HttpServletResponse resp)方法
    // 下面的这个service就是模板方法,在该方法中定义核心算法骨架,具体的实现步骤延迟到子类中去完成
    protected void service(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
    // 获取请求方式
    // 注意:request.getMethod()方法获取的是请求方式,可能是七种之一:
    // GET POST PUT DELETE HEAD OPTIONS TRACE
    String method = req.getMethod();

    long lastModified;

    // 如果请求方式是GET请求,则执行doGet方法。
    if (method.equals("GET")) {
    lastModified = this.getLastModified(req);
    if (lastModified == -1L) {
    this.doGet(req, resp);
    } else {
    long ifModifiedSince;
    try {
    ifModifiedSince = req.getDateHeader("If-Modified-Since");
    } catch (IllegalArgumentException var9) {
    ifModifiedSince = -1L;
    }

    if (ifModifiedSince < lastModified / 1000L * 1000L) {
    this.maybeSetLastModified(resp, lastModified);
    this.doGet(req, resp);
    } else {
    resp.setStatus(304);
    }
    }
    } else if (method.equals("HEAD")) {
    lastModified = this.getLastModified(req);
    this.maybeSetLastModified(resp, lastModified);
    this.doHead(req, resp);
    } else if (method.equals("POST")) {
    // 如果请求方式是POST请求,则执行doPost方法。
    this.doPost(req, resp);
    } else if (method.equals("PUT")) {
    this.doPut(req, resp);
    } else if (method.equals("DELETE")) {
    this.doDelete(req, resp);
    } else if (method.equals("OPTIONS")) {
    this.doOptions(req, resp);
    } else if (method.equals("TRACE")) {
    this.doTrace(req, resp);
    } else {
    String errMsg = lStrings.getString("http.method_not_implemented");
    Object[] errArgs = new Object[]{method};
    errMsg = MessageFormat.format(errMsg, errArgs);
    resp.sendError(501, errMsg);
    }
    }

    /*
    通过以上源代码分析:
    假设前端发送的请求是get请求,后端程序员重写的方法是doPost,子类没有实现doGet方法,会继续执行父类的doGet方法,父类的doGet方法会报405错误
    假设前端发送的请求是post请求,后端程序员重写的方法是doGet
    会发生什么呢?
    发生405这样的一个错误。
    405表示前端的错误,发送的请求方式不对。和服务器不一致。不是服务器需要的请求方式。

    通过以上源代码可以知道:**只要HttpServlet类中的doGet方法或doPost方法执行了,必然405**.

    怎么避免405的错误呢?
    后端重写了doGet方法,前端一定要发get请求。
    后端重写了doPost方法,前端一定要发post请求。
    这样可以避免405错误。

    这种前端到底需要发什么样的请求,其实应该后端说了算。后端让发什么方式,前端就得发什么方式。

    有的人,你会看到为了避免405错误,在Servlet类当中,将doGet和doPost方法都进行了重写。
    这样,确实可以避免405的发生,但是不建议,405错误还是有用的。该报错的时候就应该让他报错。
    如果你要是同时重写了doGet和doPost,那还不如你直接重写service方法好了。这样代码还能
    少写一点。
    */
    }
    • 我们编写的 HelloServlet 继承 HttpServlet,直接重写 HttpServlet 类的 service() 方法行吗?
      • 可以,只不过你享受不到 405 错误,享受不到 HTTP 协议专属的东西,这些东西写在了 HttpServlet 类的 service() 方法中,即上面的“只要HttpServlet类中的doGet方法或doPost方法执行了,必然405”。
    • ★到今天我们终于得到了最终的一个 Servlet 类的开发步骤
      • 第一步:编写一个 Servlet 类,直接继承 HttpServlet
      • 第二步:在编写的 Servlet 类中重写 doGet 方法或者重写 doPost 方法,到底重写谁,javaweb 程序员说了算。
      • 第三步:将 Servlet 类配置到 web.xml 文件当中。
      • 第四步:准备前端的页面(form表单),form表单中指定请求路径即可。

2.4 关于一个Web站点的欢迎页面

  • 什么是一个 web 站点的欢迎页面?

    • 对于一个 webapp 来说,我们是可以设置它的欢迎页面的。

    • 设置了欢迎页面之后,当你访问这个 webapp 的时候,或者访问这个 web 站点的时候,如果没有指定任何“资源路径”,这个时候会默认访问你的欢迎页面。例如:

  • 怎么设置欢迎页面呢?

    • 第一步:在 IDEA 工具的 web 目录下新建一个文件 login.html

    • 第二步:在 web.xml 文件中进行以下的配置:

      1
      2
      3
      4
      5
      6
      7
      8
      9
      10
      11
      <?xml version="1.0" encoding="UTF-8"?>
      <web-app xmlns="https://jakarta.ee/xml/ns/jakartaee"
      xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
      xsi:schemaLocation="https://jakarta.ee/xml/ns/jakartaee https://jakarta.ee/xml/ns/jakartaee/web-app_6_0.xsd"
      version="6.0">

      <welcome-file-list>
      <welcome-file>login.html</welcome-file>
      </welcome-file-list>

      </web-app>
      • 注意:设置欢迎页面的时候,这个路径不需要以 “/” 开始。并且这个路径默认是从 webapp 的根下开始查找
    • 第三步:启动服务器,浏览器地址栏输入地址:http://localhost:8080/servlet07

思考

  • 如果在 webapp 的根下新建一个目录,目录中再给一个文件,那么这个欢迎页该如何设置呢?

    • 在 webapp 根下新建 page1 目录

    • 在 page1 下新建 page2 目录

    • 在 page2 目录下新建 page.html 页面

    • 那么在 web.xml 文件中应该这样配置:

      1
      2
      3
      4
      5
      6
      7
      8
      9
      10
      11
      <?xml version="1.0" encoding="UTF-8"?>
      <web-app xmlns="https://jakarta.ee/xml/ns/jakartaee"
      xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
      xsi:schemaLocation="https://jakarta.ee/xml/ns/jakartaee https://jakarta.ee/xml/ns/jakartaee/web-app_6_0.xsd"
      version="6.0">

      <welcome-file-list>
      <welcome-file>page1/page2/page.html</welcome-file>
      </welcome-file-list>

      </web-app>
      • 注意:路径不需要以 “/” 开始,并且路径默认从 webapp 的根下开始找

    注意:一个 webapp 是可以设置多个欢迎页面的:

    • <?xml version="1.0" encoding="UTF-8"?>
      <web-app xmlns="https://jakarta.ee/xml/ns/jakartaee"
               xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
               xsi:schemaLocation="https://jakarta.ee/xml/ns/jakartaee https://jakarta.ee/xml/ns/jakartaee/web-app_6_0.xsd"
               version="6.0">
          
          <welcome-file-list>
              <welcome-file>page1/page2/page.html</welcome-file>
              <welcome-file>login.html</welcome-file>
          </welcome-file-list>
          
      </web-app>
      
      1
      2
      3
      4
      5
      6
      7
      8
      9
      10
      11
      12
      13
      14
      15
      16
      17
      18
      19

      越靠上的页面优先级越高。找不到的继续向下找。

      - 你有没有注意一件事:当我的文件名设置为 `index.html` 的时候,不需要在 `web.xml` 文件中进行配置欢迎页面。这是为什么?

      - 这是因为 Tomcat 服务器已经提前配置好了。

      实际上配置欢迎页面有两个地方可以配置:

      - 一个是在 webapp 内部的 `web.xml `文件中(在这个地方配置的属于局部配置)。

      - 一个是在 `CATALINA_HOME/conf/web.xml` 文件中进行配置(在这个地方配置的属于**全局配置**):

      ```xml
      <welcome-file-list>
      <welcome-file>index.html</welcome-file>
      <welcome-file>index.htm</welcome-file>
      <welcome-file>index.jsp</welcome-file>
      </welcome-file-list>
      - Tomcat 服务器的全局欢迎页面是:`index.html`、`index.htm`、`index.jsp`。如果你一个 web 站点没有设置局部的欢迎页面,Tomcat 服务器就会以上面几个页面作为 web 站点的欢迎页面。 - 注意原则:局部优先原则(**就近原则**)。
  • 欢迎页可以是一个 Servlet 吗?

    • 当然可以。

    • 你不要多想,欢迎页就是一个资源,既然是一个资源,那么可以是静态资源,也可以是动态资源。

    • 静态资源:index.htmlwelcome.html

    • 动态资源:Servlet 类。

    • 步骤:

      • 第一步:写一个 Servlet

        1
        2
        3
        4
        5
        6
        7
        8
        9
        10
        11
        12
        13
        14
        15
        16
        17
        18
        19
        20
        21
        22
        23
        package com.f.javaweb.servlet;

        import jakarta.servlet.ServletException;
        import jakarta.servlet.http.HttpServlet;
        import jakarta.servlet.http.HttpServletRequest;
        import jakarta.servlet.http.HttpServletResponse;

        import java.io.IOException;
        import java.io.PrintWriter;

        /**
        * @author fzy
        * @date 2023/11/24 22:15
        */
        public class WelcomeServlet extends HttpServlet {
        @Override
        protected void doGet(HttpServletRequest request, HttpServletResponse response)
        throws ServletException, IOException {
        response.setContentType("text/html");
        PrintWriter out = response.getWriter();
        out.print("<h1>Welcome to Servlet page</h1>");
        }
        }
      • 第二步:在 web.xml 文件中配置 servlet

      • 第三步:在 web.xml文件中配置欢迎页:

        1
        2
        3
        4
        5
        6
        7
        8
        9
        10
        11
        12
        13
        14
        15
        16
        17
        18
        19
        20
        <?xml version="1.0" encoding="UTF-8"?>
        <web-app xmlns="https://jakarta.ee/xml/ns/jakartaee"
        xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
        xsi:schemaLocation="https://jakarta.ee/xml/ns/jakartaee https://jakarta.ee/xml/ns/jakartaee/web-app_6_0.xsd"
        version="6.0">

        <servlet>
        <servlet-name>welcomeServlet</servlet-name>
        <servlet-class>com.f.javaweb.servlet.WelcomeServlet</servlet-class>
        </servlet>
        <servlet-mapping>
        <servlet-name>welcomeServlet</servlet-name>
        <url-pattern>/a/b/c/d</url-pattern>
        </servlet-mapping>

        <welcome-file-list>
        <welcome-file>a/b/c/d</welcome-file>
        </welcome-file-list>

        </web-app>
  • 关于 WEB-INF 目录:

    注意:放在 WEB-INF 目录下的资源是受保护的,在浏览器上不能够通过路径直接访问。所以像HTML、CSS、JS、image 等静态资源一定要放到 WEB-INF 目录之外。

---------------The End---------------