网络通信是后端架构的基石,从应用层的HTTP/HTTPS交互,到传输层的TCP/UDP可靠与高效传输,再到内核层的Socket与文件管理,每一环都隐藏着严谨的设计逻辑。本文将以“底层原理+实操落地+安全延伸”为主线,带你打通从编程实操到协议解析、安全防护再到内核逻辑的全链路,实现从理论到实战的能力跨越。
HTTPS协议:加密与安全的基石
在微服务和API通信中,数据安全是重中之重。HTTPS协议通过加密手段保护数据传输,防止中间人攻击。常见的加密方式包括对称加密和非对称加密。
对称加密:加密和解密使用同一个密钥,效率高,但密钥分发存在风险。例如,客户端和服务器共享一个密钥,如果密钥被截获,数据就会泄露。
同⼀个密钥可以同时用作信息的加密和解密,这种加密方法称为对称加密,也称为单密钥加密
特征:加密和解密所用的密钥是相同的
特点:算法公开、计算量小、加密速度快、加密效率高
举例:按位异或:
7^5 =x ;这个x是密文 7是明文 5是密钥
然后x^5之后就得到了7
非对称加密:使用公钥和私钥对,公钥加密的数据只能用私钥解密,解决了密钥分发问题,但性能较慢。
这种加密需要用到两个密钥,一个是公有密钥(公钥),一个是私有密钥(私钥)
可以通过公钥对明文加密,变成密文;通过私钥对密文解密,变成明文–一般用这种,比下面这种安全
也可以通过私钥对明文加密,变成密文;通过公钥对密文解密变成明文
设计一套安全的方案需要结合两者:先用非对称加密安全地交换对称密钥,再用对称加密进行数据传输。但如何确保公钥的真实性?这就需要CA认证。
目前已经有成熟的方案了,这里只是自己模拟设计一套较为安全的方案
方案一:只使用对称加密
这样的话,很不安全–因为密钥没有被加密
方案二:只使用非对称加密
也不安全–因为公开密钥提供给客户端时没有被加密
方案三:双方都使用非对称加密
具体流程:
服务端拥有公钥S与对应的私钥S’,客户端拥有公钥C与对应的私钥C’
1.客户端和服务端交换公钥
2.客户端给服务端发信息:先⽤S对数据加密,再发送,只能由服务器解密,因为只有服务器有私钥S’
3.服务端给客户端发信息:先用C对数据加密,再发送,只能由服务器解密,因为只有服务器有私钥C’
但是效率太低了;而且还有安全问题
安全问题:中间人被黑客入侵,有公钥M,A和私钥M’,A’–可以劫持S和C,然后把公钥换成M和A给双方,然后可以对传输内容解密之后再用S和C加密传走
方案四:非对称加密+对称加密
具体流程:
服务端具有非对称公钥S和私钥S’
客户端发起https请求,获取服务端公钥S
客户端在本地生成对称密钥C, 通过公钥S加密, 发送给服务器
只有刚开始时用的非对称加密,之后都是用的对称加密
但是也存在上面的那种安全问题 但是效率比方案三快很多–因为
这个问题就是因为客户端不能确定这个密钥是服务器发来的,所以就需要CA认证这个东西
方案五:方案四+CA证书
注意:客户端本来就是会内置很多CA机构的公钥的
CA(证书颁发机构)是可信的第三方,它为服务器颁发数字证书,证明公钥确实属于该服务器。CA证书的形成过程包括:服务器生成密钥对,将公钥提交给CA,CA验证身份后,用自己的私钥对公钥进行签名,生成证书。

这个证书的话,CA机构会核实申请认证提供的资料是不是对的–但是也有中间人篡改的风险,但是概率就非常小了
如果中间人单纯篡改证书的话–比如:篡改公钥–CA机构会去查这个公钥跟这个域名和申请者的关系
如果中间人掉包整个证书的话–必须找CA机构生成,那么申请者这些就不好填了
一般是先生成公钥和私钥对,然后再生成文件,把这个文件传给CA机构
当服务端申请CA证书的时候,CA机构会对该服务端进行审核,并专门为该网站形成数字签名–CA机构有自己的非对称加密的私钥和公钥,用证书明文数据形成数据摘要,然后私钥加密形成数字签名,把签名附加在数据上,就成了一份CA证书

问题:
为什么签名不能直接加密传过去,而是要先形成摘要再加密形成签名传过去
原因:缩小签名长度,加快验证签名的速度
为什么不能直接传摘要过去,而是要加密形成签名之后传过去
原因:不加密的话,中间人篡改了,客户端也分辨不出来
实践建议:在后端开发中,使用HTTPS时务必配置正确的证书链,并定期更新证书。避免使用自签名证书,除非在测试环境。
再谈UDP与TCP协议:传输层的双雄
UDP和TCP是传输层两大核心协议,分别适用于不同场景。
UDP协议:高效但不可靠
UDP提供无连接、不可靠的数据报服务,适用于实时性要求高的场景,如视频直播、在线游戏。
UDP协议端的格式:
UDP长度:表示整个数据报(首部+数据)的最大长度
这个检验和的话是用于检验数据有没有被篡改啥的
UDP没有真正意义上的发送缓冲区来暂存待发数据
UDP的接收缓冲区的话不维护传输顺序并且满则丢弃
管理UDP报文的话也是采用的先描述再组织
虽然UDP不可靠,但我们可以通过应用层逻辑实现可靠传输,例如添加序列号、确认重传机制。这也正是中间件设计中的常见思路。
TCP协议:可靠但复杂
TCP是面向连接的、可靠的字节流协议,是大多数后端API通信的基础。TCP协议段格式包含源端口、目的端口、序列号、确认号、标志位等关键字段。

上面的选项和数据部分是可以没有的(除了选项和数据的部分叫做标准报头)
TCP的首部是指里面除了数据的部分–其长度是在20-60个字节之间的(标准报头部分是20个字节)
数据部分叫做有效载荷
上面各个部分的作用:
4位首部长度:就是4个二进制位来表示首部长度(它的基本单位是4个字节–也就是说0001就表示首部长度一共4个字节)
16位窗口大小:存的是自己的接收缓冲区的剩余空间的大小–流量控制需要用到
32位序号:保证数据的按序到达(因为传输过去的数据因为网络传输速度不一样,到达的顺序是不一样的)–给的是传输的部分的第一个的序号
–TCP给每个字节的数据都是编了号的(一般都不是从1开始编,是X+偏移量这样规定)
–TCP每次建立连接时,都会给一个随机的初始序号X --好处:和一样,来避免收到历史数据
32位确认序号:就是收到数据的末尾序号+1再传回去–让另一方知道下一次该从哪开始传
–传递的信息是确认序号之前的报文全部收到了
16位紧急指针: 标识哪部分数据是紧急数据
(紧急数据默认只允许1个字节的空间,紧急数据又被叫做带外数据)
–接收方会优先读取这个位置的数据 应用场景:比如关机指令
6个标志位:用来表明报文的类型(置为1表示有效,置为0表示无效)
URG: 紧急指针是否有效
ACK: 表示确认序号是否有效
PSH: 提示接收端应用程序立刻从TCP缓冲区把数据读走(可能是缓冲区快满了或者其他原因)
RST: 对方要求重新建立连接; 我们把携带RST标识的称为复位报文段
SYN: 请求建立连接; 我们把携带SYN标识的称为同步报文段
FIN: 通知对方, 本端要关闭了;我们把携带FIN标识的报文段称为结束报文段
要有序号和确认序号的原因:比如捎带应答就两个都需要,它既需要传递数据,又需要应答
确认应答机制和超时重传机制:发送方发送数据后等待ACK,如果超时未收到则重传,保证数据不丢失。

确认应答机制就是发送给对方数据,对方要返回做出应答并且返回下一次该从哪里开始传
–传递数据时可以一段一段传,也可以多段一起传过去(多段一起传的话,不是最后那个应答丢失了都可以继续)
注意:在一般情况下,如果发送方没有收到应答的话,就认为对方没有收到数据–这个时候就会重新给对方传–这个就是超时重传机制
超时重传的超时时间的确定方法:
这个时间TCP是会动态计算的–因为跟网络环境有关
–如果设置的时间过长,会影响重传效率;如果设置的时间过短,会频繁发送重复的报文过去
一般超时以500ms为一个单位进行控制,每次判定超时重发的超时时间都是500ms的整数倍–并且会以指数形式递增(比如第一次是,还没应答,那下次就是)
–如果累计到一定的重传次数还没接收,TCP认为网络或者对端主机出现异常, 强制关闭连接
连接管理机制:三次握手建立连接,四次挥手释放连接。如果服务端收到了SYN但还没收到客户端对SYN+ACK的回应,连接处于半连接状态,由半连接队列管理。

SYNSYN+ACK建立连接:需要三次握手–三次握手完毕,才会返回
三次握手就是上面的SYN–SYN+ACK–ACK
(本质是在检验客户端与服务器之间的 “全双工通信通路” 是否通畅)
建立好的连接会由OS来描述后用全连接队列进行管理,的话只是从全连接队列里面去拿而已
全连接队列的最大长度由的第二个参数决定
–就是全连接队列的最大长度
三次握手的作用:
1.建立连接 2.协商起始序号 3.协商双方额接受缓冲区大小
取消连接:需要四次挥手
四次挥手就是上面的FIN–ACK–FIN–ACK
发送FIN的话就表示关闭了自己的写端,就不能发数据了–跟发控制报文(eg:ACK)区分
主动断开连接的一方在发送完最后一个 后,立即进入 状态,等待一段时间之后,会自动释放–此时连接还没有彻底断开,服务端的和还在被使用,无法立即被重新启用(客户端没关系,因为客户端本来就是随机端口)–此时的话可以通过
四次挥手有时也可以只3次
–就是客户端想FIN的时候,服务端也正好想FIN–那服务端就会把ACK捎带应答过去
为什么需要:
1.让通信双方的历史数据得以消散 – 可能会废弃的数据(比如已经被补发了的数据)还在传
2.让4次挥手有较好的容错性–让有重发的机会
一般设计的是等待两个的时间
一个是 TCP 报文段在网络中能存活的最长时间
这个可以查看或者人为改动:打开或者把里面的值改了就行
注意:跟区分
为什么全连接队列不能太长,但是也不能没有:
太长的话会太占用服务端的资源
没有的话不能充分利用服务端的资源–就像满客状态的餐厅,外面会有椅子让别人等
为什么设计成三次握手:
因为只有一次握手的话,容易有攻击服务器
只有两次握手的话,就相当于把风险给了服务器–因为服务器建立的可能客户端没建立–所以需要奇数次握手,把握手失败的成本给客户端承担
而且三次握手可以确认 “双向收发通道均正常”
但是三次握手也是有攻击的方法的:
用肉机去把服务端的全连接和半连接队列全部塞满
引申:释放全连接比释放半连接所需要的时间会长很多
为什么设计成四次挥手:
因为是全双工通信,双方都有可能发送数据,所以双方要各说两次–一次是我想结束了,一次是我收到你的回应了
⚠️ 注意事项:在高并发场景下,半连接队列和全连接队列的大小需要合理配置,否则可能导致连接失败或性能下降。
流量控制与滑动窗口:避免缓冲区溢出
TCP通过流量控制防止发送方发送数据过快导致接收方缓冲区溢出。接收方在ACK中携带窗口大小(win),发送方据此调整发送速率。
TCP支持根据接收端的处理能力, 来决定发送端的发送速度. 这个机制就叫做流量控制
–如果太快了,容易丢包;如果太慢了又影响效率
–这个机制的话以可靠性为主,以提高效率为辅
这个机制是通过控制滑动窗口大小来实现的
窗口探测时是不会携带其他数据的
问题:
第一次发送数据时是怎么保证发送数据量是合理的
–三次握手时交换了报文了,已经协商了双方的接受能力
(注意:第三次握手其实可以携带数据过去了–比如:也搞个捎带应答)
滑动窗口机制允许发送方在未收到ACK的情况下连续发送多个数据包,提高吞吐量。窗口大小动态调整,兼顾效率和可靠性。
滑动窗口是发送缓冲区的一部分(每个TCP连接都有自己专属的发送缓冲区–互不干扰的)
发送缓冲区里面的数据可以分为:已发送已应答 、已发送未应答、未发送(通过指针和下标来把区域划分出来)
引申:已发送已应答的部分可以被覆盖使用了 --空闲的空间也可以划到这个部分来
滑动窗口里面的数据是:已发送未应答的 或者 已经准备好发送,但是还没发出的
–因为有滑动窗口的存在,才可以一次向对方发送大量的tcp报文
窗口越大, 网络吞吐量就越大, 传输效率就越高
滑动窗口不会在发送缓冲区中越界的原因:
tcp采用了类似环状算法来管理发送缓冲区
滑动窗口的大小和移动方向:
滑动窗口一般都是向右移动的–向左是异常现象
滑动窗口的大小是动态变化的
–滑动窗口的大小 = min(接收窗口的大小,拥塞窗口的大小)
想要让滑动窗口变大的方法:延迟应答
让接受方收到报文后先不着急应答 -->给上层充足的时间去取走数据来让剩余空间变多
推荐做法:每次都让上层尽快通过啥的把数据从内核中拿出来
滑动窗口里面的数据出现丢包的话,处理方法:
1.数据包到了,但是ACK丢失了
这种情况没事,因为确认序号那个的存在本来就允许少量的ACK丢失
2.数据包丢失
那么确认序号就会一直卡在那里,导致确认应答是重复的–收到三次重复的确认应答,发送方就会重新发送 --这个叫做快重传(高速重发机制)
比如:传过去,丢了,那就重新传过去,就和之间已经到了的联动了
快重传和超时重传:
超时重传相当于是兜底的
–不管有没有收到重复 ACK,只要某个数据段的超时计时器到期,就直接重传这个数据段
滑动窗口内的 “流式数据”,必须按 MSS 的大小拆分成多个 TCP 分段发送
滑动窗口规定了 “当前能发的总数据量上限”
MSS 规定了 “每个 TCP 分段的最大数据量”
MSS的值就是在TCP首部的40字节变长选项中(kind=2)
TCP的单个数据报的最大消息长度, 称为MSS
实践建议:在后端架构中,合理调整TCP缓冲区大小和窗口缩放因子,可以显著提升数据库连接池或微服务间通信的性能。
拥塞控制与延迟应答:网络稳定性的守护者
拥塞控制防止过多数据注入网络导致路由器或链路拥塞。TCP采用慢启动、拥塞避免、快速重传和快速恢复等算法。
通信的时候,如果出现了少量的丢包–那是正常现象
如果出现了大量的丢包–tcp就会判定是网络出问题了(网络拥塞)–此时不能对报文进行超时重传!会加重拥塞的情况
TCP协议让大家达成了应对网络拥塞的共同规则–采用的同一个拥塞控制规则
拥塞控制的策略:引入了一个拥塞窗口 +慢启动机制
拥塞窗口:也是一个动态的窗口,是主机判断网络健康程度的指标;超过拥塞窗口的大小就会引发网络拥塞,反之则不会
发送开始的时候, 定义拥塞窗口大小为1;每次收到一个ACK应答, 拥塞窗口加1
慢启动机制:初始时慢, 但是增长速度非常快–初始时慢就是看网络是不是恢复正常了
当拥塞窗口的大小超过的时候, 不再按照指数方式增长, 而是按照线性方式增长
当TCP开始启动的时候, 慢启动阈值等于窗口最大值
在每次超时重发的时候, 慢启动阈值会变成原来的一半, 同时拥塞窗口置回
延迟应答:接收方不立即发送ACK,而是等待一段时间(通常200ms)或积累多个数据包后再确认,减少ACK数量,提升效率。
延迟应答是不能无限制延迟的,有两个约束条件:
数量限制:每隔 N 个包必须应答一次,不能无限攒包
时间限制:只要超过了最大延迟时间,就必须立刻应答
TCP协议小结:TCP提供可靠、有序、无重复的数据传输,但牺牲了一定的效率和复杂性。在实际开发中,需要根据业务场景选择合适的传输协议。
可靠性:
1.校验和 2.序列号保证按序到达 3.确认应答机制(核心) 4.超时重发
5.连接管理 6.流量控制 7.拥塞控制(还操心了网络)
提高性能:
1.滑动窗口 2.快重传 3.延迟应答 4.捎带应答
这些机制几乎在两端的机器上都起作用
对于TCP是面向字节流的理解:
tcp内核只把数据当成多个字节去传输–不关心上层协议和上层的报文格式(所以tcp的有效载荷不是以报文为单位的)
–用户层把请求发送给tcp,tcp当成多个字节去传;用户层接收的话,需要自行把多个字节组合重新形成回请求 (这个时候就容易出现粘包问题了)
内核的TCP报文里面不记录有效载荷长度的原因:
TCP是面向字节流的,本来有效载荷里面的数据就多半不是应用层完整的报文的,所以没必要
粘包问题:就是数据包和数据包的边界划分不清晰导致多划或者少划了
解决方法:制定协议(在应用层通过协议来明确报文和报文之间的边界)
1.定长报文
2.使用特殊字符
3.自描述字段+定长报文
4.自描述字段+特殊字符
TCP的异常情况:
进程终止(正常终止还是异常终止都一样):连接会以正常的方式断开
机器重启:会杀掉所有进程,连接关闭方式和进程终止一致
机器掉电或者网线断开:这里连接会非正常断开
a.发信息发现连接失效会强制重新连接
b.客户端网络没了会断开自己这边的连接,但是服务端不知道
c.长时间没有数据交互,若长时间没数据交互,TCP 的 “保活定时器” 会定期检测连接
Socket与文件的关系及UDP可靠传输
在Linux中,Socket和文件的关系密切:Socket也是一种文件描述符,支持read/write等系统调用。内核通过文件系统管理网络连接,这也是“一切皆文件”哲学的体现。
对于开发者说是接口;但是在Linux内核里面是被当作特殊文件来看待的
Linux内核里面文件通过存储的,也是这样
–是存文件的操作方法的,普通文件是指向读写磁盘的方法,是指向网络相关的方法
来指向的核心结构体
如何用UDP实现可靠传输:可以在应用层引入确认重传、序列号、超时重传等机制,模仿TCP的行为。许多中间件(如QUIC)正是基于此思路设计。
[AFFILIATE_SLOT_1]这是一道经典面试题
这样做肯定是有特定的需要可靠传输的场景,但是又不需要TCP那样非常完美的可靠性–只需要按照需要模仿TCP的实现可靠性的机制改良UDP就行了(如何模仿着实现也要说出来)
作业与实战练习
为了巩固知识,请完成以下编程练习。这些案例涵盖UDP广播、TCP多版本服务端及客户端重连,帮助你深入理解Socket编程与系统调用。
文件传输使用的协议是(B) A.SMTP//简单邮件协议 B.FTP C.UDP//用户数据报协议 D.TELNET//Internet远程登录服务的标准协议以下关于HTTP协议叙述正确的是(C) A.HTTP协议是建立在 TCP/IP 协议之上的网络层规范,分为三个部分:状态行、请求头、消息主体 //HTTP协议是TCP/IP协议栈中应用层的协议 B.Cookie数据在消息主体(body)中传输//Cookie数据是在HTTP协议头部字段中传输 C.HTTP协议支持一定时间内的TCP连接保持,这个连接可以用于发送/接收多次请求 D.HTTP是有状态的,每个请求都是独立的以下对http请求方法描述正确的是(ABC) A.POST请求永远不会被缓存,且对数据长度没有限制 B.我们可以从浏览器历史记录中查找到GET请求 C.我们无法从浏览器历史记录中查找到POST请求 引申:HTTP GET请求提交参数有长度限制--是特定的浏览器及服务器对它的限制如何在响应报文头部去设置字符编码(AC) A.Content-Type: charset=utf-8 B.Content-language: charset=utf-8 C.Content-Type: charset=UTF-8 D.Content-language: charset=UTF-8【多选题】cookie有什么用?(ABC) A.记录用户的ID B.记录用户的密码 C.记录用户浏览过的商品记录 D.记录用户的浏览器设置单个cookie保存的数据不能超过4K,很多浏览器都限制一个站点最多保存20个cookie session并不一定完全依赖于cookie实现--只是一般是用cookie搞的 一般session的有效期默认是30分钟【多选题】以下关于http和https说法正确的是(ABCD) A.http是超文本传输协议 B.https是超文本传输安全协议 C.http是明文传输 D.https是加密传输【多选题】FTP服务的控制端口与数据端口默认是(AB) A.20 B.21 C.22 D.23 FTP协议中,20端口号用于传输数据,21端口号用于传输控制关于UDP的说法正确的是(B) A.UDP的包大小没有限制//UDP报文限制传输报文大小为必须小于64k B.UDP不会进行错误重传 C.UDP跟TCP一样提供可靠的数据报协议//UDP不保证数据安全及有序到达对端 D.UDP有简单的流控制//UDP是数据报传输,没有流控制主机甲向主机乙发送一个(SYN=1,seq=11220)的TCP段,期望与主机乙建立TCP连接 若主机乙接受该连接请求,则主机乙向主机甲发送的正确的TCP段应该是(B) A.(SYN=1,ACK=1,seq=11220,ack=11220) B.(SYN=1,ACK=1,seq=11221,ack=11221) C.(SYN=0,ACK=0,seq=11221,ack=11221) D.(SYN=0,ACK=1,seq=11220,ack=11220) seq:发送方的本条报文起始序号 ack:是接收到的序号的末尾+1✅ 通过以上练习,你将掌握从Socket编程到协议定制、从加密认证到拥塞控制的全链路知识,为后端架构和微服务开发打下坚实基础。
[AFFILIATE_SLOT_2]总结:网络通信是后端开发的核心技能,本文从HTTPS加密、UDP/TCP协议、流量控制、拥塞控制到Socket与文件关系,全面解析了网络基础全链路。掌握这些知识,你将能更自信地设计高性能、安全的API和微服务系统。
.csrTIME_WAIT500*1500*2connectacceptlistenbacklogbacklog+1ACKTIME_WAITipportsetsocketopt解决TIME_WAITTIME_WAITMSLMSLproc/sys/net/ipv4/tcp_fin_timeoutTIME_WAITCLOSE_WAITSYN洪水recv、read1001-50002001-30002001-3000慢启动的阈值socketstruct filesocketconst struct file_operations *f_opsocketvoid *private_datasocketstruct socket






浙公网安备 33010602011771号