From 8dece848c0775833013e2fa6ff801478fccb4a52 Mon Sep 17 00:00:00 2001 From: jhh Date: Fri, 4 Nov 2022 11:50:17 -0500 Subject: [PATCH] Create A1P actor to talk to A1 PMS. This relates to the support for the SON use case. Issue-ID: POLICY-4444 Signed-off-by: jhh Change-Id: I2c67ec282c77d42b9e8a11cc70cb518976075a00 --- .../v5gSonA1.policy.operational.input.tosca.json | 10 +- .../v5gSonA1.policy.operational.input.tosca.yaml | 12 +- models-interactions/model-actors/actor.a1p/pom.xml | 93 ++++++++++++++ .../policy/controlloop/actor/a1p/A1pActor.java | 53 ++++++++ .../policy/controlloop/actor/a1p/A1pOperation.java | 34 ++++++ ...licy.controlloop.actorserviceprovider.spi.Actor | 1 + .../policy/controlloop/actor/a1p/A1pActorTest.java | 61 ++++++++++ .../controlloop/actor/a1p/A1pOperationTest.java | 111 +++++++++++++++++ .../controlloop/actor/a1p/BasicA1pOperation.java | 135 +++++++++++++++++++++ .../actor.a1p/src/test/resources/service.yaml | 38 ++++++ .../policy/controlloop/actor/sdnr/SdnrActor.java | 6 +- .../controlloop/actor/sdnr/SdnrOperationTest.java | 7 +- models-interactions/model-actors/pom.xml | 1 + 13 files changed, 543 insertions(+), 19 deletions(-) create mode 100644 models-interactions/model-actors/actor.a1p/pom.xml create mode 100644 models-interactions/model-actors/actor.a1p/src/main/java/org/onap/policy/controlloop/actor/a1p/A1pActor.java create mode 100644 models-interactions/model-actors/actor.a1p/src/main/java/org/onap/policy/controlloop/actor/a1p/A1pOperation.java create mode 100644 models-interactions/model-actors/actor.a1p/src/main/resources/META-INF/services/org.onap.policy.controlloop.actorserviceprovider.spi.Actor create mode 100644 models-interactions/model-actors/actor.a1p/src/test/java/org/onap/policy/controlloop/actor/a1p/A1pActorTest.java create mode 100644 models-interactions/model-actors/actor.a1p/src/test/java/org/onap/policy/controlloop/actor/a1p/A1pOperationTest.java create mode 100644 models-interactions/model-actors/actor.a1p/src/test/java/org/onap/policy/controlloop/actor/a1p/BasicA1pOperation.java create mode 100644 models-interactions/model-actors/actor.a1p/src/test/resources/service.yaml diff --git a/models-examples/src/main/resources/policies/v5gSonA1.policy.operational.input.tosca.json b/models-examples/src/main/resources/policies/v5gSonA1.policy.operational.input.tosca.json index c2790188e..a690c758c 100644 --- a/models-examples/src/main/resources/policies/v5gSonA1.policy.operational.input.tosca.json +++ b/models-examples/src/main/resources/policies/v5gSonA1.policy.operational.input.tosca.json @@ -15,14 +15,14 @@ "id": "ControlLoop-SONA1-7d4baf04-8875-4d1f-946d-06b874048b61", "timeout": 1200, "abatement": false, - "trigger": "modify-a1-policy", + "trigger": "put-a1-policy", "operations": [ { - "id": "modify-a1-policy", - "description": "Control Loop Modify A1 Policy", + "id": "put-a1-policy", + "description": "Control Loop Put A1 Policy", "operation": { - "actor": "SDNR", - "operation": "ModifyA1Policy", + "actor": "A1P", + "operation": "PutA1Policy", "target": { "targetType": "PNF" } diff --git a/models-examples/src/main/resources/policies/v5gSonA1.policy.operational.input.tosca.yaml b/models-examples/src/main/resources/policies/v5gSonA1.policy.operational.input.tosca.yaml index feaea446e..1cb9d4676 100644 --- a/models-examples/src/main/resources/policies/v5gSonA1.policy.operational.input.tosca.yaml +++ b/models-examples/src/main/resources/policies/v5gSonA1.policy.operational.input.tosca.yaml @@ -12,13 +12,13 @@ topology_template: id: ControlLoop-SONA1-7d4baf04-8875-4d1f-946d-06b874048b61 timeout: 1200 abatement: false - trigger: modify-a1-policy + trigger: put-a1-policy operations: - - id: modify-a1-policy - description: Control Loop Modify A1 Policy + - id: put-a1-policy + description: Control Loop Put A1 Policy operation: - actor: SDNR - operation: ModifyA1Policy + actor: A1P + operation: PutA1Policy target: targetType: PNF timeout: 60 @@ -29,5 +29,3 @@ topology_template: failure_retries: final_failure_retries failure_exception: final_failure_exception failure_guard: final_failure_guard - - diff --git a/models-interactions/model-actors/actor.a1p/pom.xml b/models-interactions/model-actors/actor.a1p/pom.xml new file mode 100644 index 000000000..be6942e03 --- /dev/null +++ b/models-interactions/model-actors/actor.a1p/pom.xml @@ -0,0 +1,93 @@ + + + + 4.0.0 + + + org.onap.policy.models.policy-models-interactions.model-actors + model-actors + 2.8.0-SNAPSHOT + + + actor.a1p + + + + org.onap.policy.models.policy-models-interactions.model-actors + actorServiceProvider + ${project.version} + provided + + + org.onap.policy.models.policy-models-interactions.model-impl + sdnr + ${project.version} + provided + + + org.onap.policy.models.policy-models-interactions.model-impl + events + ${project.version} + provided + + + org.onap.policy.models.policy-models-interactions.model-actors + actor.sdnr + ${project.version} + provided + + + com.google.code.gson + gson + test + + + junit + junit + test + + + org.onap.policy.models.policy-models-interactions + simulators + ${project.version} + test + + + org.onap.policy.common + policy-endpoints + ${policy.common.version} + provided + + + org.onap.policy.models.policy-models-interactions.model-actors + actor.test + ${project.version} + test + + + org.powermock + powermock-api-mockito2 + test + + + diff --git a/models-interactions/model-actors/actor.a1p/src/main/java/org/onap/policy/controlloop/actor/a1p/A1pActor.java b/models-interactions/model-actors/actor.a1p/src/main/java/org/onap/policy/controlloop/actor/a1p/A1pActor.java new file mode 100644 index 000000000..a39598a26 --- /dev/null +++ b/models-interactions/model-actors/actor.a1p/src/main/java/org/onap/policy/controlloop/actor/a1p/A1pActor.java @@ -0,0 +1,53 @@ +/*- + * ============LICENSE_START======================================================= + * ONAP + * ================================================================================ + * Copyright (C) 2022 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.actor.a1p; + +import org.onap.policy.controlloop.actor.sdnr.SdnrOperation; +import org.onap.policy.controlloop.actorserviceprovider.Operator; +import org.onap.policy.controlloop.actorserviceprovider.impl.BidirectionalTopicActor; +import org.onap.policy.controlloop.actorserviceprovider.impl.BidirectionalTopicOperator; +import org.onap.policy.controlloop.actorserviceprovider.parameters.BidirectionalTopicActorParams; + +/** + * A1-PMS actor extends the SDN-R Actor and observes the same protocol but over + * different topics. + */ +public class A1pActor extends BidirectionalTopicActor { + public static final String NAME = "A1P"; + + /** + * Constructor. + */ + public A1pActor() { + super(NAME, BidirectionalTopicActorParams.class); + + addOperator(new BidirectionalTopicOperator(NAME, SdnrOperation.NAME, this, SdnrOperation.SELECTOR_KEYS, + A1pOperation::new)); + } + + @Override + public Operator getOperator(String name) { + /* + * All operations are managed by the same operator, regardless of the name. + */ + return super.getOperator(SdnrOperation.NAME); + } +} diff --git a/models-interactions/model-actors/actor.a1p/src/main/java/org/onap/policy/controlloop/actor/a1p/A1pOperation.java b/models-interactions/model-actors/actor.a1p/src/main/java/org/onap/policy/controlloop/actor/a1p/A1pOperation.java new file mode 100644 index 000000000..c64a5344d --- /dev/null +++ b/models-interactions/model-actors/actor.a1p/src/main/java/org/onap/policy/controlloop/actor/a1p/A1pOperation.java @@ -0,0 +1,34 @@ +/*- + * ============LICENSE_START======================================================= + * ONAP + * ================================================================================ + * Copyright (C) 2022 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.actor.a1p; + +import org.onap.policy.controlloop.actor.sdnr.SdnrOperation; +import org.onap.policy.controlloop.actorserviceprovider.parameters.BidirectionalTopicConfig; +import org.onap.policy.controlloop.actorserviceprovider.parameters.ControlLoopOperationParams; + +public class A1pOperation extends SdnrOperation { + + public A1pOperation(ControlLoopOperationParams params, + BidirectionalTopicConfig config) { + super(params, config); + } + +} diff --git a/models-interactions/model-actors/actor.a1p/src/main/resources/META-INF/services/org.onap.policy.controlloop.actorserviceprovider.spi.Actor b/models-interactions/model-actors/actor.a1p/src/main/resources/META-INF/services/org.onap.policy.controlloop.actorserviceprovider.spi.Actor new file mode 100644 index 000000000..0be55a386 --- /dev/null +++ b/models-interactions/model-actors/actor.a1p/src/main/resources/META-INF/services/org.onap.policy.controlloop.actorserviceprovider.spi.Actor @@ -0,0 +1 @@ +org.onap.policy.controlloop.actor.a1p.A1pActor diff --git a/models-interactions/model-actors/actor.a1p/src/test/java/org/onap/policy/controlloop/actor/a1p/A1pActorTest.java b/models-interactions/model-actors/actor.a1p/src/test/java/org/onap/policy/controlloop/actor/a1p/A1pActorTest.java new file mode 100644 index 000000000..654c35878 --- /dev/null +++ b/models-interactions/model-actors/actor.a1p/src/test/java/org/onap/policy/controlloop/actor/a1p/A1pActorTest.java @@ -0,0 +1,61 @@ +/*- + * ONAP + * ================================================================================ + * Copyright (C) 2022 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.actor.a1p; + +import static org.junit.Assert.assertEquals; +import static org.junit.Assert.assertNotNull; +import static org.junit.Assert.assertSame; + +import java.util.stream.Collectors; +import java.util.stream.Stream; +import org.junit.Test; +import org.onap.policy.controlloop.actor.test.BasicActor; +import org.onap.policy.controlloop.actorserviceprovider.Operator; + +public class A1pActorTest extends BasicActor { + + @Test + public void testConstructor() { + A1pActor prov = new A1pActor(); + assertEquals(0, prov.getSequenceNumber()); + + // verify that it has the operators we expect + var expected = Stream.of(A1pOperation.NAME).collect(Collectors.toList()); + var actual = prov.getOperationNames().stream().sorted().collect(Collectors.toList()); + + assertEquals(expected.toString(), actual.toString()); + } + + @Test + public void testActorService() { + // verify that it all plugs into the ActorService + verifyActorService(A1pActor.NAME, "service.yaml"); + } + + @Test + public void testGetOperator() { + A1pActor sp = new A1pActor(); + + // should always return the same operator regardless of the name + Operator oper = sp.getOperator("unknown"); + assertNotNull(oper); + assertSame(oper, sp.getOperator("another")); + } +} diff --git a/models-interactions/model-actors/actor.a1p/src/test/java/org/onap/policy/controlloop/actor/a1p/A1pOperationTest.java b/models-interactions/model-actors/actor.a1p/src/test/java/org/onap/policy/controlloop/actor/a1p/A1pOperationTest.java new file mode 100644 index 000000000..cfd9f993b --- /dev/null +++ b/models-interactions/model-actors/actor.a1p/src/test/java/org/onap/policy/controlloop/actor/a1p/A1pOperationTest.java @@ -0,0 +1,111 @@ +/*- + * ============LICENSE_START======================================================= + * ONAP + * ================================================================================ + * Copyright (C) 2022 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.actor.a1p; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.junit.Assert.assertEquals; +import static org.junit.Assert.assertNotNull; +import static org.junit.Assert.assertSame; + +import java.util.List; +import org.junit.After; +import org.junit.AfterClass; +import org.junit.Before; +import org.junit.BeforeClass; +import org.junit.Test; +import org.onap.policy.controlloop.actor.test.BasicBidirectionalTopicOperation; +import org.onap.policy.controlloop.actorserviceprovider.OperationProperties; +import org.onap.policy.controlloop.actorserviceprovider.OperationResult; +import org.onap.policy.sdnr.util.StatusCodeEnum; + +public class A1pOperationTest extends BasicA1pOperation { + + private A1pOperation operation; + + @BeforeClass + public static void setUpBeforeClass() throws Exception { + BasicBidirectionalTopicOperation.initBeforeClass(MY_SINK, MY_SOURCE); + } + + @AfterClass + public static void tearDownAfterClass() { + destroyAfterClass(); + } + + /** + * Setup. + */ + @Before + @Override + public void setUp() throws Exception { + super.setUp(); + + operation = new A1pOperation(params, config); + operation.setProperty(OperationProperties.EVENT_PAYLOAD, "my payload"); + } + + @After + @Override + public void tearDown() { + super.tearDown(); + } + + @Test + public void testA1pOperation() { + assertEquals(DEFAULT_ACTOR, operation.getActorName()); + assertEquals(DEFAULT_OPERATION, operation.getName()); + } + + @Test + public void testGetPropertyNames() { + assertThat(operation.getPropertyNames()).isEqualTo(List.of(OperationProperties.EVENT_PAYLOAD)); + } + + @Test + public void testSetOutcome() { + // with a status value + checkOutcome(); + assertEquals(StatusCodeEnum.SUCCESS.toString(), outcome.getMessage()); + + // null status value + response.getBody().getOutput().getStatus().setValue(null); + checkOutcome(); + + // null status + response.getBody().getOutput().setStatus(null); + checkOutcome(); + + // null output + response.getBody().setOutput(null); + checkOutcome(); + + // null body + response.setBody(null); + checkOutcome(); + } + + protected void checkOutcome() { + assertSame(outcome, operation.setOutcome(outcome, OperationResult.SUCCESS, response)); + assertEquals(OperationResult.SUCCESS, outcome.getResult()); + assertNotNull(outcome.getMessage()); + assertSame(response, outcome.getResponse()); + } +} diff --git a/models-interactions/model-actors/actor.a1p/src/test/java/org/onap/policy/controlloop/actor/a1p/BasicA1pOperation.java b/models-interactions/model-actors/actor.a1p/src/test/java/org/onap/policy/controlloop/actor/a1p/BasicA1pOperation.java new file mode 100644 index 000000000..410dab176 --- /dev/null +++ b/models-interactions/model-actors/actor.a1p/src/test/java/org/onap/policy/controlloop/actor/a1p/BasicA1pOperation.java @@ -0,0 +1,135 @@ +/*- + * ============LICENSE_START======================================================= + * ONAP + * ================================================================================ + * Copyright (C) 2022 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.actor.a1p; + +import static org.junit.Assert.assertEquals; +import static org.junit.Assert.assertFalse; +import static org.junit.Assert.assertTrue; +import static org.mockito.ArgumentMatchers.any; +import static org.mockito.Mockito.verify; + +import java.util.concurrent.CompletableFuture; +import java.util.concurrent.ExecutionException; +import java.util.function.BiConsumer; +import org.onap.policy.common.endpoints.event.comm.TopicSink; +import org.onap.policy.common.endpoints.event.comm.TopicSource; +import org.onap.policy.common.utils.coder.StandardCoderObject; +import org.onap.policy.controlloop.actor.test.BasicBidirectionalTopicOperation; +import org.onap.policy.controlloop.actorserviceprovider.OperationOutcome; +import org.onap.policy.controlloop.actorserviceprovider.OperationResult; +import org.onap.policy.controlloop.actorserviceprovider.Util; +import org.onap.policy.sdnr.PciBody; +import org.onap.policy.sdnr.PciMessage; +import org.onap.policy.sdnr.PciResponse; +import org.onap.policy.sdnr.Status; +import org.onap.policy.sdnr.util.StatusCodeEnum; +import org.onap.policy.simulators.SdnrTopicServer; +import org.onap.policy.simulators.TopicServer; + +public abstract class BasicA1pOperation extends BasicBidirectionalTopicOperation { + + protected PciMessage response; + + /** + * Constructs the object using a default actor and operation name. + */ + public BasicA1pOperation() { + super(); + } + + /** + * Constructs the object. + * + * @param actor actor name + * @param operation operation name + */ + public BasicA1pOperation(String actor, String operation) { + super(actor, operation); + } + + /** + * Initializes mocks and sets up. + */ + public void setUp() throws Exception { + super.setUpBasic(); + + response = new PciMessage(); + + PciBody body = new PciBody(); + response.setBody(body); + + PciResponse output = new PciResponse(); + body.setOutput(output); + + Status status = new Status(); + output.setStatus(status); + status.setCode(100); + status.setValue(StatusCodeEnum.SUCCESS.toString()); + } + + public void tearDown() { + super.tearDownBasic(); + } + + @Override + protected TopicServer makeServer(TopicSink sink, TopicSource source) { + return new SdnrTopicServer(sink, source); + } + + /** + * Runs the operation and verifies that the response is successful. + * + * @param operation operation to run + */ + protected void verifyOperation(A1pOperation operation) + throws InterruptedException, ExecutionException { + + CompletableFuture future2 = operation.start(); + executor.runAll(100); + assertFalse(future2.isDone()); + + verify(forwarder).register(any(), listenerCaptor.capture()); + provideResponse(listenerCaptor.getValue(), StatusCodeEnum.SUCCESS.toString()); + + executor.runAll(100); + assertTrue(future2.isDone()); + + outcome = future2.get(); + assertEquals(OperationResult.SUCCESS, outcome.getResult()); + } + + /** + * Provides a response to the listener. + * + * @param listener listener to which to provide the response + * @param code response code + * @param description response description + */ + protected void provideResponse(BiConsumer listener, int code, String description) { + PciResponse response = new PciResponse(); + + Status status = new Status(); + response.setStatus(status); + status.setCode(code); + + provideResponse(listener, Util.translate("", response, String.class)); + } +} diff --git a/models-interactions/model-actors/actor.a1p/src/test/resources/service.yaml b/models-interactions/model-actors/actor.a1p/src/test/resources/service.yaml new file mode 100644 index 000000000..88e775ec1 --- /dev/null +++ b/models-interactions/model-actors/actor.a1p/src/test/resources/service.yaml @@ -0,0 +1,38 @@ +# +# ============LICENSE_START====================================================== +# ONAP +# =============================================================================== +# Copyright (C) 2022 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======================================================== +# +topics: + topicSources: + - topicCommInfrastructure: NOOP + topic: my-source + servers: + - localhost + managed: true + topicSinks: + - topicCommInfrastructure: NOOP + topic: my-sink + servers: + - localhost + managed: true +actors: + A1P: + sinkTopic: my-sink + sourceTopic: my-source + operations: + any: {} diff --git a/models-interactions/model-actors/actor.sdnr/src/main/java/org/onap/policy/controlloop/actor/sdnr/SdnrActor.java b/models-interactions/model-actors/actor.sdnr/src/main/java/org/onap/policy/controlloop/actor/sdnr/SdnrActor.java index de7691e0e..91b51a917 100644 --- a/models-interactions/model-actors/actor.sdnr/src/main/java/org/onap/policy/controlloop/actor/sdnr/SdnrActor.java +++ b/models-interactions/model-actors/actor.sdnr/src/main/java/org/onap/policy/controlloop/actor/sdnr/SdnrActor.java @@ -3,7 +3,7 @@ * ONAP * ================================================================================ * Copyright (C) 2018 Wipro Limited Intellectual Property. All rights reserved. - * Modifications Copyright (C) 2019-2020 AT&T Intellectual Property. All rights reserved. + * Modifications Copyright (C) 2019-2020, 2022 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. @@ -40,8 +40,8 @@ public class SdnrActor extends BidirectionalTopicActoractor.appclcm actor.sdnc actor.sdnr + actor.a1p actor.so actor.vfc actor.xacml -- 2.16.6