From f355da4d8a2f3fd3b46652d7562469af505f7f27 Mon Sep 17 00:00:00 2001 From: pwielebs Date: Tue, 27 Mar 2018 19:49:29 +0200 Subject: [PATCH] AAI HTTP simple and extended clients added Change-Id: I759aeeb64085dbe32883a942941bffc8e03515f7 Issue-ID: DCAEGEN2-407 Signed-off-by: pwielebs --- pom.xml | 23 +++- prh-aai-client/pom.xml | 25 +++- ...ration.java => AAIHttpClientConfiguration.java} | 13 +- .../services/service/AAIExtendedHttpClient.java | 27 ++++ .../service/AAIExtendedHttpClientImpl.java | 142 +++++++++++++++++++++ .../main/java/services/service/AAIHttpClient.java | 28 ++++ .../java/services/service/AAIHttpClientImpl.java | 93 ++++++++++++++ .../src/main/java/services/utils/HttpUtils.java | 37 ++++++ 8 files changed, 377 insertions(+), 11 deletions(-) rename prh-aai-client/src/main/java/services/config/{AAIDmaapProducerConfiguration.java => AAIHttpClientConfiguration.java} (86%) create mode 100644 prh-aai-client/src/main/java/services/service/AAIExtendedHttpClient.java create mode 100644 prh-aai-client/src/main/java/services/service/AAIExtendedHttpClientImpl.java create mode 100644 prh-aai-client/src/main/java/services/service/AAIHttpClient.java create mode 100644 prh-aai-client/src/main/java/services/service/AAIHttpClientImpl.java create mode 100644 prh-aai-client/src/main/java/services/utils/HttpUtils.java diff --git a/pom.xml b/pom.xml index 9843357e..142ae737 100644 --- a/pom.xml +++ b/pom.xml @@ -401,7 +401,27 @@ docker-maven-plugin 1.0.0 - + + org.apache.httpcomponents + httpclient + 4.5.4 + + + + com.google.guava + guava + 10.0.1 + + + org.apache.commons + commons-lang3 + 3.6 + + + org.springframework + spring-beans + 5.0.4.RELEASE + @@ -471,7 +491,6 @@ test - org.junit.platform diff --git a/prh-aai-client/pom.xml b/prh-aai-client/pom.xml index 6ac6484a..6a40d32c 100644 --- a/prh-aai-client/pom.xml +++ b/prh-aai-client/pom.xml @@ -46,6 +46,29 @@ org.immutables value + + org.apache.httpcomponents + httpclient + + + org.springframework + spring-beans + + + + + org.springframework + spring-context + 3.0.2.RELEASE + + + com.google.guava + guava + + + org.apache.commons + commons-lang3 + @@ -84,4 +107,4 @@ - \ No newline at end of file + diff --git a/prh-aai-client/src/main/java/services/config/AAIDmaapProducerConfiguration.java b/prh-aai-client/src/main/java/services/config/AAIHttpClientConfiguration.java similarity index 86% rename from prh-aai-client/src/main/java/services/config/AAIDmaapProducerConfiguration.java rename to prh-aai-client/src/main/java/services/config/AAIHttpClientConfiguration.java index dfeafddd..4c50966b 100644 --- a/prh-aai-client/src/main/java/services/config/AAIDmaapProducerConfiguration.java +++ b/prh-aai-client/src/main/java/services/config/AAIHttpClientConfiguration.java @@ -17,17 +17,17 @@ * limitations under the License. * ============LICENSE_END========================================================= */ + package services.config; -import java.net.URL; + import org.immutables.value.Value; +import org.springframework.stereotype.Component; -/** - * @author Przemysław Wąsala on 3/23/18 - */ +@Component @Value.Immutable(prehash = true) @Value.Style(stagedBuilder = true) -public abstract class AAIDmaapProducerConfiguration implements AAIConfig { +public abstract class AAIHttpClientConfiguration implements AAIConfig { private static final long serialVersionUID = 1L; @@ -46,9 +46,6 @@ public abstract class AAIDmaapProducerConfiguration implements AAIConfig { @Value.Parameter public abstract String aaiUserPassword(); - @Value.Parameter - public abstract URL aaiProxyURL(); - @Value.Parameter public abstract boolean aaiIgnoreSSLCertificateErrors(); diff --git a/prh-aai-client/src/main/java/services/service/AAIExtendedHttpClient.java b/prh-aai-client/src/main/java/services/service/AAIExtendedHttpClient.java new file mode 100644 index 00000000..8b7db1ba --- /dev/null +++ b/prh-aai-client/src/main/java/services/service/AAIExtendedHttpClient.java @@ -0,0 +1,27 @@ +/*- + * ============LICENSE_START======================================================= + * PROJECT + * ================================================================================ + * Copyright (C) 2018 NOKIA Intellectual Property. All rights reserved. + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ============LICENSE_END========================================================= + */ + +package services.service; + +import java.util.Map; + +public interface AAIExtendedHttpClient { + String getExtendedDetails(String aaiAPIPath, Map queryParams, Map headers); +} diff --git a/prh-aai-client/src/main/java/services/service/AAIExtendedHttpClientImpl.java b/prh-aai-client/src/main/java/services/service/AAIExtendedHttpClientImpl.java new file mode 100644 index 00000000..06d1a55f --- /dev/null +++ b/prh-aai-client/src/main/java/services/service/AAIExtendedHttpClientImpl.java @@ -0,0 +1,142 @@ +/*- + * ============LICENSE_START======================================================= + * PROJECT + * ================================================================================ + * Copyright (C) 2018 NOKIA Intellectual Property. All rights reserved. + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ============LICENSE_END========================================================= + */ +package services.service; + +import com.google.common.base.Optional; +import org.apache.commons.lang3.StringUtils; +import org.apache.http.HttpEntity; +import org.apache.http.client.ResponseHandler; +import org.apache.http.client.methods.HttpGet; +import org.apache.http.client.utils.URIBuilder; +import org.apache.http.impl.client.CloseableHttpClient; +import org.apache.http.util.EntityUtils; +import org.springframework.beans.factory.annotation.Autowired; + +import services.config.AAIHttpClientConfiguration; +import services.utils.HttpUtils; + +import javax.annotation.Nonnull; +import java.io.IOException; +import java.net.URI; +import java.net.URISyntaxException; +import java.util.Iterator; +import java.util.Map; + +public class AAIExtendedHttpClientImpl implements AAIExtendedHttpClient { + + private final CloseableHttpClient closeableHttpClient; + private final String aaiHost; + private final String aaiProtocol; + private final Integer aaiHostPortNumber; + + @Autowired + public AAIExtendedHttpClientImpl (AAIHttpClientConfiguration aaiHttpClientConfiguration) { + final AAIHttpClient aaiHttpClient = new AAIHttpClientImpl(aaiHttpClientConfiguration); + closeableHttpClient = aaiHttpClient.getAAIHttpClient(); + aaiHost = aaiHttpClientConfiguration.aaiHost(); + aaiProtocol = aaiHttpClientConfiguration.aaiProtocol(); + aaiHostPortNumber = aaiHttpClientConfiguration.aaiHostPortNumber(); + } + + @Override + public String getExtendedDetails(final String aaiAPIPath, final Map queryParams, + final Map headers) { + final URI extendedURI = + createAAIExtendedURI(aaiProtocol, aaiHost, aaiHostPortNumber, aaiAPIPath, queryParams); + + if (extendedURI == null) { + return null; + } + + final HttpGet getRequest = new HttpGet(extendedURI); + + for (Map.Entry headersEntry : headers.entrySet()) { + getRequest.addHeader(headersEntry.getKey(), headersEntry.getValue()); + } + + Optional extendedDetails = Optional.absent(); + + try { + extendedDetails = closeableHttpClient.execute(getRequest, aaiResponseHandler()); + } catch (IOException ex) { + //ToDo loging + } + + // return response + if (extendedDetails.isPresent()) { + return extendedDetails.get(); + } else { + return null; + } + } + + private URI createAAIExtendedURI(final String protocol, final String hostName, final Integer portNumber, + final String path, Map queryParams) { + final URIBuilder uriBuilder = new URIBuilder().setScheme(protocol).setHost(hostName).setPort(portNumber) + .setPath(path); + + final String customQuery = createCustomQuery(queryParams); + if (StringUtils.isNoneBlank(customQuery)) { + uriBuilder.setCustomQuery(customQuery); + } + + URI extendedURI = null; + + try { + extendedURI = uriBuilder.build(); + } catch (URISyntaxException e) { + // ToDo loging + } + + return extendedURI; + } + + private static String createCustomQuery(@Nonnull final Map queryParams) { + final StringBuilder queryStringBuilder = new StringBuilder(""); + final Iterator> queryParamIterator = queryParams.entrySet().iterator(); + while (queryParamIterator.hasNext()) { + final Map.Entry queryParamsEntry = queryParamIterator.next(); + queryStringBuilder.append(queryParamsEntry.getKey()); + queryStringBuilder.append("="); + queryStringBuilder.append(queryParamsEntry.getValue()); + if (queryParamIterator.hasNext()) { + queryStringBuilder.append("&"); + } + } + return queryStringBuilder.toString(); + } + + public static ResponseHandler> aaiResponseHandler() { + return httpResponse -> { + final int responseCode = httpResponse.getStatusLine().getStatusCode(); + final HttpEntity responseEntity = httpResponse.getEntity(); + + if (HttpUtils.isSuccessfulResponseCode(responseCode) && null != responseEntity) { + final String aaiResponse = EntityUtils.toString(responseEntity); + return Optional.of(aaiResponse); + } else { + String aaiResponse = responseEntity != null ? EntityUtils.toString(responseEntity) : ""; + //ToDo loging + return Optional.absent(); + } + }; + } + +} diff --git a/prh-aai-client/src/main/java/services/service/AAIHttpClient.java b/prh-aai-client/src/main/java/services/service/AAIHttpClient.java new file mode 100644 index 00000000..3dd17fc2 --- /dev/null +++ b/prh-aai-client/src/main/java/services/service/AAIHttpClient.java @@ -0,0 +1,28 @@ +/*- + * ============LICENSE_START======================================================= + * PROJECT + * ================================================================================ + * Copyright (C) 2018 NOKIA Intellectual Property. All rights reserved. + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ============LICENSE_END========================================================= + */ + +package services.service; + +import org.apache.http.impl.client.CloseableHttpClient; + +public interface AAIHttpClient { + CloseableHttpClient getAAIHttpClient(); +} + diff --git a/prh-aai-client/src/main/java/services/service/AAIHttpClientImpl.java b/prh-aai-client/src/main/java/services/service/AAIHttpClientImpl.java new file mode 100644 index 00000000..76d090d6 --- /dev/null +++ b/prh-aai-client/src/main/java/services/service/AAIHttpClientImpl.java @@ -0,0 +1,93 @@ +/*- + * ============LICENSE_START======================================================= + * PROJECT + * ================================================================================ + * Copyright (C) 2018 NOKIA Intellectual Property. All rights reserved. + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ============LICENSE_END========================================================= + */ + +package services.service; + +import org.apache.http.auth.AuthScope; +import org.apache.http.auth.Credentials; +import org.apache.http.auth.UsernamePasswordCredentials; +import org.apache.http.client.CredentialsProvider; +import org.apache.http.conn.ssl.NoopHostnameVerifier; +import org.apache.http.impl.client.BasicCredentialsProvider; +import org.apache.http.impl.client.CloseableHttpClient; +import org.apache.http.impl.client.HttpClientBuilder; +import org.apache.http.impl.client.HttpClients; +import org.apache.http.ssl.SSLContextBuilder; +import org.apache.http.ssl.TrustStrategy; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; +import org.springframework.beans.factory.annotation.Autowired; +import services.config.AAIHttpClientConfiguration; + + +import java.security.KeyManagementException; +import java.security.KeyStoreException; +import java.security.NoSuchAlgorithmException; + +public class AAIHttpClientImpl implements AAIHttpClient { + + Logger logger = LoggerFactory.getLogger(AAIHttpClientImpl.class); + + private AAIHttpClientConfiguration aaiHttpClientConfig; + + @Autowired + public AAIHttpClientImpl(AAIHttpClientConfiguration aaiHttpClientConfiguration) { + this.aaiHttpClientConfig = aaiHttpClientConfiguration; + } + + @Override + public CloseableHttpClient getAAIHttpClient() { + + final HttpClientBuilder httpClientBuilder = HttpClients.custom().useSystemProperties(); + final boolean aaiIgnoreSSLCertificateErrors = aaiHttpClientConfig.aaiIgnoreSSLCertificateErrors(); + + TrustStrategy acceptingTrustStrategy = (cert, authType) -> true; + + if (aaiIgnoreSSLCertificateErrors) { + try { + SSLContextBuilder sslContextBuilder = new SSLContextBuilder(); + sslContextBuilder.loadTrustMaterial(null, acceptingTrustStrategy); + httpClientBuilder.setSSLContext(sslContextBuilder.build()); + + } catch (NoSuchAlgorithmException | KeyStoreException | KeyManagementException e ) { + logger.error("Exception while setting SSL Context for AAI HTTP Client."); + } + + httpClientBuilder.setSSLHostnameVerifier(NoopHostnameVerifier.INSTANCE); + } + + final String aaiUserName = aaiHttpClientConfig.aaiUserName(); + + final CredentialsProvider credentialsProvider = new BasicCredentialsProvider(); + + if (aaiUserName != null) { + final String aaiHost = aaiHttpClientConfig.aaiHost(); + final Integer aaiHostPortNumber = aaiHttpClientConfig.aaiHostPortNumber(); + final String aaiUserPassword = aaiHttpClientConfig.aaiUserPassword(); + final AuthScope aaiHostPortAuthScope = new AuthScope(aaiHost, aaiHostPortNumber); + final Credentials aaiCredentials = new UsernamePasswordCredentials(aaiUserName, aaiUserPassword); + credentialsProvider.setCredentials(aaiHostPortAuthScope, aaiCredentials); + } + + httpClientBuilder.setDefaultCredentialsProvider(credentialsProvider); + + return httpClientBuilder.build(); + } +} diff --git a/prh-aai-client/src/main/java/services/utils/HttpUtils.java b/prh-aai-client/src/main/java/services/utils/HttpUtils.java new file mode 100644 index 00000000..f752d145 --- /dev/null +++ b/prh-aai-client/src/main/java/services/utils/HttpUtils.java @@ -0,0 +1,37 @@ +/*- + * ============LICENSE_START======================================================= + * PROJECT + * ================================================================================ + * Copyright (C) 2018 NOKIA Intellectual Property. All rights reserved. + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ============LICENSE_END========================================================= + */ +package services.utils; + +public class HttpUtils { + + private HttpUtils() {} + + public static final Integer HTTP_OK_RESPONSE_CODE = 200; + public static final Integer HTTP_ACCEPTED_RESPONSE_CODE = 200; + public static final Integer HTTP_NONAUTHORATIVE_INFORMATION_RESPONSE_CODE = 203; + public static final Integer HTTP_NO_CONTENT_RESPONSE_CODE = 204; + public static final Integer HTTP_RESET_CONTENT_RESPONSE_CODE = 205; + public static final Integer HTTP_PARTIAL_CONTENT_RESPONSE_CODE = 206; + public static final String JSON_APPLICATION_TYPE = "application/json"; + + public static boolean isSuccessfulResponseCode(Integer statusCode) { + return statusCode >= 200 && statusCode < 300; + } +} -- 2.16.6