通过 Apifox Echo 了解 Content-Type 及对应的请求体编码

2,956 阅读2分钟

我们在与后端接口联调中,你知道请求体可以由哪几种类型,以及对应的 Content-Type 是多少吗?

今天以 Apifox Echo 演示一下不同 Content-Type 的 HTTP 报文。关于 Apifox Echo 可查看我以前的文章:通过 Apifox Echo 学习 curl/httpie 命令

Content Type

当前端向后端请求 API 接口时,不同类型的 Content-Type 对应不同的请求体(Request Body)。

  • aplication/json:请求体为 JSON
  • application/x-www-form-urlencoded:请求体为以 & 分割的字符串,如 a=3&b=4
  • multipart/form-data:请求体以 Boundary 分割

在使用 curl 时,可以通过参数 --data/-d 配置请求体(Request Body)。

可通过 Apifox Echo 进行测试,如果接收到的是 JSON,则会放置于 json 字段,Form 则会置于 form 字段。

image.png

# 使用 Form 发送请求
$ curl -X POST echo.apifox.com/post -H "content-type: application/x-www-form-urlencoded" -d 'a=3&b=4'
{
  "args": {},
  "data": "", 
  "files": {}, 
  "form": {
    "a": "3",
    "b": "4"
  }, 
  "headers": {
    "Accept": "*/*", 
    "Content-Length": "3", 
    "Content-Type": "application/x-www-form-urlencoded", 
    "Host": "echo.apifox.com", 
    "User-Agent": "curl/7.79.1", 
    "X-Amzn-Trace-Id": "Root=1-63454557-3cd5f9a53682be3a327dd0a3"
  }, 
  "json": null, 
  "url": "http://echo.apifox.com/post"
}

# 使用 JSON 发送请求
$ curl -X POST echo.apifox.com/post -H "content-type: application/json" -d '{"a": 3, "b": 4}'
{
  "args": {}, 
  "data": "{\"a\": 3, \"b\": 4}",
  "files": {}, 
  "form": {}, 
  "headers": {
    "Accept": "*/*", 
    "Content-Length": "8", 
    "Content-Type": "application/json", 
    "Host": "echo.apifox.com", 
    "User-Agent": "curl/7.79.1", 
    "X-Amzn-Trace-Id": "Root=1-63454532-1aa1d82138215128077cd85d"
  }, 
  "json": {
    "a": 3
  }, 
  "url": "http://echo.apifox.com/post"
}

另外,在 Apifox 中也可以配置其 Content-Type 以及对应的请求体编码。

fetch API

因此,我们前端通过 fetch API 发送请求,携带 body 时,需要:

  1. 配置 content-type
  2. 配置为对应 content-type 的 data。比如为 JSON 时,需要手动 JSON.stringify 进行编码,为 Form(即 application/www-form-url-encoded)时,通过 URLSearchParams API 进行编码。

fetch API 中,对请求体总是最纯正原始的编码方案,但也更有助于我们理解 HTTP 中的 Content-Body 以及请求体。

可将以下代码输入浏览器控制台进行尝试。

// 对于 application/json 的数据需要手动 JSON.stringify
await fetch('https://echo.apifox.com/post', {
  method: 'POST',
  body: JSON.stringify({
    a: 3,
    b: 4
  }),
  headers: {
    'content-type': 'application/json'
  }
}).then(res => res.json())

// 对于 application/www-form-url-encoded 的数据也需要手动编码
await fetch('https://echo.apifox.com/post', {
  method: 'POST',
  body: new URLSearchParams({ a: 3, b: 4}),
  headers: {
    'content-type': 'application/www-form-url-encoded'
  }
}).then(res => res.json())

axios

axios 这种更进一步封装的请求库,将会自动指定 Content-Type 以及对数据进行自动编码。

可将以下代码输入浏览器控制台进行尝试。

const axios = await import('https://cdn.skypack.dev/axios').then(r => r.default)

// 将自动是 JSON 格式,并自动对 object 进行序列化
axios.post('https://echo.apifox.com/post', { a: 3, b: 4 })

关于 axios 更多请查看axios 中的请求体编码

作业

  1. 使用 Apifox Echo 测试 json/form,并观察请求体
  2. 如何对 JSON/Form 数据进行序列化作为 Body 在 fetch API 中发送
  3. 如何基于 fetch API 实现简单的类似 axios,使得对请求体简单封装