application/x- www-form-urlencoded是Post请求默认的请求体内容类型,也是form表单默认的类型。Servlet API规范中对该类型的请求内容提供了request.getParameter()方法来获取请求参数值。但当请求内容不是该类型时,需要调用request.getInputStream()或request.getReader()方法来获取请求内容值。

当请求体内容(注意:get请求没有请求体)类型是application/x- www-form-urlencoded时也可以直接调用request.getInputStream()或request.getReader()方法获取到请求内容再解析出具体都参数,但前提是还没调用request.getParameter()方法(先写了getParameter()方法,再用getReader()方法不能取到数据)。此时当request.getInputStream()或request.getReader()获取到请求内容后,无法再调request.getParameter()获取请求内容。即对该类型的请求,三个方法互斥,只能调其中一个。今天遇到一个Controller请求经过Spring MVC 的RequestMapping处理后,只能通过request.getParameter()获取到参数、无法通过request.getInputStream()和request.getReader()读取内容很可能就是因为在请求经过Spring MVC时已调用过request.getParameter()方法的原因。

注意:在一个请求链中,请求对象被前面对象方法中调用request.getInputStream()或request.getReader()获取过内容后,后面的对象方法里再调用这两个方法也无法获取到客户端请求的内容,但是调用request.getParameter()方法获取过内容后,后面的对象方法里依然可以调用它获取到参数的内容。

当请求体内容是其它类型时,比如 multipart/form-data或application/json时,无法通过request.getParameter()获取到请求内容,此时只能通过request.getInputStream()和request.getReader()方法获取请求内容,此时调用request.getParameter()也不会影响第一次调用request.getInputStream()或request.getReader()获取到请求内容。

request.getInputStream()返回请求内容字节流,多用于文件上传,request.getReader()是对前者返回内容的封装,可以让调用者更方便字符内容的处理(不用自己先获取字节流再做字符流的转换操作)。


POST 的三种常用 Content-Type (get没有请求体)

POST 是日常开发中非常常用的数据传输方法,请求头中的 Content-Type 指示了在一次 POST 请求中,服务器端应该如何解析客户端传递过来的数据。对于 web 开发来说, 以下三种 Content-Type 是最为常见的:

1

application/x-www-form-urlencoded

1.作为 <form /> 元素的默认 Content-Type 设定(enctype 属性),application/x-www-form-urlencoded 可能是被使用得最为广泛的一种数据编码方式。一次application/x-www-form-urlencoded 的 POST 请求内容大致如下:

名图HTTP请求报文

中间的空行是请求头和请求体的分隔符,请求体的形式和 GET 请求的参数(Query String) 一样,同样是将内容进行百分比编码。

在 chrome 调试工具中能看到发送出去的信息如下:

2.接收方式

对于 springmvc 来说,主要通过以下两种方式来接收 Content-Type 为 application/x-www-form-urlencoded 的数据:

  • 直接根据参数接收

  • 作为 domain 接收

当作为 domain 接收时,springmvc 无法对 domain 中的复杂数据类型进行解析,在这种情况下,使用 application/json 是更好的选择。

2

application/json

空行同样是请求头和请求体的分隔符, application/json 的不同在于,请求体的内容是 JSON 字符串。

chrome 调试工具中显示的内容如下:

2.接收方式

对于一个 Content-Type 为 application/json 的请求, springmvc 中可以使用 RequestBody 参数注解,请求体中的 JSON 字符串将被尝试解析为指定的对象,同时 RequestBody 也接受参数用于指示解析过程中是否允许对象为null。

3

application/x-www-form-urlencoded

1.用于文件上传的 Content-Type, 比较特殊的是,对于这样的 Content-Type 设定,浏览器会生成一个比较复杂且随机的boundary,并追加在 Content-Type 之后,用于分割请求体中的文件内容。


request.getParameter()-----post表单/ajax传对象

request.getInputStream();// 后面这2种可以获取post所有提交的数据
request.getReader()
// 方法二
public static void ReadAsChars2(HttpServletRequest request)
{ StringBuilder sb = new StringBuilder("--------");
InputStream is = null;
try
{
is = request.getInputStream();
sb = new StringBuilder();
byte[] b = new byte[4096];
for (int n; (n = is.read(b)) != -1;)
{
sb.append(new String(b, 0, n));
}
}
catch (IOException e)
{
e.printStackTrace();
}
finally
{
if (null != is)
{
try
{
is.close();
}
catch (IOException e)
{
e.printStackTrace();
}
}
} System.out.println("#"+sb);
} // 字符串读取
// 方法一
public static String ReadAsChars(HttpServletRequest request)
{ BufferedReader br = null;
StringBuilder sb = new StringBuilder("");
try
{
br = request.getReader();
String str;
while ((str = br.readLine()) != null)
{
sb.append(str);
}
br.close();
}
catch (IOException e)
{
e.printStackTrace();
}
finally
{
if (null != br)
{
try
{
br.close();
}
catch (IOException e)
{
e.printStackTrace();
}
}
}
return sb.toString();
} }

  

获取【请求体】数据的3种方式(精)(文末代码) request.getInputStream() request.getInputStream() request.getReader()的更多相关文章

  1. 获取请求体数据 POST

    POST获取请求体 请求体中封装了 POST请求的请求参数 获取流对象 再从流对象中那数据 一种字节流 一种字符流 BufferedReader getReader()获取字符输入流 只能操作字符 S ...

  2. Day20-单表中获取表单数据的3种方式

    1. 搭建环境请参考:http://www.cnblogs.com/momo8238/p/7508677.html 2. 创建表结构 models.py from django.db import m ...

  3. C# Http请求接口数据的两种方式Get and Post

    面向接口编程是一种设计思想,无论用什么语言都少不了面向接口开发思想,在软件开发过程中,常常要调用接口,接下来就是介绍C#调用其它开发商提供的接口进行获取数据,http接口方式获取接口数据. Get请求 ...

  4. 入门servlet:request获取请求体数据

    @WebServlet("/RequestDemo5") public class RequestDemo5 extends HttpServlet { protected voi ...

  5. Spring Cloud Gateway 之获取请求体(Request Body)的几种方式

    Spring Cloud Gateway 获取请求体 一.直接在全局拦截器中获取,伪代码如下 private String resolveBodyFromRequest(ServerHttpReque ...

  6. jQuery异步获取json数据的2种方式

    jQuery异步获取json数据有2种方式,一个是$.getJSON方法,一个是$.ajax方法.本篇体验使用这2种方式异步获取json数据,然后追加到页面. 在根目录下创建data.json文件: ...

  7. Struts2(四.注册时检查用户名是否存在及Action获取数据的三种方式)

    一.功能 1.用户注册页面 <%@ page language="java" contentType="text/html; charset=UTF-8" ...

  8. SparkStreaming获取kafka数据的两种方式:Receiver与Direct

    简介: Spark-Streaming获取kafka数据的两种方式-Receiver与Direct的方式,可以简单理解成: Receiver方式是通过zookeeper来连接kafka队列, Dire ...

  9. 在Express 中获取表单请求体数据

    在Express 中获取表单请求体数据 获取 GET 请求参数 获取 POST 请求体数据 安装 配置 获取 GET 请求参数 Express 内置了一个 API , 可以直接通过 req.query ...

  10. Linux就这个范儿 第15章 七种武器 linux 同步IO: sync、fsync与fdatasync Linux中的内存大页面huge page/large page David Cutler Linux读写内存数据的三种方式

    Linux就这个范儿 第15章 七种武器  linux 同步IO: sync.fsync与fdatasync   Linux中的内存大页面huge page/large page  David Cut ...

随机推荐

  1. Spring Cloud分布式微服务云架构

    分布式.微服务.云架构 JAVA语言开发.跨平台.高性能.高可用.安全.服务化.模块化.組件化.驱动式开发模式 commonservice eurekaNetflix 云端服务发现,一个基于 REST ...

  2. Hyperledger Fabric 架构梳理

    区块链的数据结构 State数据结构 由peer维护,key/value store Ledger  记录了所有成功和不成功的状态更新交易.Ledger被ordering service构造,是一个全 ...

  3. bootstrap-fileinput视频上传

    在页面编写一个input框: <input id="input-repl-3a" name="videoFileAddress" type="f ...

  4. ftp 发布配置

    地址:ftp://192.168.26.128/ 存放文件夹:jenkins

  5. pytest自动化4:fixture之yield实现teardown

    出处:https://www.cnblogs.com/yoyoketang/p/9401554.html 前言: 上一篇介绍了fixture通过scope参数控制setup级别,我们一起来温故下fix ...

  6. nc/netcat命令

    nc/netcat命令 语法 nc/netcat(选项)(参数) 选项 -g<网关>:设置路由器跃程通信网关,最多设置8个: -G<指向器数目>:设置来源路由指向器,其数值为4 ...

  7. python爬虫基础_requests和bs4

    这些都是笔记,还缺少详细整理,后续会更新. 下面这种方式,属于入门阶段,手动成分比较多. 首先安装必要组件: pip3 install requests pip3 install beautifuls ...

  8. php优秀框架codeigniter学习系列——CI_Loader类分析

    这是一个加载视图和文件的类. __construct() 设置视图文件的路径,和获取输出缓冲级别. initialize() 该方法只会被CI_Controller调用一次,会调用 $this-> ...

  9. 第二次scrum冲刺

    一.第二次冲刺任务         Scrum是在已有的基础上实现读者查询书籍的功能. 二.用户故事         用户输入账号.密码   用户输入需要查询的书籍   系统显示用户输入的信息的详细信 ...

  10. Strongly connected components

    拓扑排列可以指明除了循环以外的所有指向,当反过来还有路可以走的话,说明有刚刚没算的循环路线,所以反过来能形成的所有树都是循环