in rt/transports/http/src/main/java/org/apache/cxf/transport/http/HttpClientHTTPConduit.java [310:458]
protected void setupConnection(Message message, Address address, HTTPClientPolicy csPolicy) throws IOException {
URI uri = address.getURI();
message.put("http.scheme", uri.getScheme());
// check tlsClientParameters from message header
TLSClientParameters clientParameters = message.get(TLSClientParameters.class);
if (clientParameters == null) {
clientParameters = tlsClientParameters;
}
if (clientParameters == null) {
clientParameters = new TLSClientParameters();
}
Object o = message.getContextualProperty(FORCE_URLCONNECTION_HTTP_CONDUIT);
if (o == null) {
o = message.get("USING_URLCONNECTION");
}
//o = true;
if ("https".equals(uri.getScheme()) && clientParameters != null) {
if (clientParameters.getSSLSocketFactory() != null) {
//if they configured in an SSLSocketFactory, we cannot do anything
//with it as the NIO based transport cannot use socket created from
//the SSLSocketFactory.
o = Boolean.TRUE;
}
if (clientParameters.isDisableCNCheck()) {
if (clientParameters.getSslContext() != null) {
// If they specify their own SSLContext, we cannot handle the
// HostnameVerifier so we'll need to use the URLConnection
o = Boolean.TRUE;
}
if (clientParameters.getTrustManagers() != null
&& JavaUtils.getJavaMajorVersion() < 14) {
// trustmanagers hacks don't work on Java11
o = Boolean.TRUE;
}
}
}
if (Boolean.TRUE.equals(o)) {
message.put("USING_URLCONNECTION", Boolean.TRUE);
super.setupConnection(message, address, csPolicy);
return;
}
if (sslURL != null && isSslTargetDifferent(sslURL, uri)) {
sslURL = null;
if (clientRef != null) {
clientRef.release();
clientRef = null;
}
}
// If the HTTP_REQUEST_METHOD is not set, the default is "POST".
String httpRequestMethod =
(String)message.get(Message.HTTP_REQUEST_METHOD);
if (httpRequestMethod == null) {
httpRequestMethod = "POST";
message.put(Message.HTTP_REQUEST_METHOD, "POST");
}
RefCount<HttpClient> cl = clientRef;
if (cl == null) {
int ctimeout = determineConnectionTimeout(message, csPolicy);
ProxySelector ps = new ProxyFactoryProxySelector(proxyFactory, csPolicy);
HttpClient.Builder cb = HttpClient.newBuilder()
.proxy(ps)
.followRedirects(Redirect.NEVER);
if (ctimeout > 0) {
cb.connectTimeout(Duration.ofMillis(ctimeout));
}
if ("https".equals(uri.getScheme())) {
sslURL = uri;
try {
SSLContext sslContext = clientParameters.getSslContext();
if (sslContext == null) {
sslContext = SSLUtils.getSSLContext(clientParameters, true);
cb.sslContext(sslContext);
}
if (sslContext != null) {
cb.sslContext(sslContext);
String[] supportedCiphers = org.apache.cxf.configuration.jsse.SSLUtils
.getSupportedCipherSuites(sslContext);
String[] cipherSuites = org.apache.cxf.configuration.jsse.SSLUtils
.getCiphersuitesToInclude(clientParameters.getCipherSuites(),
clientParameters.getCipherSuitesFilter(),
sslContext.getSocketFactory().getDefaultCipherSuites(),
supportedCiphers,
LOG);
if (clientParameters.getSecureSocketProtocol() != null) {
String protocol = clientParameters.getSecureSocketProtocol();
SSLParameters params = new SSLParameters(cipherSuites, new String[] {protocol});
cb.sslParameters(params);
} else {
final SSLParameters params = new SSLParameters(cipherSuites,
TLSClientParameters.getPreferredClientProtocols());
cb.sslParameters(params);
}
}
} catch (GeneralSecurityException e) {
throw new IOException(e);
}
}
String verc = (String)message.getContextualProperty(FORCE_HTTP_VERSION);
if (verc == null) {
verc = csPolicy.getVersion();
}
if ("1.1".equals(HTTP_VERSION) || "1.1".equals(verc)) {
cb.version(Version.HTTP_1_1);
}
// make sure the conduit is not yet initialized
initializationLock.lock();
try {
cl = clientRef;
if (cl == null) {
final boolean shareHttpClient = MessageUtils.getContextualBoolean(message,
SHARE_HTTPCLIENT_CONDUIT, true);
cl = CLIENTS_CACHE.computeIfAbsent(shareHttpClient, csPolicy, clientParameters, () -> cb.build());
if (!"https".equals(uri.getScheme())
&& !KNOWN_HTTP_VERBS_WITH_NO_CONTENT.contains(httpRequestMethod)
&& cl.client().version() == Version.HTTP_2
&& ("2".equals(verc) || ("auto".equals(verc) && "2".equals(HTTP_VERSION)))) {
try {
// We specifically want HTTP2, but we're using a request
// that won't trigger an upgrade to HTTP/2 so we'll
// call OPTIONS on the URI which may trigger HTTP/2 upgrade.
// Not needed for methods that don't have a body (GET/HEAD/etc...)
// or for https (negotiated at the TLS level)
HttpRequest.Builder rb = HttpRequest.newBuilder()
.uri(uri)
.method("OPTIONS", BodyPublishers.noBody());
cl.client().send(rb.build(), BodyHandlers.ofByteArray());
} catch (IOException | InterruptedException e) {
//
}
}
clientRef = cl;
}
} finally {
initializationLock.unlock();
}
}
message.put(HttpClient.class, cl.client());
message.put(KEY_HTTP_CONNECTION_ADDRESS, address);
}