(十四)请求、响应与消息中的数据
1. 方法、路径、头部与请求体
HTTP/1.1 的一个读取请求可以看成下面的文本结构,实际行结束使用 \r\n:
GET /api/books/1 HTTP/1.1
Host: 127.0.0.1:8765
Accept: application/json
第一行选择方法与请求目标;头部提供主机、期望的数据格式等信息;空行结束头部,后面才是可选请求体。一个响应包含状态行、响应头与响应体:
HTTP/1.1 200 OK
Content-Type: application/json
Content-Length: 18
{"title":"Python"}
这里的 18 是这段 ASCII JSON 的字节数。中文文本先编码,再计算字节数;把字符串字符数当成传输字节数,会让消息长度和实际内容不一致。
# 项目文件:demos/http_body_bytes.py
# 显式编码请求体,Content-Length 等消息细节交给客户端库根据 bytes 处理。
import json
text = json.dumps({"title": "书"}, ensure_ascii=False, separators=(",", ":"))
data = text.encode("utf-8")
print(text)
print("字符", len(text), "字节", len(data))输出 {"title":"书"},字符数为 13、字节数为 15。它与第五章“先编码成字节再保存”的过程相同,只是数据现在经过网络传递。
2. 把方法对应到业务动作
| 方法 | 常见的业务意图 | 本章中的例子 |
|---|---|---|
| GET | 取得资源或查询结果 | 读取书目,不新增阅读日志 |
| POST | 提交一项操作或创建资源 | 新增一条阅读日志 |
| PUT | 用给定表示创建或替换指定资源 | 后续接口中替换某本书的完整表示 |
| PATCH | 描述对资源的局部修改 | 后续接口中修改完成状态 |
| DELETE | 删除指定资源 | 后续接口中删除书籍 |
方法先表达请求意图,实际路由由服务器程序实现。请求体里的 JSON、表单文本和二进制数据也有各自的 Content-Type,不能只改一个头部名字就把 CSV 字节变成 JSON。
| 头部 | 这里传递的信息 |
|---|---|
Accept |
客户端希望取得的响应格式 |
Content-Type |
本条消息正文使用的媒体类型与相关参数 |
Content-Length |
本条消息的正文长度,按字节计 |
Location |
重定向后的目标位置 |
Set-Cookie |
响应要求客户端保存的 Cookie |
Cookie |
客户端在后续请求中带回的 Cookie |
HTTP 头部之外,响应体才可能是 JSON 文本、HTML 页面、图片或其他内容。先看状态和格式,再决定如何解释这些字节。HTTP 消息与方法