Skip to content

数据封装与解封装

基于 HTTP 现代标准 · 核于 2026-06

速查

  • 封装(encapsulation):发送方数据自顶向下穿过协议栈,每经过一层就把它当作「载荷」,贴上本层首部(必要时再加尾部),交给下一层。
  • 解封装(decapsulation):接收方数据自底向上逐层处理,每层剥掉本层首部/尾部,把剩下的载荷交给上一层——与封装严格镜像。
  • PDU(协议数据单元,Protocol Data Unit):某一层「首部 + 载荷」打包后的整体,是该层与对端同层对话的单位。
  • 各层 PDU 名称:应用层数据 / 报文(data / message)→ 传输层段 segment(TCP)/ 数据报 datagram(UDP)→ 网络层包 / 分组(packet)→ 数据链路层帧(frame)→ 物理层比特(bit)
  • 首部 header 与载荷 payload:首部装「控制信息」(源 / 目的地址、序号、校验等),载荷是「上层交下来的真正数据」;少数层(如以太网)还有尾部 trailer(放 FCS 校验)。
  • 关注点分离:每层只认自己的首部,把下层封装、路由、转发的复杂性藏起来——上层无需关心底下如何传输。
  • 同层对话:封装让发送方某层与接收方对应层「逻辑上直接通信」,中间各层只是机械地加 / 剥首部。
  • MTU(最大传输单元):链路层一帧能携带的载荷上限,以太网典型值 1500 字节;超过就要在网络层分片(fragmentation)
  • 分片代价:分片会增加首部开销与重组负担,任一分片丢失需整体重传,故现代实践更倾向用 PMTUD(路径 MTU 发现) 提前避免分片。
  • 一句话:封装是「层层套信封」,解封装是「层层拆信封」,PDU 名称只是同一坨数据在不同层的「称呼」。
  • 边界:本页只讲封装机制与 PDU 名称;各层协议细节OSI 七层逐层职责 / TCP/IP 四层与五层教学模型端到端完整旅程一个 HTTP 请求穿越协议栈的端到端旅程

为什么需要封装

分层模型把通信拆成若干层,但层与层之间靠什么传递数据?答案就是封装

上层并不直接「调用」下层的功能,而是把自己的整块数据交给下层,对下层说:「帮我把这坨东西送到对端的同层」。下层不关心这坨数据的含义,只把它当作不透明的载荷,在前面加上自己的首部,再交给更下层。如此层层向下,数据像被套进一个又一个信封。

套信封类比

你写好一封信(应用层数据),装进一个写着「房间号」的内层信封(传输层首部 → 段),再套进写着「楼栋地址」的外层信封(网络层首部 → 包),最后交给快递贴上「面单」(链路层首部/尾部 → 帧)。每一层只看自己那层信封上的字,拆到自己负责的那层为止——这就是封装与「关注点分离」。

封装:自顶向下,逐层加首部

发送方数据从应用层出发,每下沉一层就被当作载荷并加上本层首部(链路层还会加尾部)。用一次 HTTP 请求举例,逐层封装示意如下:

text
应用层    [ HTTP 报文 ]                                     ← data / message
            │  交给传输层,整体作为载荷

传输层    [ TCP头 | HTTP 报文 ]                              ← segment(段)
            │  TCP 段整体作为载荷交给网络层

网络层    [ IP头 | TCP头 | HTTP 报文 ]                       ← packet(包/分组)
            │  IP 包整体作为载荷交给链路层

链路层    [ 帧头 | IP头 | TCP头 | HTTP 报文 | 帧尾 ]          ← frame(帧)
            │  整帧编码为信号

物理层     1011010110011010 ...                             ← bit(比特流)

要点:

  • 每层只往「最外面」加一层首部,不改动里层内容——里层对外层是「黑盒」。
  • 首部里装什么,由该层职责决定:传输层放端口与序号,网络层放源 / 目的 IP,链路层放 MAC 地址与帧校验(FCS,位于尾部)。
  • 物理层不再加首部,它的任务是把链路层的帧编码为电 / 光 / 电磁信号,以比特为单位发到线路上。

别把「封装」和 OOP 的封装搞混

网络里的「封装」指给数据加首部这件事,和面向对象编程里「隐藏内部实现」的封装是同名不同义的两个概念,只是都借用了「包起来」的意象。

各层 PDU 名称对照

同一份数据在不同层有不同的正式称呼,这个称呼就是该层的 PDU(协议数据单元)。面试与文档里经常考「网络层的 PDU 叫什么」,务必记牢:

层(OSI)PDU 名称主要新增的首部信息
应用层数据 / 报文(data / message)应用协议自身(如 HTTP 头)
传输层段 segment(TCP)/ 数据报 datagram(UDP)源 / 目的端口、序号、校验
网络层包 / 分组 packet源 / 目的 IP、TTL、分片标志
数据链路层帧 frame源 / 目的 MAC,尾部 FCS 校验
物理层比特 bit无首部,仅信号编码

记忆口诀

数据 → 段 → 包 → 帧 → 比特(自顶向下)。TCP 用「段」、UDP 用「数据报」是初学者最易混的点:段 = TCP 的 PDU,数据报 = UDP 的 PDU

解封装:自底向上,逐层剥首部

接收方做的事和发送方严格镜像:信号先在物理层还原成比特流与帧,然后自底向上每层剥掉本层首部 / 尾部,按首部指示把载荷交给正确的上层,直到应用层拿到原始 HTTP 报文。

text
物理层     1011010110011010 ...        把比特流还原成帧


链路层    [ 帧头 | IP包 | 帧尾 ]        校验 FCS,剥掉帧头/帧尾 → 取出 IP 包


网络层    [ IP头 | TCP段 ]             看目的 IP 确认是本机,剥 IP 头 → 取出 TCP 段


传输层    [ TCP头 | HTTP 报文 ]        按目的端口分用到进程,剥 TCP 头 → 取出报文


应用层    [ HTTP 报文 ]               应用程序拿到完整数据

每层在剥首部时,会先读自己那层的首部做判断:链路层校验 FCS 是否损坏、网络层确认目的 IP 是不是自己、传输层按目的端口把数据分用给对应进程。这正是「每层只认自己的首部」的体现——下层首部对上层已不可见,关注点被层层隔离

首部 header 与载荷 payload

每个 PDU 都可拆成两部分:

  • 首部 header:装控制信息——按 MDN 的定义,包括源 / 目的网络地址、序号信息、差错检测码等「为投递载荷服务」的元数据。
  • 载荷 payload:装真正要传的用户数据,即上一层整体交下来的 PDU。长度可变,但受网络协议设定的上限约束。
  • 尾部 trailer(部分层才有):如以太网帧把帧校验序列 FCS 放在尾部,用于检测整帧在传输中是否出错。

Wikipedia 对封装的定义点明了本质:封装就是「把该层专属的首部或尾部与一个服务数据单元(即载荷)拼接起来,以便在网络上传输信息」;解封装则是其逆过程,移除下层先前拼接的首部 / 尾部。

MTU 与分片简介

封装时还有一个绕不开的物理约束:MTU(Maximum Transmission Unit,最大传输单元)——链路层一帧能携带的载荷字节上限。以太网典型 MTU 为 1500 字节

当网络层要发送的 IP 包超过下一跳链路的 MTU 时,就需要分片(fragmentation):把一个大 IP 包拆成多个足够小的分片,各自独立封装成帧上路,到目的主机再按 IP 头里的分片标志重新重组。Cloudflare 文档也提到,IP 首部中就含有「该包是否已被分片」以及包总长度等字段。

分片是「不得已」而非「常态」

  • 分片放大了首部开销,并给接收端增加重组负担;
  • 任一分片丢失都要整个包重传,对性能不利;
  • 因此现代实践普遍使用 PMTUD(Path MTU Discovery,路径 MTU 发现),让发送方提前探测整条路径的最小 MTU,从源头避免分片

本页只做「封装为什么受 MTU 限制」的概览,TCP 如何据此协商分段大小(MSS)等细节属传输层范畴,不在本页展开。

小结

  • 封装 = 自顶向下、层层加首部(必要时加尾部);解封装 = 自底向上、层层剥首部,二者严格镜像。
  • PDU 名称自顶向下为:数据 / 报文 → 段(TCP)/ 数据报(UDP)比特,是同一份数据在各层的不同称呼。
  • 每个 PDU = 首部(控制信息)+ 载荷(上层数据),少数层还有尾部(如以太网 FCS)。
  • 每层只认自己的首部,这是分层「关注点分离」在数据传递上的直接落地。
  • MTU 限制单帧载荷上限,超限触发分片;分片代价高,现代靠 PMTUD 规避。

延伸阅读:上一页 TCP/IP 四层与五层教学模型 讲清楚了「数据流经哪些层」;理解了本页的「逐层加 / 剥首部」后,下一页 两模型对照与协议归层 会把常见协议精确地放进对应的层里。