From 10861257022cf5daeecc0392f4c88930e6bdb47a Mon Sep 17 00:00:00 2001 From: Jesse Wilson Date: Sat, 8 Nov 2025 16:45:04 -0500 Subject: [PATCH] Fix a flake in TrailersTest (#9185) * Fix a flake in TrailersTest We weren't testing what we wanted to be testing because the cache was on, and that impacts how Response.body.close() works. * Fix HTTP/1 also * Spotless --------- Co-authored-by: Jesse Wilson --- .../jvmTest/kotlin/okhttp3/TrailersTest.kt | 24 +++++++++++++++++-- 1 file changed, 22 insertions(+), 2 deletions(-) diff --git a/okhttp/src/jvmTest/kotlin/okhttp3/TrailersTest.kt b/okhttp/src/jvmTest/kotlin/okhttp3/TrailersTest.kt index c7b269fe9..e41124d54 100644 --- a/okhttp/src/jvmTest/kotlin/okhttp3/TrailersTest.kt +++ b/okhttp/src/jvmTest/kotlin/okhttp3/TrailersTest.kt @@ -37,6 +37,7 @@ import mockwebserver3.junit5.StartStop import okhttp3.Headers.Companion.headersOf import okhttp3.HttpUrl.Companion.toHttpUrl import okhttp3.ResponseBody.Companion.toResponseBody +import okhttp3.internal.http.ExchangeCodec.Companion.DISCARD_STREAM_TIMEOUT_MILLIS import okhttp3.internal.http2.Http2Connection.Companion.OKHTTP_CLIENT_WINDOW_SIZE import okhttp3.testing.PlatformRule import okio.BufferedSource @@ -585,6 +586,15 @@ open class TrailersTest { /** * If the client closes the connection while it is consuming the response body, attempts to peek * or read the trailers should throw. + * + * This test needs to make two interventions to prevent OkHttp from reading the entire response + * body, which it will attempt to do otherwise: + * + * * Don't cache the response. The cache will try to read the entire response body so that it + * can successfully complete the cache entry. + * + * * Throttle the response. The HTTP/1 connection pool will attempt to read the entire response + * body so that it can pool the connection. */ private fun trailersWithClientPrematureClose(protocol: Protocol) { val halfResponseBody = "a".repeat(OKHTTP_CLIENT_WINDOW_SIZE) @@ -596,10 +606,20 @@ open class TrailersTest { .addHeader("h1", "v1") .trailers(headersOf("t1", "v2")) .body(protocol, halfResponseBody + halfResponseBody) - .build(), + .throttleBody( + OKHTTP_CLIENT_WINDOW_SIZE.toLong(), + DISCARD_STREAM_TIMEOUT_MILLIS.toLong() + 1L, + TimeUnit.MILLISECONDS, + ).build(), ) - val call = client.newCall(Request(server.url("/"))) + val call = + client.newCall( + Request( + url = server.url("/"), + headers = headersOf("Cache-Control", "no-store"), + ), + ) call.execute().use { response -> val source = response.body.source() assertThat(response.header("h1")).isEqualTo("v1")