/.classpath
/.project
/.settings
-/target/
+target
/.mvn/wrapper/maven-wrapper.jar
/.tox
import org.springframework.web.bind.annotation.PutMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
+import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;
-
+import java.util.Collection;
import io.swagger.annotations.ApiOperation;
/**
+ "}")
@Secured({ DashboardConstants.ROLE_ADMIN })
public void putPolicyInstance(@PathVariable(POLICY_TYPE_ID_NAME) String policyTypeIdString,
+ @RequestParam(name = "ric", required = true) String ric,
@PathVariable(POLICY_INSTANCE_ID_NAME) String policyInstanceId, @RequestBody String instance) {
logger.debug("putPolicyInstance typeId: {}, instanceId: {}, instance: {}", policyTypeIdString, policyInstanceId,
instance);
- this.policyAgentApi.putPolicy(policyTypeIdString, policyInstanceId, instance);
+ this.policyAgentApi.putPolicy(policyTypeIdString, policyInstanceId, instance, ric);
}
@ApiOperation(value = "Deletes the policy instances for the given policy type.")
throw new HttpNotImplementedException("Not Implemented Exception");
}
}
-}
+
+ @ApiOperation(value = "Returns the rics supporting the given policy type.")
+ @GetMapping("/rics")
+ @Secured({ DashboardConstants.ROLE_ADMIN, DashboardConstants.ROLE_STANDARD })
+ public String getRicsSupportingType(
+ @RequestParam(name = "policyType", required = true) String supportingPolicyType) {
+ logger.debug("getRicsSupportingType {}", supportingPolicyType);
+
+ Collection<String> result = this.policyAgentApi.getRicsSupportingType(supportingPolicyType);
+ String json = gson.toJson(result);
+ return json;
+ }
+
+};
*/
package org.oransc.ric.portal.dashboard.policyagentapi;
+import java.util.Collection;
+
import org.oransc.ric.portal.dashboard.model.PolicyInstances;
import org.oransc.ric.portal.dashboard.model.PolicyTypes;
import org.springframework.web.client.RestClientException;
public String getPolicyInstance(String id) throws RestClientException;
- public void putPolicy(String policyTypeIdString, String policyInstanceId, String json) throws RestClientException;
+ public void putPolicy(String policyTypeIdString, String policyInstanceId, String json, String ric)
+ throws RestClientException;
public void deletePolicy(String policyInstanceId) throws RestClientException;
+
+ public Collection<String> getRicsSupportingType(String typeName);
+
}
import org.springframework.web.client.RestClientException;
import org.springframework.web.client.RestTemplate;
+import java.util.Collection;
import java.util.List;
import java.util.Map;
+import java.util.Vector;
import java.lang.invoke.MethodHandles;
import java.lang.reflect.Type;
result.add(p);
}
return result;
-
}
@Override
}
@Override
- public void putPolicy(String policyTypeIdString, String policyInstanceId, String json) throws RestClientException {
+ public void putPolicy(String policyTypeIdString, String policyInstanceId, String json, String ric)
+ throws RestClientException {
String url = baseUrl() + "/policy?type={type}&instance={instance}&ric={ric}&service={service}";
Map<String, ?> uriVariables = Map.of( //
"type", policyTypeIdString, //
"instance", policyInstanceId, //
- "ric", "ric1", // TODO
+ "ric", ric, //
"service", "dashboard");
this.restTemplate.put(url, json, uriVariables);
this.restTemplate.delete(url, uriVariables);
}
+ @Value.Immutable
+ @Gson.TypeAdapters
+ interface RicInfo {
+ public String name();
+
+ public Collection<String> nodeNames();
+
+ public Collection<String> policyTypes();
+ }
+
+ @Override
+ public Collection<String> getRicsSupportingType(String typeName) {
+ String url = baseUrl() + "/rics?policyType={typeName}";
+ Map<String, ?> uriVariables = Map.of("typeName", typeName);
+ String rsp = this.restTemplate.getForObject(url, String.class, uriVariables);
+
+ Type listType = new TypeToken<List<ImmutableRicInfo>>() {
+ }.getType();
+ List<RicInfo> rspParsed = gson.fromJson(rsp, listType);
+
+ Collection<String> result = new Vector<>(rspParsed.size());
+ for (RicInfo ric : rspParsed) {
+ result.add(ric.name());
+ }
+ return result;
+ }
+
}
import java.util.List;
import java.util.Map;
import java.util.Optional;
+import java.util.Vector;
import java.util.stream.Collectors;
import org.oransc.ric.portal.dashboard.model.ImmutablePolicyInfo;
}
@Override
- public void putPolicy(String policyTypeIdString, String policyInstanceId, String json)
+ public void putPolicy(String policyTypeIdString, String policyInstanceId, String json, String ric)
throws RestClientException {
- database.putInstance(policyTypeIdString, policyInstanceId, json);
+ database.putInstance(policyTypeIdString, policyInstanceId, json, ric);
}
@Override
return result;
}
+ @Override
+ public Collection<String> getRicsSupportingType(String typeName) {
+ Vector<String> res = new Vector<>();
+ res.add("ric_1");
+ res.add("ric_2");
+ res.add("ric_3");
+ return res;
+ }
}
class Database {
policy = new PolicyType("type4", schema);
types.put("type4", policy);
try {
- putInstance("ANR", "ANR-1", getStringFromFile("anr-policy-instance.json"));
+ putInstance("ANR", "ANR-1", getStringFromFile("anr-policy-instance.json"), "ric_1");
} catch (Exception e) {
// Nothing
}
return java.time.Instant.now().toString();
}
- void putInstance(String typeId, String instanceId, String instanceData) {
+ void putInstance(String typeId, String instanceId, String instanceData, String ric) {
PolicyInfo i = ImmutablePolicyInfo.builder().json(instanceData).lastModified(getTimeStampUTC())
- .id(instanceId).ric("ricXX").service("service").type(typeId).build();
+ .id(instanceId).ric(ric).service("service").type(typeId).build();
instances.put(instanceId, i);
}
color: gray;
letter-spacing: 0.1rem;
font-size: 10px;
+ margin-left: 10px;
}
.copyright__text-dark {
<div class="text-muted" *ngIf="jsonSchemaObject.description">{{jsonSchemaObject.description}}</div>
<div fxLayout="row" fxLayoutAlign="space-around start" fxLayout.lt-sm="column" fxLayoutAlign.lt-sm="flex-start center">
+
+
<mat-card class="card" [ngClass]="{'card-dark': darkMode}">
+
+ <mat-form-field *ngIf="!this.policyInstanceId">
+ <mat-label [class.text-danger]="!this.ric">Select RIC</mat-label>
+ <mat-select [(value)]="this.ric">
+ <mat-option *ngFor="let ric of this.allRics" [value]="ric">
+ {{ric}}
+ </mat-option>
+ </mat-select>
+ </mat-form-field>
+
<h4 class="default-cursor" (click)="toggleVisible('form')">
<mat-icon matTooltip="Properties">{{isVisible.form ? 'expand_less' : 'expand_more'}}</mat-icon>
Properties
</json-schema-form>
</div>
<hr />
- <button mat-raised-button (click)="this.onSubmit()" [disabled]="!this.formIsValid" class="submitBtn"
- style="margin-right:10px">Submit</button>
+ <button mat-raised-button (click)="this.onSubmit()" [disabled]="!this.formIsValid || !this.ric"
+ class="submitBtn">Submit</button>
<button mat-raised-button (click)="this.onClose()">Close</button>
<hr />
<h4 [class.text-danger]="!formIsValid && !isVisible.json" [class.default-cursor]="formIsValid || isVisible.json"
.submitBtn {
background-color: #4CAF50;
/* Green */
+ margin-right: 10px;
}
.card {
formValidationErrors: any;
formIsValid = false;
-
@ViewChild(MatMenuTrigger, { static: true }) menuTrigger: MatMenuTrigger;
- public policyInstanceId: string;
- public policyTypeName: string;
+ policyInstanceId: string; // null if not yet created
+ policyTypeName: string;
darkMode: boolean;
+ ric: string;
+ allRics: string[];
+ private fetchRics() {
+ console.log('fetchRics ' + this.policyTypeName);
+ const self: PolicyInstanceDialogComponent = this;
+ this.dataService.getRics(this.policyTypeName).subscribe(
+ {
+ next(value) {
+ self.allRics = value;
+ console.log(value);
+ },
+ error(error) {
+ self.errorService.displayError('Fetching of rics failed: ' + error.message);
+ },
+ complete() { }
+ });
+ }
constructor(
private dataService: PolicyService,
this.policyTypeName = data.name;
this.jsonSchemaObject = data.createSchema;
this.jsonObject = this.parseJson(data.instanceJson);
+ this.ric = data.ric;
}
ngOnInit() {
this.ui.darkModeState.subscribe((isDark) => {
this.darkMode = isDark;
});
+ if (!this.policyInstanceId) {
+ this.fetchRics();
+ }
}
ngAfterViewInit() {
}
const policyJson: string = this.prettyLiveFormData;
const self: PolicyInstanceDialogComponent = this;
- this.dataService.putPolicy(this.policyTypeName, this.policyInstanceId, policyJson).subscribe(
+ this.dataService.putPolicy(this.policyTypeName, this.policyInstanceId, policyJson, this.ric).subscribe(
{
next(value) {
self.notificationService.success('Policy ' + self.policyTypeName + ':' + self.policyInstanceId + ' submitted');
const instanceId = instance ? instance.id : null;
const instanceJson = instance ? instance.json : null;
const name = policyType.name;
+ const ric = instance ? instance.ric : null;
return {
maxWidth: '1200px',
maxHeight: '900px',
createSchema,
instanceId,
instanceJson,
- name
+ name,
+ ric
}
};
}
* @param policyJson Json with the policy content
* @returns Observable that should yield a response code, no data
*/
- putPolicy(policyTypeId: string, policyInstanceId: string, policyJson: string): Observable<any> {
- const url = this.buildPath(this.policyTypePath, policyTypeId, this.policyPath, policyInstanceId);
+ putPolicy(policyTypeId: string, policyInstanceId: string, policyJson: string, ric: string): Observable<any> {
+ const url = this.buildPath(this.policyTypePath, policyTypeId, this.policyPath, policyInstanceId) + "?ric=" + ric;
return this.httpClient.put<PolicyInstanceAck>(url, policyJson, { observe: 'response' });
}
const url = this.buildPath(this.policyTypePath, policyTypeId, this.policyPath, policyInstanceId);
return this.httpClient.delete(url, { observe: 'response' });
}
+
+
+ getRics(policyTypeId: string): Observable<string[]> {
+ const url = this.buildPath('rics') + '?policyType=' + policyTypeId;
+ return this.httpClient.get<any>(url);
+ }
}
--- /dev/null
+logs
+.tmp_*
\ No newline at end of file
--- /dev/null
+#!/usr/bin/env bash
+
+TC_ONELINE_DESCR="Auto test for policy agent with simulator"
+
+. ../common/testcase_common.sh $1 $2
+
+clean_containers
+
+start_simulators
+
+consul_config_app "../simulator-group/consul_cbs/config.json"
+
+start_policy_agent
+
+check_policy_agent_logs
+
+#### TEST COMPLETE ####
+
+store_logs END
+
--- /dev/null
+#!/usr/bin/env bash
+
+# Local image and tag, shall point to locally built image (non-nexus path)
+export POLICY_AGENT_LOCAL_IMAGE=o-ran-sc/policy-agent
+
+
+# Common env var for auto-test.
+
+POLICY_AGENT_PORT=8081
+POLICY_AGENT_LOGPATH="/var/log/policy-agent/application.log" #Path the application log in the policy agent container
+DOCKER_SIM_NWNAME="nonrtric-docker-net" #Name of docker private network
+CONSUL_HOST="consul-server" #Host name of consul
+CONSUL_PORT=8500 #Port number of consul
+CONFIG_BINDING_SERVICE="config-binding-service" #Host name of CBS
+PA_APP_BASE="policy-agent"
--- /dev/null
+#!/usr/bin/env bash
+
+. ../common/test_env.sh
+
+echo "Test case started as: ${BASH_SOURCE[$i+1]} "$1 $2
+
+STARTED_POLICY_AGENT="" #Policy agent app names added to this var to keep track of started container in the script
+START_ARG=$1
+IMAGE_TAG="1.0.0-SNAPSHOT"
+
+if [ $# -lt 1 ] || [ $# -gt 2 ]; then
+ echo "Expected arg: local [<image-tag>] ]| remote [<image-tag>] ]| remote-remove [<image-tag>]] | manual-container | manual-app"
+ exit 1
+elif [ $1 == "local" ]; then
+ if [ -z $POLICY_AGENT_LOCAL_IMAGE ]; then
+ echo "POLICY_AGENT_LOCAL_IMAGE not set in test_env"
+ exit 1
+ fi
+ POLICY_AGENT_IMAGE=$POLICY_AGENT_LOCAL_IMAGE":"$IMAGE_TAG
+fi
+
+# Set a description string for the test case
+if [ -z "$TC_ONELINE_DESCR" ]; then
+ TC_ONELINE_DESCR="<no-description>"
+ echo "No test case description found, TC_ONELINE_DESCR should be set on in the test script , using "$TC_ONELINE_DESCR
+fi
+
+ATC=$(basename "${BASH_SOURCE[$i+1]}" .sh)
+
+
+# Create the logs dir if not already created in the current dir
+if [ ! -d "logs" ]; then
+ mkdir logs
+fi
+
+TESTLOGS=$PWD/logs
+
+mkdir -p $TESTLOGS/$ATC
+
+TCLOG=$TESTLOGS/$ATC/TC.log
+exec &> >(tee ${TCLOG})
+
+#Variables for counting tests as well as passed and failed tests
+RES_TEST=0
+RES_PASS=0
+RES_FAIL=0
+TCTEST_START=$SECONDS
+
+echo "-------------------------------------------------------------------------------------------------"
+echo "----------------------------------- Test case: "$ATC
+echo "----------------------------------- Started: "$(date)
+echo "-------------------------------------------------------------------------------------------------"
+echo "-- Description: "$TC_ONELINE_DESCR
+echo "-------------------------------------------------------------------------------------------------"
+echo "----------------------------------- Test case setup -----------------------------------"
+
+
+if [ -z "$SIM_GROUP" ]; then
+ SIM_GROUP=$PWD/../simulator-group
+ if [ ! -d $SIM_GROUP ]; then
+ echo "Trying to set env var SIM_GROUP to dir 'simulator-group' in the integration repo, but failed."
+ echo "Please set the SIM_GROUP manually in the test_env.sh"
+ exit 1
+ else
+ echo "SIM_GROUP auto set to: " $SIM_GROUP
+ fi
+elif [ $SIM_GROUP = *simulator_group ]; then
+ echo "Env var SIM_GROUP does not seem to point to dir 'simulator-group' in the integration repo, check test_env.sh"
+ exit 1
+fi
+
+echo ""
+
+if [ $1 != "manual-container" ] && [ $1 != "manual-app" ]; then
+ echo -e "Policy agent image tag set to: \033[1m" $IMAGE_TAG"\033[0m"
+ echo "Configured image for policy agent app(s) (${1}): "$POLICY_AGENT_LOCAL_IMAGE
+ tmp_im=$(docker images ${POLICY_AGENT_LOCAL_IMAGE} | grep -v REPOSITORY)
+
+ if [ $1 == "local" ]; then
+ if [ -z "$tmp_im" ]; then
+ echo "Local image (non nexus) "$POLICY_AGENT_LOCAL_IMAGE" does not exist in local registry, need to be built"
+ exit 1
+ else
+ echo -e "Policy agent local image: \033[1m"$tmp_im"\033[0m"
+ echo "If the policy agen image seem outdated, rebuild the image and run the test again."
+ fi
+ fi
+fi
+
+
+
+__consul_config() {
+
+ appname=$PA_APP_BASE
+
+ echo "Configuring consul for " $appname " from " $1
+ curl -s http://127.0.0.1:${CONSUL_PORT}/v1/kv/${appname}?dc=dc1 -X PUT -H 'Accept: application/json' -H 'Content-Type: application/json' -H 'X-Requested-With: XMLHttpRequest' --data-binary "@"$1 >/dev/null
+}
+
+
+consul_config_app() {
+
+ __consul_config $1
+
+}
+
+# Start all simulators in the simulator group
+start_simulators() {
+
+ echo "Starting all simulators"
+ curdir=$PWD
+ cd $SIM_GROUP
+ $SIM_GROUP/simulators-start.sh
+ cd $curdir
+ echo ""
+}
+
+clean_containers() {
+ echo "Stopping all containers, policy agent app(s) and simulators with name prefix 'policy_agent'"
+ docker stop $(docker ps -q --filter name=/policy-agent) &> /dev/null
+ echo "Removing all containers, policy agent app and simulators with name prefix 'policy_agent'"
+ docker rm $(docker ps -a -q --filter name=/policy-agent) &> /dev/null
+ echo "Removing unused docker networks with substring 'policy agent' in network name"
+ docker network rm $(docker network ls -q --filter name=nonrtric)
+ echo ""
+}
+
+start_policy_agent() {
+
+ appname=$PA_APP_BASE
+
+ if [ $START_ARG == "local" ] ; then
+ __start_policy_agent_image $appname
+ fi
+}
+
+__start_policy_agent_image() {
+
+ appname=$1
+ localport=$POLICY_AGENT_PORT
+
+ echo "Creating docker network $DOCKER_SIM_NWNAME, if needed"
+
+ docker network ls| grep $DOCKER_SIM_NWNAME > /dev/null || docker network create $DOCKER_SIM_NWNAME
+
+ echo "Starting policy agent: " $appname " with ports mapped to " $localport " in docker network "$DOCKER_SIM_NWNAME
+ docker run -d -p $localport":8081" --network=$DOCKER_SIM_NWNAME -e CONSUL_HOST=$CONSUL_HOST -e CONSUL_PORT=$CONSUL_PORT -e CONFIG_BINDING_SERVICE=$CONFIG_BINDING_SERVICE -e HOSTNAME=$appname --name $appname $POLICY_AGENT_IMAGE
+ #docker run -d -p 8081:8081 --network=nonrtric-docker-net -e CONSUL_HOST=CONSUL_HOST=$CONSUL_HOST -e CONSUL_PORT=$CONSUL_PORT -e CONFIG_BINDING_SERVICE=$CONFIG_BINDING_SERVICE -e HOSTNAME=policy-agent
+ sleep 3
+ set +x
+ pa_started=false
+ for i in {1..10}; do
+ if [ $(docker inspect --format '{{ .State.Running }}' $appname) ]
+ then
+ echo " Image: $(docker inspect --format '{{ .Config.Image }}' ${appname})"
+ echo "Policy Agent container ${appname} running"
+ pa_started=true
+ break
+ else
+ sleep $i
+ fi
+ done
+ if ! [ $pa_started ]; then
+ echo "Policy Agent container ${appname} could not be started"
+ exit 1
+ fi
+
+ pa_st=false
+ echo "Waiting for Policy Agent ${appname} service status..."
+ for i in {1..10}; do
+ result="$(__do_curl http://127.0.0.1:${localport}/status)"
+ if [ $? -eq 0 ]; then
+ echo "Policy Agent ${appname} responds to service status: " $result
+ pa_st=true
+ break
+ else
+ sleep $i
+ fi
+ done
+
+ if [ "$pa_st" = "false" ]; then
+ echo "Policy Agent ${appname} did not respond to service status"
+ exit 1
+ fi
+}
+
+check_policy_agent_logs() {
+
+ appname=$PA_APP_BASE
+ tmp=$(docker ps | grep $appname)
+ if ! [ -z "$tmp" ]; then #Only check logs for running policy agent apps
+ __check_policy_agent_log $appname
+ fi
+
+}
+
+__check_policy_agent_log() {
+ echo "Checking $1 log $POLICY_AGENT_LOGPATH for WARNINGs and ERRORs"
+ foundentries=$(docker exec -it $1 grep WARN /var/log/policy-agent/application.log | wc -l)
+ if [ $? -ne 0 ];then
+ echo " Problem to search $1 log $POLICY_AGENT_LOGPATH"
+ else
+ if [ $foundentries -eq 0 ]; then
+ echo " No WARN entries found in $1 log $POLICY_AGENT_LOGPATH"
+ else
+ echo -e " Found \033[1m"$foundentries"\033[0m WARN entries in $1 log $POLICY_AGENT_LOGPATH"
+ fi
+ fi
+ foundentries=$(docker exec -it $1 grep ERR $POLICY_AGENT_LOGPATH | wc -l)
+ if [ $? -ne 0 ];then
+ echo " Problem to search $1 log $POLICY_AGENT_LOGPATH"
+ else
+ if [ $foundentries -eq 0 ]; then
+ echo " No ERR entries found in $1 log $POLICY_AGENT_LOGPATH"
+ else
+ echo -e " Found \033[1m"$foundentries"\033[0m ERR entries in $1 log $POLICY_AGENT_LOGPATH"
+ fi
+ fi
+}
+
+store_logs() {
+ if [ $# != 1 ]; then
+ __print_err "need one arg, <file-prefix>"
+ exit 1
+ fi
+ echo "Storing all container logs and policy agent app log using prefix: "$1
+
+ docker logs polman_consul > $TESTLOGS/$ATC/$1_consul.log 2>&1
+ docker logs polman_cbs > $TESTLOGS/$ATC/$1_cbs.log 2>&1
+}
+
+__do_curl() {
+ res=$(curl -skw "%{http_code}" $1)
+ http_code="${res:${#res}-3}"
+ if [ ${#res} -eq 3 ]; then
+ echo "<no-response-from-server>"
+ return 1
+ else
+ if [ $http_code -lt 200 ] && [ $http_code -gt 299]; then
+ echo "<not found, resp:${http_code}>"
+ return 1
+ fi
+ if [ $# -eq 2 ]; then
+ echo "${res:0:${#res}-3}" | xargs
+ else
+ echo "${res:0:${#res}-3}"
+ fi
+
+ return 0
+ fi
+}
+
--- /dev/null
+#server = true
+#bootstrap = true
+#client_addr = "0.0.0.0"
+
+service {
+ # Name for CBS in consul, env var CONFIG_BINDING_SERVICE
+ # should be passed to policy agent app with this value
+ Name = "config-binding-service"
+ # Host name where CBS is running
+ Address = "config-binding-service"
+ # Port number where CBS is running
+ Port = 10000
+}
\ No newline at end of file
service {
# Name for CBS in consul, env var CONFIG_BINDING_SERVICE
- # should be passed to dfc app with this value
+ # should be passed to policy agent app with this value
# This is only to be used when contacting cbs via local host
- # (typicall when dfc is executed as an application without a container)
+ # (typicall when policy agent is executed as an application without a container)
Name = "config-binding-service-localhost"
# Host name where CBS is running
Address = "localhost"
ports:
- 8500:8500/tcp
volumes:
- - /Users/yonwu/ORAN/nonrtric/near-rt-ric-simulator/consul_cbs/consul:/consul/config:rw
+ - /Users/yonwu/ORAN/nonrtric/near-rt-ric-simulator/simulator-group/consul_cbs/consul:/consul/config:rw
version: '3.0'
--- /dev/null
+#!/usr/bin/env bash
+
+DOCKER_SIM_NWNAME="nonrtric-docker-net"
+echo "Creating docker network $DOCKER_SIM_NWNAME, if needed"
+docker network ls| grep $DOCKER_SIM_NWNAME > /dev/null || docker network create $DOCKER_SIM_NWNAME
+
+docker-compose -f consul_cbs/docker-compose-template.yml config > docker-compose.yml
+
+docker-compose up -d
\ No newline at end of file
# SPDX-License-Identifier: Apache-2.0
# ============LICENSE_END=========================================================
#
-FROM adoptopenjdk/openjdk11:latest
+FROM openjdk:11-jre-slim
WORKDIR /opt/app/policy-agent
RUN mkdir -p /var/log/policy-agent
RUN mkdir -p /opt/app/policy-agent/etc/cert/
+EXPOSE 8081
ADD /config/application.yaml /opt/app/policy-agent/config/
ADD /target/policy-agent-1.0.0-SNAPSHOT.jar /opt/app/policy-agent/
RUN chmod -R 777 /opt/app/policy-agent/config/
-ENTRYPOINT ["/usr/bin/java", "-jar", "/opt/app/policy-agent/policy-agent-1.0.0-SNAPSHOT.jar"]
+CMD ["java", "-jar", "/opt/app/policy-agent/policy-agent-1.0.0-SNAPSHOT.jar"]
+
+
<project
xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
- xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
+ xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
- <groupId>org.oransc</groupId>
+ <parent>
+ <groupId>org.springframework.boot</groupId>
+ <artifactId>spring-boot-starter-parent</artifactId>
+ <version>2.1.6.RELEASE</version>
+ <relativePath />
+ </parent>
+ <groupId>org.o-ran-sc.nonrtric</groupId>
<artifactId>policy-agent</artifactId>
<version>1.0.0-SNAPSHOT</version>
<licenses>
<url>https://nexus.onap.org/content/repositories/releases/</url>
</repository>
</repositories>
- <parent>
- <groupId>org.springframework.boot</groupId>
- <artifactId>spring-boot-starter-parent</artifactId>
- <version>2.1.6.RELEASE</version>
- <relativePath />
- </parent>
+ <properties>
+ <java.version>11</java.version>
+ <springfox.version>2.8.0</springfox.version>
+ <immutable.version>2.7.1</immutable.version>
+ <sdk.version>1.1.6</sdk.version>
+ <swagger.version>2.0.0</swagger.version>
+ <json.version>20180130</json.version>
+ <awaitility.version>4.0.1</awaitility.version>
+ <maven-compiler-plugin.version>3.8.0</maven-compiler-plugin.version>
+ <formatter-maven-plugin.version>2.8.1</formatter-maven-plugin.version>
+ <spotless-maven-plugin.version>1.18.0</spotless-maven-plugin.version>
+ <docker-maven-plugin>0.30.0</docker-maven-plugin>
+ </properties>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<dependency>
<groupId>io.swagger.core.v3</groupId>
<artifactId>swagger-jaxrs2</artifactId>
- <version>2.0.0</version>
+ <version>${swagger.version}</version>
</dependency>
<dependency>
<groupId>io.swagger.core.v3</groupId>
<artifactId>swagger-jaxrs2-servlet-initializer</artifactId>
- <version>2.0.0</version>
+ <version>${swagger.version}</version>
</dependency>
<dependency>
<groupId>io.springfox</groupId>
<dependency>
<groupId>org.json</groupId>
<artifactId>json</artifactId>
- <version>20180130</version>
+ <version>${json.version}</version>
</dependency>
<!--TEST -->
<dependency>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
+ <dependency>
+ <groupId>org.springframework.boot</groupId>
+ <artifactId>spring-boot-configuration-processor</artifactId>
+ <optional>true</optional>
+ </dependency>
+ <dependency>
+ <groupId>org.onap.dcaegen2.services.sdk.rest.services</groupId>
+ <artifactId>cbs-client</artifactId>
+ <version>${sdk.version}</version>
+ </dependency>
<!--REQUIRED TO GENERATE DOCUMENTATION -->
<dependency>
<groupId>io.springfox</groupId>
<artifactId>springfox-swagger-ui</artifactId>
<version>${springfox.version}</version>
</dependency>
+ <!-- TEST -->
<dependency>
- <groupId>org.onap.dcaegen2.services.sdk.rest.services</groupId>
- <artifactId>cbs-client</artifactId>
- <version>${sdk.version}</version>
+ <groupId>org.awaitility</groupId>
+ <artifactId>awaitility</artifactId>
+ <version>${awaitility.version}</version>
+ <scope>test</scope>
</dependency>
<dependency>
<groupId>io.projectreactor</groupId>
<dependency>
<groupId>org.junit.jupiter</groupId>
<artifactId>junit-jupiter-engine</artifactId>
- <version>${junit-jupiter.version}</version>
+ <scope>test</scope>
+ </dependency>
+ <dependency>
+ <groupId>org.mockito</groupId>
+ <artifactId>mockito-junit-jupiter</artifactId>
+ <scope>test</scope>
+ </dependency>
+ <dependency>
+ <groupId>org.mockito</groupId>
+ <artifactId>mockito-core</artifactId>
<scope>test</scope>
</dependency>
</dependencies>
- <properties>
- <java.version>11</java.version>
- <springfox.version>2.8.0</springfox.version>
- <immutable.version>2.7.1</immutable.version>
- <sdk.version>1.1.6</sdk.version>
- <junit-jupiter.version>5.4.0</junit-jupiter.version>
- </properties>
<build>
<plugins>
<plugin>
<plugin>
<groupId>net.revelc.code.formatter</groupId>
<artifactId>formatter-maven-plugin</artifactId>
- <version>2.8.1</version>
+ <version>${formatter-maven-plugin.version}</version>
<configuration>
<configFile>${project.basedir}/eclipse-formatter.xml</configFile>
</configuration>
- <!-- https://code.revelc.net/formatter-maven-plugin/ use
- mvn formatter:format spotless:apply process-sources -->
+ <!-- https://code.revelc.net/formatter-maven-plugin/ use
+ mvn formatter:format spotless:apply process-sources -->
</plugin>
<plugin>
<groupId>com.diffplug.spotless</groupId>
<artifactId>spotless-maven-plugin</artifactId>
- <version>1.18.0</version>
+ <version>${spotless-maven-plugin.version}</version>
<configuration>
<java>
- <removeUnusedImports/>
+ <removeUnusedImports />
<importOrder>
<order>com,java,javax,org</order>
</importOrder>
</java>
</configuration>
- <!-- https://github.com/diffplug/spotless/tree/master/plugin-maven use
- mvn spotless:apply to rewrite source files use mvn spotless:check to validate
- source files -->
+ <!-- https://github.com/diffplug/spotless/tree/master/plugin-maven
+ use mvn spotless:apply to rewrite source files use mvn spotless:check to
+ validate source files -->
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-surefire-plugin</artifactId>
- <version>2.17</version>
<configuration>
<skipTests>false</skipTests>
</configuration>
</plugin>
<plugin>
- <groupId>com.spotify</groupId>
- <artifactId>dockerfile-maven-plugin</artifactId>
- <configuration>
- <repository>oransc/policy-agent</repository>
- <tag>${project.version}</tag>
- <buildArgs>
- <JAR_FILE>${project.build.finalName}.jar</JAR_FILE>
- </buildArgs>
- </configuration>
+ <artifactId>maven-failsafe-plugin</artifactId>
</plugin>
<plugin>
<groupId>org.codehaus.mojo</groupId>
</execution>
</executions>
</plugin>
+ <plugin>
+ <groupId>io.fabric8</groupId>
+ <artifactId>docker-maven-plugin</artifactId>
+ <version>${docker-maven-plugin}</version>
+ <inherited>false</inherited>
+ <executions>
+ <execution>
+ <id>push-policy-agent-image</id>
+ <goals>
+ <goal>build</goal>
+ <goal>push</goal>
+ </goals>
+ <configuration>
+ <pullRegistry>${env.CONTAINER_PULL_REGISTRY}</pullRegistry>
+ <pushRegistry>${env.CONTAINER_PUSH_REGISTRY}</pushRegistry>
+ <images>
+ <image>
+ <name>o-ran-sc/policy-agent:${project.version}</name>
+ <build>
+ <contextDir>${basedir}</contextDir>
+ <dockerFile>Dockerfile</dockerFile>
+ <tags>
+ <tag>${project.version}</tag>
+ </tags>
+ </build>
+ </image>
+ </images>
+ </configuration>
+ </execution>
+ </executions>
+ </plugin>
</plugins>
</build>
+ <issueManagement>
+ <system>JIRA</system>
+ <url>https://jira.o-ran-sc.org/</url>
+ </issueManagement>
</project>
/**
* Starts the service and reads the configuration.
*
- * @param ctx
- * @return
+ * @param ctx the application context.
+ *
+ * @return the command line runner performing tasks at startup.
*/
@Bean
public CommandLineRunner commandLineRunner(ApplicationContext ctx) {
startupService.startup();
};
}
-
}
package org.oransc.policyagent;
+import org.oransc.policyagent.clients.A1Client;
+import org.oransc.policyagent.clients.A1ClientImpl;
import org.oransc.policyagent.configuration.ApplicationConfig;
import org.oransc.policyagent.repository.Policies;
import org.oransc.policyagent.repository.PolicyTypes;
return new Services();
}
+ @Bean
+ A1Client getA1Client() {
+ return new A1ClientImpl();
+ }
+
}
* limitations under the License.
* ========================LICENSE_END===================================
*/
+
package org.oransc.policyagent.clients;
-import java.lang.invoke.MethodHandles;
-import java.util.ArrayList;
-import java.util.List;
-import org.json.JSONArray;
-import org.json.JSONException;
-import org.json.JSONObject;
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
import reactor.core.publisher.Flux;
import reactor.core.publisher.Mono;
-public class A1Client {
- private static final Logger logger = LoggerFactory.getLogger(MethodHandles.lookup().lookupClass());
-
- public String getBaseUrl(final String nearRtRicUrl) {
- return nearRtRicUrl + "/A1-P/v1";
- }
-
- public Flux<String> getAllPolicyTypes(String nearRtRicUrl) {
- logger.debug("getAllPolicyTypes nearRtRicUrl = {}", nearRtRicUrl);
- AsyncRestClient client = new AsyncRestClient(getBaseUrl(nearRtRicUrl));
- Mono<String> response = client.get("/policytypes");
- return response.flatMapMany(this::createPolicyTypesFlux);
- }
-
- public Flux<String> getPoliciesForType(String nearRtRicUrl, String policyTypeId) {
- logger.debug("getPoliciesForType nearRtRicUrl = {}, policyTypeId = {}", nearRtRicUrl, policyTypeId);
- AsyncRestClient client = new AsyncRestClient(getBaseUrl(nearRtRicUrl));
- Mono<String> response = client.get("/policies");
- return response.flatMapMany(policiesString -> createPoliciesFlux(policiesString, policyTypeId));
- }
+public interface A1Client {
- public Mono<String> getPolicy(String nearRtRicUrl, String policyId) {
- logger.debug("getPolicy nearRtRicUrl = {}, policyId = {}", nearRtRicUrl, policyId);
- AsyncRestClient client = new AsyncRestClient(getBaseUrl(nearRtRicUrl));
- Mono<String> response = client.get("/policies/" + policyId);
- return response.flatMap(this::createPolicyMono);
- }
+ public Flux<String> getPolicyTypeIdentities(String nearRtRicUrl);
- public Mono<String> putPolicy(String nearRtRicUrl, String policyId, String policyString) {
- logger.debug("putPolicy nearRtRicUrl = {}, policyId = {}, policyString = {}", nearRtRicUrl, policyId,
- policyString);
- try {
- new JSONObject(policyString);
- } catch (JSONException ex) { // invalid json
- return Mono.error(ex);
- }
- AsyncRestClient client = new AsyncRestClient(getBaseUrl(nearRtRicUrl));
- Mono<String> response = client.put("/policies/" + policyId, policyString);
- return response.flatMap(this::createPolicyMono);
- }
+ public Flux<String> getPolicyIdentities(String nearRtRicUrl);
- public Mono<Void> deletePolicy(String nearRtRicUrl, String policyId) {
- logger.debug("deletePolicy nearRtRicUrl = {}, policyId = {}", nearRtRicUrl, policyId);
- AsyncRestClient client = new AsyncRestClient(getBaseUrl(nearRtRicUrl));
- return client.delete("/policies/" + policyId);
- }
+ public Mono<String> getPolicyType(String nearRtRicUrl, String policyTypeId);
- private Flux<String> createPolicyTypesFlux(String policyTypesString) {
- try {
- List<String> policyTypesList = new ArrayList<>();
- JSONArray policyTypesArray = new JSONArray(policyTypesString);
- for (int i = 0; i < policyTypesArray.length(); i++) {
- policyTypesList.add(policyTypesArray.getJSONObject(i).toString());
- }
- logger.debug("A1 client: policyTypes = {}", policyTypesList);
- return Flux.fromIterable(policyTypesList);
- } catch (JSONException ex) { // invalid json
- return Flux.error(ex);
- }
- }
+ public Mono<String> putPolicy(String nearRtRicUrl, String policyId, String policyString);
- private Flux<String> createPoliciesFlux(String policiesString, String policyTypeId) {
- try {
- List<String> policiesList = new ArrayList<>();
- JSONArray policiesArray = new JSONArray(policiesString);
- for (int i = 0; i < policiesArray.length(); i++) {
- JSONObject policyObject = policiesArray.getJSONObject(i);
- if (policyObject.get("policyTypeId").equals(policyTypeId)) {
- policiesList.add(policyObject.toString());
- }
- }
- logger.debug("A1 client: policies = {}", policiesList);
- return Flux.fromIterable(policiesList);
- } catch (JSONException ex) { // invalid json
- return Flux.error(ex);
- }
- }
+ public Mono<Void> deletePolicy(String nearRtRicUrl, String policyId);
- private Mono<String> createPolicyMono(String policyString) {
- try {
- JSONObject policyObject = new JSONObject(policyString);
- String policy = policyObject.toString();
- logger.debug("A1 client: policy = {}", policy);
- return Mono.just(policy);
- } catch (JSONException ex) { // invalid json
- return Mono.error(ex);
- }
- }
}
--- /dev/null
+/*-
+ * ========================LICENSE_START=================================
+ * O-RAN-SC
+ * %%
+ * Copyright (C) 2019 Nordix Foundation
+ * %%
+ * 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.oransc.policyagent.clients;
+
+import java.lang.invoke.MethodHandles;
+import java.util.ArrayList;
+import java.util.List;
+
+import org.json.JSONArray;
+import org.json.JSONException;
+import org.json.JSONObject;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import reactor.core.publisher.Flux;
+import reactor.core.publisher.Mono;
+
+public class A1ClientImpl implements A1Client {
+ private static final Logger logger = LoggerFactory.getLogger(MethodHandles.lookup().lookupClass());
+
+ private static String getBaseUrl(final String nearRtRicUrl) {
+ return nearRtRicUrl + "/A1-P/v1";
+ }
+
+ @Override
+ public Flux<String> getPolicyTypeIdentities(String nearRtRicUrl) {
+ logger.debug("getPolicyTypeIdentities nearRtRicUrl = {}", nearRtRicUrl);
+ AsyncRestClient client = new AsyncRestClient(getBaseUrl(nearRtRicUrl));
+ Mono<String> response = client.get("/policytypes/identities");
+ return response.flatMapMany(this::createFlux);
+ }
+
+ @Override
+ public Flux<String> getPolicyIdentities(String nearRtRicUrl) {
+ logger.debug("getPolicyIdentities nearRtRicUrl = {}", nearRtRicUrl);
+ AsyncRestClient client = new AsyncRestClient(getBaseUrl(nearRtRicUrl));
+ Mono<String> response = client.get("/policies/identities");
+ return response.flatMapMany(this::createFlux);
+ }
+
+ @Override
+ public Mono<String> getPolicyType(String nearRtRicUrl, String policyTypeId) {
+ logger.debug("getPolicyType nearRtRicUrl = {}, policyTypeId = {}", nearRtRicUrl, policyTypeId);
+ AsyncRestClient client = new AsyncRestClient(getBaseUrl(nearRtRicUrl));
+ Mono<String> response = client.get("/policytypes/" + policyTypeId);
+ return response.flatMap(this::createMono);
+ }
+
+ @Override
+ public Mono<String> putPolicy(String nearRtRicUrl, String policyId, String policyString) {
+ logger.debug("putPolicy nearRtRicUrl = {}, policyId = {}, policyString = {}", nearRtRicUrl, policyId,
+ policyString);
+ AsyncRestClient client = new AsyncRestClient(getBaseUrl(nearRtRicUrl));
+ Mono<String> response = client.put("/policies/" + policyId, policyString);
+ return response.flatMap(this::createMono);
+ }
+
+ @Override
+ public Mono<Void> deletePolicy(String nearRtRicUrl, String policyId) {
+ logger.debug("deletePolicy nearRtRicUrl = {}, policyId = {}", nearRtRicUrl, policyId);
+ AsyncRestClient client = new AsyncRestClient(getBaseUrl(nearRtRicUrl));
+ return client.delete("/policies/" + policyId);
+ }
+
+ private Flux<String> createFlux(String inputString) {
+ try {
+ List<String> arrayList = new ArrayList<>();
+ JSONArray jsonArray = new JSONArray(inputString);
+ for (int i = 0; i < jsonArray.length(); i++) {
+ arrayList.add(jsonArray.getString(i));
+ }
+ logger.debug("A1 client: received list = {}", arrayList);
+ return Flux.fromIterable(arrayList);
+ } catch (JSONException ex) { // invalid json
+ return Flux.error(ex);
+ }
+ }
+
+ private Mono<String> createMono(String inputString) {
+ try {
+ JSONObject jsonObject = new JSONObject(inputString);
+ String jsonString = jsonObject.toString();
+ logger.debug("A1 client: received string = {}", jsonString);
+ return Mono.just(jsonString);
+ } catch (JSONException ex) { // invalid json
+ return Mono.error(ex);
+ }
+ }
+}
*/
package org.oransc.policyagent.clients;
-import org.oransc.policyagent.exceptions.AsyncRestClientException;
import org.springframework.http.HttpStatus;
import org.springframework.http.MediaType;
import org.springframework.web.reactive.function.client.WebClient;
public class AsyncRestClient {
private final WebClient client;
+ private static class AsyncRestClientException extends Exception {
+
+ private static final long serialVersionUID = 1L;
+
+ public AsyncRestClientException(String message) {
+ super(message);
+ }
+ }
+
public AsyncRestClient(String baseUrl) {
this.client = WebClient.create(baseUrl);
}
+++ /dev/null
-/*-
- * ========================LICENSE_START=================================
- * O-RAN-SC
- * %%
- * Copyright (C) 2019 Nordix Foundation
- * %%
- * 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.oransc.policyagent.clients;
-
-import java.util.Vector;
-
-import org.oransc.policyagent.repository.PolicyType;
-import org.springframework.stereotype.Service;
-
-@Service
-public class RicClient {
-
- public void deleteAllPolicies(String url) {
- // TODO Auto-generated method stub
-
- }
-
- public Vector<PolicyType> getPolicyTypes(String url) {
- return new Vector<>();
- }
-
-}
InputStream createInputStream(@NotNull String filepath) throws IOException {
return new BufferedInputStream(new FileInputStream(filepath));
}
-
}
* limitations under the License.
* ========================LICENSE_END===================================
*/
+
package org.oransc.policyagent.controllers;
import com.google.gson.Gson;
Vector<PolicyTypeInfo> v = new Vector<>(types.size());
for (PolicyType t : types) {
PolicyTypeInfo policyInfo = ImmutablePolicyTypeInfo.builder() //
- .schema(t.jsonSchema()) //
.name(t.name()) //
.build();
v.add(policyInfo);
* limitations under the License.
* ========================LICENSE_END===================================
*/
-package org.oransc.policyagent.controllers;
+package org.oransc.policyagent.controllers;
import org.immutables.gson.Gson;
import org.immutables.value.Value;
* limitations under the License.
* ========================LICENSE_END===================================
*/
-package org.oransc.policyagent.controllers;
+package org.oransc.policyagent.controllers;
import org.immutables.gson.Gson;
import org.immutables.value.Value;
public interface PolicyTypeInfo {
public String name();
-
- public String schema();
}
* limitations under the License.
* ========================LICENSE_END===================================
*/
-package org.oransc.policyagent.controllers;
+package org.oransc.policyagent.controllers;
-import java.util.Vector;
+import java.util.Collection;
import org.immutables.gson.Gson;
import org.immutables.value.Value;
public String name();
- public Vector<String> nodeNames();
+ public Collection<String> nodeNames();
+
+ public Collection<String> policyTypes();
}
value = { //
@ApiResponse(code = 200, message = "OK") //
})
- public ResponseEntity<String> getRics() {
+ public ResponseEntity<String> getRics(
+ @RequestParam(name = "policyType", required = false) String supportingPolicyType) {
Vector<RicInfo> result = new Vector<>();
for (Ric ric : rics.getRics()) {
- result.add(ImmutableRicInfo.builder() //
- .name(ric.name()) //
- .nodeNames(ric.getManagedNodes()) //
- .build());
+ if (supportingPolicyType == null || ric.isSupportingType(supportingPolicyType)) {
+ result.add(ImmutableRicInfo.builder() //
+ .name(ric.name()) //
+ .nodeNames(ric.getManagedNodes()) //
+ .policyTypes(ric.getSupportedPolicyTypeNames()) //
+ .build());
+ }
}
return new ResponseEntity<>(gson.toJson(result), HttpStatus.OK);
* limitations under the License.
* ========================LICENSE_END===================================
*/
+
package org.oransc.policyagent.controllers;
import com.google.gson.Gson;
* limitations under the License.
* ========================LICENSE_END===================================
*/
-package org.oransc.policyagent.controllers;
+package org.oransc.policyagent.controllers;
import org.immutables.gson.Gson;
import org.immutables.value.Value;
* limitations under the License.
* ========================LICENSE_END===================================
*/
+
package org.oransc.policyagent.controllers;
import com.google.gson.annotations.SerializedName;
* limitations under the License.
* ========================LICENSE_END===================================
*/
+
package org.oransc.policyagent.controllers;
import io.swagger.annotations.ApiOperation;
+++ /dev/null
-/*-
- * ========================LICENSE_START=================================
- * O-RAN-SC
- * %%
- * Copyright (C) 2019 Nordix Foundation
- * %%
- * 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.oransc.policyagent.exceptions;
-
-public class AsyncRestClientException extends Exception {
-
- private static final long serialVersionUID = 1L;
-
- public AsyncRestClientException(String message) {
- super(message);
- }
-}
import java.util.Vector;
import org.oransc.policyagent.exceptions.ServiceException;
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
public class Policies {
- private static final Logger logger = LoggerFactory.getLogger(Policies.class);
-
private Map<String, Policy> policiesId = new HashMap<>();
private Map<String, Map<String, Policy>> policiesRic = new HashMap<>();
private Map<String, Map<String, Policy>> policiesService = new HashMap<>();
* limitations under the License.
* ========================LICENSE_END===================================
*/
+
package org.oransc.policyagent.repository;
import org.immutables.gson.Gson;
@Gson.TypeAdapters
public interface PolicyType {
public String name();
-
- public String jsonSchema();
-
}
types.put(type.name(), type);
}
- public boolean contains(PolicyType policyType) {
- return types.containsKey(policyType.name());
+ public boolean contains(String policyType) {
+ return types.containsKey(policyType);
}
public synchronized Collection<PolicyType> getAll() {
package org.oransc.policyagent.repository;
-import java.util.Collections;
-import java.util.List;
+import java.util.Collection;
+import java.util.HashMap;
+import java.util.Map;
import java.util.Vector;
import org.oransc.policyagent.configuration.RicConfig;
-import org.oransc.policyagent.repository.Ric.RicState;
/**
* Represents the dynamic information about a NearRealtime-RIC.
public class Ric {
private final RicConfig ricConfig;
private RicState state = RicState.NOT_INITIATED;
- private Vector<PolicyType> supportedPolicyTypes = new Vector<>();
+ private Map<String, PolicyType> supportedPolicyTypes = new HashMap<>();
/**
* Creates the Ric. Initial state is {@link RicState.NOT_INITIATED}.
state = newState;
}
+ public RicConfig getConfig() {
+ return this.ricConfig;
+ }
+
/**
* Gets the nodes managed by this Ric.
*
*
* @return the policy types supported by this Ric in an unmodifiable list.
*/
- public List<PolicyType> getSupportedPolicyTypes() {
- return Collections.unmodifiableList(supportedPolicyTypes);
+ public Collection<PolicyType> getSupportedPolicyTypes() {
+ return supportedPolicyTypes.values();
+ }
+
+ public Collection<String> getSupportedPolicyTypeNames() {
+ return supportedPolicyTypes.keySet();
}
/**
* @param type the policy type to support.
*/
public void addSupportedPolicyType(PolicyType type) {
- if (!supportedPolicyTypes.contains(type)) {
- supportedPolicyTypes.add(type);
- }
+ supportedPolicyTypes.put(type.name(), type);
}
/**
*
* @param types the policy types to support.
*/
- public void addSupportedPolicyTypes(Vector<PolicyType> types) {
+ public void addSupportedPolicyTypes(Collection<PolicyType> types) {
for (PolicyType type : types) {
addSupportedPolicyType(type);
}
* @param type the policy type to remove as supported by this Ric.
*/
public void removeSupportedPolicyType(PolicyType type) {
- supportedPolicyTypes.remove(type);
+ supportedPolicyTypes.remove(type.name());
}
/**
* Checks if a type is supported by this Ric.
*
- * @param type the type to check if it is supported.
+ * @param typeName the name of the type to check if it is supported.
*
- * @return true if the given type issupported by this Ric, false otherwise.
+ * @return true if the given type is supported by this Ric, false otherwise.
*/
- public boolean isSupportingType(PolicyType type) {
- return supportedPolicyTypes.contains(type);
+ public boolean isSupportingType(String typeName) {
+ return supportedPolicyTypes.containsKey(typeName);
}
/**
/**
* The Ric is working fine.
*/
- ACTIVE,
- /**
- * Something is wrong with the Ric.
- */
- FAULTY,
- /**
- * The node is unreachable at the moment.
- */
- UNREACHABLE
+ ACTIVE
}
}
* limitations under the License.
* ========================LICENSE_END===================================
*/
+
package org.oransc.policyagent.repository;
import java.time.Duration;
package org.oransc.policyagent.tasks;
+import org.oransc.policyagent.clients.A1Client;
import org.oransc.policyagent.repository.Policies;
import org.oransc.policyagent.repository.Policy;
import org.oransc.policyagent.repository.Service;
import org.springframework.scheduling.annotation.EnableScheduling;
import org.springframework.scheduling.annotation.Scheduled;
import org.springframework.stereotype.Component;
+
import reactor.core.publisher.Flux;
+import reactor.core.publisher.Mono;
@Component
@EnableScheduling
private static final Logger logger = LoggerFactory.getLogger(ServiceSupervision.class);
private final Services services;
private final Policies policies;
+ private A1Client a1Client;
@Autowired
- public ServiceSupervision(Services services, Policies policies) {
+ public ServiceSupervision(Services services, Policies policies, A1Client a1Client) {
this.services = services;
this.policies = policies;
+ this.a1Client = a1Client;
}
@Scheduled(fixedRate = 1000 * 60)
logger.debug("Checking services completed");
}
- Flux<Policy> createTask() {
+ private Flux<Policy> createTask() {
return Flux.fromIterable(services.getAll()) //
.filter(service -> service.isExpired()) //
.doOnNext(service -> logger.info("Service is expired:" + service.getName()))
.flatMap(service -> getAllPolicies(service)) //
- .doOnNext(policy -> this.policies.remove(policy));
+ .doOnNext(policy -> this.policies.remove(policy)) //
+ .flatMap(policy -> deletePolicyInRic(policy));
}
- Flux<Policy> getAllPolicies(Service service) {
+ private Flux<Policy> getAllPolicies(Service service) {
return Flux.fromIterable(policies.getForService(service.getName()));
}
+ private Mono<Policy> deletePolicyInRic(Policy policy) {
+ return a1Client.deletePolicy(policy.ric().getConfig().baseUrl(), policy.id()) //
+ .onErrorResume(exception -> handleDeleteFromRicFailure(policy, exception)) //
+ .map((nothing) -> policy);
+ }
+
+ private Mono<Void> handleDeleteFromRicFailure(Policy policy, Throwable e) {
+ logger.warn("Could not delete policy: {} from ric: {}", policy.id(), policy.ric().name(), e);
+ return Mono.empty();
+ }
}
package org.oransc.policyagent.tasks;
-import java.util.Vector;
-
-import org.oransc.policyagent.clients.RicClient;
+import org.oransc.policyagent.clients.A1Client;
import org.oransc.policyagent.configuration.ApplicationConfig;
-import org.oransc.policyagent.configuration.RicConfig;
+import org.oransc.policyagent.repository.ImmutablePolicyType;
import org.oransc.policyagent.repository.PolicyType;
import org.oransc.policyagent.repository.PolicyTypes;
import org.oransc.policyagent.repository.Ric;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
+import reactor.core.publisher.Flux;
+import reactor.core.publisher.Mono;
+
/**
* Loads information about RealTime-RICs at startup.
*/
PolicyTypes policyTypes;
@Autowired
- private RicClient ricClient;
+ private A1Client a1Client;
- StartupService(ApplicationConfig appConfig, Rics rics, PolicyTypes policyTypes, RicClient ricClient) {
+ StartupService(ApplicationConfig appConfig, Rics rics, PolicyTypes policyTypes, A1Client a1Client) {
this.applicationConfig = appConfig;
this.rics = rics;
this.policyTypes = policyTypes;
- this.ricClient = ricClient;
+ this.a1Client = a1Client;
}
/**
*/
public void startup() {
applicationConfig.initialize();
- Vector<RicConfig> ricConfigs = applicationConfig.getRicConfigs();
- for (RicConfig ricConfig : ricConfigs) {
- Ric ric = new Ric(ricConfig);
- String baseUrl = ricConfig.baseUrl();
- ricClient.deleteAllPolicies(baseUrl);
- Vector<PolicyType> types = ricClient.getPolicyTypes(baseUrl);
- for (PolicyType policyType : types) {
- if (!policyTypes.contains(policyType)) {
- policyTypes.put(policyType);
- }
- }
- ric.addSupportedPolicyTypes(types);
- ric.setState(RicState.ACTIVE);
- rics.put(ric);
+ Flux.fromIterable(applicationConfig.getRicConfigs()) //
+ .map(ricConfig -> new Ric(ricConfig)) //
+ .doOnNext(ric -> logger.debug("Handling ric: {}", ric.getConfig().name())) //
+ .flatMap(this::addPolicyTypesForRic)
+ .flatMap(this::deletePoliciesForRic) //
+ .flatMap(this::setRicToActive) //
+ .flatMap(this::addRicToRepo) //
+ .subscribe();
+ }
+
+ private Mono<Ric> addPolicyTypesForRic(Ric ric) {
+ a1Client.getPolicyTypeIdentities(ric.getConfig().baseUrl()) //
+ .doOnNext(typeId -> logger.debug("For ric: {}, handling type: {}", ric.getConfig().name(), typeId))
+ .flatMap(this::addTypeToRepo) //
+ .flatMap(type -> addTypeToRic(ric, type)) //
+ .subscribe();
+ return Mono.just(ric);
+ }
+
+ private Mono<PolicyType> addTypeToRepo(String policyTypeId) {
+ ImmutablePolicyType type = ImmutablePolicyType.builder().name(policyTypeId).build();
+ if (!policyTypes.contains(policyTypeId)) {
+ policyTypes.put(type);
}
+ return Mono.just(type);
+ }
+ private Mono<Void> addTypeToRic(Ric ric, PolicyType policyType) {
+ ric.addSupportedPolicyType(policyType);
+ return Mono.empty();
}
+ private Mono<Ric> deletePoliciesForRic(Ric ric) {
+ a1Client.getPolicyIdentities(ric.getConfig().baseUrl()) //
+ .doOnNext(policyId -> logger.debug("deleting policy: {}, for ric: {}", policyId, ric.getConfig().name())) //
+ .flatMap(policyId -> a1Client.deletePolicy(ric.getConfig().baseUrl(), policyId)) //
+ .subscribe();
+
+ return Mono.just(ric);
+ }
+
+ private Mono<Ric> setRicToActive(Ric ric) {
+ ric.setState(RicState.ACTIVE);
+
+ return Mono.just(ric);
+ }
+
+ private Mono<Void> addRicToRepo(Ric ric) {
+ rics.put(ric);
+
+ return Mono.empty();
+ }
}
* limitations under the License.
* ========================LICENSE_END===================================
*/
+
package org.oransc.policyagent;
import static org.assertj.core.api.Assertions.assertThat;
-import static org.junit.Assert.assertFalse;
+import static org.junit.jupiter.api.Assertions.assertFalse;
import com.google.gson.Gson;
import com.google.gson.GsonBuilder;
import java.util.List;
import java.util.Vector;
-import org.junit.Test;
-import org.junit.jupiter.api.BeforeEach;
-import org.junit.runner.RunWith;
+import org.junit.jupiter.api.Test;
+import org.junit.jupiter.api.extension.ExtendWith;
import org.oransc.policyagent.configuration.ApplicationConfig;
import org.oransc.policyagent.configuration.ImmutableRicConfig;
import org.oransc.policyagent.configuration.RicConfig;
import org.springframework.boot.test.context.SpringBootTest.WebEnvironment;
import org.springframework.boot.test.context.TestConfiguration;
import org.springframework.boot.web.server.LocalServerPort;
+import org.springframework.context.ApplicationContext;
import org.springframework.context.annotation.Bean;
import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;
-import org.springframework.test.context.junit4.SpringRunner;
+import org.springframework.test.context.junit.jupiter.SpringExtension;
import org.springframework.web.client.RestTemplate;
-@RunWith(SpringRunner.class)
+@ExtendWith(SpringExtension.class)
@SpringBootTest(webEnvironment = WebEnvironment.RANDOM_PORT)
public class ApplicationTest {
+ @Autowired
+ ApplicationContext context;
@Autowired
private Rics rics;
}
/**
- * overrides the BeanFactory
+ * Overrides the BeanFactory.
*/
@TestConfiguration
static class TestBeanFactory {
public ApplicationConfig getApplicationConfig() {
return new MockApplicationConfig();
}
+
+ @Bean
+ public Rics getRics() {
+ Rics rics = new Rics();
+ rics.put(new Ric(ImmutableRicConfig.builder().name("kista_1").baseUrl("kista_url")
+ .managedElementIds(new Vector<>()).build()));
+ rics.put(new Ric(ImmutableRicConfig.builder().name("ric1").baseUrl("ric_url")
+ .managedElementIds(new Vector<>()).build()));
+ return rics;
+ }
}
@LocalServerPort
private final RestTemplate restTemplate = new RestTemplate();
- @BeforeEach
- public void reset() {
+ private void reset() {
rics.clear();
policies.clear();
policyTypes.clear();
public void testGetRics() throws Exception {
String url = baseUrl() + "/rics";
String rsp = this.restTemplate.getForObject(url, String.class);
+ System.out.println(rsp);
assertThat(rsp).contains("kista_1");
+
+ url = baseUrl() + "/rics?policyType=ANR";
+ rsp = this.restTemplate.getForObject(url, String.class);
+ // TODO this should test that the correct types are retrieved from the RIC
+ assertThat(rsp).isEqualTo("[]");
}
@Test
private PolicyType addPolicyType(String name) {
PolicyType type = ImmutablePolicyType.builder() //
- .jsonSchema("") //
.name(name) //
.build();
assertThat(policies.size()).isEqualTo(0);
}
- public static <T> List<T> parseList(String json, Class<T> clazz) {
+ private static <T> List<T> parseList(String json, Class<T> clazz) {
if (null == json) {
return null;
}
@Test
public void testGetPolicyTypes() throws Exception {
- String url = baseUrl() + "/policy_types";
reset();
addPolicy("id1", "type1", "service1");
addPolicy("id2", "type2", "service2");
+ String url = baseUrl() + "/policy_types";
String rsp = this.restTemplate.getForObject(url, String.class);
System.out.println(rsp);
assertThat(rsp).contains("type1");
* limitations under the License.
* ========================LICENSE_END===================================
*/
+
package org.oransc.policyagent;
import com.google.gson.JsonObject;
import java.io.IOException;
import java.net.URL;
import java.nio.file.Files;
+import java.util.Vector;
import org.junit.Test;
import org.junit.runner.RunWith;
+import org.oransc.policyagent.clients.A1Client;
import org.oransc.policyagent.configuration.ApplicationConfig;
import org.oransc.policyagent.repository.ImmutablePolicyType;
import org.oransc.policyagent.repository.Policies;
+import org.oransc.policyagent.repository.Policy;
import org.oransc.policyagent.repository.PolicyType;
import org.oransc.policyagent.repository.PolicyTypes;
import org.oransc.policyagent.repository.Rics;
import org.springframework.context.annotation.Bean;
import org.springframework.test.context.junit4.SpringRunner;
+import reactor.core.publisher.Flux;
+import reactor.core.publisher.Mono;
+
@RunWith(SpringRunner.class)
@SpringBootTest(webEnvironment = WebEnvironment.DEFINED_PORT)
public class MockPolicyAgent {
}
}
+ static class A1ClientMock implements A1Client {
+ private final Policies policies;
+ private final PolicyTypes policyTypes;
+
+ A1ClientMock(Policies policies, PolicyTypes policyTypes) {
+ this.policies = policies;
+ this.policyTypes = policyTypes;
+ }
+
+ @Override
+ public Flux<String> getPolicyTypeIdentities(String nearRtRicUrl) {
+ Vector<String> result = new Vector<>();
+ for (PolicyType p : this.policyTypes.getAll()) {
+ result.add(p.name());
+ }
+ return Flux.fromIterable(result);
+ }
+
+ @Override
+ public Flux<String> getPolicyIdentities(String nearRtRicUrl) {
+ Vector<String> result = new Vector<>();
+ for (Policy p : this.policies.getAll()) {
+ result.add(p.id());
+ }
+ return Flux.fromIterable(result);
+ }
+
+ @Override
+ public Mono<String> getPolicyType(String nearRtRicUrl, String policyTypeId) {
+ try {
+ return Mono.just(this.policyTypes.getType(policyTypeId).toString());
+ } catch (Exception e) {
+ return Mono.error(e);
+ }
+ }
+
+ @Override
+ public Mono<String> putPolicy(String nearRtRicUrl, String policyId, String policyString) {
+ return Mono.just("OK");
+ }
+
+ @Override
+ public Mono<Void> deletePolicy(String nearRtRicUrl, String policyId) {
+ return Mono.error(new Exception("TODO We cannot use Void like this")); // TODO We cannot use Void like this
+ }
+
+ }
+
/**
* overrides the BeanFactory
*/
@TestConfiguration
static class TestBeanFactory {
+ private final Rics rics = new Rics();
+ private final Policies policies = new Policies();
+ private final PolicyTypes policyTypes = new PolicyTypes();
+
@Bean
public ApplicationConfig getApplicationConfig() {
return new MockApplicationConfig();
}
+
+ @Bean
+ A1Client getA1Client() {
+ return new A1ClientMock(this.policies, this.policyTypes);
+ }
+
+ @Bean
+ public Policies getPolicies() {
+ return this.policies;
+ }
+
+ @Bean
+ public PolicyTypes getPolicyTypes() {
+ return this.policyTypes;
+ }
+
+ @Bean
+ public Rics getRics() {
+ return this.rics;
+ }
+
}
@LocalServerPort
try {
String schema = readFile(file);
String typeName = title(schema);
- PolicyType type = ImmutablePolicyType.builder().name(typeName).jsonSchema(schema).build();
+ PolicyType type = ImmutablePolicyType.builder().name(typeName).build();
policyTypes.put(type);
} catch (Exception e) {
System.out.println("Could not load json schema " + e);
package org.oransc.policyagent.configuration;
import static org.assertj.core.api.Assertions.assertThat;
-import static org.junit.Assert.assertTrue;
+import static org.junit.jupiter.api.Assertions.assertTrue;
import static org.mockito.ArgumentMatchers.any;
import static org.mockito.Mockito.doReturn;
-import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.spy;
import static org.mockito.Mockito.times;
import static org.mockito.Mockito.verify;
import org.junit.jupiter.api.Assertions;
import org.junit.jupiter.api.Test;
+import org.junit.jupiter.api.extension.ExtendWith;
+import org.junit.runner.RunWith;
+import org.mockito.Mock;
+import org.mockito.junit.MockitoJUnitRunner;
+import org.mockito.junit.jupiter.MockitoExtension;
import org.onap.dcaegen2.services.sdk.rest.services.cbs.client.api.CbsClient;
import org.onap.dcaegen2.services.sdk.rest.services.cbs.client.model.EnvProperties;
import org.onap.dcaegen2.services.sdk.rest.services.cbs.client.model.ImmutableEnvProperties;
import reactor.core.publisher.Mono;
import reactor.test.StepVerifier;
+@ExtendWith(MockitoExtension.class)
+@RunWith(MockitoJUnitRunner.class)
public class ApplicationConfigTest {
private ApplicationConfig appConfigUnderTest;
- CbsClient cbsClient = mock(CbsClient.class);
+
+ @Mock
+ CbsClient cbsClient;
public static final ImmutableRicConfig CORRECT_RIC_CONIFG = ImmutableRicConfig.builder() //
.name("ric1") //
package org.oransc.policyagent.tasks;
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertNotNull;
-import static org.junit.Assert.assertTrue;
-import static org.mockito.Mockito.mock;
+import static org.assertj.core.api.Assertions.assertThat;
+import static org.awaitility.Awaitility.await;
+import static org.junit.jupiter.api.Assertions.assertEquals;
+import static org.junit.jupiter.api.Assertions.assertNotNull;
+import static org.junit.jupiter.api.Assertions.assertTrue;
+import static org.mockito.ArgumentMatchers.anyString;
import static org.mockito.Mockito.verify;
-import static org.mockito.Mockito.verifyNoMoreInteractions;
import static org.mockito.Mockito.when;
import static org.oransc.policyagent.repository.Ric.RicState.ACTIVE;
import java.util.Vector;
import org.junit.jupiter.api.Test;
-import org.oransc.policyagent.clients.RicClient;
+import org.junit.jupiter.api.extension.ExtendWith;
+import org.junit.runner.RunWith;
+import org.mockito.Mock;
+import org.mockito.junit.MockitoJUnitRunner;
+import org.mockito.junit.jupiter.MockitoExtension;
+import org.oransc.policyagent.clients.A1Client;
import org.oransc.policyagent.configuration.ApplicationConfig;
import org.oransc.policyagent.configuration.ImmutableRicConfig;
import org.oransc.policyagent.configuration.RicConfig;
import org.oransc.policyagent.repository.Ric;
import org.oransc.policyagent.repository.Rics;
+import reactor.core.publisher.Flux;
+import reactor.core.publisher.Mono;
+
+@ExtendWith(MockitoExtension.class)
+@RunWith(MockitoJUnitRunner.class)
public class StartupServiceTest {
private static final String FIRST_RIC_NAME = "first";
private static final String FIRST_RIC_URL = "firstUrl";
private static final String MANAGED_NODE_C = "nodeC";
private static final String POLICY_TYPE_1_NAME = "type1";
+ private static final PolicyType POLICY_TYPE_1 = ImmutablePolicyType.builder().name(POLICY_TYPE_1_NAME).build();
private static final String POLICY_TYPE_2_NAME = "type2";
+ private static final PolicyType POLICY_TYPE_2 = ImmutablePolicyType.builder().name(POLICY_TYPE_2_NAME).build();
+ private static final String POLICY_ID_1 = "policy1";
+ private static final String POLICY_ID_2 = "policy2";
+ @Mock
ApplicationConfig appConfigMock;
+ @Mock
+ A1Client a1ClientMock;
+
@Test
public void startup_allOk() throws ServiceException {
- ApplicationConfig appConfigMock = mock(ApplicationConfig.class);
Vector<RicConfig> ricConfigs = new Vector<>(2);
ricConfigs.add(getRicConfig(FIRST_RIC_NAME, FIRST_RIC_URL, MANAGED_NODE_A));
ricConfigs.add(getRicConfig(SECOND_RIC_NAME, SECOND_RIC_URL, MANAGED_NODE_B, MANAGED_NODE_C));
when(appConfigMock.getRicConfigs()).thenReturn(ricConfigs);
- Vector<PolicyType> firstTypes = new Vector<>();
- PolicyType type1 = ImmutablePolicyType.builder().name(POLICY_TYPE_1_NAME).jsonSchema("{}").build();
- firstTypes.add(type1);
- Vector<PolicyType> secondTypes = new Vector<>();
- secondTypes.add(type1);
- PolicyType type2 = ImmutablePolicyType.builder().name(POLICY_TYPE_2_NAME).jsonSchema("{}").build();
- secondTypes.add(type2);
- RicClient ricClientMock = mock(RicClient.class);
- when(ricClientMock.getPolicyTypes(FIRST_RIC_URL)).thenReturn(firstTypes);
- when(ricClientMock.getPolicyTypes("secondUrl")).thenReturn(secondTypes);
+ Flux<String> fluxType1 = Flux.just(POLICY_TYPE_1_NAME);
+ Flux<String> fluxType2 = Flux.just(POLICY_TYPE_2_NAME);
+ when(a1ClientMock.getPolicyTypeIdentities(anyString())).thenReturn(fluxType1)
+ .thenReturn(fluxType1.concatWith(fluxType2));
+ Flux<String> policies = Flux.just(new String[] {POLICY_ID_1, POLICY_ID_2});
+ when(a1ClientMock.getPolicyIdentities(anyString())).thenReturn(policies);
+ when(a1ClientMock.deletePolicy(anyString(), anyString())).thenReturn(Mono.empty());
Rics rics = new Rics();
PolicyTypes policyTypes = new PolicyTypes();
- StartupService serviceUnderTest = new StartupService(appConfigMock, rics, policyTypes, ricClientMock);
+ StartupService serviceUnderTest = new StartupService(appConfigMock, rics, policyTypes, a1ClientMock);
serviceUnderTest.startup();
- verify(ricClientMock).deleteAllPolicies(FIRST_RIC_URL);
- verify(ricClientMock).getPolicyTypes(FIRST_RIC_URL);
- verify(ricClientMock).deleteAllPolicies(SECOND_RIC_URL);
- verify(ricClientMock).getPolicyTypes(SECOND_RIC_URL);
- verifyNoMoreInteractions(ricClientMock);
+ await().untilAsserted(() -> assertThat(policyTypes.size()).isEqualTo(2));
+
+ verify(a1ClientMock).getPolicyTypeIdentities(FIRST_RIC_URL);
+ verify(a1ClientMock).deletePolicy(FIRST_RIC_URL, POLICY_ID_1);
+ verify(a1ClientMock).deletePolicy(FIRST_RIC_URL, POLICY_ID_2);
+
+ verify(a1ClientMock).getPolicyTypeIdentities(SECOND_RIC_URL);
+ verify(a1ClientMock).deletePolicy(SECOND_RIC_URL, POLICY_ID_1);
+ verify(a1ClientMock).deletePolicy(SECOND_RIC_URL, POLICY_ID_2);
- assertEquals("Not correct number of policy types added.", 2, policyTypes.size());
- assertEquals("Not correct type added.", type1, policyTypes.getType(POLICY_TYPE_1_NAME));
- assertEquals("Not correct type added.", type2, policyTypes.getType(POLICY_TYPE_2_NAME));
- assertEquals("Correct nymber of Rics not added to Rics", 2, rics.size());
+ assertTrue(policyTypes.contains(POLICY_TYPE_1_NAME), POLICY_TYPE_1_NAME + " not added to PolicyTypes.");
+ assertTrue(policyTypes.contains(POLICY_TYPE_2_NAME), POLICY_TYPE_2_NAME + " not added to PolicyTypes.");
+ assertEquals(2, rics.size(), "Correct number of Rics not added to Rics");
Ric firstRic = rics.getRic(FIRST_RIC_NAME);
- assertNotNull("Ric \"" + FIRST_RIC_NAME + "\" not added to repositpry", firstRic);
- assertEquals("Not correct Ric \"" + FIRST_RIC_NAME + "\" added to Rics", FIRST_RIC_NAME, firstRic.name());
- assertEquals("Not correct state for \"" + FIRST_RIC_NAME + "\"", ACTIVE, firstRic.state());
- assertEquals("Not correct no of types supported", 1, firstRic.getSupportedPolicyTypes().size());
- assertTrue("Not correct type supported", firstRic.isSupportingType(type1));
- assertEquals("Not correct no of managed nodes", 1, firstRic.getManagedNodes().size());
- assertTrue("Not managed by node", firstRic.isManaging(MANAGED_NODE_A));
+ assertNotNull(firstRic, "Ric \"" + FIRST_RIC_NAME + "\" not added to repositpry");
+ assertEquals(FIRST_RIC_NAME, firstRic.name(), "Not correct Ric \"" + FIRST_RIC_NAME + "\" added to Rics");
+ assertEquals(ACTIVE, firstRic.state(), "Not correct state for \"" + FIRST_RIC_NAME + "\"");
+ assertEquals(1, firstRic.getSupportedPolicyTypes().size(), "Not correct no of types supported");
+ assertTrue(firstRic.isSupportingType(POLICY_TYPE_1_NAME), "Not correct type supported");
+ assertEquals(1, firstRic.getManagedNodes().size(), "Not correct no of managed nodes");
+ assertTrue(firstRic.isManaging(MANAGED_NODE_A), "Not managed by node");
Ric secondRic = rics.getRic(SECOND_RIC_NAME);
- assertNotNull("Ric \"" + SECOND_RIC_NAME + "\" not added to repositpry", secondRic);
- assertEquals("Not correct Ric \"" + SECOND_RIC_NAME + "\" added to Rics", SECOND_RIC_NAME, secondRic.name());
- assertEquals("Not correct state for \"" + SECOND_RIC_NAME + "\"", ACTIVE, secondRic.state());
- assertEquals("Not correct no of types supported", 2, secondRic.getSupportedPolicyTypes().size());
- assertTrue("Not correct type supported", secondRic.isSupportingType(type1));
- assertTrue("Not correct type supported", secondRic.isSupportingType(type2));
- assertEquals("Not correct no of managed nodes", 2, secondRic.getManagedNodes().size());
- assertTrue("Not correct managed node", secondRic.isManaging(MANAGED_NODE_B));
- assertTrue("Not correct managed node", secondRic.isManaging(MANAGED_NODE_C));
+ assertNotNull(secondRic, "Ric \"" + SECOND_RIC_NAME + "\" not added to repositpry");
+ assertEquals(SECOND_RIC_NAME, secondRic.name(), "Not correct Ric \"" + SECOND_RIC_NAME + "\" added to Rics");
+ assertEquals(ACTIVE, secondRic.state(), "Not correct state for \"" + SECOND_RIC_NAME + "\"");
+ assertEquals(2, secondRic.getSupportedPolicyTypes().size(), "Not correct no of types supported");
+ assertTrue(secondRic.isSupportingType(POLICY_TYPE_1_NAME), "Not correct type supported");
+ assertTrue(secondRic.isSupportingType(POLICY_TYPE_2_NAME), "Not correct type supported");
+ assertEquals(2, secondRic.getManagedNodes().size(), "Not correct no of managed nodes");
+ assertTrue(secondRic.isManaging(MANAGED_NODE_B), "Not correct managed node");
+ assertTrue(secondRic.isManaging(MANAGED_NODE_C), "Not correct managed node");
}
private RicConfig getRicConfig(String name, String baseUrl, String... nodeNames) {
--- /dev/null
+{
+ "$schema": "http://json-schema.org/draft-07/schema#",
+ "title": "ANR",
+ "description": "ANR Neighbour Cell Relation Policy",
+ "type": "object",
+ "properties": {
+ "servingCellNrcgi": {
+ "type": "string",
+ "description": "Serving Cell Identifier (NR CGI)"
+ },
+ "neighborCellNrpci": {
+ "type": "string",
+ "description": "Neighbor Cell Identifier (NR PCI)"
+ },
+ "neighborCellNrcgi": {
+ "type": "string",
+ "description": "Neighbor Cell Identifier (NR CGI)"
+ },
+ "flagNoHo": {
+ "type": "boolean",
+ "description": "Flag for HANDOVER NOT ALLOWED"
+ },
+ "flagNoXn": {
+ "type": "boolean",
+ "description": "Flag for Xn CONNECTION NOT ALLOWED"
+ },
+ "flagNoRemove": {
+ "type": "boolean",
+ "description": "Flag for DELETION NOT ALLOWED"
+ }
+ },
+ "required": [
+ "servingCellNrcgi",
+ "neighborCellNrpci",
+ "neighborCellNrcgi",
+ "flagNoHo",
+ "flagNoXn",
+ "flagNoRemove"
+ ]
+}
\ No newline at end of file
--- /dev/null
+{
+ "$schema": "http://json-schema.org/draft-07/schema#",
+ "title": "Example_QoSTarget_1.0.0",
+ "description": "Example QoS Target policy type",
+ "type": "object",
+ "properties": {
+ "scope": {
+ "type": "object",
+ "properties": {
+ "qosId": {
+ "type": "string"
+ },
+ "cellId": {
+ "type": "string"
+ }
+ },
+ "additionalProperties": false,
+ "required": [
+ "qosId"
+ ]
+ },
+ "statement": {
+ "type": "object",
+ "properties": {
+ "gfbr": {
+ "type": "number"
+ },
+ "mfbr": {
+ "type": "number"
+ },
+ "priorityLevel": {
+ "type": "number"
+ },
+ "pdb": {
+ "type": "number"
+ }
+ },
+ "minProperties": 1,
+ "additionalProperties": false
+ }
+ }
+}
\ No newline at end of file
--- /dev/null
+{
+ "$schema": "http://json-schema.org/draft-07/schema#",
+ "title": "Example_QoETarget_1.0.0",
+ "description": "Example QoE Target policy type",
+ "type": "object",
+ "properties": {
+ "scope": {
+ "type": "object",
+ "properties": {
+ "ueId": {
+ "type": "string"
+ },
+ "sliceId": {
+ "type": "string"
+ },
+ "qosId": {
+ "type": "string"
+ },
+ "cellId": {
+ "type": "string"
+ }
+ },
+ "additionalProperties": false,
+ "required": [
+ "ueId",
+ "sliceId"
+ ]
+ },
+ "statement": {
+ "type": "object",
+ "properties": {
+ "qoeScore": {
+ "type": "number"
+ },
+ "initialBuffering": {
+ "type": "number"
+ },
+ "reBuffFreq": {
+ "type": "number"
+ },
+ "stallRatio": {
+ "type": "number"
+ }
+ },
+ "minProperties": 1,
+ "additionalProperties": false
+ }
+ }
+}
\ No newline at end of file
--- /dev/null
+{
+ "$schema": "http://json-schema.org/draft-07/schema#",
+ "title": "Example_TrafficSteeringPreference_1.0.0",
+ "description": "Example QoE Target policy type",
+ "type": "object",
+ "properties": {
+ "scope": {
+ "type": "object",
+ "properties": {
+ "ueId": {
+ "type": "string"
+ },
+ "sliceId": {
+ "type": "string"
+ },
+ "qosId": {
+ "type": "string"
+ },
+ "cellId": {
+ "type": "string"
+ }
+ },
+ "additionalProperties": false,
+ "required": [
+ "ueId"
+ ]
+ },
+ "statement": {
+ "type": "object",
+ "properties": {
+ "cellIdList": {
+ "type": "array",
+ "minItems": 1,
+ "uniqueItems": true,
+ "items": {
+ "type": "string"
+ }
+ },
+ "preference": {
+ "type": "string",
+ "enum": [
+ "SHALL",
+ "PREFER",
+ "AVOID",
+ "FORBID"
+ ]
+ },
+ "primary": {
+ "type": "boolean"
+ }
+ },
+ "required": [
+ "cellIdList",
+ "preference"
+ ],
+ "additionalProperties": false
+ }
+ }
+}
\ No newline at end of file
============LICENSE_END=========================================================
-->
<project xmlns="http://maven.apache.org/POM/4.0.0"
- xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
- xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
- <modelVersion>4.0.0</modelVersion>
+ xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
+ <modelVersion>4.0.0</modelVersion>
- <groupId>org.oransc</groupId>
- <artifactId>nonrtric</artifactId>
- <version>1.0.0-SNAPSHOT</version>
- <packaging>pom</packaging>
+ <groupId>org.o-ran-sc</groupId>
+ <artifactId>nonrtric</artifactId>
+ <version>1.0.0-SNAPSHOT</version>
+ <packaging>pom</packaging>
- <name>nonrtric</name>
- <modules>
- <module>dashboard</module>
- <module>near-rt-ric-simulator</module>
- <module>sdnc-a1-controller</module>
- <module>policy-agent</module>
- </modules>
-</project>
+ <name>nonrtric</name>
+ <modules>
+ <module>policy-agent</module>
+ <module>dashboard</module>
+ <module>near-rt-ric-simulator</module>
+ </modules>
+ </project>