# java.net.SocketException: recvfrom失败: ETIMEDOUT（连接超时）在okhttp3.internal.http2.Http2Connection$ReaderRunnable.onSettings

- **ID:** `android/backpressure-queue-overflow-in-okhttp`
- **领域:** android
- **类别:** network_error
- **验证级别:** ai_generated
- **修复率:** 82%

## 根因

OkHttp的HTTP/2连接背压机制在服务器SETTINGS帧未在默认2秒窗口内确认时触发超时，通常是由于网络缓慢或服务器端连接饱和。

## 版本兼容性

| 版本 | 状态 | 引入 | 弃用 |
|------|------|------|------|
| OkHttp 4.12.0 | active | — | — |
| Android 14 (API 34) | active | — | — |
| Android 13 (API 33) | active | — | — |
| OkHttp 3.12.13 | active | — | — |

## 解决方案

1. ```
   Configure OkHttp to use a custom dispatcher with maxRequestsPerHost=1 and retryOnConnectionFailure(true) to reduce backpressure pressure. Example: new OkHttpClient.Builder().dispatcher(new Dispatcher() {{ setMaxRequestsPerHost(1); }}).retryOnConnectionFailure(true).build()
   ```
2. ```
   Set a custom socket factory that adjusts the SO_TIMEOUT to 5000ms on the underlying socket before the HTTP/2 connection is established. Example: OkHttpClient.Builder().socketFactory(new SocketFactory() { ... });
   ```
3. ```
   Upgrade OkHttp to version 4.12.0 or later which includes a fix for the backpressure timeout handling in the HTTP/2 reader loop.
   ```

## 无效尝试

- **Increase OkHttp connectTimeout to 30 seconds** — connectTimeout controls the initial TCP handshake, not the SETTINGS acknowledgment timeout. The backpressure timeout is hardcoded in OkHttp's HTTP/2 implementation at 2 seconds. (90% 失败率)
- **Disable HTTP/2 entirely by setting protocol to Protocol.HTTP_1_1** — While this avoids the error, it disables multiplexing and header compression, degrading performance for all requests. The underlying server or network issue remains unaddressed. (70% 失败率)
- **Increase readTimeout to 60 seconds** — readTimeout applies to individual stream reads, not the connection-level SETTINGS exchange. The backpressure timeout is independent and remains at 2 seconds. (95% 失败率)
