feat: sync httpdns sdk/platform updates without large binaries

This commit is contained in:
robin
2026-03-04 17:59:14 +08:00
parent 853897a6f8
commit 532891fad0
700 changed files with 6096 additions and 2712 deletions

View File

@@ -0,0 +1,282 @@
# HttpdnsNWHTTPClient 测试套件
本目录包<EFBFBD><EFBFBD>?`HttpdnsNWHTTPClient` <20><>?`HttpdnsNWReusableConnection` 的完整测试套件<E5A597><E4BBB6>?
## 测试文件结构
```
TrustHttpDNSTests/Network/
├── HttpdnsNWHTTPClientTests.m # 主单元测试44个
├── HttpdnsNWHTTPClientIntegrationTests.m # 集成测试<E6B58B><E8AF95>?个)
├── HttpdnsNWHTTPClientTestHelper.h/m # 测试辅助工具<E5B7A5><E585B7>?
└── README.md # 本文<E69CAC><E69687>?
```
## 测试覆盖范围
### 单元测试 (HttpdnsNWHTTPClientTests.m)
#### A. HTTP 解析逻辑测试 (25<32><35>?
- **A1. Header 解析 (9<><39>?**
- 正常响应解析
- 多个头部字段
- 不完整数据处<E68DAE><E5A484>?
- 无效状态行
- 空格处理<E5A484><E79086>?trim
- 空值头<E580BC><E5A4B4>?
- 非数字状态码
- 状态码为零
- 无效头部<E5A4B4><E983A8>?
- **A2. Chunked 编码检<E7A081><E6A380>?(8<><38>?**
- 单个 chunk
- 多个 chunks
- 不完<E4B88D><E5AE8C>?chunk
- Chunk extension 支持
- 无效十六进制 size
- Chunk size 溢出
- 缺少 CRLF 终止<E7BB88><E6ADA2>?
- <20><>?trailers <20><>?chunked
- **A3. Chunked 解码 (2<><32>?**
- 多个 chunks 正确解码
- 无效格式返回 nil
- **A4. 完整响应解析 (6<><36>?**
- Content-Length 响应
- Chunked 编码响应
- <20><>?body
- Content-Length 不匹<E4B88D><E58CB9>?
- 空数据错<E68DAE><E99499>?
- 只有 headers <20><>?body
#### C. 请求构建测试 (7<><37>?
- 基本 GET 请求格式
- 查询参数处理
- User-Agent 头部
- HTTP 默认端口处理
- HTTPS 默认端口处理
- 非默认端口显<E58FA3><E698BE>?
- 固定头部验证
#### E. TLS 验证测试 (4个占位符)
- 有效证书返回 YES
- Proceed 结果返回 YES
- 无效证书返回 NO
- 指定域名使用 SSL Policy
*注TLS 测试需要真实的 SecTrustRef 或复<E68896><E5A48D>?mock当前为占位<E58DA0><E4BD8D>?
#### F. 边缘情况测试 (8<><38>?
- 超长 URL 处理
- <20><>?User-Agent
- 超大响应体5MB<4D><42>?
- Chunked 解码失败回退
- 连接<E8BF9E><E68EA5>?key - 不同 hosts
- 连接<E8BF9E><E68EA5>?key - 不同 ports
- 连接<E8BF9E><E68EA5>?key - HTTP vs HTTPS
### 集成测试 (HttpdnsNWHTTPClientIntegrationTests.m)
使用 httpbin.org 进行真实网络测试 (22<32><32>?<3F><>?
**G. 基础集成测试 (7<><37>?**
- HTTP GET 请求
- HTTPS GET 请求
- HTTP 404 响应
- 连接复用(两次请求)
- Chunked 响应处理
- 请求超时测试
- 自定义头部验<E983A8><E9AA8C>?
**H. 并发测试 (5<><35>?**
- 并发请求同一主机<E4B8BB><E69CBA>?0个线程
- 并发请求不同路径<E8B7AF><E5BE84>?个不同endpoint<6E><74>?
- 混合 HTTP + HTTPS 并发各5个线程
- 高负载压力测试50个并发请求
- 混合串行+并发模式
**I. 竞态条件测<E4BBB6><E6B58B>?(5<><35>?**
- 连接池容量测试超过4个连接上限
- 同时归还连接<E8BF9E><E68EA5>?个并发)
- 获取-归还-再获取竞<E58F96><E7AB9E>?
- 超时与活跃连接冲突需31秒可跳过
- 错误恢复后连接池健康状<E5BAB7><E78AB6>?
**J. 高级连接复用测试 (5<><35>?**
- 连接过期与清理31秒可跳过
- 连接池容量限制验证10个连续请求
- 不同路径复用连接<E8BF9E><E68EA5>?个不同路径)
- HTTP vs HTTPS 使用不同连接池key
- 长连接保持测试20个请求间<E6B182><E997B4>?秒,可跳过)
## 运行测试
### 运行所有单元测<E58583><E6B58B>?
```bash
xcodebuild test \
-workspace TrustHttpDNS.xcworkspace \
-scheme TrustHttpDNSTests \
-destination 'platform=iOS Simulator,name=iPhone 15' \
-only-testing:TrustHttpDNSTests/HttpdnsNWHTTPClientTests
```
### 运行集成测试(需要网络)
```bash
xcodebuild test \
-workspace TrustHttpDNS.xcworkspace \
-scheme TrustHttpDNSTests \
-destination 'platform=iOS Simulator,name=iPhone 15' \
-only-testing:TrustHttpDNSTests/HttpdnsNWHTTPClientIntegrationTests
```
### 运行单个测试
```bash
xcodebuild test \
-workspace TrustHttpDNS.xcworkspace \
-scheme TrustHttpDNSTests \
-destination 'platform=iOS Simulator,name=iPhone 15' \
-only-testing:TrustHttpDNSTests/HttpdnsNWHTTPClientTests/testParseHTTPHeaders_ValidResponse_Success
```
## 测试辅助工具
### HttpdnsNWHTTPClientTestHelper
提供以下工具方法<EFBFBD><EFBFBD>?
#### HTTP 响应构<E5BA94><E69E84>?
```objc
// 构造标<E980A0><E6A087>?HTTP 响应
+ (NSData *)createHTTPResponseWithStatus:(NSInteger)statusCode
statusText:(NSString *)statusText
headers:(NSDictionary *)headers
body:(NSData *)body;
// 构<><E69E84>?chunked 响应
+ (NSData *)createChunkedHTTPResponseWithStatus:(NSInteger)statusCode
headers:(NSDictionary *)headers
chunks:(NSArray<NSData *> *)chunks;
```
#### Chunked 编码工具
```objc
+ (NSData *)encodeChunk:(NSData *)data;
+ (NSData *)encodeLastChunk;
```
#### 数据生成
```objc
+ (NSData *)randomDataWithSize:(NSUInteger)size;
+ (NSData *)jsonBodyWithDictionary:(NSDictionary *)dictionary;
```
## 测试统计
| 测试类别 | 测试数量 | 覆盖范围 |
|---------|---------|---------|
| HTTP 解析 | 25 | HTTP 头部、Chunked 编码、完整响<E695B4><E5938D>?|
| 请求构建 | 7 | URL 处理、头部生<E983A8><E7949F>?|
| TLS 验证 | 4 (占位<E58DA0><E4BD8D>? | 证书验证 |
| 边缘情况 | 8 | 异常输入、连接池 key |
| **单元测试合计** | **43** | - |
| 基础集成测试 (G) | 7 | 真实网络请求、基本场<E69CAC><E59CBA>?|
| 并发测试 (H) | 5 | 多线程并发、高负载 |
| 竞态条件测<E4BBB6><E6B58B>?(I) | 5 | 连接池竞态、错误恢<E8AFAF><E681A2>?|
| 连接复用测试 (J) | 5 | 连接过期、长连接、协议隔<E8AEAE><E99A94>?|
| 多端口连接隔<E68EA5><E99A94>?(K) | 5 | 不同端口独立连接<E8BF9E><E68EA5>?|
| 端口池耗尽测试 (L) | 3 | 多端口高负载、池隔离 |
| 边界条件验证 (M) | 4 | 端口迁移、高端口数量 |
| 并发多端口场<E58FA3><E59CBA>?(N) | 3 | 并行 keep-alive、轮询分<E8AFA2><E58886>?|
| **集成测试合计** | **37** | - |
| **总计** | **80** | - |
## 待实现测试(可选)
以下测试组涉及复杂的 Mock 场景,可根据需要添加:
### B. 连接池管理测<E79086><E6B58B>?(18<31><38>?
<EFBFBD><EFBFBD>?Mock `HttpdnsNWReusableConnection` 的完整生命周<E591BD><E591A8>?
### D. 完整流程测试 (13<31><33>?
<EFBFBD><EFBFBD>?Mock 连接池和网络层的集成场景
## Mock Server 使用
集成测试使用本地 mock server (127.0.0.1) 替代 httpbin.org提供稳定可靠的测试环境<E78EAF><E5A283>?
### 启动 Mock Server
```bash
cd TrustHttpDNSTests/Network
python3 mock_server.py
```
**注意**使用非特权端口<EFBFBD><EFBFBD>?1080/11443-11446无需 `sudo` 权限<E69D83><E99990>?
### 运行集成测试
在另一个终端窗口:
```bash
xcodebuild test \
-workspace TrustHttpDNS.xcworkspace \
-scheme TrustHttpDNSTests \
-destination 'platform=iOS Simulator,name=iPhone 15' \
-only-testing:TrustHttpDNSTests/HttpdnsNWHTTPClientIntegrationTests
```
### Mock Server 特<><E789B9>?
- **HTTP**: 监听 `127.0.0.1:11080`
- **HTTPS**: 监听 `127.0.0.1:11443`, `11444`, `11445`, `11446` (自签名证<E5908D><E8AF81>?
- **多端口目<E58FA3><E79BAE>?*: 测试连接池的端口隔离机制
- **并发支持**: 多线程处理,适合并发测试
- **零延<E99BB6><E5BBB6>?*: 本地响应测试速度<E9809F><E5BAA6>?
详见 [MOCK_SERVER.md](./MOCK_SERVER.md)
## 注意事项
1. **集成测试依赖 Mock Server**`HttpdnsNWHTTPClientIntegrationTests` 使用本地 mock server (127.0.0.1)。测试前需先启<E58588><E590AF>?`mock_server.py`<EFBFBD><EFBFBD>?
2. **慢测试跳<E8AF95><E8B7B3>?*部分测试需要等<E8A681><E7AD89>?1秒测试连接过期可设置环境变<E5A283><E58F98>?`SKIP_SLOW_TESTS=1` 跳过这些测试<E6B58B><E8AF95>?
- `testRaceCondition_ExpiredConnectionPruning_CreatesNewConnection`
- `testConnectionReuse_Expiry31Seconds_NewConnectionCreated`
- `testConnectionReuse_TwentyRequestsOneSecondApart_ConnectionKeptAlive`
3. **并发测试容错**并发和压力测试允许部分失败<EFBFBD><EFBFBD>?H.4 要求80%成功率因为高负载下仍可能出现网络波动<E6B3A2><E58AA8>?
4. **TLS 测试占位<E58DA0><E4BD8D>?*E <20><>?TLS 测试需要真实的 `SecTrustRef` 或高<E68896><E9AB98>?mock 框架当前仅为占位符<E4BD8D><E7ACA6>?
5. **新文件添加到 Xcode**:创建的测试文件需要手动添加到 `TrustHttpDNSTests` target<65><74>?
6. **测试数据**使<EFBFBD><EFBFBD>?`HttpdnsNWHTTPClientTestHelper` 生成测试数据确保测试的可重复性<E5A48D><E680A7>?
## 文件依赖
测试文件依赖以下源文件:
- `HttpdnsNWHTTPClient.h/m` - 主要被测试类
- `HttpdnsNWHTTPClient_Internal.h` - 内部方法暴露(测试专用)
- `HttpdnsNWReusableConnection.h/m` - 连接管理
- `HttpdnsNWHTTPClientResponse` - 响应模型
## 贡献指南
添加新测试时请遵循<EFBFBD><EFBFBD>?
1. 命名规范:`test<Component>_<Scenario>_<ExpectedResult>`
2. 使用 `#pragma mark` 组织测试分组
3. 添加清晰的注释说明测试目<E8AF95><E79BAE>?
4. 验证测试覆盖率并更新本文<E69CAC><E69687>?
---
**最后更<E5908E><E69BB4>?*: 2025-11-01
**测试框架**: XCTest + OCMock
**维护<E7BBB4><E68AA4>?*: Claude Code
**更新日志**:
- 2025-11-01: 新增 15 个多端口连接复用测试K、L、M、N组测试总数增至 37 <20><>?
- 2025-11-01: Mock server 新增 3 <20><>?HTTPS 端口<E7ABAF><E58FA3>?1444-11446用于测试连接池隔离
- 2025-11-01: 新增本地 mock server<EFBC8C><E69BBF>?httpbin.org提供稳定测试环<E8AF95><E78EAF>?
- 2025-11-01: 新增 15 个并发、竞态和连接复用集成测试H、I、J组