Documentation
¶
Overview ¶
Package transport 提供 BridgeTransport 的具体实现.
当前实现:
- SSETransport : Server-Sent Events, 防火墙友好, 适合 Web/IDE 客户端
- WebSocketTransport : 双向 WebSocket, 低延迟, 适合实时交互 (websocket.go, 2026-04-16 L1328b)
未实现 (待真实客户驱动):
- LongPoll : 最大兼容性, 现代网络环境基本不需要, 不做假设性实现
Package transport - websocket.go 实现 bridge.BridgeTransport 的 WebSocket 协议.
协议约定:
- 客户端 GET <prefix>/ws?session_id=<id> 建立双向 WS 通道
- 上行: 客户端发 WS text frame, payload 是 bridge.ClientMessage JSON
- 下行: 服务端发 WS text frame, payload 是 bridge.BridgeEvent JSON
- Keepalive: 服务端每 PingInterval 主动发 Ping, 客户端回 Pong
与 SSE 的差异:
- 单端点双向, 不需要分离 /events (GET 流) 和 /messages (POST)
- 低延迟 (无 POST 往返成本), 但企业代理/WAF 可能拦 Upgrade 帧
- 不原生支持 Last-Event-ID 断线重连 -- 本最小版未实现 ResumeWindow, 客户端必须自行保留未确认事件序号并在重连 query 里传 last_event_id. SSE 环形缓冲设计迁移 WS 需要新 ack 协议, 非零成本, 留作独立 TODO.
升华改进(ELEVATED): 复用 pkg/websocket.UpgradeHTTP + WebSocketConn 的 825 行 底层 RFC 6455 实现, bridge 层只做 SessionConn 契约适配, 协议栈零重复. 替代方案(路径 B, 否决): 让 websocket 包反向 import bridge 自暴露 BridgeTransport -- 破坏 websocket 包自包含性且依赖层级倒挂 (bridge 消费 websocket 是正向, 反过来不是).
Index ¶
- type SSESessionConn
- type SSETransport
- type WebSocketSessionConn
- func (c *WebSocketSessionConn) Close() error
- func (c *WebSocketSessionConn) Done() <-chan struct{}
- func (c *WebSocketSessionConn) Recv() <-chan bridge.ClientMessage
- func (c *WebSocketSessionConn) Send(ctx context.Context, evt bridge.BridgeEvent) error
- func (c *WebSocketSessionConn) SessionID() string
- type WebSocketTransport
Constants ¶
This section is empty.
Variables ¶
This section is empty.
Functions ¶
This section is empty.
Types ¶
type SSESessionConn ¶
type SSESessionConn struct {
// contains filtered or unexported fields
}
SSESessionConn 实现 bridge.SessionConn,基于 SSE 协议.
func (*SSESessionConn) Close ¶
func (c *SSESessionConn) Close() error
func (*SSESessionConn) Done ¶
func (c *SSESessionConn) Done() <-chan struct{}
func (*SSESessionConn) Recv ¶
func (c *SSESessionConn) Recv() <-chan bridge.ClientMessage
func (*SSESessionConn) Send ¶
func (c *SSESessionConn) Send(ctx context.Context, evt bridge.BridgeEvent) error
Send 将事件序列化为 SSE 格式推送给客户端.
SSE 格式:
id: <event-id>\n event: <type>\n data: <json-payload>\n \n
精妙之处(CLEVER): id 字段对 Last-Event-ID 机制至关重要-- 浏览器在断线重连时自动携带最后收到的 id,服务端据此重放. 没有 id 则 EventSource API 无法感知断线期间的事件.
func (*SSESessionConn) SessionID ¶
func (c *SSESessionConn) SessionID() string
type SSETransport ¶
type SSETransport struct {
// contains filtered or unexported fields
}
SSETransport 实现 bridge.BridgeTransport,使用 Server-Sent Events 协议.
协议约定:
- 客户端通过 GET /<prefix>/events?session_id=<id> 建立 SSE 流(接收事件)
- 客户端通过 POST /<prefix>/messages 发送消息(prompt/权限回复)
- 客户端可以携带 Last-Event-ID header 断线重连(服务端重放未收到的事件)
升华改进(ELEVATED): 早期方案 SSETransport 没有实现 Last-Event-ID 重连-- 断线后客户端丢失中间的事件,用户看到输出缺失. 我们维护每个会话的事件环形缓冲(ResumeWindow 条),断线重连时从指定 ID 重放. 替代方案:<强制客户端重新加载完整会话状态> - 否决:对长时间运行的 Agent 任务 用户体验很差(任务跑了 10 分钟,断线后前 9 分钟的输出全没了).
func NewSSETransport ¶
func NewSSETransport(prefix string, cfg bridge.BridgeConfig) *SSETransport
NewSSETransport 创建 SSE 传输层.
prefix: HTTP 路径前缀,如 "/bridge". SSE 端点:GET <prefix>/events?session_id=<id> 消息端点:POST <prefix>/messages
func (*SSETransport) Accept ¶
func (t *SSETransport) Accept() <-chan bridge.SessionConn
Accept 实现 bridge.BridgeTransport.
func (*SSETransport) ServeHTTP ¶
func (t *SSETransport) ServeHTTP(w http.ResponseWriter, r *http.Request)
ServeHTTP 实现 http.Handler,路由 SSE/消息端点请求.
type WebSocketSessionConn ¶
type WebSocketSessionConn struct {
// contains filtered or unexported fields
}
WebSocketSessionConn 实现 bridge.SessionConn, 基于 WebSocket 协议.
func (*WebSocketSessionConn) Close ¶
func (c *WebSocketSessionConn) Close() error
func (*WebSocketSessionConn) Done ¶
func (c *WebSocketSessionConn) Done() <-chan struct{}
func (*WebSocketSessionConn) Recv ¶
func (c *WebSocketSessionConn) Recv() <-chan bridge.ClientMessage
func (*WebSocketSessionConn) Send ¶
func (c *WebSocketSessionConn) Send(ctx context.Context, evt bridge.BridgeEvent) error
Send 将 BridgeEvent 序列化为 JSON 通过 WS text frame 推送给客户端.
func (*WebSocketSessionConn) SessionID ¶
func (c *WebSocketSessionConn) SessionID() string
type WebSocketTransport ¶
type WebSocketTransport struct {
// contains filtered or unexported fields
}
WebSocketTransport 实现 bridge.BridgeTransport, 使用 WebSocket 协议.
func NewWebSocketTransport ¶
func NewWebSocketTransport(prefix string, cfg bridge.BridgeConfig) *WebSocketTransport
NewWebSocketTransport 创建 WebSocket 传输层.
prefix 默认 "/bridge", 端点 GET <prefix>/ws?session_id=<id>.
func (*WebSocketTransport) Accept ¶
func (t *WebSocketTransport) Accept() <-chan bridge.SessionConn
Accept 实现 bridge.BridgeTransport.
func (*WebSocketTransport) ServeHTTP ¶
func (t *WebSocketTransport) ServeHTTP(w http.ResponseWriter, r *http.Request)
ServeHTTP 实现 http.Handler, 路由 WS 升级端点.