Friday, 17 May 2024

Http Client 5: Set the response time out for http client

 

In Apache HttpClient 5, the response timeout is the maximum time the client can wait to get a response from the server after making a connection. This timeout covers the whole response, including both the headers and the actual data.

 

Key points to remember:

a.   The response timeout includes waiting for both the headers and the data.

b.   If the response timeout happens, you'll see an error message like below

"java.net.SocketTimeoutException: Read timed out." Sample error looks like below.
java.net.SocketTimeoutException: Read timed out
    at java.net.SocketInputStream.socketRead0(Native Method)
    at java.net.SocketInputStream.socketRead(SocketInputStream.java:116)
    at java.net.SocketInputStream.read(SocketInputStream.java:171)
    at java.net.SocketInputStream.read(SocketInputStream.java:141)
    at org.apache.hc.core5.http.impl.io.SessionInputBufferImpl.fillBuffer(SessionInputBufferImpl.java:149)
    at org.apache.hc.core5.http.impl.io.SessionInputBufferImpl.readLine(SessionInputBufferImpl.java:280)
    at org.apache.hc.core5.http.impl.io.AbstractMessageParser.parse(AbstractMessageParser.java:247)
    at org.apache.hc.core5.http.impl.io.AbstractMessageParser.parse(AbstractMessageParser.java:54)
    at org.apache.hc.core5.http.impl.io.DefaultBHttpClientConnection.receiveResponseHeader(DefaultBHttpClientConnection.java:299)
    at org.apache.hc.core5.http.impl.io.HttpRequestExecutor.execute(HttpRequestExecutor.java:175)
    at org.apache.hc.core5.http.impl.io.HttpRequestExecutor.execute(HttpRequestExecutor.java:218)
    at org.apache.hc.client5.http.impl.io.PoolingHttpClientConnectionManager$InternalConnectionEndpoint.execute(PoolingHttpClientConnectionManager.java:717)
    at org.apache.hc.client5.http.impl.classic.InternalExecRuntime.execute(InternalExecRuntime.java:216)
    at org.apache.hc.client5.http.impl.classic.MainClientExec.execute(MainClientExec.java:116)
    at org.apache.hc.client5.http.impl.classic.ExecChainElement.execute(ExecChainElement.java:51)
    at org.apache.hc.client5.http.impl.classic.ConnectExec.execute(ConnectExec.java:188)
    at org.apache.hc.client5.http.impl.classic.ExecChainElement.execute(ExecChainElement.java:51)
    at org.apache.hc.client5.http.impl.classic.ProtocolExec.execute(ProtocolExec.java:192)
    at org.apache.hc.client5.http.impl.classic.ExecChainElement.execute(ExecChainElement.java:51)
    at org.apache.hc.client5.http.impl.classic.HttpRequestRetryExec.execute(HttpRequestRetryExec.java:113)
    at org.apache.hc.client5.http.impl.classic.ExecChainElement.execute(ExecChainElement.java:51)
    at org.apache.hc.client5.http.impl.classic.ContentCompressionExec.execute(ContentCompressionExec.java:152)
    at org.apache.hc.client5.http.impl.classic.ExecChainElement.execute(ExecChainElement.java:51)
    at org.apache.hc.client5.http.impl.classic.RedirectExec.execute(RedirectExec.java:116)
    at org.apache.hc.client5.http.impl.classic.ExecChainElement.execute(ExecChainElement.java:51)
    at org.apache.hc.client5.http.impl.classic.InternalHttpClient.doExecute(InternalHttpClient.java:170)
    at org.apache.hc.client5.http.impl.classic.CloseableHttpClient.execute(CloseableHttpClient.java:245)
    at org.apache.hc.client5.http.impl.classic.CloseableHttpClient.execute(CloseableHttpClient.java:188)
    at org.apache.hc.client5.http.impl.classic.CloseableHttpClient.execute(CloseableHttpClient.java:162)
    at com.sample.app.CustomizedHttpClient.main(CustomizedHttpClient.java:59)

 

c.    It's important to pick the right timeout values based on how quickly your server usually responds and how fast your network is. If the timeout is too short, your client might give up too soon, but if it's too long, your application could hang.

 

 

How to set the response timeout?

Step 1: Get the RequestConfig object.

RequestConfig.Builder builder = RequestConfig.custom();
builder.setResponseTimeout(5, TimeUnit.SECONDS);
RequestConfig requestConfig = builder.build();

Step 2: Set the requestConfig while creating Http Client.

CloseableHttpClient httpClient = HttpClients.custom().setDefaultRequestConfig(requestConfig).build();

Find the below working application.

 

ResponseTimeoutDemo.java

package com.sample.app;

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.nio.charset.Charset;
import java.nio.charset.StandardCharsets;
import java.util.concurrent.TimeUnit;
import java.util.stream.Collectors;

import org.apache.hc.client5.http.classic.methods.HttpGet;
import org.apache.hc.client5.http.config.RequestConfig;
import org.apache.hc.client5.http.impl.classic.CloseableHttpClient;
import org.apache.hc.client5.http.impl.classic.HttpClients;
import org.apache.hc.core5.http.ClassicHttpRequest;
import org.apache.hc.core5.http.ClassicHttpResponse;
import org.apache.hc.core5.http.HttpEntity;
import org.apache.hc.core5.http.ParseException;
import org.apache.hc.core5.http.io.HttpClientResponseHandler;

public class ResponseTimeoutDemo {

    public static String inputStreamToString(InputStream inputStream, Charset charSet) throws IOException {

        try (BufferedReader reader = new BufferedReader(new InputStreamReader(inputStream, charSet))) {
            return reader.lines().collect(Collectors.joining("\n"));
        }

    }

    public static void main(String[] args) {

        RequestConfig.Builder builder = RequestConfig.custom();
        builder.setResponseTimeout(5, TimeUnit.SECONDS);
        RequestConfig requestConfig = builder.build();

        HttpClientResponseHandler<String> responseHandler = new HttpClientResponseHandler<String>() {
            @Override
            public String handleResponse(final ClassicHttpResponse response) throws IOException, ParseException {

                HttpEntity httpEntity = response.getEntity();

                try (InputStream is = httpEntity.getContent()) {
                    return inputStreamToString(is, StandardCharsets.UTF_8);
                }

            }
        };

        try (CloseableHttpClient httpClient = HttpClients.custom().setDefaultRequestConfig(requestConfig).build()) {

            ClassicHttpRequest request = new HttpGet("http://localhost:8080/api/v1/employees/1");

            String response = httpClient.execute(request, responseHandler);
            System.out.println(response);
        } catch (IOException e) {
            e.printStackTrace();
        }
    }

}

Output

{"id":1,"firstName":"Deepak","lastName":"Moud"}

Previous                                                    Next                                                    Home

No comments:

Post a Comment