Fix security vulnerabilities
[externalapi/nbi.git] / src / main / java / org / onap / nbi / apis / serviceorder / SoClient.java
1 /**
2  * Copyright (c) 2018 Orange
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except
5  * in compliance with the License. You may obtain a copy of the License at
6  *
7  * http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * Unless required by applicable law or agreed to in writing, software distributed under the License
10  * is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express
11  * or implied. See the License for the specific language governing permissions and limitations under
12  * the License.
13  */
14
15 package org.onap.nbi.apis.serviceorder;
16
17 import javax.annotation.PostConstruct;
18 import org.onap.nbi.OnapComponentsUrlPaths;
19 import org.onap.nbi.apis.serviceorder.model.consumer.CreateE2EServiceInstanceResponse;
20 import org.onap.nbi.apis.serviceorder.model.consumer.CreateMacroServiceInstanceResponse;
21 import org.onap.nbi.apis.serviceorder.model.consumer.CreateServiceInstanceResponse;
22 import org.onap.nbi.apis.serviceorder.model.consumer.DeleteE2EServiceInstanceResponse;
23 import org.onap.nbi.apis.serviceorder.model.consumer.GetE2ERequestStatusResponse;
24 import org.onap.nbi.apis.serviceorder.model.consumer.GetRequestStatusResponse;
25 import org.onap.nbi.apis.serviceorder.model.consumer.MSODeleteE2EPayload;
26 import org.onap.nbi.apis.serviceorder.model.consumer.MSOE2EPayload;
27 import org.onap.nbi.apis.serviceorder.model.consumer.MSOPayload;
28 import org.onap.nbi.apis.serviceorder.model.consumer.ServiceResponse;
29 import org.onap.nbi.exceptions.BackendFunctionalException;
30 import org.slf4j.Logger;
31 import org.slf4j.LoggerFactory;
32 import org.springframework.beans.factory.annotation.Autowired;
33 import org.springframework.beans.factory.annotation.Value;
34 import org.springframework.http.HttpEntity;
35 import org.springframework.http.HttpHeaders;
36 import org.springframework.http.HttpMethod;
37 import org.springframework.http.HttpStatus;
38 import org.springframework.http.ResponseEntity;
39 import org.springframework.stereotype.Service;
40 import org.springframework.web.client.ResourceAccessException;
41 import org.springframework.web.client.RestTemplate;
42
43 @Service
44 public class SoClient {
45
46     public static final String RESPONSE_STATUS = "response status : ";
47     public static final String RETURNS = " returns ";
48     public static final String ERROR_ON_CALLING = "error on calling ";
49     @Autowired
50     private RestTemplate restTemplate;
51
52     @Value("${so.host}")
53     private String soHostname;
54
55     @Value("${so.onap.partner.name}")
56     private String soOnapPartnerName;
57
58     @Value("${so.header.authorization}")
59     private String soHeaderAuthorization;
60
61     private static final String HEADER_AUTHORIZATION = "Authorization";
62     private static final String X_ONAP_PARTNER_HEADER = "X-ONAP-PartnerName";
63
64     private static final Logger LOGGER = LoggerFactory.getLogger(SoClient.class);
65
66     private String createSoUrl;
67     private String createE2ESoUrl;
68     private String getSoStatus;
69     private String getE2ESoStatus;
70     private String deleteE2ESoUrl;
71     private String deleteSoUrl;
72     private String SoHealthCheck;
73
74     @PostConstruct
75     private void setUpAndLogSOUrl() {
76         createSoUrl = new StringBuilder().append(soHostname)
77                 .append(OnapComponentsUrlPaths.MSO_CREATE_SERVICE_INSTANCE_PATH).toString();
78         createE2ESoUrl = new StringBuilder().append(soHostname)
79                 .append(OnapComponentsUrlPaths.MSO_CREATE_E2ESERVICE_INSTANCE_PATH).toString();
80         deleteSoUrl = new StringBuilder().append(soHostname)
81                 .append(OnapComponentsUrlPaths.MSO_DELETE_REQUEST_STATUS_PATH).toString();
82         deleteE2ESoUrl = new StringBuilder().append(soHostname)
83                 .append(OnapComponentsUrlPaths.MSO_DELETE_E2ESERVICE_INSTANCE_PATH).toString();
84         getSoStatus = new StringBuilder().append(soHostname).append(OnapComponentsUrlPaths.MSO_GET_REQUEST_STATUS_PATH)
85                 .toString();
86         getE2ESoStatus = new StringBuilder().append(soHostname)
87                 .append(OnapComponentsUrlPaths.MSO_GET_E2EREQUEST_STATUS_PATH).toString();
88         SoHealthCheck =
89                 new StringBuilder().append(soHostname).append(OnapComponentsUrlPaths.MSO_HEALTH_CHECK).toString();
90
91         LOGGER.info("SO create service url :  " + createSoUrl);
92         LOGGER.info("SO create e2e service url :  " + createE2ESoUrl);
93         LOGGER.info("SO delete service url :  " + deleteSoUrl);
94         LOGGER.info("SO delete e2e service url :  " + deleteE2ESoUrl);
95         LOGGER.info("SO get so status url :  " + getSoStatus);
96         LOGGER.info("SO get e2e so status url :  " + getE2ESoStatus);
97         LOGGER.info("SO healthCheck :  " + SoHealthCheck);
98
99     }
100
101     public ResponseEntity<CreateServiceInstanceResponse> callCreateServiceInstance(MSOPayload msoPayload) {
102
103         if (LOGGER.isDebugEnabled()) {
104             LOGGER.debug("Calling SO CreateServiceInstance with msoPayload : " + msoPayload.toString());
105         }
106
107         try {
108             ResponseEntity<CreateServiceInstanceResponse> response = restTemplate.exchange(createSoUrl, HttpMethod.POST,
109                     new HttpEntity<>(msoPayload, buildRequestHeader()), CreateServiceInstanceResponse.class);
110
111             logResponsePost(createSoUrl, response);
112             return response;
113
114         } catch (BackendFunctionalException e) {
115             LOGGER.error(ERROR_ON_CALLING + createSoUrl + " ," + e.getHttpStatus() + " , " + e.getBodyResponse());
116             return new ResponseEntity(e.getBodyResponse(), e.getHttpStatus());
117         } catch (ResourceAccessException e) {
118             LOGGER.error(ERROR_ON_CALLING + createSoUrl + " ," + e.getMessage());
119             return new ResponseEntity<>(HttpStatus.INTERNAL_SERVER_ERROR);
120         }
121     }
122
123     public ResponseEntity<CreateMacroServiceInstanceResponse> callMacroCreateServiceInstance(MSOPayload msoPayload) {
124
125         if (LOGGER.isDebugEnabled()) {
126           LOGGER.debug("Calling SO CreateServiceInstance with msoPayload : " + msoPayload.toString());
127         }
128
129         try {
130           ResponseEntity<CreateMacroServiceInstanceResponse> response = restTemplate.exchange(createSoUrl,
131                    HttpMethod.POST, new HttpEntity<>(msoPayload, buildRequestHeader()),CreateMacroServiceInstanceResponse.class);
132           
133           logMacroResponsePost(createSoUrl, response);
134           return response;
135         } catch (BackendFunctionalException e) {
136           LOGGER.error(ERROR_ON_CALLING + createSoUrl + " ," + e.getHttpStatus() + " , " + e.getBodyResponse());
137           return new ResponseEntity(e.getBodyResponse(), e.getHttpStatus());
138         } catch (ResourceAccessException e) {
139           LOGGER.error(ERROR_ON_CALLING + createSoUrl + " ," + e.getMessage());
140           return new ResponseEntity<>(HttpStatus.INTERNAL_SERVER_ERROR);
141         }
142     }
143     
144     public ResponseEntity<CreateE2EServiceInstanceResponse> callE2ECreateServiceInstance(MSOE2EPayload msoPayloadE2E) {
145
146         if (LOGGER.isDebugEnabled()) {
147             LOGGER.debug("Calling SO CreateServiceInstanceE2E with msoPayload : " + msoPayloadE2E.toString());
148         }
149
150         try {
151             ResponseEntity<CreateE2EServiceInstanceResponse> response = restTemplate.exchange(createE2ESoUrl,
152                     HttpMethod.POST, new HttpEntity<>(msoPayloadE2E, buildRequestHeader()),
153                     CreateE2EServiceInstanceResponse.class);
154
155             logE2EResponsePost(createE2ESoUrl, response);
156             return response;
157
158         } catch (BackendFunctionalException e) {
159             LOGGER.error(ERROR_ON_CALLING + createE2ESoUrl + " ," + e.getHttpStatus() + " , " + e.getBodyResponse());
160             return new ResponseEntity(e.getBodyResponse(), e.getHttpStatus());
161         } catch (ResourceAccessException e) {
162             LOGGER.error(ERROR_ON_CALLING + createE2ESoUrl + " ," + e.getMessage());
163             return new ResponseEntity<>(HttpStatus.INTERNAL_SERVER_ERROR);
164         }
165     }
166
167     public ResponseEntity<CreateServiceInstanceResponse> callDeleteServiceInstance(MSOPayload msoPayload,
168             String serviceId) {
169
170         if (LOGGER.isDebugEnabled()) {
171             LOGGER.debug("Calling SO DeleteServiceInstance with msoPayload : " + msoPayload.toString());
172         }
173
174         String url = deleteSoUrl + serviceId;
175
176         try {
177             ResponseEntity<CreateServiceInstanceResponse> response = restTemplate.exchange(url, HttpMethod.DELETE,
178                     new HttpEntity<>(msoPayload, buildRequestHeader()), CreateServiceInstanceResponse.class);
179
180             logResponsePost(url, response);
181             return response;
182
183         } catch (BackendFunctionalException e) {
184             LOGGER.error(ERROR_ON_CALLING + url + " ," + e);
185             return new ResponseEntity<>(e.getHttpStatus());
186         } catch (ResourceAccessException e) {
187             LOGGER.error(ERROR_ON_CALLING + url + " ," + e);
188             return new ResponseEntity<>(HttpStatus.INTERNAL_SERVER_ERROR);
189         }
190
191     }
192
193     public ResponseEntity<CreateE2EServiceInstanceResponse> callE2EDeleteServiceInstance(String globalSubscriberId,
194             String serviceType, String serviceInstanceId) {
195
196         String url = deleteE2ESoUrl + serviceInstanceId;
197         MSODeleteE2EPayload msoDeleteE2EPayload = new MSODeleteE2EPayload();
198         msoDeleteE2EPayload.setGlobalSubscriberId(globalSubscriberId);
199         msoDeleteE2EPayload.setServiceType(serviceType);
200
201         if (LOGGER.isDebugEnabled()) {
202             LOGGER.debug("Calling SO DeleteE2EServiceInstance with url : " + url + " MSODeleteE2EPayload : "
203                     + msoDeleteE2EPayload.toString());
204         }
205
206         try {
207             ResponseEntity<DeleteE2EServiceInstanceResponse> deleteresponse = restTemplate.exchange(url,
208                     HttpMethod.DELETE, new HttpEntity<>(msoDeleteE2EPayload, buildRequestHeader()),
209                     DeleteE2EServiceInstanceResponse.class);
210
211             // For E2E Services , Create and Delete Service responses are different, to maintain
212             // consistentcy with ServiceInstances
213             // Copy contents of DeleteE2EServiceInstanceResponse to CreateE2EServiceInstanceResponse
214             CreateE2EServiceInstanceResponse dummyresponse = new CreateE2EServiceInstanceResponse();
215             ServiceResponse serviceResponse = new ServiceResponse();
216             dummyresponse.setService(serviceResponse);
217             dummyresponse.getService().setOperationId(deleteresponse.getBody().getOperationId());
218             dummyresponse.getService().setServiceId(serviceInstanceId);
219
220             ResponseEntity<CreateE2EServiceInstanceResponse> response =
221                     new ResponseEntity(dummyresponse, deleteresponse.getStatusCode());
222             logE2EResponsePost(url, response);
223             return response;
224
225         } catch (BackendFunctionalException e) {
226             LOGGER.error(ERROR_ON_CALLING + url + " ," + e);
227             return new ResponseEntity<>(e.getHttpStatus());
228         } catch (ResourceAccessException e) {
229             LOGGER.error(ERROR_ON_CALLING + url + " ," + e);
230             return new ResponseEntity<>(HttpStatus.INTERNAL_SERVER_ERROR);
231         }
232     }
233
234     private void logResponsePost(String url, ResponseEntity<CreateServiceInstanceResponse> response) {
235         LOGGER.info(RESPONSE_STATUS + response.getStatusCodeValue());
236         if (LOGGER.isDebugEnabled()) {
237             LOGGER.debug("response body : {}", response.getBody().toString());
238         }
239
240         if (LOGGER.isWarnEnabled() && !response.getStatusCode().equals(HttpStatus.CREATED)) {
241             LOGGER.warn("HTTP call SO on {} returns {} , {}", url, response.getStatusCodeValue(),
242                     response.getBody().toString());
243         }
244     }
245
246     private void logMacroResponsePost(String url, ResponseEntity<CreateMacroServiceInstanceResponse> response) {
247       LOGGER.info(RESPONSE_STATUS + response.getStatusCodeValue());
248       if (LOGGER.isDebugEnabled()) {
249         LOGGER.debug("response body : {}", response.getBody().toString());
250       }
251       
252       if (LOGGER.isWarnEnabled() && !response.getStatusCode().equals(HttpStatus.CREATED)) {
253         LOGGER.warn("HTTP call SO on {} returns {} , {}", url, response.getStatusCodeValue(),
254                     response.getBody().toString());
255       }
256     }
257     
258     private void logE2EResponsePost(String url, ResponseEntity<CreateE2EServiceInstanceResponse> response) {
259         LOGGER.info(RESPONSE_STATUS + response.getStatusCodeValue());
260         if (LOGGER.isDebugEnabled()) {
261             LOGGER.debug("response body : {}", response.getBody().toString());
262         }
263
264         if (LOGGER.isWarnEnabled() && !response.getStatusCode().equals(HttpStatus.CREATED)) {
265             LOGGER.warn("HTTP call SO on {} returns {} , {}", url, response.getStatusCodeValue(),
266                     response.getBody().toString());
267         }
268     }
269
270     public GetRequestStatusResponse callGetRequestStatus(String requestId) {
271         String url = getSoStatus + requestId;
272
273         try {
274
275             ResponseEntity<GetRequestStatusResponse> response = restTemplate.exchange(url, HttpMethod.GET,
276                     new HttpEntity<>(buildRequestHeader()), GetRequestStatusResponse.class);
277             logResponseGet(url, response);
278             if (null == response) {
279                 return null;
280             } else {
281                 return response.getBody();
282             }
283
284         } catch (BackendFunctionalException | ResourceAccessException e) {
285             LOGGER.error(ERROR_ON_CALLING + url + " ," + e);
286             return null;
287         }
288     }
289
290     public void callCheckConnectivity() {
291         String url = SoHealthCheck;
292         restTemplate.exchange(url, HttpMethod.GET, new HttpEntity<>(buildRequestHeader()), String.class);
293
294     }
295
296     public GetE2ERequestStatusResponse callE2EGetRequestStatus(String operationId, String serviceId) {
297
298         String callUrlFormated = getE2ESoStatus.replace("$serviceId", serviceId);
299         callUrlFormated = callUrlFormated.replace("$operationId", operationId);
300
301         if (LOGGER.isDebugEnabled()) {
302             LOGGER.debug("Calling SO callE2EGetRequestStatus with url : " + callUrlFormated);
303         }
304
305         try {
306
307             ResponseEntity<GetE2ERequestStatusResponse> response = restTemplate.exchange(callUrlFormated,
308                     HttpMethod.GET, new HttpEntity<>(buildRequestHeader()), GetE2ERequestStatusResponse.class);
309             logE2EResponseGet(callUrlFormated, response);
310             if (null == response) {
311                 return null;
312             } else {
313                 return response.getBody();
314             }
315
316         } catch (BackendFunctionalException | ResourceAccessException e) {
317             LOGGER.error(ERROR_ON_CALLING + callUrlFormated + " ," + e);
318             return null;
319         }
320     }
321
322     private void logResponseGet(String url, ResponseEntity<GetRequestStatusResponse> response) {
323         if (response != null) {
324             if (LOGGER.isDebugEnabled()) {
325                 LOGGER.debug("response status : {} , response body : {}", response.getStatusCodeValue(),
326                         response.getBody().toString());
327             }
328             if (LOGGER.isWarnEnabled() && !response.getStatusCode().equals(HttpStatus.OK)) {
329                 LOGGER.warn("HTTP call SO on {} returns {} , {}", url, response.getStatusCodeValue(),
330                         response.getBody().toString());
331             }
332         } else {
333             if (LOGGER.isWarnEnabled()) {
334                 LOGGER.warn("no response calling url {}", url);
335             }
336         }
337     }
338
339     private void logE2EResponseGet(String url, ResponseEntity<GetE2ERequestStatusResponse> response) {
340         if (response != null) {
341             if (LOGGER.isDebugEnabled()) {
342                 LOGGER.debug("response status : {} , response body : {}", response.getStatusCodeValue(),
343                         response.getBody().toString());
344             }
345             if (LOGGER.isWarnEnabled() && !response.getStatusCode().equals(HttpStatus.OK)) {
346                 LOGGER.warn("HTTP call SO on {} returns {} , {}", url, response.getStatusCodeValue(),
347                         response.getBody().toString());
348             }
349         } else {
350             if (LOGGER.isWarnEnabled()) {
351                 LOGGER.warn("no response calling url {}", url);
352             }
353         }
354     }
355
356     private HttpHeaders buildRequestHeader() {
357         HttpHeaders httpHeaders = new HttpHeaders();
358         httpHeaders.add(HEADER_AUTHORIZATION, soHeaderAuthorization);
359         httpHeaders.add(X_ONAP_PARTNER_HEADER, soOnapPartnerName);
360         httpHeaders.add("Accept", "application/json");
361         httpHeaders.add("Content-Type", "application/json");
362         return httpHeaders;
363     }
364
365 }