计算机网络之应用层
网络应用体系结构
目前主流的网络应用体系结构主要有以下三种:
客户端-服务器(Client-Server)体系结构
这是目前最主流、最常见的网络应用结构。
- 核心概念
- 服务器 (Server):
- 地位: 始终开启的主机。
- 功能: 持续提供服务,拥有固定的、永久的IP地址,并负责存储数据和运行应用的核心逻辑。例如,Web服务器、邮件服务器。
- 客户端 (Client):
- 地位: 需要服务时请求的主机。
- 功能: 与服务器通信,获取服务,通常是终端用户设备(PC、手机等)。客户端可以是动态IP地址,且不需要始终开启。
- 交互模式: 客户端发起请求,服务器响应请求。
- 优点
- 集中控制和管理: 数据和应用逻辑集中在服务器上,便于安全管理、备份和维护。
- 可扩展性好: 通过增加或升级服务器(如使用负载均衡),可以支持更多客户端。
- 安全性高: 服务器可以实施严格的身份验证和授权。
- 缺点
- 单点故障风险(SPOF): 如果中心服务器出现故障,整个应用服务可能会中断。
- 网络瓶颈: 所有请求都集中在服务器端,在高并发情况下可能成为性能瓶颈。
- 典型应用
- Web应用: 浏览器(客户端)访问网站服务器。
- FTP: 文件传输。
- 电子邮件: 客户端访问邮件服务器。
对等(Peer-to-Peer, P2P)体系结构
- 核心概念
- 对等方 (Peer):
- 地位: 任何主机既可以作为客户端向其他主机请求服务,也可以作为服务器向其他主机提供服务。
- 特点: 每个对等方都是平等的,没有固定的中心服务器。节点间歇性连接,且IP地址可能频繁变动。
- 交互模式: 对等方之间直接通信,共享资源。
- 优点
- 高度可扩展性: 系统的容量和带宽随着用户的增加而增加。
- 健壮性/抗毁性: 没有单点故障,部分节点失效不影响整体运行。
- 成本低廉: 无需昂贵的服务器基础设施。
- 缺点
- 复杂性高: 难以管理和维护,资源的搜索和定位相对复杂。
- 安全性挑战: 难以实施集中化的安全策略和身份验证。
- 性能波动: 资源由用户提供,网络性能和资源可用性不稳定。
- 典型应用
- 文件共享: BitTorrent、eMule。
- 加密货币网络: 比特币等(节点同时作为客户端和服务器)。
- VolP应用: 一些早期的网络电话服务。
混合(Hybrid)体系结构
混合结构将客户端-服务器模式的集中管理优势与P2P模式的分布式资源共享优势结合起来。
- 核心概念
- 中心服务器: 用于进行集中化管理,例如用户登录、资源索引、对等方状态跟踪等。
- 对等方: 一旦连接建立,数据传输则直接在对等方之间进行。
- 工作流程
- 连接/定位: 用户登录到中心服务器。
- 查询: 用户向中心服务器查询所需资源的索引或某个对等方的地址。
- 传输: 获得信息后,用户直接与提供资源的对等方建立P2P连接,进行实际的数据传输。
- 典型应用
- 即时通讯(IM): QQ、微信等应用。用户登录和状态信息(谁在线)由服务器管理,但语音/视频通话等大流量数据传输,有时会尝试在用户之间直接进行P2P连接。
- 某些P2P文件共享系统: 使用中心服务器来维护索引。
简要对比总结
| 特征 | 客户端-服务器 (C/S) | 对等 (P2P) | 混合 (Hybrid) |
|---|---|---|---|
| 中心化 | 高度集中(有永久性服务器) | 完全分散(没有中心服务器) | 部分集中(用于管理和索引) |
| 角色 | 严格区分(客户端/服务器) | 角色对等(同时是客户端/服务器) | 分阶段角色(服务器用于索引,Peer用于传输) |
| 可扩展性 | 需要服务器升级或集群 | 随用户数自然增强 | 集中管理部分有限制 |
| 安全性 | 易于实施集中安全 | 难以保证 | 集中部分安全可控 |
| 健壮性 | 易受单点故障影响 | 高度健壮,无单点故障 | 优于C/S,劣于纯P2P |
Web和HTTP
HTTP概述
Web的应⽤层协议是超⽂本传输协议(HTTP),它是Web的核⼼,在[RFC1945]、[RFC7230]和[RFC7540]中进⾏了定义。HTTP由两个程序实现:⼀个客户程序和⼀个服务器程序。客户程序和服务器程序运⾏在不同的端系统中,通过交换HTTP报⽂进⾏会话。HTTP定义了这些报⽂的结构以及客户和服务器进⾏报⽂交换的⽅式。
Web页⾯(Web page)(也叫⽂档)是由对象组成的。⼀个对象只是⼀个⽂件,诸如⼀个HTML.⽂件、⼀个JPEG图形、⼀个JavaScript⽂件、⼀个CCS样式表⽂件或⼀个视频⽚段,它们可通过⼀个URL寻址。多数Web页⾯含有⼀个HTML基本⽂件(baseHTMLfile)以及⼏个引⽤对象。例如,如果⼀个Web页⾯包含HTML⽂本和5个JPEG图形,那么这个web页⾯有6个对象:⼀个HTML基本⽂件加5个图形。HTML基本⽂件通过对象的URL引⽤页⾯中的其他对象。
当⽤户请求⼀个web页⾯(如点击⼀个超链接)时,浏览器向服务器发出对该页⾯中所包含对象的HTTP请求报⽂,服务器接收到请求并⽤包含这些对象的HTTP响应报⽂进⾏响应。
HTTP使⽤TCP作为它的⽀撑运输协议(⽽不是在UDP上运⾏)。HTTP客户⾸先发起⼀个与服务器的TCP连接。⼀旦连接建⽴,该浏览器和服务器进程就可以通过套接字接口访问TCP。客户端的套接字接口是客户进程与TCP连接之间的门,服务器端的套接字接口则是服务器进程与TCP连接之间的门。客户向它的套接字接口发送HTTP请求报⽂并从它的套接字接口接收HTTP响应报⽂。类似地,服务器从它的套接字接口接收HTTP请求报⽂并向它的套接字接口发送HTTP响应报⽂。
HTTP是一个无状态协议,不保存用户的任何信息。
FTP、SMTP、telnet/ssh、WebSocket、TCP都是有状态的。
| 类型 | 协议 | 状态性 | 原因 |
|---|---|---|---|
| 传输层 | TCP | 有状态 | 需要维护连接状态 |
| 传输层 | UDP | 无状态 | 每个报文独立 |
| 应用层 | HTTP | 无状态 | 每次请求独立 |
| 应用层 | FTP、SMTP、SSH、WebSocket | 有状态 | 需要维持会话上下文 |
| 网络层 | IP、ICMP | 无状态 | 无连接状态维护 |
非持续连接和持续连接
非持续连接:每个请求/响应由一个单独的TCP连接发送。
持续连接:所有请求/响应由相同的TCP连接发送。
HTTP1.0默认采用非持续连接,HTTP1.1开始默认采用持续连接
HTTP报文格式
分为请求报文和响应报文
请求报文
格式如下:
1 | <请求行> |
请求行
1 | <Method> <Request-URI> <HTTP-Version> |
例如:
1 | GET /index.html HTTP/1.1 |
请求头部
以“键: 值”形式表示,用于说明请求的附加信息:
1 | Host: www.example.com |
请求体
请求体是可选的,主要在以下请求中使用:
POST(表单提交、JSON 数据等)
PUT(上传或更新资源)
PATCH
示例(POST 发送 JSON):
1 | POST /api/login |
响应报文
格式如下:
1 | <状态行> |
状态行
1 | <HTTP-Version> <Status-Code> <Reason-Phrase> |
例如:
1 | HTTP1.1 200 OK |
响应头部
1 | Date: Thu, 13 Nov 2025 01:45:00 GMT |
响应体
包含服务器返回的内容,比如:
HTML页面
JSON数据
图片/文件内容
1 | 200 OK |
Cookie
Cookie 主要是为了解决HTTP无状态导致的“服务器记不住客户端”的问题。
Cookie 主要完成的任务
HTTP是无状态协议,每个请求都是独立的,服务器不会自动记得上次是谁发的请求。
Cookie的核心任务,就是让服务器能识别同一个用户的连续请求。
Cookie 的常见任务分类如下:
| 任务类别 | 说明 | 示例 |
|---|---|---|
| 1. 会话管理(Session Management) | 维持用户登录状态、购物车、浏览状态等。 | 登录后,Cookie 中存有 session_id,服务器据此识别当前用户。 |
| 2. 个性化设置(Personalization) | 保存用户偏好,如语言、主题、字体大小。 | lang=zh-CN,theme=dark |
| 3. 跟踪与分析(Tracking / Analytics) | 统计用户访问次数、来源或行为,用于广告和分析。 | user_uuid=abcd1234 |
| 4. 安全控制(Security) | 管理 CSRF 令牌、防重放、验证设备。 | csrftoken=xyz |
| 5. 状态缓存 | 临时保存上次访问的资源、表单输入状态。 | 表单恢复、导航状态保持 |
Cookie 的工作机制
Cookie是由服务器生成,存储在客户端,由浏览器自动携带的。
- 服务器发送 Cookie(Set-Cookie)
服务器通过响应头告诉浏览器“请你保存一个 Cookie”。
示例:
1 | 200 OK |
含义:
- 浏览器收到这条
Set-Cookie后,会保存键值对sessionId=abc123 - 同时记录属性(作用域、有效期、安全限制)
- 浏览器保存 Cookie
浏览器内部会为每个域维护一个“Cookie 存储区”。
当收到 Set-Cookie:
- 浏览器检查是否允许保存(根据 SameSite、安全策略等)
- 将 Cookie 保存到内存或磁盘(取决于是 session 还是持久化)
- 记下 Domain、Path、Expires/Max-Age 等属性
存储示意(浏览器内部表):
| Name | Value | Domain | Path | ExpireTime | Secure | HttpOnly |
|---|---|---|---|---|---|---|
| sessionId | abc123 | example.com | / | +1小时 | ✅ | ✅ |
- 浏览器发送 Cookie(请求时自动附带)
当你再次访问同一网站(域、路径匹配)时:
浏览器自动在请求头中加入 Cookie:
1 | GET /user/profile |
浏览器只会附带符合以下条件的 Cookie:
- 请求域名匹配 Cookie 的
Domain - 请求路径匹配 Cookie 的
Path - 当前时间未超过过期时间
- 如果是 HTTPS,则
SecureCookie 只在加密连接上传输 - 如果有
SameSite限制,则要满足跨站策略
- 服务器接收并解析 Cookie
服务器端在收到请求后:
- 读取请求头中的
Cookie; - 解析出键值对;
- 根据
sessionId去服务器端的 Session 表中查找用户状态; - 确定当前是谁、是否已登录等。
服务器端伪代码示例:
1 | string cookie = request.getHeader("Cookie"); |
然后,服务器就能基于这个会话信息提供个性化服务。
| 阶段 | 由谁发起 | 说明 |
|---|---|---|
| 创建 | 服务器(Set-Cookie) | 服务器告诉浏览器保存 Cookie |
| 存储 | 浏览器 | 浏览器按规则保存 |
| 发送 | 浏览器 | 请求时自动附带符合条件的 Cookie |
| 使用 | 服务器 | 识别用户、维持会话 |
| 失效 | 浏览器 | 到期时间到、清除缓存或被新 Cookie 覆盖 |
安全与行为:
| 属性 | 浏览器行为 | 作用 |
|---|---|---|
| Secure | 只在 HTTPS 上传输 | 防止被中间人窃听 |
| HttpOnly | JS 无法访问(document.cookie) | 防止 XSS 窃取 |
| SameSite | 控制跨站是否附带 | 防御 CSRF |
| Domain/Path | 控制作用范围 | 避免滥发 |
| Expires/Max-Age | 控制过期时间 | 生命周期管理 |
完整例子:登录过程中的 Cookie
用户访问登录页
→ 浏览器发请求(无 Cookie)用户提交表单(用户名/密码)
→ 服务器验证成功
→ 服务器返回响应头:
1 | Set-Cookie: sessionId=xyz123; Path=/; HttpOnly; Secure; SameSite=Lax |
浏览器保存 Cookie
→sessionId=xyz123被记录用户刷新或访问其他页面
→ 浏览器自动在请求头中加:
1 | Cookie: sessionId=xyz123 |
- 服务器识别 session
→ 找到对应用户信息
→ 响应内容展示“欢迎回来,Alice!”
Web缓存
什么是Web缓存器(Web Cache)
定义:
Web 缓存器是一种临时存储网页资源(如 HTML、图片、CSS、JS、API 响应等)的系统,用于在后续请求时直接提供这些资源,而不必重新从源服务器获取。
它是浏览器和服务器之间的“中间层”,用来减少重复下载。
Web缓存的常见类型
| 类型 | 位置 | 举例 | 说明 |
|---|---|---|---|
| 浏览器缓存(Browser Cache) | 客户端 | Chrome、Edge、Safari | 用户本地保存静态资源(HTML、JS、CSS、图片) |
| 代理缓存(Proxy Cache) | 网络中间层 | 企业代理服务器、CDN 节点 | 多个用户共享缓存内容 |
| 网关缓存(Gateway Cache/反向代理) | 靠近服务器 | Nginx、Varnish、Cloudflare | 替服务器缓存响应,减轻源服务器压力 |
| CDN缓存 | 全球分布 | Cloudflare、Akamai、腾讯云 CDN | 将资源缓存到边缘节点,用户就近访问 |
Web缓存的核心工作机制
当浏览器发出请求时,缓存器会进行如下逻辑:
检查缓存是否存在
- 如果命中缓存(Cache Hit)且仍在有效期内 → 直接返回;
- 否则(Cache Miss)→ 向服务器请求。
服务器响应时可能附带缓存控制头:
1
2
3Cache-Control: max-age=3600, public
ETag: "abc123"
Last-Modified: Wed, 10 Jan 2024 10:00:00 GMT缓存器根据这些头判断:
- 资源能否缓存;
- 缓存有效期;
- 是否可共享给多个用户;
- 过期后是否能通过条件请求验证。
HTTP 中与缓存相关的关键首部
| 首部字段 | 作用 |
|---|---|
| Cache-Control | 指定缓存策略,如 max-age、no-cache、public、private |
| Expires | 指定资源过期时间(HTTP/1.0 旧字段) |
| ETag | 资源内容标识(可用于校验是否变更) |
| Last-Modified | 资源最后修改时间 |
| If-None-Match | 客户端带上上次的 ETag 请求校验 |
| If-Modified-Since | 客户端带上上次修改时间请求校验 |
Web缓存的优点
| 优点 | 说明 |
|---|---|
| 提升访问速度 | 用户可从本地或附近的缓存节点直接获取资源,响应更快。 |
| 减少服务器负载 | 大量重复请求可由缓存处理,服务器压力降低。 |
| 节省带宽 | 不重复下载相同资源,尤其是图片、JS、CSS 等大文件。 |
| 提高可用性 | 源服务器短暂不可用时,缓存仍可提供旧内容(称为 stale content)。 |
| 提升用户体验 | 页面加载速度更快,尤其在移动端和高延迟网络中。 |
Web缓存的缺点/潜在问题
| 缺点 | 说明 |
|---|---|
| 数据可能不新鲜(过期) | 缓存内容未及时更新时,用户可能看到旧数据。 |
| 缓存一致性难题 | 当服务器更新资源后,如何通知缓存器刷新是复杂问题。 |
| 隐私与安全风险 | 若公共缓存(如代理)缓存了私密响应,可能导致泄露。 |
| 开发调试不便 | 开发阶段缓存常导致“改了代码但浏览器还在用旧文件”的问题。 |
| 动态内容难缓存 | 用户定制化、实时变化的数据往往不能缓存。 |
Web缓存的两种失效策略
| 策略 | 描述 | 举例 |
|---|---|---|
| 强缓存(Fresh Cache) | 在有效期内直接使用,不访问服务器 | Cache-Control: max-age=3600 |
| 协商缓存(Conditional Cache) | 到期后带验证信息向服务器确认是否更新 | ETag / If-None-Match 验证 |
工作流程示意:
1 | 浏览器缓存中命中资源 |
现实应用举例
| 场景 | 使用的缓存类型 | 说明 |
|---|---|---|
| 浏览器打开网页 | 浏览器缓存 | 静态资源(图片、JS、CSS)本地缓存 |
| 企业内网访问外部网页 | 代理缓存 | 所有人共享缓存,提高整体访问速度 |
| 大型网站(YouTube、Bilibili) | CDN 缓存 + 反向代理缓存 | 视频内容分布式缓存,减少回源流量 |
总结
| 分类 | 优点 | 缺点 |
|---|---|---|
| 性能 | 加快访问速度、减少延迟 | 数据可能不新鲜 |
| 资源利用 | 降低服务器负载、节省带宽 | 缓存失效管理复杂 |
| 安全性 | 提供容错能力 | 不当缓存可能泄露私密信息 |
| 适用性 | 适合静态内容 | 不适合高动态内容 |
HTTP和版本区别以及HTTP与HTTPS
HTTP协议的特点
| 特点 | 描述 | 备注 |
|---|---|---|
| 无状态 (Stateless) | 服务器不存储关于客户端的任何信息。每一次请求都是独立的,服务器不知道上一次请求是谁发的。 | 为了保持用户的状态(如登录、购物车),通常需要利用 Cookie、Session 或 Token 等机制。 |
| 灵活可扩展 | HTTP头部字段定义灵活,允许添加新的头部字段来增强功能和语义。 | 这是它能不断发展和演进的基础。 |
| 基于 TCP/IP | HTTP 默认使用 TCP 连接进行数据传输,确保传输的可靠性。 | |
| 明文传输 | HTTP/1.x 和 HTTP/2 默认都是明文传输,内容容易被嗅探。 | HTTPS 是在 HTTP 上加入了 SSL/TLS 加密层,解决安全问题。 |
| 请求-响应模型 | 严格的交互模式:客户端发起请求,服务器处理并返回响应。 |
HTTP协议版本对比(进化史)
HTTP 经历了多个版本的迭代,主要是为了解决性能和效率问题。
- HTTP/0.9 (原始版本)
- 特点: 极其简单,只有一个请求方法
GET。只支持传输纯文本,不支持头部和状态码。 - 用途: 实验性质,已废弃。
- HTTP/1.0 (第一个正式版本)
- 特点: 引入了头部(Headers)、状态码和多媒体文件类型的支持。
- 连接模型: 默认使用非持久连接(Non-persistent Connection)。
- 每发起一个请求,客户端都需要与服务器建立一个新的 TCP 连接。请求完成后,连接立即关闭。
- 问题: 效率低下,频繁建立/断开连接(三次握手/四次挥手)带来了巨大的开销。
- HTTP/1.1 (长期主导版本)
- 特点: 解决了 HTTP/1.0 的性能瓶颈,是使用时间最长、最普及的版本。
- 核心改进:
- 持久连接(Persistent Connection): 默认开启。在一次 TCP 连接上,可以发送多个请求和接收多个响应。
- 管线化(Pipelining): 客户端可以不等上一个响应返回,就发送下一个请求。(实践中应用不多,有队头阻塞问题)
- 引入 Host 头部: 允许同一台服务器托管多个域名(虚拟主机)。
- 主要性能瓶颈: 队头阻塞(Head-of-Line Blocking, HOL)。虽然管线化允许并发发送请求,但服务器必须按请求的顺序返回响应。如果第一个请求处理耗时,会阻塞后面所有请求的响应,导致带宽利用率不高。
- HTTP/2 (性能飞跃)
- 特点: 彻底解决了 HTTP/1.1 的队头阻塞问题,是基于 Google SPDY 协议开发的。
- 核心改进:
- 二进制分帧(Binary Framing): 将报文拆分成二进制的帧,在传输层上实现并发。
- 多路复用(Multiplexing): 在一个 TCP 连接上,同时处理多个请求和响应,并且请求和响应之间互不干扰。彻底消除了 HTTP/1.1 的队头阻塞。
- 头部压缩(Header Compression): 使用 HPACK 算法压缩请求/响应头部,减小传输数据量。
- 服务器推送(Server Push): 服务器可以主动推送客户端可能需要的资源(如 CSS/JS 文件),提前加载,无需客户端请求。
- 部署: 多数浏览器只支持基于 HTTPS 的 HTTP/2 部署,这意味着它默认是加密的。
- HTTP/3 (基于 UDP 的创新)
- 特点: 最大的变化是不再使用 TCP 协议,而是基于 QUIC (Quick UDP Internet Connections) 协议。
- 核心改进:
- 解决 TCP 队头阻塞: 虽然 HTTP/2 解决了应用层的队头阻塞,但 TCP 协议本身在丢包重传时仍可能导致 TCP 级别的队头阻塞。HTTP/3(QUIC)在应用层实现自己的可靠传输,解决了这个问题。
- 更快的连接建立: QUIC 协议集成了 TLS 握手,通常只需1个RTT(Round Trip Time)甚至 0 个 RTT 即可完成连接建立和加密握手,比 TCP 的三次握手+TLS 握手快得多。
- 连接迁移: 当客户端网络环境变化(如 Wi-Fi 切换到 4G),底层 IP 地址变化时,HTTP/2 需要重新建立 TCP 连接。QUIC 通过 Connection ID 机制,可以保持连接不断,实现无缝切换。
- 部署: 尽管协议新,但主流浏览器和 CDN 服务商已经广泛支持。
HTTP与HTTPS
HTTPS 并非是HTTP的复数形式(滑稽),而是 HTTP + SSL/TLS 协议的组合。
| 特点 | HTTP | HTTPS |
|---|---|---|
| 安全性 | 明文传输,容易被窃听或篡改。 | 加密传输,数据安全可靠 |
| 端口 | 默认端口:80 | 默认端口:443 |
| 证书 | 不需要证书 | 需要 SSL/TLS 证书来验证服务器身份和实现加密 |
| 层级 | 应用层 | 应用层 + 表示层(加密层) |