2 * ============LICENSE_START=======================================================
3 * Copyright (C) 2021 Nordix Foundation.
4 * Modifications Copyright (C) 2021 AT&T Intellectual Property. All rights reserved.
5 * ================================================================================
6 * Licensed under the Apache License, Version 2.0 (the "License");
7 * you may not use this file except in compliance with the License.
8 * You may obtain a copy of the License at
10 * http://www.apache.org/licenses/LICENSE-2.0
12 * Unless required by applicable law or agreed to in writing, software
13 * distributed under the License is distributed on an "AS IS" BASIS,
14 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15 * See the License for the specific language governing permissions and
16 * limitations under the License.
18 * SPDX-License-Identifier: Apache-2.0
19 * ============LICENSE_END=========================================================
22 package org.onap.policy.clamp.acm.runtime.instantiation;
24 import com.google.gson.Gson;
25 import com.google.gson.internal.LinkedTreeMap;
26 import com.google.gson.reflect.TypeToken;
27 import java.lang.reflect.Type;
28 import java.util.ArrayList;
29 import java.util.Collection;
30 import java.util.HashMap;
31 import java.util.List;
33 import java.util.UUID;
34 import java.util.function.Function;
35 import java.util.function.UnaryOperator;
36 import java.util.stream.Collectors;
37 import java.util.stream.Stream;
38 import javax.ws.rs.core.Response;
39 import javax.ws.rs.core.Response.Status;
40 import lombok.AllArgsConstructor;
41 import org.onap.policy.clamp.acm.runtime.commissioning.CommissioningProvider;
42 import org.onap.policy.clamp.acm.runtime.supervision.SupervisionHandler;
43 import org.onap.policy.clamp.common.acm.exception.AutomationCompositionException;
44 import org.onap.policy.clamp.models.acm.concepts.AutomationComposition;
45 import org.onap.policy.clamp.models.acm.concepts.AutomationCompositionElement;
46 import org.onap.policy.clamp.models.acm.concepts.AutomationCompositionOrderedState;
47 import org.onap.policy.clamp.models.acm.concepts.AutomationCompositionState;
48 import org.onap.policy.clamp.models.acm.concepts.AutomationCompositions;
49 import org.onap.policy.clamp.models.acm.concepts.Participant;
50 import org.onap.policy.clamp.models.acm.messages.rest.GenericNameVersion;
51 import org.onap.policy.clamp.models.acm.messages.rest.instantiation.AutomationCompositionOrderStateResponse;
52 import org.onap.policy.clamp.models.acm.messages.rest.instantiation.AutomationCompositionPrimed;
53 import org.onap.policy.clamp.models.acm.messages.rest.instantiation.AutomationCompositionPrimedResponse;
54 import org.onap.policy.clamp.models.acm.messages.rest.instantiation.InstancePropertiesResponse;
55 import org.onap.policy.clamp.models.acm.messages.rest.instantiation.InstantiationCommand;
56 import org.onap.policy.clamp.models.acm.messages.rest.instantiation.InstantiationResponse;
57 import org.onap.policy.clamp.models.acm.persistence.provider.AutomationCompositionProvider;
58 import org.onap.policy.clamp.models.acm.persistence.provider.ParticipantProvider;
59 import org.onap.policy.common.parameters.BeanValidationResult;
60 import org.onap.policy.common.parameters.ObjectValidationResult;
61 import org.onap.policy.common.parameters.ValidationResult;
62 import org.onap.policy.common.parameters.ValidationStatus;
63 import org.onap.policy.models.base.PfModelException;
64 import org.onap.policy.models.tosca.authorative.concepts.ToscaConceptIdentifier;
65 import org.onap.policy.models.tosca.authorative.concepts.ToscaNameVersion;
66 import org.onap.policy.models.tosca.authorative.concepts.ToscaNodeTemplate;
67 import org.onap.policy.models.tosca.authorative.concepts.ToscaServiceTemplate;
68 import org.springframework.stereotype.Service;
69 import org.springframework.transaction.annotation.Transactional;
72 * This class is dedicated to the Instantiation of Commissioned automation composition.
77 public class AutomationCompositionInstantiationProvider {
78 private static final String AUTOMATION_COMPOSITION_NODE_TYPE = "org.onap.policy.clamp.acm.AutomationComposition";
79 private static final String AUTOMATION_COMPOSITION_NODE_ELEMENT_TYPE = "AutomationCompositionElement";
80 private static final String PARTICIPANT_ID_PROPERTY_KEY = "participant_id";
81 private static final String PARTICIPANT_TYPE_PROPERTY_KEY = "participantType";
82 private static final String AC_ELEMENT_NAME = "name";
83 private static final String AC_ELEMENT_VERSION = "version";
84 private static final String HYPHEN = "-";
86 private static final Gson GSON = new Gson();
88 private final AutomationCompositionProvider automationCompositionProvider;
89 private final CommissioningProvider commissioningProvider;
90 private final SupervisionHandler supervisionHandler;
91 private final ParticipantProvider participantProvider;
92 private static final String ENTRY = "entry ";
95 * Creates Instance Properties and automation composition.
97 * @param serviceTemplate the service template
98 * @return the result of the instantiation operation
99 * @throws PfModelException on creation errors
101 public InstancePropertiesResponse createInstanceProperties(ToscaServiceTemplate serviceTemplate)
102 throws PfModelException {
104 String instanceName = serviceTemplate.getName();
105 AutomationComposition automationComposition = new AutomationComposition();
106 Map<UUID, AutomationCompositionElement> automationCompositionElements = new HashMap<>();
108 ToscaServiceTemplate toscaServiceTemplate = commissioningProvider.getAllToscaServiceTemplate().get(0);
110 Map<String, ToscaNodeTemplate> persistedNodeTemplateMap =
111 toscaServiceTemplate.getToscaTopologyTemplate().getNodeTemplates();
113 Map<String, ToscaNodeTemplate> nodeTemplates = deepCloneNodeTemplate(serviceTemplate);
115 nodeTemplates.forEach((key, template) -> {
116 ToscaNodeTemplate newNodeTemplate = new ToscaNodeTemplate();
117 String name = key + "-" + instanceName;
118 String version = template.getVersion();
119 String description = template.getDescription() + " " + instanceName;
120 newNodeTemplate.setName(name);
121 newNodeTemplate.setVersion(version);
122 newNodeTemplate.setDescription(description);
123 newNodeTemplate.setProperties(new HashMap<>(template.getProperties()));
124 newNodeTemplate.setType(template.getType());
125 newNodeTemplate.setTypeVersion(template.getTypeVersion());
126 newNodeTemplate.setMetadata(template.getMetadata());
128 crateNewAutomationCompositionInstance(instanceName, automationComposition, automationCompositionElements,
129 template, newNodeTemplate);
131 persistedNodeTemplateMap.put(name, newNodeTemplate);
134 AutomationCompositions automationCompositions = new AutomationCompositions();
136 serviceTemplate.getToscaTopologyTemplate().getNodeTemplates().putAll(persistedNodeTemplateMap);
138 automationComposition.setElements(automationCompositionElements);
139 automationCompositions.getAutomationCompositionList().add(automationComposition);
141 return saveInstancePropertiesAndAutomationComposition(serviceTemplate, automationCompositions);
145 * Deletes Instance Properties.
147 * @param name the name of the automation composition to delete
148 * @param version the version of the automation composition to delete
149 * @return the result of the deletion
150 * @throws PfModelException on deletion errors
152 public InstantiationResponse deleteInstanceProperties(String name, String version) throws PfModelException {
154 String instanceName = getInstancePropertyName(name, version);
156 Map<String, ToscaNodeTemplate> filteredToscaNodeTemplateMap = new HashMap<>();
158 ToscaServiceTemplate toscaServiceTemplate = commissioningProvider.getAllToscaServiceTemplate().get(0);
160 toscaServiceTemplate.getToscaTopologyTemplate().getNodeTemplates().forEach((key, nodeTemplate) -> {
161 if (!nodeTemplate.getName().contains(instanceName)) {
162 filteredToscaNodeTemplateMap.put(key, nodeTemplate);
166 List<ToscaNodeTemplate> filteredToscaNodeTemplateList =
167 toscaServiceTemplate.getToscaTopologyTemplate().getNodeTemplates().values().stream()
168 .filter(nodeTemplate -> nodeTemplate.getName().contains(instanceName)).collect(Collectors.toList());
170 InstantiationResponse response = this.deleteAutomationComposition(name, version);
172 automationCompositionProvider.deleteInstanceProperties(filteredToscaNodeTemplateMap,
173 filteredToscaNodeTemplateList);
179 * Create automation compositions.
181 * @param automationCompositions the automation composition
182 * @return the result of the instantiation operation
183 * @throws PfModelException on creation errors
185 public InstantiationResponse createAutomationCompositions(AutomationCompositions automationCompositions)
186 throws PfModelException {
187 for (AutomationComposition automationComposition : automationCompositions.getAutomationCompositionList()) {
188 var checkAutomationCompositionOpt =
189 automationCompositionProvider.findAutomationComposition(automationComposition.getKey().asIdentifier());
190 if (checkAutomationCompositionOpt.isPresent()) {
191 throw new PfModelException(Response.Status.BAD_REQUEST,
192 automationComposition.getKey().asIdentifier() + " already defined");
195 BeanValidationResult validationResult = validateAutomationCompositions(automationCompositions);
196 if (!validationResult.isValid()) {
197 throw new PfModelException(Response.Status.BAD_REQUEST, validationResult.getResult());
199 automationCompositionProvider.saveAutomationCompositions(automationCompositions.getAutomationCompositionList());
201 var response = new InstantiationResponse();
202 response.setAffectedAutomationCompositions(automationCompositions.getAutomationCompositionList().stream()
203 .map(ac -> ac.getKey().asIdentifier()).collect(Collectors.toList()));
209 * Update automation compositions.
211 * @param automationCompositions the automation composition
212 * @return the result of the instantiation operation
213 * @throws PfModelException on update errors
215 public InstantiationResponse updateAutomationCompositions(AutomationCompositions automationCompositions)
216 throws PfModelException {
217 BeanValidationResult validationResult = validateAutomationCompositions(automationCompositions);
218 if (!validationResult.isValid()) {
219 throw new PfModelException(Response.Status.BAD_REQUEST, validationResult.getResult());
221 automationCompositionProvider.saveAutomationCompositions(automationCompositions.getAutomationCompositionList());
223 var response = new InstantiationResponse();
224 response.setAffectedAutomationCompositions(automationCompositions.getAutomationCompositionList().stream()
225 .map(ac -> ac.getKey().asIdentifier()).collect(Collectors.toList()));
231 * Validate AutomationCompositions.
233 * @param automationCompositions AutomationCompositions to validate
234 * @return the result of validation
235 * @throws PfModelException if automationCompositions is not valid
237 private BeanValidationResult validateAutomationCompositions(AutomationCompositions automationCompositions)
238 throws PfModelException {
240 var result = new BeanValidationResult("AutomationCompositions", automationCompositions);
242 for (AutomationComposition automationComposition : automationCompositions.getAutomationCompositionList()) {
243 var subResult = new BeanValidationResult(ENTRY + automationComposition.getDefinition().getName(),
244 automationComposition);
246 List<ToscaNodeTemplate> toscaNodeTemplates = commissioningProvider.getAutomationCompositionDefinitions(
247 automationComposition.getDefinition().getName(), automationComposition.getDefinition().getVersion());
249 if (toscaNodeTemplates.isEmpty()) {
251 new ObjectValidationResult("AutomationComposition", automationComposition.getDefinition().getName(),
252 ValidationStatus.INVALID, "Commissioned automation composition definition not found"));
253 } else if (toscaNodeTemplates.size() > 1) {
255 new ObjectValidationResult("AutomationComposition", automationComposition.getDefinition().getName(),
256 ValidationStatus.INVALID, "Commissioned automation composition definition not valid"));
259 List<ToscaNodeTemplate> acElementDefinitions =
260 commissioningProvider.getAutomationCompositionElementDefinitions(toscaNodeTemplates.get(0));
263 Map<String, ToscaConceptIdentifier> definitions = acElementDefinitions
265 .map(nodeTemplate -> nodeTemplate.getKey().asIdentifier())
266 .collect(Collectors.toMap(ToscaConceptIdentifier::getName, UnaryOperator.identity()));
269 for (AutomationCompositionElement element : automationComposition.getElements().values()) {
270 subResult.addResult(validateDefinition(definitions, element.getDefinition()));
273 result.addResult(subResult);
279 * Validate ToscaConceptIdentifier, checking if exist in ToscaConceptIdentifiers map.
281 * @param definitions map of all ToscaConceptIdentifiers
282 * @param definition ToscaConceptIdentifier to validate
283 * @return the validation result
285 private ValidationResult validateDefinition(Map<String, ToscaConceptIdentifier> definitions,
286 ToscaConceptIdentifier definition) {
287 var result = new BeanValidationResult(ENTRY + definition.getName(), definition);
288 ToscaConceptIdentifier identifier = definitions.get(definition.getName());
289 if (identifier == null) {
290 result.setResult(ValidationStatus.INVALID, "Not found");
291 } else if (!identifier.equals(definition)) {
292 result.setResult(ValidationStatus.INVALID, "Version not matching");
294 return (result.isClean() ? null : result);
298 * Delete the automation composition with the given name and version.
300 * @param name the name of the automation composition to delete
301 * @param version the version of the automation composition to delete
302 * @return the result of the deletion
303 * @throws PfModelException on deletion errors
305 public InstantiationResponse deleteAutomationComposition(String name, String version) throws PfModelException {
306 var automationCompositionOpt = automationCompositionProvider.findAutomationComposition(name, version);
307 if (automationCompositionOpt.isEmpty()) {
308 throw new PfModelException(Response.Status.NOT_FOUND, "Automation composition not found");
310 var automationComposition = automationCompositionOpt.get();
311 if (!AutomationCompositionState.UNINITIALISED.equals(automationComposition.getState())) {
312 throw new PfModelException(Response.Status.BAD_REQUEST,
313 "Automation composition state is still " + automationComposition.getState());
315 var response = new InstantiationResponse();
316 response.setAffectedAutomationCompositions(
317 List.of(automationCompositionProvider.deleteAutomationComposition(name, version).getKey().asIdentifier()));
322 * Get the requested automation compositions.
324 * @param name the name of the automation composition to get, null for all automation compositions
325 * @param version the version of the automation composition to get, null for all automation compositions
326 * @return the automation compositions
327 * @throws PfModelException on errors getting automation compositions
329 @Transactional(readOnly = true)
330 public AutomationCompositions getAutomationCompositions(String name, String version) throws PfModelException {
331 var automationCompositions = new AutomationCompositions();
332 automationCompositions
333 .setAutomationCompositionList(automationCompositionProvider.getAutomationCompositions(name, version));
335 return automationCompositions;
339 * Issue a command to automation compositions, setting their ordered state.
341 * @param command the command to issue to automation compositions
342 * @return the result of the initiation command
343 * @throws PfModelException on errors setting the ordered state on the automation compositions
344 * @throws AutomationCompositionException on ordered state invalid
346 public InstantiationResponse issueAutomationCompositionCommand(InstantiationCommand command)
347 throws AutomationCompositionException, PfModelException {
349 if (command.getOrderedState() == null) {
350 throw new AutomationCompositionException(Status.BAD_REQUEST,
351 "ordered state invalid or not specified on command");
354 var participants = participantProvider.getParticipants();
355 if (participants.isEmpty()) {
356 throw new AutomationCompositionException(Status.BAD_REQUEST, "No participants registered");
358 var validationResult = new BeanValidationResult("InstantiationCommand", command);
359 List<AutomationComposition> automationCompositions =
360 new ArrayList<>(command.getAutomationCompositionIdentifierList().size());
361 for (ToscaConceptIdentifier id : command.getAutomationCompositionIdentifierList()) {
362 var automationCompositionOpt = automationCompositionProvider.findAutomationComposition(id);
363 if (automationCompositionOpt.isEmpty()) {
364 validationResult.addResult("ToscaConceptIdentifier", id, ValidationStatus.INVALID,
365 "AutomationComposition with id " + id + " not found");
367 var automationComposition = automationCompositionOpt.get();
368 automationComposition.setCascadedOrderedState(command.getOrderedState());
369 automationCompositions.add(automationComposition);
372 if (validationResult.isValid()) {
373 validationResult = validateIssueAutomationCompositions(automationCompositions, participants);
375 if (!validationResult.isValid()) {
376 throw new PfModelException(Response.Status.BAD_REQUEST, validationResult.getResult());
378 automationCompositionProvider.saveAutomationCompositions(automationCompositions);
380 supervisionHandler.triggerAutomationCompositionSupervision(command.getAutomationCompositionIdentifierList());
381 var response = new InstantiationResponse();
382 response.setAffectedAutomationCompositions(command.getAutomationCompositionIdentifierList());
387 private BeanValidationResult validateIssueAutomationCompositions(List<AutomationComposition> automationCompositions,
388 List<Participant> participants) {
389 var result = new BeanValidationResult("AutomationCompositions", automationCompositions);
391 Map<ToscaConceptIdentifier, Participant> participantMap = participants.stream()
392 .collect(Collectors.toMap(participant -> participant.getKey().asIdentifier(), Function.identity()));
394 for (AutomationComposition automationComposition : automationCompositions) {
396 for (var element : automationComposition.getElements().values()) {
398 var subResult = new BeanValidationResult(ENTRY + element.getDefinition().getName(), element);
399 Participant p = participantMap.get(element.getParticipantId());
401 subResult.addResult(new ObjectValidationResult(AUTOMATION_COMPOSITION_NODE_ELEMENT_TYPE,
402 element.getDefinition().getName(), ValidationStatus.INVALID,
403 "Participant with ID " + element.getParticipantId() + " is not registered"));
404 } else if (!p.getParticipantType().equals(element.getParticipantType())) {
405 subResult.addResult(new ObjectValidationResult(AUTOMATION_COMPOSITION_NODE_ELEMENT_TYPE,
406 element.getDefinition().getName(), ValidationStatus.INVALID,
407 "Participant with ID " + element.getParticipantType() + " - " + element.getParticipantId()
408 + " is not registered"));
410 result.addResult(subResult);
419 * Gets a list of automation compositions with it's ordered state.
421 * @param name the name of the automation composition to get, null for all automation compositions
422 * @param version the version of the automation composition to get, null for all automation compositions
423 * @return a list of Instantiation Command
424 * @throws PfModelException on errors getting automation compositions
426 @Transactional(readOnly = true)
427 public AutomationCompositionOrderStateResponse getInstantiationOrderState(String name, String version)
428 throws PfModelException {
430 List<AutomationComposition> automationCompositions =
431 automationCompositionProvider.getAutomationCompositions(name, version);
433 var response = new AutomationCompositionOrderStateResponse();
435 automationCompositions.forEach(automationComposition -> {
436 var genericNameVersion = new GenericNameVersion();
437 genericNameVersion.setName(automationComposition.getName());
438 genericNameVersion.setVersion(automationComposition.getVersion());
439 response.getAutomationCompositionIdentifierList().add(genericNameVersion);
446 * Saves Instance Properties and automation composition.
447 * Gets a list of automation compositions which are primed or de-primed.
449 * @param name the name of the automation composition to get, null for all automation compositions
450 * @param version the version of the automation composition to get, null for all automation compositions
451 * @return a list of Instantiation Command
452 * @throws PfModelException on errors getting automation compositions
454 @Transactional(readOnly = true)
455 public AutomationCompositionPrimedResponse getAutomationCompositionPriming(String name, String version)
456 throws PfModelException {
458 List<AutomationComposition> automationCompositions =
459 automationCompositionProvider.getAutomationCompositions(name, version);
461 var response = new AutomationCompositionPrimedResponse();
463 automationCompositions.forEach(automationComposition -> {
464 var primed = new AutomationCompositionPrimed();
465 primed.setName(automationComposition.getName());
466 primed.setVersion(automationComposition.getVersion());
467 primed.setPrimed(automationComposition.getPrimed());
468 response.getPrimedAutomationCompositionsList().add(primed);
475 * Creates instance element name.
477 * @param serviceTemplate the service template
478 * @param automationCompositions a list of automation compositions
479 * @return the result of the instance properties and instantiation operation
480 * @throws PfModelException on creation errors
482 private InstancePropertiesResponse saveInstancePropertiesAndAutomationComposition(
483 ToscaServiceTemplate serviceTemplate, AutomationCompositions automationCompositions) throws PfModelException {
485 for (var automationComposition : automationCompositions.getAutomationCompositionList()) {
486 var checkAutomationCompositionOpt =
487 automationCompositionProvider.findAutomationComposition(automationComposition.getKey().asIdentifier());
488 if (checkAutomationCompositionOpt.isPresent()) {
489 throw new PfModelException(Response.Status.BAD_REQUEST, "Automation composition with id "
490 + automationComposition.getKey().asIdentifier() + " already defined");
493 Map<String, ToscaNodeTemplate> toscaSavedNodeTemplate =
494 automationCompositionProvider.saveInstanceProperties(serviceTemplate);
495 automationCompositionProvider.saveAutomationCompositions(automationCompositions.getAutomationCompositionList());
496 List<ToscaConceptIdentifier> affectedAutomationCompositions = automationCompositions
497 .getAutomationCompositionList().stream().map(ac -> ac.getKey().asIdentifier()).collect(Collectors.toList());
499 List<ToscaConceptIdentifier> toscaAffectedProperties = toscaSavedNodeTemplate.values().stream()
500 .map(template -> template.getKey().asIdentifier()).collect(Collectors.toList());
502 var response = new InstancePropertiesResponse();
503 response.setAffectedInstanceProperties(Stream.of(affectedAutomationCompositions, toscaAffectedProperties)
504 .flatMap(Collection::stream).collect(Collectors.toList()));
510 * Crates a new automation composition instance.
512 * @param instanceName automation composition Instance name
513 * @param automationComposition empty automation composition
514 * @param automationCompositionElements new automation composition Element map
515 * @param template original Cloned Tosca Node Template
516 * @param newNodeTemplate new Tosca Node Template
518 private void crateNewAutomationCompositionInstance(String instanceName, AutomationComposition automationComposition,
519 Map<UUID, AutomationCompositionElement> automationCompositionElements, ToscaNodeTemplate template,
520 ToscaNodeTemplate newNodeTemplate) {
521 if (template.getType().equals(AUTOMATION_COMPOSITION_NODE_TYPE)) {
522 automationComposition.setDefinition(getAutomationCompositionDefinition(newNodeTemplate));
525 if (template.getType().contains(AUTOMATION_COMPOSITION_NODE_ELEMENT_TYPE)) {
526 AutomationCompositionElement automationCompositionElement =
527 getAutomationCompositionElement(newNodeTemplate);
528 automationCompositionElements.put(automationCompositionElement.getId(), automationCompositionElement);
531 automationComposition.setName(instanceName);
532 automationComposition.setVersion(template.getVersion());
533 automationComposition.setDescription("Automation composition " + instanceName);
534 automationComposition.setState(AutomationCompositionState.UNINITIALISED);
535 automationComposition.setOrderedState(AutomationCompositionOrderedState.UNINITIALISED);
539 * Get's the instance property name of the automation composition.
541 * @param name the name of the automation composition to get, null for all automation compositions
542 * @param version the version of the automation composition to get, null for all automation compositions
543 * @return the instance name of the automation composition instance properties
544 * @throws PfModelException on errors getting automation compositions
546 private String getInstancePropertyName(String name, String version) throws PfModelException {
547 List<String> toscaDefinitionsNames =
548 automationCompositionProvider.getAutomationCompositions(name, version).stream()
549 .map(AutomationComposition::getDefinition).map(ToscaNameVersion::getName).collect(Collectors.toList());
551 return toscaDefinitionsNames.stream().reduce("", (s1, s2) -> {
553 if (s2.contains(HYPHEN)) {
554 String[] instances = s2.split(HYPHEN);
556 return HYPHEN + instances[1];
564 * Retrieves automation composition Definition.
566 * @param template tosca node template
567 * @return automation composition definition
569 private ToscaConceptIdentifier getAutomationCompositionDefinition(ToscaNodeTemplate template) {
570 ToscaConceptIdentifier definition = new ToscaConceptIdentifier();
571 definition.setName(template.getName());
572 definition.setVersion(template.getVersion());
577 * Retrieves automation composition Element.
579 * @param template tosca node template
580 * @return a automation composition element
582 @SuppressWarnings("unchecked")
583 private AutomationCompositionElement getAutomationCompositionElement(ToscaNodeTemplate template) {
584 AutomationCompositionElement automationCompositionElement = new AutomationCompositionElement();
585 ToscaConceptIdentifier definition = new ToscaConceptIdentifier();
586 definition.setName(template.getName());
587 definition.setVersion(template.getVersion());
588 automationCompositionElement.setDefinition(definition);
589 LinkedTreeMap<String, Object> participantId =
590 (LinkedTreeMap<String, Object>) template.getProperties().get(PARTICIPANT_ID_PROPERTY_KEY);
591 if (participantId != null) {
592 ToscaConceptIdentifier participantIdProperty = new ToscaConceptIdentifier();
593 participantIdProperty.setName(String.valueOf(participantId.get(AC_ELEMENT_NAME)));
594 participantIdProperty.setVersion(String.valueOf(participantId.get(AC_ELEMENT_VERSION)));
595 automationCompositionElement.setParticipantId(participantIdProperty);
597 LinkedTreeMap<String, Object> participantType =
598 (LinkedTreeMap<String, Object>) template.getProperties().get(PARTICIPANT_TYPE_PROPERTY_KEY);
599 if (participantType != null) {
600 ToscaConceptIdentifier participantTypeProperty = new ToscaConceptIdentifier();
601 participantTypeProperty.setName(String.valueOf(participantType.get(AC_ELEMENT_NAME)));
602 participantTypeProperty.setVersion(participantType.get(AC_ELEMENT_VERSION).toString());
603 automationCompositionElement.setParticipantType(participantTypeProperty);
605 return automationCompositionElement;
609 * Deep clones ToscaNodeTemplate.
611 * @param serviceTemplate ToscaServiceTemplate
612 * @return a cloned Hash Map of ToscaNodeTemplate
614 private Map<String, ToscaNodeTemplate> deepCloneNodeTemplate(ToscaServiceTemplate serviceTemplate) {
615 String jsonString = GSON.toJson(serviceTemplate.getToscaTopologyTemplate().getNodeTemplates());
616 Type type = new TypeToken<HashMap<String, ToscaNodeTemplate>>() {}.getType();
617 return GSON.fromJson(jsonString, type);