JavaWeb(二) Servlet-Request&Response

        前言:了解了Servlet的快速入门,这里开始正式学习Request&Response对象

一、Request和Response介绍

  • Request是请求对象

        在后台服务器接收到请求后,后台服务器会对HTTP请求[请求行+请求头+请求体] 中的数据进行解析并把解析结果存入到一个对象中,这个对象就是Request对象

  • Response是响应对象        

        在处理完逻辑后,会把响应数据封装到Response对象中,后台服务器会解析Response对象,按照HTTP请求[响应行+响应头+响应体]格式拼接结果;在前端页面中,我们可以通过response.data拿到其中的数据。

二、Request

2.1 HTTP请求报文的组成

2.2 Request继承体系

  • 当Servlet类实现的是Servlet接口的时候,service方法中的参数是ServletRequest和ServletResp

  • 当Servlet类继承的是HttpServlet类的时候,doGet和doPost方法中的参数就变成HttpServletRequest和HttpServletReponse

这里说一下Request的继承体系:ServletRequest -> HttpServletRequest -> RequestFacade

2.3 Request获取请求数据

        这里讲下通过Request获取请求行数据、请求头数据、请求体数据

2.3.1 获取请求行数据

  • 获取请求方式: GET

String getMethod()
  • 获取虚拟目录(项目访问路径): /json

String getContextPath()
  • 获取URL(统一资源定位符):http://localhost:8080/json/a.html 

StringBuffer getRequestURL()
  • 获取URI(统一资源标识符):/json/a.html

String getRequestURI()
  • 获取请求参数(GET方式): username=ls&password=123

String getQueryString()

这里用代码实现下这些方法

/**
 * request 获取请求数据
 */
@WebServlet("/req1")
public class RequestDemo1 extends HttpServlet {
    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {

        // String getMethod():获取请求方式: GET
        String method = req.getMethod();
        System.out.println(method);//GET


        // String getContextPath():获取虚拟目录(项目访问路径):/json
        String contextPath = req.getContextPath();
        System.out.println(contextPath);


        // StringBuffer getRequestURL(): 
        //获取URL(统一资源定位符):http://localhost:8080/json/a.html 
        StringBuffer url = req.getRequestURL();
        System.out.println(url.toString());


        // String getRequestURI():获取URI(统一资源标识符):/json/a.html
        String uri = req.getRequestURI();
        System.out.println(uri);


        // String getQueryString():获取请求参数(GET方式):username=ls&password=123
        String queryString = req.getQueryString();
        System.out.println(queryString);


    }
    @Override
    protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
    }
}

2.3.2 获取请求头数据

        在请求头中,数据的存储方式为键值对格式,当我们获取值的时候需要用String  getHeader(String name) 方法。

/**
 * request 获取请求数据
 */
@WebServlet("/req1")
public class RequestDemo1 extends HttpServlet {
    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        //获取请求头: user-agent: 浏览器的版本信息
        String agent = req.getHeader("user-agent");
		System.out.println(agent);
    }
    @Override
    protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
    }
}

2.3.3 获取请求体数据

  • 获取字节输入流,如果前端发送的是字节数据,比如传递的是文件数据,则使用该方法

ServletInputStream getInputStream()

  • 获取字符输入流,如果前端发送的是纯文本数据,则使用该方法

BufferedReader getReader()

下面是代码实现

/**
 * request 获取请求数据
 */
@WebServlet("/req1")
public class RequestDemo1 extends HttpServlet {
    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        //获取post 请求体:请求参数
        //1. 获取字符输入流
        BufferedReader br = req.getReader();
        //2. 读取数据
        String line = br.readLine();
        System.out.println(line);
    }
    @Override
    protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {

    }
}

2.3.4 请求转发

        请求转发是一种在服务器内部的资源跳转方式,其流程如下

        (1)浏览器发送请求给服务器,服务器中对应的资源A接收到请求

        (2)资源A处理完请求后将请求发给资源B

        (3)资源B处理完后将结果响应给浏览器

        (4)请求从资源A到资源B的过程就叫请求转发 

        代码实现:

req.getRequestDispatcher("资源B路径").forward(req,resp);

        在请求转发的过程中,也可以共享数据,这里需要用到三个方法。

  • 存储数据到request域中

void setAttribute(String name,Object o);
  • 根据key获取值

Object getAttribute(String name);
  • 根据key删除该键值对

void removeAttribute(String name);

2.3.5 乱码问题

        乱码出现的原因是在请求发送到服务器时,在获取流的时候采用的编码是ISO-8859-1,而且ISO-8859-1编码是不支持中文的,所以会出现乱码。

        所以需要在获取流数据之前的编码设置为UTF-8。

        代码实现为:

request.setCharacterEncoding("UTF-8");

2.3.6 小结

  • 请求行

    • getMethod()获取请求方式

    • getContextPath()获取项目访问路径

    • getRequestURL()获取请求URL

    • getRequestURI()获取请求URI

    • getQueryString()获取GET请求方式的请求参数

  • 请求头

    • getHeader(String name)根据请求头名称获取其对应的值

  • 请求体

    • 注意: 浏览器发送的POST请求才有请求体

    • 如果是纯文本数据:getReader()

    • 如果是字节数据如文件数据:getInputStream()

三、Response

3.1 Response体系结构

        Reponse的继承体系和Request的继承体系也非常相似

 3.2 Response

        HTTP响应数据总共分为三部分内容,分别是响应行、响应头、响应体。respone对象分别提供了三种方法,分别来设置这三部分。

  • 响应行

响应头为:HTTP/1.1   200   OK        

                  HTTP协议/及版本   响应状态码  状态码描述

设置的方法为:

void setStatus(int sc);
  • 响应头

响应头为:Content-Type:text/html

                        键                 值

设置的方法为:

void setHeader(String name,String value);
  • 响应体

响应体为:<html></html>

设置的方法为:

获取字符输出流:

PrintWriter getWriter();

获取字节输出流:

ServletOutputStream getOutputStream();

3.2 Respones请求重定向

        Response重定向是一种资源跳转方式,实现步骤如下

        (1)浏览器发送请求给服务器,服务器中对应的资源A接收到请求

        (2)资源A现在无法处理该请求,就会给浏览器响应一个302的状态码+location的一个访问资源B的路径

        (3)浏览器接收到响应状态码为302就会重新发送请求到location对应的访问地址去访问资源B

        (4)资源B接收到请求后进行处理并最终给浏览器响应结果,这整个过程就叫重定向

 代码实现:

​	response.setStatus(302);

​	response.setHeader("Location","/request-demo/resp2");

3.3 请求转发和重定向的特点 

        具体如下

3.4 Response响应数据

  • 响应字符数据

步骤为:

1)通过Response对象获取字符输出流:

PrintWriter writer = resp.getWriter();

2)通过字符输出流写数据:

writer.write("aaa");

***当返回html字符串的时候,需要在字符输出流输出前写

***一次请求响应结束后,response对象就会被销毁掉,所以不要手动关闭流。

response.setHeader("content-type","text/html");
  • 响应字节数据

1)通过Response对象获取字节输出流:

ServletOutputStream outputStream = resp.getOutputStream();

2)通过字节输出流写数据:

outputStream.write(字节数据);

这里举个例子:返回一个图片文件到浏览器

/**
 * 响应字节数据:设置字节数据的响应体
 */
@WebServlet("/resp4")
public class ResponseDemo4 extends HttpServlet {
    @Override
    protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        //1. 读取文件
        FileInputStream fis = new FileInputStream("d://a.jpg");
        //2. 获取response字节输出流
        ServletOutputStream os = response.getOutputStream();
        //3. 完成流的copy
        byte[] buff = new byte[1024];
        int len = 0;
        while ((len = fis.read(buff))!= -1){
            os.write(buff,0,len);
        }
        fis.close();
    }

    @Override
    protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        this.doGet(request, response);
    }
}

***我们可以导入jar包,把步骤进行化简

步骤为

(1)pom.xml添加依赖

<dependency>
    <groupId>commons-io</groupId>
    <artifactId>commons-io</artifactId>
    <version>2.6</version>
</dependency>

(2)调用工具类方法

//fis:输入流
//os:输出流
IOUtils.copy(fis,os);

3)优化后的代码为

/**
 * 响应字节数据:设置字节数据的响应体
 */
@WebServlet("/resp4")
public class ResponseDemo4 extends HttpServlet {
    @Override
    protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        //1. 读取文件
        FileInputStream fis = new FileInputStream("d://a.jpg");
        //2. 获取response字节输出流
        ServletOutputStream os = response.getOutputStream();
        //3. 完成流的copy
      	IOUtils.copy(fis,os);
        fis.close();
    }

    @Override
    protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        this.doGet(request, response);
    }
}

三、总结

        这篇文章主要讲Request和Response对象的介绍、以及内部的API,我觉得这些知识是学习后面知识的基础,建议多看多练。(今天学校停电,用电脑仅剩的电量写完的...)

  • 2
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值