Merge "update operation status for E2Edelete"
[so.git] / mso-api-handlers / mso-api-handler-infra / src / main / java / org / openecomp / mso / apihandlerinfra / E2EServiceInstances.java
1 /*-
2  * ============LICENSE_START=======================================================
3  * ONAP - SO
4  * ================================================================================
5  * Copyright (C) 2017 Huawei Technologies Co., Ltd. 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
21 package org.openecomp.mso.apihandlerinfra;
22
23 import java.io.IOException;
24 import java.sql.Timestamp;
25 import java.util.ArrayList;
26 import java.util.HashMap;
27 import java.util.List;
28 import java.util.Map;
29
30 import javax.ws.rs.Consumes;
31 import javax.ws.rs.DELETE;
32 import javax.ws.rs.GET;
33 import javax.ws.rs.POST;
34 import javax.ws.rs.Path;
35 import javax.ws.rs.PathParam;
36 import javax.ws.rs.Produces;
37 import javax.ws.rs.core.MediaType;
38 import javax.ws.rs.core.Response;
39
40 import org.apache.http.HttpResponse;
41 import org.apache.http.HttpStatus;
42 import org.codehaus.jackson.map.ObjectMapper;
43 import org.hibernate.Session;
44 import org.json.JSONObject;
45 import org.openecomp.mso.apihandler.common.ErrorNumbers;
46 import org.openecomp.mso.apihandler.common.RequestClient;
47 import org.openecomp.mso.apihandler.common.RequestClientFactory;
48 import org.openecomp.mso.apihandler.common.ResponseHandler;
49 import org.openecomp.mso.apihandlerinfra.Messages;
50 import org.openecomp.mso.apihandlerinfra.MsoException;
51 import org.openecomp.mso.apihandlerinfra.MsoRequest;
52 import org.openecomp.mso.apihandlerinfra.e2eserviceinstancebeans.DelE2ESvcResp;
53 import org.openecomp.mso.apihandlerinfra.e2eserviceinstancebeans.E2EServiceInstanceDeleteRequest;
54 import org.openecomp.mso.apihandlerinfra.e2eserviceinstancebeans.E2EServiceInstanceRequest;
55 import org.openecomp.mso.apihandlerinfra.e2eserviceinstancebeans.E2EUserParam;
56 import org.openecomp.mso.apihandlerinfra.e2eserviceinstancebeans.GetE2EServiceInstanceResponse;
57 import org.openecomp.mso.apihandlerinfra.serviceinstancebeans.ModelInfo;
58 import org.openecomp.mso.apihandlerinfra.serviceinstancebeans.RequestDetails;
59 import org.openecomp.mso.apihandlerinfra.serviceinstancebeans.RequestInfo;
60 import org.openecomp.mso.apihandlerinfra.serviceinstancebeans.RequestParameters;
61 import org.openecomp.mso.apihandlerinfra.serviceinstancebeans.ServiceInstancesRequest;
62 import org.openecomp.mso.apihandlerinfra.serviceinstancebeans.SubscriberInfo;
63 import org.openecomp.mso.db.AbstractSessionFactoryManager;
64 import org.openecomp.mso.db.catalog.CatalogDatabase;
65 import org.openecomp.mso.db.catalog.beans.Service;
66 import org.openecomp.mso.db.catalog.beans.ServiceRecipe;
67 import org.openecomp.mso.logger.MessageEnum;
68 import org.openecomp.mso.logger.MsoAlarmLogger;
69 import org.openecomp.mso.logger.MsoLogger;
70 import org.openecomp.mso.requestsdb.InfraActiveRequests;
71 import org.openecomp.mso.requestsdb.OperationStatus;
72 import org.openecomp.mso.requestsdb.RequestsDatabase;
73 import org.openecomp.mso.requestsdb.RequestsDbSessionFactoryManager;
74 import org.openecomp.mso.utils.UUIDChecker;
75
76 import com.wordnik.swagger.annotations.Api;
77 import com.wordnik.swagger.annotations.ApiOperation;
78
79 @Path("/e2eServiceInstances")
80 @Api(value = "/e2eServiceInstances", description = "API Requests for E2E Service Instances")
81 public class E2EServiceInstances {
82
83         private HashMap<String, String> instanceIdMap = new HashMap<>();
84         private static MsoLogger msoLogger = MsoLogger.getMsoLogger(MsoLogger.Catalog.APIH);
85         private static MsoAlarmLogger alarmLogger = new MsoAlarmLogger();
86         public static final String MSO_PROP_APIHANDLER_INFRA = "MSO_PROP_APIHANDLER_INFRA";
87         private ServiceInstancesRequest sir = null;
88         
89         public static final String END_OF_THE_TRANSACTION = "End of the transaction, the final response is: ";
90         public static final String EXCEPTION_CREATING_DB_RECORD = "Exception while creating record in DB";
91         public static final String EXCEPTION_COMMUNICATE_BPMN_ENGINE = "Exception while communicate with BPMN engine";
92
93         /**
94          * POST Requests for E2E Service create Instance on a version provided
95          */
96
97         @POST
98         @Path("/{version:[vV][3-5]}")
99         @Consumes(MediaType.APPLICATION_JSON)
100         @Produces(MediaType.APPLICATION_JSON)
101         @ApiOperation(value = "Create a E2E Service Instance on a version provided", response = Response.class)
102         public Response createE2EServiceInstance(String request, @PathParam("version") String version) {
103
104                 return processE2EserviceInstances(request, Action.createInstance, null, version);
105         }
106
107         /**
108          * DELETE Requests for E2E Service delete Instance on a specified version
109          * and serviceId
110          */
111
112         @DELETE
113         @Path("/{version:[vV][3-5]}/{serviceId}")
114         @Consumes(MediaType.APPLICATION_JSON)
115         @Produces(MediaType.APPLICATION_JSON)
116         @ApiOperation(value = "Delete E2E Service Instance on a specified version and serviceId", response = Response.class)
117         public Response deleteE2EServiceInstance(String request, @PathParam("version") String version,
118                         @PathParam("serviceId") String serviceId) {
119
120                 instanceIdMap.put("serviceId", serviceId);
121
122                 return deleteE2EserviceInstances(request, Action.deleteInstance, instanceIdMap, version);
123         }
124         
125         @GET
126         @Path("/{version:[vV][3-5]}/{serviceId}/operations/{operationId}")
127         @ApiOperation(value = "Find e2eServiceInstances Requests for a given serviceId and operationId", response = Response.class)
128         @Produces(MediaType.APPLICATION_JSON)
129         public Response getE2EServiceInstances(@PathParam("serviceId") String serviceId,
130                         @PathParam("version") String version, @PathParam("operationId") String operationId) {
131                 RequestsDatabase requestsDB = RequestsDatabase.getInstance();
132                 
133                 GetE2EServiceInstanceResponse e2eServiceResponse = new GetE2EServiceInstanceResponse();
134
135                 MsoRequest msoRequest = new MsoRequest(serviceId);
136
137                 long startTime = System.currentTimeMillis();
138
139                 OperationStatus operationStatus = null;
140
141                 try {
142                         operationStatus = requestsDB.getOperationStatus(serviceId, operationId);
143
144                 } catch (Exception e) {
145                         msoLogger.error(MessageEnum.APIH_DB_ACCESS_EXC, MSO_PROP_APIHANDLER_INFRA, "", "",
146                                         MsoLogger.ErrorCode.AvailabilityError,
147                                         "Exception while communciate with Request DB - Infra Request Lookup", e);
148                         msoRequest.setStatus(org.openecomp.mso.apihandlerinfra.vnfbeans.RequestStatusType.FAILED);
149                         Response response = msoRequest.buildServiceErrorResponse(HttpStatus.SC_NOT_FOUND,
150                                         MsoException.ServiceException, e.getMessage(), ErrorNumbers.NO_COMMUNICATION_TO_REQUESTS_DB, null);
151                         alarmLogger.sendAlarm("MsoDatabaseAccessError", MsoAlarmLogger.CRITICAL,
152                                         Messages.errors.get(ErrorNumbers.NO_COMMUNICATION_TO_REQUESTS_DB));
153                         msoLogger.recordAuditEvent(startTime, MsoLogger.StatusCode.ERROR, MsoLogger.ResponseCode.DBAccessError,
154                                         "Exception while communciate with Request DB");
155                         msoLogger.debug("End of the transaction, the final response is: " + (String) response.getEntity());
156                         return response;
157
158                 }
159
160                 if (operationStatus == null) {
161                         Response resp = msoRequest.buildServiceErrorResponse(HttpStatus.SC_NO_CONTENT,
162                                         MsoException.ServiceException, "E2E serviceId " + serviceId + " is not found in DB",
163                                         ErrorNumbers.SVC_DETAILED_SERVICE_ERROR, null);
164                         msoLogger.error(MessageEnum.APIH_BPEL_COMMUNICATE_ERROR, MSO_PROP_APIHANDLER_INFRA, "", "",
165                                         MsoLogger.ErrorCode.BusinessProcesssError,
166                                         "Null response from RequestDB when searching by serviceId");
167                         msoLogger.recordAuditEvent(startTime, MsoLogger.StatusCode.ERROR, MsoLogger.ResponseCode.DataNotFound,
168                                         "Null response from RequestDB when searching by serviceId");
169                         msoLogger.debug("End of the transaction, the final response is: " + (String) resp.getEntity());
170                         return resp;
171
172                 }
173
174                 e2eServiceResponse.setE2eRequest(operationStatus);
175
176                 return Response.status(200).entity(e2eServiceResponse).build();
177         }
178
179         private Response deleteE2EserviceInstances(String requestJSON, Action action,
180                         HashMap<String, String> instanceIdMap, String version) {
181                 //TODO should be a new one or the same service instance Id
182                 String requestId = instanceIdMap.get("serviceId");
183                 long startTime = System.currentTimeMillis();
184                 msoLogger.debug("requestId is: " + requestId);
185                 E2EServiceInstanceDeleteRequest e2eDelReq = null;
186
187                 MsoRequest msoRequest = new MsoRequest(requestId);
188                 
189                 ObjectMapper mapper = new ObjectMapper();
190                 try {
191                         e2eDelReq = mapper.readValue(requestJSON, E2EServiceInstanceDeleteRequest.class);
192
193                 } catch (Exception e) {
194
195                         msoLogger.debug("Mapping of request to JSON object failed : ", e);
196                         Response response = msoRequest.buildServiceErrorResponse(HttpStatus.SC_BAD_REQUEST,
197                                         MsoException.ServiceException, "Mapping of request to JSON object failed.  " + e.getMessage(),
198                                         ErrorNumbers.SVC_BAD_PARAMETER, null);
199                         msoLogger.error(MessageEnum.APIH_REQUEST_VALIDATION_ERROR, MSO_PROP_APIHANDLER_INFRA, "", "",
200                                         MsoLogger.ErrorCode.SchemaError, requestJSON, e);
201                         msoLogger.recordAuditEvent(startTime, MsoLogger.StatusCode.ERROR, MsoLogger.ResponseCode.SchemaError,
202                                         "Mapping of request to JSON object failed");
203                         msoLogger.debug("End of the transaction, the final response is: " + (String) response.getEntity());
204                         createOperationStatusRecordForError(action, requestId);
205                         return response;
206                 }
207                 
208                 CatalogDatabase db = null;
209                 RecipeLookupResult recipeLookupResult = null;
210                 try {
211                         db = CatalogDatabase.getInstance();
212                         recipeLookupResult = getServiceInstanceOrchestrationURI(db, action);
213                 } catch (Exception e) {
214                         msoLogger.error(MessageEnum.APIH_DB_ACCESS_EXC, MSO_PROP_APIHANDLER_INFRA, "", "",
215                                         MsoLogger.ErrorCode.AvailabilityError, "Exception while communciate with Catalog DB", e);
216                         msoRequest.setStatus(org.openecomp.mso.apihandlerinfra.vnfbeans.RequestStatusType.FAILED);
217                         Response response = msoRequest.buildServiceErrorResponse(HttpStatus.SC_NOT_FOUND,
218                                         MsoException.ServiceException, "No communication to catalog DB " + e.getMessage(),
219                                         ErrorNumbers.SVC_NO_SERVER_RESOURCES, null);
220                         alarmLogger.sendAlarm("MsoDatabaseAccessError", MsoAlarmLogger.CRITICAL,
221                                         Messages.errors.get(ErrorNumbers.NO_COMMUNICATION_TO_CATALOG_DB));
222                         msoRequest.createRequestRecord(Status.FAILED, action);
223                         msoLogger.recordAuditEvent(startTime, MsoLogger.StatusCode.ERROR, MsoLogger.ResponseCode.DBAccessError,
224                                         "Exception while communciate with DB");
225                         msoLogger.debug(END_OF_THE_TRANSACTION + (String) response.getEntity());
226                         return response;
227                 } finally {
228                         closeCatalogDB(db);
229                 }
230                 if (recipeLookupResult == null) {
231                         msoLogger.error(MessageEnum.APIH_DB_ATTRIBUTE_NOT_FOUND, MSO_PROP_APIHANDLER_INFRA, "", "",
232                                         MsoLogger.ErrorCode.DataError, "No recipe found in DB");
233                         msoRequest.setStatus(org.openecomp.mso.apihandlerinfra.vnfbeans.RequestStatusType.FAILED);
234                         Response response = msoRequest.buildServiceErrorResponse(HttpStatus.SC_NOT_FOUND,
235                                         MsoException.ServiceException, "Recipe does not exist in catalog DB",
236                                         ErrorNumbers.SVC_GENERAL_SERVICE_ERROR, null);
237                         msoRequest.createRequestRecord(Status.FAILED, action);
238                         msoLogger.recordAuditEvent(startTime, MsoLogger.StatusCode.ERROR, MsoLogger.ResponseCode.DataNotFound,
239                                         "No recipe found in DB");
240                         msoLogger.debug(END_OF_THE_TRANSACTION + (String) response.getEntity());
241                         createOperationStatusRecordForError(action, requestId);
242                         return response;
243                 }
244
245                 
246                 RequestClient requestClient = null;
247                 HttpResponse response = null;
248
249                 long subStartTime = System.currentTimeMillis();
250                 //String sirRequestJson = mapReqJsonToSvcInstReq(e2eSir, requestJSON);
251
252                 try {
253                         requestClient = RequestClientFactory.getRequestClient(recipeLookupResult.getOrchestrationURI(),
254                                         MsoPropertiesUtils.loadMsoProperties());
255
256                         // Capture audit event
257                         msoLogger.debug("MSO API Handler Posting call to BPEL engine for url: " + requestClient.getUrl());
258             String serviceId = instanceIdMap.get("serviceId");
259             String serviceInstanceType = e2eDelReq.getServiceType();
260                         response = requestClient.post(requestId, false, recipeLookupResult.getRecipeTimeout(), action.name(),
261                                         serviceId, null, null, null, null, serviceInstanceType, null, null, null, requestJSON);
262
263                         msoLogger.recordMetricEvent(subStartTime, MsoLogger.StatusCode.COMPLETE, MsoLogger.ResponseCode.Suc,
264                                         "Successfully received response from BPMN engine", "BPMN", recipeLookupResult.getOrchestrationURI(),
265                                         null);
266                 } catch (Exception e) {
267                         msoLogger.recordMetricEvent(subStartTime, MsoLogger.StatusCode.ERROR,
268                                         MsoLogger.ResponseCode.CommunicationError, "Exception while communicate with BPMN engine", "BPMN",
269                                         recipeLookupResult.getOrchestrationURI(), null);
270                         Response resp = msoRequest.buildServiceErrorResponse(HttpStatus.SC_BAD_GATEWAY,
271                                         MsoException.ServiceException, "Failed calling bpmn " + e.getMessage(),
272                                         ErrorNumbers.SVC_NO_SERVER_RESOURCES, null);
273                         alarmLogger.sendAlarm("MsoConfigurationError", MsoAlarmLogger.CRITICAL,
274                                         Messages.errors.get(ErrorNumbers.NO_COMMUNICATION_TO_BPEL));
275                         msoLogger.error(MessageEnum.APIH_BPEL_COMMUNICATE_ERROR, MSO_PROP_APIHANDLER_INFRA, "", "",
276                                         MsoLogger.ErrorCode.AvailabilityError, "Exception while communicate with BPMN engine");
277                         msoLogger.recordAuditEvent(startTime, MsoLogger.StatusCode.ERROR, MsoLogger.ResponseCode.CommunicationError,
278                                         "Exception while communicate with BPMN engine");
279                         msoLogger.debug("End of the transaction, the final response is: " + (String) resp.getEntity());
280                         createOperationStatusRecordForError(action, requestId);
281                         return resp;
282                 }
283
284                 if (response == null) {
285                         Response resp = msoRequest.buildServiceErrorResponse(HttpStatus.SC_BAD_GATEWAY,
286                                         MsoException.ServiceException, "bpelResponse is null", ErrorNumbers.SVC_NO_SERVER_RESOURCES, null);
287                         msoLogger.error(MessageEnum.APIH_BPEL_COMMUNICATE_ERROR, MSO_PROP_APIHANDLER_INFRA, "", "",
288                                         MsoLogger.ErrorCode.BusinessProcesssError, "Null response from BPEL");
289                         msoLogger.recordAuditEvent(startTime, MsoLogger.StatusCode.ERROR, MsoLogger.ResponseCode.InternalError,
290                                         "Null response from BPMN");
291                         msoLogger.debug(END_OF_THE_TRANSACTION + (String) resp.getEntity());
292                         createOperationStatusRecordForError(action, requestId);
293                         return resp;
294                 }
295
296                 ResponseHandler respHandler = new ResponseHandler(response, requestClient.getType());
297                 int bpelStatus = respHandler.getStatus();
298
299                 return beplStatusUpdate(requestId, startTime, msoRequest, requestClient, respHandler, bpelStatus, action);
300         }
301
302         private Response processE2EserviceInstances(String requestJSON, Action action,
303                         HashMap<String, String> instanceIdMap, String version) {
304
305                 String requestId = UUIDChecker.generateUUID(msoLogger);
306                 long startTime = System.currentTimeMillis();
307                 msoLogger.debug("requestId is: " + requestId);
308                 E2EServiceInstanceRequest e2eSir = null;
309
310                 MsoRequest msoRequest = new MsoRequest(requestId);
311                 ObjectMapper mapper = new ObjectMapper();
312                 try {
313                         e2eSir = mapper.readValue(requestJSON, E2EServiceInstanceRequest.class);
314
315                 } catch (Exception e) {
316           //TODO update the service name
317           this.createOperationStatusRecordForError(action, requestId);
318                   
319                         msoLogger.debug("Mapping of request to JSON object failed : ", e);
320                         Response response = msoRequest.buildServiceErrorResponse(HttpStatus.SC_BAD_REQUEST,
321                                         MsoException.ServiceException, "Mapping of request to JSON object failed.  " + e.getMessage(),
322                                         ErrorNumbers.SVC_BAD_PARAMETER, null);
323                         msoLogger.error(MessageEnum.APIH_REQUEST_VALIDATION_ERROR, MSO_PROP_APIHANDLER_INFRA, "", "",
324                                         MsoLogger.ErrorCode.SchemaError, requestJSON, e);
325                         msoLogger.recordAuditEvent(startTime, MsoLogger.StatusCode.ERROR, MsoLogger.ResponseCode.SchemaError,
326                                         "Mapping of request to JSON object failed");
327                         msoLogger.debug("End of the transaction, the final response is: " + (String) response.getEntity());
328                         return response;
329                 }
330
331                 mapReqJsonToSvcInstReq(e2eSir, requestJSON);
332                 sir.getRequestDetails().getRequestParameters().setaLaCarte(true);
333                 try {
334                         msoRequest.parse(sir, instanceIdMap, action, version);
335                 } catch (Exception e) {
336                         msoLogger.debug("Validation failed: ", e);
337                         Response response = msoRequest.buildServiceErrorResponse(HttpStatus.SC_BAD_REQUEST,
338                                         MsoException.ServiceException, "Error parsing request.  " + e.getMessage(),
339                                         ErrorNumbers.SVC_BAD_PARAMETER, null);
340                         if (msoRequest.getRequestId() != null) {
341                                 msoLogger.debug("Logging failed message to the database");
342                                 //TODO update the service name
343                           this.createOperationStatusRecordForError(action, requestId);
344                         }
345                         msoLogger.error(MessageEnum.APIH_REQUEST_VALIDATION_ERROR, MSO_PROP_APIHANDLER_INFRA, "", "",
346                                         MsoLogger.ErrorCode.SchemaError, requestJSON, e);
347                         msoLogger.recordAuditEvent(startTime, MsoLogger.StatusCode.ERROR, MsoLogger.ResponseCode.SchemaError,
348                                         "Validation of the input request failed");
349                         msoLogger.debug("End of the transaction, the final response is: " + (String) response.getEntity());
350                         return response;
351                 }
352
353                 InfraActiveRequests dup = null;
354 //              String instanceName = sir.getService().getName();
355 //              String requestScope = sir.getService().getParameters().getNodeType();
356                 String instanceName = sir.getRequestDetails().getRequestInfo().getInstanceName();
357                 String requestScope = sir.getRequestDetails().getModelInfo().getModelType().name();
358                 try {
359                         if (!(instanceName == null && "service".equals(requestScope)
360                                         && (action == Action.createInstance || action == Action.activateInstance))) {
361                           //TODO : Need to check for the duplicate record from the operation status,
362                           //TODO : commenting this check for unblocking current testing for now...  induces dead code...
363 //                              dup = (RequestsDatabase.getInstance()).checkInstanceNameDuplicate(instanceIdMap, instanceName,
364 //                                              requestScope);
365                         }
366                 } catch (Exception e) {
367                         msoLogger.error(MessageEnum.APIH_DUPLICATE_CHECK_EXC, MSO_PROP_APIHANDLER_INFRA, "", "",
368                                         MsoLogger.ErrorCode.DataError, "Error during duplicate check ", e);
369
370                         Response response = msoRequest.buildServiceErrorResponse(HttpStatus.SC_INTERNAL_SERVER_ERROR,
371                                         MsoException.ServiceException, e.getMessage(), ErrorNumbers.SVC_DETAILED_SERVICE_ERROR, null);
372
373                         msoLogger.recordAuditEvent(startTime, MsoLogger.StatusCode.ERROR, MsoLogger.ResponseCode.DBAccessError,
374                                         "Error during duplicate check");
375                         msoLogger.debug("End of the transaction, the final response is: " + (String) response.getEntity());
376                         return response;
377                 }
378
379                 if (dup != null) {
380                         // Found the duplicate record. Return the appropriate error.
381                         String instance = null;
382                         if (instanceName != null) {
383                                 instance = instanceName;
384                         } else {
385                                 instance = instanceIdMap.get(requestScope + "InstanceId");
386                         }
387                         String dupMessage = "Error: Locked instance - This " + requestScope + " (" + instance + ") "
388                                         + "already has a request being worked with a status of " + dup.getRequestStatus() + " (RequestId - "
389                                         + dup.getRequestId() + "). The existing request must finish or be cleaned up before proceeding.";
390
391                         Response response = msoRequest.buildServiceErrorResponse(HttpStatus.SC_CONFLICT,
392                                         MsoException.ServiceException, dupMessage, ErrorNumbers.SVC_DETAILED_SERVICE_ERROR, null);
393
394                         msoLogger.warn(MessageEnum.APIH_DUPLICATE_FOUND, dupMessage, "", "", MsoLogger.ErrorCode.SchemaError,
395                                         "Duplicate request - Subscriber already has a request for this service");
396                         
397                         
398                         msoLogger.recordAuditEvent(startTime, MsoLogger.StatusCode.ERROR, MsoLogger.ResponseCode.Conflict,
399                                         dupMessage);
400                         msoLogger.debug("End of the transaction, the final response is: " + (String) response.getEntity());
401                         createOperationStatusRecordForError(action, requestId);
402                         return response;
403                 }
404                 
405                 CatalogDatabase db = null;
406                 RecipeLookupResult recipeLookupResult = null;
407                 try {
408                         db = CatalogDatabase.getInstance();
409                         recipeLookupResult = getServiceInstanceOrchestrationURI(db, action);
410                 } catch (Exception e) {
411                         msoLogger.error(MessageEnum.APIH_DB_ACCESS_EXC, MSO_PROP_APIHANDLER_INFRA, "", "",
412                                         MsoLogger.ErrorCode.AvailabilityError, "Exception while communciate with Catalog DB", e);
413                         msoRequest.setStatus(org.openecomp.mso.apihandlerinfra.vnfbeans.RequestStatusType.FAILED);
414                         Response response = msoRequest.buildServiceErrorResponse(HttpStatus.SC_NOT_FOUND,
415                                         MsoException.ServiceException, "No communication to catalog DB " + e.getMessage(),
416                                         ErrorNumbers.SVC_NO_SERVER_RESOURCES, null);
417                         alarmLogger.sendAlarm("MsoDatabaseAccessError", MsoAlarmLogger.CRITICAL,
418                                         Messages.errors.get(ErrorNumbers.NO_COMMUNICATION_TO_CATALOG_DB));
419                         
420                         msoLogger.recordAuditEvent(startTime, MsoLogger.StatusCode.ERROR, MsoLogger.ResponseCode.DBAccessError,
421                                         "Exception while communciate with DB");
422                         msoLogger.debug(END_OF_THE_TRANSACTION + (String) response.getEntity());
423                         createOperationStatusRecordForError(action, requestId);
424                         return response;
425                 } finally {
426                         closeCatalogDB(db);
427                 }
428
429                 if (recipeLookupResult == null) {
430                         msoLogger.error(MessageEnum.APIH_DB_ATTRIBUTE_NOT_FOUND, MSO_PROP_APIHANDLER_INFRA, "", "",
431                                         MsoLogger.ErrorCode.DataError, "No recipe found in DB");
432                         msoRequest.setStatus(org.openecomp.mso.apihandlerinfra.vnfbeans.RequestStatusType.FAILED);
433                         Response response = msoRequest.buildServiceErrorResponse(HttpStatus.SC_NOT_FOUND,
434                                         MsoException.ServiceException, "Recipe does not exist in catalog DB",
435                                         ErrorNumbers.SVC_GENERAL_SERVICE_ERROR, null);
436                 
437                         msoLogger.recordAuditEvent(startTime, MsoLogger.StatusCode.ERROR, MsoLogger.ResponseCode.DataNotFound,
438                                         "No recipe found in DB");
439                         msoLogger.debug(END_OF_THE_TRANSACTION + (String) response.getEntity());
440                         createOperationStatusRecordForError(action, requestId);
441                         return response;
442                 }
443
444 //              try {
445 //                      msoRequest.createRequestRecord(Status.PENDING, action);
446 //                      //createOperationStatusRecord(action, requestId);
447 //              } catch (Exception e) {
448 //                      msoLogger.error(MessageEnum.APIH_DB_ACCESS_EXC_REASON, "Exception while creating record in DB", "", "",
449 //                                      MsoLogger.ErrorCode.SchemaError, "Exception while creating record in DB", e);
450 //                      msoRequest.setStatus(org.openecomp.mso.apihandlerinfra.vnfbeans.RequestStatusType.FAILED);
451 //                      Response response = msoRequest.buildServiceErrorResponse(HttpStatus.SC_INTERNAL_SERVER_ERROR,
452 //                                      MsoException.ServiceException, "Exception while creating record in DB " + e.getMessage(),
453 //                                      ErrorNumbers.SVC_BAD_PARAMETER, null);
454 //                      msoLogger.recordAuditEvent(startTime, MsoLogger.StatusCode.ERROR, MsoLogger.ResponseCode.DBAccessError,
455 //                                      "Exception while creating record in DB");
456 //                      msoLogger.debug("End of the transaction, the final response is: " + (String) response.getEntity());
457 //                      return response;
458 //              }
459
460                 String serviceInstanceType = e2eSir.getService().getParameters().getServiceType();
461
462                 String serviceId = "";
463                 RequestClient requestClient = null;
464                 HttpResponse response = null;
465
466                 long subStartTime = System.currentTimeMillis();
467                 String sirRequestJson = mapReqJsonToSvcInstReq(e2eSir, requestJSON);
468
469                 try {
470                         requestClient = RequestClientFactory.getRequestClient(recipeLookupResult.getOrchestrationURI(),
471                                         MsoPropertiesUtils.loadMsoProperties());
472
473                         // Capture audit event
474                         msoLogger.debug("MSO API Handler Posting call to BPEL engine for url: " + requestClient.getUrl());
475
476                         response = requestClient.post(requestId, false, recipeLookupResult.getRecipeTimeout(), action.name(),
477                                         serviceId, null, null, null, null, serviceInstanceType, null, null, null, sirRequestJson);
478
479                         msoLogger.recordMetricEvent(subStartTime, MsoLogger.StatusCode.COMPLETE, MsoLogger.ResponseCode.Suc,
480                                         "Successfully received response from BPMN engine", "BPMN", recipeLookupResult.getOrchestrationURI(),
481                                         null);
482                 } catch (Exception e) {
483                         msoLogger.recordMetricEvent(subStartTime, MsoLogger.StatusCode.ERROR,
484                                         MsoLogger.ResponseCode.CommunicationError, "Exception while communicate with BPMN engine", "BPMN",
485                                         recipeLookupResult.getOrchestrationURI(), null);
486                         Response resp = msoRequest.buildServiceErrorResponse(HttpStatus.SC_BAD_GATEWAY,
487                                         MsoException.ServiceException, "Failed calling bpmn " + e.getMessage(),
488                                         ErrorNumbers.SVC_NO_SERVER_RESOURCES, null);
489                         alarmLogger.sendAlarm("MsoConfigurationError", MsoAlarmLogger.CRITICAL,
490                                         Messages.errors.get(ErrorNumbers.NO_COMMUNICATION_TO_BPEL));
491                         msoLogger.error(MessageEnum.APIH_BPEL_COMMUNICATE_ERROR, MSO_PROP_APIHANDLER_INFRA, "", "",
492                                         MsoLogger.ErrorCode.AvailabilityError, "Exception while communicate with BPMN engine");
493                         msoLogger.recordAuditEvent(startTime, MsoLogger.StatusCode.ERROR, MsoLogger.ResponseCode.CommunicationError,
494                                         "Exception while communicate with BPMN engine");
495                         msoLogger.debug("End of the transaction, the final response is: " + (String) resp.getEntity());
496                         createOperationStatusRecordForError(action, requestId);
497                         return resp;
498                 }
499
500                 if (response == null) {
501                         Response resp = msoRequest.buildServiceErrorResponse(HttpStatus.SC_BAD_GATEWAY,
502                                         MsoException.ServiceException, "bpelResponse is null", ErrorNumbers.SVC_NO_SERVER_RESOURCES, null);
503                         msoLogger.error(MessageEnum.APIH_BPEL_COMMUNICATE_ERROR, MSO_PROP_APIHANDLER_INFRA, "", "",
504                                         MsoLogger.ErrorCode.BusinessProcesssError, "Null response from BPEL");
505                         msoLogger.recordAuditEvent(startTime, MsoLogger.StatusCode.ERROR, MsoLogger.ResponseCode.InternalError,
506                                         "Null response from BPMN");
507                         msoLogger.debug(END_OF_THE_TRANSACTION + (String) resp.getEntity());
508                         return resp;
509                 }
510
511                 ResponseHandler respHandler = new ResponseHandler(response, requestClient.getType());
512                 int bpelStatus = respHandler.getStatus();
513
514                 return beplStatusUpdate(requestId, startTime, msoRequest, requestClient, respHandler, bpelStatus, action);
515         }
516
517         private void closeCatalogDB(CatalogDatabase db) {
518                 if (db != null) {
519                         db.close();
520                 }
521         }
522
523         private InfraActiveRequests checkForDuplicateRecord(Action action, HashMap<String, String> instanceIdMap,
524                         String instanceName, String requestScope) {
525                 InfraActiveRequests dupValue = null;
526                 if (!(instanceName == null && "service".equals(requestScope)
527                                 && (action == Action.createInstance || action == Action.activateInstance))) {
528                         dupValue = (RequestsDatabase.getInstance()).checkInstanceNameDuplicate(instanceIdMap, instanceName,
529                                         requestScope);
530                 }
531                 return dupValue;
532         }
533
534         private Response duplicateRecordFound(Action action, HashMap<String, String> instanceIdMap, long startTime,
535                         MsoRequest msoRequest, InfraActiveRequests dup, String instanceName, String requestScope) {
536                 String instance = null;
537                 if (instanceName != null) {
538                         instance = instanceName;
539                 } else {
540                         instance = instanceIdMap.get(requestScope + "InstanceId");
541                 }
542                 String dupMessage = "Error: Locked instance - This " + requestScope + " (" + instance + ") "
543                                 + "already has a request being worked with a status of " + dup.getRequestStatus() + " (RequestId - "
544                                 + dup.getRequestId() + "). The existing request must finish or be cleaned up before proceeding.";
545
546                 Response response = msoRequest.buildServiceErrorResponse(HttpStatus.SC_CONFLICT, MsoException.ServiceException,
547                                 dupMessage, ErrorNumbers.SVC_DETAILED_SERVICE_ERROR, null);
548
549                 msoLogger.warn(MessageEnum.APIH_DUPLICATE_FOUND, dupMessage, "", "", MsoLogger.ErrorCode.SchemaError,
550                                 "Duplicate request - Subscriber already has a request for this service");
551                 msoRequest.createRequestRecord(Status.FAILED, action);
552                 msoLogger.recordAuditEvent(startTime, MsoLogger.StatusCode.ERROR, MsoLogger.ResponseCode.Conflict, dupMessage);
553                 msoLogger.debug(END_OF_THE_TRANSACTION + (String) response.getEntity());
554                 return response;
555         }
556
557         private Response beplStatusUpdate(String requestId, long startTime, MsoRequest msoRequest,
558                         RequestClient requestClient, ResponseHandler respHandler, int bpelStatus, Action action) {
559                 // BPMN accepted the request, the request is in progress
560                 if (bpelStatus == HttpStatus.SC_ACCEPTED) {
561                         String camundaJSONResponseBody = respHandler.getResponseBody();
562                         msoLogger.debug("Received from Camunda: " + camundaJSONResponseBody);
563                         
564                         // currently only for delete case we update the status here
565                         if(action.name().equals("DELETE")){
566                                 ObjectMapper mapper = new ObjectMapper();
567                                 try{
568                                         DelE2ESvcResp jo = mapper.readValue(camundaJSONResponseBody, DelE2ESvcResp.class);
569                                         String operationId = jo.getOperationId();
570
571                                         this.createOperationStatusRecord("DELETE", requestId, operationId);
572                                 }
573                                 catch(Exception ex)
574                                 {
575                                         msoLogger.error(MessageEnum.APIH_BPEL_RESPONSE_ERROR, requestClient.getUrl(), "", "",
576                                                         MsoLogger.ErrorCode.BusinessProcesssError,
577                                                         "Response from BPEL engine is failed with HTTP Status=" + bpelStatus);
578                                 }
579                         }
580                         msoLogger.recordAuditEvent(startTime, MsoLogger.StatusCode.COMPLETE, MsoLogger.ResponseCode.Suc,
581                                         "BPMN accepted the request, the request is in progress");
582                         msoLogger.debug(END_OF_THE_TRANSACTION + camundaJSONResponseBody);
583                         return Response.status(HttpStatus.SC_ACCEPTED).entity(camundaJSONResponseBody).build();
584                 } else {
585                         List<String> variables = new ArrayList<>();
586                         variables.add(bpelStatus + "");
587                         String camundaJSONResponseBody = respHandler.getResponseBody();
588                         if (camundaJSONResponseBody != null && !camundaJSONResponseBody.isEmpty()) {
589                                 Response resp = msoRequest.buildServiceErrorResponse(bpelStatus, MsoException.ServiceException,
590                                                 "Request Failed due to BPEL error with HTTP Status= %1 " + '\n' + camundaJSONResponseBody,
591                                                 ErrorNumbers.SVC_DETAILED_SERVICE_ERROR, variables);
592                                 msoLogger.error(MessageEnum.APIH_BPEL_RESPONSE_ERROR, requestClient.getUrl(), "", "",
593                                                 MsoLogger.ErrorCode.BusinessProcesssError,
594                                                 "Response from BPEL engine is failed with HTTP Status=" + bpelStatus);
595                                 msoLogger.recordAuditEvent(startTime, MsoLogger.StatusCode.ERROR, MsoLogger.ResponseCode.InternalError,
596                                                 "Response from BPMN engine is failed");
597                                 msoLogger.debug(END_OF_THE_TRANSACTION + (String) resp.getEntity());
598                                 return resp;
599                         } else {
600                                 Response resp = msoRequest.buildServiceErrorResponse(bpelStatus, MsoException.ServiceException,
601                                                 "Request Failed due to BPEL error with HTTP Status= %1",
602                                                 ErrorNumbers.SVC_DETAILED_SERVICE_ERROR, variables);
603                                 msoLogger.error(MessageEnum.APIH_BPEL_RESPONSE_ERROR, requestClient.getUrl(), "", "",
604                                                 MsoLogger.ErrorCode.BusinessProcesssError, "Response from BPEL engine is empty");
605                                 msoLogger.recordAuditEvent(startTime, MsoLogger.StatusCode.ERROR, MsoLogger.ResponseCode.InternalError,
606                                                 "Response from BPEL engine is empty");
607                                 msoLogger.debug(END_OF_THE_TRANSACTION + (String) resp.getEntity());
608                                 return resp;
609                         }
610                 }
611         }
612
613         /**
614          * Getting recipes from catalogDb
615          * 
616          * @param db
617          * @param action
618          * @return
619          */
620         private RecipeLookupResult getServiceInstanceOrchestrationURI(CatalogDatabase db, Action action) {
621
622                 RecipeLookupResult recipeLookupResult = getServiceURI(db, action);
623
624                 if (recipeLookupResult != null) {
625                         msoLogger.debug("Orchestration URI is: " + recipeLookupResult.getOrchestrationURI()
626                                         + ", recipe Timeout is: " + Integer.toString(recipeLookupResult.getRecipeTimeout()));
627                 } else {
628                         msoLogger.debug("No matching recipe record found");
629                 }
630                 return recipeLookupResult;
631         }
632
633         /**
634          * Getting recipes from catalogDb
635          * 
636          * @param db
637          * @param action
638          * @return
639          */
640         private RecipeLookupResult getServiceURI(CatalogDatabase db, Action action) {
641
642                 String defaultServiceModelName = "UUI_DEFAULT";
643
644                 Service serviceRecord = db.getServiceByModelName(defaultServiceModelName);
645                 ServiceRecipe recipe = db.getServiceRecipeByModelUUID(serviceRecord.getModelUUID(), action.name());
646
647                 if (recipe == null) {
648                         return null;
649                 }
650                 return new RecipeLookupResult(recipe.getOrchestrationUri(), recipe.getRecipeTimeout());
651
652         }
653
654         /**
655          * Converting E2EServiceInstanceRequest to ServiceInstanceRequest and
656          * passing it to camunda engine.
657          * 
658          * @param e2eSir
659          * @return
660          */
661         private String mapReqJsonToSvcInstReq(E2EServiceInstanceRequest e2eSir, String requestJSON) {
662
663                 sir = new ServiceInstancesRequest();
664
665                 String returnString = null;
666                 RequestDetails requestDetails = new RequestDetails();
667                 ModelInfo modelInfo = new ModelInfo();
668
669                 // ModelInvariantId
670                 modelInfo.setModelInvariantId(e2eSir.getService().getServiceDefId());
671
672                 // modelNameVersionId
673                 modelInfo.setModelNameVersionId(e2eSir.getService().getTemplateId());
674
675 //              String modelInfoValue = e2eSir.getService().getParameters().getNodeTemplateName();
676 //              String[] arrayOfInfo = modelInfoValue.split(":");
677 //              String modelName = arrayOfInfo[0];
678 //              String modelVersion = arrayOfInfo[1];
679
680 //      TODO: To ensure, if we dont get the values from the UUI
681         String modelName = "voLTE";
682         String modelVersion = "1.0";
683                 // modelName
684                 modelInfo.setModelName(modelName);
685
686                 // modelVersion
687                 modelInfo.setModelVersion(modelVersion);
688
689                 // modelType
690                 modelInfo.setModelType(ModelType.service);
691
692                 // setting modelInfo to requestDetails
693                 requestDetails.setModelInfo(modelInfo);
694
695                 SubscriberInfo subscriberInfo = new SubscriberInfo();
696
697                 // globalsubscriberId
698                 subscriberInfo.setGlobalSubscriberId(e2eSir.getService().getParameters().getGlobalSubscriberId());
699
700                 // subscriberName
701                 subscriberInfo.setSubscriberName(e2eSir.getService().getParameters().getSubscriberName());
702
703                 // setting subscriberInfo to requestDetails
704                 requestDetails.setSubscriberInfo(subscriberInfo);
705
706                 RequestInfo requestInfo = new RequestInfo();
707
708                 // instanceName
709                 requestInfo.setInstanceName(e2eSir.getService().getName());
710
711                 // source
712                 requestInfo.setSource("UUI");
713
714                 // suppressRollback
715                 requestInfo.setSuppressRollback(true);
716
717                 // setting requestInfo to requestDetails
718                 requestDetails.setRequestInfo(requestInfo);
719
720                 RequestParameters requestParameters = new RequestParameters();
721
722                 // subscriptionServiceType
723                 requestParameters.setSubscriptionServiceType("MOG");
724
725                 // Userparams
726                 List<E2EUserParam> userParams;
727                 //userParams = e2eSir.getService().getParameters().getRequestParameters().getUserParams();
728                 List<Map<String, String>> userParamList = new ArrayList<>();
729                 Map<String, String> userParamMap = new HashMap<>();
730                 //complete json request updated in the camunda
731                 userParamMap.put("UUIRequest", requestJSON);
732                 userParamMap.put("ServiceInstanceName", e2eSir.getService().getName());
733
734 //              Map<String, String> userParamMap3 = null;
735 //              for (E2EUserParam userp : userParams) {
736 //                      userParamMap.put(userp.getName(), userp.getValue());
737 //                      
738 //              }
739                 userParamList.add(userParamMap);
740                 requestParameters.setUserParams(userParamList);
741
742                 // setting requestParameters to requestDetails
743                 requestDetails.setRequestParameters(requestParameters);
744
745                 sir.setRequestDetails(requestDetails);
746
747                 // converting to string
748                 ObjectMapper mapper = new ObjectMapper();
749                 try {
750                         returnString = mapper.writeValueAsString(sir);
751                 } catch (IOException e) {
752                         msoLogger.debug("Exception while converting ServiceInstancesRequest object to string", e);
753                 }
754
755                 return returnString;
756         }
757
758         
759         private void createOperationStatusRecordForError(Action action, String requestId) {
760
761                         AbstractSessionFactoryManager requestsDbSessionFactoryManager = new RequestsDbSessionFactoryManager();
762
763                         Session session = null;
764                         try {
765
766                                 session = requestsDbSessionFactoryManager.getSessionFactory().openSession();
767                                 session.beginTransaction();
768                                 
769                           OperationStatus os = new OperationStatus();
770                           os.setOperation(action.name());
771                           os.setOperationContent("");
772                           os.setOperationId("");
773                           os.setProgress("100");
774                           os.setReason("");
775                           os.setResult("error");
776                           os.setServiceId(requestId);
777                           os.setUserId("");
778                           os.setFinishedAt(new Timestamp(System.currentTimeMillis()));
779                           os.setOperateAt(new Timestamp(System.currentTimeMillis()));
780
781                                 session.save(os);
782                                 session.getTransaction().commit();
783
784                         } catch (Exception e) {
785                                 msoLogger.error (MessageEnum.APIH_DB_INSERT_EXC, "", "", MsoLogger.ErrorCode.DataError, "Exception when creation record request in Operation", e);
786                         } finally {
787                                 if (null != session) {
788                                         session.close();
789                                 }
790                         }
791                 }
792                         private void createOperationStatusRecord(String actionNm, String serviceId, String operationId) {
793
794                                 AbstractSessionFactoryManager requestsDbSessionFactoryManager = new RequestsDbSessionFactoryManager();
795
796                                 Session session = null;
797                                 try {
798
799                                         session = requestsDbSessionFactoryManager.getSessionFactory().openSession();
800                                         session.beginTransaction();
801                                         
802                                   OperationStatus os = new OperationStatus();
803                                   os.setOperation(actionNm);
804                                   os.setOperationContent("");
805                                   os.setOperationId(operationId);
806                                   os.setProgress("0");
807                                   os.setReason("");
808                                   os.setResult("processing");
809                                   os.setServiceId(serviceId);
810                                   //TODO : to be updated...
811                                   os.setUserId("");
812                                   os.setFinishedAt(new Timestamp(System.currentTimeMillis()));
813                                   os.setOperateAt(new Timestamp(System.currentTimeMillis()));
814
815                                         session.save(os);
816                                         session.getTransaction().commit();
817
818                                 } catch (Exception e) {
819                                         msoLogger.error (MessageEnum.APIH_DB_INSERT_EXC, "", "", MsoLogger.ErrorCode.DataError, "Exception when creation record request in Operation", e);
820                                 } finally {
821                                         if (null != session) {
822                                                 session.close();
823                                         }
824                         }
825         }
826 }