Skip to content

Commit ef5fff5

Browse files
committed
8218546: Unable to connect to https://google.com using java.net.HttpClient
Reviewed-by: clanger Backport-of: b240c60
1 parent 8359d7f commit ef5fff5

File tree

2 files changed

+63
-28
lines changed

2 files changed

+63
-28
lines changed

src/java.net.http/share/classes/jdk/internal/net/http/Stream.java

Lines changed: 0 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -614,10 +614,6 @@ private OutgoingHeaders<Stream<T>> headerFrame(long contentLength) {
614614
if (contentLength > 0) {
615615
h.setHeader("content-length", Long.toString(contentLength));
616616
}
617-
URI uri = request.uri();
618-
if (uri != null) {
619-
h.setHeader("host", Utils.hostString(request));
620-
}
621617
HttpHeaders sysh = filterHeaders(h.build());
622618
HttpHeaders userh = filterHeaders(request.getUserHeaders());
623619
// Filter context restricted from userHeaders

test/jdk/java/net/httpclient/SpecialHeadersTest.java

Lines changed: 63 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*
2-
* Copyright (c) 2018, Oracle and/or its affiliates. All rights reserved.
2+
* Copyright (c) 2018, 2019, Oracle and/or its affiliates. All rights reserved.
33
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
44
*
55
* This code is free software; you can redistribute it and/or modify it
@@ -25,7 +25,7 @@
2525
* @test
2626
* @summary Verify that some special headers - such as User-Agent
2727
* can be specified by the caller.
28-
* @bug 8203771
28+
* @bug 8203771 8218546
2929
* @modules java.base/sun.net.www.http
3030
* java.net.http/jdk.internal.net.http.common
3131
* java.net.http/jdk.internal.net.http.frame
@@ -64,8 +64,6 @@
6464
import java.net.http.HttpRequest;
6565
import java.net.http.HttpResponse;
6666
import java.net.http.HttpResponse.BodyHandlers;
67-
import java.security.AccessController;
68-
import java.security.PrivilegedAction;
6967
import java.time.Duration;
7068
import java.util.ArrayList;
7169
import java.util.Arrays;
@@ -74,13 +72,13 @@
7472
import java.util.Map;
7573
import java.util.Optional;
7674
import java.util.function.Function;
77-
78-
import static java.lang.System.err;
7975
import static java.lang.System.out;
8076
import static java.net.http.HttpClient.Builder.NO_PROXY;
77+
import static java.net.http.HttpClient.Version.HTTP_2;
8178
import static java.nio.charset.StandardCharsets.US_ASCII;
8279
import org.testng.Assert;
8380
import static org.testng.Assert.assertEquals;
81+
import static org.testng.Assert.assertTrue;
8482

8583
public class SpecialHeadersTest implements HttpServerAdapters {
8684

@@ -151,7 +149,11 @@ static String userAgent() {
151149
"USER-AGENT", u -> userAgent(), "HOST", u -> u.getRawAuthority());
152150

153151
@Test(dataProvider = "variants")
154-
void test(String uriString, String headerNameAndValue, boolean sameClient) throws Exception {
152+
void test(String uriString,
153+
String headerNameAndValue,
154+
boolean sameClient)
155+
throws Exception
156+
{
155157
out.println("\n--- Starting ");
156158

157159
int index = headerNameAndValue.indexOf(":");
@@ -183,21 +185,41 @@ void test(String uriString, String headerNameAndValue, boolean sameClient) throw
183185
assertEquals(resp.statusCode(), 200,
184186
"Expected 200, got:" + resp.statusCode());
185187

186-
String receivedHeaderString = value == null ? null
187-
: resp.headers().firstValue("X-"+key).get();
188-
out.println("Got X-" + key + ": " + resp.headers().allValues("X-"+key));
189-
if (value != null) {
190-
assertEquals(receivedHeaderString, value);
191-
assertEquals(resp.headers().allValues("X-"+key), List.of(value));
188+
boolean isInitialRequest = i == 0;
189+
boolean isSecure = uri.getScheme().equalsIgnoreCase("https");
190+
boolean isHTTP2 = resp.version() == HTTP_2;
191+
boolean isNotH2CUpgrade = isSecure || (sameClient == true && !isInitialRequest);
192+
boolean isDefaultHostHeader = name.equalsIgnoreCase("host") && useDefault;
193+
194+
// By default, HTTP/2 sets the `:authority:` pseudo-header, instead
195+
// of the `Host` header. Therefore, there should be no "X-Host"
196+
// header in the response, except the response to the h2c Upgrade
197+
// request which will have been sent through HTTP/1.1.
198+
199+
if (isDefaultHostHeader && isHTTP2 && isNotH2CUpgrade) {
200+
assertTrue(resp.headers().firstValue("X-" + key).isEmpty());
201+
assertTrue(resp.headers().allValues("X-" + key).isEmpty());
202+
out.println("No X-" + key + " header received, as expected");
192203
} else {
193-
assertEquals(resp.headers().allValues("X-"+key).size(), 0);
204+
String receivedHeaderString = value == null ? null
205+
: resp.headers().firstValue("X-"+key).get();
206+
out.println("Got X-" + key + ": " + resp.headers().allValues("X-"+key));
207+
if (value != null) {
208+
assertEquals(receivedHeaderString, value);
209+
assertEquals(resp.headers().allValues("X-"+key), List.of(value));
210+
} else {
211+
assertEquals(resp.headers().allValues("X-"+key).size(), 0);
212+
}
194213
}
195-
196214
}
197215
}
198216

199217
@Test(dataProvider = "variants")
200-
void testHomeMadeIllegalHeader(String uriString, String headerNameAndValue, boolean sameClient) throws Exception {
218+
void testHomeMadeIllegalHeader(String uriString,
219+
String headerNameAndValue,
220+
boolean sameClient)
221+
throws Exception
222+
{
201223
out.println("\n--- Starting ");
202224
final URI uri = URI.create(uriString);
203225

@@ -266,22 +288,39 @@ void testAsync(String uriString, String headerNameAndValue, boolean sameClient)
266288
}
267289
HttpRequest request = requestBuilder.build();
268290

291+
boolean isInitialRequest = i == 0;
292+
boolean isSecure = uri.getScheme().equalsIgnoreCase("https");
293+
boolean isNotH2CUpgrade = isSecure || (sameClient == true && !isInitialRequest);
294+
boolean isDefaultHostHeader = name.equalsIgnoreCase("host") && useDefault;
295+
269296
client.sendAsync(request, BodyHandlers.ofString())
270297
.thenApply(response -> {
271298
out.println("Got response: " + response);
272299
out.println("Got body: " + response.body());
273300
assertEquals(response.statusCode(), 200);
274301
return response;})
275302
.thenAccept(resp -> {
276-
String receivedHeaderString = value == null ? null
277-
: resp.headers().firstValue("X-"+key).get();
278-
out.println("Got X-" + key + ": " + resp.headers().allValues("X-"+key));
279-
if (value != null) {
280-
assertEquals(receivedHeaderString, value);
281-
assertEquals(resp.headers().allValues("X-" + key), List.of(value));
303+
// By default, HTTP/2 sets the `:authority:` pseudo-header, instead
304+
// of the `Host` header. Therefore, there should be no "X-Host"
305+
// header in the response, except the response to the h2c Upgrade
306+
// request which will have been sent through HTTP/1.1.
307+
308+
if (isDefaultHostHeader && resp.version() == HTTP_2 && isNotH2CUpgrade) {
309+
assertTrue(resp.headers().firstValue("X-" + key).isEmpty());
310+
assertTrue(resp.headers().allValues("X-" + key).isEmpty());
311+
out.println("No X-" + key + " header received, as expected");
282312
} else {
283-
assertEquals(resp.headers().allValues("X-" + key).size(), 1);
284-
} })
313+
String receivedHeaderString = value == null ? null
314+
: resp.headers().firstValue("X-"+key).get();
315+
out.println("Got X-" + key + ": " + resp.headers().allValues("X-"+key));
316+
if (value != null) {
317+
assertEquals(receivedHeaderString, value);
318+
assertEquals(resp.headers().allValues("X-" + key), List.of(value));
319+
} else {
320+
assertEquals(resp.headers().allValues("X-" + key).size(), 1);
321+
}
322+
}
323+
})
285324
.join();
286325
}
287326
}

0 commit comments

Comments
 (0)