2 * ============LICENSE_START=======================================================
3 * Copyright (C) 2023-2024 Nordix Foundation.
4 * ================================================================================
5 * Licensed under the Apache License, Version 2.0 (the "License");
6 * you may not use this file except in compliance with the License.
7 * You may obtain a copy of the License at
9 * http://www.apache.org/licenses/LICENSE-2.0
11 * Unless required by applicable law or agreed to in writing, software
12 * distributed under the License is distributed on an "AS IS" BASIS,
13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 * See the License for the specific language governing permissions and
15 * limitations under the License.
17 * SPDX-License-Identifier: Apache-2.0
18 * ============LICENSE_END=========================================================
21 package org.onap.policy.clamp.acm.participant.sim.main.handler;
23 import java.lang.invoke.MethodHandles;
24 import java.util.ArrayList;
26 import java.util.UUID;
29 import org.onap.policy.clamp.acm.participant.intermediary.api.CompositionDto;
30 import org.onap.policy.clamp.acm.participant.intermediary.api.CompositionElementDto;
31 import org.onap.policy.clamp.acm.participant.intermediary.api.InstanceElementDto;
32 import org.onap.policy.clamp.acm.participant.intermediary.api.ParticipantIntermediaryApi;
33 import org.onap.policy.clamp.acm.participant.intermediary.api.impl.AcElementListenerV2;
34 import org.onap.policy.clamp.acm.participant.sim.model.InternalData;
35 import org.onap.policy.clamp.acm.participant.sim.model.InternalDatas;
36 import org.onap.policy.clamp.acm.participant.sim.model.SimConfig;
37 import org.onap.policy.clamp.models.acm.concepts.AcTypeState;
38 import org.onap.policy.clamp.models.acm.concepts.AutomationComposition;
39 import org.onap.policy.clamp.models.acm.concepts.AutomationCompositions;
40 import org.onap.policy.clamp.models.acm.concepts.DeployState;
41 import org.onap.policy.clamp.models.acm.concepts.LockState;
42 import org.onap.policy.clamp.models.acm.concepts.StateChangeResult;
43 import org.onap.policy.clamp.models.acm.utils.AcmUtils;
44 import org.onap.policy.models.base.PfModelException;
45 import org.onap.policy.models.tosca.authorative.concepts.ToscaConceptIdentifier;
46 import org.slf4j.Logger;
47 import org.slf4j.LoggerFactory;
48 import org.springframework.stereotype.Component;
51 * This class handles implementation of automationCompositionElement updates.
54 public class AutomationCompositionElementHandler extends AcElementListenerV2 {
56 private static final Logger LOGGER = LoggerFactory.getLogger(MethodHandles.lookup().lookupClass());
60 private SimConfig config = new SimConfig();
62 public AutomationCompositionElementHandler(ParticipantIntermediaryApi intermediaryApi) {
63 super(intermediaryApi);
67 * Handle a deploy on a automation composition element.
69 * @param compositionElement the information of the Automation Composition Definition Element
70 * @param instanceElement the information of the Automation Composition Instance Element
71 * @throws PfModelException from Policy framework
74 public void deploy(CompositionElementDto compositionElement, InstanceElementDto instanceElement)
75 throws PfModelException {
76 LOGGER.debug("deploy call compositionElement: {}, instanceElement: {}", compositionElement, instanceElement);
78 if (!execution(config.getDeployTimerMs(), "Current Thread deploy is Interrupted during execution {}",
79 instanceElement.elementId())) {
83 if (config.isDeploySuccess()) {
84 intermediaryApi.updateAutomationCompositionElementState(instanceElement.instanceId(),
85 instanceElement.elementId(), DeployState.DEPLOYED, null, StateChangeResult.NO_ERROR,
88 intermediaryApi.updateAutomationCompositionElementState(instanceElement.instanceId(),
89 instanceElement.elementId(), DeployState.UNDEPLOYED, null, StateChangeResult.FAILED,
94 private boolean execution(int timeMs, String msg, UUID elementId) {
95 long endTime = System.currentTimeMillis() + timeMs;
96 while (System.currentTimeMillis() < endTime) {
98 if (Thread.currentThread().isInterrupted()) {
99 LOGGER.debug(msg, elementId);
103 } catch (InterruptedException e) {
104 LOGGER.debug(msg, elementId);
105 Thread.currentThread().interrupt();
113 * Handle a automation composition element state change.
115 * @param compositionElement the information of the Automation Composition Definition Element
116 * @param instanceElement the information of the Automation Composition Instance Element
117 * @throws PfModelException from Policy framework
120 public void undeploy(CompositionElementDto compositionElement, InstanceElementDto instanceElement)
121 throws PfModelException {
122 LOGGER.debug("undeploy call compositionElement: {}, instanceElement: {}", compositionElement, instanceElement);
124 if (!execution(config.getUndeployTimerMs(), "Current Thread undeploy is Interrupted during execution {}",
125 instanceElement.elementId())) {
129 if (config.isUndeploySuccess()) {
130 intermediaryApi.updateAutomationCompositionElementState(instanceElement.instanceId(),
131 instanceElement.elementId(), DeployState.UNDEPLOYED, null, StateChangeResult.NO_ERROR,
134 intermediaryApi.updateAutomationCompositionElementState(instanceElement.instanceId(),
135 instanceElement.elementId(), DeployState.DEPLOYED, null, StateChangeResult.FAILED,
141 public void lock(CompositionElementDto compositionElement, InstanceElementDto instanceElement)
142 throws PfModelException {
143 LOGGER.debug("lock call compositionElement: {}, instanceElement: {}", compositionElement, instanceElement);
145 if (!execution(config.getLockTimerMs(), "Current Thread lock is Interrupted during execution {}",
146 instanceElement.elementId())) {
150 if (config.isLockSuccess()) {
151 intermediaryApi.updateAutomationCompositionElementState(instanceElement.instanceId(),
152 instanceElement.elementId(), null, LockState.LOCKED, StateChangeResult.NO_ERROR, "Locked");
154 intermediaryApi.updateAutomationCompositionElementState(instanceElement.instanceId(),
155 instanceElement.elementId(), null, LockState.UNLOCKED, StateChangeResult.FAILED, "Lock failed!");
160 public void unlock(CompositionElementDto compositionElement, InstanceElementDto instanceElement)
161 throws PfModelException {
162 LOGGER.debug("unlock call compositionElement: {}, instanceElement: {}", compositionElement, instanceElement);
164 if (!execution(config.getUnlockTimerMs(), "Current Thread unlock is Interrupted during execution {}",
165 instanceElement.elementId())) {
169 if (config.isUnlockSuccess()) {
170 intermediaryApi.updateAutomationCompositionElementState(instanceElement.instanceId(),
171 instanceElement.elementId(), null, LockState.UNLOCKED, StateChangeResult.NO_ERROR, "Unlocked");
173 intermediaryApi.updateAutomationCompositionElementState(instanceElement.instanceId(),
174 instanceElement.elementId(), null, LockState.LOCKED, StateChangeResult.FAILED, "Unlock failed!");
179 public void delete(CompositionElementDto compositionElement, InstanceElementDto instanceElement)
180 throws PfModelException {
181 LOGGER.debug("delete call compositionElement: {}, instanceElement: {}", compositionElement, instanceElement);
183 if (!execution(config.getDeleteTimerMs(), "Current Thread delete is Interrupted during execution {}",
184 instanceElement.elementId())) {
188 if (config.isDeleteSuccess()) {
189 intermediaryApi.updateAutomationCompositionElementState(instanceElement.instanceId(),
190 instanceElement.elementId(), DeployState.DELETED, null, StateChangeResult.NO_ERROR, "Deleted");
192 intermediaryApi.updateAutomationCompositionElementState(instanceElement.instanceId(),
193 instanceElement.elementId(), DeployState.UNDEPLOYED, null, StateChangeResult.FAILED,
199 public void update(CompositionElementDto compositionElement, InstanceElementDto instanceElement,
200 InstanceElementDto instanceElementUpdated) throws PfModelException {
201 LOGGER.debug("update call compositionElement: {}, instanceElement: {}, instanceElementUpdated: {}",
202 compositionElement, instanceElement, instanceElementUpdated);
204 if (!execution(config.getUpdateTimerMs(), "Current Thread update is Interrupted during execution {}",
205 instanceElement.elementId())) {
209 if (config.isUpdateSuccess()) {
210 intermediaryApi.updateAutomationCompositionElementState(
211 instanceElement.instanceId(), instanceElement.elementId(),
212 DeployState.DEPLOYED, null, StateChangeResult.NO_ERROR, "Updated");
214 intermediaryApi.updateAutomationCompositionElementState(
215 instanceElement.instanceId(), instanceElement.elementId(),
216 DeployState.DEPLOYED, null, StateChangeResult.FAILED, "Update failed!");
221 * Get AutomationComposition.
223 * @return the AutomationCompositions
225 public AutomationCompositions getAutomationCompositions() {
226 var result = new AutomationCompositions();
227 result.setAutomationCompositionList(new ArrayList<>(intermediaryApi.getAutomationCompositions().values()));
231 public AutomationComposition getAutomationComposition(UUID instanceId) {
232 return intermediaryApi.getAutomationComposition(instanceId);
238 * @param automationCompositionId the automationComposition Id
239 * @param elementId the automationComposition Element Id
240 * @param useState the useState
241 * @param operationalState the operationalState
242 * @param outProperties the outProperties
244 public void setOutProperties(UUID automationCompositionId, UUID elementId, String useState, String operationalState,
245 Map<String, Object> outProperties) {
246 intermediaryApi.sendAcElementInfo(automationCompositionId, elementId, useState, operationalState,
251 public void prime(CompositionDto composition) throws PfModelException {
252 LOGGER.debug("prime call composition: {}", composition);
254 if (!execution(config.getPrimeTimerMs(), "Current Thread prime is Interrupted during execution {}",
255 composition.compositionId())) {
259 if (config.isPrimeSuccess()) {
260 intermediaryApi.updateCompositionState(composition.compositionId(),
261 AcTypeState.PRIMED, StateChangeResult.NO_ERROR, "Primed");
263 intermediaryApi.updateCompositionState(composition.compositionId(),
264 AcTypeState.COMMISSIONED, StateChangeResult.FAILED, "Prime failed!");
269 public void deprime(CompositionDto composition) throws PfModelException {
270 LOGGER.debug("deprime call composition: {}", composition);
272 if (!execution(config.getDeprimeTimerMs(), "Current Thread deprime is Interrupted during execution {}",
273 composition.compositionId())) {
277 if (config.isDeprimeSuccess()) {
278 intermediaryApi.updateCompositionState(composition.compositionId(), AcTypeState.COMMISSIONED,
279 StateChangeResult.NO_ERROR, "Deprimed");
281 intermediaryApi.updateCompositionState(composition.compositionId(), AcTypeState.PRIMED,
282 StateChangeResult.FAILED, "Deprime failed!");
287 * Get Instance Data List.
289 * @return the InternalDatas
291 public InternalDatas getDataList() {
292 var result = new InternalDatas();
293 var map = intermediaryApi.getAutomationCompositions();
294 for (var instance : map.values()) {
295 for (var element : instance.getElements().values()) {
296 var data = new InternalData();
297 data.setCompositionId(instance.getCompositionId());
298 data.setCompositionDefinitionElementId(element.getDefinition());
299 data.setAutomationCompositionId(instance.getInstanceId());
300 data.setAutomationCompositionElementId(element.getId());
301 data.setIntProperties(element.getProperties());
302 data.setOperationalState(element.getOperationalState());
303 data.setUseState(element.getUseState());
304 data.setOutProperties(element.getOutProperties());
305 result.getList().add(data);
312 public void handleRestartComposition(CompositionDto composition, AcTypeState state) throws PfModelException {
313 LOGGER.debug("restart composition definition call");
320 deprime(composition);
324 intermediaryApi.updateCompositionState(composition.compositionId(), state,
325 StateChangeResult.NO_ERROR, "Restarted");
330 public void handleRestartInstance(CompositionElementDto compositionElement, InstanceElementDto instanceElement,
331 DeployState deployState, LockState lockState) throws PfModelException {
332 LOGGER.debug("restart instance call");
333 if (!AcmUtils.isInTransitionalState(deployState, lockState)) {
334 intermediaryApi.updateAutomationCompositionElementState(
335 instanceElement.instanceId(), instanceElement.elementId(), deployState, lockState,
336 StateChangeResult.NO_ERROR, "Restarted");
339 if (DeployState.DEPLOYING.equals(deployState)) {
340 deploy(compositionElement, instanceElement);
343 if (DeployState.UNDEPLOYING.equals(deployState)) {
344 undeploy(compositionElement, instanceElement);
347 if (DeployState.UPDATING.equals(deployState)) {
348 update(compositionElement, instanceElement, instanceElement);
351 if (DeployState.DELETING.equals(deployState)) {
352 delete(compositionElement, instanceElement);
355 if (LockState.LOCKING.equals(lockState)) {
356 lock(compositionElement, instanceElement);
359 if (LockState.UNLOCKING.equals(lockState)) {
360 unlock(compositionElement, instanceElement);
365 * Get Composition Data List.
367 * @return the InternalDatas
369 public InternalDatas getCompositionDataList() {
370 var acElementsDefinitions = intermediaryApi.getAcElementsDefinitions();
371 var internalDatas = new InternalDatas();
372 for (var entry : acElementsDefinitions.entrySet()) {
373 for (var acElementsDefinition : entry.getValue().values()) {
374 var internalData = new InternalData();
375 internalData.setCompositionId(entry.getKey());
376 internalData.setCompositionDefinitionElementId(acElementsDefinition.getAcElementDefinitionId());
377 internalData.setIntProperties(
378 acElementsDefinition.getAutomationCompositionElementToscaNodeTemplate().getProperties());
379 internalData.setOutProperties(acElementsDefinition.getOutProperties());
380 internalDatas.getList().add(internalData);
383 return internalDatas;
386 public void setCompositionOutProperties(UUID compositionId, ToscaConceptIdentifier compositionDefinitionElementId,
387 Map<String, Object> outProperties) {
388 intermediaryApi.sendAcDefinitionInfo(compositionId, compositionDefinitionElementId, outProperties);
393 public void migrate(CompositionElementDto compositionElement, CompositionElementDto compositionElementTarget,
394 InstanceElementDto instanceElement, InstanceElementDto instanceElementMigrate)
395 throws PfModelException {
396 LOGGER.debug("migrate call compositionElement: {}, compositionElementTarget: {}, instanceElement: {},"
397 + " instanceElementMigrate: {}",
398 compositionElement, compositionElementTarget, instanceElement, instanceElementMigrate);
400 if (!execution(config.getMigrateTimerMs(), "Current Thread migrate is Interrupted during execution {}",
401 instanceElement.elementId())) {
405 if (config.isMigrateSuccess()) {
406 intermediaryApi.updateAutomationCompositionElementState(
407 instanceElement.instanceId(), instanceElement.elementId(),
408 DeployState.DEPLOYED, null, StateChangeResult.NO_ERROR, "Migrated");
410 intermediaryApi.updateAutomationCompositionElementState(
411 instanceElement.instanceId(), instanceElement.elementId(),
412 DeployState.DEPLOYED, null, StateChangeResult.FAILED, "Migrate failed!");