Skip to content

Commit 3c1fcf4

Browse files
oschwaldclaude
andcommitted
STF-322: Document transport-failure retry in README and CHANGELOG
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
1 parent 7cb87c5 commit 3c1fcf4

2 files changed

Lines changed: 49 additions & 0 deletions

File tree

CHANGELOG.md

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,16 @@
11
CHANGELOG
22
=========
33

4+
5.0.3 (unreleased)
5+
------------------
6+
7+
* Added `WebServiceClient.Builder.maxRetries(int)` to configure transport-
8+
failure retry behavior. Defaults to 1 (one retry on transient transport
9+
errors such as connection reset, broken pipe, EOF, or closed channel).
10+
Set to 0 to disable. `HttpTimeoutException` (covering both request-phase
11+
and connect-phase timeouts), `InterruptedIOException`, and HTTP 4xx/5xx
12+
responses are never retried.
13+
414
5.0.2 (2025-12-08)
515
------------------
616

README.md

Lines changed: 39 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -72,6 +72,45 @@ are not created for each request.
7272
See the [API documentation](https://maxmind.github.io/GeoIP2-java/) for
7373
more details.
7474

75+
### Connection pooling and transport retries ###
76+
77+
`WebServiceClient` is thread-safe and reuses a pooled `HttpClient` across
78+
requests. Idle connections in the pool can be silently closed by load
79+
balancers or other intermediaries. When the next request reuses one of these
80+
half-closed connections, the JDK reports the failure as a `Connection reset`,
81+
`Broken pipe`, or related transport `IOException`.
82+
83+
To smooth over these intermittent transport failures, the SDK retries once
84+
by default. Any transport-level `IOException` raised by the underlying HTTP
85+
send is retried, with two exceptions:
86+
87+
* `HttpTimeoutException` — a request-phase timeout. Connect-phase timeouts
88+
(`HttpConnectTimeoutException`) are also excluded because they extend
89+
`HttpTimeoutException`. The SDK honors the timeouts you configure.
90+
* `InterruptedIOException` — the calling thread was interrupted; the SDK
91+
honors the cancellation rather than override it.
92+
93+
HTTP 4xx and 5xx responses are not retried — they are returned as
94+
`HttpResponse` objects (not `IOException`s) and surfaced through the existing
95+
exception hierarchy. Web service requests are idempotent GETs, so retried
96+
requests are byte-identical to the original.
97+
98+
You can change the retry budget via the builder:
99+
100+
```java
101+
WebServiceClient client = new WebServiceClient.Builder(42, "license_key")
102+
.maxRetries(2) // up to two retries (three total attempts)
103+
.build();
104+
```
105+
106+
Set `.maxRetries(0)` to disable the retry entirely. Negative values throw
107+
`IllegalArgumentException`.
108+
109+
If you frequently see `Connection reset` errors, you can also reduce the
110+
JDK's keep-alive timeout via the system property
111+
`jdk.httpclient.keepalive.timeout` (in seconds) to evict pooled connections
112+
before any intermediary does so.
113+
75114
## Web Service Example ##
76115

77116
### Country Service ###

0 commit comments

Comments
 (0)