Apache Commons AsyncClient - игнорировать сертификаты - SSLPeerUnverifiedException - PullRequest
0 голосов
/ 15 мая 2018

Хотя я отключил проверку сертификатов в своем Http-клиенте, но продолжаю получать SSLPeerUnverifiedException.

Вот мой клиент:

import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.nio.charset.Charset;
import java.nio.charset.StandardCharsets;
import java.security.GeneralSecurityException;
import java.util.Arrays;
import java.util.concurrent.CompletableFuture;
import java.util.function.Consumer;
import java.util.stream.Stream;

import org.apache.commons.codec.binary.Base64;
import org.apache.commons.lang3.StringUtils;
import org.apache.commons.lang3.Validate;
import org.apache.http.Header;
import org.apache.http.HttpEntity;
import org.apache.http.HttpEntityEnclosingRequest;
import org.apache.http.HttpHeaders;
import org.apache.http.HttpResponse;
import org.apache.http.NameValuePair;
import org.apache.http.client.config.RequestConfig;
import org.apache.http.client.methods.HttpUriRequest;
import org.apache.http.client.methods.RequestBuilder;
import org.apache.http.concurrent.FutureCallback;
import org.apache.http.conn.ssl.NoopHostnameVerifier;
import org.apache.http.conn.ssl.TrustSelfSignedStrategy;
import org.apache.http.entity.BufferedHttpEntity;
import org.apache.http.impl.nio.client.CloseableHttpAsyncClient;
import org.apache.http.impl.nio.client.HttpAsyncClients;
import org.apache.http.impl.nio.conn.PoolingNHttpClientConnectionManager;
import org.apache.http.impl.nio.reactor.DefaultConnectingIOReactor;
import org.apache.http.message.BasicHeader;
import org.apache.http.nio.reactor.ConnectingIOReactor;
import org.apache.http.nio.reactor.IOReactorException;
import org.apache.http.ssl.SSLContextBuilder;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

class ApacheCommonsAsyncClient implements IMakeHttpRequests {
    private static final Logger LOGGER = LoggerFactory.getLogger(PaxHttpClient.class);
    private static final int MAX_POOL_SIZE = 100;
    private static final int MAX_CONN_PER_ROUTE = 10;

    private final CloseableHttpAsyncClient httpClient;

    ApacheCommonsAsyncClient() {
        final RequestConfig requestConfig = RequestConfig.custom().setConnectTimeout(5000)
                .setConnectionRequestTimeout(5000).setSocketTimeout(0).build();
        final Header doNotKeepAlive = new BasicHeader("Connection: keep-alive", "false");
        final Header closeConnection = new BasicHeader("Connection", "close");

        try {
            final SSLContextBuilder sslContextBuilder = new SSLContextBuilder().loadTrustMaterial(null,
                    new TrustSelfSignedStrategy());
            final ConnectingIOReactor ioReactor = new DefaultConnectingIOReactor();
            final PoolingNHttpClientConnectionManager cm = new PoolingNHttpClientConnectionManager(ioReactor);

            // @formatter:off
            this.httpClient = HttpAsyncClients.custom()
                    .setDefaultRequestConfig(requestConfig)
                    .setKeepAliveStrategy((httpResponse, httpContext) -> 0)
                    .setDefaultHeaders(Arrays.asList(doNotKeepAlive, closeConnection))
                    .setConnectionManager(cm)
                    .setSSLContext(sslContextBuilder.build())
                    .setSSLHostnameVerifier(NoopHostnameVerifier.INSTANCE)
                    .setMaxConnTotal(MAX_POOL_SIZE)
                    .setMaxConnPerRoute(MAX_CONN_PER_ROUTE)
                    .build();
            // @formatter:on

            this.httpClient.start();
        } catch (final GeneralSecurityException | IOReactorException e) {
            throw new RuntimeException(e);
        }
    }
}

Исключение:

java.util.concurrent.ExecutionException: javax.net.ssl.SSLPeerUnverifiedException: Host name '<public-dns>' does not match the certificate subject provided by the peer (CN=*.<domain>.com, O="<org>", L=<location>, ST=<state>, C=<country>)
    at java.util.concurrent.CompletableFuture.reportGet(CompletableFuture.java:357)
    at java.util.concurrent.CompletableFuture.get(CompletableFuture.java:1895)
    at com.paxata.performance.App.run(App.java:30)
    at com.paxata.performance.Bootstrap.main(Bootstrap.java:43)
Caused by: javax.net.ssl.SSLPeerUnverifiedException: Host name '<public-dns>' does not match the certificate subject provided by the peer (CN=*.<domain>.com, O="<org>", L=<location>, ST=<state>, C=<country>)
    at org.apache.http.nio.conn.ssl.SSLIOSessionStrategy.verifySession(SSLIOSessionStrategy.java:208)
    at org.apache.http.nio.conn.ssl.SSLIOSessionStrategy$1.verify(SSLIOSessionStrategy.java:188)
    at org.apache.http.nio.reactor.ssl.SSLIOSession.doHandshake(SSLIOSession.java:367)
    at org.apache.http.nio.reactor.ssl.SSLIOSession.isAppInputReady(SSLIOSession.java:508)
    at org.apache.http.impl.nio.reactor.AbstractIODispatch.inputReady(AbstractIODispatch.java:120)
    at org.apache.http.impl.nio.reactor.BaseIOReactor.readable(BaseIOReactor.java:162)
    at org.apache.http.impl.nio.reactor.AbstractIOReactor.processEvent(AbstractIOReactor.java:337)
    at org.apache.http.impl.nio.reactor.AbstractIOReactor.processEvents(AbstractIOReactor.java:315)
    at org.apache.http.impl.nio.reactor.AbstractIOReactor.execute(AbstractIOReactor.java:276)
    at org.apache.http.impl.nio.reactor.BaseIOReactor.execute(BaseIOReactor.java:104)
    at org.apache.http.impl.nio.reactor.AbstractMultiworkerIOReactor$Worker.run(AbstractMultiworkerIOReactor.java:588)
    at java.lang.Thread.run(Thread.java:748)

и версии зависимостей, которые я ввожу:

    <dependency>
        <groupId>org.apache.httpcomponents</groupId>
        <artifactId>httpmime</artifactId>
        <version>4.5.5</version>
    </dependency>
    <dependency>
        <groupId>org.apache.httpcomponents</groupId>
        <artifactId>httpcore</artifactId>
        <version>4.4.9</version>
    </dependency>
    <dependency>
        <groupId>org.apache.httpcomponents</groupId>
        <artifactId>httpasyncclient</artifactId>
        <version>4.1.3</version>
    </dependency>

1 Ответ

0 голосов
/ 16 мая 2018

Экземпляр диспетчера соединений, переданный построителю, заменяет все параметры управления соединением, такие как SSL и параметры пула.

Существует два способа исправления.

  1. Позволить построителю построитьи инициализировать менеджер соединений

final SSLContextBuilder sslContextBuilder = new SSLContextBuilder().loadTrustMaterial(null,
        new TrustSelfSignedStrategy());
this.httpClient = HttpAsyncClients.custom()
        .setDefaultRequestConfig(requestConfig)
        .setKeepAliveStrategy((httpResponse, httpContext) -> 0)
        .setDefaultHeaders(Arrays.asList(doNotKeepAlive, closeConnection))
        .setSSLContext(sslContextBuilder.build())
        .setSSLHostnameVerifier(NoopHostnameVerifier.INSTANCE)
        .setMaxConnTotal(MAX_POOL_SIZE)
        .setMaxConnPerRoute(MAX_CONN_PER_ROUTE)
        .build();
Сконфигурируйте диспетчер соединений перед передачей сборщику
final SSLContextBuilder sslContextBuilder = new SSLContextBuilder().loadTrustMaterial(null,
        new TrustSelfSignedStrategy());
final PoolingNHttpClientConnectionManager cm = new PoolingNHttpClientConnectionManager(
        new DefaultConnectingIOReactor(), 
        RegistryBuilder.<SchemeIOSessionStrategy>create()
            .register("http", NoopIOSessionStrategy.INSTANCE)
            .register("https", new SSLIOSessionStrategy(sslContextBuilder.build(), NoopHostnameVerifier.INSTANCE))
            .build());
cm.setMaxTotal(MAX_POOL_SIZE);
cm.setDefaultMaxPerRoute(MAX_CONN_PER_ROUTE);

this.httpClient = HttpAsyncClients.custom()
        .setDefaultRequestConfig(requestConfig)
        .setKeepAliveStrategy((httpResponse, httpContext) -> 0)
        .setDefaultHeaders(Arrays.asList(doNotKeepAlive, closeConnection))
        .setConnectionManager(cm)
        .build();

Первый рекомендуется, если только для этого нет очень веских причин.

PS: Вы не хотите отключить постоянство соединения

...