ff725bb59ac688fe33b9bd6825ff24f9d78225d7
[aai/aai-common.git] / aai-core / src / main / java / org / onap / aai / util / RestController.java
1 /**
2  * ============LICENSE_START=======================================================
3  * org.onap.aai
4  * ================================================================================
5  * Copyright © 2017-2018 AT&T Intellectual Property. All rights reserved.
6  * ================================================================================
7  * Licensed under the Apache License, Version 2.0 (the "License");
8  * you may not use this file except in compliance with the License.
9  * You may obtain a copy of the License at
10  *
11  *    http://www.apache.org/licenses/LICENSE-2.0
12  *
13  * Unless required by applicable law or agreed to in writing, software
14  * distributed under the License is distributed on an "AS IS" BASIS,
15  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16  * See the License for the specific language governing permissions and
17  * limitations under the License.
18  * ============LICENSE_END=========================================================
19  */
20 package org.onap.aai.util;
21
22 import java.security.KeyManagementException;
23 import java.util.ArrayList;
24 import java.util.List;
25 import java.util.UUID;
26
27 import org.onap.aai.exceptions.AAIException;
28 import org.onap.aai.logging.LoggingContext;
29
30 import com.att.eelf.configuration.EELFLogger;
31 import com.att.eelf.configuration.EELFManager;
32 import com.fasterxml.jackson.databind.ObjectMapper;
33 import com.fasterxml.jackson.databind.type.TypeFactory;
34 import com.sun.jersey.api.client.Client;
35 import com.sun.jersey.api.client.ClientHandlerException;
36 import com.sun.jersey.api.client.ClientResponse;
37
38 public class RestController implements RestControllerInterface {
39
40         private static final String TARGET_NAME = "AAI";
41         private static EELFLogger LOGGER = EELFManager.getInstance().getLogger(RestController.class);
42         
43         private static Client client = null;
44         
45         private String restSrvrBaseURL;
46         
47         //To do - Come up with helper function that will automatically
48         //generate the REST API path based on path parameter(s) and query parameter(s)!
49         public static final String REST_APIPATH_COMPLEXES = "cloud-infrastructure/complexes";
50         public static final String REST_APIPATH_COMPLEX = "cloud-infrastructure/complexes/complex/";
51         public static final String REST_APIPATH_PSERVERS = "cloud-infrastructure/pservers";
52         public static final String REST_APIPATH_PSERVER = "cloud-infrastructure/pservers/pserver/";
53         public static final String REST_APIPATH_PHYSICALLINKS = "network/physical-links/";
54         public static final String REST_APIPATH_PHYSICALLINK = "network/physical-links/physical-link/";
55         public static final String REST_APIPATH_PINTERFACES = "network/p-interfaces/";
56         public static final String REST_APIPATH_PINTERFACE = "network/p-interfaces/p-interface/";
57         public static final String REST_APIPATH_VPLSPES = "network/vpls-pes/";
58         public static final String REST_APIPATH_VPLSPE = "network/vpls-pes/vpls-pe/";
59         public static final String REST_APIPATH_UPDATE = "actions/update/";
60         public static final String REST_APIPATH_SEARCH = "search/nodes-query?search-node-type=";
61         
62         public static final String REST_APIPATH_CLOUDREGION = "cloud-infrastructure/cloud-regions/cloud-region/";
63         public static final  String REST_APIPATH_TENANT = "cloud-infrastructure/tenants/tenant/";
64         public static final String REST_APIPATH_VIRTUAL_DATA_CENTER = "cloud-infrastructure/virtual-data-centers/virtual-data-center/";
65         public static final String REST_APIPATH_VIRTUAL_DATA_CENTERS = "cloud-infrastructure/virtual-data-centers/";
66         public static final String REST_APIPATH_GENERIC_VNF = "network/generic-vnfs/generic-vnf/";
67         public static final String REST_APIPATH_GENERIC_VNFS = "network/generic-vnfs";
68         public static final String REST_APIPATH_L3_NETWORK = "network/l3-networks/l3-network/";
69         public static final String REST_APIPATH_L3_NETWORKS = "network/l3-networks";
70         public static final String REST_APIPATH_INSTANCE_GROUP = "network/instance-groups/instance-group";
71         public static final String REST_APIPATH_INSTANCE_GROUPS = "network/instance-groups";
72         public static final String REST_APIPATH_VFMODULE = "nodes/vf-modules/vf-module/";
73         
74         public static final  String REST_APIPATH_VCE = "network/vces/vce/";
75         
76         public static final  String REST_APIPATH_SERVICE = "service-design-and-creation/services/service/";
77         public static final String REST_APIPATH_LOGICALLINKS = "network/logical-links/";
78         public static final String REST_APIPATH_LOGICALLINK = "network/logical-links/logical-link/";
79
80         public RestController() throws AAIException {
81                 this.initRestClient();
82         }
83         /**
84          * Inits the rest client.
85          *
86          * @throws AAIException the AAI exception
87          */
88         public void initRestClient() throws AAIException
89         {
90                 if (client == null) {
91                         try {
92                                 client = getHttpsAuthClient();
93                         }
94                         catch (KeyManagementException e){
95                                 throw new AAIException("AAI_7117", "KeyManagementException in REST call to DB: " + e.toString());
96                         } catch (Exception e) {
97                                 throw new AAIException("AAI_7117", " Exception in REST call to DB: " + e.toString());
98                         }
99                 }
100         }
101         
102     public Client getHttpsAuthClient() throws KeyManagementException {
103         return HttpsAuthClient.getClient();
104     }
105
106         
107         /**
108          * Sets the rest srvr base URL.
109          *
110          * @param baseURL the base URL
111          * @throws AAIException the AAI exception
112          */
113         public void SetRestSrvrBaseURL(String baseURL) throws AAIException
114         {
115                 if (baseURL == null)
116                         throw new AAIException("AAI_7117", "REST Server base URL cannot be null.");
117                 restSrvrBaseURL = baseURL;
118         }
119         
120         /**
121          * Gets the rest srvr base URL.
122          *
123          * @return the rest srvr base URL
124          */
125         public String getRestSrvrBaseURL() 
126         {
127                 return restSrvrBaseURL;
128         }
129         
130         
131         public <T> void Get(T t, String sourceID,  String transId,  String path, RestObject<T> restObject, boolean oldserver) throws AAIException {
132                 Get(t, sourceID, transId, path, restObject, oldserver, AAIConstants.AAI_RESOURCES_PORT);
133         }
134         /**
135          * To do - optimization and automation.  Also make it as generic as possible.
136          *
137          * @param <T> the generic type
138          * @param t the t
139          * @param sourceID the source ID
140          * @param transId the trans id
141          * @param path the path
142          * @param restObject the rest object
143          * @param oldserver the oldserver
144          * @throws AAIException the AAI exception
145          */
146         @SuppressWarnings("unchecked")
147         public <T> void Get(T t, String sourceID,  String transId,  String path, RestObject<T> restObject, boolean oldserver, int port) throws AAIException {
148                 String methodName = "Get";
149                 String url="";
150                 transId += ":" + UUID.randomUUID().toString();
151
152                 LoggingContext.save();
153                 LoggingContext.partnerName(sourceID);
154                 LoggingContext.targetEntity(TARGET_NAME);
155                 LoggingContext.requestId(transId);
156                 LoggingContext.serviceName(methodName);
157                 LoggingContext.targetServiceName(methodName);
158                 
159                 LOGGER.debug(methodName + " start");
160         
161                 restObject.set(t);
162                 
163                 if (oldserver)
164                         url = AAIConfig.get(AAIConstants.AAI_OLDSERVER_URL) + path;
165                 else
166                         url = String.format(AAIConstants.AAI_LOCAL_REST, port, AAIConfig.get(AAIConstants.AAI_DEFAULT_API_VERSION_PROP)) + path;
167                 initRestClient();
168                 LOGGER.debug(url + " for the get REST API");
169                 ClientResponse cres = client.resource(url)
170                  .accept("application/json")
171                  .header("X-TransactionId", transId)
172                  .header("X-FromAppId",  sourceID)
173                  .header("Real-Time", "true")
174                  .type("application/json")
175                  .get(ClientResponse.class);
176
177 //                      System.out.println("cres.EntityInputSream()="+cres.getEntityInputStream().toString());
178 //                      System.out.println("cres.tostring()="+cres.toString());
179                         
180                  if (cres.getStatus() == 200) {
181 //                   System.out.println(methodName + ": url=" + url);
182                          t = (T) cres.getEntity(t.getClass());
183                          restObject.set(t);
184                          LOGGER.debug(methodName + "REST api GET was successfull!");                
185                  } else {
186                          LoggingContext.restore();
187 //                   System.out.println(methodName + ": url=" + url + " failed with status=" + cres.getStatus());
188                      throw new AAIException("AAI_7116", methodName +" with status="+cres.getStatus()+", url="+url);
189                  }
190
191                  LoggingContext.restore();
192         }
193         
194         /**
195          * To do - optimization and automation.  Also make it as generic as possible.
196          *
197          * @param <T> the generic type
198          * @param t the t
199          * @param sourceID the source ID
200          * @param transId the trans id
201          * @param path the path
202          * @param restObject the rest object
203          * @param oldserver the oldserver
204          * @throws AAIException the AAI exception
205          */
206         @SuppressWarnings("unchecked")
207         public <T> void Get(T t, String sourceID,  String transId,  String path, RestObject<T> restObject, String apiVersion) throws AAIException {
208                 String methodName = "Get";
209                 String url="";
210                 transId += ":" + UUID.randomUUID().toString();
211
212                 LoggingContext.save();
213                 LoggingContext.partnerName(sourceID);
214                 LoggingContext.targetEntity(TARGET_NAME);
215                 LoggingContext.requestId(transId);
216                 LoggingContext.serviceName(methodName);
217                 LoggingContext.targetServiceName(methodName);
218                 
219                 LOGGER.debug(methodName + " start");
220         
221                 restObject.set(t);
222                 
223                 url = AAIConfig.get(AAIConstants.AAI_SERVER_URL_BASE) + apiVersion + "/"+ path;
224                 
225                 initRestClient();
226                 LOGGER.debug(url + " for the get REST API");
227                 ClientResponse cres = client.resource(url)
228                  .accept("application/json")
229                  .header("X-TransactionId", transId)
230                  .header("X-FromAppId",  sourceID)
231                  .header("Real-Time", "true")
232                  .type("application/json")
233                  .get(ClientResponse.class);
234
235 //                      System.out.println("cres.EntityInputSream()="+cres.getEntityInputStream().toString());
236 //                      System.out.println("cres.tostring()="+cres.toString());
237                         
238                  if (cres.getStatus() == 200) {
239 //                   System.out.println(methodName + ": url=" + url);
240                          t = (T) cres.getEntity(t.getClass());
241                          restObject.set(t);
242                          LOGGER.debug(methodName + "REST api GET was successfull!");                
243                  } else {
244                          LoggingContext.restore();
245 //                   System.out.println(methodName + ": url=" + url + " failed with status=" + cres.getStatus());
246                      throw new AAIException("AAI_7116", methodName +" with status="+cres.getStatus()+", url="+url);
247                  }
248
249                  LoggingContext.restore();
250         }
251         
252    /**
253     * Map json to object list.
254     *
255     * @param <T> the generic type
256     * @param typeDef the type def
257     * @param json the json
258     * @param clazz the clazz
259     * @return the list
260     * @throws Exception the exception
261     */
262    private <T> List<T> mapJsonToObjectList(T typeDef,String json, Class clazz) throws Exception
263    {
264       List<T> list;
265       ObjectMapper mapper = new ObjectMapper();
266       System.out.println(json);
267       TypeFactory t = TypeFactory.defaultInstance();
268       list = mapper.readValue(json, t.constructCollectionType(ArrayList.class,clazz));
269
270       return list;
271    }
272    
273    /**
274          * Put.
275          *
276          * @param <T> the generic type
277          * @param t the t
278          * @param sourceID the source ID
279          * @param transId the trans id
280          * @param path the path
281          * @throws AAIException the AAI exception
282          */
283         public <T> void Put(T t, String sourceID,  String transId,  String path) throws AAIException {
284                 Put( t, sourceID, transId, path, false, AAIConstants.AAI_RESOURCES_PORT);
285         }
286            
287         /**
288          * Put.
289          *
290          * @param <T> the generic type
291          * @param t the t
292          * @param sourceID the source ID
293          * @param transId the trans id
294          * @param path the path
295          * @throws AAIException the AAI exception
296          */
297         public <T> void Put(T t, String sourceID,  String transId,  String path, boolean oldserver) throws AAIException {
298                 Put( t, sourceID, transId, path, oldserver, AAIConstants.AAI_RESOURCES_PORT);
299         }
300
301         /**
302          * Put.
303          *
304          * @param <T> the generic type
305          * @param t the t
306          * @param sourceID the source ID
307          * @param transId the trans id
308          * @param path the path
309          * @param oldserver the oldserver
310          * @throws AAIException the AAI exception
311          */
312         public <T> void Put(T t, String sourceID,  String transId,  String path, boolean oldserver, int port) throws AAIException {
313                 String methodName = "Put";
314                 String url="";
315                 transId += ":" + UUID.randomUUID().toString();
316                 
317                 LoggingContext.save();
318                 LoggingContext.partnerName(sourceID);
319                 LoggingContext.targetEntity(TARGET_NAME);
320                 LoggingContext.requestId(transId);
321                 LoggingContext.serviceName(methodName);
322                 LoggingContext.targetServiceName(methodName);
323                 
324                 LOGGER.debug(methodName + " start");            
325
326                 initRestClient();
327                 
328                 if (oldserver)
329                         url = AAIConfig.get(AAIConstants.AAI_OLDSERVER_URL) + path;
330                 else
331                         url = String.format(AAIConstants.AAI_LOCAL_REST, port, AAIConfig.get(AAIConstants.AAI_DEFAULT_API_VERSION_PROP)) + path;
332                 
333                 ClientResponse cres = client.resource(url)
334                  .accept("application/json")
335                  .header("X-TransactionId", transId)
336                  .header("X-FromAppId",  sourceID)
337                  .header("Real-Time", "true")
338                  .type("application/json")
339                  .entity(t)
340                  .put(ClientResponse.class);
341         
342 //                      System.out.println("cres.tostring()="+cres.toString());
343                 
344                 int statuscode = cres.getStatus();
345                 if ( statuscode >= 200 && statuscode <= 299 ) {
346                          LOGGER.debug(methodName+": url=" + url + ", request=" + path);
347                          LoggingContext.restore();
348                  } else {
349                          LoggingContext.restore();
350                          throw new AAIException("AAI_7116", methodName +" with status="+statuscode+", url="+url + ", msg=" + cres.getEntity(String.class));
351                  }                       
352         }
353         
354         public void Delete(String sourceID,  String transId,  String path) throws AAIException {
355                 Delete(sourceID, transId, path, AAIConstants.AAI_RESOURCES_PORT);
356         }
357         /**
358          * Delete.
359          *
360          * @param sourceID the source ID
361          * @param transId the trans id
362          * @param path the path
363          * @throws AAIException the AAI exception
364          */
365         public void Delete(String sourceID,  String transId,  String path, int port) throws AAIException {
366                 String methodName = "Delete";
367                 String url="";
368                 transId += ":" + UUID.randomUUID().toString();
369                 
370                 LoggingContext.save();
371                 LoggingContext.partnerName(sourceID);
372                 LoggingContext.targetEntity(TARGET_NAME);
373                 LoggingContext.requestId(transId);
374                 LoggingContext.serviceName(methodName);
375                 LoggingContext.targetServiceName(methodName);
376                 
377                 LOGGER.debug(methodName + " start");
378                 
379                 initRestClient();
380                 String request = "{}";
381                 url = String.format(AAIConstants.AAI_LOCAL_REST, port, AAIConfig.get(AAIConstants.AAI_DEFAULT_API_VERSION_PROP)) + path;
382                 ClientResponse cres = client.resource(url)
383                          .accept("application/json")
384                          .header("X-TransactionId", transId)
385                          .header("X-FromAppId",  sourceID)
386                          .header("Real-Time", "true")
387                          .type("application/json")
388                          .entity(request)
389                          .delete(ClientResponse.class);
390                         
391                 if (cres.getStatus() == 404) { // resource not found
392                         LOGGER.info("Resource does not exist...: " + cres.getStatus()
393                                         + ":" + cres.getEntity(String.class));
394                         LoggingContext.restore();
395                 } else if (cres.getStatus() == 200  || cres.getStatus() == 204){
396                         LOGGER.info("Resource " + url + " deleted");
397                         LoggingContext.restore();
398                 } else {
399                         LOGGER.error("Deleting Resource failed: " + cres.getStatus()
400                                 + ":" + cres.getEntity(String.class));
401                         LoggingContext.restore();
402             throw new AAIException("AAI_7116", "Error during DELETE");
403                 }
404         }
405         
406          public <T> String Post(T t, String sourceID,  String transId,  String path) throws Exception {          
407                  return Post(t, sourceID,  transId,  path, AAIConfig.get(AAIConstants.AAI_DEFAULT_API_VERSION_PROP));   
408          }
409     /**
410      * Post.
411      *
412      * @param <T> the generic type
413      * @param t the t
414      * @param sourceID the source ID
415      * @param transId the trans id
416      * @param path the path
417      * @param apiVersion the apiVersion
418      * @return the string
419      * @throws Exception the exception
420      */
421     public <T> String Post(T t, String sourceID,  String transId,  String path, String apiVersion) throws Exception {
422         String methodName = "Post";
423         String url="";
424         transId += ":" + UUID.randomUUID().toString();
425         
426         LoggingContext.save();
427         LoggingContext.partnerName(sourceID);
428                 LoggingContext.targetEntity(TARGET_NAME);
429                 LoggingContext.requestId(transId);
430                 LoggingContext.serviceName(methodName);
431                 LoggingContext.targetServiceName(methodName);
432                 
433         LOGGER.debug(methodName + " start");        
434         
435         try {
436             
437             initRestClient();    
438             url = AAIConfig.get(AAIConstants.AAI_SERVER_URL_BASE) + apiVersion + "/" + path;
439             
440             ClientResponse cres = client.resource(url)
441                  .accept("application/json")
442                  .header("X-TransactionId", transId)
443                  .header("X-FromAppId",  sourceID)
444                  .header("Real-Time", "true")
445                  .type("application/json")
446                  .entity(t)
447                  .post(ClientResponse.class);
448             
449             int statuscode = cres.getStatus();
450                 if ( statuscode >= 200 && statuscode <= 299 ) {    
451                  LOGGER.debug(methodName + "REST api POST was successful!");
452                  return cres.getEntity(String.class);
453              } else {
454                  throw new AAIException("AAI_7116", methodName +" with status="+statuscode+", url="+url + ", msg=" + cres.getEntity(String.class));
455              }    
456         
457         } catch (AAIException e) {
458             throw new AAIException("AAI_7116", methodName + " with url="+url+ ", Exception: " + e.toString());
459         } catch (Exception e)
460         {
461             throw new AAIException("AAI_7116", methodName + " with url="+url+ ", Exception: " + e.toString());
462         
463         }
464         finally {
465                 LoggingContext.restore();
466         }
467     }
468
469         
470     /**
471      * Gets the single instance of RestController.
472      *
473      * @param <T> the generic type
474      * @param clazz the clazz
475      * @return single instance of RestController
476      * @throws IllegalAccessException the illegal access exception
477      * @throws InstantiationException the instantiation exception
478      */
479     public <T> T getInstance(Class<T> clazz) throws IllegalAccessException, InstantiationException
480         {
481                 return clazz.newInstance();
482         } 
483         
484     /**
485      * Does resource exist.
486      *
487      * @param <T> the generic type
488      * @param resourcePath the resource path
489      * @param resourceClassName the resource class name
490      * @param fromAppId the from app id
491      * @param transId the trans id
492      * @return the t
493      */
494     /*
495      *     DoesResourceExist
496      *     
497      *     To check whether a resource exist or get a copy of the existing version of the resource
498      *  
499      *       Resourcepath: should contain the qualified resource path (including encoded unique key identifier value),
500      *       resourceClassName: is the canonical name of the resource class name, 
501      *       fromAppId:
502      *       transId:
503      *       
504      *     Will return null (if the resource doesn’t exist)  (or) 
505      *     Will return the specified resource from the Graph.
506      *     
507      *     Example:
508      *     LogicalLink llink = new LogicalLink();
509      *     String resourceClassName = llink.getClass().getCanonicalName();
510      *     llink = RestController.DoesResourceExist("network/logical-links/logical-link/" + <encoded-link-name>, resourceClassName, fromAppId, transId);
511    */
512         public <T> T DoesResourceExist(String resourcePath, String resourceClassName, String fromAppId, String transId) {
513                                         
514                 try {
515                         
516                         RestObject<T> restObj = new RestObject<T>();
517                         @SuppressWarnings("unchecked")
518                         T resourceObj = (T)getInstance(Class.forName(resourceClassName));
519                         restObj.set(resourceObj);
520                         Get(resourceObj, fromAppId, transId, resourcePath, restObj, false, AAIConstants.AAI_RESOURCES_PORT);
521                         
522                         resourceObj = restObj.get();
523                         if (resourceObj != null)
524                           return resourceObj;
525
526                 } catch (AAIException e) {
527                         
528                 } catch (ClientHandlerException che) {
529                         
530                 }catch (Exception e) {
531                         
532                 }
533                 
534                 return null;
535         }
536         
537         /**
538          * Patch.
539          *
540          * @param <T> the generic type
541          * @param sourceID the source ID
542          * @param transId the trans id
543          * @param path the path
544          * @throws AAIException the AAI exception
545          */
546         public <T> void Patch(T t, String sourceID,  String transId,  String path) throws AAIException {
547                     String methodName = "Patch";
548                 String url="";
549                 transId += ":" + UUID.randomUUID().toString();
550                 
551                 LoggingContext.save();
552                 LoggingContext.partnerName(sourceID);
553                         LoggingContext.targetEntity(TARGET_NAME);
554                         LoggingContext.requestId(transId);
555                         LoggingContext.serviceName(methodName);
556                         LoggingContext.targetServiceName(methodName);
557
558
559                         int numRetries = 5;
560                         ClientResponse cres = null;
561                         int statusCode = -1;
562
563                         try {
564                                 url = String.format(AAIConstants.AAI_LOCAL_REST, AAIConstants.AAI_RESOURCES_PORT, AAIConfig.get(AAIConstants.AAI_DEFAULT_API_VERSION_PROP)) + path;
565                             
566                     initRestClient();    
567                                 do {
568                 
569                             cres = client.resource(url)
570                                 .accept("application/json")
571                                 .header("X-TransactionId", transId)
572                                 .header("X-FromAppId", sourceID)
573                                 .header("X-HTTP-Method-Override", "PATCH")
574                                 .type("application/merge-patch+json")
575                                 .entity(t)
576                                 .post(ClientResponse.class);
577                 
578                             statusCode = cres.getStatus();
579                 
580                             if ( statusCode >= 200 && statusCode <= 299 ) {
581                                 LOGGER.debug(methodName + "REST api PATCH was successful!");
582                                 return;
583                             } else {
584                                 LOGGER.debug(methodName +  "Unable to make the patch request to url "  + url + " so retrying");
585                             }
586                 
587                             numRetries--;
588                 
589                                 } while(numRetries >= 0);
590                                 
591                                 LOGGER.debug(methodName +  "Unable to make the patch request to url "  + url + " even after trying = " + numRetries + " times.");
592                                 throw new AAIException("AAI_7116", methodName +" with status="+statusCode+", url="+url + ", msg=" + cres.getEntity(String.class));
593                  
594                         } catch (AAIException e) {
595                         throw new AAIException("AAI_7116", methodName + " with url="+url+ ", Exception: " + e.toString());
596                     } catch (Exception e)
597                     {
598                         throw new AAIException("AAI_7116", methodName + " with url="+url+ ", Exception: " + e.toString());
599                     
600                     }
601                     finally {
602                         LoggingContext.restore();
603                     }
604
605         }
606 }