Hi Oleg,

thanks for the fast answer!
I adapted the config removing the interceptors, but that doesn't change the behavior. See the config below. I also added the source of the two "creates", which are also used
for the config.

(And what wonders me is, that it works for "http" but not for "https").

best regards
Achim


------------------------------------------------------------------------------------------------
    public static CloseableHttpAsyncClient createClient(Configuration config) {         int connectionIdleSecs = config.getTimeAsInt(Proxy2Config.HTTP_CONNECTION_IDLE_TIMEOUT, TimeUnit.SECONDS);         final CloseableHttpAsyncClient client = HttpAsyncClientBuilder.create()
                .disableCookieManagement()
.setDefaultRequestConfig(createCustomRequestConfig(config))
.setConnectionManager(createPoolingConnManager(config))
                .setVersionPolicy(HttpVersionPolicy.NEGOTIATE)
                .setIOReactorConfig(
IOReactorConfig.custom().setSoTimeout(Timeout.ofSeconds(connectionIdleSecs)).build())
                .setKeepAliveStrategy(new DefaultConnectionKeepAliveStrategy() {

                    @Override
                    public TimeValue getKeepAliveDuration(HttpResponse response, HttpContext context) {                         TimeValue keepAlive = super.getKeepAliveDuration(response, context);                         if (keepAlive == null || keepAlive.getDuration() < 0) {
                            // Keep connections alive if a keep-alive value
                            // has not be explicitly set by the server
                            keepAlive = KEEP_ALIVE;
                        }
                        return keepAlive;
                    }

                }).build();
        client.start();
        return client;
    }

    /**
     * Create the http request-config.
     *
     * @param config configuration for the http client
     * @return http request-config
     * @since 3.0 (changed parameter to Configuration)
     */
    private static RequestConfig createCustomRequestConfig(Configuration config) {         long connecTimeoutMillis = config.get(Proxy2Config.HTTP_CONNECT_TIMEOUT, TimeUnit.MILLISECONDS);         return RequestConfig.custom().setConnectionRequestTimeout(Timeout.ofMilliseconds(connecTimeoutMillis * 4))
.setConnectTimeout(Timeout.ofMilliseconds(connecTimeoutMillis)).build();
    }

    /**
     * Create pooling connection Manager.
     *
     * @param config configuration for the http client
     * @return pooling connection Manager
     * @since 3.0 (changed parameter to Configuration)
     */
    private static PoolingAsyncClientConnectionManager createPoolingConnManager(Configuration config) {         long connectionIdleSecs = config.get(Proxy2Config.HTTP_CONNECTION_IDLE_TIMEOUT, TimeUnit.MILLISECONDS);
        return PoolingAsyncClientConnectionManagerBuilder.create()
.setPoolConcurrencyPolicy(PoolConcurrencyPolicy.STRICT).setConnPoolPolicy(PoolReusePolicy.LIFO)
.setConnectionTimeToLive(TimeValue.ofSeconds(connectionIdleSecs)).setMaxConnTotal(250)
                .setMaxConnPerRoute(50).build();
    }
------------------------------------------------------------------------------------------------



Am 07.09.22 um 08:57 schrieb Oleg Kalnichevski:


On 9/7/2022 7:49 AM, Achim Kraus wrote:
Hi list,

sometime ago I updated the coap-to-http proxy of Eclipse/Californium to apache http client 5.1.
That still runs nice using java 7.

But using java 8 or java 11, a "https" request fails with

"ProtocolException: Header 'Connection: keep-alive' is illegal for HTTP/2 messages "

(see the log below). "http" requests are working.

What wonders me, if the request is HTTP/1.1, why is the response HTTP/2.0? If I switch the HttpVersionPolicy.NEGOTIATE to FORCE_HTTP_1 it works again also for "https".

I updated to 5.1.3, but that doesn't change it.

I use the code in https://github.com/eclipse-californium/californium/blob/main/californium-proxy2/src/main/java/org/eclipse/californium/proxy2/http/HttpClientFactory.java#L96-L122 to setup the client.

-------------------------------------
HttpAsyncClientBuilder.create().disableCookieManagement()
     .setDefaultRequestConfig(createCustomRequestConfig(config))
     .setConnectionManager(createPoolingConnManager(config)).setVersionPolicy(HttpVersionPolicy.NEGOTIATE)
     .setIOReactorConfig(
IOReactorConfig.custom().setSoTimeout(Timeout.ofSeconds(connectionIdleSecs)).build())      .addRequestInterceptorFirst(new RequestConnControl()).addRequestInterceptorFirst(new RequestDate())
     .addRequestInterceptorFirst(new RequestExpectContinue())
     .addRequestInterceptorFirst(new RequestTargetHost()).addRequestInterceptorFirst(new RequestUserAgent())
     .setKeepAliveStrategy(new DefaultConnectionKeepAliveStrategy() {

         @Override
         public TimeValue getKeepAliveDuration(HttpResponse response, HttpContext context) {              TimeValue keepAlive = super.getKeepAliveDuration(response, context);
             if (keepAlive == null || keepAlive.getDuration() < 0) {
                 // Keep connections alive if a keep-alive value
                 // has not be explicitly set by the server
                 keepAlive = KEEP_ALIVE;
             }
             return keepAlive;
         }

     }).build();
-------------------------------------

Removing the getKeepAliveDuration doesn't help.

I spend also a couple of hours to search the web, but in the flood of information I was not able to solve this issue.


Hi Achim

You are breaking the H2 protocol processing by adding HTTP/1.1 specific interceptors to the inteceptor chain.

Please remove RequestConnControl, RequestExpectContinue, RequestTargetHost and RequestUserAgent interceptors from the initialization code and the problem should go away. Those interceptors are introduced to the protocol processing chain automatically.

Oleg


---------------------------------------------------------------------
To unsubscribe, e-mail: httpclient-users-unsubscr...@hc.apache.org
For additional commands, e-mail: httpclient-users-h...@hc.apache.org

Reply via email to