Remove unnecessary use of Calendar.getInstance()
[so.git] / bpmn / MSOCommonBPMN / src / main / groovy / org / openecomp / mso / bpmn / common / scripts / PrepareUpdateAAIVfModule.groovy
1 /*-
2  * ============LICENSE_START=======================================================
3  * OPENECOMP - MSO
4  * ================================================================================
5  * Copyright (C) 2017 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
21 package org.openecomp.mso.bpmn.common.scripts
22
23 import org.camunda.bpm.engine.delegate.BpmnError
24 import org.camunda.bpm.engine.runtime.Execution
25 import org.openecomp.mso.bpmn.core.WorkflowException
26 import org.openecomp.mso.rest.APIResponse
27 import org.openecomp.mso.rest.RESTClient
28 import org.openecomp.mso.rest.RESTConfig
29 import org.springframework.web.util.UriUtils
30
31 public class PrepareUpdateAAIVfModule extends VfModuleBase {
32         
33         /**
34          * Initialize the flow's variables.
35          * 
36          * @param execution The flow's execution instance.
37          */
38         public void initProcessVariables(Execution execution) {
39                 execution.setVariable('prefix', 'PUAAIVfMod_')
40                 execution.setVariable('PUAAIVfMod_vnfId', null)
41                 execution.setVariable('PUAAIVfMod_vfModuleId', null)
42                 execution.setVariable('PUAAIVfMod_vnfName', null)
43                 execution.setVariable('PUAAIVfMod_orchestrationStatus', null)
44                 execution.setVariable('PUAAIVfMod_vfModule', null)
45                 execution.setVariable('PUAAIVfMod_vfModuleOK', false)
46                 execution.setVariable('PUAAIVfMod_vfModuleValidationError', null)
47                 execution.setVariable('PUAAIVfMod_getVnfResponseCode' ,null)
48                 execution.setVariable('PUAAIVfMod_getVnfResponse', '')
49                 execution.setVariable('PUAAIVfMod_updateVfModuleResponseCode', null)
50                 execution.setVariable('PUAAIVfMod_updateVfModuleResponse', '')
51                 execution.setVariable('PUAAIVfMod_outVfModule', null)
52         }       
53         
54         /**
55          * Check for missing elements in the received request.
56          * 
57          * @param execution The flow's execution instance.
58          */
59         public void preProcessRequest(Execution execution) {
60                 def method = getClass().getSimpleName() + '.preProcessRequest(' +
61                         'execution=' + execution.getId() +
62                         ')'
63                 def isDebugLogEnabled = execution.getVariable('isDebugLogEnabled')
64                 logDebug('Entered ' + method, isDebugLogEnabled)
65
66                 try {
67                         def xml = execution.getVariable('PrepareUpdateAAIVfModuleRequest')
68                         logDebug('Received request xml:\n' + xml, isDebugLogEnabled)
69                         utils.logAudit("PrepareUpdateAAIVfModule Request  : " + xml)
70                         
71                         initProcessVariables(execution)
72                         
73                         def vnfId = getRequiredNodeText(execution, xml,'vnf-id')
74                         execution.setVariable('PUAAIVfMod_vnfId', vnfId)
75
76                         def vfModuleId = getRequiredNodeText(execution, xml,'vf-module-id')
77                         execution.setVariable('PUAAIVfMod_vfModuleId', vfModuleId)
78                         
79                         def orchestrationStatus = getRequiredNodeText(execution, xml,'orchestration-status')
80                         execution.setVariable('PUAAIVfMod_orchestrationStatus', orchestrationStatus)
81
82                         logDebug('Exited ' + method, isDebugLogEnabled)
83                 } catch (BpmnError e) {
84                         throw e;
85                 } catch (Exception e) {
86                         logError('Caught exception in ' + method, e)
87                         createWorkflowException(execution, 1002, 'Error in preProcessRequest(): ' + e.getMessage())
88                 }
89         }
90         
91         /**
92          * Using the received vnfId, query AAI to get the corresponding Generic VNF.
93          * A 200 response is expected with the Generic VNF in the response body.
94          * 
95          * @param execution The flow's execution instance.
96          */
97         public void getGenericVnf(Execution execution) {
98                 def method = getClass().getSimpleName() + '.getGenericVnf(' +
99                         'execution=' + execution.getId() +
100                         ')'
101                 def isDebugLogEnabled = execution.getVariable('isDebugLogEnabled')
102                 logDebug('Entered ' + method, isDebugLogEnabled)
103
104                 try {
105                         def vnfId = execution.getVariable('PUAAIVfMod_vnfId')
106                         
107                         AaiUtil aaiUriUtil = new AaiUtil(this)
108                         def aai_uri = aaiUriUtil.getNetworkGenericVnfUri(execution)
109                         logDebug('AAI URI is: ' + aai_uri, isDebugLogEnabled)
110                         
111                         String endPoint = execution.getVariable("URN_aai_endpoint") + "${aai_uri}/" + UriUtils.encode(vnfId, "UTF-8") + "?depth=1"
112                                 
113                         utils.logAudit("PrepareUpdateAAIVfModule: AAI endPoint  : " + endPoint)
114                         String basicAuthCred = utils.getBasicAuth(execution.getVariable("URN_aai_auth"),execution.getVariable("URN_mso_msoKey"))
115                         try {
116                                 RESTConfig config = new RESTConfig(endPoint);
117                                 def responseData = ''
118                                 def aaiRequestId = UUID.randomUUID().toString()
119                                 RESTClient client = new RESTClient(config).
120                                         addHeader('X-TransactionId', aaiRequestId).
121                                         addHeader('X-FromAppId', 'MSO').
122                                         addHeader('Content-Type', 'application/xml').
123                                         addHeader('Accept','application/xml');
124                                 if (basicAuthCred != null && !"".equals(basicAuthCred)) {
125                                         client.addAuthorizationHeader(basicAuthCred)
126                                 }
127                                 logDebug('sending GET to AAI endpoint \'' + endPoint + '\'', isDebugLogEnabled)
128                                 APIResponse response = client.httpGet()
129                                 utils.logAudit("PrepareUpdateAAIVfModule: - invoking httpGet to AAI")
130                                 
131                                 responseData = response.getResponseBodyAsString()
132                                 execution.setVariable('PUAAIVfMod_getVnfResponseCode', response.getStatusCode())
133                                 execution.setVariable('PUAAIVfMod_getVnfResponse', responseData)
134                                 
135                                 utils.logAudit("PrepareUpdateAAIVfModule: AAI Response : " + responseData)
136                                 utils.logAudit("PrepareUpdateAAIVfModule: AAI ResponseCode : " + response.getStatusCode())
137                                 
138                                 logDebug('Response code:' + response.getStatusCode(), isDebugLogEnabled)
139                                 logDebug('Response:' + System.lineSeparator() + responseData, isDebugLogEnabled)
140                         } catch (Exception ex) {
141                                 ex.printStackTrace()
142                                 logDebug('Exception occurred while executing AAI GET:' + ex.getMessage(), isDebugLogEnabled)
143                                 execution.setVariable('PUAAIVfMod_getVnfResponseCode', 500)
144                                 execution.setVariable('PUAAIVfMod_getVnfResponse', 'AAI GET Failed:' + ex.getMessage())
145                         }
146                         logDebug('Exited ' + method, isDebugLogEnabled)
147                 } catch (BpmnError e) {
148                         throw e;
149                 } catch (Exception e) {
150                         logError('Caught exception in ' + method, e)
151                         createWorkflowException(execution, 1002, 'Error in getGenericVnf(): ' + e.getMessage())
152                 }
153         }
154         
155         /**
156          * Validate the VF Module.  That is, confirm that a VF Module with the input VF Module ID
157          * exists in the retrieved Generic VNF.  Then, check to make sure that if that VF Module
158          * is the base VF Module and it's not the only VF Module for this Generic VNF, that we're not
159          * attempting to delete it.
160          * 
161          * @param execution The flow's execution instance.
162          */
163         public void validateVfModule(Execution execution) {
164                 def method = getClass().getSimpleName() + '.validateVfModule(' +
165                         'execution=' + execution.getId() +
166                         ')'
167                 def isDebugLogEnabled = execution.getVariable('isDebugLogEnabled')
168                 logDebug('Entered ' + method, isDebugLogEnabled)
169                 
170                 try {
171                         def genericVnf = execution.getVariable('PUAAIVfMod_getVnfResponse')
172                         def vnfId = execution.getVariable('PUAAIVfMod_vnfId')
173                         def vfModuleId = execution.getVariable('PUAAIVfMod_vfModuleId')
174                         def vnfName = getNodeTextForce(genericVnf, 'vnf-name')
175                         execution.setVariable('PUAAIVfMod_vnfName', vnfName)
176                         def VfModule vfModule = findVfModule(genericVnf, vfModuleId)
177                         if (vfModule == null) {
178                                 def String msg = 'VF Module \'' + vfModuleId + '\' does not exist in Generic VNF \'' + vnfId + '\''
179                                 execution.setVariable('PUAAIVfMod_vfModuleValidationError', msg)
180                                 execution.setVariable('PUAAIVfMod_vfModuleOK', false)
181                         } else {
182                                 def orchestrationStatus = execution.getVariable('PUAAIVfMod_orchestrationStatus')
183                                 if (isDebugLogEnabled) {
184                                         logDebug('VF Module \'' + vfModuleId + '\': isBaseVfModule=' + vfModule.isBaseVfModule() +
185                                                 ', isOnlyVfModule=' + vfModule.isOnlyVfModule() + ', new orchestration-status=' + orchestrationStatus,
186                                                 isDebugLogEnabled)
187                                 }
188                                 if (vfModule.isBaseVfModule() && !vfModule.isOnlyVfModule() && orchestrationStatus.equals('pending-delete')) {
189                                         def String msg = 'Orchestration status for VF Module \'' + vfModuleId +
190                                                 '\' cannot be set to \'pending-delete\' since it is the base VF Module and it\'s not the only VF Module in Generic VNF \'' + vnfId + '\''
191                                         execution.setVariable('PUAAIVfMod_vfModuleValidationError', msg)
192                                         execution.setVariable('PUAAIVfMod_vfModuleOK', false)
193                                 } else {
194                                         execution.setVariable('PUAAIVfMod_vfModule', vfModule)
195                                         execution.setVariable('PUAAIVfMod_vfModuleOK', true)
196                                 }
197                         }
198                         
199                         logDebug('Exited ' + method, isDebugLogEnabled)
200                 } catch (BpmnError e) {
201                         throw e;
202                 } catch (Exception e) {
203                         logError('Caught exception in ' + method, e)
204                         createWorkflowException(execution, 1002, 'Error in validateVfModule(): ' + e.getMessage())
205                 }
206         }
207         
208         /**
209          * Construct and send a PUT request to AAI to update the VF Module.
210          * 
211          * @param execution The flow's execution instance.
212          */
213         public void updateVfModule(Execution execution) {
214                 def method = getClass().getSimpleName() + '.updateVfModule(' +
215                         'execution=' + execution.getId() +
216                         ')'
217                 def isDebugLogEnabled = execution.getVariable('isDebugLogEnabled')
218                 logDebug('Entered ' + method, isDebugLogEnabled)
219                 
220                 try {
221                         // Construct payload
222                         def VfModule vfModule = (VfModule) execution.getVariable('PUAAIVfMod_vfModule')
223                         def Node newVfModuleNode = vfModule.getNode().clone()
224                         def orchestrationStatus = execution.getVariable('PUAAIVfMod_orchestrationStatus')
225                         def Node orchestrationStatusNode = utils.getChildNode(newVfModuleNode, 'orchestration-status')
226                         if (orchestrationStatusNode == null) {
227                                 // Node doesn't exist, this should never happen, right?
228                                 new Node(newVfModuleNode, 'orchestration-status', orchestrationStatus)
229                         } else {
230                                 // Node already exists, just give it a new value
231                                 orchestrationStatusNode.setValue(orchestrationStatus)
232                         }
233                         def VfModule newVfModule = new VfModule(newVfModuleNode, vfModule.isOnlyVfModule())
234                         def payload = utils.nodeToString(newVfModuleNode)
235                         
236                         utils.logAudit("VfModule payload : " + payload)
237                         
238                         // Construct endpoint
239                         def vnfId = execution.getVariable('PUAAIVfMod_vnfId')
240                         def vfModuleId = execution.getVariable('PUAAIVfMod_vfModuleId')
241                         
242                         
243                         AaiUtil aaiUriUtil = new AaiUtil(this)
244                         def aai_uri = aaiUriUtil.getNetworkGenericVnfUri(execution)
245                         logDebug('AAI URI is: ' + aai_uri, isDebugLogEnabled)
246                         
247                         String endPoint = execution.getVariable("URN_aai_endpoint") + "${aai_uri}/" + UriUtils.encode(vnfId, "UTF-8") + "/vf-modules/vf-module/" + UriUtils.encode(vfModuleId, "UTF-8")
248                         utils.logAudit("PrepareUpdateAAIVfModule: AAI endPoint  : " + endPoint)
249                         String basicAuthCred = utils.getBasicAuth(execution.getVariable("URN_aai_auth"),execution.getVariable("URN_mso_msoKey"))
250                         try {
251                                 RESTConfig config = new RESTConfig(endPoint);
252                                 def responseData = ''
253                                 def aaiRequestId = UUID.randomUUID().toString()
254                                 RESTClient client = new RESTClient(config).
255                                         addHeader('X-TransactionId', aaiRequestId).
256                                         addHeader('X-FromAppId', 'MSO').
257                                         addHeader('Content-Type', 'application/xml').
258                                         addHeader('Accept','application/xml');
259                                 if (basicAuthCred != null && !"".equals(basicAuthCred)) {
260                                         client.addAuthorizationHeader(basicAuthCred)
261                                 }
262                                 logDebug('sending PUT to AAI endpoint \'' + endPoint + '\'' + 'with payload \n' + payload, isDebugLogEnabled)
263                                 APIResponse response = client.httpPut(payload)
264                                 utils.logAudit("PrepareUpdateAAIVfModule: - invoking httpPut to AAI")
265                                 
266                                 responseData = response.getResponseBodyAsString()
267                                 execution.setVariable('PUAAIVfMod_updateVfModuleResponseCode', response.getStatusCode())
268                                 execution.setVariable('PUAAIVfMod_updateVfModuleResponse', responseData)
269                                 logDebug('Response code:' + response.getStatusCode(), isDebugLogEnabled)
270                                 logDebug('Response:' + System.lineSeparator() + responseData, isDebugLogEnabled)
271                                 utils.logAudit("PrepareUpdateAAIVfModule: AAI Response : " + responseData)
272                                 utils.logAudit("PrepareUpdateAAIVfModule: AAI ResponseCode : " + response.getStatusCode())
273                                 
274                                 // Set the output for this flow.  The updated VfModule is an output, the generic VNF name, and for
275                                 // backward compatibilty, the heat-stack-id is an output
276                                 execution.setVariable('PUAAIVfMod_outVfModule', newVfModule)
277                                 def vnfName = execution.getVariable('PUAAIVfMod_vnfName')
278                                 logDebug('Output PUAAIVfMod_vnfName set to ' + vnfName, isDebugLogEnabled)
279                                 // TODO: Should deprecate use of processKey+Response variable for the response. Will use "WorkflowResponse" instead
280                                 execution.setVariable('WorkflowResponse', newVfModule)
281                                 logDebug('Output PUAAIVfMod_outVfModule set for VF Module Id \'' + newVfModule.getElementText('vf-module-id') + '\'', isDebugLogEnabled)
282                                 def heatStackId = newVfModule.getElementText('heat-stack-id')
283                                 execution.setVariable('PUAAIVfMod_heatStackId', heatStackId)
284                                 logDebug('Output PUAAIVfMod_heatStackId set to \'' + heatStackId + '\'', isDebugLogEnabled)
285                         } catch (Exception ex) {
286                                 ex.printStackTrace()
287                                 logDebug('Exception occurred while executing AAI PUT:' + ex.getMessage(), isDebugLogEnabled)
288                                 execution.setVariable('PUAAIVfMod_updateVfModuleResponseCode', 500)
289                                 execution.setVariable('PUAAIVfMod_updateVfModuleResponse', 'AAI PUT Failed:' + ex.getMessage())
290                         }
291                         logDebug('Exited ' + method, isDebugLogEnabled)
292                 } catch (BpmnError e) {
293                         throw e;
294                 } catch (Exception e) {
295                         logError('Caught exception in ' + method, e)
296                         createWorkflowException(execution, 1002, 'Error in updateVfModule(): ' + e.getMessage())
297                 }                               
298         }
299                 
300         /**
301          * Generates a WorkflowException if the AAI query returns a response code other than 200.
302          * 
303          * @param execution The flow's execution instance.
304          */
305         public void handleVnfNotFound(Execution execution) {
306                 def method = getClass().getSimpleName() + '.handleVnfNotFound(' +
307                         'execution=' + execution.getId() +
308                         ')'
309                 def isDebugLogEnabled = execution.getVariable('isDebugLogEnabled')
310                 logDebug('Entered ' + method, isDebugLogEnabled)
311
312                 logError('Error occurred attempting to query AAI, Response Code ' +
313                         execution.getVariable('PUAAIVfMod_getVnfResponseCode') + ', Error Response ' +
314                         execution.getVariable('PUAAIVfMod_getVnfResponse'))
315                 String processKey = getProcessKey(execution);
316                 WorkflowException exception = new WorkflowException(processKey, 5000,
317                         execution.getVariable('PUAAIVfMod_getVnfResponse'))
318                 execution.setVariable('WorkflowException', exception)
319                 
320                 logDebug('Exited ' + method, isDebugLogEnabled)
321         }
322         
323         /**
324          * Generates a WorkflowException if the VF Module does not pass validation.
325          * 
326          * @param execution The flow's execution instance.
327          */
328         public void handleVfModuleValidationError(Execution execution) {
329                 def method = getClass().getSimpleName() + '.handleVfModuleValidationError(' +
330                         'execution=' + execution.getId() +
331                         ')'
332                 def isDebugLogEnabled = execution.getVariable('isDebugLogEnabled')
333                 logDebug('Entered ' + method, isDebugLogEnabled)
334                                 
335                 def String errorMsg = 'VF Module validation error: ' + execution.getVariable('PUAAIVfMod_vfModuleValidationError')
336                 logError(errorMsg)
337                 utils.logAudit("PrepareUpdateAAIVfModule: Error Message : " + errorMsg)
338                 
339                 String processKey = getProcessKey(execution);
340                 WorkflowException exception = new WorkflowException(processKey, 5000, errorMsg)
341                 execution.setVariable('WorkflowException', exception)
342
343                 logDebug('Exited ' + method, isDebugLogEnabled)
344         }
345         
346         /**
347          * Generates a WorkflowException if updating a VF Module in AAI returns a response code other than 200.
348          * 
349          * @param execution The flow's execution instance.
350          */
351         public void handleUpdateVfModuleFailure(Execution execution) {
352                 def method = getClass().getSimpleName() + '.handleUpdateVfModuleFailure(' +
353                         'execution=' + execution.getId() +
354                         ')'
355                 def isDebugLogEnabled = execution.getVariable('isDebugLogEnabled')
356                 logDebug('Entered ' + method, isDebugLogEnabled)
357
358                 logError('Error occurred attempting to update VF Module in AAI, Response Code ' +
359                         execution.getVariable('PUAAIVfMod_updateVfModuleResponseCode') + ', Error Response ' +
360                         execution.getVariable('PUAAIVfMod_updateVfModuleResponse'))
361                 String processKey = getProcessKey(execution);
362                 WorkflowException exception = new WorkflowException(processKey, 5000,
363                         execution.getVariable('PUAAIVfMod_updateVfModuleResponse'))
364                 execution.setVariable('WorkflowException', exception)
365                 
366                 logDebug('Exited ' + method, isDebugLogEnabled)
367         }
368 }