2 * ============LICENSE_START=======================================================
4 * ================================================================================
5 * Copyright (C) 2017 - 2019 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
11 * http://www.apache.org/licenses/LICENSE-2.0
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=========================================================
21 package org.onap.vid.services;
23 import static org.apache.commons.lang3.ObjectUtils.defaultIfNull;
24 import static org.onap.vid.controller.MsoController.SVC_INSTANCE_ID;
25 import static org.onap.vid.controller.MsoController.VNF_INSTANCE_ID;
26 import static org.onap.vid.utils.KotlinUtilsKt.JACKSON_OBJECT_MAPPER;
28 import com.google.common.collect.ImmutableMap;
29 import java.io.IOException;
30 import java.time.ZonedDateTime;
31 import java.util.ArrayList;
32 import java.util.Calendar;
33 import java.util.Date;
34 import java.util.List;
36 import java.util.UUID;
37 import java.util.function.Consumer;
38 import org.apache.commons.lang3.StringUtils;
39 import org.hibernate.SessionFactory;
40 import org.onap.portalsdk.core.logging.logic.EELFLoggerDelegate;
41 import org.onap.vid.aai.AaiClientInterface;
42 import org.onap.vid.aai.ExceptionWithRequestInfo;
43 import org.onap.vid.aai.model.ResourceType;
44 import org.onap.vid.dal.AsyncInstantiationRepository;
45 import org.onap.vid.exceptions.DbFailureUncheckedException;
46 import org.onap.vid.exceptions.GenericUncheckedException;
47 import org.onap.vid.exceptions.MaxRetriesException;
48 import org.onap.vid.exceptions.OperationNotAllowedException;
49 import org.onap.vid.job.Job;
50 import org.onap.vid.job.Job.JobStatus;
51 import org.onap.vid.job.JobAdapter;
52 import org.onap.vid.job.JobType;
53 import org.onap.vid.job.JobsBrokerService;
54 import org.onap.vid.job.impl.JobSharedData;
55 import org.onap.vid.model.Action;
56 import org.onap.vid.model.NameCounter;
57 import org.onap.vid.model.ResourceInfo;
58 import org.onap.vid.model.ServiceInfo;
59 import org.onap.vid.model.serviceInstantiation.BaseResource;
60 import org.onap.vid.model.serviceInstantiation.ServiceInstantiation;
61 import org.onap.vid.mso.MsoBusinessLogicImpl;
62 import org.onap.vid.mso.MsoProperties;
63 import org.onap.vid.mso.MsoUtil;
64 import org.onap.vid.mso.RestObject;
65 import org.onap.vid.mso.rest.AsyncRequestStatus;
66 import org.onap.vid.mso.rest.RequestStatus;
67 import org.onap.vid.properties.Features;
68 import org.onap.vid.utils.DaoUtils;
69 import org.onap.vid.utils.TimeUtils;
70 import org.springframework.beans.factory.annotation.Autowired;
71 import org.springframework.stereotype.Service;
72 import org.togglz.core.manager.FeatureManager;
75 public class AsyncInstantiationBusinessLogicImpl implements
76 AsyncInstantiationBusinessLogic {
78 private static final int MAX_RETRIES_GETTING_COUNTER = 100;
79 private static final int MAX_RETRIES_GETTING_FREE_NAME_FROM_AAI = 10000;
80 public static final String NAME_FOR_CHECK_AAI_STATUS = "NAME_FOR_CHECK_AAI_STATUS";
82 private final JobAdapter jobAdapter;
84 private final JobsBrokerService jobService;
86 private final CloudOwnerService cloudOwnerService;
88 private final AsyncInstantiationRepository asyncInstantiationRepository;
90 private SessionFactory sessionFactory;
92 private AaiClientInterface aaiClient;
94 private FeatureManager featureManager;
96 private AuditService auditService;
99 private int maxRetriesGettingFreeNameFromAai = MAX_RETRIES_GETTING_FREE_NAME_FROM_AAI;
101 private static final EELFLoggerDelegate logger = EELFLoggerDelegate.getLogger(AsyncInstantiationBusinessLogicImpl.class);
102 private Map<String, JobStatus> msoStateToJobStatusMap = ImmutableMap.<String, JobStatus>builder()
103 .put("inprogress", JobStatus.IN_PROGRESS)
104 .put("failed", JobStatus.FAILED)
105 .put("pause", JobStatus.PAUSE)
106 .put("paused", JobStatus.PAUSE)
107 .put("complete", JobStatus.COMPLETED)
108 .put("pending", JobStatus.IN_PROGRESS)
109 .put("pendingmanualtask", JobStatus.PAUSE)
110 .put("unlocked", JobStatus.IN_PROGRESS)
111 .put("aborted", JobStatus.COMPLETED_WITH_ERRORS)
112 .put("rolledback", JobStatus.FAILED)
113 .put("rolledbacktoassigned", JobStatus.FAILED)
114 .put("rolledbacktocreated", JobStatus.FAILED)
119 public AsyncInstantiationBusinessLogicImpl(JobAdapter jobAdapter,
120 JobsBrokerService jobService,
121 SessionFactory sessionFactory,
122 AaiClientInterface aaiClient,
123 FeatureManager featureManager,
124 CloudOwnerService cloudOwnerService, AsyncInstantiationRepository asyncInstantiationRepository,
125 AuditService auditService) {
126 this.jobAdapter = jobAdapter;
127 this.jobService = jobService;
128 this.sessionFactory = sessionFactory;
129 this.aaiClient = aaiClient;
130 this.featureManager = featureManager;
131 this.cloudOwnerService = cloudOwnerService;
132 this.asyncInstantiationRepository = asyncInstantiationRepository;
133 this.auditService = auditService;
137 public List<ServiceInfo> getAllServicesInfo() {
138 return asyncInstantiationRepository.getAllServicesInfo();
141 JobType getJobType(ServiceInstantiation request) {
142 if (request.isALaCarte()) {
143 switch (defaultIfNull(request.getAction(), Action.Create)) {
145 return JobType.ALaCarteService;
147 return JobType.ALaCarteService;
149 return JobType.ALaCarteServiceInstantiation;
152 return JobType.MacroServiceInstantiation;
157 public List<UUID> pushBulkJob(ServiceInstantiation request, String userId) {
159 List<UUID> uuids = new ArrayList<>();
160 Date createdBulkDate = Calendar.getInstance().getTime();
161 int bulkSize = request.getBulkSize();
162 UUID templateId = UUID.randomUUID();
163 for (int i = 0; i < bulkSize; i++) {
164 ServiceInstantiation requestPerJob = prepareServiceToBeUnique(request);
165 ServiceInfo.ServiceAction serviceAction = getAction(requestPerJob);
166 JobType jobType = getJobType(requestPerJob);
167 final String optimisticUniqueServiceInstanceName = bulkSize>1 ? //only bulk with more than 1 service need to get multiple names
168 getOptimisticUniqueServiceInstanceName(requestPerJob.getInstanceName()) : requestPerJob.getInstanceName();
169 Job job = jobAdapter.createServiceInstantiationJob(jobType, requestPerJob, templateId, userId, request.getTestApi(), optimisticUniqueServiceInstanceName, i);
170 UUID jobId = job.getUuid();
172 asyncInstantiationRepository.saveServiceInfo(createServiceInfo(userId, requestPerJob, jobId, templateId, createdBulkDate, optimisticUniqueServiceInstanceName, serviceAction));
173 asyncInstantiationRepository.addJobRequest(jobId, requestPerJob);
174 auditService.auditVidStatus(jobId, job.getStatus());
182 private ServiceInfo.ServiceAction getAction(ServiceInstantiation request) {
183 if (request.getAction() == null) {
184 //throw new GenericUncheckedException("Required 'action' field not provided at service level");
185 return Action.Create.getServiceAction();
187 return request.getAction().getServiceAction();
191 private String getOptimisticUniqueServiceInstanceName(String instanceName) {
192 return StringUtils.isNotEmpty(instanceName) ? getUniqueNameFromDbOnly(instanceName) : instanceName;
195 protected ServiceInfo createServiceInfo(String userId, ServiceInstantiation serviceInstantiation, UUID jobId, UUID templateId, Date createdBulkDate, String optimisticUniqueServiceInstanceName, ServiceInfo.ServiceAction serviceAction) {
196 return new ServiceInfo(
198 serviceInstantiation.isALaCarte(),
199 Job.JobStatus.PENDING, serviceInstantiation.isPause(), jobId, templateId,
200 serviceInstantiation.getOwningEntityId(),
201 serviceInstantiation.getOwningEntityName(),
202 serviceInstantiation.getProjectName(),
203 serviceInstantiation.getAicZoneId(),
204 serviceInstantiation.getAicZoneName(),
205 serviceInstantiation.getTenantId(),
206 serviceInstantiation.getTenantName(),
207 serviceInstantiation.getLcpCloudRegionId(),
209 serviceInstantiation.getSubscriptionServiceType(),
210 serviceInstantiation.getSubscriberName(),
211 serviceInstantiation.getGlobalSubscriberId(),
212 serviceInstantiation.getInstanceId(),
213 optimisticUniqueServiceInstanceName,
214 serviceInstantiation.getModelInfo().getModelVersionId(),
215 serviceInstantiation.getModelInfo().getModelName(),
216 serviceInstantiation.getModelInfo().getModelVersion(),
223 public boolean isPartOfBulk(UUID jobId) {
227 ServiceInfo serviceInfo = asyncInstantiationRepository.getServiceInfoByJobId(jobId);
228 UUID templateId = serviceInfo.getTemplateId();
229 if (templateId != null) {
230 return getNumberOfJobsInBulk(templateId) > 1;
236 private int getNumberOfJobsInBulk(UUID templateId) {
237 String hqlSelectJob = "from JobDaoImpl where templateId = :templateId";
238 return DaoUtils.tryWithSessionAndTransaction(sessionFactory, session ->
239 session.createQuery(hqlSelectJob)
240 .setText("templateId", templateId.toString())
247 public String getServiceInstantiationPath(ServiceInstantiation serviceInstantiationRequest) {
248 //in case pause flag is true - use assign , else - use create.
249 return MsoBusinessLogicImpl.validateEndpointPath(
250 serviceInstantiationRequest.isPause() ?
251 MsoProperties.MSO_REST_API_SERVICE_INSTANCE_ASSIGN : MsoProperties.MSO_REST_API_SERVICE_INSTANCE_CREATE
256 public String getServiceDeletionPath(String serviceInstanceId) {
257 return MsoBusinessLogicImpl.validateEndpointPath( MsoProperties.MSO_DELETE_OR_UNASSIGN_REST_API_SVC_INSTANCE) + "/" + serviceInstanceId;
261 public String getVnfInstantiationPath(String serviceInstanceId) {
262 return MsoBusinessLogicImpl.validateEndpointPath(MsoProperties.MSO_REST_API_VNF_INSTANCE).
263 replaceFirst(SVC_INSTANCE_ID, serviceInstanceId);
267 public String getVnfDeletionPath(String serviceInstanceId, String vnfInstanceId) {
268 return (MsoBusinessLogicImpl.validateEndpointPath(MsoProperties.MSO_REST_API_VNF_INSTANCE)
269 + '/' + vnfInstanceId)
270 .replaceFirst(SVC_INSTANCE_ID, serviceInstanceId).replaceFirst(VNF_INSTANCE_ID, vnfInstanceId);
274 public String getNetworkInstantiationPath(String serviceInstanceId) {
275 return MsoBusinessLogicImpl.validateEndpointPath(MsoProperties.MSO_REST_API_NETWORK_INSTANCE).
276 replaceFirst(SVC_INSTANCE_ID, serviceInstanceId);
280 public String getVfmoduleInstantiationPath(String serviceInstanceId, String vnfInstanceId) {
281 return MsoBusinessLogicImpl.validateEndpointPath(MsoProperties.MSO_REST_API_VF_MODULE_INSTANCE)
282 .replaceFirst(SVC_INSTANCE_ID, serviceInstanceId)
283 .replaceFirst(VNF_INSTANCE_ID, vnfInstanceId);
287 public String getVfModuleReplacePath(String serviceInstanceId, String vnfInstanceId, String vfModuleInstanceId)
289 return MsoBusinessLogicImpl.validateEndpointPath(MsoProperties.MSO_REST_API_VF_MODULE_INSTANCE)
290 .replaceFirst(SVC_INSTANCE_ID, serviceInstanceId)
291 .replaceFirst(VNF_INSTANCE_ID, vnfInstanceId)
292 + "/" + vfModuleInstanceId
297 public String getVfModuleDeletePath(String serviceInstanceId, String vnfInstanceId, String vfModuleInstanceId) {
298 return MsoBusinessLogicImpl.validateEndpointPath(MsoProperties.MSO_REST_API_VF_MODULE_INSTANCE)
299 .replaceFirst(SVC_INSTANCE_ID, serviceInstanceId)
300 .replaceFirst(VNF_INSTANCE_ID, vnfInstanceId)
301 + "/" + vfModuleInstanceId;
305 public String getVolumeGroupInstantiationPath(String serviceInstanceId, String vnfInstanceId) {
306 return MsoBusinessLogicImpl.validateEndpointPath(MsoProperties.MSO_REST_API_VOLUME_GROUP_INSTANCE)
307 .replaceFirst(SVC_INSTANCE_ID, serviceInstanceId)
308 .replaceFirst(VNF_INSTANCE_ID, vnfInstanceId);
312 public String getInstanceGroupInstantiationPath() {
313 return MsoBusinessLogicImpl.validateEndpointPath(MsoProperties.MSO_REST_API_INSTANCE_GROUP);
317 public String getInstanceGroupMemberInstantiationPath(String vnfGroupInstanceId) {
318 return MsoBusinessLogicImpl.validateEndpointPath(MsoProperties.MSO_REST_API_INSTANCE_GROUP)
319 + '/' + vnfGroupInstanceId + "/addMembers";
323 public String getInstanceGroupDeletePath(String instanceGroupId) {
324 return MsoBusinessLogicImpl.validateEndpointPath(MsoProperties.MSO_REST_API_INSTANCE_GROUP)
325 + '/' + instanceGroupId;
329 public String getInstanceGroupMemberDeletePath(String vnfGroupInstanceId){
330 return MsoBusinessLogicImpl.validateEndpointPath(MsoProperties.MSO_REST_API_INSTANCE_GROUP)
331 + '/' + vnfGroupInstanceId + "/removeMembers";
335 public String getNetworkDeletePath(String serviceInstanceId, String networkInstanceId) {
336 return (MsoBusinessLogicImpl.validateEndpointPath(MsoProperties.MSO_REST_API_NETWORK_INSTANCE)
337 + "/" + networkInstanceId)
338 .replaceFirst(SVC_INSTANCE_ID, serviceInstanceId);
342 public String getResumeRequestPath(String requestId) {
343 return MsoBusinessLogicImpl.validateEndpointPath("mso.restapi.resume.orc.req")
344 .replaceFirst("<request_id>", requestId);
348 public String getOrchestrationRequestsPath() {
349 return MsoBusinessLogicImpl.validateEndpointPath(MsoProperties.MSO_REST_API_GET_ORC_REQ);
353 public ServiceInfo updateServiceInfo(UUID jobUUID, Consumer<ServiceInfo> serviceUpdater) {
354 ServiceInfo serviceInfo = asyncInstantiationRepository.getServiceInfoByJobId(jobUUID);
355 serviceUpdater.accept(serviceInfo);
356 asyncInstantiationRepository.saveServiceInfo(serviceInfo);
361 public ServiceInfo updateServiceInfoAndAuditStatus(UUID jobUuid, JobStatus jobStatus) {
362 auditService.auditVidStatus(jobUuid, jobStatus);
363 return updateServiceInfo(jobUuid, x -> setServiceInfoStatus(x, jobStatus));
366 private boolean isRetryEnabledForStatus(JobStatus jobStatus) {
367 return featureManager.isActive(Features.FLAG_1902_RETRY_JOB) &&
368 (jobStatus==JobStatus.COMPLETED_WITH_ERRORS || jobStatus==JobStatus.FAILED);
371 private void setServiceInfoStatus(ServiceInfo serviceInfo, JobStatus jobStatus) {
372 serviceInfo.setJobStatus(jobStatus);
373 serviceInfo.setStatusModifiedDate(new Date());
374 serviceInfo.setRetryEnabled(isRetryEnabledForStatus(jobStatus));
377 public Job.JobStatus calcStatus(AsyncRequestStatus asyncRequestStatus) {
378 String msoRequestState = asyncRequestStatus.request.requestStatus.getRequestState().toLowerCase().replaceAll("[^a-z]+", "");
379 JobStatus jobStatus = msoStateToJobStatusMap.get(msoRequestState);
380 return (jobStatus != null ? jobStatus : JobStatus.IN_PROGRESS);
384 public void handleFailedInstantiation(UUID jobUUID) {
385 ServiceInfo serviceInfo = asyncInstantiationRepository.getServiceInfoByJobId(jobUUID);
386 List<ServiceInfo> serviceInfoList = asyncInstantiationRepository.getServiceInfoByTemplateIdAndJobStatus(serviceInfo.getTemplateId(), JobStatus.PENDING);
387 serviceInfoList.forEach(si -> updateServiceInfoAndAuditStatus(si.getJobId(), JobStatus.STOPPED));
391 public void deleteJob(UUID jobId) {
392 jobService.delete(jobId);
393 Date now = new Date();
394 updateServiceInfo(jobId, x -> x.setDeletedAt(now));
398 public void hideServiceInfo(UUID jobUUID) {
399 ServiceInfo serviceInfo = asyncInstantiationRepository.getServiceInfoByJobId(jobUUID);
400 if (!serviceInfo.getJobStatus().isFinal()) {
401 String message = String.format("jobId %s: Service status does not allow hide service, status = %s",
402 serviceInfo.getJobId(),
403 serviceInfo.getJobStatus());
404 logger.error(EELFLoggerDelegate.errorLogger, message);
405 throw new OperationNotAllowedException(message);
407 serviceInfo.setHidden(true);
408 asyncInstantiationRepository.saveServiceInfo(serviceInfo);
412 public int getCounterForName(String name) {
414 String hqlSelectNC = "from NameCounter where name = :name";
415 String hqlUpdateCounter = "update NameCounter set counter = :newCounter " +
416 "where name= :name " +
417 "and counter= :prevCounter";
419 Integer counter = null;
420 GenericUncheckedException lastException = null;
421 for (int i = 0; i< MAX_RETRIES_GETTING_COUNTER && counter==null; i++) {
423 counter = calcCounter(name, hqlSelectNC, hqlUpdateCounter);
425 catch (GenericUncheckedException exception) {
426 lastException = exception; //do nothing, we will try again in the loop
434 throw lastException!=null ? new DbFailureUncheckedException(lastException) :
435 new DbFailureUncheckedException("Failed to get counter for "+name+" due to unknown error");
439 private Integer calcCounter(String name, String hqlSelectNC, String hqlUpdateCounter) {
441 counter = DaoUtils.tryWithSessionAndTransaction(sessionFactory, session -> {
442 NameCounter nameCounter = (NameCounter) session.createQuery(hqlSelectNC)
443 .setText("name", name)
445 if (nameCounter != null) {
446 int updatedRows = session.createQuery(hqlUpdateCounter)
447 .setText("name", nameCounter.getName())
448 .setInteger("prevCounter", nameCounter.getCounter())
449 .setInteger("newCounter", nameCounter.getCounter() + 1)
451 if (updatedRows == 1) {
452 return nameCounter.getCounter() + 1;
455 Object nameAsId = session.save(new NameCounter(name));
457 if (nameAsId != null) {
461 //in case of failure return null, in order to continue the loop
468 public int getMaxRetriesGettingFreeNameFromAai() {
469 return maxRetriesGettingFreeNameFromAai;
473 public void setMaxRetriesGettingFreeNameFromAai(int maxRetriesGettingFreeNameFromAai) {
474 this.maxRetriesGettingFreeNameFromAai = maxRetriesGettingFreeNameFromAai;
478 public String getUniqueName(String name, ResourceType resourceType) {
479 //check that name aai response well before increasing counter from DB
480 //Prevents unnecessary increasing of the counter while AAI doesn't response
481 isNameFreeInAai(NAME_FOR_CHECK_AAI_STATUS, resourceType);
483 for (int i=0; i<getMaxRetriesGettingFreeNameFromAai(); i++) {
484 String newName = getUniqueNameFromDbOnly(name);
485 if (isNameFreeInAai(newName, resourceType)) {
490 throw new MaxRetriesException("can't find unused name for "+name, getMaxRetriesGettingFreeNameFromAai());
494 public ServiceInstantiation prepareServiceToBeUnique(ServiceInstantiation serviceInstantiation) {
496 ServiceInstantiation clonedServiceInstantiation = JACKSON_OBJECT_MAPPER.readValue(
497 JACKSON_OBJECT_MAPPER.writeValueAsBytes(serviceInstantiation), ServiceInstantiation.class);
498 clonedServiceInstantiation.setBulkSize(1);
499 return replaceAllTrackById(clonedServiceInstantiation);
500 } catch (IOException e) {
501 throw new GenericUncheckedException(e);
506 private<T extends BaseResource> T replaceAllTrackById(T resource) {
507 resource.setTrackById(UUID.randomUUID().toString());
508 resource.getChildren().forEach(this::replaceAllTrackById);
513 public List<UUID> retryJob(ServiceInstantiation request, UUID jobId, String userId ) {
514 updateServiceInfo(jobId, si->si.setRetryEnabled(false));
515 return pushBulkJob(request, userId);
519 public List<UUID> retryJob(UUID jobId, String userId) {
520 ServiceInstantiation serviceInstantiationRequest = asyncInstantiationRepository.getJobRequest(jobId);
521 enrichBulkForRetry(serviceInstantiationRequest, jobId);
524 logger.debug(EELFLoggerDelegate.debugLogger, "retry ServiceInstantiation request: "+
525 JACKSON_OBJECT_MAPPER.writeValueAsString(serviceInstantiationRequest));
526 } catch (Exception e) {
527 logger.error(EELFLoggerDelegate.errorLogger, "failed to log retry of ServiceInstantiation request ", e);
529 return retryJob(serviceInstantiationRequest, jobId, userId);
533 public ServiceInstantiation getBulkForRetry(UUID jobId) {
534 return enrichBulkForRetry( asyncInstantiationRepository.getJobRequest(jobId), jobId);
538 public void addResourceInfo(JobSharedData sharedData, Job.JobStatus jobStatus, String instanceId) {
539 String trackById = ((BaseResource) sharedData.getRequest()).getTrackById();
540 ResourceInfo resourceInfo = new ResourceInfo(trackById, sharedData.getRootJobId(), instanceId, jobStatus, null);
541 asyncInstantiationRepository.saveResourceInfo(resourceInfo);
545 public void addFailedResourceInfo(JobSharedData sharedData, RestObject msoResponse) {
546 String trackById = ((BaseResource) sharedData.getRequest()).getTrackById();
547 String errorMessage = MsoUtil.formatExceptionAdditionalInfo(msoResponse.getStatusCode(), msoResponse.getRaw());
548 AsyncRequestStatus asyncRequestStatus = convertMessageToAsyncRequestStatus(errorMessage);
549 ResourceInfo resourceInfo = new ResourceInfo(trackById, sharedData.getRootJobId(), null, JobStatus.FAILED, asyncRequestStatus);
551 asyncInstantiationRepository.saveResourceInfo(resourceInfo);
555 public void updateResourceInfo(JobSharedData sharedData, JobStatus jobStatus, AsyncRequestStatus message) {
556 ResourceInfo resourceInfo = asyncInstantiationRepository.getResourceInfoByTrackId(((BaseResource) sharedData.getRequest()).getTrackById());
557 resourceInfo.setJobStatus(jobStatus);
558 if (jobStatus.isFailure()) {
559 resourceInfo.setErrorMessage(message);
561 asyncInstantiationRepository.saveResourceInfo(resourceInfo);
564 public AsyncRequestStatus convertMessageToAsyncRequestStatus(String message) {
565 RequestStatus requestStatus = new RequestStatus("FAILED", message, TimeUtils.zonedDateTimeToString(ZonedDateTime.now()));
566 AsyncRequestStatus.Request request = new AsyncRequestStatus.Request(requestStatus);
567 return new AsyncRequestStatus(request);
570 protected String getUniqueNameFromDbOnly(String name) {
571 int counter = getCounterForName(name);
572 return formatNameAndCounter(name, counter);
575 //the method is protected so we can call it in the UT
576 protected String formatNameAndCounter(String name, int counter) {
577 return counter==0 ? name : name + "_" + String.format("%03d", counter);
580 private boolean isNameFreeInAai(String name, ResourceType resourceType) throws ExceptionWithRequestInfo {
581 return !aaiClient.isNodeTypeExistsByName(name, resourceType);
585 public ServiceInstantiation enrichBulkForRetry(ServiceInstantiation serviceInstantiation, UUID jobId){
586 Map<String, ResourceInfo> resourceInfoByTrackId = asyncInstantiationRepository.getResourceInfoByRootJobId(jobId);
588 return setResourceStatus(resourceInfoByTrackId, serviceInstantiation);
591 protected String readStatusMsg(ResourceInfo resourceInfo){
592 if(resourceInfo!=null && resourceInfo.getErrorMessage()!=null && resourceInfo.getErrorMessage().request != null &&resourceInfo.getErrorMessage().request.requestStatus != null ) {
593 return resourceInfo.getErrorMessage().request.requestStatus.getStatusMessage();
598 private<T extends BaseResource> T setResourceStatus(Map<String, ResourceInfo> resourceInfoByTrackId, T resource) {
599 ResourceInfo resourceInfo = resourceInfoByTrackId.get(resource.getTrackById());
600 if(resourceInfo != null) {
601 boolean failed = resourceInfo.getJobStatus().isFailure();
602 resource.setIsFailed(failed);
603 resource.setStatusMessage(readStatusMsg(resourceInfo));
605 // if(resource.getAction().equals(Action.Delete)){
606 // TODO not yet implemented- completed after delete should remove the node
607 resource.setAction(Action.None);
608 resource.setInstanceId(resourceInfo.getInstanceId());
611 resource.getChildren().forEach(child -> setResourceStatus(resourceInfoByTrackId, child));