WebSocket

WebSocket连接建立过程

  sequenceDiagram
	note over Client,Server: TCP三次握手(传输层)
	Client ->> Server: SYN
	Server ->> Client: SYNC+ACK
	Client ->> Server: ACK
	
	note over Client,Server: HTTP请求 转换为WebSocket协议(应用层)
	Client ->> Server: HTTP GET请求<br>GET HTTP1.1<br>Connection:Upgrade<br>Upgrade:websocket<br>Sec-Websocket-Key: 字符串.base64()
	note over Server: Sec-Websocket-Accept=fn(字符串)
	Server ->> Client: HTTP 101响应<br>HTTP1.1 101 Switching Protocals<br>Sec-Websocket-Accept:base64码<br>Upgrade:websocket<br>Connection:Upgrade
	note over Client: check(fn(base64(字符串))=Sec-Websocket-Accept)
	
	note over Client,Server: Websocket连接成功 基于TCP长连接<br>(HTTP通常返回消息后就断开了 但是ws没断开)
	Server ->> Client: Websocket数据帧
	Server ->> Client: Websocket数据帧
	Client ->> Server: Websocket数据帧
	Client --> Server: ......

SSE

llm chatbot 挨个吐字的过程展示

  sequenceDiagram
    autonumber
    participant Client as 浏览器/客户端
    participant Server as 后端服务 (Go)
    participant AI as 大模型 (LLM)

    Note over Client, Server: 1. 建立连接
    Client->>Server: HTTP GET /chat/stream
    Server-->>Client: 200 OK<br/>Content-Type: text/event-stream<br/>Connection: keep-alive

    Note over Server, AI: 2. 触发推理
    Server->>AI: 发送 Prompt
    
    loop 流式生成 (Streaming)
        AI-->>Server: 生成 Token: "你"
        Server-->>Client: data: "你"\n\n (立即 Flush)
        
        AI-->>Server: 生成 Token: "好"
        Server-->>Client: data: "好"\n\n (立即 Flush)
        
        AI-->>Server: 生成 Token: "..."
        Server-->>Client: data: "..."\n\n (立即 Flush)
    end

    AI-->>Server: 生成结束 [DONE]
    Server-->>Client: data: [DONE]\n\n
    Note over Client, Server: 3. 连接关闭 (可选)

几个思考

  1. 双工通信 客户端用http 服务端用SSE不就行了,为什么有的场景要用websocket

    1. 频繁交互的从场景,每次http都会重新握手(而且每次请求带完整头部),严重影响效率

    2. 一些要保活的场景,无法知道客户端是否断开了(除非手动实现心跳),而webocket有专门的断开事件

      webskt通过http建联(通过你要到了你室友的微信) 后续不再需要http建联,直接互相沟通(再多一个步骤 会降低很多效率 每次都要经过你)

    3. 1条sse长链接+n个http短连接 vs 1条websocket长链接

    4. SSE 的定位:仅作为补充方案,用于纯单向、低频次、非核心的推送场景

    5. SSE 是单向推送,服务端调用 Write 后无法知道客户端是否收到,也无法捕获 “推送失败” 的错误。而websocket可以收到 然后选择是否重试

    6. 消息结构

      1. WebSocket 采用二进制 / 文本帧传输,帧头部仅 2~10 字节
      2. SSE 必须遵循 data: 内容\n\n 的格式,每条消息都要加 data: 前缀和 \n\n 后缀
  2. 为什么AI回复这个场景适合使用SSE?一次请求多次响应 完全符合SSE的原理。这一次建联请求忽略不计

  3. 为什么直播间或游戏用WebSocket?多次请求多次响应并行 双向通信