From: waynedunican Date: Wed, 15 Jan 2025 08:54:20 +0000 (+0000) Subject: Update drools-s3ps to use Kafka producers and consumers X-Git-Tag: 3.1.0~2 X-Git-Url: https://gerrit.onap.org/r/gitweb?a=commitdiff_plain;h=5e4e67a2d39f72ac818487bcde0c40e8a6c661bd;p=policy%2Fdrools-applications.git Update drools-s3ps to use Kafka producers and consumers Issue-ID: POLICY-5152 Change-Id: Id05f6cc3f460a37feb2b81425068c9e73cca7980 Signed-off-by: waynedunican --- diff --git a/testsuites/run-s3p-test.sh b/testsuites/run-s3p-test.sh index 8af1c9291..0523876e6 100755 --- a/testsuites/run-s3p-test.sh +++ b/testsuites/run-s3p-test.sh @@ -1,6 +1,6 @@ #!/bin/bash # ============LICENSE_START======================================================= -# Copyright (C) 2023 Nordix Foundation. All rights reserved. +# Copyright (C) 2023-2025 Nordix Foundation. 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. @@ -22,28 +22,44 @@ if [ -z "${WORKSPACE}" ]; then export WORKSPACE=$(git rev-parse --show-toplevel) fi +export PROJECT="drools-pdp" export TESTDIR=${WORKSPACE}/testsuites export DROOLS_PERF_TEST_FILE=$TESTDIR/performance/src/main/resources/amsterdam/policyMTPerformanceTestPlan.jmx export DROOLS_STAB_TEST_FILE=$TESTDIR/stability/src/main/resources/s3p.jmx -if [ $1 == "run" ] -then - - mkdir automate-performance;cd automate-performance; - git clone "https://gerrit.onap.org/r/policy/docker" - cd docker/csit - - if [ $2 == "performance" ] - then - bash start-s3p-tests.sh run $DROOLS_PERF_TEST_FILE drools-applications; - elif [ $2 == "stability" ] - then - bash start-s3p-tests.sh run $DROOLS_STAB_TEST_FILE drools-applications; - else - echo "echo Invalid arguments provided. Usage: $0 [option..] {performance | stability}" - fi - -else - echo "Invalid arguments provided. Usage: $0 [option..] {run | uninstall}" -fi +function run_tests() { + local test_file=$1 + + mkdir -p automate-s3p-test + cd automate-s3p-test || exit 1 + git clone "https://gerrit.onap.org/r/policy/docker" + cd docker/csit || exit 1 + + bash run-s3p-tests.sh test "$test_file" $PROJECT +} + +function clean() { + cd $TESTDIR/automate-s3p-test/docker/csit + bash run-s3p-tests.sh clean +} + +echo "===========================" +echo "Running tests for: $PROJECT" +echo "===========================" + +case $1 in + performance) + run_tests "$DROOLS_PERF_TEST_FILE" + ;; + stability) + run_tests "$DROOLS_STAB_TEST_FILE" + ;; + clean) + clean + ;; + *) + echo "Invalid arguments provided. Usage: $0 {performance | stability | clean}" + exit 1 + ;; +esac diff --git a/testsuites/stability/src/main/resources/s3p.jmx b/testsuites/stability/src/main/resources/s3p.jmx index c4ebb7ae9..cde152771 100644 --- a/testsuites/stability/src/main/resources/s3p.jmx +++ b/testsuites/stability/src/main/resources/s3p.jmx @@ -1,11 +1,9 @@ - + - - false + true - false - + API_HOST @@ -34,7 +32,7 @@ KAFKA_PORT - 9092 + 29092 = @@ -54,14 +52,14 @@ HTTP - https + http = - + Accept @@ -102,52 +100,41 @@ - - - 9696 http + + + + - + + 1 + 1 + true continue - + 1 false - 1 - 1 - false - - - true - - false - - - + + 6 ${API_HOST} ${API_PORT} ${HTTP} /policy/api/v1/healthcheck GET - false - false - false - false - false - false - false - 6 - false - 0 + false + + + - + 200 @@ -157,7 +144,7 @@ 8 - + $.healthy true true @@ -167,7 +154,13 @@ - + + 6 + ${API_HOST} + ${API_PORT} + ${HTTP} + policy/api/v1/policytypes/onap.policies.controlloop.operational.common.Drools/versions/1.0.0/policies + POST true @@ -222,26 +215,11 @@ - ${API_HOST} - ${API_PORT} - ${HTTP} - policy/api/v1/policytypes/onap.policies.controlloop.operational.common.Drools/versions/1.0.0/policies - POST - false - false - false - false - false - false - false - 6 - false - 0 - 200 + 201 Assertion.response_code @@ -251,6 +229,12 @@ + 6 + ${API_HOST} + ${API_PORT} + ${HTTP} + policy/api/v1/policytypes/onap.policies.controlloop.operational.common.Drools/versions/1.0.0/policies + POST true @@ -305,26 +289,11 @@ - ${API_HOST} - ${API_PORT} - ${HTTP} - policy/api/v1/policytypes/onap.policies.controlloop.operational.common.Drools/versions/1.0.0/policies - POST - false - false - false - false - false - false - false - 6 - false - 0 - 200 + 201 Assertion.response_code @@ -334,6 +303,12 @@ + 6 + ${API_HOST} + ${API_PORT} + ${HTTP} + policy/api/v1/policytypes/onap.policies.controlloop.operational.common.Drools/versions/1.0.0/policies + POST true @@ -388,26 +363,11 @@ - ${API_HOST} - ${API_PORT} - ${HTTP} - policy/api/v1/policytypes/onap.policies.controlloop.operational.common.Drools/versions/1.0.0/policies - POST - false - false - false - false - false - false - false - 6 - false - 0 - 200 + 201 Assertion.response_code @@ -417,31 +377,22 @@ - + - - false - - - + + 6 ${PAP_HOST} ${PAP_PORT} ${HTTP} /policy/pap/v1/healthcheck GET - false - false - false - false - false - false - false - 6 - false - 0 + false + + + - + 200 @@ -451,7 +402,7 @@ 8 - + $.healthy true true @@ -461,7 +412,13 @@ - + + 6 + ${PAP_HOST} + ${PAP_PORT} + ${HTTP} + policy/pap/v1/pdps/policies + POST true @@ -472,24 +429,9 @@ - ${PAP_HOST} - ${PAP_PORT} - ${HTTP} - policy/pap/v1/pdps/policies - POST - false - false - false - false - false - false - false - 6 - false - 0 - + 202 @@ -500,7 +442,13 @@ - + + 6 + ${PAP_HOST} + ${PAP_PORT} + ${HTTP} + policy/pap/v1/pdps/policies + POST true @@ -511,21 +459,6 @@ - ${PAP_HOST} - ${PAP_PORT} - ${HTTP} - policy/pap/v1/pdps/policies - POST - false - false - false - false - false - false - false - 6 - false - 0 @@ -539,7 +472,13 @@ - + + 6 + ${PAP_HOST} + ${PAP_PORT} + ${HTTP} + policy/pap/v1/pdps/policies + POST true @@ -550,21 +489,6 @@ - ${PAP_HOST} - ${PAP_PORT} - ${HTTP} - policy/pap/v1/pdps/policies - POST - false - false - false - false - false - false - false - 6 - false - 0 @@ -579,425 +503,19 @@ - - false - - - - ${KAFKA_HOST} - ${KAFKA_PORT} - ${HTTP} - events/policy-pdp-pap/${__time()}/1?timeout=2000 - GET - false - false - false - false - false - false - false - 6 - false - 0 - - - - - 200 - - - Assertion.response_code - false - 8 - - - - - false - - - - ${KAFKA_HOST} - ${KAFKA_PORT} - ${HTTP} - events/appc-lcm-read/vcpesuccess/1?timeout=5000 - GET - false - false - false - false - false - false - false - 6 - false - 0 - - - - - 200 - - - Assertion.response_code - false - 8 - - - - - false - - - - ${KAFKA_HOST} - ${KAFKA_PORT} - ${HTTP} - events/policy-cl-mgt/vcpesuccess/1?timeout=5000 - GET - false - false - false - false - false - false - false - 6 - false - 0 - - - - - 200 - - - Assertion.response_code - false - 8 - - - - - false - - - - ${KAFKA_HOST} - ${KAFKA_PORT} - ${HTTP} - events/SDNR-CL/sonO1/1?timeout=5000 - GET - false - false - false - false - false - false - false - 6 - false - 0 - - - - - 200 - - - Assertion.response_code - false - 8 - - - - - false - - - - ${KAFKA_HOST} - ${KAFKA_PORT} - ${HTTP} - events/SDNR-CL-RSP/sonO1/1?timeout=5000 - GET - false - false - false - false - false - false - false - 6 - false - 0 - - - - - 200 - - - Assertion.response_code - false - 8 - - - - - false - - - - ${KAFKA_HOST} - ${KAFKA_PORT} - ${HTTP} - events/DCAE_CL_RSP/son01/1?timeout=5000 - GET - false - false - false - false - false - false - false - 6 - false - 0 - - - - - 200 - - - Assertion.response_code - false - 8 - - - - - false - - - - ${KAFKA_HOST} - ${KAFKA_PORT} - ${HTTP} - events/SDNR-CL/sonA1/1?timeout=5000 - GET - false - false - false - false - false - false - false - 6 - false - 0 - - - - - 200 - - - Assertion.response_code - false - 8 - - - - - false - - - - ${KAFKA_HOST} - ${KAFKA_PORT} - ${HTTP} - events/SDNR-CL-RSP/sonA1/1?timeout=5000 - GET - false - false - false - false - false - false - false - 6 - false - 0 - - - - - 200 - - - Assertion.response_code - false - 8 - - - - - false - - - - ${KAFKA_HOST} - ${KAFKA_PORT} - ${HTTP} - events/DCAE_CL_RSP/sonA1/1?timeout=5000 - GET - false - false - false - false - false - false - false - 6 - false - 0 - - - - - 200 - - - Assertion.response_code - false - 8 - - - - - false - - - - ${KAFKA_HOST} - ${KAFKA_PORT} - ${HTTP} - events/policy-cl-mgt/sonA1/1?timeout=5000 - GET - false - false - false - false - false - false - false - 6 - false - 0 - - - - - 200 - - - Assertion.response_code - false - 8 - - - - - false - - - - ${KAFKA_HOST} - ${KAFKA_PORT} - ${HTTP} - events/policy-cl-mgt/sonA1/1?timeout=5000 - GET - false - false - false - false - false - false - false - 6 - false - 0 - - - - - 200 - - - Assertion.response_code - false - 8 - - - - - false - - - - ${DROOLS_HOST} - ${DROOLS_PORT} - ${HTTP} - policy/pdp/engine/controllers/usecases/drools/facts - GET - false - false - false - false - false - false - false - 6 - false - 0 - - - - - 200 - - - Assertion.response_code - false - 8 - - - - $.usecases - 7 - true - false - false - false - - - - - startnextloop - + + 1 + 1 + ${duration} + 11 + true + true + continue + -1 false - 1 - 1 - true - ${duration} - 11 - true - false @@ -1013,7 +531,7 @@ Global to the thread group - + requestId @@ -1026,60 +544,65 @@ Update on a per iteration basis - - true - - - - false - { - "closedLoopControlName": "ControlLoop-vCPE-48f0c2c3-a172-4192-9ae3-052274181b6e", - "closedLoopAlarmStart": 1463679805324, - "closedLoopEventClient": "DCAE_INSTANCE_ID.dcae-tca", - "closedLoopEventStatus": "ONSET", - "requestID": "${requestId}", - "target_type": "VNF", - "target": "generic-vnf.vnf-id", - "AAI": { - "vserver.is-closed-loop-disabled": "false", - "vserver.prov-status": "ACTIVE", - "generic-vnf.vnf-id": "vCPE_Infrastructure_vGMUX_demo_app" - }, - "from": "DCAE", - "version": "1.0.2" -} - = - - - - ${DROOLS_HOST} - ${DROOLS_PORT} - ${HTTP} - policy/pdp/engine/topics/sources/dmaap/dcae_topic/events - PUT - false - false - false - false - false - false - false - 6 - false - 0 - - - - - - Content-Type - text/plain - - - - - - + + groovy + + + true + import org.apache.kafka.clients.producer.KafkaProducer +import org.apache.kafka.clients.producer.ProducerConfig +import org.apache.kafka.clients.producer.ProducerRecord +import org.apache.kafka.common.serialization.StringSerializer + +// Kafka producer configuration +def props = new Properties() +props.put(ProducerConfig.BOOTSTRAP_SERVERS_CONFIG, vars.get("KAFKA_HOST") + ":" + vars.get("KAFKA_PORT")) +props.put(ProducerConfig.KEY_SERIALIZER_CLASS_CONFIG, StringSerializer.class.getName()) +props.put(ProducerConfig.VALUE_SERIALIZER_CLASS_CONFIG, StringSerializer.class.getName()) +props.put(ProducerConfig.CLIENT_ID_CONFIG, "dcae-topic-producer") + +// Create Kafka producer +def producer = new KafkaProducer<>(props) + +// Prepare the message +def message = """ +{ + "closedLoopControlName": "ControlLoop-vCPE-48f0c2c3-a172-4192-9ae3-052274181b6e", + "closedLoopAlarmStart": 1463679805324, + "closedLoopEventClient": "DCAE_INSTANCE_ID.dcae-tca", + "closedLoopEventStatus": "ONSET", + "requestID": "${requestId}", + "target_type": "VNF", + "target": "generic-vnf.vnf-id", + "AAI": { + "vserver.is-closed-loop-disabled": "false", + "vserver.prov-status": "ACTIVE", + "generic-vnf.vnf-id": "vCPE_Infrastructure_vGMUX_demo_app" + }, + "from": "DCAE", + "version": "1.0.2" +} +""".toString() + +// Create a producer record +def record = new ProducerRecord<>("unauthenticated.dcae_cl_output", vars.get("requestId").toString(), message) + +// Send the message +def future = producer.send(record) + +// Wait for the send to complete and log the result +def metadata = future.get() +log.info("Message sent to topic: ${metadata.topic()}, partition: ${metadata.partition()}, offset: ${metadata.offset()}") + +// Close the producer +producer.close() + +// Set a variable to indicate successful sending +vars.put("messageSent", "true") + + + + groovy @@ -1087,318 +610,403 @@ vars.put("counter", "0"); - - ${__javaScript(${counter} < 10)} - + + 10 + - - false - - - - true - {"class":"And", "filters": [ { "class":"Equals", "field":"request-id", "value":"${requestId}" }, { "class":"Equals", "field":"rpc-name", "value":"restart" }]} - = - true - filter - - - - ${KAFKA_HOST} - ${KAFKA_PORT} - ${HTTP} - events/appc-lcm-read/${consumerGroup}/1?timeout=15000&limit=1 - GET - false - false - false - false - false - false - false - 6 - false - 0 - + + groovy + + + true + import org.apache.kafka.clients.consumer.KafkaConsumer +import org.apache.kafka.clients.consumer.ConsumerConfig +import org.apache.kafka.common.serialization.StringDeserializer +import java.time.Duration + +// Kafka consumer configuration +def props = new Properties() +props.put(ConsumerConfig.BOOTSTRAP_SERVERS_CONFIG, vars.get("KAFKA_HOST") + ":" + vars.get("KAFKA_PORT")) +props.put(ConsumerConfig.GROUP_ID_CONFIG, vars.get("consumerGroup")) +props.put(ConsumerConfig.KEY_DESERIALIZER_CLASS_CONFIG, StringDeserializer.class.getName()) +props.put(ConsumerConfig.VALUE_DESERIALIZER_CLASS_CONFIG, StringDeserializer.class.getName()) +props.put(ConsumerConfig.AUTO_OFFSET_RESET_CONFIG, "earliest") + +// Create Kafka consumer +def consumer = new KafkaConsumer<>(props) + +try { + // Subscribe to the topic + consumer.subscribe(Arrays.asList("appc-lcm-read")) + + // Poll for records + def records = consumer.poll(Duration.ofMillis(15000)) + + if (records.isEmpty()) { + log.warn("No records found within the timeout period") + vars.put("messageConsumed", "false") + } else { + // Process the first record + def record = records.first() + def requestId = record.key() + def value = record.value() + + // Store the entire message + vars.put("kafkaMessage", value) + + // Parse the value + def jsonSlurper = new groovy.json.JsonSlurper() + def parsedValue = jsonSlurper.parseText(value) + + // Extract required fields + vars.put("requestIdOnset", parsedValue["request-id"]) + vars.put("correlationId", parsedValue["correlation-id"]) + vars.put("subRequestId", parsedValue["sub-request-id"]) + + // Log the extracted information + log.info("RequestId: " + requestId) + log.info("Parsed Value: " + parsedValue) + + vars.put("messageConsumed", "true") + } +} catch (Exception e) { + log.error("Error processing Kafka message: " + e.getMessage()) + vars.put("messageConsumed", "false") +} finally { + // Close the consumer + consumer.close() +} + + - - - [] - - - Assertion.response_data - false - 12 - - - - false - requestIdOnset - \\"request-id\\": \\"(.+?)\\" - $1$ - none - false - - - - false - correlationId - correlation-id\\": \\"(.+?)\\" - $1$ - none - false - + + true + + + import groovy.json.JsonSlurper + +def message = vars.get("kafkaMessage") +def jsonSlurper = new JsonSlurper() +def parsedMessage = jsonSlurper.parseText(message) + +vars.put("requestIdOnset", parsedMessage.requestId ?: "none") + + groovy + - - false - subRequestId - sub-request-id\\": \\"(.+?)\\" - $1$ - none - false - + + groovy + + + true + import groovy.json.JsonSlurper + +def message = vars.get("kafkaMessage") +def jsonSlurper = new JsonSlurper() +def parsedMessage = jsonSlurper.parseText(message) + +vars.put("notification", parsedMessage.notification ?: "none") + + - + groovy true - String requestIdOnset = vars.get("requestIdOnset"); -String requestId = vars.get("requestId"); -String correlationId = vars.get("correlationId"); -String subRequestId = vars.get("subRequestId"); -String counter = vars.get("counter"); - -String transaction = "none"; - -log.info ("The requestId id is " + requestId); -log.info ("The requestIdOnset id is " + requestIdOnset); -log.info ("The correlation id is " + correlationId); -log.info ("The subrequest id is " + subRequestId); -log.info ("The counter is " + counter); - -if ( requestId == requestIdOnset ) { - if ( correlationId == "none" || subRequestId == "none" ) { - transaction = "FINAL"; - log.info ("Final Failure Transaction"); - AssertionResult.setFailureMessage("Missing correlationId or subRequestId"); - AssertionResult.setFailure(true); - } else { - transaction = "FINAL"; - vars.put("transaction", "FINAL"); - log.info ("Final Success Transaction"); - } + import org.apache.kafka.clients.consumer.ConsumerRecord + +// Assuming the Kafka message is stored in a variable named 'kafkaMessage' +ConsumerRecord<String, String> record = vars.getObject("kafkaMessage") + +String requestIdOnset = record.key() +String requestId = vars.get("requestId") +String correlationId = "none" +String subRequestId = "none" +String counter = vars.get("counter") + +String transaction = "none" + +// Parse the Kafka message value (assuming it's JSON) +def jsonSlurper = new groovy.json.JsonSlurper() +def messageContent = jsonSlurper.parseText(record.value()) + +if (messageContent.containsKey("correlation-id")) { + correlationId = messageContent["correlation-id"] +} +if (messageContent.containsKey("sub-request-id")) { + subRequestId = messageContent["sub-request-id"] } -int counterTemp = Integer.parseInt(counter) +1; +log.info("The requestId is " + requestId) +log.info("The requestIdOnset is " + requestIdOnset) +log.info("The correlation id is " + correlationId) +log.info("The subrequest id is " + subRequestId) +log.info("The counter is " + counter) + +if (requestId == requestIdOnset) { + if (correlationId == "none" || subRequestId == "none") { + transaction = "FINAL" + log.info("Final Failure Transaction") + AssertionResult.setFailureMessage("Missing correlationId or subRequestId") + AssertionResult.setFailure(true) + } else { + transaction = "FINAL" + vars.put("transaction", "FINAL") + log.info("Final Success Transaction") + } +} + +int counterTemp = Integer.parseInt(counter) + 1 if (transaction == "FINAL") { - counterTemp = 99; + counterTemp = 99 } else if (counterTemp >= 10) { - AssertionResult.setFailureMessage("vCPE Success APPCL Failure, reached maximum number of 10 attempts "); - AssertionResult.setFailure(true); + AssertionResult.setFailureMessage("vCPE Success APPCL Failure, reached maximum number of 10 attempts") + AssertionResult.setFailure(true) } -vars.put("counter", Integer.toString(counterTemp)); - +vars.put("counter", Integer.toString(counterTemp)) - - true - - - - false - { - "body": { - "output": { - "common-header": { - "timestamp": "2020-05-05T15:56:34.845Z", - "api-ver": "2.00", - "originator-id": "${requestId}", - "request-id": "${requestId}", - "sub-request-id": "${subRequestId}", - "flags": {} - }, - "status": { - "code": 400, - "message": "Restart Successful" - } - } - }, - "version": "2.0", - "rpc-name": "restart", - "correlation-id": "${correlationId}", - "type": "response" -} - - = - - - - ${DROOLS_HOST} - ${DROOLS_PORT} - ${HTTP} - policy/pdp/engine/topics/sources/dmaap/appc-lcm-write/events - PUT - false - false - false - false - false - false - false - 6 - false - 0 - - - - - - Content-Type - text/plain - - - - - - + groovy true - vars.put("counter", "0"); + import org.apache.kafka.clients.producer.KafkaProducer +import org.apache.kafka.clients.producer.ProducerConfig +import org.apache.kafka.clients.producer.ProducerRecord +import org.apache.kafka.common.serialization.StringSerializer + +// Kafka producer configuration +def props = new Properties() +props.put(ProducerConfig.BOOTSTRAP_SERVERS_CONFIG, vars.get("KAFKA_HOST") + ":" + vars.get("KAFKA_PORT")) +props.put(ProducerConfig.KEY_SERIALIZER_CLASS_CONFIG, StringSerializer.class.getName()) +props.put(ProducerConfig.VALUE_SERIALIZER_CLASS_CONFIG, StringSerializer.class.getName()) +props.put(ProducerConfig.CLIENT_ID_CONFIG, "appc-lcm-write-producer") + +// Create Kafka producer +def producer = new KafkaProducer<>(props) + +// Prepare the message +def message = """ +{ + "body": { + "output": { + "common-header": { + "timestamp": "${new Date().format("yyyy-MM-dd'T'HH:mm:ss.SSS'Z'", TimeZone.getTimeZone("UTC"))}", + "api-ver": "2.00", + "originator-id": "${vars.get("requestId")}", + "request-id": "${vars.get("requestId")}", + "sub-request-id": "${vars.get("subRequestId")}", + "flags": {} + }, + "status": { + "code": 400, + "message": "Restart Successful" + } + } + }, + "version": "2.0", + "rpc-name": "restart", + "correlation-id": "${vars.get("correlationId")}", + "type": "response" +} +""".toString() + +// Create a producer record +def record = new ProducerRecord<>("appc-lcm-write", vars.get("requestId").toString(), message) + +// Send the message +def future = producer.send(record) + +// Wait for the send to complete and log the result +def metadata = future.get() +log.info("Message sent to topic: ${metadata.topic()}, partition: ${metadata.partition()}, offset: ${metadata.offset()}") + +// Close the producer +producer.close() + +// Set a variable to indicate successful sending +vars.put("messageSent", "true") + - + ${__javaScript(${counter} < 60)} - - false - - - - true - {"class":"And", "filters": [ { "class":"Equals", "field":"requestId", "value":"${requestId}" }, { "class":"Equals", "field":"notification", "value":"FINAL: SUCCESS" }]} - = - true - filter - - - - ${KAFKA_HOST} - ${KAFKA_PORT} - ${HTTP} - events/policy-cl-mgt/${consumerGroup}/1?timeout=15000&limit=1 - GET - false - false - false - false - false - false - false - 6 - false - 0 - - - - - [] - - - Assertion.response_data - false - 12 - - - - false - requestIdOnset - requestId\\": \\"(.+?)\\" - $1$ - none - false - - - - false - notification - notification\\": \\"FINAL: (.+?)\\" - $1$ - none - false - - - - groovy - - - true - String requestIdOnset = vars.get("requestIdOnset"); -String requestId = vars.get("requestId"); -String notification = vars.get("notification"); -String counter = vars.get("counter"); - -String transaction = "none"; - -log.info ("The requestId id is " + requestId); -log.info ("The requestIdOnset id is " + requestIdOnset); -log.info ("The notification is " + notification); -log.info ("The transaction is " + transaction); -log.info ("The counter is " + counter); - -if ( requestId == requestIdOnset ) { - if ( notification == "SUCCESS" ) { - transaction = "FINAL"; - log.info ("Final Success Transaction"); - log.info ("The notification is SUCCESS"); - } else if ( notification == "FAILURE" ) { - transaction = "FINAL"; - log.info ("Final Failure Transaction"); - AssertionResult.setFailureMessage("Bad final notification"); - AssertionResult.setFailure(true); - } -} + + groovy + + + true + import org.apache.kafka.clients.consumer.KafkaConsumer +import org.apache.kafka.clients.consumer.ConsumerConfig +import org.apache.kafka.common.serialization.StringDeserializer +import java.time.Duration -int counterTemp = Integer.parseInt(counter) +1; -if (transaction == "FINAL") { - counterTemp = 99; -} else if (counterTemp >= 60) { - AssertionResult.setFailureMessage("vCPE Success POLICYCL Failure, reached maximum number of attempts "); - AssertionResult.setFailure(true); +// Kafka consumer configuration +def props = new Properties() +props.put(ConsumerConfig.BOOTSTRAP_SERVERS_CONFIG, vars.get("KAFKA_HOST") + ":" + vars.get("KAFKA_PORT")) +props.put(ConsumerConfig.GROUP_ID_CONFIG, vars.get("consumerGroup")) +props.put(ConsumerConfig.KEY_DESERIALIZER_CLASS_CONFIG, StringDeserializer.class.getName()) +props.put(ConsumerConfig.VALUE_DESERIALIZER_CLASS_CONFIG, StringDeserializer.class.getName()) +props.put(ConsumerConfig.AUTO_OFFSET_RESET_CONFIG, "earliest") + +// Create Kafka consumer +def consumer = new KafkaConsumer<>(props) + +// Subscribe to the topic +consumer.subscribe(Arrays.asList("policy-cl-mgt")) + +// Initialize variables +def maxAttempts = 60 +def attempts = 0 +def success = false + +// Poll for records +while (attempts < maxAttempts && !success) { + def records = consumer.poll(Duration.ofMillis(15000)) + + for (record in records) { + def value = record.value() + log.info("Received message: " + value) + + // Parse the value + def jsonSlurper = new groovy.json.JsonSlurper() + def parsedValue = jsonSlurper.parseText(value) + + // Extract required fields + def requestId = parsedValue.requestId + def notification = parsedValue.notification + + // Check if this is the message we're looking for + if (requestId == vars.get("requestId") && notification == "FINAL: SUCCESS") { + success = true + log.info("Final Success: RequestId=" + requestId + ", Notification=" + notification) + break + } + } + + attempts++ + if (!success) { + log.info("Attempt " + attempts + " of " + maxAttempts + " failed to find matching message") + } +} + +// Close the consumer +consumer.close() + +// Set variables based on the result +if (success) { + vars.put("finalStatus", "SUCCESS") +} else { + vars.put("finalStatus", "FAILURE") + AssertionResult.setFailureMessage("Failed to receive FINAL: SUCCESS notification after " + maxAttempts + " attempts") + AssertionResult.setFailure(true) +} + + + + + true + + + import groovy.json.JsonSlurper + +def message = vars.get("kafkaMessage") +def jsonSlurper = new JsonSlurper() +def parsedMessage = jsonSlurper.parseText(message) + +vars.put("requestIdOnset", parsedMessage.requestId ?: "none") + + groovy + + + + groovy + + + true + import groovy.json.JsonSlurper + +def message = vars.get("kafkaMessage") +def jsonSlurper = new JsonSlurper() +def parsedMessage = jsonSlurper.parseText(message) + +vars.put("notification", parsedMessage.notification ?: "none") + + + + + groovy + + + true + import groovy.json.JsonSlurper + +// Parse Kafka message content +def message = vars.get("kafkaMessage") +def jsonSlurper = new JsonSlurper() +def parsedMessage = jsonSlurper.parseText(message) + +// Extract relevant fields +String requestIdOnset = parsedMessage.requestId +String notification = parsedMessage.notification +String requestId = vars.get("requestId") +String counter = vars.get("counter") +String transaction = "none" + +// Log extracted information +log.info("The requestId is " + requestId) +log.info("The requestIdOnset is " + requestIdOnset) +log.info("The notification is " + notification) +log.info("The counter is " + counter) + +// Perform assertions +if (requestId == requestIdOnset) { + if (notification == "SUCCESS") { + transaction = "FINAL" + log.info("Final Success Transaction") + } else if (notification == "FAILURE") { + transaction = "FINAL" + log.info("Final Failure Transaction") + AssertionResult.setFailureMessage("Bad final notification") + AssertionResult.setFailure(true) + } } -vars.put("counter", Integer.toString(counterTemp)); +// Update counter +int counterTemp = Integer.parseInt(counter) + 1 +if (transaction == "FINAL") { + counterTemp = 99 +} else if (counterTemp >= 60) { + AssertionResult.setFailureMessage("vCPE Success POLICYCL Failure, reached maximum number of attempts") + AssertionResult.setFailure(true) +} +vars.put("counter", Integer.toString(counterTemp)) + - - 1 - 0 - 200 - - - - startnextloop - + + 1 + 1 + ${duration} + 11 + true + true + continue + -1 false - 1 - 1 - true - ${duration} - 11 - true - false @@ -1427,385 +1035,482 @@ vars.put("counter", Integer.toString(counterTemp)); Update on a per iteration basis - - true - - - - false - { - "closedLoopControlName": "ControlLoop-SONO1-fb41f388-a5f2-11e8-98d0-529269fb1459", - "closedLoopAlarmStart": 1606806580487, - "closedLoopEventClient": "microservice.PCI", - "closedLoopEventStatus": "ONSET", - "requestID": "${requestId}", - "target_type": "PNF", - "target": "pnf.pnf-name", - "AAI": { - "generic-vnf.prov-status": "ACTIVE", - "generic-vnf.is-closed-loop-disabled": "false", - "pnf.pnf-name": "ncserver1" - }, - "from": "PCIMS", - "version": "1.0.2", - "policyName": "SONO1", - "policyVersion": "1.0.2", - "Action": "ModifyO1Config", - "payload": "{\"Configurations\":[{\"data\":{\"FAPService\":{\"alias\":\"Chn0330\",\"X0005b9Lte\":{\"phyCellIdInUse\":6,\"pnfName\":\"ncserver23\"},\"CellConfig\":{\"LTE\":{\"RAN\":{\"Common\":{\"CellIdentity\":\"Chn0330\"}}}}}}},{\"data\":{\"FAPService\":{\"alias\":\"Chn0331\",\"X0005b9Lte\":{\"phyCellIdInUse\":7,\"pnfName\":\"ncserver23\"},\"CellConfig\":{\"LTE\":{\"RAN\":{\"Common\":{\"CellIdentity\":\"Chn0331\"}}}}}}}]}" -} - = - - - - ${DROOLS_HOST} - ${DROOLS_PORT} - ${HTTP} - policy/pdp/engine/topics/sources/dmaap/dcae_topic/events - PUT - false - false - false - false - false - false - false - 6 - false - 0 - - - - - - Content-Type - text/plain - - - - - - + + groovy + + + true + import org.apache.kafka.clients.producer.KafkaProducer +import org.apache.kafka.clients.producer.ProducerConfig +import org.apache.kafka.clients.producer.ProducerRecord +import org.apache.kafka.common.serialization.StringSerializer + +// Kafka producer configuration +def props = new Properties() +props.put(ProducerConfig.BOOTSTRAP_SERVERS_CONFIG, vars.get("KAFKA_HOST") + ":" + vars.get("KAFKA_PORT")) +props.put(ProducerConfig.KEY_SERIALIZER_CLASS_CONFIG, StringSerializer.class.getName()) +props.put(ProducerConfig.VALUE_SERIALIZER_CLASS_CONFIG, StringSerializer.class.getName()) +props.put(ProducerConfig.CLIENT_ID_CONFIG, "dcae-topic-producer") + +// Create Kafka producer +def producer = new KafkaProducer<>(props) + +// Prepare the message +def message = """ +{ + "closedLoopControlName": "ControlLoop-SONO1-fb41f388-a5f2-11e8-98d0-529269fb1459", + "closedLoopAlarmStart": 1606806580487, + "closedLoopEventClient": "microservice.PCI", + "closedLoopEventStatus": "ONSET", + "requestID": "${requestId}", + "target_type": "PNF", + "target": "pnf.pnf-name", + "AAI": { + "generic-vnf.prov-status": "ACTIVE", + "generic-vnf.is-closed-loop-disabled": "false", + "pnf.pnf-name": "ncserver1" + }, + "from": "PCIMS", + "version": "1.0.2", + "policyName": "SONO1", + "policyVersion": "1.0.2", + "Action": "ModifyO1Config", + "payload": "{\"Configurations\":[{\"data\":{\"FAPService\":{\"alias\":\"Chn0330\",\"X0005b9Lte\":{\"phyCellIdInUse\":6,\"pnfName\":\"ncserver23\"},\"CellConfig\":{\"LTE\":{\"RAN\":{\"Common\":{\"CellIdentity\":\"Chn0330\"}}}}}}},{\"data\":{\"FAPService\":{\"alias\":\"Chn0331\",\"X0005b9Lte\":{\"phyCellIdInUse\":7,\"pnfName\":\"ncserver23\"},\"CellConfig\":{\"LTE\":{\"RAN\":{\"Common\":{\"CellIdentity\":\"Chn0331\"}}}}}}}]}" +} +""".toString() + +// Create a producer record +def record = new ProducerRecord<>("unauthenticated.dcae_cl_output", vars.get("requestId").toString(), message) + +// Send the message +def future = producer.send(record) + +// Wait for the send to complete and log the result +def metadata = future.get() +log.info("Message sent to topic: ${metadata.topic()}, partition: ${metadata.partition()}, offset: ${metadata.offset()}") + +// Close the producer +producer.close() + +// Set a variable to indicate successful sending +vars.put("messageSent", "true") + + + + groovy true - vars.put("counterO1", "0"); + vars.put("counter01", "0"); - - ${__javaScript(${counterO1} < 10)} - + + 10 + - - false - - - - true - {"class":"And", "filters": [ { "class":"Equals", "field":"request-id", "value":"${requestId}" }, { "class":"Equals", "field":"rpc-name", "value":"modifyo1config" }]} - = - true - filter - - - - ${KAFKA_HOST} - ${KAFKA_PORT} - ${HTTP} - events/SDNR-CL/${consumerGroup}/1?timeout=15000&limit=1 - GET - false - false - false - false - false - false - false - 6 - false - 0 - + + groovy + + + true + import org.apache.kafka.clients.consumer.KafkaConsumer +import org.apache.kafka.clients.consumer.ConsumerConfig +import org.apache.kafka.common.serialization.StringDeserializer +import java.time.Duration + +// Kafka consumer configuration +def props = new Properties() +props.put(ConsumerConfig.BOOTSTRAP_SERVERS_CONFIG, vars.get("KAFKA_HOST") + ":" + vars.get("KAFKA_PORT")) +props.put(ConsumerConfig.GROUP_ID_CONFIG, vars.get("consumerGroup")) +props.put(ConsumerConfig.KEY_DESERIALIZER_CLASS_CONFIG, StringDeserializer.class.getName()) +props.put(ConsumerConfig.VALUE_DESERIALIZER_CLASS_CONFIG, StringDeserializer.class.getName()) +props.put(ConsumerConfig.AUTO_OFFSET_RESET_CONFIG, "earliest") + +// Create Kafka consumer +def consumer = new KafkaConsumer<>(props) + +try { + // Subscribe to the topic + consumer.subscribe(Arrays.asList("SDNR-CL")) + + // Poll for records + def records = consumer.poll(Duration.ofMillis(15000)) + + if (records.isEmpty()) { + log.warn("No records found within the timeout period") + vars.put("messageConsumed", "false") + } else { + // Process the first record + def record = records.first() + def requestId = record.key() + def value = record.value() + + // Store the entire message + vars.put("kafkaMessage", value) + + // Parse the value + def jsonSlurper = new groovy.json.JsonSlurper() + def parsedValue = jsonSlurper.parseText(value) + + // Extract required fields + vars.put("requestIdOnset", parsedValue["request-id"]) + vars.put("correlationId", parsedValue["correlation-id"]) + vars.put("subRequestId", parsedValue["sub-request-id"]) + + // Log the extracted information + log.info("RequestId: " + requestId) + log.info("Parsed Value: " + parsedValue) + + vars.put("messageConsumed", "true") + } +} catch (Exception e) { + log.error("Error processing Kafka message: " + e.getMessage()) + vars.put("messageConsumed", "false") +} finally { + // Close the consumer + consumer.close() +} + + - - - [] - - - Assertion.response_data - false - 12 - - - - false - requestIdOnset - \\"RequestID\\": \\"(.+?)\\" - $1$ - none - false - - - - false - correlationId - correlation-id\\": \\"(.+?)\\" - $1$ - none - false - + + true + + + import groovy.json.JsonSlurper + +def message = vars.get("kafkaMessage") +def jsonSlurper = new JsonSlurper() +def parsedMessage = jsonSlurper.parseText(message) + +vars.put("requestIdOnset", parsedMessage.requestId ?: "none") + + groovy + - - false - subRequestId - SubRequestID\\": \\"(.+?)\\" - $1$ - none - false - + + groovy + + + true + import groovy.json.JsonSlurper + +def message = vars.get("kafkaMessage") +def jsonSlurper = new JsonSlurper() +def parsedMessage = jsonSlurper.parseText(message) + +vars.put("notification", parsedMessage.notification ?: "none") + + - + groovy true - String requestIdOnset = vars.get("requestIdOnset"); -String requestId = vars.get("requestId"); -String correlationId = vars.get("correlationId"); -String subRequestId = vars.get("subRequestId"); -String counter = vars.get("counterO1"); - -String transaction = "none"; - -log.info ("The requestId id is " + requestId); -log.info ("The requestIdOnset id is " + requestIdOnset); -log.info ("The correlation id is " + correlationId); -log.info ("The subrequest id is " + subRequestId); -log.info ("The counter is " + counter); - -if ( requestId == requestIdOnset ) { - if ( correlationId == "none" || subRequestId == "none" ) { - transaction = "FINAL"; - log.info ("Final Failure Transaction"); - AssertionResult.setFailureMessage("Missing correlationId or subRequestId"); - AssertionResult.setFailure(true); - } else { - transaction = "FINAL"; - vars.put("transaction", "FINAL"); - log.info ("Final Success Transaction"); - } + import org.apache.kafka.clients.consumer.ConsumerRecord + +// Assuming the Kafka message is stored in a variable named 'kafkaMessage' +ConsumerRecord<String, String> record = vars.getObject("kafkaMessage") + +String requestIdOnset = record.key() +String requestId = vars.get("requestId") +String correlationId = "none" +String subRequestId = "none" +String counter = vars.get("counter") + +String transaction = "none" + +// Parse the Kafka message value (assuming it's JSON) +def jsonSlurper = new groovy.json.JsonSlurper() +def messageContent = jsonSlurper.parseText(record.value()) + +if (messageContent.containsKey("correlation-id")) { + correlationId = messageContent["correlation-id"] +} +if (messageContent.containsKey("sub-request-id")) { + subRequestId = messageContent["sub-request-id"] +} + +log.info("The requestId is " + requestId) +log.info("The requestIdOnset is " + requestIdOnset) +log.info("The correlation id is " + correlationId) +log.info("The subrequest id is " + subRequestId) +log.info("The counter is " + counter) + +if (requestId == requestIdOnset) { + if (correlationId == "none" || subRequestId == "none") { + transaction = "FINAL" + log.info("Final Failure Transaction") + AssertionResult.setFailureMessage("Missing correlationId or subRequestId") + AssertionResult.setFailure(true) + } else { + transaction = "FINAL" + vars.put("transaction", "FINAL") + log.info("Final Success Transaction") + } } -int counterTemp = Integer.parseInt(counter) +1; +int counterTemp = Integer.parseInt(counter) + 1 if (transaction == "FINAL") { - counterTemp = 99; + counterTemp = 99 } else if (counterTemp >= 10) { - AssertionResult.setFailureMessage("SON 01 Failure, reached maximum number of 10 attempts "); - AssertionResult.setFailure(true); + AssertionResult.setFailureMessage("SON 01 Failure, reached maximum number of 10 attempts") + AssertionResult.setFailure(true) } -vars.put("counterO1", Integer.toString(counterTemp)); - +vars.put("counter01", Integer.toString(counterTemp)) - - true - - - - false - { - "body": { - "output": { - "CommonHeader": { - "TimeStamp": "2022-08-10T07:10:05.614Z", - "APIver": "1.0", - "RequestID": "${requestId}", - "SubRequestID": "${subRequestId}", - "RequestTrack": [], - "Flags": [] - }, - "Status": { - "Code": 200, - "Value": "SUCCESS" - }, - "Payload": "{ \"Configurations\":[ { \"Status\": { \"Code\": 200, \"Value\": \"SUCCESS\" }, \"data\":{\"FAPService\":{\"alias\":\"Chn0330\",\"X0005b9Lte\":{\"phyCellIdInUse\":6,\"pnfName\":\"ncserver23\"},\"CellConfig\":{\"LTE\":{\"RAN\":{\"Common\":{\"CellIdentity\":\"Chn0330\"}}}}}} } ] }" - } - }, - "version": "1.0", - "rpc-name": "ModifyO1Config", - "correlation-id": "${correlationId}", - "type": "response" -} - + + groovy + + + true + import org.apache.kafka.clients.producer.KafkaProducer +import org.apache.kafka.clients.producer.ProducerConfig +import org.apache.kafka.clients.producer.ProducerRecord +import org.apache.kafka.common.serialization.StringSerializer + +// Kafka producer configuration +def props = new Properties() +props.put(ProducerConfig.BOOTSTRAP_SERVERS_CONFIG, vars.get("KAFKA_HOST") + ":" + vars.get("KAFKA_PORT")) +props.put(ProducerConfig.KEY_SERIALIZER_CLASS_CONFIG, StringSerializer.class.getName()) +props.put(ProducerConfig.VALUE_SERIALIZER_CLASS_CONFIG, StringSerializer.class.getName()) +props.put(ProducerConfig.CLIENT_ID_CONFIG, "sdnr-cl-rsp-producer") + +// Create Kafka producer +def producer = new KafkaProducer<>(props) + +// Prepare the message +def message = """ +{ + "body": { + "output": { + "CommonHeader": { + "TimeStamp": "2022-08-10T07:10:05.614Z", + "APIver": "1.0", + "RequestID": "${requestId}", + "SubRequestID": "${subRequestId}", + "RequestTrack": [], + "Flags": [] + }, + "Status": { + "Code": 200, + "Value": "SUCCESS" + }, + "Payload": "{ \"Configurations\":[ { \"Status\": { \"Code\": 200, \"Value\": \"SUCCESS\" }, \"data\":{\"FAPService\":{\"alias\":\"Chn0330\",\"X0005b9Lte\":{\"phyCellIdInUse\":6,\"pnfName\":\"ncserver23\"},\"CellConfig\":{\"LTE\":{\"RAN\":{\"Common\":{\"CellIdentity\":\"Chn0330\"}}}}}} } ] }" + } + }, + "version": "1.0", + "rpc-name": "ModifyO1Config", + "correlation-id": "${correlationId}", + "type": "response" +} +""".toString() + +// Create a producer record +def record = new ProducerRecord<>("sdnr-cl-rsp", vars.get("requestId").toString(), message) + +// Send the message +def future = producer.send(record) + +// Wait for the send to complete and log the result +def metadata = future.get() +log.info("Message sent to topic: ${metadata.topic()}, partition: ${metadata.partition()}, offset: ${metadata.offset()}") + +// Close the producer +producer.close() + +// Set a variable to indicate successful sending +vars.put("messageSent", "true") - = - - - - ${DROOLS_HOST} - ${DROOLS_PORT} - ${HTTP} - policy/pdp/engine/topics/sources/dmaap/sdnr-cl-rsp/events - PUT - false - false - false - false - false - false - false - 6 - false - 0 - - - - - - Content-Type - text/plain - - - - - - + + + groovy true - vars.put("counterO1", "0"); + vars.put("counter01", "0"); - - ${__javaScript(${counterO1} < 60)} + + ${__javaScript(${counter} < 60)} - - false - - - - true - {"class":"And", "filters": [ { "class":"Equals", "field":"requestId", "value":"${requestId}" }, { "class":"Equals", "field":"notification", "value":"FINAL: SUCCESS" }]} - = - true - filter - - - - ${KAFKA_HOST} - ${KAFKA_PORT} - ${HTTP} - events/policy-cl-mgt/${consumerGroup}/1?timeout=15000&limit=1 - GET - false - false - false - false - false - false - false - 6 - false - 0 - + + groovy + + + true + import org.apache.kafka.clients.consumer.KafkaConsumer +import org.apache.kafka.clients.consumer.ConsumerConfig +import org.apache.kafka.common.serialization.StringDeserializer +import java.time.Duration + +// Kafka consumer configuration +def props = new Properties() +props.put(ConsumerConfig.BOOTSTRAP_SERVERS_CONFIG, vars.get("KAFKA_HOST") + ":" + vars.get("KAFKA_PORT")) +props.put(ConsumerConfig.GROUP_ID_CONFIG, vars.get("consumerGroup")) +props.put(ConsumerConfig.KEY_DESERIALIZER_CLASS_CONFIG, StringDeserializer.class.getName()) +props.put(ConsumerConfig.VALUE_DESERIALIZER_CLASS_CONFIG, StringDeserializer.class.getName()) +props.put(ConsumerConfig.AUTO_OFFSET_RESET_CONFIG, "earliest") + +// Create Kafka consumer +def consumer = new KafkaConsumer<>(props) + +// Subscribe to the topic +consumer.subscribe(Arrays.asList("policy-cl-mgt")) + +// Initialize variables +def maxAttempts = 60 +def attempts = 0 +def success = false + +// Poll for records +while (attempts < maxAttempts && !success) { + def records = consumer.poll(Duration.ofMillis(15000)) + + for (record in records) { + def value = record.value() + log.info("Received message: " + value) + + // Parse the value + def jsonSlurper = new groovy.json.JsonSlurper() + def parsedValue = jsonSlurper.parseText(value) + + // Extract required fields + def requestId = parsedValue.requestId + def notification = parsedValue.notification + + // Check if this is the message we're looking for + if (requestId == vars.get("requestId") && notification == "FINAL: SUCCESS") { + success = true + log.info("Final Success: RequestId=" + requestId + ", Notification=" + notification) + break + } + } + + attempts++ + if (!success) { + log.info("Attempt " + attempts + " of " + maxAttempts + " failed to find matching message") + } +} + +// Close the consumer +consumer.close() + +// Set variables based on the result +if (success) { + vars.put("finalStatus", "SUCCESS") +} else { + vars.put("finalStatus", "FAILURE") + AssertionResult.setFailureMessage("Failed to receive FINAL: SUCCESS notification after " + maxAttempts + " attempts") + AssertionResult.setFailure(true) +} + + - - - [] - - - Assertion.response_data - false - 12 - - - - false - requestIdOnset - requestId\\": \\"(.+?)\\" - $1$ - none - false - + + true + + + import groovy.json.JsonSlurper + +def message = vars.get("kafkaMessage") +def jsonSlurper = new JsonSlurper() +def parsedMessage = jsonSlurper.parseText(message) + +vars.put("requestIdOnset", parsedMessage.requestId ?: "none") + + groovy + - - false - notification - notification\\": \\"FINAL: (.+?)\\" - $1$ - none - false - + + groovy + + + true + import groovy.json.JsonSlurper + +def message = vars.get("kafkaMessage") +def jsonSlurper = new JsonSlurper() +def parsedMessage = jsonSlurper.parseText(message) + +vars.put("notification", parsedMessage.notification ?: "none") + + - + groovy true - String requestIdOnset = vars.get("requestIdOnset"); -String requestId = vars.get("requestId"); -String notification = vars.get("notification"); -String counter = vars.get("counterO1"); - -String transaction = "none"; - -log.info ("The requestId id is " + requestId); -log.info ("The requestIdOnset id is " + requestIdOnset); -log.info ("The notification is " + notification); -log.info ("The transaction is " + transaction); -log.info ("The counter is " + counter); - -if ( requestId == requestIdOnset ) { - if ( notification == "SUCCESS" ) { - transaction = "FINAL"; - log.info ("Final Success Transaction"); - log.info ("The notification is SUCCESS"); - } else if ( notification == "FAILURE" ) { - transaction = "FINAL"; - log.info ("Final Failure Transaction"); - AssertionResult.setFailureMessage("Bad final notification"); - AssertionResult.setFailure(true); - } + import groovy.json.JsonSlurper + +// Parse Kafka message content +def message = vars.get("kafkaMessage") +def jsonSlurper = new JsonSlurper() +def parsedMessage = jsonSlurper.parseText(message) + +// Extract relevant fields +String requestIdOnset = parsedMessage.requestId +String notification = parsedMessage.notification +String requestId = vars.get("requestId") +String counter = vars.get("counter") +String transaction = "none" + +// Log extracted information +log.info("The requestId is " + requestId) +log.info("The requestIdOnset is " + requestIdOnset) +log.info("The notification is " + notification) +log.info("The counter is " + counter) + +// Perform assertions +if (requestId == requestIdOnset) { + if (notification == "SUCCESS") { + transaction = "FINAL" + log.info("Final Success Transaction") + } else if (notification == "FAILURE") { + transaction = "FINAL" + log.info("Final Failure Transaction") + AssertionResult.setFailureMessage("Bad final notification") + AssertionResult.setFailure(true) + } } -int counterTemp = Integer.parseInt(counter) +1; +// Update counter +int counterTemp = Integer.parseInt(counter) + 1 if (transaction == "FINAL") { - counterTemp = 99; + counterTemp = 99 } else if (counterTemp >= 60) { - AssertionResult.setFailureMessage("vCPE Success POLICYCL Failure, reached maximum number of attempts "); - AssertionResult.setFailure(true); + AssertionResult.setFailureMessage("vCPE Success POLICYCL Failure, reached maximum number of attempts") + AssertionResult.setFailure(true) } - -vars.put("counterO1", Integer.toString(counterTemp)); +vars.put("counter01", Integer.toString(counterTemp)) + - - 1 - 0 - 250 - - - - startnextloop - + + 1 + 1 + ${duration} + 11 + true + true + continue + -1 false - 1 - 1 - true - ${duration} - 11 - true - false @@ -1813,8 +1518,8 @@ vars.put("counterO1", Integer.toString(counterTemp)); consumerGroup - - sonA1 + + sonO1 false @@ -1834,406 +1539,494 @@ vars.put("counterO1", Integer.toString(counterTemp)); Update on a per iteration basis - - true - - - - false - { - "closedLoopControlName": "ControlLoop-SONA1-7d4baf04-8875-4d1f-946d-06b874048b61", - "closedLoopAlarmStart": 1606805921693, - "closedLoopEventClient": "microservice.SONH", - "closedLoopEventStatus": "ONSET", - "requestID": "${requestId}", - "target_type": "PNF", - "target": "pnf.pnf-name", - "AAI": { - "generic-vnf.prov-status": "ACTIVE", - "generic-vnf.is-closed-loop-disabled": "false", - "pnf.pnf-name": "ncserver2" - }, - "from": "SONHMS", - "version": "1.0.2", - "policyName": "SONA1", - "policyVersion": "1.0.2", - "Action": "ModifyA1Policy", - "payload": "{ \"Configurations\":[ { \"data\":{ \"FAPService\":{ \"alias\":\"Cell1\", \"CellConfig\":{ \"LTE\":{ \"RAN\":{ \"Common\":{ \"CellIdentity\":\"1\" }, \"NeighborListInUse\" : { \"LTECellNumberOfEntries\" : \"1\" , \"LTECell\" : [{ \"PLMNID\" :\"plmnid1\", \"CID\":\"Chn0001\", \"PhyCellID\":\"3\", \"PNFName\":\"ncserver01\", \"Blacklisted\":\"false\"}] } } } } } } } ] }" -} - = - - - - ${DROOLS_HOST} - ${DROOLS_PORT} - ${HTTP} - policy/pdp/engine/topics/sources/dmaap/dcae_topic/events - PUT - false - false - false - false - false - false - false - 6 - false - 0 - - - - - - Content-Type - text/plain - - - - - - + groovy true - vars.put("counterA1", "0"); + import org.apache.kafka.clients.producer.KafkaProducer +import org.apache.kafka.clients.producer.ProducerConfig +import org.apache.kafka.clients.producer.ProducerRecord +import org.apache.kafka.common.serialization.StringSerializer + +// Kafka producer configuration +def props = new Properties() +props.put(ProducerConfig.BOOTSTRAP_SERVERS_CONFIG, vars.get("KAFKA_HOST") + ":" + vars.get("KAFKA_PORT")) +props.put(ProducerConfig.KEY_SERIALIZER_CLASS_CONFIG, StringSerializer.class.getName()) +props.put(ProducerConfig.VALUE_SERIALIZER_CLASS_CONFIG, StringSerializer.class.getName()) +props.put(ProducerConfig.CLIENT_ID_CONFIG, "dcae-topic-producer") + +// Create Kafka producer +def producer = new KafkaProducer<>(props) + +// Prepare the message +def message = """ +{ + "closedLoopControlName": "ControlLoop-SONA1-7d4baf04-8875-4d1f-946d-06b874048b61", + "closedLoopAlarmStart": 1606805921693, + "closedLoopEventClient": "microservice.SONH", + "closedLoopEventStatus": "ONSET", + "requestID": "${requestId}", + "target_type": "PNF", + "target": "pnf.pnf-name", + "AAI": { + "generic-vnf.prov-status": "ACTIVE", + "generic-vnf.is-closed-loop-disabled": "false", + "pnf.pnf-name": "ncserver2" + }, + "from": "SONHMS", + "version": "1.0.2", + "policyName": "SONA1", + "policyVersion": "1.0.2", + "Action": "ModifyA1Policy", + "payload": "{ \"Configurations\":[ { \"data\":{ \"FAPService\":{ \"alias\":\"Cell1\", \"CellConfig\":{ \"LTE\":{ \"RAN\":{ \"Common\":{ \"CellIdentity\":\"1\" }, \"NeighborListInUse\" : { \"LTECellNumberOfEntries\" : \"1\" , \"LTECell\" : [{ \"PLMNID\" :\"plmnid1\", \"CID\":\"Chn0001\", \"PhyCellID\":\"3\", \"PNFName\":\"ncserver01\", \"Blacklisted\":\"false\"}] } } } } } } } ] }" +} +""".toString() + +// Create a producer record +def record = new ProducerRecord<>("unauthenticated.dcae_cl_output", vars.get("requestId").toString(), message) + +// Send the message +def future = producer.send(record) + +// Wait for the send to complete and log the result +def metadata = future.get() +log.info("Message sent to topic: ${metadata.topic()}, partition: ${metadata.partition()}, offset: ${metadata.offset()}") + +// Close the producer +producer.close() + +// Set a variable to indicate successful sending +vars.put("messageSent", "true") + - - ${__javaScript(${counterA1} < 10)} - + + groovy + + + true + vars.put("counter01", "0"); + + + + 10 + - - false - - - - true - {"class":"And", "filters": [ { "class":"Equals", "field":"request-id", "value":"${requestId}" }, { "class":"Equals", "field":"rpc-name", "value":"modifya1config" }]} - = - true - filter - - - - ${KAFKA_HOST} - ${KAFKA_PORT} - ${HTTP} - events/SDNR-CL/${consumerGroup}/1?timeout=15000&limit=1 - GET - false - false - false - false - false - false - false - 6 - false - 0 - + + groovy + + + true + import org.apache.kafka.clients.consumer.KafkaConsumer +import org.apache.kafka.clients.consumer.ConsumerConfig +import org.apache.kafka.common.serialization.StringDeserializer +import java.time.Duration + +// Kafka consumer configuration +def props = new Properties() +props.put(ConsumerConfig.BOOTSTRAP_SERVERS_CONFIG, vars.get("KAFKA_HOST") + ":" + vars.get("KAFKA_PORT")) +props.put(ConsumerConfig.GROUP_ID_CONFIG, vars.get("consumerGroup")) +props.put(ConsumerConfig.KEY_DESERIALIZER_CLASS_CONFIG, StringDeserializer.class.getName()) +props.put(ConsumerConfig.VALUE_DESERIALIZER_CLASS_CONFIG, StringDeserializer.class.getName()) +props.put(ConsumerConfig.AUTO_OFFSET_RESET_CONFIG, "earliest") + +// Create Kafka consumer +def consumer = new KafkaConsumer<>(props) + +try { + // Subscribe to the topic + consumer.subscribe(Arrays.asList("SDNR-CL")) + + // Poll for records + def records = consumer.poll(Duration.ofMillis(15000)) + + if (records.isEmpty()) { + log.warn("No records found within the timeout period") + vars.put("messageConsumed", "false") + } else { + // Process the first record + def record = records.first() + def requestId = record.key() + def value = record.value() + + // Store the entire message + vars.put("kafkaMessage", value) + + // Parse the value + def jsonSlurper = new groovy.json.JsonSlurper() + def parsedValue = jsonSlurper.parseText(value) + + // Extract required fields + vars.put("requestIdOnset", parsedValue["request-id"]) + vars.put("correlationId", parsedValue["correlation-id"]) + vars.put("subRequestId", parsedValue["sub-request-id"]) + + // Log the extracted information + log.info("RequestId: " + requestId) + log.info("Parsed Value: " + parsedValue) + + vars.put("messageConsumed", "true") + } +} catch (Exception e) { + log.error("Error processing Kafka message: " + e.getMessage()) + vars.put("messageConsumed", "false") +} finally { + // Close the consumer + consumer.close() +} + + - - - [] - - - Assertion.response_data - false - 12 - - - - false - requestIdOnset - \\"RequestID\\": \\"(.+?)\\" - $1$ - none - false - - - - false - correlationId - correlation-id\\": \\"(.+?)\\" - $1$ - none - false - + + true + + + import groovy.json.JsonSlurper + +def message = vars.get("kafkaMessage") +def jsonSlurper = new JsonSlurper() +def parsedMessage = jsonSlurper.parseText(message) + +vars.put("requestIdOnset", parsedMessage.requestId ?: "none") + + groovy + - - false - subRequestId - SubRequestID\\": \\"(.+?)\\" - $1$ - none - false - + + groovy + + + true + import groovy.json.JsonSlurper + +def message = vars.get("kafkaMessage") +def jsonSlurper = new JsonSlurper() +def parsedMessage = jsonSlurper.parseText(message) + +vars.put("notification", parsedMessage.notification ?: "none") + + - + groovy true - String requestIdOnset = vars.get("requestIdOnset"); -String requestId = vars.get("requestId"); -String correlationId = vars.get("correlationId"); -String subRequestId = vars.get("subRequestId"); -String counter = vars.get("counterA1"); - -String transaction = "none"; - -log.info ("The requestId id is " + requestId); -log.info ("The requestIdOnset id is " + requestIdOnset); -log.info ("The correlation id is " + correlationId); -log.info ("The subrequest id is " + subRequestId); -log.info ("The counter is " + counter); - -if ( requestId == requestIdOnset ) { - if ( correlationId == "none" || subRequestId == "none" ) { - transaction = "FINAL"; - log.info ("Final Failure Transaction"); - AssertionResult.setFailureMessage("Missing correlationId or subRequestId"); - AssertionResult.setFailure(true); - } else { - transaction = "FINAL"; - vars.put("transaction", "FINAL"); - log.info ("Final Success Transaction"); - } + import org.apache.kafka.clients.consumer.ConsumerRecord + +// Assuming the Kafka message is stored in a variable named 'kafkaMessage' +ConsumerRecord<String, String> record = vars.getObject("kafkaMessage") + +String requestIdOnset = record.key() +String requestId = vars.get("requestId") +String correlationId = "none" +String subRequestId = "none" +String counter = vars.get("counter") + +String transaction = "none" + +// Parse the Kafka message value (assuming it's JSON) +def jsonSlurper = new groovy.json.JsonSlurper() +def messageContent = jsonSlurper.parseText(record.value()) + +if (messageContent.containsKey("correlation-id")) { + correlationId = messageContent["correlation-id"] +} +if (messageContent.containsKey("sub-request-id")) { + subRequestId = messageContent["sub-request-id"] +} + +log.info("The requestId is " + requestId) +log.info("The requestIdOnset is " + requestIdOnset) +log.info("The correlation id is " + correlationId) +log.info("The subrequest id is " + subRequestId) +log.info("The counter is " + counter) + +if (requestId == requestIdOnset) { + if (correlationId == "none" || subRequestId == "none") { + transaction = "FINAL" + log.info("Final Failure Transaction") + AssertionResult.setFailureMessage("Missing correlationId or subRequestId") + AssertionResult.setFailure(true) + } else { + transaction = "FINAL" + vars.put("transaction", "FINAL") + log.info("Final Success Transaction") + } } -int counterTemp = Integer.parseInt(counter) +1; +int counterTemp = Integer.parseInt(counter) + 1 if (transaction == "FINAL") { - counterTemp = 99; + counterTemp = 99 } else if (counterTemp >= 10) { - AssertionResult.setFailureMessage("SON A1 Success SDNR-CL Failure, reached maximum number of 10 attempts "); - AssertionResult.setFailure(true); + AssertionResult.setFailureMessage("SON A1 Failure, reached maximum number of 10 attempts") + AssertionResult.setFailure(true) } -vars.put("counterA1", Integer.toString(counterTemp)); - +vars.put("counter01", Integer.toString(counterTemp)) - - true - - - - false - { - "body": { - "output": { - "CommonHeader": { - "TimeStamp": "2022-09-10T07:10:05.614Z", - "APIver": "1.0", - "RequestID": "${requestId}", - "SubRequestID": "${subRequestId}", - "RequestTrack": [], - "Flags": [] - }, - "Status": { - "Code": 200, - "Value": "SUCCESS" - }, - "Payload": "{ \"Configurations\":[ { \"Status\": { \"Code\": 200, \"Value\": \"SUCCESS\" }, \"data\":{ \"FAPService\":{ \"alias\":\"Cell1\", \"CellConfig\":{ \"LTE\":{ \"RAN\":{ \"Common\":{ \"CellIdentity\":\"1\" }, \"NeighborListInUse\" : { \"LTECellNumberOfEntries\" : \"1\" , \"LTECell\" : [{ \"PLMNID\" :\"plmnid1\", \"CID\":\"Chn0001\", \"PhyCellID\":\"3\", \"PNFName\":\"ncserver01\", \"Blacklisted\":\"false\"}] } } } } } } } ] }" - } - }, - "version": "1.0", - "rpc-name": "ModifyA1Policy", - "correlation-id": "${correlationId}", - "type": "response" -} - = - - - - ${DROOLS_HOST} - ${DROOLS_PORT} - ${HTTP} - policy/pdp/engine/topics/sources/dmaap/sdnr-cl-rsp/events - PUT - false - false - false - false - false - false - false - 6 - false - 0 - - - - - - Content-Type - text/plain - - - - - - + + groovy + + + true + import org.apache.kafka.clients.producer.KafkaProducer +import org.apache.kafka.clients.producer.ProducerConfig +import org.apache.kafka.clients.producer.ProducerRecord +import org.apache.kafka.common.serialization.StringSerializer + +// Kafka producer configuration +def props = new Properties() +props.put(ProducerConfig.BOOTSTRAP_SERVERS_CONFIG, vars.get("KAFKA_HOST") + ":" + vars.get("KAFKA_PORT")) +props.put(ProducerConfig.KEY_SERIALIZER_CLASS_CONFIG, StringSerializer.class.getName()) +props.put(ProducerConfig.VALUE_SERIALIZER_CLASS_CONFIG, StringSerializer.class.getName()) +props.put(ProducerConfig.CLIENT_ID_CONFIG, "sdnr-cl-rsp-producer") + +// Create Kafka producer +def producer = new KafkaProducer<>(props) + +// Prepare the message +def message = """ +{ + "body": { + "output": { + "CommonHeader": { + "TimeStamp": "2022-08-10T07:10:05.614Z", + "APIver": "1.0", + "RequestID": "${requestId}", + "SubRequestID": "${subRequestId}", + "RequestTrack": [], + "Flags": [] + }, + "Status": { + "Code": 200, + "Value": "SUCCESS" + }, + "Payload": "{ \"Configurations\":[ { \"Status\": { \"Code\": 200, \"Value\": \"SUCCESS\" }, \"data\":{\"FAPService\":{\"alias\":\"Chn0330\",\"X0005b9Lte\":{\"phyCellIdInUse\":6,\"pnfName\":\"ncserver23\"},\"CellConfig\":{\"LTE\":{\"RAN\":{\"Common\":{\"CellIdentity\":\"Chn0330\"}}}}}} } ] }" + } + }, + "version": "1.0", + "rpc-name": "ModifyO1Config", + "correlation-id": "${correlationId}", + "type": "response" +} +""".toString() + +// Create a producer record +def record = new ProducerRecord<>("sdnr-cl-rsp", vars.get("requestId").toString(), message) + +// Send the message +def future = producer.send(record) + +// Wait for the send to complete and log the result +def metadata = future.get() +log.info("Message sent to topic: ${metadata.topic()}, partition: ${metadata.partition()}, offset: ${metadata.offset()}") + +// Close the producer +producer.close() + +// Set a variable to indicate successful sending +vars.put("messageSent", "true") + + + + groovy true - vars.put("counterA1", "0"); + vars.put("counter01", "0"); - ${__javaScript(${counterA1} < 60)} + ${__javaScript(${counter} < 60)} - - false - - - - true - {"class":"And", "filters": [ { "class":"Equals", "field":"requestId", "value":"${requestId}" }, { "class":"Equals", "field":"notification", "value":"FINAL: SUCCESS" }]} - = - true - filter - - - - ${KAFKA_HOST} - ${KAFKA_PORT} - ${HTTP} - events/policy-cl-mgt/${consumerGroup}/1?timeout=15000&limit=1 - GET - false - false - false - false - false - false - false - 6 - false - 0 - + + groovy + + + true + import org.apache.kafka.clients.consumer.KafkaConsumer +import org.apache.kafka.clients.consumer.ConsumerConfig +import org.apache.kafka.common.serialization.StringDeserializer +import java.time.Duration + +// Kafka consumer configuration +def props = new Properties() +props.put(ConsumerConfig.BOOTSTRAP_SERVERS_CONFIG, vars.get("KAFKA_HOST") + ":" + vars.get("KAFKA_PORT")) +props.put(ConsumerConfig.GROUP_ID_CONFIG, vars.get("consumerGroup")) +props.put(ConsumerConfig.KEY_DESERIALIZER_CLASS_CONFIG, StringDeserializer.class.getName()) +props.put(ConsumerConfig.VALUE_DESERIALIZER_CLASS_CONFIG, StringDeserializer.class.getName()) +props.put(ConsumerConfig.AUTO_OFFSET_RESET_CONFIG, "earliest") + +// Create Kafka consumer +def consumer = new KafkaConsumer<>(props) + +// Subscribe to the topic +consumer.subscribe(Arrays.asList("policy-cl-mgt")) + +// Initialize variables +def maxAttempts = 60 +def attempts = 0 +def success = false + +// Poll for records +while (attempts < maxAttempts && !success) { + def records = consumer.poll(Duration.ofMillis(15000)) + + for (record in records) { + def value = record.value() + log.info("Received message: " + value) + + // Parse the value + def jsonSlurper = new groovy.json.JsonSlurper() + def parsedValue = jsonSlurper.parseText(value) + + // Extract required fields + def requestId = parsedValue.requestId + def notification = parsedValue.notification + + // Check if this is the message we're looking for + if (requestId == vars.get("requestId") && notification == "FINAL: SUCCESS") { + success = true + log.info("Final Success: RequestId=" + requestId + ", Notification=" + notification) + break + } + } + + attempts++ + if (!success) { + log.info("Attempt " + attempts + " of " + maxAttempts + " failed to find matching message") + } +} + +// Close the consumer +consumer.close() + +// Set variables based on the result +if (success) { + vars.put("finalStatus", "SUCCESS") +} else { + vars.put("finalStatus", "FAILURE") + AssertionResult.setFailureMessage("Failed to receive FINAL: SUCCESS notification after " + maxAttempts + " attempts") + AssertionResult.setFailure(true) +} + + - - - [] - - - Assertion.response_data - false - 12 - - - - false - requestIdOnset - requestId\\": \\"(.+?)\\" - $1$ - none - false - + + true + + + import groovy.json.JsonSlurper + +def message = vars.get("kafkaMessage") +def jsonSlurper = new JsonSlurper() +def parsedMessage = jsonSlurper.parseText(message) + +vars.put("requestIdOnset", parsedMessage.requestId ?: "none") + + groovy + - - false - notification - notification\\": \\"FINAL: (.+?)\\" - $1$ - none - false - + + groovy + + + true + import groovy.json.JsonSlurper + +def message = vars.get("kafkaMessage") +def jsonSlurper = new JsonSlurper() +def parsedMessage = jsonSlurper.parseText(message) + +vars.put("notification", parsedMessage.notification ?: "none") + + groovy true - String requestIdOnset = vars.get("requestIdOnset"); -String requestId = vars.get("requestId"); -String notification = vars.get("notification"); -String counter = vars.get("counterA1"); - -String transaction = "none"; - -log.info ("The requestId id is " + requestId); -log.info ("The requestIdOnset id is " + requestIdOnset); -log.info ("The notification is " + notification); -log.info ("The transaction is " + transaction); -log.info ("The counter is " + counter); - -if ( requestId == requestIdOnset ) { - if ( notification == "SUCCESS" ) { - transaction = "FINAL"; - log.info ("Final Success Transaction"); - log.info ("The notification is SUCCESS"); - } else if ( notification == "FAILURE" ) { - transaction = "FINAL"; - log.info ("Final Failure Transaction"); - AssertionResult.setFailureMessage("Bad final notification"); - AssertionResult.setFailure(true); - } + import groovy.json.JsonSlurper + +// Parse Kafka message content +def message = vars.get("kafkaMessage") +def jsonSlurper = new JsonSlurper() +def parsedMessage = jsonSlurper.parseText(message) + +// Extract relevant fields +String requestIdOnset = parsedMessage.requestId +String notification = parsedMessage.notification +String requestId = vars.get("requestId") +String counter = vars.get("counter") +String transaction = "none" + +// Log extracted information +log.info("The requestId is " + requestId) +log.info("The requestIdOnset is " + requestIdOnset) +log.info("The notification is " + notification) +log.info("The counter is " + counter) + +// Perform assertions +if (requestId == requestIdOnset) { + if (notification == "SUCCESS") { + transaction = "FINAL" + log.info("Final Success Transaction") + } else if (notification == "FAILURE") { + transaction = "FINAL" + log.info("Final Failure Transaction") + AssertionResult.setFailureMessage("Bad final notification") + AssertionResult.setFailure(true) + } } -int counterTemp = Integer.parseInt(counter) +1; +// Update counter +int counterTemp = Integer.parseInt(counter) + 1 if (transaction == "FINAL") { - counterTemp = 99; + counterTemp = 99 } else if (counterTemp >= 60) { - AssertionResult.setFailureMessage("vCPE Success POLICYCL Failure, reached maximum number of attempts "); - AssertionResult.setFailure(true); + AssertionResult.setFailureMessage("vCPE Success POLICYCL Failure, reached maximum number of attempts") + AssertionResult.setFailure(true) } - -vars.put("counterA1", Integer.toString(counterTemp)); +vars.put("counter01", Integer.toString(counterTemp)) + - - 1 - 0 - 250 - - + 1 + 1 + true continue - + 1 false - 1 - 1 - false - - - true - false - - - + 6 ${PAP_HOST} ${PAP_PORT} ${HTTP} policy/pap/v1/pdps/policies/operational.restart/versions/1.0.0 DELETE - false - false - false - false - false - false - false - 6 - false - 0 + false + + + @@ -2248,25 +2041,16 @@ vars.put("counterA1", Integer.toString(counterTemp)); - false - - - + 6 ${PAP_HOST} ${PAP_PORT} ${HTTP} policy/pap/v1/pdps/policies/op.5g.son.a1/versions/1.0.0 DELETE - false - false - false - false - false - false - false - 6 - false - 0 + false + + + @@ -2281,25 +2065,16 @@ vars.put("counterA1", Integer.toString(counterTemp)); - false - - - + 6 ${PAP_HOST} ${PAP_PORT} ${HTTP} policy/pap/v1/pdps/policies/op.5g.son.o1/versions/1.0.0 DELETE - false - false - false - false - false - false - false - 6 - false - 0 + false + + + @@ -2317,25 +2092,16 @@ vars.put("counterA1", Integer.toString(counterTemp)); - false - - - + 6 ${API_HOST} ${API_PORT} ${HTTP} policy/api/v1/policytypes/onap.policies.controlloop.operational.common.Drools/versions/1.0.0/policies/operational.restart/versions/1.0.0 DELETE - false - false - false - false - false - false - false - 6 - false - 0 + false + + + @@ -2350,25 +2116,16 @@ vars.put("counterA1", Integer.toString(counterTemp)); - false - - - + 6 ${API_HOST} ${API_PORT} ${HTTP} policy/api/v1/policytypes/onap.policies.controlloop.operational.common.Drools/versions/1.0.0/policies/op.5g.son.a1/versions/1.0.0 DELETE - false - false - false - false - false - false - false - 6 - false - 0 + false + + + @@ -2383,25 +2140,16 @@ vars.put("counterA1", Integer.toString(counterTemp)); - false - - - + 6 ${API_HOST} ${API_PORT} ${HTTP} policy/api/v1/policytypes/onap.policies.controlloop.operational.common.Drools/versions/1.0.0/policies/op.5g.son.o1/versions/1.0.0 DELETE - false - false - false - false - false - false - false - 6 - false - 0 + false + + +