iOS Swift:用URLRequest创建WebSocket时Charles/Proxyman无法捕获流量
问题原因分析
- 用
URLRequest初始化URLSessionWebSocketTask时,URLSession内部请求处理逻辑可能绕过系统全局代理配置,尤其是手动构建的URLRequest未显式继承代理规则时,抓包工具无法拦截流量。 - 直接通过
URL初始化任务时,URLSession会自动加载系统预设的代理(即Charles/Proxyman配置的代理),因此抓包工具能正常捕获流量。 - 部分场景下,手动构建的
URLRequest若包含自定义头或特殊属性(如缓存策略、网络权限限制),可能干扰代理的拦截逻辑,导致流量无法被抓包工具捕获。
解决方法
显式为URLRequest配置代理
获取系统全局代理配置并应用到URLRequest中,确保请求走抓包工具的代理:let wsURL = URL(string: "wss://your-target-url")! var request = URLRequest(url: wsURL) // 复用系统代理字典(对应Charles/Proxyman的设置) if let proxyDict = URLSessionConfiguration.default.connectionProxyDictionary { request.connectionProxyDictionary = proxyDict } let task = URLSession.shared.webSocketTask(with: request)使用带代理配置的自定义URLSession
创建包含代理规则的会话配置,基于此配置初始化URLSession,后续无论用URL还是URLRequest创建任务,都会自动走代理:let proxyConfig = URLSessionConfiguration.default proxyConfig.connectionProxyDictionary = URLSessionConfiguration.default.connectionProxyDictionary let proxySession = URLSession(configuration: proxyConfig) // 两种初始化方式均能被抓包工具捕获 let taskWithURL = proxySession.webSocketTask(with: wsURL) let taskWithRequest = proxySession.webSocketTask(with: request)检查URLRequest的特殊属性
- 避免手动设置WebSocket握手相关的HTTP头(如
Connection: Upgrade、Sec-WebSocket-Key),交由系统自动处理,手动设置可能破坏代理的拦截流程。 - 确保未设置
allowsConstrainedNetworkAccess、timeoutInterval等可能干扰代理的属性,保持请求的默认网络权限配置。
- 避免手动设置WebSocket握手相关的HTTP头(如
验证SSL证书信任
确认iOS设备已信任Charles/Proxyman的根证书,避免因证书不被信任导致抓包工具无法解密WebSocket流量(此类场景下抓包工具会显示加密流量而非完全无数据)。
内容的提问来源于stack exchange,提问作者Matteo
相关产品推荐
相关产品推荐

