diff --git a/cloudplatform/connectivity-destination-service/pom.xml b/cloudplatform/connectivity-destination-service/pom.xml index c456286ba..f54859b34 100644 --- a/cloudplatform/connectivity-destination-service/pom.xml +++ b/cloudplatform/connectivity-destination-service/pom.xml @@ -41,10 +41,10 @@ com.sap.cloud.sdk.cloudplatform cloudplatform-connectivity - - com.sap.cloud.sdk.cloudplatform - connectivity-apache-httpclient4 - + + com.sap.cloud.sdk.cloudplatform + connectivity-apache-httpclient5 + com.sap.cloud.sdk.cloudplatform @@ -97,26 +97,14 @@ commons-io commons-io - - org.apache.httpcomponents - httpcore - - - commons-logging - commons-logging - - - - - org.apache.httpcomponents - httpclient - - - commons-logging - commons-logging - - - + + org.apache.httpcomponents.core5 + httpcore5 + + + org.apache.httpcomponents.client5 + httpclient5 + io.vavr vavr diff --git a/cloudplatform/connectivity-destination-service/src/main/java/com/sap/cloud/sdk/cloudplatform/connectivity/AuthTokenHeaderProvider.java b/cloudplatform/connectivity-destination-service/src/main/java/com/sap/cloud/sdk/cloudplatform/connectivity/AuthTokenHeaderProvider.java index 504b35d83..4b1fc00ba 100644 --- a/cloudplatform/connectivity-destination-service/src/main/java/com/sap/cloud/sdk/cloudplatform/connectivity/AuthTokenHeaderProvider.java +++ b/cloudplatform/connectivity-destination-service/src/main/java/com/sap/cloud/sdk/cloudplatform/connectivity/AuthTokenHeaderProvider.java @@ -11,7 +11,7 @@ import javax.annotation.Nonnull; -import org.apache.http.HttpHeaders; +import org.apache.hc.core5.http.HttpHeaders; import com.google.common.base.Strings; import com.sap.cloud.sdk.cloudplatform.connectivity.exception.DestinationAccessException; @@ -96,13 +96,9 @@ private static List
getDestinationHeaders( @Nonnull final List false; + default -> true; + }; } } diff --git a/cloudplatform/connectivity-destination-service/src/main/java/com/sap/cloud/sdk/cloudplatform/connectivity/DestinationServiceAdapter.java b/cloudplatform/connectivity-destination-service/src/main/java/com/sap/cloud/sdk/cloudplatform/connectivity/DestinationServiceAdapter.java index 51b964383..80c414074 100644 --- a/cloudplatform/connectivity-destination-service/src/main/java/com/sap/cloud/sdk/cloudplatform/connectivity/DestinationServiceAdapter.java +++ b/cloudplatform/connectivity-destination-service/src/main/java/com/sap/cloud/sdk/cloudplatform/connectivity/DestinationServiceAdapter.java @@ -13,11 +13,11 @@ import javax.annotation.Nonnull; import javax.annotation.Nullable; -import org.apache.http.HttpResponse; -import org.apache.http.HttpStatus; -import org.apache.http.StatusLine; -import org.apache.http.client.methods.HttpGet; -import org.apache.http.client.methods.HttpUriRequest; +import org.apache.hc.client5.http.classic.methods.HttpGet; +import org.apache.hc.client5.http.impl.classic.BasicHttpClientResponseHandler; +import org.apache.hc.core5.http.ClassicHttpRequest; +import org.apache.hc.core5.http.ClassicHttpResponse; +import org.apache.hc.core5.http.HttpStatus; import com.google.common.base.Strings; import com.sap.cloud.environment.servicebinding.api.DefaultServiceBindingAccessor; @@ -32,6 +32,7 @@ import io.vavr.control.Try; import lombok.AccessLevel; import lombok.Getter; +import lombok.RequiredArgsConstructor; import lombok.extern.slf4j.Slf4j; @Slf4j @@ -126,53 +127,62 @@ String getConfigurationAsJson( serviceDestinationLoader.apply(strategy.behalf()), () -> "Destination for Destination Service on behalf of " + strategy.behalf() + " not found."); - final HttpUriRequest request = prepareRequest(servicePath, strategy); + final ClassicHttpRequest request = prepareRequest(servicePath, strategy); - final HttpResponse response; try { - response = HttpClientAccessor.getHttpClient(serviceDestination).execute(request); + return ApacheHttpClient5Accessor + .getHttpClient(serviceDestination) + .execute(request, new DestinationHttpClientResponseHandler(request)); } catch( final IOException e ) { throw new DestinationAccessException(e); } - return handleResponse(request, response); } - @Nonnull - private static String handleResponse( final HttpUriRequest request, final HttpResponse response ) + @RequiredArgsConstructor( access = AccessLevel.PRIVATE ) + static class DestinationHttpClientResponseHandler extends BasicHttpClientResponseHandler { - final StatusLine status = response.getStatusLine(); - final int statusCode = status.getStatusCode(); - final String reasonPhrase = status.getReasonPhrase(); + final ClassicHttpRequest request; - log.debug("Destination service returned HTTP status {} ({})", statusCode, reasonPhrase); + @Override + public String handleResponse( final ClassicHttpResponse response ) + { + final int statusCode = response.getCode(); + final String reasonPhrase = response.getReasonPhrase(); - Try maybeBody = Try.of(() -> HttpEntityUtil.getResponseBody(response)); - if( maybeBody.isFailure() ) { - final var ex = - new DestinationAccessException("Failed to read body from HTTP response", maybeBody.getCause()); - maybeBody = Try.failure(ex); - } + log.debug("Destination service returned HTTP status {} ({})", statusCode, reasonPhrase); - if( statusCode == HttpStatus.SC_OK ) { - final var ex = new DestinationAccessException("Failed to get destinations: no body returned in response."); - maybeBody = maybeBody.filter(it -> !Strings.isNullOrEmpty(it), () -> ex); - return maybeBody.get(); - } + Try maybeBody = Try.of(() -> handleEntity(response.getEntity())); + if( maybeBody.isFailure() ) { + final var ex = + new DestinationAccessException("Failed to read body from HTTP response", maybeBody.getCause()); + maybeBody = Try.failure(ex); + } - final String requestUri = request.getURI().getPath(); - if( statusCode == HttpStatus.SC_NOT_FOUND ) { - throw new DestinationNotFoundException(null, "Destination could not be found for path " + requestUri + "."); + if( statusCode == HttpStatus.SC_OK ) { + final var ex = + new DestinationAccessException("Failed to get destinations: no body returned in response."); + maybeBody = maybeBody.filter(it -> !Strings.isNullOrEmpty(it), () -> ex); + return maybeBody.get(); + } + + final String requestUri = request.getRequestUri(); + if( statusCode == HttpStatus.SC_NOT_FOUND ) { + throw new DestinationNotFoundException( + null, + "Destination could not be found for path " + requestUri + "."); + } + final String message = + "Failed to get destinations: destination service responded with HTTP status %s (%S) at '%s'." + .formatted(statusCode, reasonPhrase, requestUri); + final String messageWithBody = + message + " Body: %s".formatted(maybeBody.getOrElseGet(Throwable::getMessage)); + log.error(messageWithBody); + throw new DestinationAccessException(message); } - final String message = - "Failed to get destinations: destination service responded with HTTP status %s (%S) at '%s'." - .formatted(statusCode, reasonPhrase, requestUri); - final String messageWithBody = message + " Body: %s".formatted(maybeBody.getOrElseGet(Throwable::getMessage)); - log.error(messageWithBody); - throw new DestinationAccessException(message); } - private HttpUriRequest prepareRequest( final String servicePath, final DestinationRetrievalStrategy strategy ) + private ClassicHttpRequest prepareRequest( final String servicePath, final DestinationRetrievalStrategy strategy ) { final URI requestUri; try { @@ -183,7 +193,7 @@ private HttpUriRequest prepareRequest( final String servicePath, final Destinati } log.debug("Querying Destination Service via URI {}.", requestUri); - final HttpUriRequest request = new HttpGet(requestUri); + final ClassicHttpRequest request = new HttpGet(requestUri); if( !servicePath.startsWith(DestinationService.PATH_DEFAULT) && !servicePath.startsWith(DestinationService.PATH_V2) ) { diff --git a/cloudplatform/connectivity-destination-service/src/test/java/com/sap/cloud/sdk/cloudplatform/connectivity/AuthTokenHeaderProviderTest.java b/cloudplatform/connectivity-destination-service/src/test/java/com/sap/cloud/sdk/cloudplatform/connectivity/AuthTokenHeaderProviderTest.java index 7251358fe..9022aab16 100644 --- a/cloudplatform/connectivity-destination-service/src/test/java/com/sap/cloud/sdk/cloudplatform/connectivity/AuthTokenHeaderProviderTest.java +++ b/cloudplatform/connectivity-destination-service/src/test/java/com/sap/cloud/sdk/cloudplatform/connectivity/AuthTokenHeaderProviderTest.java @@ -8,7 +8,7 @@ import java.util.Arrays; import java.util.Collection; -import org.apache.http.HttpHeaders; +import org.apache.hc.core5.http.HttpHeaders; import org.junit.jupiter.api.AfterEach; import org.junit.jupiter.api.BeforeEach; import org.junit.jupiter.api.DisplayName; diff --git a/cloudplatform/connectivity-destination-service/src/test/java/com/sap/cloud/sdk/cloudplatform/connectivity/DestinationServiceAdapterTest.java b/cloudplatform/connectivity-destination-service/src/test/java/com/sap/cloud/sdk/cloudplatform/connectivity/DestinationServiceAdapterTest.java index 477659db6..4d9fbf9e4 100644 --- a/cloudplatform/connectivity-destination-service/src/test/java/com/sap/cloud/sdk/cloudplatform/connectivity/DestinationServiceAdapterTest.java +++ b/cloudplatform/connectivity-destination-service/src/test/java/com/sap/cloud/sdk/cloudplatform/connectivity/DestinationServiceAdapterTest.java @@ -22,7 +22,7 @@ import static org.assertj.core.api.Assertions.assertThatThrownBy; import static org.mockito.ArgumentMatchers.any; import static org.mockito.Mockito.atLeastOnce; -import static org.mockito.Mockito.doReturn; +import static org.mockito.Mockito.doAnswer; import static org.mockito.Mockito.mock; import static org.mockito.Mockito.spy; import static org.mockito.Mockito.times; @@ -40,10 +40,13 @@ import javax.annotation.Nonnull; import javax.annotation.Nullable; -import org.apache.http.HttpVersion; -import org.apache.http.client.HttpClient; -import org.apache.http.entity.InputStreamEntity; -import org.apache.http.message.BasicHttpResponse; +import org.apache.hc.client5.http.classic.HttpClient; +import org.apache.hc.core5.http.ClassicHttpRequest; +import org.apache.hc.core5.http.ContentType; +import org.apache.hc.core5.http.HttpStatus; +import org.apache.hc.core5.http.io.HttpClientResponseHandler; +import org.apache.hc.core5.http.io.entity.InputStreamEntity; +import org.apache.hc.core5.http.message.BasicClassicHttpResponse; import org.junit.jupiter.api.AfterEach; import org.junit.jupiter.api.BeforeAll; import org.junit.jupiter.api.BeforeEach; @@ -52,6 +55,7 @@ import org.mockito.Mockito; import com.auth0.jwt.JWT; +import com.github.tomakehurst.wiremock.junit5.WireMockExtension; import com.github.tomakehurst.wiremock.junit5.WireMockRuntimeInfo; import com.github.tomakehurst.wiremock.junit5.WireMockTest; import com.sap.cloud.environment.servicebinding.api.DefaultServiceBinding; @@ -59,6 +63,7 @@ import com.sap.cloud.environment.servicebinding.api.ServiceBinding; import com.sap.cloud.environment.servicebinding.api.ServiceBindingAccessor; import com.sap.cloud.environment.servicebinding.api.ServiceIdentifier; +import com.sap.cloud.sdk.cloudplatform.connectivity.DestinationServiceAdapter.DestinationHttpClientResponseHandler; import com.sap.cloud.sdk.cloudplatform.connectivity.exception.DestinationAccessException; import com.sap.cloud.sdk.cloudplatform.connectivity.exception.DestinationNotFoundException; import com.sap.cloud.sdk.cloudplatform.exception.MultipleServiceBindingsException; @@ -93,6 +98,9 @@ class DestinationServiceAdapterTest private String xsuaaToken; + @RegisterExtension + static final WireMockExtension server = WireMockExtension.newInstance().build(); + @BeforeAll static void setupSession() { @@ -434,20 +442,33 @@ void getDestinationServiceProviderTenantShouldThrowForMissingId() @Test void testErrorHandling() { - final var httpClient = mock(HttpClient.class); - final var destination = DefaultHttpDestination.builder("http://foo").build(); - HttpClientAccessor.setHttpClientFactory(( dest ) -> dest == destination ? httpClient : null); + final HttpClient httpClient = mock(HttpClient.class); + final HttpDestination destination = DefaultHttpDestination.builder("http://foo").build(); + ApacheHttpClient5Accessor.setHttpClientFactory(dest -> httpClient); final var destinations = Collections.singletonMap(OnBehalfOf.TECHNICAL_USER_PROVIDER, destination); final var SUT = new DestinationServiceAdapter(destinations::get, () -> null, null); - // setup 400 response - var stream400 = spy(new ByteArrayInputStream("bad, evil request".getBytes(StandardCharsets.UTF_8))); - var response400 = new BasicHttpResponse(HttpVersion.HTTP_1_1, 400, "Bad Request"); - response400.setEntity(new InputStreamEntity(stream400)); - doReturn(response400).when(httpClient).execute(any()); - - // test + // prepare 400 response with a spied input stream so we can verify it is closed + final var stream400 = spy(new ByteArrayInputStream("bad, evil request".getBytes(StandardCharsets.UTF_8))); + final var response400 = new BasicClassicHttpResponse(HttpStatus.SC_BAD_REQUEST, "Bad Request"); + response400.setEntity(new InputStreamEntity(stream400, -1, ContentType.TEXT_PLAIN)); + + // prepare 404 response with a spied input stream + final var stream404 = spy(new ByteArrayInputStream("Nothing here.".getBytes(StandardCharsets.UTF_8))); + final var response404 = new BasicClassicHttpResponse(HttpStatus.SC_NOT_FOUND, "Not Found"); + response404.setEntity(new InputStreamEntity(stream404, -1, ContentType.TEXT_PLAIN)); + + // make the mocked httpClient call the provided response handler with our prepared responses + doAnswer(invocation -> { + final HttpClientResponseHandler handler = invocation.getArgument(1); + return handler.handleResponse(response400); + }).doAnswer(invocation -> { + final HttpClientResponseHandler handler = invocation.getArgument(1); + return handler.handleResponse(response404); + }).when(httpClient).execute(any(ClassicHttpRequest.class), any(DestinationHttpClientResponseHandler.class)); + + // first invocation -> 400 -> DestinationAccessException assertThatThrownBy( () -> SUT.getConfigurationAsJson("/service-path", withoutToken(OnBehalfOf.TECHNICAL_USER_PROVIDER))) .isInstanceOf(DestinationAccessException.class) @@ -456,13 +477,7 @@ void testErrorHandling() // verify closed stream Mockito.verify(stream400, atLeastOnce()).close(); - // setup 404 response - var stream404 = spy(new ByteArrayInputStream("Nothing here.".getBytes(StandardCharsets.UTF_8))); - var response404 = new BasicHttpResponse(HttpVersion.HTTP_1_1, 404, "Not Found"); - response404.setEntity(new InputStreamEntity(stream404)); - doReturn(response404).when(httpClient).execute(any()); - - // test + // second invocation -> 404 -> DestinationNotFoundException assertThatThrownBy( () -> SUT.getConfigurationAsJson("/service-path", withoutToken(OnBehalfOf.TECHNICAL_USER_PROVIDER))) .describedAs("A 404 should produce a DestinationNotFoundException") @@ -472,7 +487,7 @@ void testErrorHandling() // verify closed stream Mockito.verify(stream404, atLeastOnce()).close(); - HttpClientAccessor.setHttpClientFactory(null); + ApacheHttpClient5Accessor.setHttpClientFactory(null); } private static DestinationServiceAdapter createSut( @Nonnull final ServiceBinding... serviceBindings ) diff --git a/cloudplatform/connectivity-destination-service/src/test/java/com/sap/cloud/sdk/cloudplatform/connectivity/DestinationServiceAuthenticationTest.java b/cloudplatform/connectivity-destination-service/src/test/java/com/sap/cloud/sdk/cloudplatform/connectivity/DestinationServiceAuthenticationTest.java index 914e6fce1..9038024a3 100644 --- a/cloudplatform/connectivity-destination-service/src/test/java/com/sap/cloud/sdk/cloudplatform/connectivity/DestinationServiceAuthenticationTest.java +++ b/cloudplatform/connectivity-destination-service/src/test/java/com/sap/cloud/sdk/cloudplatform/connectivity/DestinationServiceAuthenticationTest.java @@ -22,7 +22,7 @@ import javax.annotation.Nonnull; import javax.annotation.Nullable; -import org.apache.http.HttpHeaders; +import org.apache.hc.core5.http.HttpHeaders; import org.junit.jupiter.api.BeforeEach; import org.junit.jupiter.api.Test; import org.junit.jupiter.api.extension.RegisterExtension; diff --git a/cloudplatform/connectivity-destination-service/src/test/java/com/sap/cloud/sdk/cloudplatform/connectivity/DestinationServiceTest.java b/cloudplatform/connectivity-destination-service/src/test/java/com/sap/cloud/sdk/cloudplatform/connectivity/DestinationServiceTest.java index a23533da1..ded53f767 100644 --- a/cloudplatform/connectivity-destination-service/src/test/java/com/sap/cloud/sdk/cloudplatform/connectivity/DestinationServiceTest.java +++ b/cloudplatform/connectivity-destination-service/src/test/java/com/sap/cloud/sdk/cloudplatform/connectivity/DestinationServiceTest.java @@ -27,9 +27,7 @@ import static org.mockito.Mockito.times; import static org.mockito.Mockito.verify; import static org.mockito.Mockito.verifyNoMoreInteractions; -import static org.mockito.Mockito.when; -import java.io.IOException; import java.net.URI; import java.time.Duration; import java.time.Instant; @@ -50,9 +48,11 @@ import java.util.concurrent.locks.ReentrantLock; import java.util.function.Function; -import org.apache.http.HttpVersion; -import org.apache.http.client.HttpClient; -import org.apache.http.message.BasicHttpResponse; +import org.apache.hc.client5.http.classic.HttpClient; +import org.apache.hc.core5.http.ClassicHttpRequest; +import org.apache.hc.core5.http.HttpStatus; +import org.apache.hc.core5.http.io.HttpClientResponseHandler; +import org.apache.hc.core5.http.message.BasicClassicHttpResponse; import org.assertj.core.api.Condition; import org.assertj.core.api.SoftAssertions; import org.junit.jupiter.api.AfterEach; @@ -68,6 +68,7 @@ import com.google.gson.stream.MalformedJsonException; import com.sap.cloud.environment.servicebinding.api.ServiceBinding; import com.sap.cloud.sdk.cloudplatform.cache.CacheKey; +import com.sap.cloud.sdk.cloudplatform.connectivity.DestinationServiceAdapter.DestinationHttpClientResponseHandler; import com.sap.cloud.sdk.cloudplatform.connectivity.exception.DestinationAccessException; import com.sap.cloud.sdk.cloudplatform.connectivity.exception.DestinationNotFoundException; import com.sap.cloud.sdk.cloudplatform.resilience.ResilienceConfiguration; @@ -497,21 +498,20 @@ void testGettingDestinationPropertiesSubscriber() .containsExactly("CC8-HTTP-BASIC", "CC8-HTTP-CERT1", "CC8-HTTP-CERT"); } + @SneakyThrows @Test // slow test, run manually if needed void destinationServiceTimeOutWhileGettingDestination() - throws IOException { final HttpDestination serviceDestination = DefaultHttpDestination.builder("").build(); // prepare slow HttpClient - HttpClientFactory factory = HttpClientAccessor.getHttpClientFactory(); - HttpClient cl = mock(HttpClient.class); + final HttpClient cl = mock(HttpClient.class); doAnswer(invocation -> { Thread.sleep(TEST_TIMEOUT); return null; - }).when(cl).execute(any()); - HttpClientAccessor.setHttpClientFactory(dest -> cl); + }).when(cl).execute(any(ClassicHttpRequest.class), any(DestinationHttpClientResponseHandler.class)); + ApacheHttpClient5Accessor.setHttpClientFactory(dest -> cl); // prepare adapter final DestinationServiceAdapter adapter = @@ -540,11 +540,11 @@ void destinationServiceTimeOutWhileGettingDestination() .isExactlyInstanceOf(DestinationAccessException.class) .hasRootCauseExactlyInstanceOf(TimeoutException.class); - verify(cl, times(1)).execute(any()); + verify(cl, times(1)).execute(any(ClassicHttpRequest.class), any(DestinationHttpClientResponseHandler.class)); verify(adapter, times(1)).getConfigurationAsJson(eq("/v1/destinations/SomeDestinationName"), any()); // reset - HttpClientAccessor.setHttpClientFactory(null); + ApacheHttpClient5Accessor.setHttpClientFactory(null); } @Test @@ -892,21 +892,25 @@ void testCachingHttpDestination() assertThat(DestinationService.Cache.instanceSingle().estimatedSize()).isEqualTo(1); } + @SneakyThrows @Test void testUnknownDestinationLeadsToDestinationNotFoundException() - throws IOException { // prepare 404 HttpClient - final HttpClientFactory factory = HttpClientAccessor.getHttpClientFactory(); final HttpClient client404 = mock(HttpClient.class); - when(client404.execute(any())).thenReturn(new BasicHttpResponse(HttpVersion.HTTP_1_1, 404, "Not found")); - HttpClientAccessor.setHttpClientFactory(dest -> client404); + ApacheHttpClient5Accessor.setHttpClientFactory(dest -> client404); + + final var response404 = new BasicClassicHttpResponse(HttpStatus.SC_NOT_FOUND, "Not Found"); + doAnswer(invocation -> { + final HttpClientResponseHandler handler = invocation.getArgument(1); + return handler.handleResponse(response404); + }).when(client404).execute(any(ClassicHttpRequest.class), any(DestinationHttpClientResponseHandler.class)); assertThatThrownBy(() -> loader.tryGetDestination("UnknownDestination").get()) .isInstanceOf(DestinationNotFoundException.class); // reset - HttpClientAccessor.setHttpClientFactory(factory); + ApacheHttpClient5Accessor.setHttpClientFactory(null); } private void tryGetDestinationTwice( String destinationName, String responseDestination, int numberOfFetches ) @@ -1864,11 +1868,11 @@ public void performanceTest() assertThat(PrincipalAccessor.getCurrentPrincipal().getPrincipalId()).isEqualTo("principal-" + i); destination = loader.tryGetDestination(name, DestinationOptions.builder().build()).get().asHttp(); - httpClient = HttpClientAccessor.getHttpClient(destination); + httpClient = ApacheHttpClient5Accessor.getHttpClient(destination); System.out.println("[" + LocalDateTime.now() + "] Got " + name); } assertThat(DestinationService.Cache.instanceSingle().estimatedSize()).isEqualTo(1); - assertThat(httpClient).isSameAs(HttpClientAccessor.getHttpClient(destination)); + assertThat(httpClient).isSameAs(ApacheHttpClient5Accessor.getHttpClient(destination)); } @Test diff --git a/cloudplatform/connectivity-destination-service/src/test/java/com/sap/cloud/sdk/cloudplatform/connectivity/XsuaaSecurityTest.java b/cloudplatform/connectivity-destination-service/src/test/java/com/sap/cloud/sdk/cloudplatform/connectivity/XsuaaSecurityTest.java index ce4d2738b..b939a66dc 100644 --- a/cloudplatform/connectivity-destination-service/src/test/java/com/sap/cloud/sdk/cloudplatform/connectivity/XsuaaSecurityTest.java +++ b/cloudplatform/connectivity-destination-service/src/test/java/com/sap/cloud/sdk/cloudplatform/connectivity/XsuaaSecurityTest.java @@ -5,17 +5,15 @@ import static org.assertj.core.api.Assertions.assertThat; import java.io.IOException; -import java.nio.charset.StandardCharsets; import java.util.Collections; import javax.annotation.Nonnull; -import org.apache.commons.io.IOUtils; -import org.apache.http.HttpHeaders; -import org.apache.http.HttpStatus; -import org.apache.http.client.methods.CloseableHttpResponse; -import org.apache.http.client.methods.HttpGet; -import org.apache.http.impl.client.HttpClients; +import org.apache.hc.client5.http.classic.methods.HttpGet; +import org.apache.hc.client5.http.impl.classic.BasicHttpClientResponseHandler; +import org.apache.hc.client5.http.impl.classic.CloseableHttpClient; +import org.apache.hc.client5.http.impl.classic.HttpClients; +import org.apache.hc.core5.http.HttpHeaders; import org.junit.jupiter.api.AfterEach; import org.junit.jupiter.api.BeforeEach; import org.junit.jupiter.api.Test; @@ -98,10 +96,9 @@ void requestWithValidTokenRequest() final HttpGet request = new HttpGet(RULE.getApplicationServerUri() + "/app"); request.setHeader(HttpHeaders.AUTHORIZATION, "Bearer " + token.getTokenValue()); - try( CloseableHttpResponse response = HttpClients.createDefault().execute(request) ) { - final String responseBody = IOUtils.toString(response.getEntity().getContent(), StandardCharsets.UTF_8); - assertThat(responseBody).isEmpty(); - assertThat(response.getStatusLine().getStatusCode()).isEqualTo(HttpStatus.SC_OK); + try( CloseableHttpClient client = HttpClients.createDefault() ) { + String response = client.execute(request, new BasicHttpClientResponseHandler()); + assertThat(response).isEmpty(); } }