2 * ============LICENSE_START=======================================================
4 * ================================================================================
5 * Copyright (C) 2017-2019 AT&T Intellectual Property. All rights reserved.
6 * Modifications Copyright (C) 2018 Samsung Electronics Co., Ltd.
7 * ================================================================================
8 * Licensed under the Apache License, Version 2.0 (the "License");
9 * you may not use this file except in compliance with the License.
10 * You may obtain a copy of the License at
12 * http://www.apache.org/licenses/LICENSE-2.0
14 * Unless required by applicable law or agreed to in writing, software
15 * distributed under the License is distributed on an "AS IS" BASIS,
16 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
17 * See the License for the specific language governing permissions and
18 * limitations under the License.
19 * ============LICENSE_END=========================================================
22 package org.onap.policy.common.endpoints.http.client.internal;
24 import com.fasterxml.jackson.annotation.JsonIgnore;
25 import java.security.KeyManagementException;
26 import java.security.NoSuchAlgorithmException;
27 import java.security.SecureRandom;
28 import java.security.cert.CertificateException;
29 import java.security.cert.X509Certificate;
31 import java.util.Map.Entry;
32 import javax.net.ssl.SSLContext;
33 import javax.net.ssl.TrustManager;
34 import javax.net.ssl.X509TrustManager;
35 import javax.ws.rs.client.Client;
36 import javax.ws.rs.client.ClientBuilder;
37 import javax.ws.rs.client.Entity;
38 import javax.ws.rs.client.Invocation.Builder;
39 import javax.ws.rs.core.Response;
40 import org.glassfish.jersey.client.ClientProperties;
41 import org.glassfish.jersey.client.authentication.HttpAuthenticationFeature;
42 import org.onap.policy.common.endpoints.event.comm.bus.internal.BusTopicParams;
43 import org.onap.policy.common.endpoints.http.client.HttpClient;
44 import org.onap.policy.common.gson.annotation.GsonJsonIgnore;
45 import org.slf4j.Logger;
46 import org.slf4j.LoggerFactory;
49 * Http Client implementation using a Jersey Client.
51 * <p>Note: the serialization provider will be ignored if the maven artifact,
52 * <i>jersey-media-json-jackson</i>, is included, regardless of whether it's included
53 * directly or indirectly.
55 public class JerseyClient implements HttpClient {
60 private static Logger logger = LoggerFactory.getLogger(JerseyClient.class);
62 protected static final String JERSEY_DEFAULT_SERIALIZATION_PROVIDER =
63 "com.fasterxml.jackson.jaxrs.json.JacksonJaxbJsonProvider";
65 protected final String name;
66 protected final boolean https;
67 protected final boolean selfSignedCerts;
68 protected final String hostname;
69 protected final int port;
70 protected final String basePath;
71 protected final String userName;
72 protected final String password;
74 protected final Client client;
75 protected final String baseUrl;
77 protected boolean alive = true;
82 * <p>name the name https is it https or not selfSignedCerts are there self signed certs
83 * hostname the hostname port port being used basePath base context userName user
86 * @param busTopicParams Input parameters object
87 * @throws KeyManagementException key exception
88 * @throws NoSuchAlgorithmException no algorithm exception
89 * @throws ClassNotFoundException if the serialization provider cannot be found
91 public JerseyClient(BusTopicParams busTopicParams)
92 throws KeyManagementException, NoSuchAlgorithmException, ClassNotFoundException {
96 if (busTopicParams.isClientNameInvalid()) {
97 throw new IllegalArgumentException("Name must be provided");
100 if (busTopicParams.isHostnameInvalid()) {
101 throw new IllegalArgumentException("Hostname must be provided");
104 if (busTopicParams.isPortInvalid()) {
105 throw new IllegalArgumentException("Invalid Port provided: " + busTopicParams.getPort());
108 this.name = busTopicParams.getClientName();
109 this.https = busTopicParams.isUseHttps();
110 this.hostname = busTopicParams.getHostname();
111 this.port = busTopicParams.getPort();
112 this.basePath = busTopicParams.getBasePath();
113 this.userName = busTopicParams.getUserName();
114 this.password = busTopicParams.getPassword();
115 this.selfSignedCerts = busTopicParams.isAllowSelfSignedCerts();
117 StringBuilder tmpBaseUrl = new StringBuilder();
119 tmpBaseUrl.append("https://");
120 ClientBuilder clientBuilder;
121 SSLContext sslContext = SSLContext.getInstance("TLSv1.2");
122 if (this.selfSignedCerts) {
123 sslContext.init(null, new TrustManager[] {new X509TrustManager() {
125 public void checkClientTrusted(X509Certificate[] chain, String authType)
126 throws CertificateException {
131 public void checkServerTrusted(X509Certificate[] chain, String authType)
132 throws CertificateException {
137 public X509Certificate[] getAcceptedIssuers() {
138 return new X509Certificate[0];
141 } }, new SecureRandom());
143 ClientBuilder.newBuilder().sslContext(sslContext).hostnameVerifier((host, session) -> true);
145 sslContext.init(null, null, null);
146 clientBuilder = ClientBuilder.newBuilder().sslContext(sslContext);
148 this.client = clientBuilder.build();
150 tmpBaseUrl.append("http://");
151 this.client = ClientBuilder.newClient();
154 if (this.userName != null && !this.userName.isEmpty() && this.password != null && !this.password.isEmpty()) {
155 HttpAuthenticationFeature authFeature = HttpAuthenticationFeature.basic(userName, password);
156 this.client.register(authFeature);
159 registerSerProviders(busTopicParams.getSerializationProvider());
161 this.client.property(ClientProperties.METAINF_SERVICES_LOOKUP_DISABLE, "true");
163 this.baseUrl = tmpBaseUrl.append(this.hostname).append(":").append(this.port).append("/")
164 .append((this.basePath == null) ? "" : this.basePath).toString();
168 * Registers the serialization provider(s) with the client.
170 * @param serializationProvider comma-separated list of serialization providers
171 * @throws ClassNotFoundException if the serialization provider cannot be found
173 private void registerSerProviders(String serializationProvider) throws ClassNotFoundException {
174 String providers = (serializationProvider == null || serializationProvider.isEmpty()
175 ? JERSEY_DEFAULT_SERIALIZATION_PROVIDER : serializationProvider);
176 for (String prov : providers.split(",")) {
177 this.client.register(Class.forName(prov));
182 public Response get(String path) {
183 if (path != null && !path.isEmpty()) {
184 return this.client.target(this.baseUrl).path(path).request().get();
186 return this.client.target(this.baseUrl).request().get();
191 public Response get() {
192 return this.client.target(this.baseUrl).request().get();
196 public Response put(String path, Entity<?> entity, Map<String, Object> headers) {
197 return getBuilder(path, headers).put(entity);
201 public Response post(String path, Entity<?> entity, Map<String, Object> headers) {
202 return getBuilder(path, headers).post(entity);
206 public Response delete(String path, Map<String, Object> headers) {
207 return getBuilder(path, headers).delete();
211 public boolean start() {
216 public boolean stop() {
221 public void shutdown() {
222 synchronized (this) {
228 } catch (Exception e) {
229 logger.warn("{}: cannot close because of {}", this, e.getMessage(), e);
234 public synchronized boolean isAlive() {
239 public String getName() {
244 public boolean isHttps() {
249 public boolean isSelfSignedCerts() {
250 return selfSignedCerts;
254 public String getHostname() {
259 public int getPort() {
264 public String getBasePath() {
269 public String getUserName() {
276 public String getPassword() {
281 public String getBaseUrl() {
286 public String toString() {
287 StringBuilder builder = new StringBuilder();
288 builder.append("JerseyClient [name=");
289 builder.append(name);
290 builder.append(", https=");
291 builder.append(https);
292 builder.append(", selfSignedCerts=");
293 builder.append(selfSignedCerts);
294 builder.append(", hostname=");
295 builder.append(hostname);
296 builder.append(", port=");
297 builder.append(port);
298 builder.append(", basePath=");
299 builder.append(basePath);
300 builder.append(", userName=");
301 builder.append(userName);
302 builder.append(", password=");
303 builder.append(password);
304 builder.append(", client=");
305 builder.append(client);
306 builder.append(", baseUrl=");
307 builder.append(baseUrl);
308 builder.append(", alive=");
309 builder.append(alive);
311 return builder.toString();
314 private Builder getBuilder(String path, Map<String, Object> headers) {
315 Builder builder = this.client.target(this.baseUrl).path(path).request();
316 for (Entry<String, Object> header : headers.entrySet()) {
317 builder.header(header.getKey(), header.getValue());