From e8369d6d3088b7b68acb987ebff432ac830a3200 Mon Sep 17 00:00:00 2001 From: Jim Hahn Date: Mon, 26 Oct 2020 16:48:47 -0400 Subject: Make drools-apps event agnostic Removed tdjam and frankfurt controllers, which use event-specific actors. Issue-ID: POLICY-2804 Change-Id: Ica05f80bf72d039d9c4903591af7fb3793a81159 Signed-off-by: Jim Hahn --- .../eventmanager/ControlLoopEventManager2Test.java | 848 ---------------- .../ControlLoopOperationManager2Test.java | 1037 -------------------- .../controlloop/eventmanager/LockDataTest.java | 8 +- .../policy/controlloop/eventmanager/StepTest.java | 10 +- 4 files changed, 6 insertions(+), 1897 deletions(-) delete mode 100644 controlloop/common/eventmanager/src/test/java/org/onap/policy/controlloop/eventmanager/ControlLoopEventManager2Test.java delete mode 100644 controlloop/common/eventmanager/src/test/java/org/onap/policy/controlloop/eventmanager/ControlLoopOperationManager2Test.java (limited to 'controlloop/common/eventmanager/src/test') diff --git a/controlloop/common/eventmanager/src/test/java/org/onap/policy/controlloop/eventmanager/ControlLoopEventManager2Test.java b/controlloop/common/eventmanager/src/test/java/org/onap/policy/controlloop/eventmanager/ControlLoopEventManager2Test.java deleted file mode 100644 index d3c217c9f..000000000 --- a/controlloop/common/eventmanager/src/test/java/org/onap/policy/controlloop/eventmanager/ControlLoopEventManager2Test.java +++ /dev/null @@ -1,848 +0,0 @@ -/*- - * ============LICENSE_START======================================================= - * ONAP - * ================================================================================ - * Copyright (C) 2020 AT&T Intellectual Property. All rights reserved. - * ================================================================================ - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - * ============LICENSE_END========================================================= - */ - -package org.onap.policy.controlloop.eventmanager; - -import static org.assertj.core.api.Assertions.assertThatCode; -import static org.assertj.core.api.Assertions.assertThatThrownBy; -import static org.junit.Assert.assertEquals; -import static org.junit.Assert.assertFalse; -import static org.junit.Assert.assertNotNull; -import static org.junit.Assert.assertNull; -import static org.junit.Assert.assertSame; -import static org.junit.Assert.assertTrue; -import static org.mockito.ArgumentMatchers.any; -import static org.mockito.ArgumentMatchers.anyLong; -import static org.mockito.Mockito.never; -import static org.mockito.Mockito.times; -import static org.mockito.Mockito.verify; -import static org.mockito.Mockito.when; - -import java.util.ArrayList; -import java.util.Arrays; -import java.util.List; -import java.util.Map; -import java.util.TreeMap; -import java.util.UUID; -import java.util.concurrent.CompletableFuture; -import java.util.concurrent.ExecutorService; -import java.util.function.Consumer; -import org.drools.core.WorkingMemory; -import org.junit.Before; -import org.junit.Test; -import org.kie.api.runtime.rule.FactHandle; -import org.mockito.ArgumentCaptor; -import org.mockito.Mock; -import org.mockito.MockitoAnnotations; -import org.onap.policy.common.utils.coder.Coder; -import org.onap.policy.common.utils.coder.CoderException; -import org.onap.policy.common.utils.coder.StandardYamlCoder; -import org.onap.policy.common.utils.io.Serializer; -import org.onap.policy.common.utils.resources.ResourceUtils; -import org.onap.policy.controlloop.ControlLoopEventStatus; -import org.onap.policy.controlloop.ControlLoopException; -import org.onap.policy.controlloop.ControlLoopNotificationType; -import org.onap.policy.controlloop.ControlLoopOperation; -import org.onap.policy.controlloop.ControlLoopTargetType; -import org.onap.policy.controlloop.VirtualControlLoopEvent; -import org.onap.policy.controlloop.VirtualControlLoopNotification; -import org.onap.policy.controlloop.actorserviceprovider.ActorService; -import org.onap.policy.controlloop.actorserviceprovider.OperationOutcome; -import org.onap.policy.controlloop.actorserviceprovider.OperationResult; -import org.onap.policy.controlloop.actorserviceprovider.controlloop.ControlLoopEventContext; -import org.onap.policy.controlloop.drl.legacy.ControlLoopParams; -import org.onap.policy.controlloop.eventmanager.ControlLoopEventManager2.NewEventStatus; -import org.onap.policy.controlloop.eventmanager.ControlLoopOperationManager2.State; -import org.onap.policy.controlloop.ophistory.OperationHistoryDataManager; -import org.onap.policy.drools.core.lock.LockCallback; -import org.onap.policy.drools.core.lock.LockImpl; -import org.onap.policy.drools.core.lock.LockState; -import org.onap.policy.drools.domain.models.operational.Operation; -import org.onap.policy.models.tosca.authorative.concepts.ToscaPolicy; -import org.onap.policy.models.tosca.authorative.concepts.ToscaServiceTemplate; - -public class ControlLoopEventManager2Test { - private static final UUID REQ_ID = UUID.randomUUID(); - private static final String CL_NAME = "my-closed-loop-name"; - private static final String POLICY_NAME = "my-policy-name"; - private static final String POLICY_SCOPE = "my-scope"; - private static final String POLICY_VERSION = "1.2.3"; - private static final String MY_TARGET = "my-target"; - private static final String LOCK1 = "my-lock-A"; - private static final String LOCK2 = "my-lock-B"; - private static final Coder yamlCoder = new StandardYamlCoder(); - - @Mock - private WorkingMemory workMem; - @Mock - private Consumer callback1; - @Mock - private Consumer callback2; - @Mock - private Consumer callback3; - @Mock - private FactHandle factHandle; - @Mock - private ActorService actors; - @Mock - private OperationHistoryDataManager dataMgr; - @Mock - private ControlLoopOperationManager2 oper1; - @Mock - private ControlLoopOperationManager2 oper2; - @Mock - private ControlLoopOperationManager2 oper3; - @Mock - private ExecutorService executor; - - private long preCreateTimeMs; - private List locks; - private ToscaPolicy tosca; - private ControlLoopParams params; - private VirtualControlLoopEvent event; - private int updateCount; - private ControlLoopEventManager2Drools mgr; - - /** - * Sets up. - */ - @Before - public void setUp() throws ControlLoopException, CoderException { - MockitoAnnotations.initMocks(this); - - when(oper1.getHistory()).thenReturn(makeHistory("A")); - when(oper2.getHistory()).thenReturn(makeHistory("B")); - when(oper3.getHistory()).thenReturn(makeHistory("C")); - - when(oper1.getActor()).thenReturn("First"); - when(oper1.getOperation()).thenReturn("OperationA"); - when(oper1.getOperationMessage()).thenReturn("message-A"); - when(oper1.getOperationHistory()).thenReturn("history-A"); - - when(oper2.getActor()).thenReturn("Second"); - when(oper2.getOperation()).thenReturn("OperationB"); - when(oper2.getOperationMessage()).thenReturn("message-B"); - when(oper2.getOperationHistory()).thenReturn("history-B"); - - when(oper3.getActor()).thenReturn("Third"); - when(oper3.getOperation()).thenReturn("OperationC"); - when(oper3.getOperationMessage()).thenReturn("message-C"); - when(oper3.getOperationHistory()).thenReturn("history-C"); - - when(workMem.getFactHandle(any())).thenReturn(factHandle); - - event = new VirtualControlLoopEvent(); - event.setRequestId(REQ_ID); - event.setTarget(ControlLoopOperationManager2.VSERVER_VSERVER_NAME); - event.setAai(new TreeMap<>(Map.of(ControlLoopOperationManager2.VSERVER_VSERVER_NAME, MY_TARGET))); - event.setClosedLoopEventStatus(ControlLoopEventStatus.ONSET); - event.setClosedLoopControlName(CL_NAME); - event.setTargetType(ControlLoopTargetType.VNF); - - params = new ControlLoopParams(); - params.setClosedLoopControlName(CL_NAME); - params.setPolicyName(POLICY_NAME); - params.setPolicyScope(POLICY_SCOPE); - params.setPolicyVersion(POLICY_VERSION); - - loadPolicy("eventManager/event-mgr-simple.yaml"); - - locks = new ArrayList<>(); - - updateCount = 0; - - preCreateTimeMs = System.currentTimeMillis(); - - mgr = new MyManagerWithOper(params, event, workMem); - } - - @Test - public void testConstructor() { - assertEquals(POLICY_NAME, mgr.getPolicyName()); - - Map orig = event.getAai(); - - event.setAai(addAai(orig, ControlLoopEventManager2.VSERVER_IS_CLOSED_LOOP_DISABLED, "true")); - assertThatThrownBy(() -> new ControlLoopEventManager2Drools(params, event, workMem)) - .hasMessage("is-closed-loop-disabled is set to true on VServer or VNF"); - - // vserver ACTIVE - event.setAai(addAai(orig, ControlLoopEventManager2.VSERVER_PROV_STATUS, - ControlLoopEventManager2.PROV_STATUS_ACTIVE.toUpperCase())); - assertThatCode(() -> new ControlLoopEventManager2Drools(params, event, workMem)).doesNotThrowAnyException(); - - // vserver active - event.setAai(addAai(orig, ControlLoopEventManager2.VSERVER_PROV_STATUS, - ControlLoopEventManager2.PROV_STATUS_ACTIVE.toLowerCase())); - assertThatCode(() -> new ControlLoopEventManager2Drools(params, event, workMem)).doesNotThrowAnyException(); - - // vserver inactive - event.setAai(addAai(orig, ControlLoopEventManager2.VSERVER_PROV_STATUS, "inactive")); - assertThatThrownBy(() -> new ControlLoopEventManager2Drools(params, event, workMem)) - .hasMessage("prov-status is not ACTIVE on VServer or VNF"); - - // vnf ACTIVE - event.setAai(addAai(orig, ControlLoopEventManager2.GENERIC_VNF_PROV_STATUS, - ControlLoopEventManager2.PROV_STATUS_ACTIVE.toUpperCase())); - assertThatCode(() -> new ControlLoopEventManager2Drools(params, event, workMem)).doesNotThrowAnyException(); - - // vnf active - event.setAai(addAai(orig, ControlLoopEventManager2.GENERIC_VNF_PROV_STATUS, - ControlLoopEventManager2.PROV_STATUS_ACTIVE.toLowerCase())); - assertThatCode(() -> new ControlLoopEventManager2Drools(params, event, workMem)).doesNotThrowAnyException(); - - // vnf inactive - event.setAai(addAai(orig, ControlLoopEventManager2.GENERIC_VNF_PROV_STATUS, "inactive")); - assertThatThrownBy(() -> new ControlLoopEventManager2Drools(params, event, workMem)) - .hasMessage("prov-status is not ACTIVE on VServer or VNF"); - - // valid - event.setAai(orig); - assertThatCode(() -> mgr.checkEventSyntax(event)).doesNotThrowAnyException(); - - // invalid - event.setTarget("unknown-target"); - assertThatThrownBy(() -> new ControlLoopEventManager2Drools(params, event, workMem)) - .isInstanceOf(ControlLoopException.class); - } - - /** - * Runs through a policy that has several operations. - */ - @Test - public void testMultiOperation() throws Exception { - - loadPolicy("eventManager/event-mgr-multi.yaml"); - - mgr = new MyManagerWithOper(params, event, workMem); - mgr.start(); - - for (ControlLoopOperationManager2 oper : Arrays.asList(oper1, oper2, oper3)) { - assertTrue(mgr.isActive()); - nextStep(oper, true, OperationResult.SUCCESS); - runRule(); - - assertTrue(mgr.isActive()); - nextStep(oper, false, OperationResult.SUCCESS); - runRule(); - } - - assertFalse(mgr.isActive()); - } - - @Test - public void testStart() throws Exception { - // start it - mgr.start(); - - // cannot re-start - assertThatCode(() -> mgr.start()).isInstanceOf(IllegalStateException.class) - .hasMessage("manager already started"); - } - - /** - * Tests start() error cases. - */ - @Test - public void testStartErrors() throws Exception { - // wrong jvm - ControlLoopEventManager2Drools mgr2 = new ControlLoopEventManager2Drools(params, event, workMem); - ControlLoopEventManager2Drools mgr3 = Serializer.roundTrip(mgr2); - assertThatCode(() -> mgr3.start()).isInstanceOf(IllegalStateException.class) - .hasMessage("manager is no longer active"); - - // no fact handle - when(workMem.getFactHandle(any())).thenReturn(null); - assertThatCode(() -> mgr.start()).isInstanceOf(IllegalStateException.class) - .hasMessage("manager is not in working memory"); - } - - @Test - public void testNextStep_testStartOperationSuccess() throws ControlLoopException { - runOperation(OperationResult.SUCCESS); - - VirtualControlLoopNotification notif = mgr.getNotification(); - assertEquals(ControlLoopNotificationType.FINAL_SUCCESS, notif.getNotification()); - assertNull(notif.getMessage()); - - assertThatCode(() -> mgr.nextStep()).doesNotThrowAnyException(); - } - - /** - * Tests nextStep() when the next step is invalid, which should cause an exception to - * be thrown by the processor. - */ - @Test - public void testNextStepMissing() throws Exception { - mgr.start(); - - when(oper1.nextStep()).thenThrow(new IllegalArgumentException("expected exception")); - - mgr.nextStep(); - - assertFalse(mgr.isActive()); - - VirtualControlLoopNotification notif = mgr.getNotification(); - assertEquals(ControlLoopNotificationType.FINAL_FAILURE, notif.getNotification()); - assertEquals("Policy processing aborted due to policy error", notif.getMessage()); - assertTrue(notif.getHistory().isEmpty()); - } - - /** - * Tests startOperation() with FINAL_FAILURE_EXCEPTION. - */ - @Test - public void testStartOperationException() throws ControlLoopException { - runOperation(OperationResult.FAILURE_EXCEPTION); - - VirtualControlLoopNotification notif = mgr.getNotification(); - assertEquals(ControlLoopNotificationType.FINAL_FAILURE, notif.getNotification()); - assertEquals("Exception in processing closed loop", notif.getMessage()); - } - - /** - * Tests startOperation() with FINAL_FAILURE. - */ - @Test - public void testStartOperationFailure() throws ControlLoopException { - runOperation(OperationResult.FAILURE); - - VirtualControlLoopNotification notif = mgr.getNotification(); - assertEquals(ControlLoopNotificationType.FINAL_FAILURE, notif.getNotification()); - assertNull(notif.getMessage()); - } - - /** - * Tests startOperation() with FINAL_OPENLOOP. - */ - @Test - public void testStartOperationOpenLoop() throws ControlLoopException { - runOperation(OperationResult.FAILURE_GUARD); - - VirtualControlLoopNotification notif = mgr.getNotification(); - assertEquals(ControlLoopNotificationType.FINAL_OPENLOOP, notif.getNotification()); - assertNull(notif.getMessage()); - } - - @Test - public void testIsActive() throws Exception { - mgr = new ControlLoopEventManager2Drools(params, event, workMem); - assertTrue(mgr.isActive()); - - ControlLoopEventManager2Drools mgr2 = Serializer.roundTrip(mgr); - assertFalse(mgr2.isActive()); - } - - @Test - public void testUpdated() throws ControlLoopException { - mgr.start(); - - // not the active operation - should be ignored - mgr.updated(oper3); - verify(workMem, never()).update(any(), any()); - - VirtualControlLoopNotification notif; - - // check notification data - when(oper1.getState()).thenReturn(State.LOCK_DENIED); - mgr.updated(oper1); - notif = mgr.getNotification(); - assertNotNull(notif.getHistory()); - - /* - * try the various cases - */ - when(oper1.getState()).thenReturn(State.LOCK_DENIED); - mgr.updated(oper1); - verifyNotification(ControlLoopNotificationType.REJECTED, "The target my-target is already locked"); - - when(oper1.getState()).thenReturn(State.LOCK_LOST); - mgr.updated(oper1); - verifyNotification(ControlLoopNotificationType.OPERATION_FAILURE, "The target my-target is no longer locked"); - - when(oper1.getState()).thenReturn(State.GUARD_STARTED); - mgr.updated(oper1); - verifyNotification(ControlLoopNotificationType.OPERATION, "Sending guard query for First OperationA"); - - when(oper1.getState()).thenReturn(State.GUARD_PERMITTED); - mgr.updated(oper1); - verifyNotification(ControlLoopNotificationType.OPERATION, "Guard result for First OperationA is Permit"); - - when(oper1.getState()).thenReturn(State.GUARD_DENIED); - mgr.updated(oper1); - verifyNotification(ControlLoopNotificationType.OPERATION, "Guard result for First OperationA is Deny"); - - when(oper1.getState()).thenReturn(State.OPERATION_STARTED); - mgr.updated(oper1); - verifyNotification(ControlLoopNotificationType.OPERATION, "message-A"); - - when(oper1.getState()).thenReturn(State.OPERATION_SUCCESS); - mgr.updated(oper1); - verifyNotification(ControlLoopNotificationType.OPERATION_SUCCESS, "history-A"); - - when(oper1.getState()).thenReturn(State.OPERATION_FAILURE); - mgr.updated(oper1); - verifyNotification(ControlLoopNotificationType.OPERATION_FAILURE, "history-A"); - - // should still be active - assertTrue(mgr.isActive()); - - /* - * control loop time - */ - when(oper1.getState()).thenReturn(State.CONTROL_LOOP_TIMEOUT); - mgr.updated(oper1); - verifyNotification(ControlLoopNotificationType.FINAL_FAILURE, "Control Loop timed out"); - - // should now be done - assertFalse(mgr.isActive()); - } - - @Test - public void testDestroy() { - mgr.requestLock(LOCK1, callback1); - mgr.requestLock(LOCK2, callback2); - mgr.requestLock(LOCK1, callback3); - - mgr.destroy(); - - freeLocks(); - - for (LockImpl lock : locks) { - assertTrue(lock.isUnavailable()); - } - } - - /** - * Tests destroy() once it has been started. - */ - @Test - public void testDestroyStarted() throws ControlLoopException { - mgr.start(); - - mgr.requestLock(LOCK1, callback1); - mgr.requestLock(LOCK2, callback2); - mgr.requestLock(LOCK1, callback3); - - mgr.destroy(); - - freeLocks(); - - // should have canceled the operation - verify(oper1).cancel(); - - for (LockImpl lock : locks) { - assertTrue(lock.isUnavailable()); - } - } - - @Test - public void testMakeNotification() throws ControlLoopException { - // before started - assertNotNull(mgr.makeNotification()); - - mgr.start(); - - nextStep(oper1, true, OperationResult.SUCCESS); - runRule(); - - // check notification while running - VirtualControlLoopNotification notif = mgr.getNotification(); - assertEquals("history-A", notif.getMessage()); - - List history = notif.getHistory(); - assertNotNull(history); - - nextStep(oper1, false, OperationResult.SUCCESS); - runRule(); - - assertFalse(mgr.isActive()); - - // check notification when complete - notif = mgr.getNotification(); - assertNull(notif.getMessage()); - assertEquals(history, notif.getHistory()); - } - - @Test - public void testOnNewEvent() { - VirtualControlLoopEvent event2 = new VirtualControlLoopEvent(event); - assertEquals(NewEventStatus.FIRST_ONSET, mgr.onNewEvent(event2)); - - event2.setPayload("other payload"); - assertEquals(NewEventStatus.SUBSEQUENT_ONSET, mgr.onNewEvent(event2)); - assertEquals(NewEventStatus.SUBSEQUENT_ONSET, mgr.onNewEvent(event2)); - assertEquals(NewEventStatus.FIRST_ONSET, mgr.onNewEvent(event)); - - event2.setClosedLoopEventStatus(ControlLoopEventStatus.ABATED); - assertEquals(NewEventStatus.FIRST_ABATEMENT, mgr.onNewEvent(event2)); - - assertEquals(NewEventStatus.SUBSEQUENT_ABATEMENT, mgr.onNewEvent(event2)); - assertEquals(NewEventStatus.SUBSEQUENT_ABATEMENT, mgr.onNewEvent(event2)); - - event2.setClosedLoopEventStatus(null); - assertEquals(NewEventStatus.SYNTAX_ERROR, mgr.onNewEvent(event2)); - } - - @Test - public void testDetmControlLoopTimeoutMs() throws Exception { - verifyTimeout(1200 * 1000L); - } - - private void verifyTimeout(long timeMs) { - long end = mgr.getEndTimeMs(); - assertTrue(end >= preCreateTimeMs + timeMs); - assertTrue(end < preCreateTimeMs + timeMs + 5000); - } - - @Test - public void testCheckEventSyntax() { - // initially, it's valid - assertThatCode(() -> mgr.checkEventSyntax(event)).doesNotThrowAnyException(); - - event.setTarget("unknown-target"); - assertThatCode(() -> mgr.checkEventSyntax(event)).isInstanceOf(ControlLoopException.class) - .hasMessage("target field invalid"); - - event.setTarget(null); - assertThatCode(() -> mgr.checkEventSyntax(event)).isInstanceOf(ControlLoopException.class) - .hasMessage("No target field"); - - // abated supersedes previous errors - so it shouldn't throw an exception - event.setClosedLoopEventStatus(ControlLoopEventStatus.ABATED); - assertThatCode(() -> mgr.checkEventSyntax(event)).doesNotThrowAnyException(); - - event.setRequestId(null); - assertThatCode(() -> mgr.checkEventSyntax(event)).isInstanceOf(ControlLoopException.class) - .hasMessage("No request ID"); - - event.setClosedLoopControlName(null); - assertThatCode(() -> mgr.checkEventSyntax(event)).isInstanceOf(ControlLoopException.class) - .hasMessage("No control loop name"); - } - - @Test - public void testValidateStatus() { - event.setClosedLoopEventStatus(ControlLoopEventStatus.ONSET); - assertThatCode(() -> mgr.checkEventSyntax(event)).doesNotThrowAnyException(); - - event.setClosedLoopEventStatus(ControlLoopEventStatus.ABATED); - assertThatCode(() -> mgr.checkEventSyntax(event)).doesNotThrowAnyException(); - - event.setClosedLoopEventStatus(null); - assertThatCode(() -> mgr.checkEventSyntax(event)).isInstanceOf(ControlLoopException.class) - .hasMessage("Invalid value in closedLoopEventStatus"); - } - - @Test - public void testValidateAaiData() { - event.setTargetType("unknown-target-type"); - assertThatCode(() -> mgr.checkEventSyntax(event)).isInstanceOf(ControlLoopException.class) - .hasMessage("The target type is not supported"); - - event.setTargetType(null); - assertThatCode(() -> mgr.checkEventSyntax(event)).isInstanceOf(ControlLoopException.class) - .hasMessage("The Target type is null"); - - event.setAai(null); - assertThatCode(() -> mgr.checkEventSyntax(event)).isInstanceOf(ControlLoopException.class) - .hasMessage("AAI is null"); - - // VM case - event.setTargetType(ControlLoopTargetType.VM); - event.setAai(Map.of(ControlLoopEventManager2.GENERIC_VNF_VNF_ID, MY_TARGET)); - assertThatCode(() -> mgr.checkEventSyntax(event)).doesNotThrowAnyException(); - - event.setAai(Map.of()); - assertThatCode(() -> mgr.checkEventSyntax(event)).isInstanceOf(ControlLoopException.class); - - // VNF case - event.setTargetType(ControlLoopTargetType.VNF); - event.setAai(Map.of(ControlLoopEventManager2.GENERIC_VNF_VNF_ID, MY_TARGET)); - assertThatCode(() -> mgr.checkEventSyntax(event)).doesNotThrowAnyException(); - - event.setAai(Map.of()); - assertThatCode(() -> mgr.checkEventSyntax(event)).isInstanceOf(ControlLoopException.class); - - // PNF case - event.setTargetType(ControlLoopTargetType.PNF); - event.setAai(Map.of(ControlLoopEventManager2.PNF_NAME, MY_TARGET)); - assertThatCode(() -> mgr.checkEventSyntax(event)).doesNotThrowAnyException(); - - event.setAai(Map.of()); - assertThatCode(() -> mgr.checkEventSyntax(event)).isInstanceOf(ControlLoopException.class); - } - - @Test - public void testValidateAaiVmVnfData() { - event.setTargetType(ControlLoopTargetType.VM); - event.setAai(Map.of(ControlLoopEventManager2.GENERIC_VNF_VNF_ID, MY_TARGET)); - assertThatCode(() -> mgr.checkEventSyntax(event)).doesNotThrowAnyException(); - - event.setAai(Map.of(ControlLoopEventManager2.VSERVER_VSERVER_NAME, MY_TARGET)); - assertThatCode(() -> mgr.checkEventSyntax(event)).doesNotThrowAnyException(); - - event.setAai(Map.of(ControlLoopEventManager2.GENERIC_VNF_VNF_NAME, MY_TARGET)); - assertThatCode(() -> mgr.checkEventSyntax(event)).doesNotThrowAnyException(); - - event.setAai(Map.of()); - assertThatCode(() -> mgr.checkEventSyntax(event)).isInstanceOf(ControlLoopException.class).hasMessage( - "generic-vnf.vnf-id or generic-vnf.vnf-name or vserver.vserver-name information missing"); - } - - @Test - public void testValidateAaiPnfData() { - event.setTargetType(ControlLoopTargetType.PNF); - event.setAai(Map.of(ControlLoopEventManager2.PNF_NAME, MY_TARGET)); - assertThatCode(() -> mgr.checkEventSyntax(event)).doesNotThrowAnyException(); - - event.setAai(Map.of()); - assertThatCode(() -> mgr.checkEventSyntax(event)).isInstanceOf(ControlLoopException.class) - .hasMessage("AAI PNF object key pnf-name is missing"); - } - - @Test - public void testIsClosedLoopDisabled() { - Map orig = event.getAai(); - - event.setAai(addAai(orig, ControlLoopEventManager2.VSERVER_IS_CLOSED_LOOP_DISABLED, "true")); - assertThatThrownBy(() -> new ControlLoopEventManager2Drools(params, event, workMem)) - .isInstanceOf(IllegalStateException.class); - - event.setAai(addAai(orig, ControlLoopEventManager2.GENERIC_VNF_IS_CLOSED_LOOP_DISABLED, "true")); - assertThatThrownBy(() -> new ControlLoopEventManager2Drools(params, event, workMem)) - .isInstanceOf(IllegalStateException.class); - - event.setAai(addAai(orig, ControlLoopEventManager2.PNF_IS_IN_MAINT, "true")); - assertThatThrownBy(() -> new ControlLoopEventManager2Drools(params, event, workMem)) - .isInstanceOf(IllegalStateException.class); - } - - private Map addAai(Map original, String key, String value) { - Map map = new TreeMap<>(original); - map.put(key, value); - return map; - } - - @Test - public void testIsProvStatusInactive() { - Map orig = event.getAai(); - - event.setAai(addAai(orig, ControlLoopEventManager2.VSERVER_PROV_STATUS, "ACTIVE")); - assertThatCode(() -> new ControlLoopEventManager2Drools(params, event, workMem)).doesNotThrowAnyException(); - - event.setAai(addAai(orig, ControlLoopEventManager2.VSERVER_PROV_STATUS, "inactive")); - assertThatThrownBy(() -> new ControlLoopEventManager2Drools(params, event, workMem)) - .isInstanceOf(IllegalStateException.class); - - event.setAai(addAai(orig, ControlLoopEventManager2.GENERIC_VNF_PROV_STATUS, "ACTIVE")); - assertThatCode(() -> new ControlLoopEventManager2Drools(params, event, workMem)).doesNotThrowAnyException(); - event.setAai(addAai(orig, ControlLoopEventManager2.GENERIC_VNF_PROV_STATUS, "inactive")); - assertThatThrownBy(() -> new ControlLoopEventManager2Drools(params, event, workMem)) - .isInstanceOf(IllegalStateException.class); - } - - @Test - public void testIsAaiTrue() { - Map orig = event.getAai(); - - for (String value : Arrays.asList("yes", "y", "true", "t", "yEs", "trUe")) { - event.setAai(addAai(orig, ControlLoopEventManager2.VSERVER_IS_CLOSED_LOOP_DISABLED, value)); - assertThatThrownBy(() -> new ControlLoopEventManager2Drools(params, event, workMem)) - .isInstanceOf(IllegalStateException.class); - } - - event.setAai(addAai(orig, ControlLoopEventManager2.VSERVER_IS_CLOSED_LOOP_DISABLED, "false")); - assertThatCode(() -> new ControlLoopEventManager2Drools(params, event, workMem)).doesNotThrowAnyException(); - - event.setAai(addAai(orig, ControlLoopEventManager2.VSERVER_IS_CLOSED_LOOP_DISABLED, "no")); - assertThatCode(() -> new ControlLoopEventManager2Drools(params, event, workMem)).doesNotThrowAnyException(); - } - - @Test - public void testRequestLock() { - final CompletableFuture future1 = mgr.requestLock(LOCK1, callback1); - final CompletableFuture future2 = mgr.requestLock(LOCK2, callback2); - assertSame(future1, mgr.requestLock(LOCK1, callback3)); - - assertEquals(2, locks.size()); - - assertTrue(future1.isDone()); - assertTrue(future2.isDone()); - - verify(callback1, never()).accept(any()); - verify(callback2, never()).accept(any()); - verify(callback3, never()).accept(any()); - - // indicate that the first lock failed - locks.get(0).notifyUnavailable(); - - verify(callback1).accept(any()); - verify(callback2, never()).accept(any()); - verify(callback3).accept(any()); - } - - @Test - public void testMakeOperationManager() throws ControlLoopException { - // use a manager that creates real operation managers - mgr = new MyManager(params, event, workMem); - - assertThatCode(() -> mgr.start()).doesNotThrowAnyException(); - } - - @Test - public void testGetBlockingExecutor() throws Exception { - mgr = new ControlLoopEventManager2Drools(params, event, workMem); - assertThatCode(() -> mgr.getBlockingExecutor()).doesNotThrowAnyException(); - } - - @Test - public void testToString() { - assertNotNull(mgr.toString()); - } - - - private void nextStep(ControlLoopOperationManager2 oper, boolean moreSteps, OperationResult result) { - when(oper.nextStep()).thenReturn(moreSteps); - when(oper.getOperationResult()).thenReturn(result); - - if (result == OperationResult.SUCCESS) { - when(oper.getState()).thenReturn(State.OPERATION_SUCCESS); - } else { - when(oper.getState()).thenReturn(State.OPERATION_FAILURE); - } - - mgr.updated(oper); - - updateCount++; - - verify(workMem, times(updateCount)).update(factHandle, mgr); - } - - private void runRule() { - assertTrue(mgr.isActive()); - mgr.nextStep(); - } - - private void runOperation(OperationResult finalResult) throws ControlLoopException { - mgr.start(); - verify(oper1).start(anyLong()); - - assertTrue(mgr.isActive()); - - nextStep(oper1, true, OperationResult.SUCCESS); - runRule(); - - nextStep(oper1, false, finalResult); - runRule(); - - assertFalse(mgr.isActive()); - - // should have no effect, because it's done - mgr.updated(oper1); - verify(workMem, times(updateCount)).update(any(), any()); - } - - private void verifyNotification(ControlLoopNotificationType expectedType, String expectedMsg) { - VirtualControlLoopNotification notif = mgr.getNotification(); - assertEquals(expectedType, notif.getNotification()); - assertEquals(expectedMsg, notif.getMessage()); - } - - private List makeHistory(String message) { - ControlLoopOperation clo = new ControlLoopOperation(); - clo.setMessage("history-" + message); - - return List.of(clo); - } - - private void loadPolicy(String fileName) throws CoderException { - ToscaServiceTemplate template = - yamlCoder.decode(ResourceUtils.getResourceAsString(fileName), ToscaServiceTemplate.class); - tosca = template.getToscaTopologyTemplate().getPolicies().get(0).values().iterator().next(); - - params.setToscaPolicy(tosca); - } - - private void freeLocks() { - ArgumentCaptor runCaptor = ArgumentCaptor.forClass(Runnable.class); - verify(executor).execute(runCaptor.capture()); - - runCaptor.getValue().run(); - } - - - private class MyManager extends ControlLoopEventManager2Drools { - private static final long serialVersionUID = 1L; - - public MyManager(ControlLoopParams params, VirtualControlLoopEvent event, WorkingMemory workMem) - throws ControlLoopException { - - super(params, event, workMem); - } - - @Override - protected ExecutorService getBlockingExecutor() { - return executor; - } - - @Override - protected void makeLock(String targetEntity, String requestId, int holdSec, LockCallback callback) { - LockImpl lock = new LockImpl(LockState.ACTIVE, targetEntity, requestId, holdSec, callback); - locks.add(lock); - callback.lockAvailable(lock); - } - - @Override - public ActorService getActorService() { - return actors; - } - - @Override - public OperationHistoryDataManager getDataManager() { - return dataMgr; - } - } - - - private class MyManagerWithOper extends MyManager { - private static final long serialVersionUID = 1L; - - public MyManagerWithOper(ControlLoopParams params, VirtualControlLoopEvent event, WorkingMemory workMem) - throws ControlLoopException { - - super(params, event, workMem); - } - - @Override - protected ControlLoopOperationManager2 makeOperationManager(ControlLoopEventContext ctx, Operation policy) { - switch (policy.getActorOperation().getActor()) { - case "First": - return oper1; - case "Second": - return oper2; - case "Third": - return oper3; - default: - throw new IllegalArgumentException("unknown policy actor " + policy.getActorOperation().getActor()); - } - } - } -} diff --git a/controlloop/common/eventmanager/src/test/java/org/onap/policy/controlloop/eventmanager/ControlLoopOperationManager2Test.java b/controlloop/common/eventmanager/src/test/java/org/onap/policy/controlloop/eventmanager/ControlLoopOperationManager2Test.java deleted file mode 100644 index 0b066651b..000000000 --- a/controlloop/common/eventmanager/src/test/java/org/onap/policy/controlloop/eventmanager/ControlLoopOperationManager2Test.java +++ /dev/null @@ -1,1037 +0,0 @@ -/*- - * ============LICENSE_START======================================================= - * ONAP - * ================================================================================ - * Copyright (C) 2020 AT&T Intellectual Property. All rights reserved. - * ================================================================================ - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - * ============LICENSE_END========================================================= - */ - -package org.onap.policy.controlloop.eventmanager; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.assertj.core.api.Assertions.assertThatIllegalArgumentException; -import static org.junit.Assert.assertEquals; -import static org.junit.Assert.assertFalse; -import static org.junit.Assert.assertNotNull; -import static org.junit.Assert.assertNull; -import static org.junit.Assert.assertSame; -import static org.junit.Assert.assertTrue; -import static org.mockito.ArgumentMatchers.any; -import static org.mockito.ArgumentMatchers.eq; -import static org.mockito.Mockito.doAnswer; -import static org.mockito.Mockito.never; -import static org.mockito.Mockito.times; -import static org.mockito.Mockito.verify; -import static org.mockito.Mockito.when; - -import java.time.Instant; -import java.util.Map; -import java.util.TreeMap; -import java.util.UUID; -import java.util.concurrent.CompletableFuture; -import java.util.concurrent.CountDownLatch; -import java.util.concurrent.TimeUnit; -import java.util.function.Consumer; -import org.junit.Before; -import org.junit.Test; -import org.mockito.ArgumentCaptor; -import org.mockito.Captor; -import org.mockito.Mock; -import org.mockito.MockitoAnnotations; -import org.onap.aai.domain.yang.GenericVnf; -import org.onap.policy.aai.AaiCqResponse; -import org.onap.policy.common.utils.time.PseudoExecutor; -import org.onap.policy.controlloop.ControlLoopOperation; -import org.onap.policy.controlloop.ControlLoopResponse; -import org.onap.policy.controlloop.VirtualControlLoopEvent; -import org.onap.policy.controlloop.actor.guard.DecisionOperation; -import org.onap.policy.controlloop.actor.guard.GuardActor; -import org.onap.policy.controlloop.actorserviceprovider.ActorService; -import org.onap.policy.controlloop.actorserviceprovider.Operation; -import org.onap.policy.controlloop.actorserviceprovider.OperationOutcome; -import org.onap.policy.controlloop.actorserviceprovider.OperationResult; -import org.onap.policy.controlloop.actorserviceprovider.Operator; -import org.onap.policy.controlloop.actorserviceprovider.TargetType; -import org.onap.policy.controlloop.actorserviceprovider.controlloop.ControlLoopEventContext; -import org.onap.policy.controlloop.actorserviceprovider.parameters.ControlLoopOperationParams; -import org.onap.policy.controlloop.actorserviceprovider.spi.Actor; -import org.onap.policy.controlloop.ophistory.OperationHistoryDataManager; -import org.onap.policy.drools.domain.models.operational.ActorOperation; -import org.onap.policy.drools.domain.models.operational.OperationalTarget; -import org.onap.policy.sdnr.PciBody; -import org.onap.policy.sdnr.PciMessage; -import org.onap.policy.sdnr.PciResponse; - -public class ControlLoopOperationManager2Test { - private static final UUID REQ_ID = UUID.randomUUID(); - private static final String MISMATCH = "mismatch"; - private static final String POLICY_ID = "my-policy"; - private static final String POLICY_ACTOR = "my-actor"; - private static final String POLICY_OPERATION = "my-operation"; - private static final String OTHER_ACTOR = "another-actor"; - private static final String MY_TARGET = "my-target"; - private static final String MY_VNF_ID = "my-vnf-id"; - private static final String PAYLOAD_KEY = "payload-key"; - private static final String PAYLOAD_VALUE = "payload-value"; - private static final long REMAINING_MS = 5000; - private static final int MAX_RUN = 100; - private static final Integer POLICY_RETRY = 3; - private static final Integer POLICY_TIMEOUT = 20; - private static final IllegalArgumentException EXPECTED_EXCEPTION = - new IllegalArgumentException("expected exception"); - - @Captor - private ArgumentCaptor> lockCallback; - - @Mock - private OperationHistoryDataManager dataMgr; - @Mock - private ManagerContext mgrctx; - @Mock - private Operator policyOperator; - @Mock - private Operation policyOperation; - @Mock - private Actor policyActor; - @Mock - private ActorService actors; - @Mock - private AaiCqResponse cqdata; - @Mock - private GenericVnf vnf; - - private CompletableFuture lockFuture; - private CompletableFuture policyFuture; - private ActorOperation operation; - private OperationalTarget target; - private Map entityIds; - private Map payload; - private org.onap.policy.drools.domain.models.operational.Operation policy; - private VirtualControlLoopEvent event; - private ControlLoopEventContext context; - private PseudoExecutor executor; - private ControlLoopOperationManager2 mgr; - - /** - * Sets up. - */ - @Before - public void setUp() { - MockitoAnnotations.initMocks(this); - - lockFuture = new CompletableFuture<>(); - policyFuture = new CompletableFuture<>(); - - when(mgrctx.getActorService()).thenReturn(actors); - when(mgrctx.getDataManager()).thenReturn(dataMgr); - when(mgrctx.requestLock(any(), any())).thenReturn(lockFuture); - - // configure policy operation - when(actors.getActor(POLICY_ACTOR)).thenReturn(policyActor); - when(policyActor.getOperator(POLICY_OPERATION)).thenReturn(policyOperator); - when(policyOperator.buildOperation(any())).thenReturn(policyOperation); - when(policyOperation.start()).thenReturn(policyFuture); - - when(vnf.getVnfId()).thenReturn(MY_VNF_ID); - when(cqdata.getDefaultGenericVnf()).thenReturn(vnf); - - entityIds = Map.of("entity-name-A", "entity-value-A"); - - target = OperationalTarget.builder() - .targetType(TargetType.VM.toString()) - .entityIds(entityIds) - .build(); - - payload = Map.of(PAYLOAD_KEY, PAYLOAD_VALUE); - - operation = ActorOperation.builder() - .actor(POLICY_ACTOR) - .operation(POLICY_OPERATION) - .payload(payload) - .target(target) - .build(); - - policy = org.onap.policy.drools.domain.models.operational.Operation.builder() - .id(POLICY_ID) - .actorOperation(operation) - .retries(POLICY_RETRY) - .timeout(POLICY_TIMEOUT) - .build(); - - event = new VirtualControlLoopEvent(); - event.setRequestId(REQ_ID); - event.setTarget(ControlLoopOperationManager2.VSERVER_VSERVER_NAME); - event.setAai(new TreeMap<>(Map.of(ControlLoopOperationManager2.VSERVER_VSERVER_NAME, MY_TARGET))); - - context = new ControlLoopEventContext(event); - context.setProperty(AaiCqResponse.CONTEXT_KEY, cqdata); - - executor = new PseudoExecutor(); - - mgr = new ControlLoopOperationManager2(mgrctx, context, policy, executor); - } - - @Test - public void testStart() { - mgr.start(REMAINING_MS); - - // should have determined the target entity by now - assertEquals(MY_TARGET, mgr.getTargetEntity()); - - verify(mgrctx).requestLock(eq(MY_TARGET), any()); - - lockFuture.complete(new OperationOutcome()); - genGuardOutcome(); - policyFuture.complete(genOpOutcome()); - runToCompletion(); - - assertEquals(ControlLoopOperationManager2.State.GUARD_STARTED, mgr.getState()); - - assertTrue(mgr.nextStep()); - assertEquals(ControlLoopOperationManager2.State.GUARD_PERMITTED, mgr.getState()); - - assertTrue(mgr.nextStep()); - assertEquals(ControlLoopOperationManager2.State.OPERATION_STARTED, mgr.getState()); - - assertTrue(mgr.nextStep()); - assertEquals(ControlLoopOperationManager2.State.OPERATION_SUCCESS, mgr.getState()); - - assertFalse(mgr.nextStep()); - - OperationOutcome outcome = mgr.getOutcomes().peek(); - assertEquals(OperationResult.SUCCESS, outcome.getResult()); - assertTrue(outcome.isFinalOutcome()); - - verify(mgrctx, times(4)).updated(mgr); - } - - /** - * Tests start() when detmTarget() (i.e., the first task) throws an exception. - */ - @Test - public void testStartDetmTargetException() { - operation.setTarget(OperationalTarget.builder().build()); - mgr = new ControlLoopOperationManager2(mgrctx, context, policy, executor); - mgr.start(REMAINING_MS); - - runToCompletion(); - - assertFalse(mgr.nextStep()); - assertEquals(ControlLoopOperationManager2.State.OPERATION_FAILURE, mgr.getState()); - - // should have called update() for operation-start, but not for any nextStep() - verify(mgrctx).updated(mgr); - } - - /** - * Tests start() when a subsequent task throws an exception. - */ - @Test - public void testStartException() { - when(policyOperation.start()).thenThrow(EXPECTED_EXCEPTION); - - mgr.start(REMAINING_MS); - - lockFuture.complete(new OperationOutcome()); - runToCompletion(); - - assertFalse(mgr.nextStep()); - assertEquals(ControlLoopOperationManager2.State.OPERATION_FAILURE, mgr.getState()); - - // should have called update() for operation-start, but not for any nextStep() - verify(mgrctx).updated(mgr); - } - - /** - * Tests start() when the control loop times out before the operation starts. - */ - @Test - public void testStartClTimeout_testHandleTimeout() throws InterruptedException { - // catch the callback when it times out - CountDownLatch updatedLatch = new CountDownLatch(1); - doAnswer(args -> { - updatedLatch.countDown(); - return null; - }).when(mgrctx).updated(any()); - - long tstart = System.currentTimeMillis(); - - // give it a short timeout - mgr.start(100); - - assertTrue(updatedLatch.await(5, TimeUnit.SECONDS)); - assertTrue(System.currentTimeMillis() - tstart >= 100); - - // don't generate any responses - runToCompletion(); - - // wait for the future to be canceled, via a background thread - CountDownLatch futureLatch = new CountDownLatch(1); - mgr.getFuture().whenComplete((unused, thrown) -> futureLatch.countDown()); - assertTrue(futureLatch.await(5, TimeUnit.SECONDS)); - - // lock should have been canceled - assertTrue(mgr.getFuture().isCancelled()); - - assertFalse(mgr.nextStep()); - assertEquals(ControlLoopOperationManager2.State.CONTROL_LOOP_TIMEOUT, mgr.getState()); - - // should have called update() for operation-start, but not for any nextStep() - verify(mgrctx).updated(mgr); - - // should have added a record to the DB - verify(dataMgr).store(any(), any(), any(), any()); - } - - @Test - public void testStartOperation() { - mgr.start(REMAINING_MS); - - lockFuture.complete(new OperationOutcome()); - genGuardOutcome(); - runToCompletion(); - - verify(policyOperation).start(); - - ArgumentCaptor captor = ArgumentCaptor.forClass(ControlLoopOperationParams.class); - verify(policyOperator).buildOperation(captor.capture()); - - ControlLoopOperationParams params = captor.getValue(); - - assertNotNull(params); - assertEquals(POLICY_ACTOR, params.getActor()); - assertSame(actors, params.getActorService()); - assertNotNull(params.getCompleteCallback()); - assertSame(context, params.getContext()); - assertSame(executor, params.getExecutor()); - assertEquals(POLICY_OPERATION, params.getOperation()); - assertEquals(payload, params.getPayload()); - assertSame(REQ_ID, params.getRequestId()); - assertSame(POLICY_RETRY, params.getRetry()); - assertNotNull(params.getStartCallback()); - assertEquals(target.getTargetType().toString(), params.getTargetType().toString()); - assertSame(entityIds, params.getTargetEntityIds()); - assertEquals(MY_TARGET, params.getTargetEntity()); - assertSame(POLICY_TIMEOUT, params.getTimeoutSec()); - } - - @Test - public void testStartOperationNullPayload() { - operation.setPayload(null); - mgr.start(REMAINING_MS); - - lockFuture.complete(new OperationOutcome()); - genGuardOutcome(); - runToCompletion(); - - verify(policyOperation).start(); - - ArgumentCaptor captor = ArgumentCaptor.forClass(ControlLoopOperationParams.class); - verify(policyOperator).buildOperation(captor.capture()); - - ControlLoopOperationParams params = captor.getValue(); - - assertNotNull(params); - assertEquals(POLICY_ACTOR, params.getActor()); - assertSame(actors, params.getActorService()); - assertNotNull(params.getCompleteCallback()); - assertSame(context, params.getContext()); - assertSame(executor, params.getExecutor()); - assertEquals(POLICY_OPERATION, params.getOperation()); - assertTrue(params.getPayload().isEmpty()); - assertSame(REQ_ID, params.getRequestId()); - assertSame(POLICY_RETRY, params.getRetry()); - assertNotNull(params.getStartCallback()); - assertEquals(target.getTargetType().toString(), params.getTargetType().toString()); - assertSame(entityIds, params.getTargetEntityIds()); - assertEquals(MY_TARGET, params.getTargetEntity()); - assertSame(POLICY_TIMEOUT, params.getTimeoutSec()); - } - - @Test - public void testMakeControlLoopResponse() { - final OperationOutcome outcome = new OperationOutcome(); - PciMessage msg = new PciMessage(); - outcome.setResponse(msg); - - PciBody body = new PciBody(); - msg.setBody(body); - - PciResponse output = new PciResponse(); - body.setOutput(output); - - output.setPayload("my-payload"); - - - // not an SDNR action - should return null - assertNull(mgr.makeControlLoopResponse(outcome)); - - /* - * now work with SDNR actor - */ - operation.setActor("SDNR"); - mgr = new ControlLoopOperationManager2(mgrctx, context, policy, executor); - - // should return null for a null input - assertNull(mgr.makeControlLoopResponse(null)); - - // should generate a response, with a payload - checkResp(outcome, "my-payload"); - - /* - * these should generate a response, with null payload - */ - output.setPayload(null); - checkResp(outcome, null); - - body.setOutput(null); - checkResp(outcome, null); - - msg.setBody(null); - checkResp(outcome, null); - - outcome.setResponse(null); - checkResp(outcome, null); - } - - @Test - public void testGetOperationMessage() { - // no history yet - assertNull(mgr.getOperationMessage()); - - runCyle(); - assertThat(mgr.getOperationMessage()).contains("actor=my-actor").contains("operation=my-operation"); - } - - @Test - public void testGetOperationResult() { - // no history yet - assertNotNull(mgr.getOperationResult()); - - runCyle(); - assertEquals(OperationResult.SUCCESS, mgr.getOperationResult()); - } - - /** - * Tests getOperationResult() when it ends in a failure. - */ - @Test - public void testGetOperationResultFailure() { - mgr.start(REMAINING_MS); - - genLockFailure(); - runToCompletion(); - - assertEquals(OperationResult.FAILURE_GUARD, mgr.getOperationResult()); - } - - /** - * Tests handleException() when the exception is a "cancel". - */ - @Test - public void testHandleExceptionCanceled() { - lockFuture.cancel(false); - - mgr.start(REMAINING_MS); - - runToCompletion(); - - assertTrue(mgr.nextStep()); - assertEquals(ControlLoopOperationManager2.State.ACTIVE, mgr.getState()); - } - - @Test - public void testCancel() { - mgr.start(REMAINING_MS); - - mgr.cancel(); - assertTrue(mgr.getFuture().isCancelled()); - } - - /** - * Tests cancel() when the operation hasn't been started. - */ - @Test - public void testCancelNotStarted() { - assertNull(mgr.getFuture()); - - mgr.cancel(); - assertNull(mgr.getFuture()); - } - - @Test - public void testLockUnavailable() { - mgr.start(REMAINING_MS); - - runToCompletion(); - - // lock failure outcome - final OperationOutcome outcome = genLockFailure(); - - runToCompletion(); - - assertFalse(mgr.nextStep()); - assertEquals(ControlLoopOperationManager2.State.LOCK_DENIED, mgr.getState()); - - assertEquals(outcome, mgr.getOutcomes().peek()); - - // should have called update() for operation-start, but not for any nextStep() - verify(mgrctx).updated(mgr); - } - - /** - * Tests onStart() and onComplete() with other actors. - */ - @Test - public void testOnStart_testOnComplete() { - mgr.start(REMAINING_MS); - - lockFuture.complete(new OperationOutcome()); - genGuardOutcome(); - - // generate failure outcome for ANOTHER actor - should be ignored - OperationOutcome outcome = mgr.getParams().makeOutcome(); - outcome.setActor(OTHER_ACTOR); - outcome.setResult(OperationResult.FAILURE); - outcome.setStart(Instant.now()); - mgr.getParams().callbackStarted(new OperationOutcome(outcome)); - - outcome.setEnd(Instant.now()); - mgr.getParams().callbackCompleted(outcome); - - policyFuture.complete(genOpOutcome()); - runToCompletion(); - - // should not include the other actor's outcome - assertEquals(ControlLoopOperationManager2.State.GUARD_STARTED, mgr.getState()); - - assertTrue(mgr.nextStep()); - assertEquals(ControlLoopOperationManager2.State.GUARD_PERMITTED, mgr.getState()); - - assertTrue(mgr.nextStep()); - assertEquals(ControlLoopOperationManager2.State.OPERATION_STARTED, mgr.getState()); - - assertTrue(mgr.nextStep()); - assertEquals(ControlLoopOperationManager2.State.OPERATION_SUCCESS, mgr.getState()); - - assertFalse(mgr.nextStep()); - - assertEquals(OperationResult.SUCCESS, mgr.getOutcomes().peek().getResult()); - - verify(mgrctx, times(4)).updated(mgr); - } - - @Test - public void testNextStep() { - mgr.start(REMAINING_MS); - - // only do the lock and the guard - lockFuture.complete(new OperationOutcome()); - genGuardOutcome(); - runToCompletion(); - - assertEquals(ControlLoopOperationManager2.State.GUARD_STARTED, mgr.getState()); - - assertTrue(mgr.nextStep()); - assertEquals(ControlLoopOperationManager2.State.GUARD_PERMITTED, mgr.getState()); - - assertTrue(mgr.nextStep()); - assertTrue(mgr.nextStep()); - - verify(mgrctx, times(2)).updated(mgr); - } - - /** - * Tests processOutcome() when the lock is denied. - */ - @Test - public void testProcessOutcomeLockDenied() { - mgr.start(REMAINING_MS); - - // unavailable from the start => "denied" - genLockFailure(); - - runToCompletion(); - - assertEquals(ControlLoopOperationManager2.State.LOCK_DENIED, mgr.getState()); - - assertFalse(mgr.nextStep()); - verify(mgrctx).updated(mgr); - - verifyDb(1, OperationResult.FAILURE_GUARD, "Operation denied by Lock"); - } - - /** - * Tests processOutcome() when the lock is lost. - */ - @Test - public void testProcessOutcomeLockLost() { - mgr.start(REMAINING_MS); - - // indicate lock success initially - lockFuture.complete(new OperationOutcome()); - - // do the guard - genGuardOutcome(); - - // now generate a lock failure => "lost" - genLockFailure(); - - runToCompletion(); - - assertEquals(ControlLoopOperationManager2.State.GUARD_STARTED, mgr.getState()); - - assertTrue(mgr.nextStep()); - assertEquals(ControlLoopOperationManager2.State.GUARD_PERMITTED, mgr.getState()); - - assertTrue(mgr.nextStep()); - assertEquals(ControlLoopOperationManager2.State.LOCK_LOST, mgr.getState()); - - assertFalse(mgr.nextStep()); - verify(mgrctx, times(3)).updated(mgr); - - verifyDb(1, OperationResult.FAILURE, "Operation aborted by Lock"); - } - - /** - * Tests processOutcome() when the guard is permitted. - */ - @Test - public void testProcessOutcomeGuardPermit() { - mgr.start(REMAINING_MS); - - lockFuture.complete(new OperationOutcome()); - genGuardOutcome(); - - runToCompletion(); - - assertEquals(ControlLoopOperationManager2.State.GUARD_STARTED, mgr.getState()); - - assertTrue(mgr.nextStep()); - assertEquals(ControlLoopOperationManager2.State.GUARD_PERMITTED, mgr.getState()); - - assertTrue(mgr.nextStep()); - verify(mgrctx, times(2)).updated(mgr); - - verify(dataMgr, never()).store(any(), any(), any(), any()); - } - - /** - * Tests processOutcome() when the guard is permitted. - */ - @Test - public void testProcessOutcomeGuardDenied() { - mgr.start(REMAINING_MS); - - lockFuture.complete(new OperationOutcome()); - genGuardOutcome(false); - - runToCompletion(); - - assertEquals(ControlLoopOperationManager2.State.GUARD_STARTED, mgr.getState()); - - assertTrue(mgr.nextStep()); - assertEquals(ControlLoopOperationManager2.State.GUARD_DENIED, mgr.getState()); - - assertFalse(mgr.nextStep()); - verify(mgrctx, times(2)).updated(mgr); - - verifyDb(1, OperationResult.FAILURE_GUARD, "Operation denied by Guard"); - } - - /** - * Tests processOutcome() when the operation is a success. - */ - @Test - public void testProcessOutcomeOperSuccess() { - mgr.start(REMAINING_MS); - - lockFuture.complete(new OperationOutcome()); - genGuardOutcome(); - genOpOutcome(); - - runToCompletion(); - - assertEquals(ControlLoopOperationManager2.State.GUARD_STARTED, mgr.getState()); - - assertTrue(mgr.nextStep()); - assertEquals(ControlLoopOperationManager2.State.GUARD_PERMITTED, mgr.getState()); - - assertTrue(mgr.nextStep()); - assertEquals(ControlLoopOperationManager2.State.OPERATION_STARTED, mgr.getState()); - - assertTrue(mgr.nextStep()); - assertEquals(ControlLoopOperationManager2.State.OPERATION_SUCCESS, mgr.getState()); - - assertFalse(mgr.nextStep()); - verify(mgrctx, times(4)).updated(mgr); - - verifyDb(2, OperationResult.SUCCESS, null); - } - - /** - * Tests processOutcome() when the operation is a failure. - */ - @Test - public void testProcessOutcomeOperFailure() { - mgr.start(REMAINING_MS); - - lockFuture.complete(new OperationOutcome()); - genGuardOutcome(); - genOpOutcome(false); - - runToCompletion(); - - assertEquals(ControlLoopOperationManager2.State.GUARD_STARTED, mgr.getState()); - - assertTrue(mgr.nextStep()); - assertEquals(ControlLoopOperationManager2.State.GUARD_PERMITTED, mgr.getState()); - - assertTrue(mgr.nextStep()); - assertEquals(ControlLoopOperationManager2.State.OPERATION_STARTED, mgr.getState()); - - assertTrue(mgr.nextStep()); - assertEquals(ControlLoopOperationManager2.State.OPERATION_FAILURE, mgr.getState()); - verifyDb(2, OperationResult.FAILURE, null); - - assertThat(mgr.toString()).contains("attempts=1"); - - // next failure - genOpOutcome(false); - runToCompletion(); - - assertTrue(mgr.nextStep()); - assertEquals(ControlLoopOperationManager2.State.OPERATION_STARTED, mgr.getState()); - - assertTrue(mgr.nextStep()); - assertEquals(ControlLoopOperationManager2.State.OPERATION_FAILURE, mgr.getState()); - verifyDb(4, OperationResult.FAILURE, null); - - assertThat(mgr.toString()).contains("attempts=2"); - - // and finally a success - genOpOutcome(); - - assertTrue(mgr.nextStep()); - assertEquals(ControlLoopOperationManager2.State.OPERATION_STARTED, mgr.getState()); - - assertTrue(mgr.nextStep()); - assertEquals(ControlLoopOperationManager2.State.OPERATION_SUCCESS, mgr.getState()); - verifyDb(6, OperationResult.SUCCESS, null); - - assertThat(mgr.toString()).contains("attempts=3"); - - assertFalse(mgr.nextStep()); - verify(mgrctx, times(8)).updated(mgr); - } - - @Test - public void testGetOperationHistory() { - // no history yet - assertNull(mgr.getOperationHistory()); - - runCyle(); - assertThat(mgr.getOperationHistory()).contains("actor=my-actor").contains("operation=my-operation") - .contains("outcome=Success"); - } - - @Test - public void testGetHistory() { - // no history yet - assertEquals(0, mgr.getHistory().size()); - - runCyle(); - assertEquals(1, mgr.getHistory().size()); - } - - @Test - public void testDetmTargetVm() { - target.setTargetType(TargetType.VM.toString()); - assertNull(mgr.detmTarget()); - assertEquals(MY_TARGET, mgr.getTargetEntity()); - - target.setTargetType(TargetType.VNF.toString()); - assertNull(mgr.detmTarget()); - assertEquals(MY_TARGET, mgr.getTargetEntity()); - - target.setTargetType(TargetType.VFMODULE.toString()); - assertNull(mgr.detmTarget()); - assertEquals(MY_TARGET, mgr.getTargetEntity()); - - // unsupported type - target.setTargetType(TargetType.VFC.toString()); - assertThatIllegalArgumentException().isThrownBy(() -> mgr.detmTarget()) - .withMessage("The target type is not supported"); - - // null type - target.setTargetType(null); - assertThatIllegalArgumentException().isThrownBy(() -> mgr.detmTarget()).withMessage("The target type is null"); - - // null target - operation.setTarget(null); - mgr = new ControlLoopOperationManager2(mgrctx, context, policy, executor); - assertThatIllegalArgumentException().isThrownBy(() -> mgr.detmTarget()).withMessage("The target is null"); - } - - @Test - public void testDetmPnfTarget() { - setTargetPnf(); - assertNull(mgr.detmTarget()); - assertEquals(MY_TARGET, mgr.getTargetEntity()); - - // missing enrichment data - event.getAai().clear(); - assertThatIllegalArgumentException().isThrownBy(() -> mgr.detmTarget()) - .withMessage("AAI section is missing " + ControlLoopOperationManager2.PNF_NAME); - - // wrong target - event.setTarget(MISMATCH); - assertThatIllegalArgumentException().isThrownBy(() -> mgr.detmTarget()) - .withMessage("Target does not match target type"); - } - - @Test - public void testDetmVfModuleTarget() { - // vserver - event.setTarget(ControlLoopOperationManager2.VSERVER_VSERVER_NAME); - event.getAai().clear(); - event.getAai().putAll(Map.of(ControlLoopOperationManager2.VSERVER_VSERVER_NAME, MY_TARGET)); - assertNull(mgr.detmTarget()); - assertEquals(MY_TARGET, mgr.getTargetEntity()); - - // vnf-id - event.setTarget(ControlLoopOperationManager2.GENERIC_VNF_VNF_ID); - event.getAai().clear(); - event.getAai().putAll(Map.of(ControlLoopOperationManager2.GENERIC_VNF_VNF_ID, MY_TARGET)); - assertNull(mgr.detmTarget()); - assertEquals(MY_TARGET, mgr.getTargetEntity()); - - // wrong type - event.setTarget(MISMATCH); - assertThatIllegalArgumentException().isThrownBy(() -> mgr.detmTarget()) - .withMessage("Target does not match target type"); - - // missing enrichment data - event.setTarget(ControlLoopOperationManager2.VSERVER_VSERVER_NAME); - event.getAai().clear(); - assertThatIllegalArgumentException().isThrownBy(() -> mgr.detmTarget()) - .withMessage("Enrichment data is missing " + ControlLoopOperationManager2.VSERVER_VSERVER_NAME); - - // null target - event.setTarget(null); - assertThatIllegalArgumentException().isThrownBy(() -> mgr.detmTarget()).withMessage("Target is null"); - } - - @Test - public void testDetmVnfName() { - setTargetVnfName(); - assertNull(mgr.detmTarget()); - assertEquals(MY_TARGET, mgr.getTargetEntity()); - - // force it to be gotten from the CQ data - event.getAai().clear(); - assertNull(mgr.detmTarget()); - assertEquals(MY_VNF_ID, mgr.getTargetEntity()); - } - - @Test - public void testExtractVnfFromCq() { - // force it to be gotten from the CQ data - setTargetVnfName(); - event.getAai().clear(); - - // missing vnf id in CQ data - when(vnf.getVnfId()).thenReturn(null); - assertThatIllegalArgumentException().isThrownBy(() -> mgr.detmTarget()).withMessage("No vnf-id found"); - - // missing default vnf in CQ data - when(cqdata.getDefaultGenericVnf()).thenReturn(null); - assertThatIllegalArgumentException().isThrownBy(() -> mgr.detmTarget()).withMessage("No vnf-id found"); - } - - @Test - public void testGetState_testGetActor_testGetOperation() { - assertEquals(ControlLoopOperationManager2.State.ACTIVE, mgr.getState()); - assertEquals(POLICY_ACTOR, mgr.getActor()); - assertEquals(POLICY_OPERATION, mgr.getOperation()); - } - - @Test - public void testToString() { - assertThat(mgr.toString()).contains("state").contains("requestId").contains("policyId").contains("attempts"); - } - - /** - * Runs a cycle, from start to completion. - */ - private void runCyle() { - mgr.start(REMAINING_MS); - - lockFuture.complete(new OperationOutcome()); - genGuardOutcome(); - genOpOutcome(); - - runToCompletion(); - - // guard start - assertTrue(mgr.nextStep()); - - // guard permit - assertTrue(mgr.nextStep()); - - // operation start - assertTrue(mgr.nextStep()); - - // operation success - assertFalse(mgr.nextStep()); - } - - /** - * Runs everything until the executor queue is empty. - */ - private void runToCompletion() { - assertTrue(executor.runAll(MAX_RUN)); - } - - /** - * Generates a failure outcome for the lock, and invokes the callbacks. - * - * @return the generated outcome - */ - private OperationOutcome genLockFailure() { - OperationOutcome outcome = new OperationOutcome(); - outcome.setActor(ControlLoopOperationManager2.LOCK_ACTOR); - outcome.setOperation(ControlLoopOperationManager2.LOCK_OPERATION); - outcome.setResult(OperationResult.FAILURE); - outcome.setStart(Instant.now()); - outcome.setEnd(Instant.now()); - outcome.setFinalOutcome(true); - - verify(mgrctx).requestLock(eq(MY_TARGET), lockCallback.capture()); - lockCallback.getValue().accept(outcome); - - lockFuture.complete(outcome); - - return outcome; - } - - /** - * Generates an outcome for the guard, and invokes the callbacks. - * - * @return the generated outcome - */ - private OperationOutcome genGuardOutcome() { - return genGuardOutcome(true); - } - - /** - * Generates an outcome for the guard, and invokes the callbacks. - * - * @param permit {@code true} if the guard should be permitted, {@code false} if - * denied - * @return the generated outcome - */ - private OperationOutcome genGuardOutcome(boolean permit) { - OperationOutcome outcome = mgr.getParams().makeOutcome(); - outcome.setActor(GuardActor.NAME); - outcome.setOperation(DecisionOperation.NAME); - outcome.setStart(Instant.now()); - mgr.getParams().callbackStarted(new OperationOutcome(outcome)); - - if (!permit) { - outcome.setResult(OperationResult.FAILURE); - } - - outcome.setEnd(Instant.now()); - mgr.getParams().callbackCompleted(outcome); - - return outcome; - } - - /** - * Generates an outcome for the operation, itself, and invokes the callbacks. - * - * @return the generated outcome - */ - private OperationOutcome genOpOutcome() { - return genOpOutcome(true); - } - - /** - * Generates an outcome for the operation, itself, and invokes the callbacks. - * - * @param success {@code true} if the outcome should be a success, {@code false} if a - * failure - * @return the generated outcome - */ - private OperationOutcome genOpOutcome(boolean success) { - OperationOutcome outcome = mgr.getParams().makeOutcome(); - outcome.setStart(Instant.now()); - mgr.getParams().callbackStarted(new OperationOutcome(outcome)); - - if (success) { - outcome.setFinalOutcome(true); - } else { - outcome.setResult(OperationResult.FAILURE); - } - - outcome.setEnd(Instant.now()); - mgr.getParams().callbackCompleted(outcome); - - return outcome; - } - - /** - * Configures the data for a PNF target. - */ - private void setTargetPnf() { - event.setTarget(ControlLoopOperationManager2.PNF_NAME); - event.getAai().clear(); - event.getAai().putAll(Map.of(ControlLoopOperationManager2.PNF_NAME, MY_TARGET)); - - target.setTargetType(TargetType.PNF.toString()); - } - - /** - * Configures the data for a VNF-NAME target. - */ - private void setTargetVnfName() { - event.setTarget(ControlLoopOperationManager2.GENERIC_VNF_VNF_NAME); - event.getAai().clear(); - event.getAai().putAll(Map.of(ControlLoopOperationManager2.GENERIC_VNF_VNF_ID, MY_TARGET)); - - target.setTargetType(TargetType.VNF.toString()); - } - - private void checkResp(OperationOutcome outcome, String expectedPayload) { - ControlLoopResponse resp = mgr.makeControlLoopResponse(outcome); - assertNotNull(resp); - assertEquals(REQ_ID, resp.getRequestId()); - assertEquals(expectedPayload, resp.getPayload()); - } - - private void verifyDb(int nrecords, OperationResult expectedResult, String expectedMsg) { - ArgumentCaptor entityCaptor = ArgumentCaptor.forClass(String.class); - ArgumentCaptor opCaptor = ArgumentCaptor.forClass(ControlLoopOperation.class); - verify(dataMgr, times(nrecords)).store(any(), any(), entityCaptor.capture(), opCaptor.capture()); - - assertEquals(MY_TARGET, entityCaptor.getValue()); - - ControlLoopOperation oper = opCaptor.getValue(); - - assertEquals(expectedResult.toString(), oper.getOutcome()); - assertEquals(expectedMsg, oper.getMessage()); - } -} diff --git a/controlloop/common/eventmanager/src/test/java/org/onap/policy/controlloop/eventmanager/LockDataTest.java b/controlloop/common/eventmanager/src/test/java/org/onap/policy/controlloop/eventmanager/LockDataTest.java index 98ff04da5..164dfb4d1 100644 --- a/controlloop/common/eventmanager/src/test/java/org/onap/policy/controlloop/eventmanager/LockDataTest.java +++ b/controlloop/common/eventmanager/src/test/java/org/onap/policy/controlloop/eventmanager/LockDataTest.java @@ -132,8 +132,8 @@ public class LockDataTest { assertTrue(future.isDone()); OperationOutcome outcome = future.get(); - assertEquals(ControlLoopOperationManager2.LOCK_ACTOR, outcome.getActor()); - assertEquals(ControlLoopOperationManager2.LOCK_OPERATION, outcome.getOperation()); + assertEquals(ActorConstants.LOCK_ACTOR, outcome.getActor()); + assertEquals(ActorConstants.LOCK_OPERATION, outcome.getOperation()); assertEquals(ENTITY, outcome.getTarget()); assertEquals(OperationResult.SUCCESS, outcome.getResult()); assertEquals(ControlLoopOperation.SUCCESS_MSG, outcome.getMessage()); @@ -173,8 +173,8 @@ public class LockDataTest { assertTrue(future2.isDone()); assertSame(outcome, future2.get()); - assertEquals(ControlLoopOperationManager2.LOCK_ACTOR, outcome.getActor()); - assertEquals(ControlLoopOperationManager2.LOCK_OPERATION, outcome.getOperation()); + assertEquals(ActorConstants.LOCK_ACTOR, outcome.getActor()); + assertEquals(ActorConstants.LOCK_OPERATION, outcome.getOperation()); assertEquals(ENTITY, outcome.getTarget()); assertEquals(OperationResult.FAILURE, outcome.getResult()); assertEquals(ControlLoopOperation.FAILED_MSG, outcome.getMessage()); diff --git a/controlloop/common/eventmanager/src/test/java/org/onap/policy/controlloop/eventmanager/StepTest.java b/controlloop/common/eventmanager/src/test/java/org/onap/policy/controlloop/eventmanager/StepTest.java index efcc6101a..aec4693f8 100644 --- a/controlloop/common/eventmanager/src/test/java/org/onap/policy/controlloop/eventmanager/StepTest.java +++ b/controlloop/common/eventmanager/src/test/java/org/onap/policy/controlloop/eventmanager/StepTest.java @@ -55,7 +55,6 @@ import org.onap.policy.controlloop.actorserviceprovider.OperationOutcome; import org.onap.policy.controlloop.actorserviceprovider.OperationResult; import org.onap.policy.controlloop.actorserviceprovider.Operator; import org.onap.policy.controlloop.actorserviceprovider.TargetType; -import org.onap.policy.controlloop.actorserviceprovider.controlloop.ControlLoopEventContext; import org.onap.policy.controlloop.actorserviceprovider.parameters.ControlLoopOperationParams; import org.onap.policy.controlloop.actorserviceprovider.spi.Actor; import org.onap.policy.drools.domain.models.operational.OperationalTarget; @@ -84,7 +83,6 @@ public class StepTest { private Map entityIds; private Map payload; private VirtualControlLoopEvent event; - private ControlLoopEventContext context; private BlockingQueue starts; private BlockingQueue completions; private ControlLoopOperationParams params; @@ -117,19 +115,15 @@ public class StepTest { event = new VirtualControlLoopEvent(); event.setRequestId(REQ_ID); - event.setTarget(ControlLoopOperationManager2.VSERVER_VSERVER_NAME); - event.setAai(new TreeMap<>(Map.of(ControlLoopOperationManager2.VSERVER_VSERVER_NAME, MY_TARGET))); - - context = new ControlLoopEventContext(event); starts = new LinkedBlockingQueue<>(); completions = new LinkedBlockingQueue<>(); params = ControlLoopOperationParams.builder().actor(POLICY_ACTOR).actorService(actors) - .completeCallback(completions::add).context(context).executor(ForkJoinPool.commonPool()) + .completeCallback(completions::add).executor(ForkJoinPool.commonPool()) .operation(POLICY_OPERATION).payload(new TreeMap<>(payload)).startCallback(starts::add) .targetType(TargetType.valueOf(target.getTargetType())).targetEntityIds(target.getEntityIds()) - .targetEntity(MY_TARGET).build(); + .requestId(REQ_ID).targetEntity(MY_TARGET).build(); startTime = new AtomicReference<>(); -- cgit 1.2.3-korg