diff options
163 files changed, 4265 insertions, 757 deletions
@@ -49,6 +49,16 @@ committers: company: 'IBM' id: 'brindasanthm' timezone: 'America/New_York' + - name: 'Kevin Smokowski' + email: 'ks6305@att.com' + company: 'ATT' + id: 'nullop' + timezone: 'America/New_York' + - name: 'Kapil Singal' + email: 'kaggarwal@in.ibm.com' + company: 'IBM' + id: 'kasingal' + timezone: 'America/New_York' repositories: - ccsdk/cds tsc: @@ -63,3 +73,9 @@ tsc: - type: 'Addition' name: 'Brinda Santh Muthuramalingam' link: 'https://lists.onap.org/g/onap-tsc/message/5208' + - type: 'Addition' + name: 'Kevin Smokowski' + link: 'https://lists.onap.org/g/onap-tsc/message/5635' + - type: 'Addition' + name: 'Kapil Singal' + link: 'https://lists.onap.org/g/onap-tsc/message/5635' diff --git a/cds-ui/client/.gitignore b/cds-ui/client/.gitignore new file mode 100644 index 000000000..cd7838c5c --- /dev/null +++ b/cds-ui/client/.gitignore @@ -0,0 +1,2 @@ +/target-ide/ +/target/ diff --git a/cds-ui/pom.xml b/cds-ui/pom.xml index 08c10305b..a95e494d6 100644 --- a/cds-ui/pom.xml +++ b/cds-ui/pom.xml @@ -24,7 +24,7 @@ limitations under the License. <parent> <groupId>org.onap.ccsdk.parent</groupId> <artifactId>spring-boot-starter-parent</artifactId> - <version>1.5.0-SNAPSHOT</version> + <version>1.5.0</version> <relativePath/> </parent> diff --git a/cds-ui/server/.gitignore b/cds-ui/server/.gitignore new file mode 100644 index 000000000..b83d22266 --- /dev/null +++ b/cds-ui/server/.gitignore @@ -0,0 +1 @@ +/target/ diff --git a/cds-ui/server/pom.xml b/cds-ui/server/pom.xml index 4c37667a9..fee5c27f4 100644 --- a/cds-ui/server/pom.xml +++ b/cds-ui/server/pom.xml @@ -58,8 +58,8 @@ limitations under the License. <configuration> <artifactItems> <artifactItem> - <groupId>org.onap.ccsdk.cds.components</groupId> - <artifactId>proto-definition</artifactId> + <groupId>org.onap.ccsdk.cds.controllerblueprints</groupId> + <artifactId>blueprint-proto</artifactId> <version>${project.version}</version> <type>jar</type> <overWrite>true</overWrite> diff --git a/cds-ui/server/src/controllers/blueprint-rest.controller.ts b/cds-ui/server/src/controllers/blueprint-rest.controller.ts index 1eef6fbcb..49ecb9df1 100644 --- a/cds-ui/server/src/controllers/blueprint-rest.controller.ts +++ b/cds-ui/server/src/controllers/blueprint-rest.controller.ts @@ -69,6 +69,35 @@ export class BlueprintRestController { return await this.bpservice.getAllblueprints(); } + @get('/controllerblueprint/paged', { + responses: { + '200': { + description: 'Blueprint model instance with pagination', + content: { 'application/json': { schema: { 'x-ts-type': Blueprint } } }, + }, + }, + }) + async getPagedBlueprints( + @param.query.number('limit') limit: number, + @param.query.number('offset') offset: number, + @param.query.string('sort') sort: string) { + return await this.bpservice.getPagedBueprints(limit, offset, sort); + } + + @get('/controllerblueprint/meta-data/{keyword}', { + responses: { + '200': { + description: 'Blueprint model instance', + content: { 'application/json': { schema: { 'x-ts-type': Blueprint } } }, + }, + }, + }) + async getAllPacakgesByKeword(@param.path.string('keyword') keyword: string) { + return await this.bpservice.getBlueprintsByKeyword(keyword); + } + + + @get('/controllerblueprint/searchByTags/{tags}', { responses: { '200': { @@ -344,4 +373,4 @@ export class BlueprintRestController { }); }); } -}
\ No newline at end of file +} diff --git a/cds-ui/server/src/datasources/blueprint.datasource-template.ts b/cds-ui/server/src/datasources/blueprint.datasource-template.ts index 85e0aa342..914021887 100644 --- a/cds-ui/server/src/datasources/blueprint.datasource-template.ts +++ b/cds-ui/server/src/datasources/blueprint.datasource-template.ts @@ -38,5 +38,36 @@ export default { } }, + { + "template": { + "method": "GET", + "url": processorApiConfig.http.url + "/blueprint-model/meta-data/{keyword}", + "headers": { + "accepts": "application/json", + "content-type": "application/json", + "authorization": processorApiConfig.http.authToken + }, + "responsePath": "$.*" + }, + "functions": { + "getBlueprintsByKeyword": ["keyword"] + + } + }, + { + "template": { + "method": "GET", + "url": processorApiConfig.http.url + "/blueprint-model/paged?limit={limit}&offset={offset}&sort={sort}", + "headers": { + "accepts": "application/json", + "content-type": "application/json", + "authorization": processorApiConfig.http.authToken + }, + "responsePath": "$", + }, + "functions": { + "getPagedBueprints": ["limit","offset", "sort"], + } + }, ] -};
\ No newline at end of file +}; diff --git a/cds-ui/server/src/services/blueprint.service.ts b/cds-ui/server/src/services/blueprint.service.ts index 0545faca8..bc93fa1be 100644 --- a/cds-ui/server/src/services/blueprint.service.ts +++ b/cds-ui/server/src/services/blueprint.service.ts @@ -4,7 +4,9 @@ import {BlueprintDataSource} from '../datasources'; export interface BlueprintService { getAllblueprints(): Promise<any>; + getBlueprintsByKeyword(keyword: string): Promise<any>; getByTags(tags: string): Promise<JSON>; + getPagedBueprints(limit: number, offset: number , sort: string): Promise<any>; } export class BlueprintServiceProvider implements Provider<BlueprintService> { @@ -17,4 +19,4 @@ export class BlueprintServiceProvider implements Provider<BlueprintService> { value(): Promise<BlueprintService> { return getService(this.dataSource); } -}
\ No newline at end of file +} diff --git a/ms/blueprintsprocessor/application/pom.xml b/ms/blueprintsprocessor/application/pom.xml index 0ee6ac339..dc0e49fd7 100755 --- a/ms/blueprintsprocessor/application/pom.xml +++ b/ms/blueprintsprocessor/application/pom.xml @@ -84,12 +84,16 @@ <groupId>org.onap.ccsdk.cds.blueprintsprocessor</groupId> <artifactId>configs-api</artifactId> </dependency> - <!-- - <dependency> + <dependency> <groupId>org.onap.ccsdk.cds.blueprintsprocessor</groupId> <artifactId>health-api</artifactId> + <version>0.7.0-SNAPSHOT</version> + </dependency> + <dependency> + <groupId>org.onap.ccsdk.cds.blueprintsprocessor</groupId> + <artifactId>health-api-common</artifactId> + <version>0.7.0-SNAPSHOT</version> </dependency> - --> <!-- Functions --> <dependency> @@ -180,6 +184,7 @@ <groupId>ch.qos.logback</groupId> <artifactId>logback-classic</artifactId> </dependency> + </dependencies> <build> diff --git a/ms/blueprintsprocessor/application/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/LoggingWebFilter.kt b/ms/blueprintsprocessor/application/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/LoggingWebFilter.kt index 68fbf256c..236c8d7f6 100644 --- a/ms/blueprintsprocessor/application/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/LoggingWebFilter.kt +++ b/ms/blueprintsprocessor/application/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/LoggingWebFilter.kt @@ -16,24 +16,8 @@ package org.onap.ccsdk.cds.blueprintsprocessor -import org.onap.ccsdk.cds.blueprintsprocessor.rest.service.RestLoggerService -import org.onap.ccsdk.cds.controllerblueprints.core.MDCContext +import org.onap.ccsdk.cds.blueprintsprocessor.rest.filters.RestServerLoggingWebFilter import org.springframework.stereotype.Component -import org.springframework.web.server.ServerWebExchange -import org.springframework.web.server.WebFilter -import org.springframework.web.server.WebFilterChain -import reactor.core.publisher.Mono -import reactor.util.context.Context @Component -open class LoggingWebFilter : WebFilter { - override fun filter(serverWebExchange: ServerWebExchange, webFilterChain: WebFilterChain): Mono<Void> { - - val loggingService = RestLoggerService() - loggingService.entering(serverWebExchange.request) - val filterChain = webFilterChain.filter(serverWebExchange).subscriberContext( - Context.of(MDCContext, MDCContext())) - loggingService.exiting(serverWebExchange.request, serverWebExchange.response) - return filterChain - } -}
\ No newline at end of file +open class LoggingWebFilter : RestServerLoggingWebFilter() diff --git a/ms/blueprintsprocessor/application/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/actuator/indicator/BluePrintCustomIndicator.kt b/ms/blueprintsprocessor/application/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/actuator/indicator/BluePrintCustomIndicator.kt new file mode 100644 index 000000000..66a19b2c5 --- /dev/null +++ b/ms/blueprintsprocessor/application/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/actuator/indicator/BluePrintCustomIndicator.kt @@ -0,0 +1,47 @@ +/* + * Copyright © 2019-2020 Orange. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.actuator.indicator + +import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain.HealthApiResponse +import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain.HealthCheckStatus +import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.service.health.BluePrintProcessorHealthCheck +import org.springframework.boot.actuate.health.AbstractHealthIndicator +import org.springframework.boot.actuate.health.Health +import org.springframework.stereotype.Component + +/** + * Health Indicator for BluePrintProcessor. + * @author Shaaban Ebrahim + * @version 1.0 + */ +@Component +open class BluePrintCustomIndicator(private val bluePrintProcessorHealthCheck: BluePrintProcessorHealthCheck) + : AbstractHealthIndicator() { + + @Throws(Exception::class) + override fun doHealthCheck(builder: Health.Builder) { + var result: HealthApiResponse? = bluePrintProcessorHealthCheck!!.retrieveEndpointExecutionStatus() + if (result?.status == HealthCheckStatus.UP) { + builder.up() + } else { + builder.down() + } + builder.withDetail("Services", result?.checks) + } + + +} diff --git a/ms/blueprintsprocessor/application/src/main/resources/application-dev.properties b/ms/blueprintsprocessor/application/src/main/resources/application-dev.properties index faabb80e7..485b0bfee 100755 --- a/ms/blueprintsprocessor/application/src/main/resources/application-dev.properties +++ b/ms/blueprintsprocessor/application/src/main/resources/application-dev.properties @@ -24,8 +24,8 @@ # Web server config server.port=8081 # Used in Health Check -endpoints.user.name=ccsdkapps -endpoints.user.password=ccsdkapps +security.user.password: {bcrypt}$2a$10$duaUzVUVW0YPQCSIbGEkQOXwafZGwQ/b32/Ys4R1iwSSawFgz7QNu +security.user.name: ccsdkapps ### START -Controller Blueprints Properties # Load Resource Source Mappings diff --git a/ms/blueprintsprocessor/application/src/main/resources/application.properties b/ms/blueprintsprocessor/application/src/main/resources/application.properties index b8f0d2344..6708dcf69 100755 --- a/ms/blueprintsprocessor/application/src/main/resources/application.properties +++ b/ms/blueprintsprocessor/application/src/main/resources/application.properties @@ -107,4 +107,25 @@ blueprintsprocessor.messageconsumer.self-service-api.pollMillSec=1000 blueprintsprocessor.messageproducer.self-service-api.type=kafka-basic-auth blueprintsprocessor.messageproducer.self-service-api.bootstrapServers=127.0.0.1:9092 blueprintsprocessor.messageproducer.self-service-api.clientId=default-client-id -blueprintsprocessor.messageproducer.self-service-api.topic=producer.t
\ No newline at end of file +blueprintsprocessor.messageproducer.self-service-api.topic=producer.t + + +blueprintprocessor.remoteScriptCommand.enabled=true + +#Encrypted username and password for health check service +endpoints.user.name=eHbVUbJAj4AG2522cSbrOQ== +endpoints.user.password=eHbVUbJAj4AG2522cSbrOQ== + +#BaseUrls for health check blueprint processor services +blueprintprocessor.healthcheck.baseUrl=http://localhost:8080/ +blueprintprocessor.healthcheck.mapping-service-name-with-service-link=[Execution service,/api/v1/execution-service/health-check],[Resources service,/api/v1/resources/health-check],[Template service,/api/v1/template/health-check] + +#BaseUrls for health check Cds Listener services +cdslistener.healthcheck.baseUrl=http://cds-sdc-listener:8080/ +cdslistener.healthcheck.mapping-service-name-with-service-link=[SDC Listener service,/api/v1/sdclistener/healthcheck] + +#Actuator properties +management.endpoints.web.exposure.include=* +management.endpoint.health.show-details=always + + diff --git a/ms/blueprintsprocessor/application/src/main/resources/logback.xml b/ms/blueprintsprocessor/application/src/main/resources/logback.xml index 9d2b82f25..e1389a66f 100644 --- a/ms/blueprintsprocessor/application/src/main/resources/logback.xml +++ b/ms/blueprintsprocessor/application/src/main/resources/logback.xml @@ -20,12 +20,20 @@ <property name="defaultPattern" value="%date{ISO8601,UTC}|%X{RequestID}|%X{InvocationID}|%thread|%X{ServiceName}|%X{ClientIPAddress}|%logger{50}| %msg%n"/> - <appender name="STDOUT" class="ch.qos.logback.core.ConsoleAppender"> - <!-- encoders are assigned the type - ch.qos.logback.classic.encoder.PatternLayoutEncoder by default --> - <encoder> - <pattern>${defaultPattern}</pattern> - </encoder> + <property name="colorPattern" + value="%${color}(%d{HH:mm:ss.SSS}|%X{RequestID}|%thread|%X{ServiceName}|%X{ClientIPAddress}|%logger{50}| %msg%n)"/> + + <appender name="SIFT" class="ch.qos.logback.classic.sift.SiftingAppender"> + <discriminator class="org.onap.ccsdk.cds.blueprintsprocessor.uat.logging.SmartColorDiscriminator"> + <defaultValue>white</defaultValue> + </discriminator> + <sift> + <appender name="STDOUT" class="ch.qos.logback.core.ConsoleAppender"> + <encoder> + <pattern>${defaultPattern}</pattern> + </encoder> + </appender> + </sift> </appender> <logger name="org.springframework" level="info"/> @@ -34,7 +42,7 @@ <logger name="org.onap.ccsdk.cds" level="info"/> <root level="info"> - <appender-ref ref="STDOUT"/> + <appender-ref ref="SIFT"/> </root> </configuration> diff --git a/ms/blueprintsprocessor/application/src/test/resources/application-test.properties b/ms/blueprintsprocessor/application/src/test/resources/application-test.properties index 0f3457454..1d2565be3 100644 --- a/ms/blueprintsprocessor/application/src/test/resources/application-test.properties +++ b/ms/blueprintsprocessor/application/src/test/resources/application-test.properties @@ -48,3 +48,17 @@ blueprintsprocessor.cliExecutor.enabled=true blueprintsprocessor.netconfExecutor.enabled=true blueprintsprocessor.restconfEnabled=true + + +#Encrypted username and password for health check service +endpoints.user.name=eHbVUbJAj4AG2522cSbrOQ== +endpoints.user.password=eHbVUbJAj4AG2522cSbrOQ== + +#BaseUrls for health check blueprint processor services +blueprintprocessor.healthcheck.baseUrl=http://localhost:8080/ +blueprintprocessor.healthcheck.mapping-service-name-with-service-link=[Execution service,/api/v1/execution-service/health-check],[Resources service,/api/v1/resources/health-check],[Template service,/api/v1/template/health-check] + +#BaseUrls for health check Cds Listener services +cdslistener.healthcheck.baseUrl=http://cds-sdc-listener:8080/ +cdslistener.healthcheck.mapping-service-name-with-service-link=[SDC Listener service,/api/v1/sdclistener/healthcheck] + diff --git a/ms/blueprintsprocessor/application/src/test/resources/application.properties b/ms/blueprintsprocessor/application/src/test/resources/application.properties index 92d54f6f5..ea14c493a 100644 --- a/ms/blueprintsprocessor/application/src/test/resources/application.properties +++ b/ms/blueprintsprocessor/application/src/test/resources/application.properties @@ -79,5 +79,5 @@ blueprintsprocessor.messageclient.self-service-api.clientId=default-client-id blueprintsprocessor.messageclient.self-service-api.kafkaEnable=false -endpoints.user.name=ccsdkapps -endpoints.user.password=ccsdkapps +endpoints.user.name=eHbVUbJAj4AG2522cSbrOQ== +endpoints.user.password=eHbVUbJAj4AG2522cSbrOQ== diff --git a/ms/blueprintsprocessor/application/src/test/resources/logback-test.xml b/ms/blueprintsprocessor/application/src/test/resources/logback-test.xml index f635e7925..90dfed324 100644 --- a/ms/blueprintsprocessor/application/src/test/resources/logback-test.xml +++ b/ms/blueprintsprocessor/application/src/test/resources/logback-test.xml @@ -23,7 +23,7 @@ <sift> <appender name="STDOUT" class="ch.qos.logback.core.ConsoleAppender"> <encoder> - <pattern>%${color}(%d{HH:mm:ss.SSS} %-5level %-40.40logger{39} : %msg%n)</pattern> + <pattern>%${color}(%d{HH:mm:ss.SSS}|%X{RequestID}|%X{InvocationID}| %-5level %-40.40logger{39} : %msg%n)</pattern> </encoder> </appender> </sift> diff --git a/ms/blueprintsprocessor/functions/cli-executor/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/cli/executor/ComponentCliExecutorTest.kt b/ms/blueprintsprocessor/functions/cli-executor/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/cli/executor/ComponentCliExecutorTest.kt index 9c0258db0..c4e674c91 100644 --- a/ms/blueprintsprocessor/functions/cli-executor/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/cli/executor/ComponentCliExecutorTest.kt +++ b/ms/blueprintsprocessor/functions/cli-executor/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/cli/executor/ComponentCliExecutorTest.kt @@ -23,8 +23,8 @@ import io.mockk.mockk import kotlinx.coroutines.runBlocking import org.junit.Test import org.junit.runner.RunWith -import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintProperties -import org.onap.ccsdk.cds.blueprintsprocessor.core.BlueprintPropertyConfiguration +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertiesService +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertyConfiguration import org.onap.ccsdk.cds.blueprintsprocessor.core.api.data.ActionIdentifiers import org.onap.ccsdk.cds.blueprintsprocessor.core.api.data.CommonHeader import org.onap.ccsdk.cds.blueprintsprocessor.core.api.data.ExecutionServiceInput @@ -50,7 +50,7 @@ import kotlin.test.assertNotNull @ContextConfiguration(classes = [CliExecutorConfiguration::class, ExecutionServiceConfiguration::class, BluePrintSshLibConfiguration::class, BluePrintScriptsServiceImpl::class, - BlueprintPropertyConfiguration::class, BluePrintProperties::class, BluePrintDependencyService::class]) + BluePrintPropertyConfiguration::class, BluePrintPropertiesService::class, BluePrintDependencyService::class]) @DirtiesContext @TestPropertySource(properties = [], locations = ["classpath:application-test.properties"]) class ComponentCliExecutorTest { diff --git a/ms/blueprintsprocessor/functions/config-snapshots/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/config/snapshots/ComponentConfigSnapshotsExecutorTest.kt b/ms/blueprintsprocessor/functions/config-snapshots/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/config/snapshots/ComponentConfigSnapshotsExecutorTest.kt index baff96a07..f013e89a1 100644 --- a/ms/blueprintsprocessor/functions/config-snapshots/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/config/snapshots/ComponentConfigSnapshotsExecutorTest.kt +++ b/ms/blueprintsprocessor/functions/config-snapshots/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/config/snapshots/ComponentConfigSnapshotsExecutorTest.kt @@ -23,8 +23,8 @@ import org.junit.Assert.assertTrue import org.junit.Before import org.junit.Test import org.junit.runner.RunWith -import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintProperties -import org.onap.ccsdk.cds.blueprintsprocessor.core.BlueprintPropertyConfiguration +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertiesService +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertyConfiguration import org.onap.ccsdk.cds.blueprintsprocessor.core.api.data.ExecutionServiceInput import org.onap.ccsdk.cds.blueprintsprocessor.db.BluePrintDBLibConfiguration import org.onap.ccsdk.cds.blueprintsprocessor.functions.config.snapshots.ComponentConfigSnapshotsExecutor.Companion.DIFF_JSON @@ -48,7 +48,7 @@ import org.springframework.test.context.junit4.SpringRunner @RunWith(SpringRunner::class) @ContextConfiguration(classes = [ResourceConfigSnapshotService::class, - BlueprintPropertyConfiguration::class, BluePrintProperties::class, + BluePrintPropertyConfiguration::class, BluePrintPropertiesService::class, BluePrintDBLibConfiguration::class, BluePrintLoadConfiguration::class]) @TestPropertySource(locations = ["classpath:application-test.properties"]) @ComponentScan(basePackages = ["org.onap.ccsdk.cds.blueprintsprocessor", "org.onap.ccsdk.cds.controllerblueprints"]) diff --git a/ms/blueprintsprocessor/functions/message-prioritizaion/README.txt b/ms/blueprintsprocessor/functions/message-prioritizaion/README.txt new file mode 100644 index 000000000..baf168767 --- /dev/null +++ b/ms/blueprintsprocessor/functions/message-prioritizaion/README.txt @@ -0,0 +1,28 @@ + +To Delete Topics +------------------ +kafka-topics --zookeeper localhost:2181 --delete --topic prioritize-input-topic +kafka-topics --zookeeper localhost:2181 --delete --topic prioritize-output-topic +kafka-topics --zookeeper localhost:2181 --delete --topic prioritize-expired-topic +kafka-topics --zookeeper localhost:2181 --delete --topic test-prioritize-application-PriorityMessage-changelog + +Create Topics +-------------- + +kafka-topics --create --zookeeper localhost:2181 --replication-factor 1 --partitions 1 --topic prioritize-input-topic +kafka-topics --create --zookeeper localhost:2181 --replication-factor 1 --partitions 1 --topic prioritize-output-topic +kafka-topics --create --zookeeper localhost:2181 --replication-factor 1 --partitions 1 --topic prioritize-expired-topic + +To List topics +---------------- +kafka-topics --list --bootstrap-server localhost:9092 + + +To Listen for Output +---------------------- +kafka-console-consumer --bootstrap-server localhost:9092 --topic prioritize-output-topic --from-beginning + +kafka-console-consumer --bootstrap-server localhost:9092 --topic prioritize-input-topic --from-beginning + +kafka-console-consumer --bootstrap-server localhost:9092 --topic prioritize-expired-topic --from-beginning + diff --git a/ms/blueprintsprocessor/functions/message-prioritizaion/pom.xml b/ms/blueprintsprocessor/functions/message-prioritizaion/pom.xml new file mode 100644 index 000000000..ac46b3635 --- /dev/null +++ b/ms/blueprintsprocessor/functions/message-prioritizaion/pom.xml @@ -0,0 +1,43 @@ +<?xml version="1.0" encoding="UTF-8"?> +<!-- + ~ Copyright © 2018-2019 AT&T Intellectual Property. + ~ + ~ 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. + --> + +<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> + + <parent> + <groupId>org.onap.ccsdk.cds.blueprintsprocessor</groupId> + <artifactId>functions</artifactId> + <version>0.7.0-SNAPSHOT</version> + </parent> + + <groupId>org.onap.ccsdk.cds.blueprintsprocessor.functions</groupId> + <artifactId>message-prioritizaion</artifactId> + + <name>Blueprints Processor Function - Message Prioritization</name> + <description>Blueprints Processor Function - Message Prioritization</description> + + <dependencies> + <dependency> + <groupId>org.onap.ccsdk.cds.blueprintsprocessor</groupId> + <artifactId>message-lib</artifactId> + </dependency> + <dependency> + <groupId>com.h2database</groupId> + <artifactId>h2</artifactId> + </dependency> + </dependencies> +</project> diff --git a/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/AbstractTopologyComponents.kt b/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/AbstractTopologyComponents.kt new file mode 100644 index 000000000..d114da521 --- /dev/null +++ b/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/AbstractTopologyComponents.kt @@ -0,0 +1,41 @@ +/* + * Copyright © 2018-2019 AT&T Intellectual Property. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization + +import org.apache.kafka.streams.processor.ProcessorContext +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.service.MessagePrioritizationStateService +import org.onap.ccsdk.cds.blueprintsprocessor.message.kafka.AbstractBluePrintMessageProcessor +import org.onap.ccsdk.cds.controllerblueprints.core.logger +import org.onap.ccsdk.cds.controllerblueprints.core.service.BluePrintDependencyService + +/** CDS Message Prioritazation Kafka Stream Processor abstract class to implement */ +abstract class AbstractMessagePrioritizeProcessor<K, V> : AbstractBluePrintMessageProcessor<K, V>() { + + private val log = logger(AbstractMessagePrioritizeProcessor::class) + + lateinit var prioritizationConfiguration: PrioritizationConfiguration + lateinit var messagePrioritizationStateService: MessagePrioritizationStateService + + override fun init(context: ProcessorContext) { + this.processorContext = context + /** Get the State service to update in store */ + this.messagePrioritizationStateService = BluePrintDependencyService + .messagePrioritizationStateService() + + } + +}
\ No newline at end of file diff --git a/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/MessagePrioritizationConfiguration.kt b/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/MessagePrioritizationConfiguration.kt new file mode 100644 index 000000000..cce883c91 --- /dev/null +++ b/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/MessagePrioritizationConfiguration.kt @@ -0,0 +1,37 @@ +/* + * Copyright © 2018-2019 AT&T Intellectual Property. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization + +import org.springframework.context.annotation.ComponentScan +import org.springframework.context.annotation.Configuration + +@Configuration +@ComponentScan +open class MessagePrioritizationConfiguration + + +object MessagePrioritizationConstants { + + const val SOURCE_INPUT = "source-prioritization-input" + + const val PROCESSOR_PRIORITIZE = "processor-prioritization-prioritize" + const val PROCESSOR_AGGREGATE = "processor-prioritization-aggregate" + const val PROCESSOR_OUTPUT = "processor-prioritization-output" + + const val SINK_OUTPUT = "sink-prioritization-output" + const val SINK_EXPIRED = "sink-prioritization-expired" +}
\ No newline at end of file diff --git a/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/MessagePrioritizationConsumer.kt b/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/MessagePrioritizationConsumer.kt new file mode 100644 index 000000000..967cc190e --- /dev/null +++ b/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/MessagePrioritizationConsumer.kt @@ -0,0 +1,105 @@ +/* + * Copyright © 2018-2019 AT&T Intellectual Property. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization + +import org.apache.kafka.common.serialization.Serdes +import org.apache.kafka.streams.Topology +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.topology.MessagePrioritizationSerde +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.utils.MessageProcessorUtils.bluePrintProcessorSupplier +import org.onap.ccsdk.cds.blueprintsprocessor.message.KafkaStreamsBasicAuthConsumerProperties +import org.onap.ccsdk.cds.blueprintsprocessor.message.MessageConsumerProperties +import org.onap.ccsdk.cds.blueprintsprocessor.message.service.BluePrintMessageLibPropertyService +import org.onap.ccsdk.cds.blueprintsprocessor.message.service.BlueprintMessageConsumerService +import org.onap.ccsdk.cds.blueprintsprocessor.message.service.KafkaStreamConsumerFunction +import org.onap.ccsdk.cds.controllerblueprints.core.logger + +open class MessagePrioritizationConsumer( + private val bluePrintMessageLibPropertyService: BluePrintMessageLibPropertyService) { + + private val log = logger(MessagePrioritizationConsumer::class) + + lateinit var streamingConsumerService: BlueprintMessageConsumerService + + open fun consumerService(selector: String): BlueprintMessageConsumerService { + return bluePrintMessageLibPropertyService + .blueprintMessageConsumerService(selector) + } + + open fun kafkaStreamConsumerFunction(prioritizationConfiguration: PrioritizationConfiguration) + : KafkaStreamConsumerFunction { + return object : KafkaStreamConsumerFunction { + + override suspend fun createTopology(messageConsumerProperties: MessageConsumerProperties, + additionalConfig: Map<String, Any>?): Topology { + + val topology = Topology() + val kafkaStreamsBasicAuthConsumerProperties = messageConsumerProperties + as KafkaStreamsBasicAuthConsumerProperties + + val topics = kafkaStreamsBasicAuthConsumerProperties.topic.split(",") + log.info("Consuming prioritization topics($topics)") + + topology.addSource(MessagePrioritizationConstants.SOURCE_INPUT, *topics.toTypedArray()) + + topology.addProcessor(MessagePrioritizationConstants.PROCESSOR_PRIORITIZE, + bluePrintProcessorSupplier<ByteArray, ByteArray>(MessagePrioritizationConstants.PROCESSOR_PRIORITIZE, + prioritizationConfiguration), + MessagePrioritizationConstants.SOURCE_INPUT) + + topology.addProcessor(MessagePrioritizationConstants.PROCESSOR_AGGREGATE, + bluePrintProcessorSupplier<String, String>(MessagePrioritizationConstants.PROCESSOR_AGGREGATE, + prioritizationConfiguration), + MessagePrioritizationConstants.PROCESSOR_PRIORITIZE) + + topology.addProcessor(MessagePrioritizationConstants.PROCESSOR_OUTPUT, + bluePrintProcessorSupplier<String, String>(MessagePrioritizationConstants.PROCESSOR_OUTPUT, + prioritizationConfiguration), + MessagePrioritizationConstants.PROCESSOR_AGGREGATE) + + topology.addSink(MessagePrioritizationConstants.SINK_EXPIRED, + prioritizationConfiguration.expiredTopic, + Serdes.String().serializer(), MessagePrioritizationSerde().serializer(), + MessagePrioritizationConstants.PROCESSOR_PRIORITIZE) + + /** To receive completed and error messages */ + topology.addSink(MessagePrioritizationConstants.SINK_OUTPUT, + prioritizationConfiguration.outputTopic, + Serdes.String().serializer(), MessagePrioritizationSerde().serializer(), + MessagePrioritizationConstants.PROCESSOR_PRIORITIZE, + MessagePrioritizationConstants.PROCESSOR_AGGREGATE, + MessagePrioritizationConstants.PROCESSOR_OUTPUT) + + // Output will be sent to the group-output topic from Processor API + return topology + } + } + } + + suspend fun startConsuming(prioritizationConfiguration: PrioritizationConfiguration) { + streamingConsumerService = consumerService(prioritizationConfiguration.inputTopicSelector) + + // Dynamic Consumer Function to create Topology + val consumerFunction = kafkaStreamConsumerFunction(prioritizationConfiguration) + streamingConsumerService.consume(null, consumerFunction) + } + + suspend fun shutDown() { + if (streamingConsumerService != null) { + streamingConsumerService.shutDown() + } + } +}
\ No newline at end of file diff --git a/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/MessagePrioritizationData.kt b/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/MessagePrioritizationData.kt new file mode 100644 index 000000000..3358a5643 --- /dev/null +++ b/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/MessagePrioritizationData.kt @@ -0,0 +1,68 @@ +/* + * Copyright © 2018-2019 AT&T Intellectual Property. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization + +import java.io.Serializable + +object MessageActionConstants { + const val PRIORITIZE = "prioritize" +} + +enum class MessageState(val id: String) { + NEW("new"), + WAIT("wait"), + EXPIRED("expired"), + PRIORITIZED("prioritized"), + AGGREGATED("aggregated"), + COMPLETED("completed"), + ERROR("error") +} + +open class PrioritizationConfiguration : Serializable { + lateinit var expiryConfiguration: ExpiryConfiguration + lateinit var shutDownConfiguration: ShutDownConfiguration + lateinit var cleanConfiguration: CleanConfiguration + lateinit var inputTopicSelector: String // Consumer Configuration Selector + lateinit var expiredTopic: String // Publish Configuration Selector + lateinit var outputTopic: String // Publish Configuration Selector +} + +open class ExpiryConfiguration : Serializable { + var frequencyMilli: Long = 30000L + var maxPollRecord: Int = 1000 +} + +open class ShutDownConfiguration : Serializable { + var waitMill: Long = 30000L +} + +open class CleanConfiguration : Serializable { + var frequencyMilli: Long = 30000L + var expiredRecordsHoldDays: Int = 5 +} + +open class UpdateStateRequest : Serializable { + lateinit var id: String + var group: String? = null + var state: String? = null +} + +data class CorrelationCheckResponse(var message: String? = null, + var correlated: Boolean = false) + +data class TypeCorrelationKey(val type: String, val correlationId: String) + diff --git a/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/MessagePrioritizeExtensions.kt b/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/MessagePrioritizeExtensions.kt new file mode 100644 index 000000000..ec061ad47 --- /dev/null +++ b/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/MessagePrioritizeExtensions.kt @@ -0,0 +1,50 @@ +/* + * Copyright © 2018-2019 AT&T Intellectual Property. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization + +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.db.MessagePrioritization +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.service.MessagePrioritizationStateService +import org.onap.ccsdk.cds.blueprintsprocessor.services.execution.AbstractComponentFunction +import org.onap.ccsdk.cds.controllerblueprints.core.service.BluePrintDependencyService + + +/** + * Register the MessagePrioritizationStateService and exposed dependency + */ +fun BluePrintDependencyService.messagePrioritizationStateService(): MessagePrioritizationStateService = + instance(MessagePrioritizationStateService::class) + +/** + * Expose messagePrioritizationStateService to AbstractComponentFunction + */ +fun AbstractComponentFunction.messagePrioritizationStateService() = + BluePrintDependencyService.messagePrioritizationStateService() + +/** + * MessagePrioritization correlation extensions + */ +fun MessagePrioritization.toFormatedCorrelation(): String { + val ascendingKey = this.correlationId!!.split(",") + .map { it.trim() }.sorted().joinToString(",") + return ascendingKey +} + +fun MessagePrioritization.toTypeNCorrelation(): TypeCorrelationKey { + val ascendingKey = this.correlationId!!.split(",") + .map { it.trim() }.sorted().joinToString(",") + return TypeCorrelationKey(this.type, ascendingKey) +} diff --git a/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/api/MessagePrioritizationApi.kt b/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/api/MessagePrioritizationApi.kt new file mode 100644 index 000000000..382cb9c8a --- /dev/null +++ b/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/api/MessagePrioritizationApi.kt @@ -0,0 +1,55 @@ +/* + * Copyright © 2018-2019 AT&T Intellectual Property. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.api + +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.UpdateStateRequest +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.db.MessagePrioritization +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.service.MessagePrioritizationStateService +import org.onap.ccsdk.cds.blueprintsprocessor.rest.service.monoMdc +import org.springframework.http.MediaType +import org.springframework.web.bind.annotation.* + +@RestController +@RequestMapping(value = ["/api/v1/message-prioritization"]) +open class MessagePrioritizationApi(private val messagePrioritizationStateService: MessagePrioritizationStateService) { + + @GetMapping(path = ["/ping"], produces = [MediaType.APPLICATION_JSON_VALUE]) + @ResponseBody + fun ping(): String = "Success" + + + @GetMapping(path = ["/{id}"], produces = [MediaType.APPLICATION_JSON_VALUE]) + @ResponseBody + fun messagePrioritization(@PathVariable(value = "id") id: String) = monoMdc { + messagePrioritizationStateService.getMessage(id) + } + + @PostMapping(path = ["/"], produces = [MediaType.APPLICATION_JSON_VALUE], + consumes = [MediaType.APPLICATION_JSON_VALUE]) + @ResponseBody + fun saveMessagePrioritization(@RequestBody messagePrioritization: MessagePrioritization) = monoMdc { + messagePrioritizationStateService.saveMessage(messagePrioritization) + } + + @PostMapping(path = ["/update-state"], produces = [MediaType.APPLICATION_JSON_VALUE], + consumes = [MediaType.APPLICATION_JSON_VALUE]) + fun updateMessagePrioritizationState(@RequestBody updateMessageState: UpdateStateRequest) = + monoMdc { + messagePrioritizationStateService.setMessageState(updateMessageState.id, + updateMessageState.state!!) + } +}
\ No newline at end of file diff --git a/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/db/MessagePrioritizationRepositories.kt b/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/db/MessagePrioritizationRepositories.kt new file mode 100644 index 000000000..69c81079d --- /dev/null +++ b/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/db/MessagePrioritizationRepositories.kt @@ -0,0 +1,106 @@ +/* + * Copyright © 2018-2019 AT&T Intellectual Property. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.db + +import org.springframework.data.domain.Pageable +import org.springframework.data.jpa.repository.JpaRepository +import org.springframework.data.jpa.repository.Modifying +import org.springframework.data.jpa.repository.Query +import org.springframework.stereotype.Repository +import org.springframework.transaction.annotation.Transactional +import java.util.* + +@Repository +@Transactional(readOnly = true) +interface PrioritizationMessageRepository : JpaRepository<MessagePrioritization, String> { + + @Query("FROM MessagePrioritization pm WHERE pm.group = :group ORDER BY pm.createdDate asc") + fun findByGroup(group: String, count: Pageable): List<MessagePrioritization>? + + @Query("FROM MessagePrioritization pm WHERE pm.group = :group AND pm.state in :states " + + "ORDER BY pm.createdDate asc") + fun findByGroupAndStateIn(group: String, states: List<String>, count: Pageable): List<MessagePrioritization>? + + @Query("FROM MessagePrioritization pm WHERE pm.group = :group AND pm.state in :states " + + "ORDER BY pm.updatedDate asc") + fun findByGroupAndStateInOrderByUpdatedDate(group: String, states: List<String>, count: Pageable) + : List<MessagePrioritization>? + + @Query("FROM MessagePrioritization pm WHERE pm.group = :group AND pm.state in :states " + + "AND pm.expiryDate > :expiryCheckDate ORDER BY pm.createdDate asc") + fun findByGroupAndStateInAndNotExpiredDate(group: String, states: List<String>, expiryCheckDate: Date, + count: Pageable): List<MessagePrioritization>? + + @Query("FROM MessagePrioritization pm WHERE pm.state in :states " + + "AND pm.expiryDate < :expiryCheckDate ORDER BY pm.createdDate asc") + fun findByStateInAndExpiredDate(states: List<String>, expiryCheckDate: Date, + count: Pageable): List<MessagePrioritization>? + + @Query("FROM MessagePrioritization pm WHERE pm.group = :group AND pm.state in :states " + + "AND pm.expiryDate < :expiryCheckDate ORDER BY pm.createdDate asc") + fun findByGroupAndStateInAndExpiredDate(group: String, states: List<String>, expiryCheckDate: Date, + count: Pageable): List<MessagePrioritization>? + + @Query("FROM MessagePrioritization pm WHERE pm.group = :group " + + "AND pm.expiryDate < :expiryCheckDate ORDER BY pm.createdDate asc") + fun findByByGroupAndExpiredDate(group: String, expiryCheckDate: Date, count: Pageable): List<MessagePrioritization>? + + @Query("FROM MessagePrioritization pm WHERE pm.group = :group AND pm.state in :states " + + "AND pm.correlationId = :correlationId ORDER BY pm.createdDate asc") + fun findByGroupAndCorrelationId(group: String, states: List<String>, correlationId: String) + : List<MessagePrioritization>? + + @Query("FROM MessagePrioritization pm WHERE pm.group = :group AND pm.state in :states " + + "AND pm.type in :types AND pm.correlationId = :correlationId ORDER BY pm.createdDate asc") + fun findByGroupAndTypesAndCorrelationId(group: String, states: List<String>, types: List<String>, + correlationId: String): List<MessagePrioritization>? + + @Modifying + @Transactional + @Query("UPDATE MessagePrioritization SET state = :state, updatedDate = :currentDate " + + "WHERE id = :id") + fun setStateForMessageId(id: String, state: String, currentDate: Date): Int + + @Modifying + @Transactional + @Query("UPDATE MessagePrioritization SET state = :state, updatedDate = :currentDate " + + "WHERE id IN :ids") + fun setStateForMessageIds(ids: List<String>, state: String, currentDate: Date): Int + + @Modifying + @Transactional + @Query("UPDATE MessagePrioritization SET state = :state, error = :error, updatedDate = :currentDate " + + "WHERE id = :id") + fun setStateAndErrorForMessageId(id: String, state: String, error: String, currentDate: Date): Int + + @Modifying + @Transactional + @Query("UPDATE MessagePrioritization SET state = :state, " + + "aggregatedMessageIds = :aggregatedMessageIds, updatedDate = :currentDate WHERE id = :id") + fun setStateAndAggregatedMessageIds(id: String, state: String, aggregatedMessageIds: String, currentDate: Date): Int + + @Modifying + @Transactional + @Query("DELETE FROM MessagePrioritization pm WHERE pm.group = :group") + fun deleteGroup(group: String) + + @Modifying + @Transactional + @Query("DELETE FROM MessagePrioritization pm WHERE pm.group = :group AND pm.state IN :states") + fun deleteGroupAndStateIn(group: String, states: List<String>) +} + diff --git a/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/db/PrioritizationMessageEntity.kt b/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/db/PrioritizationMessageEntity.kt new file mode 100644 index 000000000..1825f91c2 --- /dev/null +++ b/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/db/PrioritizationMessageEntity.kt @@ -0,0 +1,78 @@ +/* + * Copyright © 2018-2019 AT&T Intellectual Property. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.db + +import com.fasterxml.jackson.annotation.JsonFormat +import org.hibernate.annotations.Proxy +import org.springframework.data.annotation.LastModifiedDate +import org.springframework.data.jpa.domain.support.AuditingEntityListener +import org.springframework.data.jpa.repository.config.EnableJpaAuditing +import java.util.* +import javax.persistence.* + +@EnableJpaAuditing +@EntityListeners(AuditingEntityListener::class) +@Entity +@Table(name = "MESSAGE_PRIORITIZATION") +@Proxy(lazy = false) +open class MessagePrioritization { + @Id + @Column(name = "message_id", length = 50) + lateinit var id: String + + @Column(name = "message_group", length = 50, nullable = false) + lateinit var group: String + + @Column(name = "message_type", length = 50, nullable = false) + lateinit var type: String + + /** States Defined by MessageState */ + @Column(name = "message_state", length = 20, nullable = false) + lateinit var state: String + + @Lob + @Column(name = "message", nullable = false) + var message: String? = null + + @Lob + @Column(name = "error", nullable = true) + var error: String? = null + + @Lob + @Column(name = "aggregated_message_ids", nullable = true) + var aggregatedMessageIds: String? = null + + @Lob + @Column(name = "correlation_id", nullable = true) + var correlationId: String? = null + + @JsonFormat(shape = JsonFormat.Shape.STRING, pattern = "yyyy-MM-dd'T'HH:mm:ss.SSS'Z'") + @Temporal(TemporalType.TIMESTAMP) + @Column(name = "created_date", nullable = false) + var createdDate = Date() + + @JsonFormat(shape = JsonFormat.Shape.STRING, pattern = "yyyy-MM-dd'T'HH:mm:ss.SSS'Z'") + @LastModifiedDate + @Temporal(TemporalType.TIMESTAMP) + @Column(name = "updated_date", nullable = false) + var updatedDate: Date? = null + + @JsonFormat(shape = JsonFormat.Shape.STRING, pattern = "yyyy-MM-dd'T'HH:mm:ss.SSS'Z'") + @Temporal(TemporalType.TIMESTAMP) + @Column(name = "expiry_date", nullable = false) + var expiryDate: Date? = null +}
\ No newline at end of file diff --git a/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/service/MessagePrioritizationStateService.kt b/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/service/MessagePrioritizationStateService.kt new file mode 100644 index 000000000..8424226c2 --- /dev/null +++ b/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/service/MessagePrioritizationStateService.kt @@ -0,0 +1,184 @@ +/* + * Copyright © 2018-2019 AT&T Intellectual Property. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.service + +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.MessageState +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.db.MessagePrioritization +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.db.PrioritizationMessageRepository +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.toFormatedCorrelation +import org.onap.ccsdk.cds.controllerblueprints.core.BluePrintProcessorException +import org.onap.ccsdk.cds.controllerblueprints.core.logger +import org.springframework.data.domain.PageRequest +import org.springframework.stereotype.Service +import org.springframework.transaction.annotation.Transactional +import java.util.* + +interface MessagePrioritizationStateService { + + suspend fun saveMessage(message: MessagePrioritization): MessagePrioritization + + suspend fun getMessage(id: String): MessagePrioritization + + suspend fun getMessages(ids: List<String>): List<MessagePrioritization>? + + suspend fun getExpiryEligibleMessages(count: Int): List<MessagePrioritization>? + + suspend fun getMessageForStatesNotExpiredIn(group: String, states: List<String>, count: Int) + : List<MessagePrioritization>? + + suspend fun getMessageForStatesExpired(group: String, states: List<String>, count: Int) + : List<MessagePrioritization>? + + suspend fun getExpiredMessages(group: String, expiryDate: Date, count: Int): List<MessagePrioritization>? + + suspend fun getCorrelatedMessages(group: String, states: List<String>, types: List<String>?, + correlationIds: String): List<MessagePrioritization>? + + suspend fun updateMessagesState(ids: List<String>, state: String) + + suspend fun updateMessageState(id: String, state: String): MessagePrioritization + + suspend fun setMessageState(id: String, state: String) + + suspend fun setMessagesState(ids: List<String>, state: String) + + suspend fun setMessageStateANdError(id: String, state: String, error: String) + + suspend fun setMessageStateAndAggregatedIds(id: String, state: String, aggregatedIds: List<String>) + + suspend fun deleteMessage(id: String) + + suspend fun deleteMessageByGroup(group: String) + + suspend fun deleteMessageStates(group: String, states: List<String>) + + suspend fun deleteExpiredMessage(group: String, retentionDays: Int) +} + +@Service +open class MessagePrioritizationStateServiceImpl( + private val prioritizationMessageRepository: PrioritizationMessageRepository) + : MessagePrioritizationStateService { + + private val log = logger(MessagePrioritizationStateServiceImpl::class) + + @Transactional + override suspend fun saveMessage(message: MessagePrioritization): MessagePrioritization { + if (!message.correlationId.isNullOrBlank()) { + message.correlationId = message.toFormatedCorrelation() + } + message.updatedDate = Date() + return prioritizationMessageRepository.save(message) + } + + override suspend fun getMessage(id: String): MessagePrioritization { + return prioritizationMessageRepository.findById(id).orElseGet(null) + ?: throw BluePrintProcessorException("couldn't find message for id($id)") + } + + override suspend fun getMessages(ids: List<String>): List<MessagePrioritization>? { + return prioritizationMessageRepository.findAllById(ids) + } + + override suspend fun getExpiryEligibleMessages(count: Int): List<MessagePrioritization>? { + return prioritizationMessageRepository + .findByStateInAndExpiredDate(arrayListOf(MessageState.NEW.name, MessageState.WAIT.name), + Date(), PageRequest.of(0, count)) + } + + override suspend fun getMessageForStatesNotExpiredIn(group: String, states: List<String>, count: Int) + : List<MessagePrioritization>? { + return prioritizationMessageRepository.findByGroupAndStateInAndNotExpiredDate(group, + states, Date(), PageRequest.of(0, count)) + } + + override suspend fun getMessageForStatesExpired(group: String, states: List<String>, count: Int) + : List<MessagePrioritization>? { + return prioritizationMessageRepository.findByGroupAndStateInAndExpiredDate(group, + states, Date(), PageRequest.of(0, count)) + } + + override suspend fun getExpiredMessages(group: String, expiryDate: Date, count: Int) + : List<MessagePrioritization>? { + return prioritizationMessageRepository.findByByGroupAndExpiredDate(group, + expiryDate, PageRequest.of(0, count)) + } + + override suspend fun getCorrelatedMessages(group: String, states: List<String>, types: List<String>?, + correlationIds: String): List<MessagePrioritization>? { + return if (!types.isNullOrEmpty()) { + prioritizationMessageRepository.findByGroupAndTypesAndCorrelationId(group, states, types, correlationIds) + } else { + prioritizationMessageRepository.findByGroupAndCorrelationId(group, states, correlationIds) + } + } + + @Transactional + override suspend fun updateMessagesState(ids: List<String>, state: String) { + ids.forEach { + val updated = updateMessageState(it, state) + log.info("message($it) update to state(${updated.state})") + } + } + + @Transactional + override suspend fun setMessageState(id: String, state: String) { + prioritizationMessageRepository.setStateForMessageId(id, state, Date()) + } + + @Transactional + override suspend fun setMessagesState(ids: List<String>, state: String) { + prioritizationMessageRepository.setStateForMessageIds(ids, state, Date()) + } + + @Transactional + override suspend fun setMessageStateANdError(id: String, state: String, error: String) { + prioritizationMessageRepository.setStateAndErrorForMessageId(id, state, error, Date()) + } + + @Transactional + override suspend fun updateMessageState(id: String, state: String): MessagePrioritization { + val updateMessage = getMessage(id).apply { + this.updatedDate = Date() + this.state = state + } + return saveMessage(updateMessage) + } + + @Transactional + override suspend fun setMessageStateAndAggregatedIds(id: String, state: String, aggregatedIds: List<String>) { + val groupedIds = aggregatedIds.joinToString(",") + prioritizationMessageRepository.setStateAndAggregatedMessageIds(id, state, groupedIds, Date()) + } + + override suspend fun deleteMessage(id: String) { + return prioritizationMessageRepository.deleteById(id) + } + + override suspend fun deleteMessageByGroup(group: String) { + return prioritizationMessageRepository.deleteGroup(group) + } + + override suspend fun deleteMessageStates(group: String, states: List<String>) { + return prioritizationMessageRepository.deleteGroupAndStateIn(group, states) + } + + override suspend fun deleteExpiredMessage(group: String, retentionDays: Int) { + return prioritizationMessageRepository.deleteGroupAndStateIn(group, + arrayListOf(MessageState.EXPIRED.name)) + } +}
\ No newline at end of file diff --git a/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/topology/MessageAggregateProcessor.kt b/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/topology/MessageAggregateProcessor.kt new file mode 100644 index 000000000..45f5c773d --- /dev/null +++ b/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/topology/MessageAggregateProcessor.kt @@ -0,0 +1,76 @@ +/* + * Copyright © 2018-2019 AT&T Intellectual Property. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.topology + +import org.apache.kafka.streams.processor.To +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.AbstractMessagePrioritizeProcessor +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.MessagePrioritizationConstants +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.MessageState +import org.onap.ccsdk.cds.controllerblueprints.core.logger + + +open class MessageAggregateProcessor : AbstractMessagePrioritizeProcessor<String, String>() { + + private val log = logger(MessageAggregateProcessor::class) + + override suspend fun processNB(key: String, value: String) { + + log.info("@@@@@ received in aggregation processor key($key), value($value)") + val ids = value.split(",").map { it.trim() } + if (!ids.isNullOrEmpty()) { + try { + if (ids.size == 1) { + processorContext.forward(key, ids.first(), To.child(MessagePrioritizationConstants.PROCESSOR_OUTPUT)) + } else { + /** Implement Aggregation logic in overridden class, If necessary, + Populate New Message and Update status with Prioritized, Forward the message to next processor */ + handleAggregation(ids) + /** Update all messages to Aggregated state */ + messagePrioritizationStateService.setMessagesState(ids, MessageState.AGGREGATED.name) + } + } catch (e: Exception) { + val error = "failed in Aggregate message($ids) : ${e.message}" + log.error(error, e) + val storeMessages = messagePrioritizationStateService.getMessages(ids) + if (!storeMessages.isNullOrEmpty()) { + storeMessages.forEach { messagePrioritization -> + try { + /** Update the data store */ + messagePrioritizationStateService.setMessageStateANdError(messagePrioritization.id, + MessageState.ERROR.name, error) + /** Publish to Error topic */ + this.processorContext.forward(messagePrioritization.id, messagePrioritization, + To.child(MessagePrioritizationConstants.SINK_OUTPUT)) + } catch (sendException: Exception) { + log.error("failed to update/publish error message(${messagePrioritization.id}) : " + + "${sendException.message}", e) + } + + } + } + } + } + } + + /** Child will override this implementation , if necessary */ + open suspend fun handleAggregation(messageIds: List<String>) { + log.info("messages($messageIds) aggregated") + messageIds.forEach { id -> + processorContext.forward(id, id, To.child(MessagePrioritizationConstants.PROCESSOR_OUTPUT)) + } + } +}
\ No newline at end of file diff --git a/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/topology/MessageOutputProcessor.kt b/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/topology/MessageOutputProcessor.kt new file mode 100644 index 000000000..34faa1b3b --- /dev/null +++ b/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/topology/MessageOutputProcessor.kt @@ -0,0 +1,35 @@ +/* + * Copyright © 2018-2019 AT&T Intellectual Property. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.topology + +import org.apache.kafka.streams.processor.To +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.AbstractMessagePrioritizeProcessor +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.MessagePrioritizationConstants +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.MessageState +import org.onap.ccsdk.cds.controllerblueprints.core.logger + + +open class MessageOutputProcessor : AbstractMessagePrioritizeProcessor<String, String>() { + + private val log = logger(MessageOutputProcessor::class) + + override suspend fun processNB(key: String, value: String) { + log.info("$$$$$ received in output processor key($key), value($value)") + val message = messagePrioritizationStateService.updateMessageState(value, MessageState.COMPLETED.name) + processorContext.forward(message.id, message, To.child(MessagePrioritizationConstants.SINK_OUTPUT)) + } +}
\ No newline at end of file diff --git a/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/topology/MessagePrioritizationPunctuators.kt b/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/topology/MessagePrioritizationPunctuators.kt new file mode 100644 index 000000000..a745e034c --- /dev/null +++ b/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/topology/MessagePrioritizationPunctuators.kt @@ -0,0 +1,64 @@ +/* + * Copyright © 2018-2019 AT&T Intellectual Property. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.topology + +import org.apache.kafka.streams.processor.To +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.MessagePrioritizationConstants +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.MessageState +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.PrioritizationConfiguration +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.service.MessagePrioritizationStateService +import org.onap.ccsdk.cds.blueprintsprocessor.message.kafka.AbstractBluePrintMessagePunctuator +import org.onap.ccsdk.cds.controllerblueprints.core.logger + + +class MessagePriorityExpiryPunctuator(private val messagePrioritizationStateService: MessagePrioritizationStateService) + : AbstractBluePrintMessagePunctuator() { + + private val log = logger(MessagePriorityExpiryPunctuator::class) + lateinit var configuration: PrioritizationConfiguration + + override suspend fun punctuateNB(timestamp: Long) { + + log.info("**** executing expiry punctuator applicationId(${processorContext.applicationId()}), " + + "taskId(${processorContext.taskId()})") + val expiryConfiguration = configuration.expiryConfiguration + val fetchMessages = messagePrioritizationStateService + .getExpiryEligibleMessages(expiryConfiguration.maxPollRecord) + + val expiredIds = fetchMessages?.map { it.id } + if (expiredIds != null && expiredIds.isNotEmpty()) { + messagePrioritizationStateService.updateMessagesState(expiredIds, MessageState.EXPIRED.name) + fetchMessages.forEach { expired -> + processorContext.forward(expired.id, expired, + To.child(MessagePrioritizationConstants.SINK_EXPIRED)) + } + } + } +} + +class MessagePriorityCleanPunctuator(private val messagePrioritizationStateService: MessagePrioritizationStateService) + : AbstractBluePrintMessagePunctuator() { + + private val log = logger(MessagePriorityCleanPunctuator::class) + lateinit var configuration: PrioritizationConfiguration + + override suspend fun punctuateNB(timestamp: Long) { + log.info("**** executing clean punctuator applicationId(${processorContext.applicationId()}), " + + "taskId(${processorContext.taskId()})") + //TODO + } +}
\ No newline at end of file diff --git a/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/topology/MessagePrioritizationSerdes.kt b/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/topology/MessagePrioritizationSerdes.kt new file mode 100644 index 000000000..00d454727 --- /dev/null +++ b/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/topology/MessagePrioritizationSerdes.kt @@ -0,0 +1,64 @@ +/* + * Copyright © 2018-2019 AT&T Intellectual Property. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.topology + +import org.apache.kafka.common.serialization.Deserializer +import org.apache.kafka.common.serialization.Serde +import org.apache.kafka.common.serialization.Serializer +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.db.MessagePrioritization +import org.onap.ccsdk.cds.controllerblueprints.core.BluePrintProcessorException +import org.onap.ccsdk.cds.controllerblueprints.core.asJsonString +import org.onap.ccsdk.cds.controllerblueprints.core.utils.JacksonUtils +import java.nio.charset.Charset + +open class MessagePrioritizationSerde : Serde<MessagePrioritization> { + + override fun configure(configs: MutableMap<String, *>?, isKey: Boolean) { + } + + override fun close() { + } + + override fun deserializer(): Deserializer<MessagePrioritization> { + return object : Deserializer<MessagePrioritization> { + override fun deserialize(topic: String, data: ByteArray): MessagePrioritization { + return JacksonUtils.readValue(String(data), MessagePrioritization::class.java) + ?: throw BluePrintProcessorException("failed to convert") + } + + override fun configure(configs: MutableMap<String, *>?, isKey: Boolean) { + } + + override fun close() { + } + } + } + + override fun serializer(): Serializer<MessagePrioritization> { + return object : Serializer<MessagePrioritization> { + override fun configure(configs: MutableMap<String, *>?, isKey: Boolean) { + } + + override fun serialize(topic: String?, data: MessagePrioritization): ByteArray { + return data.asJsonString().toByteArray(Charset.defaultCharset()) + } + + override fun close() { + } + } + } +}
\ No newline at end of file diff --git a/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/topology/MessagePrioritizeProcessor.kt b/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/topology/MessagePrioritizeProcessor.kt new file mode 100644 index 000000000..7dde2655d --- /dev/null +++ b/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/topology/MessagePrioritizeProcessor.kt @@ -0,0 +1,148 @@ +/* + * Copyright © 2018-2019 AT&T Intellectual Property. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.topology + +import org.apache.kafka.streams.processor.Cancellable +import org.apache.kafka.streams.processor.ProcessorContext +import org.apache.kafka.streams.processor.PunctuationType +import org.apache.kafka.streams.processor.To +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.AbstractMessagePrioritizeProcessor +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.MessagePrioritizationConstants +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.MessageState +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.db.MessagePrioritization +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.utils.MessageCorrelationUtils +import org.onap.ccsdk.cds.controllerblueprints.core.BluePrintProcessorException +import org.onap.ccsdk.cds.controllerblueprints.core.logger +import org.onap.ccsdk.cds.controllerblueprints.core.utils.JacksonUtils +import java.time.Duration +import java.util.* + + +open class MessagePrioritizeProcessor : AbstractMessagePrioritizeProcessor<ByteArray, ByteArray>() { + + private val log = logger(MessagePrioritizeProcessor::class) + + lateinit var expiryCancellable: Cancellable + lateinit var cleanCancellable: Cancellable + + override suspend fun processNB(key: ByteArray, value: ByteArray) { + log.info("***** received in prioritize processor key(${String(key)})") + val messagePrioritize = JacksonUtils.readValue(String(value), MessagePrioritization::class.java) + ?: throw BluePrintProcessorException("failed to convert") + try { + // Save the Message + messagePrioritizationStateService.saveMessage(messagePrioritize) + handleCorrelationAndNextStep(messagePrioritize) + } catch (e: Exception) { + messagePrioritize.error = "failed in Prioritize message(${messagePrioritize.id}) : ${e.message}" + log.error(messagePrioritize.error) + /** Update the data store */ + messagePrioritizationStateService.setMessageStateANdError(messagePrioritize.id, MessageState.ERROR.name, + messagePrioritize.error!!) + /** Publish to Output topic */ + this.processorContext.forward(messagePrioritize.id, messagePrioritize, + To.child(MessagePrioritizationConstants.SINK_OUTPUT)) + } + } + + override fun init(context: ProcessorContext) { + super.init(context) + /** set up expiry marking cron */ + initializeExpiryPunctuator() + /** Set up cleaning records cron */ + initializeCleanPunctuator() + } + + override fun close() { + log.info("closing prioritization processor applicationId(${processorContext.applicationId()}), " + + "taskId(${processorContext.taskId()})") + expiryCancellable.cancel() + cleanCancellable.cancel() + } + + open fun initializeExpiryPunctuator() { + val expiryPunctuator = MessagePriorityExpiryPunctuator(messagePrioritizationStateService) + expiryPunctuator.processorContext = processorContext + expiryPunctuator.configuration = prioritizationConfiguration + val expiryConfiguration = prioritizationConfiguration.expiryConfiguration + expiryCancellable = processorContext.schedule(Duration.ofMillis(expiryConfiguration.frequencyMilli), + PunctuationType.WALL_CLOCK_TIME, expiryPunctuator) + log.info("Expiry punctuator setup complete with frequency(${expiryConfiguration.frequencyMilli})mSec") + } + + open fun initializeCleanPunctuator() { + val cleanPunctuator = MessagePriorityCleanPunctuator(messagePrioritizationStateService) + cleanPunctuator.processorContext = processorContext + cleanPunctuator.configuration = prioritizationConfiguration + val cleanConfiguration = prioritizationConfiguration.cleanConfiguration + cleanCancellable = processorContext.schedule(Duration.ofDays(cleanConfiguration.expiredRecordsHoldDays.toLong()), + PunctuationType.WALL_CLOCK_TIME, cleanPunctuator) + log.info("Clean punctuator setup complete with expiry " + + "hold(${cleanConfiguration.expiredRecordsHoldDays})days") + } + + open suspend fun handleCorrelationAndNextStep(messagePrioritization: MessagePrioritization) { + /** Check correlation enabled and correlation field has populated */ + if (!messagePrioritization.correlationId.isNullOrBlank()) { + val id = messagePrioritization.id + val group = messagePrioritization.group + val correlationId = messagePrioritization.correlationId!! + val types = getGroupCorrelationTypes(messagePrioritization) + log.info("checking correlation for message($id), group($group), types($types), " + + "correlation id($correlationId)") + + /** Get all previously received messages from database for group and optional types and correlation Id */ + val waitingCorrelatedStoreMessages = messagePrioritizationStateService.getCorrelatedMessages(group, + arrayListOf(MessageState.NEW.name, MessageState.WAIT.name), types, correlationId) + + /** If multiple records found, then check correlation */ + if (!waitingCorrelatedStoreMessages.isNullOrEmpty() && waitingCorrelatedStoreMessages.size > 1) { + /** Check all correlation satisfies */ + val correlationResults = MessageCorrelationUtils + .correlatedMessagesWithTypes(waitingCorrelatedStoreMessages, types) + + if (correlationResults.correlated) { + /** Correlation satisfied */ + val correlatedIds = waitingCorrelatedStoreMessages.map { it.id }.joinToString(",") + /** Send only correlated ids to next processor */ + this.processorContext.forward(UUID.randomUUID().toString(), correlatedIds, + To.child(MessagePrioritizationConstants.PROCESSOR_AGGREGATE)) + } else { + /** Correlation not satisfied */ + log.trace("correlation not matched : ${correlationResults.message}") + val waitMessageIds = waitingCorrelatedStoreMessages.map { it.id } + // Update the Message state to Wait + messagePrioritizationStateService.setMessagesState(waitMessageIds, MessageState.WAIT.name) + } + } else { + /** received first message of group and correlation Id, update the message with wait state */ + messagePrioritizationStateService.setMessageState(messagePrioritization.id, MessageState.WAIT.name) + } + } else { + // No Correlation check needed, simply forward to next processor. + messagePrioritizationStateService.setMessageState(messagePrioritization.id, MessageState.PRIORITIZED.name) + this.processorContext.forward(messagePrioritization.id, messagePrioritization.id, + To.child(MessagePrioritizationConstants.PROCESSOR_AGGREGATE)) + } + } + + /** If consumer wants specific correlation with respect to group and types, then populate the specific types, + * otherwise correlation happens with group and correlationId */ + open fun getGroupCorrelationTypes(messagePrioritization: MessagePrioritization): List<String>? { + return null + } +}
\ No newline at end of file diff --git a/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/utils/MessageCorrelationUtils.kt b/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/utils/MessageCorrelationUtils.kt new file mode 100644 index 000000000..cc30af2f1 --- /dev/null +++ b/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/utils/MessageCorrelationUtils.kt @@ -0,0 +1,82 @@ +/* + * Copyright © 2018-2019 AT&T Intellectual Property. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.utils + +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.CorrelationCheckResponse +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.db.MessagePrioritization +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.toFormatedCorrelation +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.toTypeNCorrelation +import org.onap.ccsdk.cds.controllerblueprints.core.BluePrintProcessorException + +object MessageCorrelationUtils { + + /** Assumption is message is of same group **/ + fun correlatedMessages(collectedMessages: List<MessagePrioritization>): CorrelationCheckResponse { + val correlationCheckResponse = CorrelationCheckResponse(message = "not correlated") + if (collectedMessages.size > 1) { + val filteredMessage = collectedMessages.filter { !it.correlationId.isNullOrBlank() } + if (filteredMessage.isNotEmpty()) { + val groupedMessage = filteredMessage.groupBy { it.toFormatedCorrelation() } + if (groupedMessage.size == 1) { + correlationCheckResponse.correlated = true + correlationCheckResponse.message = null + } + } + } else { + correlationCheckResponse.message = "received only one message for that group" + } + return correlationCheckResponse + } + + /** Assumption is message is of same group and checking for required types **/ + fun correlatedMessagesWithTypes(collectedMessages: List<MessagePrioritization>, types: List<String>?) + : CorrelationCheckResponse { + + return if (!types.isNullOrEmpty() && collectedMessages.size > 1) { + + val unknownMessageTypes = collectedMessages.filter { !types.contains(it.type) }.map { it.id } + if (!unknownMessageTypes.isNullOrEmpty()) { + throw BluePrintProcessorException("Messages($unknownMessageTypes) is not in type of($types)") + } + + val copyTypes = types.toTypedArray().copyOf().toMutableList() + + val filteredMessage = collectedMessages.filter { + !it.correlationId.isNullOrBlank() + && types.contains(it.type) + } + var correlatedKeys: MutableSet<String> = mutableSetOf() + if (filteredMessage.isNotEmpty()) { + val correlatedMap = filteredMessage.groupBy { it.toTypeNCorrelation() } + val foundType = correlatedMap.keys.map { it.type } + copyTypes.removeAll(foundType) + correlatedKeys = correlatedMap.keys.map { + it.correlationId + }.toMutableSet() + } + /** Check if any Types missing and same correlation id for all types */ + return if (copyTypes.isEmpty()) { + if (correlatedKeys.size == 1) CorrelationCheckResponse(correlated = true) + else CorrelationCheckResponse(message = "not matching correlation keys($correlatedKeys)") + } else { + CorrelationCheckResponse(message = "couldn't find types($copyTypes)") + } + } else { + return correlatedMessages(collectedMessages) + } + } +}
\ No newline at end of file diff --git a/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/utils/MessagePrioritizationSample.kt b/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/utils/MessagePrioritizationSample.kt new file mode 100644 index 000000000..3281a97f9 --- /dev/null +++ b/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/utils/MessagePrioritizationSample.kt @@ -0,0 +1,103 @@ +/* + * Copyright © 2018-2019 AT&T Intellectual Property. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.utils + +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.CleanConfiguration +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.ExpiryConfiguration +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.PrioritizationConfiguration +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.ShutDownConfiguration +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.db.MessagePrioritization +import java.util.* + +object MessagePrioritizationSample { + + fun samplePrioritizationConfiguration(): PrioritizationConfiguration { + return PrioritizationConfiguration().apply { + inputTopicSelector = "prioritize-input" + outputTopic = "prioritize-output-topic" + expiredTopic = "prioritize-expired-topic" + expiryConfiguration = ExpiryConfiguration().apply { + frequencyMilli = 10000L + maxPollRecord = 2000 + } + shutDownConfiguration = ShutDownConfiguration().apply { + waitMill = 2000L + } + cleanConfiguration = CleanConfiguration().apply { + frequencyMilli = 10000L + expiredRecordsHoldDays = 5 + } + } + } + + private fun currentDatePlusDays(days: Int): Date { + val calender = Calendar.getInstance() + calender.add(Calendar.DATE, days) + return calender.time + } + + fun sampleMessages(messageState: String, count: Int): List<MessagePrioritization> { + return sampleMessages("sample-group", messageState, count) + } + + fun sampleMessages(groupName: String, messageState: String, count: Int): List<MessagePrioritization> { + val messages: MutableList<MessagePrioritization> = arrayListOf() + repeat(count) { + val backPressureMessage = createMessage(groupName, messageState, + "sample-type", null) + messages.add(backPressureMessage) + } + return messages + } + + fun sampleMessageWithSameCorrelation(groupName: String, messageState: String, count: Int): List<MessagePrioritization> { + val messages: MutableList<MessagePrioritization> = arrayListOf() + repeat(count) { + val backPressureMessage = createMessage(groupName, messageState, "sample-type", + "key1=value1,key2=value2") + messages.add(backPressureMessage) + } + return messages + } + + fun sampleMessageWithDifferentTypeSameCorrelation(groupName: String, messageState: String, + count: Int): List<MessagePrioritization> { + val messages: MutableList<MessagePrioritization> = arrayListOf() + repeat(count) { + val backPressureMessage = createMessage(groupName, messageState, "type-$it", + "key1=value1,key2=value2") + messages.add(backPressureMessage) + } + return messages + } + + fun createMessage(groupName: String, messageState: String, messageType: String, + messageCorrelationId: String?): MessagePrioritization { + + return MessagePrioritization().apply { + id = UUID.randomUUID().toString() + group = groupName + type = messageType + state = messageState + correlationId = messageCorrelationId + message = "I am the Message" + createdDate = Date() + updatedDate = Date() + expiryDate = currentDatePlusDays(3) + } + } +}
\ No newline at end of file diff --git a/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/utils/MessageProcessorUtils.kt b/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/utils/MessageProcessorUtils.kt new file mode 100644 index 000000000..02614d821 --- /dev/null +++ b/ms/blueprintsprocessor/functions/message-prioritizaion/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/utils/MessageProcessorUtils.kt @@ -0,0 +1,36 @@ +/* + * Copyright © 2018-2019 AT&T Intellectual Property. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.utils + +import org.apache.kafka.streams.processor.ProcessorSupplier +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.AbstractMessagePrioritizeProcessor +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.PrioritizationConfiguration +import org.onap.ccsdk.cds.controllerblueprints.core.service.BluePrintDependencyService + +object MessageProcessorUtils { + + fun <K, V> bluePrintProcessorSupplier(name: String, prioritizationConfiguration: PrioritizationConfiguration) + : ProcessorSupplier<K, V> { + return ProcessorSupplier<K, V> { + // Dynamically resolve the Prioritization Processor + val processorInstance = BluePrintDependencyService.instance<AbstractMessagePrioritizeProcessor<K, V>>(name) + processorInstance.prioritizationConfiguration = prioritizationConfiguration + processorInstance + } + } + +}
\ No newline at end of file diff --git a/ms/blueprintsprocessor/functions/message-prioritizaion/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/MessagePrioritizationConsumerTest.kt b/ms/blueprintsprocessor/functions/message-prioritizaion/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/MessagePrioritizationConsumerTest.kt new file mode 100644 index 000000000..bd99f72d0 --- /dev/null +++ b/ms/blueprintsprocessor/functions/message-prioritizaion/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/MessagePrioritizationConsumerTest.kt @@ -0,0 +1,175 @@ +/* + * Copyright © 2018-2019 AT&T Intellectual Property. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization + +import io.mockk.coEvery +import io.mockk.every +import io.mockk.spyk +import kotlinx.coroutines.delay +import kotlinx.coroutines.launch +import kotlinx.coroutines.runBlocking +import org.junit.Before +import org.junit.runner.RunWith +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintProperties +import org.onap.ccsdk.cds.blueprintsprocessor.core.BlueprintPropertyConfiguration +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.db.PrioritizationMessageRepository +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.service.MessagePrioritizationStateService +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.utils.MessagePrioritizationSample +import org.onap.ccsdk.cds.blueprintsprocessor.message.BluePrintMessageLibConfiguration +import org.onap.ccsdk.cds.blueprintsprocessor.message.service.BluePrintMessageLibPropertyService +import org.onap.ccsdk.cds.blueprintsprocessor.message.service.KafkaBasicAuthMessageProducerService +import org.onap.ccsdk.cds.controllerblueprints.core.asJsonString +import org.onap.ccsdk.cds.controllerblueprints.core.service.BluePrintDependencyService +import org.springframework.beans.factory.annotation.Autowired +import org.springframework.boot.test.autoconfigure.orm.jpa.DataJpaTest +import org.springframework.context.ApplicationContext +import org.springframework.test.annotation.DirtiesContext +import org.springframework.test.context.ContextConfiguration +import org.springframework.test.context.TestPropertySource +import org.springframework.test.context.junit4.SpringRunner +import kotlin.test.Test +import kotlin.test.assertNotNull + + +@RunWith(SpringRunner::class) +@DataJpaTest +@DirtiesContext +@ContextConfiguration(classes = [BluePrintMessageLibConfiguration::class, + BlueprintPropertyConfiguration::class, BluePrintProperties::class, + MessagePrioritizationConfiguration::class, TestDatabaseConfiguration::class]) +@TestPropertySource(properties = +[ + "spring.jpa.show-sql=true", + "spring.jpa.properties.hibernate.show_sql=true", + "spring.jpa.hibernate.naming.physical-strategy=org.hibernate.boot.model.naming.PhysicalNamingStrategyStandardImpl", + + "blueprintsprocessor.messageconsumer.prioritize-input.type=kafka-streams-basic-auth", + "blueprintsprocessor.messageconsumer.prioritize-input.bootstrapServers=127.0.0.1:9092", + "blueprintsprocessor.messageconsumer.prioritize-input.applicationId=test-prioritize-application", + "blueprintsprocessor.messageconsumer.prioritize-input.topic=prioritize-input-topic", + + // To send initial test message + "blueprintsprocessor.messageproducer.prioritize-input.type=kafka-basic-auth", + "blueprintsprocessor.messageproducer.prioritize-input.bootstrapServers=127.0.0.1:9092", + "blueprintsprocessor.messageproducer.prioritize-input.topic=prioritize-input-topic" +]) +open class MessagePrioritizationConsumerTest { + + @Autowired + lateinit var applicationContext: ApplicationContext + + @Autowired + lateinit var prioritizationMessageRepository: PrioritizationMessageRepository + + @Autowired + lateinit var bluePrintMessageLibPropertyService: BluePrintMessageLibPropertyService + + @Before + fun setup() { + BluePrintDependencyService.inject(applicationContext) + } + + @Test + fun testBluePrintKafkaJDBCKeyStore() { + runBlocking { + assertNotNull(prioritizationMessageRepository, "failed to get prioritizationMessageRepository") + + val messagePrioritizationService: MessagePrioritizationStateService = BluePrintDependencyService + .instance(MessagePrioritizationStateService::class) + assertNotNull(messagePrioritizationService, "failed to get messagePrioritizationService") + + MessagePrioritizationSample.sampleMessages(MessageState.NEW.name, 1).forEach { + val message = messagePrioritizationService.saveMessage(it) + val repoResult = messagePrioritizationService.getMessage(message.id) + assertNotNull(repoResult, "failed to get inserted message.") + } + } + } + + @Test + fun testStartConsuming() { + runBlocking { + val configuration = MessagePrioritizationSample.samplePrioritizationConfiguration() + + val streamingConsumerService = bluePrintMessageLibPropertyService + .blueprintMessageConsumerService(configuration.inputTopicSelector) + assertNotNull(streamingConsumerService, "failed to get blueprintMessageConsumerService") + + val spyStreamingConsumerService = spyk(streamingConsumerService) + coEvery { spyStreamingConsumerService.consume(any(), any()) } returns Unit + coEvery { spyStreamingConsumerService.shutDown() } returns Unit + val messagePrioritizationConsumer = MessagePrioritizationConsumer(bluePrintMessageLibPropertyService) + val spyMessagePrioritizationConsumer = spyk(messagePrioritizationConsumer) + + + // Test Topology + val kafkaStreamConsumerFunction = spyMessagePrioritizationConsumer.kafkaStreamConsumerFunction(configuration) + val messageConsumerProperties = bluePrintMessageLibPropertyService + .messageConsumerProperties("blueprintsprocessor.messageconsumer.prioritize-input") + val topology = kafkaStreamConsumerFunction.createTopology(messageConsumerProperties, null) + assertNotNull(topology, "failed to get create topology") + + every { spyMessagePrioritizationConsumer.consumerService(any()) } returns spyStreamingConsumerService + spyMessagePrioritizationConsumer.startConsuming(configuration) + spyMessagePrioritizationConsumer.shutDown() + } + } + + /** Integration Kafka Testing, Enable and use this test case only for local desktop testing with real kafka broker */ + //@Test + fun testMessagePrioritizationConsumer() { + runBlocking { + val messagePrioritizationConsumer = MessagePrioritizationConsumer(bluePrintMessageLibPropertyService) + messagePrioritizationConsumer.startConsuming(MessagePrioritizationSample.samplePrioritizationConfiguration()) + + /** Send sample message with every 1 sec */ + val blueprintMessageProducerService = bluePrintMessageLibPropertyService + .blueprintMessageProducerService("prioritize-input") as KafkaBasicAuthMessageProducerService + launch { + MessagePrioritizationSample.sampleMessages(MessageState.NEW.name, 2).forEach { + delay(100) + val headers: MutableMap<String, String> = hashMapOf() + headers["id"] = it.id + blueprintMessageProducerService.sendMessageNB(message = it.asJsonString(false), + headers = headers) + } + + MessagePrioritizationSample + .sampleMessageWithSameCorrelation("same-group", MessageState.NEW.name, 2) + .forEach { + delay(100) + val headers: MutableMap<String, String> = hashMapOf() + headers["id"] = it.id + blueprintMessageProducerService.sendMessageNB(message = it.asJsonString(false), + headers = headers) + } + + MessagePrioritizationSample + .sampleMessageWithDifferentTypeSameCorrelation("group-typed", MessageState.NEW.name, 3) + .forEach { + delay(2000) + val headers: MutableMap<String, String> = hashMapOf() + headers["id"] = it.id + blueprintMessageProducerService.sendMessageNB(message = it.asJsonString(false), + headers = headers) + } + } + delay(10000) + messagePrioritizationConsumer.shutDown() + } + } +}
\ No newline at end of file diff --git a/ms/blueprintsprocessor/functions/message-prioritizaion/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/TestConfiguration.kt b/ms/blueprintsprocessor/functions/message-prioritizaion/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/TestConfiguration.kt new file mode 100644 index 000000000..4e3eb191b --- /dev/null +++ b/ms/blueprintsprocessor/functions/message-prioritizaion/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/TestConfiguration.kt @@ -0,0 +1,57 @@ +/* + * Copyright © 2018-2019 AT&T Intellectual Property. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization + +import org.onap.ccsdk.cds.blueprintsprocessor.db.primary.PrimaryDBLibGenericService +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.db.MessagePrioritization +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.topology.MessageAggregateProcessor +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.topology.MessageOutputProcessor +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.topology.MessagePrioritizeProcessor +import org.springframework.boot.autoconfigure.EnableAutoConfiguration +import org.springframework.context.annotation.Bean +import org.springframework.context.annotation.ComponentScan +import org.springframework.context.annotation.Configuration +import org.springframework.jdbc.core.namedparam.NamedParameterJdbcTemplate +import org.springframework.stereotype.Service +import javax.sql.DataSource + +@Configuration +@ComponentScan(basePackages = ["org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.db"]) +@EnableAutoConfiguration +open class TestDatabaseConfiguration { + + @Bean("primaryDBLibGenericService") + open fun primaryDBLibGenericService(dataSource: DataSource): PrimaryDBLibGenericService { + return PrimaryDBLibGenericService(NamedParameterJdbcTemplate(dataSource)) + } +} + +@Service(MessagePrioritizationConstants.PROCESSOR_PRIORITIZE) +open class TestMessagePrioritizeProcessor : MessagePrioritizeProcessor() { + override fun getGroupCorrelationTypes(messagePrioritization: MessagePrioritization): List<String>? { + return when (messagePrioritization.group) { + "group-typed" -> arrayListOf("type-0", "type-1", "type-2") + else -> null + } + } +} + +@Service(MessagePrioritizationConstants.PROCESSOR_AGGREGATE) +open class DefaultMessageAggregateProcessor() : MessageAggregateProcessor() + +@Service(MessagePrioritizationConstants.PROCESSOR_OUTPUT) +open class DefaultMessageOutputProcessor : MessageOutputProcessor()
\ No newline at end of file diff --git a/ms/blueprintsprocessor/functions/message-prioritizaion/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/utils/MessageCorrelationUtilsTest.kt b/ms/blueprintsprocessor/functions/message-prioritizaion/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/utils/MessageCorrelationUtilsTest.kt new file mode 100644 index 000000000..b470db909 --- /dev/null +++ b/ms/blueprintsprocessor/functions/message-prioritizaion/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/message/prioritization/utils/MessageCorrelationUtilsTest.kt @@ -0,0 +1,98 @@ +/* + * Copyright © 2018-2019 AT&T Intellectual Property. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.utils + +import org.junit.Test +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.MessageState +import org.onap.ccsdk.cds.blueprintsprocessor.functions.message.prioritization.db.MessagePrioritization +import kotlin.test.assertTrue + +class MessageCorrelationUtilsTest { + + @Test + fun testCorrelationKeysReordered() { + + val message1 = MessagePrioritizationSample.createMessage("sample-group", MessageState.NEW.name, + "type-0", "key1=value1,key2=value2") + val message2 = MessagePrioritizationSample.createMessage("sample-group", MessageState.NEW.name, + "type-0", "key2=value2,key1=value1") + + val multipleMessages: MutableList<MessagePrioritization> = arrayListOf() + multipleMessages.add(message1) + multipleMessages.add(message2) + val multipleMessagesResponse = MessageCorrelationUtils.correlatedMessages(multipleMessages) + assertTrue(multipleMessagesResponse.correlated, "failed in multipleMessages correlated keys reordered") + } + + @Test + fun differentTypesWithSameCorrelationMessages() { + /** With Types **/ + /* Assumption is Same group with different types */ + val differentTypesWithSameCorrelationMessages = MessagePrioritizationSample + .sampleMessageWithDifferentTypeSameCorrelation("sample-group", MessageState.NEW.name, 3) + val differentTypesWithSameCorrelationMessagesResponse = MessageCorrelationUtils.correlatedMessagesWithTypes( + differentTypesWithSameCorrelationMessages, + arrayListOf("type-0", "type-1", "type-2")) + assertTrue(differentTypesWithSameCorrelationMessagesResponse.correlated, + "failed to correlate differentTypesWithSameCorrelationMessagesResponse") + + /* Assumption is Same group with different types and one missing expected types, + In this case type-3 message is missing */ + val differentTypesWithSameCorrelationMessagesResWithMissingType = MessageCorrelationUtils.correlatedMessagesWithTypes( + differentTypesWithSameCorrelationMessages, + arrayListOf("type-0", "type-1", "type-2", "type-3")) + assertTrue(!differentTypesWithSameCorrelationMessagesResWithMissingType.correlated, + "failed to correlate differentTypesWithSameCorrelationMessagesResWithMissingType") + } + + @Test + fun withSameCorrelationMessagesWithIgnoredTypes() { + /** With ignoring Types */ + /** Assumption is only one message received */ + val withSameCorrelationOneMessages = MessagePrioritizationSample + .sampleMessageWithSameCorrelation("sample-group", MessageState.NEW.name, 1) + val withSameCorrelationOneMessagesResp = MessageCorrelationUtils.correlatedMessagesWithTypes( + withSameCorrelationOneMessages, null) + assertTrue(!withSameCorrelationOneMessagesResp.correlated, + "failed to correlate withSameCorrelationMessagesResp") + + /** Assumption is two message received for same group with same correlation */ + val withSameCorrelationMessages = MessagePrioritizationSample + .sampleMessageWithSameCorrelation("sample-group", MessageState.NEW.name, 2) + val withSameCorrelationMessagesResp = MessageCorrelationUtils.correlatedMessagesWithTypes( + withSameCorrelationMessages, null) + assertTrue(withSameCorrelationMessagesResp.correlated, + "failed to correlate withSameCorrelationMessagesResp") + } + + @Test + fun differentTypesWithDifferentCorrelationMessage() { + /** Assumption is two message received for same group with different expected types and different correlation */ + val message1 = MessagePrioritizationSample.createMessage("sample-group", MessageState.NEW.name, + "type-0", "key1=value1,key2=value2") + val message2 = MessagePrioritizationSample.createMessage("sample-group", MessageState.NEW.name, + "type-1", "key1=value1,key2=value3") + val differentTypesWithDifferentCorrelationMessage: MutableList<MessagePrioritization> = arrayListOf() + differentTypesWithDifferentCorrelationMessage.add(message1) + differentTypesWithDifferentCorrelationMessage.add(message2) + val differentTypesWithDifferentCorrelationMessageResp = MessageCorrelationUtils.correlatedMessagesWithTypes( + differentTypesWithDifferentCorrelationMessage, + arrayListOf("type-0", "type-1")) + assertTrue(!differentTypesWithDifferentCorrelationMessageResp.correlated, + "failed to correlate differentTypesWithDifferentCorrelationMessageResp") + } +}
\ No newline at end of file diff --git a/ms/blueprintsprocessor/functions/message-prioritizaion/src/test/resources/logback-test.xml b/ms/blueprintsprocessor/functions/message-prioritizaion/src/test/resources/logback-test.xml new file mode 100644 index 000000000..e3a1f7a01 --- /dev/null +++ b/ms/blueprintsprocessor/functions/message-prioritizaion/src/test/resources/logback-test.xml @@ -0,0 +1,42 @@ +<!-- + ~ Copyright © 2018-2019 AT&T Intellectual Property. + ~ + ~ 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. + --> + +<configuration> + + <property name="localPattern" value="%d{HH:mm:ss.SSS} [%thread] %-5level %logger{50} - %msg%n"/> + <property name="defaultPattern" + value="%date{ISO8601,UTC}|%X{RequestID}|%X{InvocationID}|%thread|%X{ServiceName}|%X{ClientIPAddress}|%logger{50}| %msg%n"/> + <property name="testing" + value="%X{RequestID}|%X{InvocationID}|%logger{50}| %msg%n"/> + + <appender name="STDOUT" class="ch.qos.logback.core.ConsoleAppender"> + <!-- encoders are assigned the type + ch.qos.logback.classic.encoder.PatternLayoutEncoder by default --> + <encoder> + <pattern>${localPattern}</pattern> + </encoder> + </appender> + + <logger name="org.springframework.test" level="warn"/> + <logger name="org.springframework" level="warn"/> + <logger name="org.hibernate.type.descriptor.sql" level="warn"/> + <logger name="org.onap.ccsdk.cds.blueprintsprocessor" level="info"/> + + <root level="warn"> + <appender-ref ref="STDOUT"/> + </root> + +</configuration> diff --git a/ms/blueprintsprocessor/functions/netconf-executor/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/netconf/executor/api/DeviceInfo.kt b/ms/blueprintsprocessor/functions/netconf-executor/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/netconf/executor/api/DeviceInfo.kt index f5567b7a2..2395dddb8 100644 --- a/ms/blueprintsprocessor/functions/netconf-executor/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/netconf/executor/api/DeviceInfo.kt +++ b/ms/blueprintsprocessor/functions/netconf-executor/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/netconf/executor/api/DeviceInfo.kt @@ -29,11 +29,11 @@ class DeviceInfo { @get:JsonProperty("port-number") var port: Int = 0 @get:JsonProperty("connection-time-out") - var connectTimeout: Long = 5 + var connectTimeout: Long = 30 @get:JsonIgnore var source: String? = null @get:JsonIgnore - var replyTimeout: Int = 5 + var replyTimeout: Int = 20 @get:JsonIgnore var idleTimeout: Int = 99999 @@ -50,4 +50,4 @@ class DeviceInfo { override fun hashCode(): Int { return javaClass.hashCode() } -}
\ No newline at end of file +} diff --git a/ms/blueprintsprocessor/functions/netconf-executor/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/netconf/executor/core/NetconfDeviceCommunicator.kt b/ms/blueprintsprocessor/functions/netconf-executor/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/netconf/executor/core/NetconfDeviceCommunicator.kt index bc91b7d92..06a71cad3 100644 --- a/ms/blueprintsprocessor/functions/netconf-executor/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/netconf/executor/core/NetconfDeviceCommunicator.kt +++ b/ms/blueprintsprocessor/functions/netconf-executor/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/netconf/executor/core/NetconfDeviceCommunicator.kt @@ -195,7 +195,7 @@ class NetconfDeviceCommunicator(private var inputStream: InputStream, } fun sendMessage(request: String, messageId: String): CompletableFuture<String> { - log.info("$deviceInfo: Sending message: \n $request") + log.info("$deviceInfo: Sending message with message-id: $messageId: message: \n $request") val future = CompletableFuture<String>() replies.put(messageId, future) val outputStream = OutputStreamWriter(out, StandardCharsets.UTF_8) diff --git a/ms/blueprintsprocessor/functions/netconf-executor/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/netconf/executor/core/NetconfRpcServiceImpl.kt b/ms/blueprintsprocessor/functions/netconf-executor/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/netconf/executor/core/NetconfRpcServiceImpl.kt index 6a045e365..2e33b9aa2 100644 --- a/ms/blueprintsprocessor/functions/netconf-executor/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/netconf/executor/core/NetconfRpcServiceImpl.kt +++ b/ms/blueprintsprocessor/functions/netconf-executor/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/netconf/executor/core/NetconfRpcServiceImpl.kt @@ -38,15 +38,36 @@ class NetconfRpcServiceImpl(private var deviceInfo: DeviceInfo) : NetconfRpcServ this.netconfSession = netconfSession } + /** + * accept a user-supplied RPC message WITH HEADER + * <rpc message-id="abc123" xmlns="....."> + * ..... + * ..... + * </rpc> + * + * and replace the user-supplied message-id with the one that is passed. + * Used by NetconfRpcServiceImpl.invokeRpc to keep the message-id consistent + * with auto-incremented numbering scheme. + * @param rpc: Complete custom RPC call including the header + * @param updatedMessageID new message-id to substitute + * @return updated RPC message with message-id replaced. + */ + private fun replaceUserSuppliedNetconfMessageID(rpc: String, updatedMessageID: String): String { + return rpc.replaceFirst("message-id=\".+\"".toRegex(), "message-id=\"$updatedMessageID\"") + } + override fun invokeRpc(rpc: String): DeviceResponse { var output = DeviceResponse() - val messageId = messageIdInteger.getAndIncrement().toString() - log.info("$deviceInfo: invokeRpc: messageId($messageId)") + //Attempt to extract the message-id field from the <rpc call + val updatedMessageId = messageIdInteger.getAndIncrement().toString() + val origMessageId = NetconfMessageUtils.getMsgId(rpc) + log.info("$deviceInfo: invokeRpc: updating rpc original message-id:($origMessageId) to messageId($updatedMessageId)") try { - output = asyncRpc(rpc, messageId) + output = asyncRpc(replaceUserSuppliedNetconfMessageID(rpc, updatedMessageId), updatedMessageId) } catch (e: Exception) { output.status = RpcStatus.FAILURE - output.errorMessage = "$deviceInfo: failed in 'invokeRpc' command ${e.message}" + output.errorMessage = "$deviceInfo: failed in 'invokeRpc' command. Message: ${e.message}." + log.error("$deviceInfo: failed in 'invokeRpc' command. Exception: $e") } return output } @@ -60,7 +81,8 @@ class NetconfRpcServiceImpl(private var deviceInfo: DeviceInfo) : NetconfRpcServ output = asyncRpc(message, messageId) } catch (e: Exception) { output.status = RpcStatus.FAILURE - output.errorMessage = "$deviceInfo: failed in 'get' command ${e.message}" + output.errorMessage = "$deviceInfo: failed in 'get' command. Message: ${e.message}..." + log.error("$deviceInfo: failed in 'get' command. Exception: $e") } return output } @@ -74,7 +96,8 @@ class NetconfRpcServiceImpl(private var deviceInfo: DeviceInfo) : NetconfRpcServ output = asyncRpc(message, messageId) } catch (e: Exception) { output.status = RpcStatus.FAILURE - output.errorMessage = "$deviceInfo: failed in 'get-config' command ${e.message}" + output.errorMessage = "$deviceInfo: failed in 'get-config' command. Message: ${e.message}" + log.error("$deviceInfo: failed in 'get-config' command. Exception: $e") } return output } @@ -89,7 +112,8 @@ class NetconfRpcServiceImpl(private var deviceInfo: DeviceInfo) : NetconfRpcServ output = asyncRpc(deleteConfigMessage, messageId) } catch (e: Exception) { output.status = RpcStatus.FAILURE - output.errorMessage = "$deviceInfo: failed in 'delete-config' command ${e.message}" + output.errorMessage = "$deviceInfo: failed in 'delete-config' command. Message: ${e.message}" + log.error("$deviceInfo: failed in 'deleteConfig' command. Exception: $e") } return output } @@ -104,7 +128,8 @@ class NetconfRpcServiceImpl(private var deviceInfo: DeviceInfo) : NetconfRpcServ output = asyncRpc(lockMessage, messageId) } catch (e: Exception) { output.status = RpcStatus.FAILURE - output.errorMessage = "$deviceInfo: failed in 'lock' command ${e.message}" + output.errorMessage = "$deviceInfo: failed in 'lock' command. Message ${e.message}" + log.error("$deviceInfo: failed in 'lock' command. Exception: $e") } return output @@ -120,7 +145,8 @@ class NetconfRpcServiceImpl(private var deviceInfo: DeviceInfo) : NetconfRpcServ output = asyncRpc(unlockMessage, messageId) } catch (e: Exception) { output.status = RpcStatus.FAILURE - output.errorMessage = "$deviceInfo: failed in 'unLock' command ${e.message}" + output.errorMessage = "$deviceInfo: failed in 'unLock' command. Message: ${e.message}" + log.error("$deviceInfo: failed in 'unLock' command. Exception: $e") } return output } @@ -134,7 +160,8 @@ class NetconfRpcServiceImpl(private var deviceInfo: DeviceInfo) : NetconfRpcServ output = asyncRpc(messageContent, messageId) } catch (e: Exception) { output.status = RpcStatus.FAILURE - output.errorMessage = "$deviceInfo: failed in 'commit' command ${e.message}" + output.errorMessage = "$deviceInfo: failed in 'commit' command. Message: ${e.message}" + log.error("$deviceInfo: failed in 'commit' command. Exception: $e") } return output } @@ -148,7 +175,8 @@ class NetconfRpcServiceImpl(private var deviceInfo: DeviceInfo) : NetconfRpcServ output = asyncRpc(messageContent, messageId) } catch (e: Exception) { output.status = RpcStatus.FAILURE - output.errorMessage = "$deviceInfo: failed in 'cancelCommit' command ${e.message}" + output.errorMessage = "$deviceInfo: failed in 'cancelCommit' command. Message: ${e.message}" + log.error("$deviceInfo: failed in 'cancelCommit' command. Exception: $e") } return output } @@ -163,7 +191,8 @@ class NetconfRpcServiceImpl(private var deviceInfo: DeviceInfo) : NetconfRpcServ output = asyncRpc(discardChangesMessage, messageId) } catch (e: Exception) { output.status = RpcStatus.FAILURE - output.errorMessage = "$deviceInfo: failed in 'discard-config' command ${e.message}" + output.errorMessage = "$deviceInfo: failed in 'discard-config' command. Message: ${e.message}" + log.error("$deviceInfo: failed in 'discard-config' command. Exception: $e") } return output } @@ -180,7 +209,8 @@ class NetconfRpcServiceImpl(private var deviceInfo: DeviceInfo) : NetconfRpcServ response = asyncRpc(editMessage, messageId) } catch (e: Exception) { response.status = RpcStatus.FAILURE - response.errorMessage = "$deviceInfo: failed in 'editConfig' command ${e.message}" + response.errorMessage = "$deviceInfo: failed in 'editConfig' command. Message: ${e.message}" + log.error("$deviceInfo: failed in 'editConfig' command. Exception: $e") } return response } @@ -194,7 +224,8 @@ class NetconfRpcServiceImpl(private var deviceInfo: DeviceInfo) : NetconfRpcServ output = asyncRpc(validateMessage, messageId) } catch (e: Exception) { output.status = RpcStatus.FAILURE - output.errorMessage = "$deviceInfo: failed in 'validate' command ${e.message}" + output.errorMessage = "$deviceInfo: failed in 'validate' command. Message: ${e.message}" + log.error("$deviceInfo: failed in 'validate' command. Exception: $e") } return output } @@ -208,7 +239,8 @@ class NetconfRpcServiceImpl(private var deviceInfo: DeviceInfo) : NetconfRpcServ output = asyncRpc(messageContent, messageId) } catch (e: Exception) { output.status = RpcStatus.FAILURE - output.errorMessage = "$deviceInfo: failed in 'closeSession' command ${e.message}" + output.errorMessage = "$deviceInfo: failed in 'closeSession' command. Message: ${e.message}" + log.error("$deviceInfo: failed in 'closeSession' command. Exception: $e") } return output } @@ -220,7 +252,9 @@ class NetconfRpcServiceImpl(private var deviceInfo: DeviceInfo) : NetconfRpcServ response.requestMessage = request val rpcResponse = netconfSession.asyncRpc(request, messageId).get(responseTimeout.toLong(), TimeUnit.SECONDS) + //TODO catch TimeoutException and ExecutionException if (!NetconfMessageUtils.checkReply(rpcResponse)) { + log.error("RPC response didn't pass validation... $rpcResponse") throw NetconfException(rpcResponse) } response.responseMessage = rpcResponse diff --git a/ms/blueprintsprocessor/functions/netconf-executor/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/netconf/executor/core/NetconfSessionImpl.kt b/ms/blueprintsprocessor/functions/netconf-executor/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/netconf/executor/core/NetconfSessionImpl.kt index 69b9d70bf..6be93179f 100644 --- a/ms/blueprintsprocessor/functions/netconf-executor/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/netconf/executor/core/NetconfSessionImpl.kt +++ b/ms/blueprintsprocessor/functions/netconf-executor/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/netconf/executor/core/NetconfSessionImpl.kt @@ -69,7 +69,7 @@ class NetconfSessionImpl(private val deviceInfo: DeviceInfo, private val rpcServ var retryNum = 3 while(rpcService.closeSession(false).status .equals(RpcStatus.FAILURE, true) &&retryNum>0) { - log.error("disconnect: graceful disconnect failed, attempt $retryNum") + log.error("disconnect: graceful disconnect failed, retrying $retryNum times...") retryNum--; } //if we can't close the session, try to force terminate. @@ -248,6 +248,7 @@ class NetconfSessionImpl(private val deviceInfo: DeviceInfo, private val rpcServ if (sessionIDMatcher.find()) { sessionId = sessionIDMatcher.group(1) + log.info("netconf exchangeHelloMessage sessionID: $sessionId") } else { throw NetconfException("$deviceInfo: Missing sessionId in server hello message: $serverHelloResponse") } diff --git a/ms/blueprintsprocessor/functions/netconf-executor/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/netconf/executor/utils/NetconfMessageUtils.kt b/ms/blueprintsprocessor/functions/netconf-executor/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/netconf/executor/utils/NetconfMessageUtils.kt index 4d65d36bb..34816b79b 100644 --- a/ms/blueprintsprocessor/functions/netconf-executor/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/netconf/executor/utils/NetconfMessageUtils.kt +++ b/ms/blueprintsprocessor/functions/netconf-executor/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/netconf/executor/utils/NetconfMessageUtils.kt @@ -221,7 +221,15 @@ class NetconfMessageUtils { fun closeSession(messageId: String, force: Boolean): String { val request = StringBuilder() - + //TODO: kill-session without session-id is a cisco-only variant. + //will fail on JUNIPER device. + //netconf RFC for kill-session requires session-id + //Cisco can accept <kill-session/> for current session + //or <kill-session><session-id>####</session-id></kill-session> + //as long as session ID is not the same as the current session. + + //Juniperhttps://www.juniper.net/documentation/en_US/junos/topics/task/operational/netconf-session-terminating.html + //will accept only with session-id if (force) { request.append("<kill-session/>") } else { @@ -413,4 +421,4 @@ class NetconfMessageUtils { } } -}
\ No newline at end of file +} diff --git a/ms/blueprintsprocessor/functions/netconf-executor/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/netconf/executor/ComponentNetconfExecutorTest.kt b/ms/blueprintsprocessor/functions/netconf-executor/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/netconf/executor/ComponentNetconfExecutorTest.kt index 8a08268d8..be3ee4614 100644 --- a/ms/blueprintsprocessor/functions/netconf-executor/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/netconf/executor/ComponentNetconfExecutorTest.kt +++ b/ms/blueprintsprocessor/functions/netconf-executor/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/netconf/executor/ComponentNetconfExecutorTest.kt @@ -20,51 +20,56 @@ package org.onap.ccsdk.cds.blueprintsprocessor.functions.netconf.executor import com.fasterxml.jackson.databind.JsonNode +import io.mockk.coEvery +import io.mockk.every +import io.mockk.mockk +import io.mockk.spyk import kotlinx.coroutines.runBlocking import org.junit.Test -import org.junit.runner.RunWith import org.onap.ccsdk.cds.blueprintsprocessor.core.api.data.ExecutionServiceInput import org.onap.ccsdk.cds.blueprintsprocessor.core.api.data.StepData +import org.onap.ccsdk.cds.blueprintsprocessor.services.execution.AbstractScriptComponentFunction +import org.onap.ccsdk.cds.blueprintsprocessor.services.execution.ComponentFunctionScriptingService +import org.onap.ccsdk.cds.blueprintsprocessor.services.execution.scripts.BlueprintJythonService import org.onap.ccsdk.cds.controllerblueprints.core.BluePrintConstants import org.onap.ccsdk.cds.controllerblueprints.core.asJsonType import org.onap.ccsdk.cds.controllerblueprints.core.putJsonElement import org.onap.ccsdk.cds.controllerblueprints.core.utils.BluePrintMetadataUtils import org.onap.ccsdk.cds.controllerblueprints.core.utils.JacksonUtils -import org.springframework.beans.factory.annotation.Autowired -import org.springframework.boot.autoconfigure.EnableAutoConfiguration -import org.springframework.context.annotation.ComponentScan -import org.springframework.test.annotation.DirtiesContext -import org.springframework.test.context.TestPropertySource -import org.springframework.test.context.junit4.SpringRunner - -@RunWith(SpringRunner::class) -@EnableAutoConfiguration -@ComponentScan(basePackages = ["org.onap.ccsdk.cds.blueprintsprocessor", "org.onap.ccsdk.cds.controllerblueprints"]) -@DirtiesContext -@TestPropertySource(properties = -["blueprints.processor.functions.python.executor.modulePaths=./../../../../components/scripts/python/ccsdk_netconf,./../../../../components/scripts/python/ccsdk_blueprints", - "blueprints.processor.functions.python.executor.executionPath=./../../../../components/scripts/python/ccsdk_netconf"], - locations = ["classpath:application-test.properties"]) -class ComponentNetconfExecutorTest { - - @Autowired - lateinit var componentNetconfExecutor: ComponentNetconfExecutor +import org.springframework.context.ApplicationContext +class ComponentNetconfExecutorTest { @Test fun testComponentNetconfExecutor() { runBlocking { + + val applicationContext = mockk<ApplicationContext>() + every { applicationContext.getBean(any()) } returns mockk() + + val blueprintJythonService = mockk<BlueprintJythonService>() + val mockAbstractScriptComponentFunction = spyk<AbstractScriptComponentFunction>() + coEvery { mockAbstractScriptComponentFunction.executeScript(any()) } returns mockk() + + coEvery { blueprintJythonService.jythonComponentInstance(any(), any()) } returns mockAbstractScriptComponentFunction + + val componentFunctionScriptingService = ComponentFunctionScriptingService(applicationContext, + blueprintJythonService) + + val componentNetconfExecutor = ComponentNetconfExecutor(componentFunctionScriptingService) + val executionServiceInput = JacksonUtils.readValueFromClassPathFile("requests/sample-activate-request.json", ExecutionServiceInput::class.java)!! val bluePrintRuntimeService = BluePrintMetadataUtils.getBluePrintRuntime("1234", "./../../../../components/model-catalog/blueprint-model/test-blueprint/baseconfiguration") - val assignmentParams = "{\n" + - " \"ipAddress\": \"127.0.0.1\",\n" + - " \"hostName\": \"vnf-host\"\n" + - " }" + val assignmentParams = """{ + "ipAddress" : "127.0.0.1", + "hostName" : "vnf-host" + } + """.trimIndent() val json = """{ "hostname" : "127.0.0.1" @@ -75,8 +80,6 @@ class ComponentNetconfExecutorTest { bluePrintRuntimeService.setNodeTemplateAttributeValue("resource-assignment", "assignment-params", JacksonUtils.jsonNode(assignmentParams)) - val executionContext = bluePrintRuntimeService.getExecutionContext() - componentNetconfExecutor.bluePrintRuntimeService = bluePrintRuntimeService //TODO("Set Attribute properties") @@ -93,7 +96,6 @@ class ComponentNetconfExecutorTest { executionServiceInput.stepData = stepInputData componentNetconfExecutor.applyNB(executionServiceInput) } - } } diff --git a/ms/blueprintsprocessor/functions/pom.xml b/ms/blueprintsprocessor/functions/pom.xml index 3ee6737ef..38f9071ee 100755 --- a/ms/blueprintsprocessor/functions/pom.xml +++ b/ms/blueprintsprocessor/functions/pom.xml @@ -39,6 +39,7 @@ <module>restconf-executor</module> <module>cli-executor</module> <module>config-snapshots</module> + <module>message-prioritizaion</module> </modules> <dependencies> diff --git a/ms/blueprintsprocessor/functions/resource-resolution/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/resource/resolution/ResourceResolutionServiceTest.kt b/ms/blueprintsprocessor/functions/resource-resolution/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/resource/resolution/ResourceResolutionServiceTest.kt index 5a5336ae3..db453acf4 100644 --- a/ms/blueprintsprocessor/functions/resource-resolution/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/resource/resolution/ResourceResolutionServiceTest.kt +++ b/ms/blueprintsprocessor/functions/resource-resolution/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/resource/resolution/ResourceResolutionServiceTest.kt @@ -25,8 +25,8 @@ import org.junit.Assert import org.junit.Before import org.junit.Test import org.junit.runner.RunWith -import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintProperties -import org.onap.ccsdk.cds.blueprintsprocessor.core.BlueprintPropertyConfiguration +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertiesService +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertyConfiguration import org.onap.ccsdk.cds.blueprintsprocessor.core.api.data.ExecutionServiceInput import org.onap.ccsdk.cds.blueprintsprocessor.core.utils.PayloadUtils import org.onap.ccsdk.cds.blueprintsprocessor.db.BluePrintDBLibConfiguration @@ -61,7 +61,7 @@ import kotlin.test.assertTrue InputResourceResolutionProcessor::class, DefaultResourceResolutionProcessor::class, DatabaseResourceAssignmentProcessor::class, RestResourceResolutionProcessor::class, CapabilityResourceResolutionProcessor::class, - BlueprintPropertyConfiguration::class, BluePrintProperties::class, + BluePrintPropertyConfiguration::class, BluePrintPropertiesService::class, BluePrintDBLibConfiguration::class, BluePrintLoadConfiguration::class]) @TestPropertySource(locations = ["classpath:application-test.properties"]) @ComponentScan(basePackages = ["org.onap.ccsdk.cds.blueprintsprocessor", "org.onap.ccsdk.cds.controllerblueprints"]) diff --git a/ms/blueprintsprocessor/functions/resource-resolution/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/resource/resolution/mock/MockBlueprintResLibPropertyService.kt b/ms/blueprintsprocessor/functions/resource-resolution/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/resource/resolution/mock/MockBlueprintResLibPropertyService.kt index b79f48682..f64ba2bbd 100644 --- a/ms/blueprintsprocessor/functions/resource-resolution/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/resource/resolution/mock/MockBlueprintResLibPropertyService.kt +++ b/ms/blueprintsprocessor/functions/resource-resolution/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/resource/resolution/mock/MockBlueprintResLibPropertyService.kt @@ -15,11 +15,11 @@ */ package org.onap.ccsdk.cds.blueprintsprocessor.functions.resource.resolution.mock -import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintProperties +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertiesService import org.onap.ccsdk.cds.blueprintsprocessor.rest.RestClientProperties import org.onap.ccsdk.cds.blueprintsprocessor.rest.service.BluePrintRestLibPropertyService -class MockBluePrintRestLibPropertyService(bluePrintProperties: BluePrintProperties) : +class MockBluePrintRestLibPropertyService(bluePrintProperties: BluePrintPropertiesService) : BluePrintRestLibPropertyService(bluePrintProperties) { fun mockBlueprintWebClientService (selector: String): diff --git a/ms/blueprintsprocessor/functions/resource-resolution/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/resource/resolution/processor/DatabaseResourceResolutionProcessorTest.kt b/ms/blueprintsprocessor/functions/resource-resolution/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/resource/resolution/processor/DatabaseResourceResolutionProcessorTest.kt index e6cf05955..ac5ba3c46 100644 --- a/ms/blueprintsprocessor/functions/resource-resolution/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/resource/resolution/processor/DatabaseResourceResolutionProcessorTest.kt +++ b/ms/blueprintsprocessor/functions/resource-resolution/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/resource/resolution/processor/DatabaseResourceResolutionProcessorTest.kt @@ -19,11 +19,11 @@ import kotlinx.coroutines.runBlocking import org.junit.Test import org.junit.runner.RunWith import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintCoreConfiguration -import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintProperties -import org.onap.ccsdk.cds.blueprintsprocessor.core.BlueprintPropertiesService -import org.onap.ccsdk.cds.blueprintsprocessor.core.BlueprintPropertyConfiguration +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertiesService +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertyConfiguration import org.onap.ccsdk.cds.blueprintsprocessor.db.BluePrintDBLibConfiguration import org.onap.ccsdk.cds.blueprintsprocessor.db.primary.BluePrintDBLibPropertySevice +import org.onap.ccsdk.cds.blueprintsprocessor.db.primary.PrimaryDatabaseConfiguration import org.onap.ccsdk.cds.blueprintsprocessor.functions.resource.resolution.ResourceAssignmentRuntimeService import org.onap.ccsdk.cds.blueprintsprocessor.functions.resource.resolution.mock.MockBlueprintProcessorCatalogServiceImpl import org.onap.ccsdk.cds.blueprintsprocessor.functions.resource.resolution.mock.MockDatabaseConfiguration @@ -38,10 +38,10 @@ import org.springframework.test.context.junit4.SpringRunner import kotlin.test.assertNotNull @RunWith(SpringRunner::class) -@ContextConfiguration(classes = [DatabaseResourceAssignmentProcessor::class, BlueprintPropertyConfiguration::class, - BluePrintProperties::class, BluePrintDBLibPropertySevice::class, BluePrintDBLibConfiguration::class, +@ContextConfiguration(classes = [DatabaseResourceAssignmentProcessor::class, BluePrintPropertyConfiguration::class, + BluePrintPropertiesService::class, BluePrintDBLibPropertySevice::class, BluePrintDBLibConfiguration::class, BluePrintCoreConfiguration::class, MockDatabaseConfiguration::class, MockBlueprintProcessorCatalogServiceImpl::class, - BlueprintPropertiesService::class]) + BluePrintPropertiesService::class, PrimaryDatabaseConfiguration::class]) @TestPropertySource(locations = ["classpath:application-test.properties"]) class DatabaseResourceResolutionProcessorTest { diff --git a/ms/blueprintsprocessor/functions/resource-resolution/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/resource/resolution/processor/RestResourceResolutionProcessorTest.kt b/ms/blueprintsprocessor/functions/resource-resolution/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/resource/resolution/processor/RestResourceResolutionProcessorTest.kt index 2879342f6..1c0f33fcd 100644 --- a/ms/blueprintsprocessor/functions/resource-resolution/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/resource/resolution/processor/RestResourceResolutionProcessorTest.kt +++ b/ms/blueprintsprocessor/functions/resource-resolution/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/resource/resolution/processor/RestResourceResolutionProcessorTest.kt @@ -18,8 +18,8 @@ package org.onap.ccsdk.cds.blueprintsprocessor.functions.resource.resolution.pro import kotlinx.coroutines.runBlocking import org.junit.Test import org.junit.runner.RunWith -import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintProperties -import org.onap.ccsdk.cds.blueprintsprocessor.core.BlueprintPropertyConfiguration +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertiesService +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertyConfiguration import org.onap.ccsdk.cds.blueprintsprocessor.functions.resource.resolution.ResourceAssignmentRuntimeService import org.onap.ccsdk.cds.blueprintsprocessor.functions.resource.resolution.mock.MockBluePrintRestLibPropertyService import org.onap.ccsdk.cds.blueprintsprocessor.functions.resource.resolution.mock.MockRestResourceResolutionProcessor @@ -37,7 +37,7 @@ import kotlin.test.assertNotNull @RunWith(SpringRunner::class) @ContextConfiguration(classes = [MockRestResourceResolutionProcessor::class, MockBluePrintRestLibPropertyService::class, - BlueprintPropertyConfiguration::class, BluePrintProperties::class, RestClientProperties::class]) + BluePrintPropertyConfiguration::class, BluePrintPropertiesService::class, RestClientProperties::class]) @TestPropertySource(locations = ["classpath:application-test.properties"]) class RestResourceResolutionProcessorTest { @Autowired diff --git a/ms/blueprintsprocessor/functions/restconf-executor/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/restconf/executor/ComponentRestconfExecutorTest.kt b/ms/blueprintsprocessor/functions/restconf-executor/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/restconf/executor/ComponentRestconfExecutorTest.kt index 2b2b83e4c..0336ce958 100644 --- a/ms/blueprintsprocessor/functions/restconf-executor/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/restconf/executor/ComponentRestconfExecutorTest.kt +++ b/ms/blueprintsprocessor/functions/restconf-executor/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/restconf/executor/ComponentRestconfExecutorTest.kt @@ -22,45 +22,31 @@ import io.mockk.every import io.mockk.mockk import kotlinx.coroutines.runBlocking import org.junit.Test -import org.junit.runner.RunWith import org.onap.ccsdk.cds.blueprintsprocessor.core.api.data.ActionIdentifiers import org.onap.ccsdk.cds.blueprintsprocessor.core.api.data.CommonHeader import org.onap.ccsdk.cds.blueprintsprocessor.core.api.data.ExecutionServiceInput import org.onap.ccsdk.cds.blueprintsprocessor.core.api.data.StepData +import org.onap.ccsdk.cds.blueprintsprocessor.services.execution.ComponentFunctionScriptingService import org.onap.ccsdk.cds.blueprintsprocessor.services.execution.ComponentScriptExecutor import org.onap.ccsdk.cds.controllerblueprints.core.BluePrintConstants import org.onap.ccsdk.cds.controllerblueprints.core.asJsonPrimitive import org.onap.ccsdk.cds.controllerblueprints.core.service.BluePrintContext import org.onap.ccsdk.cds.controllerblueprints.core.service.DefaultBluePrintRuntimeService import org.onap.ccsdk.cds.controllerblueprints.core.utils.JacksonUtils -import org.springframework.beans.factory.annotation.Autowired -import org.springframework.boot.autoconfigure.EnableAutoConfiguration -import org.springframework.context.annotation.ComponentScan -import org.springframework.test.annotation.DirtiesContext -import org.springframework.test.context.TestPropertySource -import org.springframework.test.context.junit4.SpringRunner +import org.springframework.context.ApplicationContext import kotlin.test.assertNotNull -@RunWith(SpringRunner::class) -@EnableAutoConfiguration -@ComponentScan(basePackages = ["org.onap.ccsdk.cds.blueprintsprocessor", "org.onap.ccsdk.cds.controllerblueprints"]) -@DirtiesContext -@TestPropertySource(properties = -["server.port=9111", - "blueprintsprocessor.restconfEnabled=true", - "blueprintsprocessor.restclient.odlPrimary.type=basic-auth", - "blueprintsprocessor.restclient.odlPrimary.url=http://127.0.0.1:9111", - "blueprintsprocessor.restclient.odlPrimary.userId=sampleuser", - "blueprintsprocessor.restclient.odlPrimary.token=sampletoken"], - locations = ["classpath:application-test.properties"]) class ComponentRestconfExecutorTest { - @Autowired - lateinit var componentScriptExecutor: ComponentScriptExecutor - @Test fun `test Restconf Component Instance`() { runBlocking { + + val applicationContext = mockk<ApplicationContext>() + every { applicationContext.getBean(any()) } returns mockk() + val componentFunctionScriptingService = ComponentFunctionScriptingService(applicationContext, mockk()) + val componentScriptExecutor = ComponentScriptExecutor(componentFunctionScriptingService) + assertNotNull(componentScriptExecutor, "failed to get ComponentRestconfExecutor instance") val executionServiceInput = ExecutionServiceInput().apply { commonHeader = CommonHeader().apply { diff --git a/ms/blueprintsprocessor/modules/commons/db-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/db/BluePrintDBLibConfiguration.kt b/ms/blueprintsprocessor/modules/commons/db-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/db/BluePrintDBLibConfiguration.kt index 11abf7b2e..a7ad921de 100644 --- a/ms/blueprintsprocessor/modules/commons/db-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/db/BluePrintDBLibConfiguration.kt +++ b/ms/blueprintsprocessor/modules/commons/db-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/db/BluePrintDBLibConfiguration.kt @@ -16,23 +16,21 @@ package org.onap.ccsdk.cds.blueprintsprocessor.db -import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintProperties +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertiesService import org.onap.ccsdk.cds.blueprintsprocessor.db.primary.BluePrintDBLibPropertySevice import org.onap.ccsdk.cds.blueprintsprocessor.db.primary.PrimaryDBLibGenericService import org.onap.ccsdk.cds.controllerblueprints.core.service.BluePrintDependencyService import org.springframework.boot.context.properties.EnableConfigurationProperties import org.springframework.context.annotation.Bean -import org.springframework.context.annotation.ComponentScan import org.springframework.context.annotation.Configuration @Configuration -@ComponentScan @EnableConfigurationProperties -open class BluePrintDBLibConfiguration(private var bluePrintProperties: BluePrintProperties) { +open class BluePrintDBLibConfiguration(private var bluePrintPropertiesService: BluePrintPropertiesService) { @Bean("primary-database-properties") open fun getPrimaryProperties(): PrimaryDataSourceProperties { - return bluePrintProperties.propertyBeanType(DBLibConstants.PREFIX_DB, + return bluePrintPropertiesService.propertyBeanType(DBLibConstants.PREFIX_DB, PrimaryDataSourceProperties::class.java) } } diff --git a/ms/blueprintsprocessor/modules/commons/db-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/db/BluePrintDBLibData.kt b/ms/blueprintsprocessor/modules/commons/db-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/db/BluePrintDBLibData.kt index b1ac5cee4..fc43ce34d 100644 --- a/ms/blueprintsprocessor/modules/commons/db-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/db/BluePrintDBLibData.kt +++ b/ms/blueprintsprocessor/modules/commons/db-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/db/BluePrintDBLibData.kt @@ -22,7 +22,6 @@ open class DBDataSourceProperties { lateinit var username: String lateinit var password: String open lateinit var driverClassName: String - } open class PrimaryDataSourceProperties: DBDataSourceProperties() { diff --git a/ms/blueprintsprocessor/modules/commons/db-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/db/primary/BluePrintDBLibPropertyService.kt b/ms/blueprintsprocessor/modules/commons/db-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/db/primary/BluePrintDBLibPropertyService.kt index 2ae50424f..ff53de89f 100644 --- a/ms/blueprintsprocessor/modules/commons/db-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/db/primary/BluePrintDBLibPropertyService.kt +++ b/ms/blueprintsprocessor/modules/commons/db-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/db/primary/BluePrintDBLibPropertyService.kt @@ -17,14 +17,14 @@ package org.onap.ccsdk.cds.blueprintsprocessor.db.primary import com.fasterxml.jackson.databind.JsonNode -import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintProperties +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertiesService import org.onap.ccsdk.cds.blueprintsprocessor.db.* import org.onap.ccsdk.cds.controllerblueprints.core.BluePrintProcessorException import org.onap.ccsdk.cds.controllerblueprints.core.utils.JacksonUtils import org.springframework.stereotype.Service @Service -class BluePrintDBLibPropertySevice(private var bluePrintProperties: BluePrintProperties) { +class BluePrintDBLibPropertySevice(private var bluePrintPropertiesService: BluePrintPropertiesService) { fun JdbcTemplate(jsonNode: JsonNode): BluePrintDBLibGenericService { val dBConnetionProperties = dBDataSourceProperties(jsonNode) @@ -53,7 +53,7 @@ class BluePrintDBLibPropertySevice(private var bluePrintProperties: BluePrintPro } private fun dBDataSourceProperties(prefix: String): DBDataSourceProperties { - val type = bluePrintProperties.propertyBeanType("$prefix.type", String::class.java) + val type = bluePrintPropertiesService.propertyBeanType("$prefix.type", String::class.java) return when (type) { DBLibConstants.MARIA_DB -> { mariaDBConnectionProperties(prefix) @@ -91,15 +91,15 @@ class BluePrintDBLibPropertySevice(private var bluePrintProperties: BluePrintPro } private fun mySqlDBConnectionProperties(prefix: String): MySqlDataSourceProperties { - return bluePrintProperties.propertyBeanType(prefix, MySqlDataSourceProperties::class.java) + return bluePrintPropertiesService.propertyBeanType(prefix, MySqlDataSourceProperties::class.java) } private fun mariaDBConnectionProperties(prefix: String): MariaDataSourceProperties { - return bluePrintProperties.propertyBeanType(prefix, MariaDataSourceProperties::class.java) + return bluePrintPropertiesService.propertyBeanType(prefix, MariaDataSourceProperties::class.java) } private fun primaryDBConnectionProperties(prefix: String): PrimaryDataSourceProperties { - return bluePrintProperties.propertyBeanType(prefix, PrimaryDataSourceProperties::class.java) + return bluePrintPropertiesService.propertyBeanType(prefix, PrimaryDataSourceProperties::class.java) } }
\ No newline at end of file diff --git a/ms/blueprintsprocessor/modules/commons/db-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/db/primary/PrimaryDatabaseConfiguration.kt b/ms/blueprintsprocessor/modules/commons/db-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/db/primary/PrimaryDatabaseConfiguration.kt index a62867053..82b77da47 100644 --- a/ms/blueprintsprocessor/modules/commons/db-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/db/primary/PrimaryDatabaseConfiguration.kt +++ b/ms/blueprintsprocessor/modules/commons/db-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/db/primary/PrimaryDatabaseConfiguration.kt @@ -18,9 +18,10 @@ package org.onap.ccsdk.cds.blueprintsprocessor.db.primary import org.onap.ccsdk.cds.blueprintsprocessor.db.PrimaryDataSourceProperties import org.slf4j.LoggerFactory +import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty import org.springframework.context.annotation.Bean +import org.springframework.context.annotation.ComponentScan import org.springframework.context.annotation.Configuration -import org.springframework.context.annotation.Primary import org.springframework.data.jpa.repository.config.EnableJpaAuditing import org.springframework.data.jpa.repository.config.EnableJpaRepositories import org.springframework.jdbc.core.namedparam.NamedParameterJdbcTemplate @@ -33,6 +34,9 @@ import java.util.* import javax.sql.DataSource @Configuration +@ConditionalOnProperty(name = ["blueprintsprocessor.db.primary.defaultConfig"], havingValue = "true", + matchIfMissing = true) +@ComponentScan @EnableJpaRepositories( basePackages = ["org.onap.ccsdk.cds.blueprintsprocessor.*", "org.onap.ccsdk.cds.controllerblueprints.*"], @@ -41,9 +45,8 @@ import javax.sql.DataSource ) @EnableJpaAuditing open class PrimaryDatabaseConfiguration(private val primaryDataSourceProperties: PrimaryDataSourceProperties) { - val log = LoggerFactory.getLogger(PrimaryDatabaseConfiguration::class.java)!! + private val log = LoggerFactory.getLogger(PrimaryDatabaseConfiguration::class.java)!! - @Primary @Bean("primaryEntityManager") open fun primaryEntityManager(): LocalContainerEntityManagerFactoryBean { val em = LocalContainerEntityManagerFactoryBean() @@ -58,7 +61,6 @@ open class PrimaryDatabaseConfiguration(private val primaryDataSourceProperties: return em } - @Primary @Bean("primaryDataSource") open fun primaryDataSource(): DataSource { val dataSource = DriverManagerDataSource() @@ -69,7 +71,6 @@ open class PrimaryDatabaseConfiguration(private val primaryDataSourceProperties: return dataSource } - @Primary @Bean("primaryTransactionManager") open fun primaryTransactionManager(): PlatformTransactionManager { val transactionManager = JpaTransactionManager() diff --git a/ms/blueprintsprocessor/modules/commons/db-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/db/primary/repository/BlueprintModelSearchRepository.kt b/ms/blueprintsprocessor/modules/commons/db-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/db/primary/repository/BlueprintModelSearchRepository.kt index f5ef0740e..60ca1fec1 100644 --- a/ms/blueprintsprocessor/modules/commons/db-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/db/primary/repository/BlueprintModelSearchRepository.kt +++ b/ms/blueprintsprocessor/modules/commons/db-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/db/primary/repository/BlueprintModelSearchRepository.kt @@ -1,5 +1,6 @@ /* * Copyright © 2019 IBM. + * Modifications Copyright © 2019 Orange. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -59,4 +60,20 @@ interface BlueprintModelSearchRepository : JpaRepository<BlueprintModelSearch, L * @return Optional<BlueprintModelSearch> </BlueprintModelSearch> */ fun findByTagsContainingIgnoreCase(tags: String): List<BlueprintModelSearch> -}
\ No newline at end of file + + /** + * This is a findby some attributes method + * + * @author Shaaban Ebrahim + * + * @param updatedBy + * @param tags + * @param artifactName + * @param artifactVersion + * @param artifactType + * @return Optional<BlueprintModelSearch> + </BlueprintModelSearch> + */ + fun findByUpdatedByOrTagsOrOrArtifactNameOrOrArtifactVersionOrArtifactType(updatedBy: String, tags: String, artifactName: String, artifactVersion: String, + artifactType: String): List<BlueprintModelSearch> +} diff --git a/ms/blueprintsprocessor/modules/commons/db-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/db/service/BlueprintCatalogServiceImpl.kt b/ms/blueprintsprocessor/modules/commons/db-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/db/primary/service/BlueprintCatalogServiceImpl.kt index aef7c18a2..5700c2a46 100644 --- a/ms/blueprintsprocessor/modules/commons/db-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/db/service/BlueprintCatalogServiceImpl.kt +++ b/ms/blueprintsprocessor/modules/commons/db-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/db/primary/service/BlueprintCatalogServiceImpl.kt @@ -16,7 +16,7 @@ * limitations under the License. */ -package org.onap.ccsdk.cds.blueprintsprocessor.db.service +package org.onap.ccsdk.cds.blueprintsprocessor.db.primary.service import org.onap.ccsdk.cds.controllerblueprints.core.* import org.onap.ccsdk.cds.controllerblueprints.core.config.BluePrintLoadConfiguration diff --git a/ms/blueprintsprocessor/modules/commons/db-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/db/service/BlueprintProcessorCatalogServiceImpl.kt b/ms/blueprintsprocessor/modules/commons/db-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/db/primary/service/BlueprintProcessorCatalogServiceImpl.kt index 5d04ddfdf..3ba25d8de 100755 --- a/ms/blueprintsprocessor/modules/commons/db-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/db/service/BlueprintProcessorCatalogServiceImpl.kt +++ b/ms/blueprintsprocessor/modules/commons/db-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/db/primary/service/BlueprintProcessorCatalogServiceImpl.kt @@ -16,7 +16,7 @@ * limitations under the License. */ -package org.onap.ccsdk.cds.blueprintsprocessor.db.service +package org.onap.ccsdk.cds.blueprintsprocessor.db.primary.service import org.onap.ccsdk.cds.blueprintsprocessor.db.primary.domain.BlueprintModel import org.onap.ccsdk.cds.blueprintsprocessor.db.primary.domain.BlueprintModelContent diff --git a/ms/blueprintsprocessor/modules/commons/db-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/db/service/ControllerBlueprintCatalogServiceImpl.kt b/ms/blueprintsprocessor/modules/commons/db-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/db/service/ControllerBlueprintCatalogServiceImpl.kt deleted file mode 100755 index e7a8e31a7..000000000 --- a/ms/blueprintsprocessor/modules/commons/db-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/db/service/ControllerBlueprintCatalogServiceImpl.kt +++ /dev/null @@ -1,127 +0,0 @@ -/* - * Copyright © 2017-2018 AT&T Intellectual Property. - * Modifications Copyright © 2019 Bell Canada. - * Modifications Copyright © 2019 IBM. - * - * 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. - */ - -package org.onap.ccsdk.cds.blueprintsprocessor.db.service - -import org.onap.ccsdk.cds.blueprintsprocessor.db.primary.domain.BlueprintModel -import org.onap.ccsdk.cds.blueprintsprocessor.db.primary.domain.BlueprintModelContent -import org.onap.ccsdk.cds.blueprintsprocessor.db.primary.repository.BlueprintModelRepository -import org.onap.ccsdk.cds.controllerblueprints.core.* -import org.onap.ccsdk.cds.controllerblueprints.core.common.ApplicationConstants -import org.onap.ccsdk.cds.controllerblueprints.core.config.BluePrintLoadConfiguration -import org.onap.ccsdk.cds.controllerblueprints.core.data.ErrorCode -import org.onap.ccsdk.cds.controllerblueprints.core.interfaces.BluePrintValidatorService -import org.onap.ccsdk.cds.controllerblueprints.core.scripts.BluePrintCompileCache -import org.onap.ccsdk.cds.controllerblueprints.core.utils.BluePrintFileUtils -import org.slf4j.LoggerFactory -import org.springframework.dao.DataIntegrityViolationException -import org.springframework.stereotype.Service -import java.io.File -import java.nio.file.Files -import java.nio.file.Path -import java.util.* - -//TODO("Duplicate : Merge BlueprintProcessorCatalogServiceImpl and ControllerBlueprintCatalogServiceImpl") -/** - * Similar implementation in [org.onap.ccsdk.cds.blueprintsprocessor.db.BlueprintProcessorCatalogServiceImpl] - */ -@Service("controllerBlueprintsCatalogService") -class ControllerBlueprintCatalogServiceImpl(bluePrintDesignTimeValidatorService: BluePrintValidatorService, - private val bluePrintLoadConfiguration: BluePrintLoadConfiguration, - private val blueprintModelRepository: BlueprintModelRepository) - : BlueprintCatalogServiceImpl(bluePrintLoadConfiguration, bluePrintDesignTimeValidatorService) { - - - private val log = LoggerFactory.getLogger(ControllerBlueprintCatalogServiceImpl::class.toString()) - - init { - log.info("BlueprintProcessorCatalogServiceImpl initialized") - } - - override suspend fun delete(name: String, version: String) { - // Cleaning Deployed Blueprint - deleteDir(bluePrintLoadConfiguration.blueprintDeployPath, name, version) - // Cleaning Data Base - blueprintModelRepository.deleteByArtifactNameAndArtifactVersion(name, version) - } - - override suspend fun get(name: String, version: String, extract: Boolean): Path? { - val path = if (extract) { - normalizedPath(bluePrintLoadConfiguration.blueprintDeployPath, name, version) - } else { - normalizedPath(bluePrintLoadConfiguration.blueprintArchivePath, UUID.randomUUID().toString(), "cba.zip") - } - blueprintModelRepository.findByArtifactNameAndArtifactVersion(name, version)?.also { - it.blueprintModelContent.run { - path.toFile().writeBytes(this!!.content!!).let { - return path - } - } - } - return null - } - - override suspend fun save(metadata: MutableMap<String, String>, archiveFile: File) { - - val artifactName = metadata[BluePrintConstants.METADATA_TEMPLATE_NAME] - val artifactVersion = metadata[BluePrintConstants.METADATA_TEMPLATE_VERSION] - - check(archiveFile.isFile && !archiveFile.isDirectory) { - throw BluePrintException("Not a valid Archive file(${archiveFile.absolutePath})") - } - - // cleanup up deploy folder for the Blueprint - val blueprintDeploy = normalizedPathName(bluePrintLoadConfiguration.blueprintDeployPath, - artifactName, artifactVersion) - val cacheKey = BluePrintFileUtils.compileCacheKey(blueprintDeploy) - BluePrintCompileCache.cleanClassLoader(cacheKey) - - blueprintModelRepository.findByArtifactNameAndArtifactVersion(artifactName!!, artifactVersion!!)?.let { - log.info("Overwriting blueprint model :$artifactName::$artifactVersion") - blueprintModelRepository.deleteByArtifactNameAndArtifactVersion(artifactName, artifactVersion) - } - - val blueprintModel = BlueprintModel() - blueprintModel.id = metadata[BluePrintConstants.PROPERTY_BLUEPRINT_PROCESS_ID] - blueprintModel.artifactType = ApplicationConstants.ASDC_ARTIFACT_TYPE_SDNC_MODEL - blueprintModel.published = metadata[BluePrintConstants.PROPERTY_BLUEPRINT_VALID] - ?: BluePrintConstants.FLAG_N - blueprintModel.artifactName = artifactName - blueprintModel.artifactVersion = artifactVersion - blueprintModel.updatedBy = metadata[BluePrintConstants.METADATA_TEMPLATE_AUTHOR]!! - blueprintModel.tags = metadata[BluePrintConstants.METADATA_TEMPLATE_TAGS]!! - blueprintModel.artifactDescription = "Controller Blueprint for $artifactName:$artifactVersion" - - val blueprintModelContent = BlueprintModelContent() - blueprintModelContent.id = metadata[BluePrintConstants.PROPERTY_BLUEPRINT_PROCESS_ID] - blueprintModelContent.contentType = "CBA_ZIP" - blueprintModelContent.name = "$artifactName:$artifactVersion" - blueprintModelContent.description = "$artifactName:$artifactVersion CBA Zip Content" - blueprintModelContent.content = Files.readAllBytes(archiveFile.toPath()) - blueprintModelContent.blueprintModel = blueprintModel - // Set the Blueprint Model Content into blueprintModel - blueprintModel.blueprintModelContent = blueprintModelContent - - try { - blueprintModelRepository.saveAndFlush(blueprintModel) - } catch (ex: DataIntegrityViolationException) { - throw BluePrintException(ErrorCode.CONFLICT_ADDING_RESOURCE.value, "The blueprint entry " + - "is already exist in database: ${ex.message}", ex) - } - } -}
\ No newline at end of file diff --git a/ms/blueprintsprocessor/modules/commons/db-lib/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/db/BlueprintProcessorCatalogServiceImplTest.kt b/ms/blueprintsprocessor/modules/commons/db-lib/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/db/BlueprintProcessorCatalogServiceImplTest.kt index 8058dc26e..d912d8eae 100644 --- a/ms/blueprintsprocessor/modules/commons/db-lib/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/db/BlueprintProcessorCatalogServiceImplTest.kt +++ b/ms/blueprintsprocessor/modules/commons/db-lib/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/db/BlueprintProcessorCatalogServiceImplTest.kt @@ -22,8 +22,8 @@ import org.junit.Test import org.junit.runner.RunWith import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintCoreConfiguration import org.onap.ccsdk.cds.blueprintsprocessor.db.mock.MockBlueprintProcessorCatalogServiceImpl -import org.onap.ccsdk.cds.blueprintsprocessor.db.service.BlueprintCatalogServiceImpl -import org.onap.ccsdk.cds.blueprintsprocessor.db.service.BlueprintProcessorCatalogServiceImpl +import org.onap.ccsdk.cds.blueprintsprocessor.db.primary.service.BlueprintCatalogServiceImpl +import org.onap.ccsdk.cds.blueprintsprocessor.db.primary.service.BlueprintProcessorCatalogServiceImpl import org.onap.ccsdk.cds.controllerblueprints.core.BluePrintConstants import org.onap.ccsdk.cds.controllerblueprints.core.deleteDir import org.onap.ccsdk.cds.controllerblueprints.core.normalizedFile diff --git a/ms/blueprintsprocessor/modules/commons/db-lib/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/db/primary/PrimaryDatabaseConfigurationTest.kt b/ms/blueprintsprocessor/modules/commons/db-lib/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/db/primary/PrimaryDatabaseConfigurationTest.kt index b4a21780b..2ab1c5d48 100644 --- a/ms/blueprintsprocessor/modules/commons/db-lib/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/db/primary/PrimaryDatabaseConfigurationTest.kt +++ b/ms/blueprintsprocessor/modules/commons/db-lib/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/db/primary/PrimaryDatabaseConfigurationTest.kt @@ -18,8 +18,8 @@ package org.onap.ccsdk.cds.blueprintsprocessor.db.primary import org.junit.Test import org.junit.runner.RunWith -import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintProperties -import org.onap.ccsdk.cds.blueprintsprocessor.core.BlueprintPropertyConfiguration +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertiesService +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertyConfiguration import org.onap.ccsdk.cds.blueprintsprocessor.db.BluePrintDBLibConfiguration import org.onap.ccsdk.cds.controllerblueprints.core.config.BluePrintLoadConfiguration import org.springframework.beans.factory.annotation.Autowired @@ -32,7 +32,7 @@ import javax.sql.DataSource import kotlin.test.assertNotNull @RunWith(SpringRunner::class) -@ContextConfiguration(classes = [BlueprintPropertyConfiguration::class, BluePrintProperties::class, +@ContextConfiguration(classes = [BluePrintPropertyConfiguration::class, BluePrintPropertiesService::class, BluePrintDBLibConfiguration::class, BluePrintLoadConfiguration::class]) @TestPropertySource(locations = ["classpath:application-test.properties"]) @ComponentScan(basePackages = ["org.onap.ccsdk.cds.blueprintsprocessor", "org.onap.ccsdk.cds.controllerblueprints"]) diff --git a/ms/blueprintsprocessor/modules/commons/db-lib/src/test/resources/application-test.properties b/ms/blueprintsprocessor/modules/commons/db-lib/src/test/resources/application-test.properties index 90cf03517..124e844cb 100644 --- a/ms/blueprintsprocessor/modules/commons/db-lib/src/test/resources/application-test.properties +++ b/ms/blueprintsprocessor/modules/commons/db-lib/src/test/resources/application-test.properties @@ -14,6 +14,8 @@ # See the License for the specific language governing permissions and # limitations under the License. # +blueprintsprocessor.db.primary.defaultConfig=true + blueprintsprocessor.db.url=jdbc:h2:mem:testdb;DB_CLOSE_DELAY=-1 blueprintsprocessor.db.username=sa blueprintsprocessor.db.password= diff --git a/ms/blueprintsprocessor/modules/commons/dmaap-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/dmaap/BluePrintDmaapLibPropertyService.kt b/ms/blueprintsprocessor/modules/commons/dmaap-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/dmaap/BluePrintDmaapLibPropertyService.kt index 8604d8880..cde4987ff 100644 --- a/ms/blueprintsprocessor/modules/commons/dmaap-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/dmaap/BluePrintDmaapLibPropertyService.kt +++ b/ms/blueprintsprocessor/modules/commons/dmaap-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/dmaap/BluePrintDmaapLibPropertyService.kt @@ -21,7 +21,7 @@ package org.onap.ccsdk.cds.blueprintsprocessor.dmaap import com.fasterxml.jackson.databind.JsonNode -import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintProperties +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertiesService import org.onap.ccsdk.cds.blueprintsprocessor.dmaap.DmaapLibConstants.Companion.SERVICE_BLUEPRINT_DMAAP_LIB_PROPERTY import org.onap.ccsdk.cds.blueprintsprocessor.dmaap.DmaapLibConstants.Companion.TYPE_HTTP_AAF_AUTH import org.onap.ccsdk.cds.blueprintsprocessor.dmaap.DmaapLibConstants.Companion.TYPE_HTTP_NO_AUTH @@ -36,7 +36,7 @@ import org.springframework.core.env.ConfigurableEnvironment import org.springframework.core.env.Environment import org.springframework.core.io.support.ResourcePropertySource import org.springframework.stereotype.Service -import java.util.Properties +import java.util.* /** * Representation of DMAAP lib property service to load the properties @@ -46,15 +46,14 @@ import java.util.Properties @Service(SERVICE_BLUEPRINT_DMAAP_LIB_PROPERTY) @Configuration @PropertySources(PropertySource("classpath:event.properties")) -open class BluePrintDmaapLibPropertyService(private var bluePrintProperties: - BluePrintProperties) { +open class BluePrintDmaapLibPropertyService(private var bluePrintPropertiesService: BluePrintPropertiesService) { /** * Static variable for logging. */ companion object { var log = LoggerFactory.getLogger( - BluePrintDmaapLibPropertyService::class.java)!! + BluePrintDmaapLibPropertyService::class.java)!! } /** @@ -90,20 +89,20 @@ open class BluePrintDmaapLibPropertyService(private var bluePrintProperties: * requires. */ fun dmaapClientProperties(prefix: String): DmaapClientProperties { - val type = bluePrintProperties.propertyBeanType( - "$prefix.type", String::class.java) - val clientProps : DmaapClientProperties + val type = bluePrintPropertiesService.propertyBeanType( + "$prefix.type", String::class.java) + val clientProps: DmaapClientProperties when (type) { TYPE_HTTP_NO_AUTH -> { - clientProps = bluePrintProperties.propertyBeanType( - prefix, HttpNoAuthDmaapClientProperties::class.java) + clientProps = bluePrintPropertiesService.propertyBeanType( + prefix, HttpNoAuthDmaapClientProperties::class.java) clientProps.props = parseEventProps() } TYPE_HTTP_AAF_AUTH -> { - clientProps = bluePrintProperties.propertyBeanType( - prefix, AafAuthDmaapClientProperties::class.java) + clientProps = bluePrintPropertiesService.propertyBeanType( + prefix, AafAuthDmaapClientProperties::class.java) clientProps.props = parseEventProps() } @@ -121,18 +120,18 @@ open class BluePrintDmaapLibPropertyService(private var bluePrintProperties: */ fun dmaapClientProperties(jsonNode: JsonNode): DmaapClientProperties { val type = jsonNode.get("type").textValue() - val clientProps : DmaapClientProperties + val clientProps: DmaapClientProperties when (type) { TYPE_HTTP_NO_AUTH -> { clientProps = JacksonUtils.readValue(jsonNode, - HttpNoAuthDmaapClientProperties::class.java)!! + HttpNoAuthDmaapClientProperties::class.java)!! clientProps.props = parseEventProps() } TYPE_HTTP_AAF_AUTH -> { clientProps = JacksonUtils.readValue(jsonNode, - AafAuthDmaapClientProperties::class.java)!! + AafAuthDmaapClientProperties::class.java)!! clientProps.props = parseEventProps() } @@ -172,7 +171,7 @@ open class BluePrintDmaapLibPropertyService(private var bluePrintProperties: private fun parseEventProps(): Properties { val prodProps = Properties() val proProps = (env as ConfigurableEnvironment).propertySources.get( - "class path resource [event.properties]") + "class path resource [event.properties]") if (proProps != null) { val entries = (proProps as ResourcePropertySource).source.entries diff --git a/ms/blueprintsprocessor/modules/commons/dmaap-lib/src/test/kotlin/org/ccsdk/cds/blueprintprocessor/dmaap/TestDmaapEventPublisher.kt b/ms/blueprintsprocessor/modules/commons/dmaap-lib/src/test/kotlin/org/ccsdk/cds/blueprintprocessor/dmaap/TestDmaapEventPublisher.kt index 65d877518..4e91d59f9 100644 --- a/ms/blueprintsprocessor/modules/commons/dmaap-lib/src/test/kotlin/org/ccsdk/cds/blueprintprocessor/dmaap/TestDmaapEventPublisher.kt +++ b/ms/blueprintsprocessor/modules/commons/dmaap-lib/src/test/kotlin/org/ccsdk/cds/blueprintprocessor/dmaap/TestDmaapEventPublisher.kt @@ -23,8 +23,8 @@ package org.ccsdk.apps.blueprintprocessor.dmaap import com.fasterxml.jackson.databind.ObjectMapper import org.junit.Test import org.junit.runner.RunWith -import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintProperties -import org.onap.ccsdk.cds.blueprintsprocessor.core.BlueprintPropertyConfiguration +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertiesService +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertyConfiguration import org.onap.ccsdk.cds.blueprintsprocessor.dmaap.BluePrintDmaapLibConfiguration import org.onap.ccsdk.cds.blueprintsprocessor.dmaap.BluePrintDmaapLibPropertyService import org.springframework.beans.factory.annotation.Autowired @@ -50,7 +50,7 @@ import kotlin.test.assertNotNull @EnableAutoConfiguration(exclude = [DataSourceAutoConfiguration::class]) @SpringBootTest(webEnvironment = SpringBootTest.WebEnvironment.DEFINED_PORT) @ContextConfiguration(classes = [BluePrintDmaapLibConfiguration::class, TestController::class, - BlueprintPropertyConfiguration::class, BluePrintProperties::class]) + BluePrintPropertyConfiguration::class, BluePrintPropertiesService::class]) @TestPropertySource(properties = ["server.port=9111", "blueprintsprocessor.dmaapclient.aai.topic=cds_aai", "blueprintsprocessor.dmaapclient.aai.type=HTTPNOAUTH", diff --git a/ms/blueprintsprocessor/modules/commons/grpc-lib/pom.xml b/ms/blueprintsprocessor/modules/commons/grpc-lib/pom.xml index 15cabb260..052b81c29 100644 --- a/ms/blueprintsprocessor/modules/commons/grpc-lib/pom.xml +++ b/ms/blueprintsprocessor/modules/commons/grpc-lib/pom.xml @@ -33,10 +33,6 @@ <dependencies> <dependency> <groupId>org.onap.ccsdk.cds.controllerblueprints</groupId> - <artifactId>blueprint-proto</artifactId> - </dependency> - <dependency> - <groupId>org.onap.ccsdk.cds.controllerblueprints</groupId> <artifactId>blueprint-core</artifactId> </dependency> <dependency> diff --git a/ms/blueprintsprocessor/modules/commons/grpc-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/grpc/service/BluePrintGrpcLibPropertyService.kt b/ms/blueprintsprocessor/modules/commons/grpc-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/grpc/service/BluePrintGrpcLibPropertyService.kt index f4933a3ad..fbc9ddd86 100644 --- a/ms/blueprintsprocessor/modules/commons/grpc-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/grpc/service/BluePrintGrpcLibPropertyService.kt +++ b/ms/blueprintsprocessor/modules/commons/grpc-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/grpc/service/BluePrintGrpcLibPropertyService.kt @@ -18,7 +18,7 @@ package org.onap.ccsdk.cds.blueprintsprocessor.grpc.service import com.fasterxml.jackson.databind.JsonNode -import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintProperties +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertiesService import org.onap.ccsdk.cds.blueprintsprocessor.grpc.* import org.onap.ccsdk.cds.controllerblueprints.core.BluePrintProcessorException import org.onap.ccsdk.cds.controllerblueprints.core.returnNullIfMissing @@ -26,7 +26,7 @@ import org.onap.ccsdk.cds.controllerblueprints.core.utils.JacksonUtils import org.springframework.stereotype.Service @Service(GRPCLibConstants.SERVICE_BLUEPRINT_GRPC_LIB_PROPERTY) -open class BluePrintGrpcLibPropertyService(private var bluePrintProperties: BluePrintProperties) { +open class BluePrintGrpcLibPropertyService(private var bluePrintPropertiesService: BluePrintPropertiesService) { /** GRPC Server Lib Property Service */ fun grpcServerProperties(jsonNode: JsonNode): GrpcServerProperties { @@ -44,7 +44,7 @@ open class BluePrintGrpcLibPropertyService(private var bluePrintProperties: Blue } fun grpcServerProperties(prefix: String): GrpcServerProperties { - val type = bluePrintProperties.propertyBeanType( + val type = bluePrintPropertiesService.propertyBeanType( "$prefix.type", String::class.java) return when (type) { GRPCLibConstants.TYPE_TOKEN_AUTH -> { @@ -60,11 +60,11 @@ open class BluePrintGrpcLibPropertyService(private var bluePrintProperties: Blue } private fun tokenAuthGrpcServerProperties(prefix: String): TokenAuthGrpcServerProperties { - return bluePrintProperties.propertyBeanType(prefix, TokenAuthGrpcServerProperties::class.java) + return bluePrintPropertiesService.propertyBeanType(prefix, TokenAuthGrpcServerProperties::class.java) } private fun tlsAuthGrpcServerProperties(prefix: String): TLSAuthGrpcServerProperties { - return bluePrintProperties.propertyBeanType(prefix, TLSAuthGrpcServerProperties::class.java) + return bluePrintPropertiesService.propertyBeanType(prefix, TLSAuthGrpcServerProperties::class.java) } /** GRPC Client Lib Property Service */ @@ -101,7 +101,7 @@ open class BluePrintGrpcLibPropertyService(private var bluePrintProperties: Blue } fun grpcClientProperties(prefix: String): GrpcClientProperties { - val type = bluePrintProperties.propertyBeanType( + val type = bluePrintPropertiesService.propertyBeanType( "$prefix.type", String::class.java) return when (type) { GRPCLibConstants.TYPE_TOKEN_AUTH -> { @@ -139,14 +139,14 @@ open class BluePrintGrpcLibPropertyService(private var bluePrintProperties: Blue } private fun tokenAuthGrpcClientProperties(prefix: String): TokenAuthGrpcClientProperties { - return bluePrintProperties.propertyBeanType(prefix, TokenAuthGrpcClientProperties::class.java) + return bluePrintPropertiesService.propertyBeanType(prefix, TokenAuthGrpcClientProperties::class.java) } private fun tlsAuthGrpcClientProperties(prefix: String): TLSAuthGrpcClientProperties { - return bluePrintProperties.propertyBeanType(prefix, TLSAuthGrpcClientProperties::class.java) + return bluePrintPropertiesService.propertyBeanType(prefix, TLSAuthGrpcClientProperties::class.java) } private fun basicAuthGrpcClientProperties(prefix: String): BasicAuthGrpcClientProperties { - return bluePrintProperties.propertyBeanType(prefix, BasicAuthGrpcClientProperties::class.java) + return bluePrintPropertiesService.propertyBeanType(prefix, BasicAuthGrpcClientProperties::class.java) } }
\ No newline at end of file diff --git a/ms/blueprintsprocessor/modules/commons/grpc-lib/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/grpc/service/BluePrintGrpcLibPropertyServiceTest.kt b/ms/blueprintsprocessor/modules/commons/grpc-lib/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/grpc/service/BluePrintGrpcLibPropertyServiceTest.kt index b7ddc1569..e4bfd5d7c 100644 --- a/ms/blueprintsprocessor/modules/commons/grpc-lib/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/grpc/service/BluePrintGrpcLibPropertyServiceTest.kt +++ b/ms/blueprintsprocessor/modules/commons/grpc-lib/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/grpc/service/BluePrintGrpcLibPropertyServiceTest.kt @@ -21,8 +21,8 @@ import com.fasterxml.jackson.databind.JsonNode import com.fasterxml.jackson.databind.ObjectMapper import org.junit.Test import org.junit.runner.RunWith -import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintProperties -import org.onap.ccsdk.cds.blueprintsprocessor.core.BlueprintPropertyConfiguration +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertiesService +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertyConfiguration import org.onap.ccsdk.cds.blueprintsprocessor.grpc.* import org.onap.ccsdk.cds.controllerblueprints.core.jsonAsJsonType import org.springframework.beans.factory.annotation.Autowired @@ -35,7 +35,7 @@ import kotlin.test.assertTrue @RunWith(SpringRunner::class) @ContextConfiguration(classes = [BluePrintGrpcLibConfiguration::class, - BlueprintPropertyConfiguration::class, BluePrintProperties::class]) + BluePrintPropertyConfiguration::class, BluePrintPropertiesService::class]) @TestPropertySource(properties = ["blueprintsprocessor.grpcclient.sample.type=basic-auth", "blueprintsprocessor.grpcclient.sample.host=127.0.0.1", diff --git a/ms/blueprintsprocessor/modules/commons/message-lib/pom.xml b/ms/blueprintsprocessor/modules/commons/message-lib/pom.xml index f92a8f45a..8d08ae838 100644 --- a/ms/blueprintsprocessor/modules/commons/message-lib/pom.xml +++ b/ms/blueprintsprocessor/modules/commons/message-lib/pom.xml @@ -42,6 +42,19 @@ <artifactId>spring-kafka</artifactId> </dependency> <dependency> + <groupId>org.apache.kafka</groupId> + <artifactId>kafka-streams</artifactId> + </dependency> + <dependency> + <groupId>org.apache.kafka</groupId> + <artifactId>kafka-clients</artifactId> + </dependency> + <dependency> + <groupId>org.apache.kafka</groupId> + <artifactId>kafka-streams-test-utils</artifactId> + <scope>test</scope> + </dependency> + <dependency> <groupId>org.springframework.kafka</groupId> <artifactId>spring-kafka-test</artifactId> <scope>test</scope> diff --git a/ms/blueprintsprocessor/modules/commons/message-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/message/BluePrintMessageLibConfiguration.kt b/ms/blueprintsprocessor/modules/commons/message-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/message/BluePrintMessageLibConfiguration.kt index 27a444bdc..ecffa280f 100644 --- a/ms/blueprintsprocessor/modules/commons/message-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/message/BluePrintMessageLibConfiguration.kt +++ b/ms/blueprintsprocessor/modules/commons/message-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/message/BluePrintMessageLibConfiguration.kt @@ -1,5 +1,6 @@ /* * Copyright © 2019 IBM. + * Modifications Copyright © 2018-2019 AT&T Intellectual Property. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -62,5 +63,6 @@ class MessageLibConstants { const val PROPERTY_MESSAGE_CONSUMER_PREFIX = "blueprintsprocessor.messageconsumer." const val PROPERTY_MESSAGE_PRODUCER_PREFIX = "blueprintsprocessor.messageproducer." const val TYPE_KAFKA_BASIC_AUTH = "kafka-basic-auth" + const val TYPE_KAFKA_STREAMS_BASIC_AUTH = "kafka-streams-basic-auth" } }
\ No newline at end of file diff --git a/ms/blueprintsprocessor/modules/commons/message-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/message/BluePrintMessageLibData.kt b/ms/blueprintsprocessor/modules/commons/message-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/message/BluePrintMessageLibData.kt index 184e85b70..d0c3d5ae1 100644 --- a/ms/blueprintsprocessor/modules/commons/message-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/message/BluePrintMessageLibData.kt +++ b/ms/blueprintsprocessor/modules/commons/message-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/message/BluePrintMessageLibData.kt @@ -17,6 +17,8 @@ package org.onap.ccsdk.cds.blueprintsprocessor.message +import org.apache.kafka.streams.StreamsConfig + /** Producer Properties **/ open class MessageProducerProperties @@ -25,12 +27,27 @@ open class KafkaBasicAuthMessageProducerProperties : MessageProducerProperties() lateinit var bootstrapServers: String var topic: String? = null var clientId: String? = null + // strongest producing guarantee + var acks: String = "all" + var retries: Int = 0 + // ensure we don't push duplicates + var enableIdempotence: Boolean = true } /** Consumer Properties **/ open class MessageConsumerProperties +open class KafkaStreamsConsumerProperties : MessageConsumerProperties() { + lateinit var bootstrapServers: String + lateinit var applicationId: String + lateinit var topic: String + var autoOffsetReset: String = "latest" + var processingGuarantee: String = StreamsConfig.EXACTLY_ONCE +} + +open class KafkaStreamsBasicAuthConsumerProperties : KafkaStreamsConsumerProperties() + open class KafkaMessageConsumerProperties : MessageConsumerProperties() { lateinit var bootstrapServers: String lateinit var groupId: String diff --git a/ms/blueprintsprocessor/modules/commons/message-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/message/kafka/AbstractKafkaTopologyComponents.kt b/ms/blueprintsprocessor/modules/commons/message-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/message/kafka/AbstractKafkaTopologyComponents.kt new file mode 100644 index 000000000..4c6c0acdd --- /dev/null +++ b/ms/blueprintsprocessor/modules/commons/message-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/message/kafka/AbstractKafkaTopologyComponents.kt @@ -0,0 +1,65 @@ +/* + * Copyright © 2018-2019 AT&T Intellectual Property. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.message.kafka + +import kotlinx.coroutines.Dispatchers +import kotlinx.coroutines.runBlocking +import org.apache.kafka.streams.processor.Processor +import org.apache.kafka.streams.processor.ProcessorContext +import org.apache.kafka.streams.processor.Punctuator +import org.onap.ccsdk.cds.controllerblueprints.core.logger + +/** CDS Kafka Stream Processor abstract class to implement */ +abstract class AbstractBluePrintMessageProcessor<K, V> : Processor<K, V> { + + private val log = logger(AbstractBluePrintMessageProcessor::class) + + lateinit var processorContext: ProcessorContext + + + override fun process(key: K, value: V) = runBlocking(Dispatchers.IO) { + try { + processNB(key, value) + } catch (e: Exception) { + log.error("failed in processor(${this.javaClass.simpleName}) message(${this.javaClass.simpleName} :", e) + } + } + + override fun init(context: ProcessorContext) { + log.info("initializing processor (${this.javaClass.simpleName})") + this.processorContext = context + + } + + override fun close() { + log.info("closing processor (${this.javaClass.simpleName})") + } + + abstract suspend fun processNB(key: K, value: V) +} + +/** CDS Kafka Stream Punctuator abstract class to implement */ +abstract class AbstractBluePrintMessagePunctuator : Punctuator { + lateinit var processorContext: ProcessorContext + + + override fun punctuate(timestamp: Long) = runBlocking(Dispatchers.IO) { + punctuateNB(timestamp) + } + + abstract suspend fun punctuateNB(timestamp: Long) +}
\ No newline at end of file diff --git a/ms/blueprintsprocessor/modules/commons/message-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/message/kafka/KafkaJDBCStores.kt b/ms/blueprintsprocessor/modules/commons/message-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/message/kafka/KafkaJDBCStores.kt new file mode 100644 index 000000000..86ccd74a2 --- /dev/null +++ b/ms/blueprintsprocessor/modules/commons/message-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/message/kafka/KafkaJDBCStores.kt @@ -0,0 +1,143 @@ +/* + * Copyright © 2018-2019 AT&T Intellectual Property. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.message.kafka + +/* +import org.apache.kafka.streams.processor.ProcessorContext +import org.apache.kafka.streams.processor.StateStore +import org.apache.kafka.streams.state.StoreBuilder +import org.apache.kafka.streams.state.StoreSupplier +import org.onap.ccsdk.cds.blueprintsprocessor.db.BluePrintDBLibGenericService +import org.onap.ccsdk.cds.blueprintsprocessor.db.primaryDBLibGenericService +import org.onap.ccsdk.cds.controllerblueprints.core.logger +import org.onap.ccsdk.cds.controllerblueprints.core.service.BluePrintDependencyService +import java.util.* + + +class KafkaJDBCKeyStoreSupplier(private val name: String) : StoreSupplier<KafkaJDBCStore> { + + override fun get(): KafkaJDBCStore { + // Get the DBLibGenericService Instance + val bluePrintDBLibGenericService = BluePrintDependencyService.primaryDBLibGenericService() + return KafkaJDBCStoreImpl(name, bluePrintDBLibGenericService) + } + + override fun name(): String { + return name + } + + override fun metricsScope(): String { + return "jdbc-state" + } +} + +class KafkaJDBCKeyStoreBuilder(private val storeSupplier: KafkaJDBCKeyStoreSupplier) + : StoreBuilder<KafkaJDBCStore> { + + private var logConfig: MutableMap<String, String> = HashMap() + private var enableCaching: Boolean = false + private var enableLogging = true + + override fun logConfig(): MutableMap<String, String> { + return logConfig + } + + override fun withCachingDisabled(): StoreBuilder<KafkaJDBCStore> { + enableCaching = false + return this + } + + override fun loggingEnabled(): Boolean { + return enableLogging + } + + override fun withLoggingDisabled(): StoreBuilder<KafkaJDBCStore> { + enableLogging = false + return this + } + + override fun withCachingEnabled(): StoreBuilder<KafkaJDBCStore> { + enableCaching = true + return this + } + + override fun withLoggingEnabled(config: MutableMap<String, String>?): StoreBuilder<KafkaJDBCStore> { + enableLogging = true + return this + } + + override fun name(): String { + return "KafkaJDBCKeyStoreBuilder" + } + + override fun build(): KafkaJDBCStore { + return storeSupplier.get() + } +} + +interface KafkaJDBCStore : StateStore { + + suspend fun query(sql: String, params: Map<String, Any>): List<Map<String, Any>> + + suspend fun update(sql: String, params: Map<String, Any>): Int +} + + +class KafkaJDBCStoreImpl(private val name: String, + private val bluePrintDBLibGenericService: BluePrintDBLibGenericService) + : KafkaJDBCStore { + + private val log = logger(KafkaJDBCStoreImpl::class) + + override fun isOpen(): Boolean { + log.info("isOpen...") + return true + } + + override fun init(context: ProcessorContext, root: StateStore) { + log.info("init...") + } + + override fun flush() { + log.info("flush...") + } + + override fun close() { + log.info("Close...") + } + + override fun name(): String { + return name + } + + override fun persistent(): Boolean { + return true + } + + override suspend fun query(sql: String, params: Map<String, Any>): List<Map<String, Any>> { + log.info("Query : $sql") + log.info("Params : $params") + return bluePrintDBLibGenericService.query(sql, params) + } + + override suspend fun update(sql: String, params: Map<String, Any>): Int { + log.info("Query : $sql") + log.info("Params : $params") + return bluePrintDBLibGenericService.update(sql, params) + } +} +*/ diff --git a/ms/blueprintsprocessor/modules/commons/message-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/message/service/BluePrintMessageLibPropertyService.kt b/ms/blueprintsprocessor/modules/commons/message-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/message/service/BluePrintMessageLibPropertyService.kt index 7c56ea432..97da7285d 100644 --- a/ms/blueprintsprocessor/modules/commons/message-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/message/service/BluePrintMessageLibPropertyService.kt +++ b/ms/blueprintsprocessor/modules/commons/message-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/message/service/BluePrintMessageLibPropertyService.kt @@ -1,5 +1,6 @@ /* * Copyright © 2019 IBM. + * Modifications Copyright © 2018-2019 AT&T Intellectual Property. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -17,14 +18,14 @@ package org.onap.ccsdk.cds.blueprintsprocessor.message.service import com.fasterxml.jackson.databind.JsonNode -import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintProperties +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertiesService import org.onap.ccsdk.cds.blueprintsprocessor.message.* import org.onap.ccsdk.cds.controllerblueprints.core.BluePrintProcessorException import org.onap.ccsdk.cds.controllerblueprints.core.utils.JacksonUtils import org.springframework.stereotype.Service @Service(MessageLibConstants.SERVICE_BLUEPRINT_MESSAGE_LIB_PROPERTY) -open class BluePrintMessageLibPropertyService(private var bluePrintProperties: BluePrintProperties) { +open class BluePrintMessageLibPropertyService(private var bluePrintPropertiesService: BluePrintPropertiesService) { fun blueprintMessageProducerService(jsonNode: JsonNode): BlueprintMessageProducerService { val messageClientProperties = messageProducerProperties(jsonNode) @@ -38,7 +39,7 @@ open class BluePrintMessageLibPropertyService(private var bluePrintProperties: B } fun messageProducerProperties(prefix: String): MessageProducerProperties { - val type = bluePrintProperties.propertyBeanType("$prefix.type", String::class.java) + val type = bluePrintPropertiesService.propertyBeanType("$prefix.type", String::class.java) return when (type) { MessageLibConstants.TYPE_KAFKA_BASIC_AUTH -> { kafkaBasicAuthMessageProducerProperties(prefix) @@ -75,7 +76,7 @@ open class BluePrintMessageLibPropertyService(private var bluePrintProperties: B } private fun kafkaBasicAuthMessageProducerProperties(prefix: String): KafkaBasicAuthMessageProducerProperties { - return bluePrintProperties.propertyBeanType( + return bluePrintPropertiesService.propertyBeanType( prefix, KafkaBasicAuthMessageProducerProperties::class.java) } @@ -96,11 +97,14 @@ open class BluePrintMessageLibPropertyService(private var bluePrintProperties: B /** Return Message Consumer Properties for [prefix] definitions. */ fun messageConsumerProperties(prefix: String): MessageConsumerProperties { - val type = bluePrintProperties.propertyBeanType("$prefix.type", String::class.java) + val type = bluePrintPropertiesService.propertyBeanType("$prefix.type", String::class.java) return when (type) { MessageLibConstants.TYPE_KAFKA_BASIC_AUTH -> { kafkaBasicAuthMessageConsumerProperties(prefix) } + MessageLibConstants.TYPE_KAFKA_STREAMS_BASIC_AUTH -> { + kafkaStreamsBasicAuthMessageConsumerProperties(prefix) + } else -> { throw BluePrintProcessorException("Message adaptor($type) is not supported") } @@ -113,6 +117,9 @@ open class BluePrintMessageLibPropertyService(private var bluePrintProperties: B MessageLibConstants.TYPE_KAFKA_BASIC_AUTH -> { JacksonUtils.readValue(jsonNode, KafkaBasicAuthMessageConsumerProperties::class.java)!! } + MessageLibConstants.TYPE_KAFKA_STREAMS_BASIC_AUTH -> { + JacksonUtils.readValue(jsonNode, KafkaStreamsBasicAuthConsumerProperties::class.java)!! + } else -> { throw BluePrintProcessorException("Message adaptor($type) is not supported") } @@ -126,6 +133,9 @@ open class BluePrintMessageLibPropertyService(private var bluePrintProperties: B is KafkaBasicAuthMessageConsumerProperties -> { return KafkaBasicAuthMessageConsumerService(messageConsumerProperties) } + is KafkaStreamsBasicAuthConsumerProperties -> { + return KafkaStreamsBasicAuthConsumerService(messageConsumerProperties) + } else -> { throw BluePrintProcessorException("couldn't get Message client service for") } @@ -133,8 +143,13 @@ open class BluePrintMessageLibPropertyService(private var bluePrintProperties: B } private fun kafkaBasicAuthMessageConsumerProperties(prefix: String): KafkaBasicAuthMessageConsumerProperties { - return bluePrintProperties.propertyBeanType( + return bluePrintPropertiesService.propertyBeanType( prefix, KafkaBasicAuthMessageConsumerProperties::class.java) } + private fun kafkaStreamsBasicAuthMessageConsumerProperties(prefix: String): KafkaStreamsBasicAuthConsumerProperties { + return bluePrintProperties.propertyBeanType( + prefix, KafkaStreamsBasicAuthConsumerProperties::class.java) + } + } diff --git a/ms/blueprintsprocessor/modules/commons/message-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/message/service/BlueprintMessageConsumerService.kt b/ms/blueprintsprocessor/modules/commons/message-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/message/service/BlueprintMessageConsumerService.kt index 8bcc7580a..716fda609 100644 --- a/ms/blueprintsprocessor/modules/commons/message-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/message/service/BlueprintMessageConsumerService.kt +++ b/ms/blueprintsprocessor/modules/commons/message-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/message/service/BlueprintMessageConsumerService.kt @@ -20,6 +20,7 @@ package org.onap.ccsdk.cds.blueprintsprocessor.message.service import kotlinx.coroutines.channels.Channel import org.apache.kafka.clients.consumer.Consumer import org.apache.kafka.clients.consumer.ConsumerRecords +import org.apache.kafka.streams.Topology import org.onap.ccsdk.cds.blueprintsprocessor.message.MessageConsumerProperties import org.onap.ccsdk.cds.controllerblueprints.core.BluePrintProcessorException @@ -61,4 +62,9 @@ interface BlueprintMessageConsumerService { interface KafkaConsumerRecordsFunction : ConsumerFunction { suspend fun invoke(messageConsumerProperties: MessageConsumerProperties, consumer: Consumer<*, *>, consumerRecords: ConsumerRecords<*, *>) +} + +interface KafkaStreamConsumerFunction : ConsumerFunction { + suspend fun createTopology(messageConsumerProperties: MessageConsumerProperties, + additionalConfig: Map<String, Any>?): Topology }
\ No newline at end of file diff --git a/ms/blueprintsprocessor/modules/commons/message-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/message/service/KafkaBasicAuthMessageProducerService.kt b/ms/blueprintsprocessor/modules/commons/message-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/message/service/KafkaBasicAuthMessageProducerService.kt index 42adcd712..ad9a594b0 100644 --- a/ms/blueprintsprocessor/modules/commons/message-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/message/service/KafkaBasicAuthMessageProducerService.kt +++ b/ms/blueprintsprocessor/modules/commons/message-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/message/service/KafkaBasicAuthMessageProducerService.kt @@ -65,9 +65,9 @@ class KafkaBasicAuthMessageProducerService( headers.forEach { (key, value) -> recordHeaders.add(RecordHeader(key, value.toByteArray())) } } val callback = Callback { metadata, exception -> - log.info("message published offset(${metadata.offset()}, headers :$headers )") + log.trace("message published to(${metadata.topic()}), offset(${metadata.offset()}), headers :$headers") } - messageTemplate().send(record, callback).get() + messageTemplate().send(record, callback) return true } @@ -77,6 +77,8 @@ class KafkaBasicAuthMessageProducerService( configProps[BOOTSTRAP_SERVERS_CONFIG] = messageProducerProperties.bootstrapServers configProps[KEY_SERIALIZER_CLASS_CONFIG] = StringSerializer::class.java configProps[VALUE_SERIALIZER_CLASS_CONFIG] = ByteArraySerializer::class.java + configProps[ACKS_CONFIG] = messageProducerProperties.acks + configProps[ENABLE_IDEMPOTENCE_CONFIG] = messageProducerProperties.enableIdempotence if (messageProducerProperties.clientId != null) { configProps[CLIENT_ID_CONFIG] = messageProducerProperties.clientId!! } diff --git a/ms/blueprintsprocessor/modules/commons/message-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/message/service/KafkaStreamsBasicAuthConsumerService.kt b/ms/blueprintsprocessor/modules/commons/message-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/message/service/KafkaStreamsBasicAuthConsumerService.kt new file mode 100644 index 000000000..d0297df4c --- /dev/null +++ b/ms/blueprintsprocessor/modules/commons/message-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/message/service/KafkaStreamsBasicAuthConsumerService.kt @@ -0,0 +1,71 @@ +/* + * Copyright © 2018-2019 AT&T Intellectual Property. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.message.service + +import kotlinx.coroutines.channels.Channel +import org.apache.kafka.clients.consumer.ConsumerConfig +import org.apache.kafka.streams.KafkaStreams +import org.apache.kafka.streams.StreamsConfig +import org.onap.ccsdk.cds.blueprintsprocessor.message.KafkaStreamsBasicAuthConsumerProperties +import org.onap.ccsdk.cds.controllerblueprints.core.BluePrintProcessorException +import org.onap.ccsdk.cds.controllerblueprints.core.logger +import java.util.* + +open class KafkaStreamsBasicAuthConsumerService(private val messageConsumerProperties: KafkaStreamsBasicAuthConsumerProperties) + : BlueprintMessageConsumerService { + + val log = logger(KafkaStreamsBasicAuthConsumerService::class) + lateinit var kafkaStreams: KafkaStreams + + private fun streamsConfig(additionalConfig: Map<String, Any>? = null): Properties { + val configProperties = Properties() + configProperties[StreamsConfig.APPLICATION_ID_CONFIG] = messageConsumerProperties.applicationId + configProperties[StreamsConfig.BOOTSTRAP_SERVERS_CONFIG] = messageConsumerProperties.bootstrapServers + configProperties[ConsumerConfig.AUTO_OFFSET_RESET_CONFIG] = messageConsumerProperties.autoOffsetReset + configProperties[StreamsConfig.PROCESSING_GUARANTEE_CONFIG] = messageConsumerProperties.processingGuarantee + // TODO("Security Implementation based on type") + /** add or override already set properties */ + additionalConfig?.let { configProperties.putAll(it) } + /** Create Kafka consumer */ + return configProperties + } + + override suspend fun subscribe(additionalConfig: Map<String, Any>?): Channel<String> { + throw BluePrintProcessorException("not implemented") + } + + override suspend fun subscribe(topics: List<String>, additionalConfig: Map<String, Any>?): Channel<String> { + throw BluePrintProcessorException("not implemented") + } + + override suspend fun consume(additionalConfig: Map<String, Any>?, consumerFunction: ConsumerFunction) { + val streamsConfig = streamsConfig(additionalConfig) + val kafkaStreamConsumerFunction = consumerFunction as KafkaStreamConsumerFunction + val topology = kafkaStreamConsumerFunction.createTopology(messageConsumerProperties, additionalConfig) + log.info("Kafka streams topology : ${topology.describe()}") + kafkaStreams = KafkaStreams(topology, streamsConfig) + kafkaStreams.cleanUp() + kafkaStreams.start() + kafkaStreams.localThreadsMetadata().forEach { data -> log.info("Topology : $data") } + } + + override suspend fun shutDown() { + if (kafkaStreams != null) { + kafkaStreams.close() + } + } +}
\ No newline at end of file diff --git a/ms/blueprintsprocessor/modules/commons/message-lib/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/message/service/BlueprintMessageConsumerServiceTest.kt b/ms/blueprintsprocessor/modules/commons/message-lib/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/message/service/BlueprintMessageConsumerServiceTest.kt index bdceec7d3..b2accfb4d 100644 --- a/ms/blueprintsprocessor/modules/commons/message-lib/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/message/service/BlueprintMessageConsumerServiceTest.kt +++ b/ms/blueprintsprocessor/modules/commons/message-lib/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/message/service/BlueprintMessageConsumerServiceTest.kt @@ -27,8 +27,8 @@ import org.apache.kafka.clients.consumer.* import org.apache.kafka.common.TopicPartition import org.junit.Test import org.junit.runner.RunWith -import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintProperties -import org.onap.ccsdk.cds.blueprintsprocessor.core.BlueprintPropertyConfiguration +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertiesService +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertyConfiguration import org.onap.ccsdk.cds.blueprintsprocessor.message.BluePrintMessageLibConfiguration import org.onap.ccsdk.cds.blueprintsprocessor.message.MessageConsumerProperties import org.onap.ccsdk.cds.controllerblueprints.core.logger @@ -44,7 +44,7 @@ import kotlin.test.assertTrue @RunWith(SpringRunner::class) @DirtiesContext @ContextConfiguration(classes = [BluePrintMessageLibConfiguration::class, - BlueprintPropertyConfiguration::class, BluePrintProperties::class]) + BluePrintPropertyConfiguration::class, BluePrintPropertiesService::class]) @TestPropertySource(properties = ["blueprintsprocessor.messageconsumer.sample.type=kafka-basic-auth", "blueprintsprocessor.messageconsumer.sample.bootstrapServers=127.0.0.1:9092", diff --git a/ms/blueprintsprocessor/modules/commons/message-lib/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/message/service/BlueprintMessageProducerServiceTest.kt b/ms/blueprintsprocessor/modules/commons/message-lib/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/message/service/BlueprintMessageProducerServiceTest.kt index f23624f7a..4fe5f5dd1 100644 --- a/ms/blueprintsprocessor/modules/commons/message-lib/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/message/service/BlueprintMessageProducerServiceTest.kt +++ b/ms/blueprintsprocessor/modules/commons/message-lib/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/message/service/BlueprintMessageProducerServiceTest.kt @@ -23,8 +23,8 @@ import kotlinx.coroutines.runBlocking import org.apache.kafka.clients.producer.KafkaProducer import org.apache.kafka.clients.producer.RecordMetadata import org.junit.runner.RunWith -import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintProperties -import org.onap.ccsdk.cds.blueprintsprocessor.core.BlueprintPropertyConfiguration +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertiesService +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertyConfiguration import org.onap.ccsdk.cds.blueprintsprocessor.message.BluePrintMessageLibConfiguration import org.springframework.beans.factory.annotation.Autowired import org.springframework.test.annotation.DirtiesContext @@ -39,7 +39,7 @@ import kotlin.test.assertTrue @RunWith(SpringRunner::class) @DirtiesContext @ContextConfiguration(classes = [BluePrintMessageLibConfiguration::class, - BlueprintPropertyConfiguration::class, BluePrintProperties::class]) + BluePrintPropertyConfiguration::class, BluePrintPropertiesService::class]) @TestPropertySource(properties = ["blueprintsprocessor.messageproducer.sample.type=kafka-basic-auth", "blueprintsprocessor.messageproducer.sample.bootstrapServers=127.0.0.1:9092", diff --git a/ms/blueprintsprocessor/modules/commons/message-lib/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/message/service/KafkaStreamsBasicAuthConsumerServiceTest.kt b/ms/blueprintsprocessor/modules/commons/message-lib/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/message/service/KafkaStreamsBasicAuthConsumerServiceTest.kt new file mode 100644 index 000000000..e2a31f40a --- /dev/null +++ b/ms/blueprintsprocessor/modules/commons/message-lib/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/message/service/KafkaStreamsBasicAuthConsumerServiceTest.kt @@ -0,0 +1,126 @@ +/* + * Copyright © 2018-2019 AT&T Intellectual Property. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.message.service + +import kotlinx.coroutines.delay +import kotlinx.coroutines.launch +import kotlinx.coroutines.runBlocking +import org.apache.kafka.common.serialization.Serdes +import org.apache.kafka.streams.Topology +import org.apache.kafka.streams.processor.Processor +import org.apache.kafka.streams.processor.ProcessorSupplier +import org.apache.kafka.streams.state.Stores +import org.junit.Test +import org.junit.runner.RunWith +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintProperties +import org.onap.ccsdk.cds.blueprintsprocessor.core.BlueprintPropertyConfiguration +import org.onap.ccsdk.cds.blueprintsprocessor.message.BluePrintMessageLibConfiguration +import org.onap.ccsdk.cds.blueprintsprocessor.message.KafkaStreamsBasicAuthConsumerProperties +import org.onap.ccsdk.cds.blueprintsprocessor.message.MessageConsumerProperties +import org.springframework.beans.factory.annotation.Autowired +import org.springframework.test.annotation.DirtiesContext +import org.springframework.test.context.ContextConfiguration +import org.springframework.test.context.TestPropertySource +import org.springframework.test.context.junit4.SpringRunner +import kotlin.test.assertNotNull + + +@RunWith(SpringRunner::class) +@DirtiesContext +@ContextConfiguration(classes = [BluePrintMessageLibConfiguration::class, + BlueprintPropertyConfiguration::class, BluePrintProperties::class]) +@TestPropertySource(properties = +[ + "blueprintsprocessor.messageproducer.sample.type=kafka-basic-auth", + "blueprintsprocessor.messageproducer.sample.bootstrapServers=127.0.0.1:9092", + "blueprintsprocessor.messageproducer.sample.topic=default-stream-topic", + "blueprintsprocessor.messageproducer.sample.clientId=default-client-id", + + "blueprintsprocessor.messageconsumer.stream-consumer.type=kafka-streams-basic-auth", + "blueprintsprocessor.messageconsumer.stream-consumer.bootstrapServers=127.0.0.1:9092", + "blueprintsprocessor.messageconsumer.stream-consumer.applicationId=test-streams-application", + "blueprintsprocessor.messageconsumer.stream-consumer.topic=default-stream-topic" + +]) +class KafkaStreamsBasicAuthConsumerServiceTest { + @Autowired + lateinit var bluePrintMessageLibPropertyService: BluePrintMessageLibPropertyService + + @Test + fun testProperties() { + val blueprintMessageConsumerService = bluePrintMessageLibPropertyService.blueprintMessageConsumerService("stream-consumer") + assertNotNull(blueprintMessageConsumerService, "failed to get blueprintMessageProducerService") + } + + /** Integration Kafka Testing, Enable and use this test case only for local desktop testing with real kafka broker */ + //@Test + fun testKafkaStreamingMessageConsumer() { + runBlocking { + val streamingConsumerService = bluePrintMessageLibPropertyService.blueprintMessageConsumerService("stream-consumer") + + // Dynamic Consumer Function to create Topology + val consumerFunction = object : KafkaStreamConsumerFunction { + override suspend fun createTopology(messageConsumerProperties: MessageConsumerProperties, + additionalConfig: Map<String, Any>?): Topology { + val topology = Topology() + val kafkaStreamsBasicAuthConsumerProperties = messageConsumerProperties + as KafkaStreamsBasicAuthConsumerProperties + + val topics = kafkaStreamsBasicAuthConsumerProperties.topic.split(",") + topology.addSource("Source", *topics.toTypedArray()) + // Processor Supplier + val firstProcessorSupplier = object : ProcessorSupplier<ByteArray, ByteArray> { + override fun get(): Processor<ByteArray, ByteArray> { + return FirstProcessor() + } + } + val changelogConfig: MutableMap<String, String> = hashMapOf() + changelogConfig.put("min.insync.replicas", "1") + + // Store Buolder + val countStoreSupplier = Stores.keyValueStoreBuilder( + Stores.persistentKeyValueStore("PriorityMessageState"), + Serdes.String(), + PriorityMessageSerde()) + .withLoggingEnabled(changelogConfig) + + topology.addProcessor("FirstProcessor", firstProcessorSupplier, "Source") + topology.addStateStore(countStoreSupplier, "FirstProcessor") + topology.addSink("SINK", "default-stream-topic-out", Serdes.String().serializer(), + PriorityMessageSerde().serializer(), "FirstProcessor") + return topology + } + } + + /** Send message with every 1 sec */ + val blueprintMessageProducerService = bluePrintMessageLibPropertyService + .blueprintMessageProducerService("sample") as KafkaBasicAuthMessageProducerService + launch { + repeat(5) { + delay(1000) + val headers: MutableMap<String, String> = hashMapOf() + headers["id"] = it.toString() + blueprintMessageProducerService.sendMessageNB(message = "this is my message($it)", + headers = headers) + } + } + streamingConsumerService.consume(null, consumerFunction) + delay(10000) + streamingConsumerService.shutDown() + } + } +}
\ No newline at end of file diff --git a/ms/blueprintsprocessor/modules/commons/message-lib/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/message/service/MockKafkaTopologyComponents.kt b/ms/blueprintsprocessor/modules/commons/message-lib/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/message/service/MockKafkaTopologyComponents.kt new file mode 100644 index 000000000..4db9c772e --- /dev/null +++ b/ms/blueprintsprocessor/modules/commons/message-lib/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/message/service/MockKafkaTopologyComponents.kt @@ -0,0 +1,103 @@ +/* + * Copyright © 2018-2019 AT&T Intellectual Property. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.message.service + +import org.apache.kafka.common.serialization.Deserializer +import org.apache.kafka.common.serialization.Serde +import org.apache.kafka.common.serialization.Serializer +import org.apache.kafka.streams.processor.Processor +import org.apache.kafka.streams.processor.ProcessorContext +import org.apache.kafka.streams.state.KeyValueStore +import org.onap.ccsdk.cds.controllerblueprints.core.BluePrintProcessorException +import org.onap.ccsdk.cds.controllerblueprints.core.asJsonString +import org.onap.ccsdk.cds.controllerblueprints.core.logger +import org.onap.ccsdk.cds.controllerblueprints.core.utils.JacksonUtils +import java.io.Serializable +import java.nio.charset.Charset +import java.util.* + +class PriorityMessage : Serializable { + lateinit var id: String + lateinit var requestMessage: String +} + +open class PriorityMessageSerde : Serde<PriorityMessage> { + + override fun configure(configs: MutableMap<String, *>?, isKey: Boolean) { + } + + override fun close() { + } + + override fun deserializer(): Deserializer<PriorityMessage> { + return object : Deserializer<PriorityMessage> { + override fun deserialize(topic: String, data: ByteArray): PriorityMessage { + return JacksonUtils.readValue(String(data), PriorityMessage::class.java) + ?: throw BluePrintProcessorException("failed to convert") + } + + override fun configure(configs: MutableMap<String, *>?, isKey: Boolean) { + } + + override fun close() { + } + } + } + + override fun serializer(): Serializer<PriorityMessage> { + return object : Serializer<PriorityMessage> { + override fun configure(configs: MutableMap<String, *>?, isKey: Boolean) { + } + + override fun serialize(topic: String?, data: PriorityMessage): ByteArray { + return data.asJsonString().toByteArray(Charset.defaultCharset()) + } + + override fun close() { + } + } + } +} + + +class FirstProcessor : Processor<ByteArray, ByteArray> { + + private val log = logger(FirstProcessor::class) + + private lateinit var context: ProcessorContext + private lateinit var kvStore: KeyValueStore<String, PriorityMessage> + + override fun process(key: ByteArray, value: ByteArray) { + log.info("First Processor key(${String(key)} : value(${String(value)})") + val newMessage = PriorityMessage().apply { + id = UUID.randomUUID().toString() + requestMessage = String(value) + } + kvStore.put(newMessage.id, newMessage) + this.context.forward(newMessage.id, newMessage) + } + + override fun init(context: ProcessorContext) { + log.info("init... ${context.keySerde()}, ${context.valueSerde()}") + this.context = context + this.kvStore = context.getStateStore("PriorityMessageState") as KeyValueStore<String, PriorityMessage> + } + + override fun close() { + log.info("Close...") + } +}
\ No newline at end of file diff --git a/ms/blueprintsprocessor/modules/commons/processor-core/pom.xml b/ms/blueprintsprocessor/modules/commons/processor-core/pom.xml index 0bc88449f..a79e8d6df 100644 --- a/ms/blueprintsprocessor/modules/commons/processor-core/pom.xml +++ b/ms/blueprintsprocessor/modules/commons/processor-core/pom.xml @@ -33,6 +33,10 @@ <dependencies> <dependency> + <groupId>org.onap.ccsdk.cds.controllerblueprints</groupId> + <artifactId>blueprint-proto</artifactId> + </dependency> + <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-webflux</artifactId> <exclusions> diff --git a/ms/blueprintsprocessor/modules/commons/processor-core/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/core/BluePrintCoreConfiguration.kt b/ms/blueprintsprocessor/modules/commons/processor-core/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/core/BluePrintCoreConfiguration.kt index 9980b9efb..62dc933f1 100644 --- a/ms/blueprintsprocessor/modules/commons/processor-core/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/core/BluePrintCoreConfiguration.kt +++ b/ms/blueprintsprocessor/modules/commons/processor-core/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/core/BluePrintCoreConfiguration.kt @@ -32,7 +32,7 @@ import org.springframework.core.env.Environment import org.springframework.stereotype.Service @Configuration -open class BluePrintCoreConfiguration(private val bluePrintPropertiesService: BlueprintPropertiesService) { +open class BluePrintCoreConfiguration(private val bluePrintPropertiesService: BluePrintPropertiesService) { companion object { const val PREFIX_BLUEPRINT_PROCESSOR = "blueprintsprocessor" @@ -46,7 +46,7 @@ open class BluePrintCoreConfiguration(private val bluePrintPropertiesService: Bl } @Configuration -open class BlueprintPropertyConfiguration { +open class BluePrintPropertyConfiguration { @Autowired lateinit var environment: Environment @@ -58,7 +58,7 @@ open class BlueprintPropertyConfiguration { } @Service -open class BlueprintPropertiesService(private var bluePrintPropertyBinder: Binder) { +open class BluePrintPropertiesService(private var bluePrintPropertyBinder: Binder) { fun <T> propertyBeanType(prefix: String, type: Class<T>): T { return bluePrintPropertyBinder.bind(prefix, Bindable.of(type)).get() } diff --git a/ms/blueprintsprocessor/modules/commons/processor-core/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/core/api/data/BlueprintProcessorData.kt b/ms/blueprintsprocessor/modules/commons/processor-core/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/core/api/data/BlueprintProcessorData.kt index 5a6ba0661..dae6eea85 100644 --- a/ms/blueprintsprocessor/modules/commons/processor-core/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/core/api/data/BlueprintProcessorData.kt +++ b/ms/blueprintsprocessor/modules/commons/processor-core/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/core/api/data/BlueprintProcessorData.kt @@ -22,6 +22,8 @@ import com.fasterxml.jackson.annotation.JsonIgnore import com.fasterxml.jackson.databind.JsonNode import com.fasterxml.jackson.databind.node.ObjectNode import io.swagger.annotations.ApiModelProperty +import org.onap.ccsdk.cds.controllerblueprints.common.api.EventType +import org.onap.ccsdk.cds.controllerblueprints.core.BluePrintConstants import java.util.* /** @@ -36,9 +38,9 @@ open class ExecutionServiceInput { @get:ApiModelProperty(required = true, value = "Provide information about the action to execute.") lateinit var actionIdentifiers: ActionIdentifiers @get:ApiModelProperty(required = true, - value = "Contain the information to be passed as input to the action." + - "The payload is constituted of two section: the workflow input which is the higher level block (xxx-request)" + - " and the input for resource resolution located within the xxx-request block, contained within xxx-properties") + value = "Contain the information to be passed as input to the action." + + "The payload is constituted of two section: the workflow input which is the higher level block (xxx-request)" + + " and the input for resource resolution located within the xxx-request block, contained within xxx-properties") lateinit var payload: ObjectNode @get:ApiModelProperty(hidden = true) @get:JsonIgnore @@ -53,9 +55,9 @@ open class ExecutionServiceOutput { @get:ApiModelProperty(required = true, value = "Status of the request.") lateinit var status: Status @get:ApiModelProperty(required = true, - value = "Contain the information to be passed as input to the action." + - "The payload is constituted of two section: the workflow input which is the higher level block (xxx-request)" + - " and the input for resource resolution located within the xxx-request block, contained within xxx-properties") + value = "Contain the information to be passed as input to the action." + + "The payload is constituted of two section: the workflow input which is the higher level block (xxx-request)" + + " and the input for resource resolution located within the xxx-request block, contained within xxx-properties") lateinit var payload: ObjectNode @get:ApiModelProperty(hidden = true) @get:JsonIgnore @@ -73,8 +75,8 @@ open class ActionIdentifiers { @get:ApiModelProperty(required = true, value = "Name of the workflow to execute.") lateinit var actionName: String @get:ApiModelProperty(required = true, - value = "Async processing is only supported for gRPC client.", - allowableValues = "sync, async") + value = "Async processing is only supported for gRPC client.", + allowableValues = "sync, async") lateinit var mode: String } @@ -103,16 +105,16 @@ open class Status { @get:ApiModelProperty(required = true, value = "HTTP status code equivalent.") var code: Int = 200 @get:ApiModelProperty(required = true, value = "Type of the event being emitted by CDS.") - var eventType: String = "" + var eventType: String = EventType.EVENT_COMPONENT_EXECUTED.name @get:ApiModelProperty(required = true, - value = "Time when the execution ended.", - example = "2012-04-23T18:25:43.511Z") + value = "Time when the execution ended.", + example = "2012-04-23T18:25:43.511Z") @get:JsonFormat(shape = JsonFormat.Shape.STRING, pattern = "yyyy-MM-dd'T'HH:mm:ss.SSS'Z'") var timestamp: Date = Date() @get:ApiModelProperty(required = false, value = "Error message when system failed") var errorMessage: String? = null @get:ApiModelProperty(required = true, value = "Message providing request status") - var message: String = "success" + var message: String = BluePrintConstants.STATUS_SUCCESS } open class StepData { diff --git a/ms/blueprintsprocessor/modules/inbounds/selfservice-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/selfservice/api/utils/BluePrintMappings.kt b/ms/blueprintsprocessor/modules/commons/processor-core/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/core/utils/BluePrintMappings.kt index 46633aa60..9cd00a3ba 100644 --- a/ms/blueprintsprocessor/modules/inbounds/selfservice-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/selfservice/api/utils/BluePrintMappings.kt +++ b/ms/blueprintsprocessor/modules/commons/processor-core/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/core/utils/BluePrintMappings.kt @@ -5,7 +5,7 @@ * 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 + * 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, @@ -13,7 +13,7 @@ * See the License for the specific language governing permissions and * limitations under the License. */ -package org.onap.ccsdk.cds.blueprintsprocessor.selfservice.api.utils +package org.onap.ccsdk.cds.blueprintsprocessor.core.utils import com.fasterxml.jackson.databind.node.ObjectNode import com.google.common.base.Strings diff --git a/ms/blueprintsprocessor/modules/inbounds/selfservice-api/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/selfservice/api/utils/BluePrintMappingTests.kt b/ms/blueprintsprocessor/modules/commons/processor-core/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/core/utils/BluePrintMappingTests.kt index 230d1fde1..b1d7d144c 100644 --- a/ms/blueprintsprocessor/modules/inbounds/selfservice-api/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/selfservice/api/utils/BluePrintMappingTests.kt +++ b/ms/blueprintsprocessor/modules/commons/processor-core/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/core/utils/BluePrintMappingTests.kt @@ -1,4 +1,4 @@ -package org.onap.ccsdk.cds.blueprintsprocessor.selfservice.api.utils +package org.onap.ccsdk.cds.blueprintsprocessor.core.utils import org.junit.Assert import org.junit.Test diff --git a/ms/blueprintsprocessor/modules/commons/rest-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/rest/filters/RestServerLoggingWebFilter.kt b/ms/blueprintsprocessor/modules/commons/rest-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/rest/filters/RestServerLoggingWebFilter.kt new file mode 100644 index 000000000..5aaee24de --- /dev/null +++ b/ms/blueprintsprocessor/modules/commons/rest-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/rest/filters/RestServerLoggingWebFilter.kt @@ -0,0 +1,38 @@ +/* + * Copyright © 2018-2019 AT&T Intellectual Property. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.rest.filters + +import org.onap.ccsdk.cds.blueprintsprocessor.rest.service.RestLoggerService +import org.onap.ccsdk.cds.controllerblueprints.core.MDCContext +import org.springframework.web.server.ServerWebExchange +import org.springframework.web.server.WebFilter +import org.springframework.web.server.WebFilterChain +import reactor.core.publisher.Mono +import reactor.util.context.Context + + +open class RestServerLoggingWebFilter : WebFilter { + override fun filter(serverWebExchange: ServerWebExchange, webFilterChain: WebFilterChain): Mono<Void> { + + val loggingService = RestLoggerService() + loggingService.entering(serverWebExchange.request) + val filterChain = webFilterChain.filter(serverWebExchange).subscriberContext( + Context.of(MDCContext, MDCContext())) + loggingService.exiting(serverWebExchange.request, serverWebExchange.response) + return filterChain + } +}
\ No newline at end of file diff --git a/ms/blueprintsprocessor/modules/commons/rest-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/rest/service/BluePrintRestLibPropertyService.kt b/ms/blueprintsprocessor/modules/commons/rest-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/rest/service/BluePrintRestLibPropertyService.kt index 9a7b3c303..84ba7d414 100644 --- a/ms/blueprintsprocessor/modules/commons/rest-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/rest/service/BluePrintRestLibPropertyService.kt +++ b/ms/blueprintsprocessor/modules/commons/rest-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/rest/service/BluePrintRestLibPropertyService.kt @@ -19,15 +19,14 @@ package org.onap.ccsdk.cds.blueprintsprocessor.rest.service import com.fasterxml.jackson.databind.JsonNode -import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintProperties +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertiesService import org.onap.ccsdk.cds.blueprintsprocessor.rest.* import org.onap.ccsdk.cds.controllerblueprints.core.BluePrintProcessorException import org.onap.ccsdk.cds.controllerblueprints.core.utils.JacksonUtils import org.springframework.stereotype.Service @Service(RestLibConstants.SERVICE_BLUEPRINT_REST_LIB_PROPERTY) -open class BluePrintRestLibPropertyService(private var bluePrintProperties: - BluePrintProperties) { +open class BluePrintRestLibPropertyService(private var bluePrintPropertiesService: BluePrintPropertiesService) { private var preInterceptor: PreInterceptor? = null private var postInterceptor: PostInterceptor? = null @@ -58,8 +57,8 @@ open class BluePrintRestLibPropertyService(private var bluePrintProperties: } fun restClientProperties(prefix: String): RestClientProperties { - val type = bluePrintProperties.propertyBeanType( - "$prefix.type", String::class.java) + val type = bluePrintPropertiesService.propertyBeanType( + "$prefix.type", String::class.java) return when (type) { RestLibConstants.TYPE_BASIC_AUTH -> { basicAuthRestClientProperties(prefix) @@ -82,7 +81,7 @@ open class BluePrintRestLibPropertyService(private var bluePrintProperties: } else -> { throw BluePrintProcessorException("Rest adaptor($type) is" + - " not supported") + " not supported") } } } @@ -112,13 +111,13 @@ open class BluePrintRestLibPropertyService(private var bluePrintProperties: } else -> { throw BluePrintProcessorException( - "Rest adaptor($type) is not supported") + "Rest adaptor($type) is not supported") } } } private fun blueprintWebClientService(restClientProperties: RestClientProperties): - BlueprintWebClientService { + BlueprintWebClientService { when (restClientProperties) { is SSLRestClientProperties -> { @@ -137,53 +136,53 @@ open class BluePrintRestLibPropertyService(private var bluePrintProperties: } private fun tokenRestClientProperties(prefix: String): - TokenAuthRestClientProperties { - return bluePrintProperties.propertyBeanType( - prefix, TokenAuthRestClientProperties::class.java) + TokenAuthRestClientProperties { + return bluePrintPropertiesService.propertyBeanType( + prefix, TokenAuthRestClientProperties::class.java) } private fun basicAuthRestClientProperties(prefix: String): - BasicAuthRestClientProperties { - return bluePrintProperties.propertyBeanType( - prefix, BasicAuthRestClientProperties::class.java) + BasicAuthRestClientProperties { + return bluePrintPropertiesService.propertyBeanType( + prefix, BasicAuthRestClientProperties::class.java) } private fun sslBasicAuthRestClientProperties(prefix: String): - SSLRestClientProperties { + SSLRestClientProperties { val sslProps: SSLBasicAuthRestClientProperties = - bluePrintProperties.propertyBeanType( - prefix, SSLBasicAuthRestClientProperties::class.java) + bluePrintPropertiesService.propertyBeanType( + prefix, SSLBasicAuthRestClientProperties::class.java) val basicProps: BasicAuthRestClientProperties = - bluePrintProperties.propertyBeanType( - prefix, BasicAuthRestClientProperties::class.java) + bluePrintPropertiesService.propertyBeanType( + prefix, BasicAuthRestClientProperties::class.java) sslProps.basicAuth = basicProps return sslProps } private fun sslTokenAuthRestClientProperties(prefix: String): - SSLRestClientProperties { + SSLRestClientProperties { val sslProps: SSLTokenAuthRestClientProperties = - bluePrintProperties.propertyBeanType(prefix, - SSLTokenAuthRestClientProperties::class.java) + bluePrintPropertiesService.propertyBeanType(prefix, + SSLTokenAuthRestClientProperties::class.java) val basicProps: TokenAuthRestClientProperties = - bluePrintProperties.propertyBeanType(prefix, - TokenAuthRestClientProperties::class.java) + bluePrintPropertiesService.propertyBeanType(prefix, + TokenAuthRestClientProperties::class.java) sslProps.tokenAuth = basicProps return sslProps } private fun sslNoAuthRestClientProperties(prefix: String): - SSLRestClientProperties { - return bluePrintProperties.propertyBeanType( - prefix, SSLRestClientProperties::class.java) + SSLRestClientProperties { + return bluePrintPropertiesService.propertyBeanType( + prefix, SSLRestClientProperties::class.java) } private fun policyManagerRestClientProperties(prefix: String): - PolicyManagerRestClientProperties { - return bluePrintProperties.propertyBeanType( - prefix, PolicyManagerRestClientProperties::class.java) + PolicyManagerRestClientProperties { + return bluePrintPropertiesService.propertyBeanType( + prefix, PolicyManagerRestClientProperties::class.java) } interface PreInterceptor { diff --git a/ms/blueprintsprocessor/modules/commons/rest-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/rest/service/BlueprintWebClientService.kt b/ms/blueprintsprocessor/modules/commons/rest-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/rest/service/BlueprintWebClientService.kt index 26c808874..3e31bf9ec 100644 --- a/ms/blueprintsprocessor/modules/commons/rest-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/rest/service/BlueprintWebClientService.kt +++ b/ms/blueprintsprocessor/modules/commons/rest-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/rest/service/BlueprintWebClientService.kt @@ -97,12 +97,14 @@ interface BlueprintWebClientService { fun <T> delete(path: String, headers: Array<BasicHeader>, responseType: Class<T>): WebClientResponse<T> { val httpDelete = HttpDelete(host(path)) + RestLoggerService.httpInvoking(headers) httpDelete.setHeaders(headers) return performCallAndExtractTypedWebClientResponse(httpDelete, responseType) } fun <T> get(path: String, headers: Array<BasicHeader>, responseType: Class<T>): WebClientResponse<T> { val httpGet = HttpGet(host(path)) + RestLoggerService.httpInvoking(headers) httpGet.setHeaders(headers) return performCallAndExtractTypedWebClientResponse(httpGet, responseType) } @@ -111,6 +113,7 @@ interface BlueprintWebClientService { val httpPost = HttpPost(host(path)) val entity = StringEntity(strRequest(request)) httpPost.entity = entity + RestLoggerService.httpInvoking(headers) httpPost.setHeaders(headers) return performCallAndExtractTypedWebClientResponse(httpPost, responseType) } @@ -119,6 +122,7 @@ interface BlueprintWebClientService { val httpPut = HttpPut(host(path)) val entity = StringEntity(strRequest(request)) httpPut.entity = entity + RestLoggerService.httpInvoking(headers) httpPut.setHeaders(headers) return performCallAndExtractTypedWebClientResponse(httpPut, responseType) } @@ -127,6 +131,7 @@ interface BlueprintWebClientService { val httpPatch = HttpPatch(host(path)) val entity = StringEntity(strRequest(request)) httpPatch.entity = entity + RestLoggerService.httpInvoking(headers) httpPatch.setHeaders(headers) return performCallAndExtractTypedWebClientResponse(httpPatch, responseType) } diff --git a/ms/blueprintsprocessor/modules/commons/rest-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/rest/service/RestLoggerService.kt b/ms/blueprintsprocessor/modules/commons/rest-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/rest/service/RestLoggerService.kt index cec11ae3c..969de836c 100644 --- a/ms/blueprintsprocessor/modules/commons/rest-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/rest/service/RestLoggerService.kt +++ b/ms/blueprintsprocessor/modules/commons/rest-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/rest/service/RestLoggerService.kt @@ -19,6 +19,7 @@ package org.onap.ccsdk.cds.blueprintsprocessor.rest.service import kotlinx.coroutines.* import kotlinx.coroutines.reactor.ReactorContext import kotlinx.coroutines.reactor.asCoroutineContext +import org.apache.http.message.BasicHeader import org.onap.ccsdk.cds.controllerblueprints.core.BluePrintConstants.ONAP_INVOCATION_ID import org.onap.ccsdk.cds.controllerblueprints.core.BluePrintConstants.ONAP_PARTNER_NAME import org.onap.ccsdk.cds.controllerblueprints.core.BluePrintConstants.ONAP_REQUEST_ID @@ -36,12 +37,24 @@ import java.net.InetAddress import java.time.ZoneOffset import java.time.ZonedDateTime import java.time.format.DateTimeFormatter +import java.util.* import kotlin.coroutines.CoroutineContext import kotlin.coroutines.EmptyCoroutineContext class RestLoggerService { private val log = logger(RestLoggerService::class) + companion object { + /** Used before invoking any REST outbound request, Inbound Invocation ID is used as request Id + * for outbound Request, If invocation Id is missing then default Request Id will be generated. + */ + fun httpInvoking(headers: Array<BasicHeader>) { + headers.plusElement(BasicHeader(ONAP_REQUEST_ID, MDC.get("InvocationID").defaultToUUID())) + headers.plusElement(BasicHeader(ONAP_INVOCATION_ID, UUID.randomUUID().toString())) + val partnerName = System.getProperty("APPNAME") ?: "BlueprintsProcessor" + headers.plusElement(BasicHeader(ONAP_PARTNER_NAME, partnerName)) + } + } fun entering(request: ServerHttpRequest) { val localhost = InetAddress.getLocalHost() @@ -54,7 +67,7 @@ class RestLoggerService { MDC.put("InvocationID", invocationID) MDC.put("PartnerName", partnerName) MDC.put("ClientIPAddress", request.remoteAddress?.address?.hostAddress.defaultToEmpty()) - MDC.put("ServerFQDN",localhost.hostName.defaultToEmpty()) + MDC.put("ServerFQDN", localhost.hostName.defaultToEmpty()) if (MDC.get("ServiceName") == null || MDC.get("ServiceName").equals("", ignoreCase = true)) { MDC.put("ServiceName", request.uri.path) } diff --git a/ms/blueprintsprocessor/modules/commons/rest-lib/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/rest/service/BluePrintRestLibPropertyServiceTest.kt b/ms/blueprintsprocessor/modules/commons/rest-lib/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/rest/service/BluePrintRestLibPropertyServiceTest.kt index b617dab90..1e4518a8c 100644 --- a/ms/blueprintsprocessor/modules/commons/rest-lib/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/rest/service/BluePrintRestLibPropertyServiceTest.kt +++ b/ms/blueprintsprocessor/modules/commons/rest-lib/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/rest/service/BluePrintRestLibPropertyServiceTest.kt @@ -23,8 +23,8 @@ import com.fasterxml.jackson.databind.JsonNode import com.fasterxml.jackson.databind.ObjectMapper import org.junit.Test import org.junit.runner.RunWith -import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintProperties -import org.onap.ccsdk.cds.blueprintsprocessor.core.BlueprintPropertyConfiguration +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertiesService +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertyConfiguration import org.onap.ccsdk.cds.blueprintsprocessor.rest.BluePrintRestLibConfiguration import org.onap.ccsdk.cds.blueprintsprocessor.rest.SSLBasicAuthRestClientProperties import org.onap.ccsdk.cds.blueprintsprocessor.rest.SSLRestClientProperties @@ -41,7 +41,8 @@ import kotlin.test.assertFailsWith import kotlin.test.assertNotNull @RunWith(SpringRunner::class) -@ContextConfiguration(classes = [BluePrintRestLibConfiguration::class, BlueprintPropertyConfiguration::class, BluePrintProperties::class]) +@ContextConfiguration(classes = [BluePrintRestLibConfiguration::class, BluePrintPropertyConfiguration::class, + BluePrintPropertiesService::class]) @TestPropertySource(properties = ["blueprintsprocessor.restclient.sample.type=basic-auth", "blueprintsprocessor.restclient.sample.url=http://localhost:8080", diff --git a/ms/blueprintsprocessor/modules/commons/rest-lib/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/rest/service/RestClientServiceTest.kt b/ms/blueprintsprocessor/modules/commons/rest-lib/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/rest/service/RestClientServiceTest.kt index 46d171b5d..05f32904a 100644 --- a/ms/blueprintsprocessor/modules/commons/rest-lib/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/rest/service/RestClientServiceTest.kt +++ b/ms/blueprintsprocessor/modules/commons/rest-lib/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/rest/service/RestClientServiceTest.kt @@ -27,8 +27,8 @@ import org.junit.After import org.junit.Before import org.junit.Test import org.junit.runner.RunWith -import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintProperties -import org.onap.ccsdk.cds.blueprintsprocessor.core.BlueprintPropertyConfiguration +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertiesService +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertyConfiguration import org.onap.ccsdk.cds.blueprintsprocessor.rest.BluePrintRestLibConfiguration import org.springframework.beans.factory.annotation.Autowired import org.springframework.boot.autoconfigure.EnableAutoConfiguration @@ -57,7 +57,7 @@ import kotlin.test.assertNotNull @SpringBootTest(webEnvironment = SpringBootTest.WebEnvironment.DEFINED_PORT) @ContextConfiguration(classes = [BluePrintRestLibConfiguration::class, SampleController::class, SecurityConfiguration::class, - BlueprintPropertyConfiguration::class, BluePrintProperties::class]) + BluePrintPropertyConfiguration::class, BluePrintPropertiesService::class]) @TestPropertySource(properties = [ "server.port=8443", diff --git a/ms/blueprintsprocessor/modules/commons/ssh-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/ssh/service/BluePrintSshLibPropertyService.kt b/ms/blueprintsprocessor/modules/commons/ssh-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/ssh/service/BluePrintSshLibPropertyService.kt index 829fdda8e..337208c78 100644 --- a/ms/blueprintsprocessor/modules/commons/ssh-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/ssh/service/BluePrintSshLibPropertyService.kt +++ b/ms/blueprintsprocessor/modules/commons/ssh-lib/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/ssh/service/BluePrintSshLibPropertyService.kt @@ -17,7 +17,7 @@ package org.onap.ccsdk.cds.blueprintsprocessor.ssh.service import com.fasterxml.jackson.databind.JsonNode -import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintProperties +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertiesService import org.onap.ccsdk.cds.blueprintsprocessor.ssh.BasicAuthSshClientProperties import org.onap.ccsdk.cds.blueprintsprocessor.ssh.SshClientProperties import org.onap.ccsdk.cds.blueprintsprocessor.ssh.SshLibConstants @@ -26,7 +26,7 @@ import org.onap.ccsdk.cds.controllerblueprints.core.utils.JacksonUtils import org.springframework.stereotype.Service @Service(SshLibConstants.SERVICE_BLUEPRINT_SSH_LIB_PROPERTY) -open class BluePrintSshLibPropertyService(private var bluePrintProperties: BluePrintProperties) { +open class BluePrintSshLibPropertyService(private var bluePrintProperties: BluePrintPropertiesService) { fun blueprintSshClientService(jsonNode: JsonNode): BlueprintSshClientService { val restClientProperties = sshClientProperties(jsonNode) diff --git a/ms/blueprintsprocessor/modules/commons/ssh-lib/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/ssh/service/BluePrintSshLibPropertyServiceTest.kt b/ms/blueprintsprocessor/modules/commons/ssh-lib/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/ssh/service/BluePrintSshLibPropertyServiceTest.kt index d5c99935c..f4275b8f2 100644 --- a/ms/blueprintsprocessor/modules/commons/ssh-lib/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/ssh/service/BluePrintSshLibPropertyServiceTest.kt +++ b/ms/blueprintsprocessor/modules/commons/ssh-lib/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/ssh/service/BluePrintSshLibPropertyServiceTest.kt @@ -18,8 +18,8 @@ package org.onap.ccsdk.cds.blueprintsprocessor.ssh.service import org.junit.Test import org.junit.runner.RunWith -import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintProperties -import org.onap.ccsdk.cds.blueprintsprocessor.core.BlueprintPropertyConfiguration +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertiesService +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertyConfiguration import org.onap.ccsdk.cds.blueprintsprocessor.ssh.BasicAuthSshClientProperties import org.onap.ccsdk.cds.blueprintsprocessor.ssh.BluePrintSshLibConfiguration import org.springframework.beans.factory.annotation.Autowired @@ -32,7 +32,7 @@ import kotlin.test.assertNotNull @RunWith(SpringRunner::class) @ContextConfiguration(classes = [BluePrintSshLibConfiguration::class, - BlueprintPropertyConfiguration::class, BluePrintProperties::class]) + BluePrintPropertyConfiguration::class, BluePrintPropertiesService::class]) @TestPropertySource(properties = ["blueprintsprocessor.sshclient.sample.type=basic-auth", "blueprintsprocessor.sshclient.sample.host=127.0.0.1", diff --git a/ms/blueprintsprocessor/modules/commons/ssh-lib/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/ssh/service/BlueprintSshClientServiceTest.kt b/ms/blueprintsprocessor/modules/commons/ssh-lib/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/ssh/service/BlueprintSshClientServiceTest.kt index d61219215..430b988a4 100644 --- a/ms/blueprintsprocessor/modules/commons/ssh-lib/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/ssh/service/BlueprintSshClientServiceTest.kt +++ b/ms/blueprintsprocessor/modules/commons/ssh-lib/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/ssh/service/BlueprintSshClientServiceTest.kt @@ -26,8 +26,8 @@ import org.apache.sshd.server.keyprovider.SimpleGeneratorHostKeyProvider import org.apache.sshd.server.session.ServerSession import org.apache.sshd.server.shell.ProcessShellCommandFactory import org.junit.runner.RunWith -import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintProperties -import org.onap.ccsdk.cds.blueprintsprocessor.core.BlueprintPropertyConfiguration +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertiesService +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertyConfiguration import org.onap.ccsdk.cds.blueprintsprocessor.ssh.BluePrintSshLibConfiguration import org.springframework.beans.factory.annotation.Autowired import org.springframework.test.context.ContextConfiguration @@ -41,7 +41,7 @@ import kotlin.test.assertNotNull @RunWith(SpringRunner::class) @ContextConfiguration(classes = [BluePrintSshLibConfiguration::class, - BlueprintPropertyConfiguration::class, BluePrintProperties::class]) + BluePrintPropertyConfiguration::class, BluePrintPropertiesService::class]) @TestPropertySource(properties = ["blueprintsprocessor.sshclient.sample.type=basic-auth", "blueprintsprocessor.sshclient.sample.host=localhost", diff --git a/ms/blueprintsprocessor/modules/inbounds/designer-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/designer/api/BlueprintModelController.kt b/ms/blueprintsprocessor/modules/inbounds/designer-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/designer/api/BlueprintModelController.kt index 10cc0a44a..ea5023cd5 100644 --- a/ms/blueprintsprocessor/modules/inbounds/designer-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/designer/api/BlueprintModelController.kt +++ b/ms/blueprintsprocessor/modules/inbounds/designer-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/designer/api/BlueprintModelController.kt @@ -1,6 +1,7 @@ /* * Copyright © 2019 Bell Canada Intellectual Property. * Modifications Copyright © 2019 IBM. + * Modifications Copyright © 2019 Orange. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -19,6 +20,7 @@ package org.onap.ccsdk.cds.blueprintsprocessor.designer.api import io.swagger.annotations.ApiOperation import io.swagger.annotations.ApiParam +import org.jetbrains.annotations.NotNull import org.onap.ccsdk.cds.blueprintsprocessor.db.primary.domain.BlueprintModelSearch import org.onap.ccsdk.cds.blueprintsprocessor.designer.api.handler.BluePrintModelHandler import org.onap.ccsdk.cds.blueprintsprocessor.designer.api.utils.BlueprintSortByOption @@ -70,6 +72,14 @@ open class BlueprintModelController(private val bluePrintModelHandler: BluePrint return this.bluePrintModelHandler.allBlueprintModel(pageRequest) } + @GetMapping("meta-data/{keyword}", produces = [MediaType.APPLICATION_JSON_VALUE]) + @ResponseBody + @PreAuthorize("hasRole('USER')") + fun allBlueprintModelMetaData(@NotNull @PathVariable(value = "keyword") keyWord: String): List<BlueprintModelSearch> { + return this.bluePrintModelHandler.searchBluePrintModelsByKeyWord(keyWord) + } + + @DeleteMapping("/{id}") @Throws(BluePrintException::class) @PreAuthorize("hasRole('USER')") diff --git a/ms/blueprintsprocessor/modules/inbounds/designer-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/designer/api/handler/BluePrintModelHandler.kt b/ms/blueprintsprocessor/modules/inbounds/designer-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/designer/api/handler/BluePrintModelHandler.kt index f4b006867..19076c681 100644 --- a/ms/blueprintsprocessor/modules/inbounds/designer-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/designer/api/handler/BluePrintModelHandler.kt +++ b/ms/blueprintsprocessor/modules/inbounds/designer-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/designer/api/handler/BluePrintModelHandler.kt @@ -2,6 +2,7 @@ * Copyright © 2017-2018 AT&T Intellectual Property. * Modifications Copyright © 2019 Bell Canada. * Modifications Copyright © 2019 IBM. + * Modifications Copyright © 2019 Orange. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -232,6 +233,20 @@ open class BluePrintModelHandler(private val blueprintsProcessorCatalogService: } /** + * This is a searchBluePrintModelsByKeyWord method to retrieve specific BlueprintModel in Database + * where keyword equals updatedBy or tags or artifcat name or artifcat version or artifact type + * @author Shaaban Ebrahim + * @param keyWord + * + * @return List<BlueprintModelSearch> list of the controller blueprint + </BlueprintModelSearch> */ + open fun searchBluePrintModelsByKeyWord(keyWord: String): List<BlueprintModelSearch> { + return blueprintModelSearchRepository. + findByUpdatedByOrTagsOrOrArtifactNameOrOrArtifactVersionOrArtifactType( + keyWord,keyWord,keyWord,keyWord,keyWord) + } + + /** * This is a deleteBlueprintModel method * * @param id id diff --git a/ms/blueprintsprocessor/modules/inbounds/designer-api/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/designer/api/BlueprintModelControllerTest.kt b/ms/blueprintsprocessor/modules/inbounds/designer-api/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/designer/api/BlueprintModelControllerTest.kt index 0d834d21c..149acb03c 100644 --- a/ms/blueprintsprocessor/modules/inbounds/designer-api/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/designer/api/BlueprintModelControllerTest.kt +++ b/ms/blueprintsprocessor/modules/inbounds/designer-api/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/designer/api/BlueprintModelControllerTest.kt @@ -26,8 +26,8 @@ import org.junit.FixMethodOrder import org.junit.Test import org.junit.runner.RunWith import org.junit.runners.MethodSorters -import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintProperties -import org.onap.ccsdk.cds.blueprintsprocessor.core.BlueprintPropertyConfiguration +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertiesService +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertyConfiguration import org.onap.ccsdk.cds.blueprintsprocessor.db.BluePrintDBLibConfiguration import org.onap.ccsdk.cds.blueprintsprocessor.db.primary.domain.BlueprintModelSearch import org.onap.ccsdk.cds.controllerblueprints.core.* @@ -61,7 +61,7 @@ import kotlin.test.assertTrue @RunWith(SpringRunner::class) @SpringBootTest(webEnvironment = SpringBootTest.WebEnvironment.RANDOM_PORT) @ContextConfiguration(classes = [DesignerApiTestConfiguration::class, - BlueprintPropertyConfiguration::class, BluePrintProperties::class, BluePrintDBLibConfiguration::class]) + BluePrintPropertyConfiguration::class, BluePrintPropertiesService::class, BluePrintDBLibConfiguration::class]) @TestPropertySource(locations = ["classpath:application-test.properties"]) @FixMethodOrder(MethodSorters.NAME_ASCENDING) class BlueprintModelControllerTest { diff --git a/ms/blueprintsprocessor/modules/inbounds/designer-api/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/designer/api/ModelTypeControllerTest.kt b/ms/blueprintsprocessor/modules/inbounds/designer-api/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/designer/api/ModelTypeControllerTest.kt index 6fe7097e5..8871676d2 100644 --- a/ms/blueprintsprocessor/modules/inbounds/designer-api/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/designer/api/ModelTypeControllerTest.kt +++ b/ms/blueprintsprocessor/modules/inbounds/designer-api/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/designer/api/ModelTypeControllerTest.kt @@ -21,8 +21,8 @@ import org.junit.FixMethodOrder import org.junit.Test import org.junit.runner.RunWith import org.junit.runners.MethodSorters -import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintProperties -import org.onap.ccsdk.cds.blueprintsprocessor.core.BlueprintPropertyConfiguration +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertiesService +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertyConfiguration import org.onap.ccsdk.cds.blueprintsprocessor.db.BluePrintDBLibConfiguration import org.onap.ccsdk.cds.controllerblueprints.core.BluePrintConstants import org.onap.ccsdk.cds.controllerblueprints.core.utils.JacksonUtils @@ -36,7 +36,7 @@ import org.springframework.test.context.junit4.SpringRunner @RunWith(SpringRunner::class) @ContextConfiguration(classes = [DesignerApiTestConfiguration::class, - BlueprintPropertyConfiguration::class, BluePrintProperties::class, BluePrintDBLibConfiguration::class]) + BluePrintPropertyConfiguration::class, BluePrintPropertiesService::class, BluePrintDBLibConfiguration::class]) @TestPropertySource(locations = ["classpath:application-test.properties"]) @FixMethodOrder(MethodSorters.NAME_ASCENDING) class ModelTypeControllerTest { diff --git a/ms/blueprintsprocessor/modules/inbounds/designer-api/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/designer/api/ResourceDictionaryControllerTest.kt b/ms/blueprintsprocessor/modules/inbounds/designer-api/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/designer/api/ResourceDictionaryControllerTest.kt index 893622308..b13b1ac08 100644 --- a/ms/blueprintsprocessor/modules/inbounds/designer-api/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/designer/api/ResourceDictionaryControllerTest.kt +++ b/ms/blueprintsprocessor/modules/inbounds/designer-api/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/designer/api/ResourceDictionaryControllerTest.kt @@ -20,8 +20,8 @@ import org.junit.FixMethodOrder import org.junit.Test import org.junit.runner.RunWith import org.junit.runners.MethodSorters -import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintProperties -import org.onap.ccsdk.cds.blueprintsprocessor.core.BlueprintPropertyConfiguration +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertiesService +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertyConfiguration import org.onap.ccsdk.cds.blueprintsprocessor.db.BluePrintDBLibConfiguration import org.springframework.beans.factory.annotation.Autowired import org.springframework.boot.test.context.SpringBootTest @@ -33,7 +33,7 @@ import kotlin.test.assertNotNull @RunWith(SpringRunner::class) @SpringBootTest(webEnvironment = SpringBootTest.WebEnvironment.RANDOM_PORT) @ContextConfiguration(classes = [DesignerApiTestConfiguration::class, - BlueprintPropertyConfiguration::class, BluePrintProperties::class, BluePrintDBLibConfiguration::class]) + BluePrintPropertyConfiguration::class, BluePrintPropertiesService::class, BluePrintDBLibConfiguration::class]) @TestPropertySource(locations = ["classpath:application-test.properties"]) @FixMethodOrder(MethodSorters.NAME_ASCENDING) class ResourceDictionaryControllerTest { diff --git a/ms/blueprintsprocessor/modules/inbounds/designer-api/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/designer/api/enhancer/BluePrintEnhancerServiceImplTest.kt b/ms/blueprintsprocessor/modules/inbounds/designer-api/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/designer/api/enhancer/BluePrintEnhancerServiceImplTest.kt index 974a3b9b7..a5a0511f5 100644 --- a/ms/blueprintsprocessor/modules/inbounds/designer-api/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/designer/api/enhancer/BluePrintEnhancerServiceImplTest.kt +++ b/ms/blueprintsprocessor/modules/inbounds/designer-api/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/designer/api/enhancer/BluePrintEnhancerServiceImplTest.kt @@ -21,8 +21,8 @@ import kotlinx.coroutines.runBlocking import org.junit.Assert import org.junit.Test import org.junit.runner.RunWith -import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintProperties -import org.onap.ccsdk.cds.blueprintsprocessor.core.BlueprintPropertyConfiguration +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertiesService +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertyConfiguration import org.onap.ccsdk.cds.blueprintsprocessor.db.BluePrintDBLibConfiguration import org.onap.ccsdk.cds.blueprintsprocessor.designer.api.DesignerApiTestConfiguration import org.onap.ccsdk.cds.blueprintsprocessor.designer.api.load.ModelTypeLoadService @@ -38,7 +38,7 @@ import org.springframework.test.context.junit4.SpringRunner @RunWith(SpringRunner::class) @ContextConfiguration(classes = [DesignerApiTestConfiguration::class, - BlueprintPropertyConfiguration::class, BluePrintProperties::class, BluePrintDBLibConfiguration::class]) + BluePrintPropertyConfiguration::class, BluePrintPropertiesService::class, BluePrintDBLibConfiguration::class]) @TestPropertySource(locations = ["classpath:application-test.properties"]) class BluePrintEnhancerServiceImplTest { diff --git a/ms/blueprintsprocessor/modules/inbounds/designer-api/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/designer/api/handler/ModelTypeServiceTest.kt b/ms/blueprintsprocessor/modules/inbounds/designer-api/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/designer/api/handler/ModelTypeServiceTest.kt index 00e78d247..7ea845dee 100644 --- a/ms/blueprintsprocessor/modules/inbounds/designer-api/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/designer/api/handler/ModelTypeServiceTest.kt +++ b/ms/blueprintsprocessor/modules/inbounds/designer-api/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/designer/api/handler/ModelTypeServiceTest.kt @@ -22,8 +22,8 @@ import org.junit.FixMethodOrder import org.junit.Test import org.junit.runner.RunWith import org.junit.runners.MethodSorters -import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintProperties -import org.onap.ccsdk.cds.blueprintsprocessor.core.BlueprintPropertyConfiguration +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertiesService +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertyConfiguration import org.onap.ccsdk.cds.blueprintsprocessor.db.BluePrintDBLibConfiguration import org.onap.ccsdk.cds.blueprintsprocessor.designer.api.DesignerApiTestConfiguration import org.onap.ccsdk.cds.controllerblueprints.core.BluePrintConstants @@ -39,7 +39,7 @@ import org.springframework.test.context.junit4.SpringRunner @RunWith(SpringRunner::class) @ContextConfiguration(classes = [DesignerApiTestConfiguration::class, - BlueprintPropertyConfiguration::class, BluePrintProperties::class, BluePrintDBLibConfiguration::class]) + BluePrintPropertyConfiguration::class, BluePrintPropertiesService::class, BluePrintDBLibConfiguration::class]) @TestPropertySource(locations = ["classpath:application-test.properties"]) @FixMethodOrder(MethodSorters.NAME_ASCENDING) class ModelTypeServiceTest { diff --git a/ms/blueprintsprocessor/modules/inbounds/designer-api/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/designer/api/repository/ModelTypeReactRepositoryTest.kt b/ms/blueprintsprocessor/modules/inbounds/designer-api/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/designer/api/repository/ModelTypeReactRepositoryTest.kt index 55bc1e4af..3dfed1ccb 100644 --- a/ms/blueprintsprocessor/modules/inbounds/designer-api/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/designer/api/repository/ModelTypeReactRepositoryTest.kt +++ b/ms/blueprintsprocessor/modules/inbounds/designer-api/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/designer/api/repository/ModelTypeReactRepositoryTest.kt @@ -21,8 +21,8 @@ import org.junit.FixMethodOrder import org.junit.Test import org.junit.runner.RunWith import org.junit.runners.MethodSorters -import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintProperties -import org.onap.ccsdk.cds.blueprintsprocessor.core.BlueprintPropertyConfiguration +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertiesService +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertyConfiguration import org.onap.ccsdk.cds.blueprintsprocessor.db.BluePrintDBLibConfiguration import org.onap.ccsdk.cds.blueprintsprocessor.designer.api.DesignerApiTestConfiguration import org.onap.ccsdk.cds.controllerblueprints.core.BluePrintConstants @@ -45,7 +45,7 @@ import java.util.* @RunWith(SpringRunner::class) @ContextConfiguration(classes = [DesignerApiTestConfiguration::class, - BlueprintPropertyConfiguration::class, BluePrintProperties::class, BluePrintDBLibConfiguration::class]) + BluePrintPropertyConfiguration::class, BluePrintPropertiesService::class, BluePrintDBLibConfiguration::class]) @TestPropertySource(locations = ["classpath:application-test.properties"]) @FixMethodOrder(MethodSorters.NAME_ASCENDING) class ModelTypeReactRepositoryTest { diff --git a/ms/blueprintsprocessor/modules/inbounds/designer-api/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/designer/api/repository/ResourceDictionaryRepositoryTest.kt b/ms/blueprintsprocessor/modules/inbounds/designer-api/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/designer/api/repository/ResourceDictionaryRepositoryTest.kt index 70e1b8ed2..6351f6aa0 100644 --- a/ms/blueprintsprocessor/modules/inbounds/designer-api/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/designer/api/repository/ResourceDictionaryRepositoryTest.kt +++ b/ms/blueprintsprocessor/modules/inbounds/designer-api/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/designer/api/repository/ResourceDictionaryRepositoryTest.kt @@ -21,8 +21,8 @@ import org.junit.FixMethodOrder import org.junit.Test import org.junit.runner.RunWith import org.junit.runners.MethodSorters -import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintProperties -import org.onap.ccsdk.cds.blueprintsprocessor.core.BlueprintPropertyConfiguration +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertiesService +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertyConfiguration import org.onap.ccsdk.cds.blueprintsprocessor.db.BluePrintDBLibConfiguration import org.onap.ccsdk.cds.blueprintsprocessor.designer.api.DesignerApiTestConfiguration import org.onap.ccsdk.cds.blueprintsprocessor.designer.api.domain.ResourceDictionary @@ -37,7 +37,7 @@ import org.springframework.transaction.annotation.Transactional @RunWith(SpringRunner::class) @ContextConfiguration(classes = [DesignerApiTestConfiguration::class, - BlueprintPropertyConfiguration::class, BluePrintProperties::class, BluePrintDBLibConfiguration::class]) + BluePrintPropertyConfiguration::class, BluePrintPropertiesService::class, BluePrintDBLibConfiguration::class]) @TestPropertySource(locations = ["classpath:application-test.properties"]) @FixMethodOrder(MethodSorters.NAME_ASCENDING) class ResourceDictionaryReactRepositoryTest { diff --git a/ms/blueprintsprocessor/modules/inbounds/health-api-common/.gitignore b/ms/blueprintsprocessor/modules/inbounds/health-api-common/.gitignore new file mode 100644 index 000000000..a2a3040aa --- /dev/null +++ b/ms/blueprintsprocessor/modules/inbounds/health-api-common/.gitignore @@ -0,0 +1,31 @@ +HELP.md +target/ +!.mvn/wrapper/maven-wrapper.jar +!**/src/main/** +!**/src/test/** + +### STS ### +.apt_generated +.classpath +.factorypath +.project +.settings +.springBeans +.sts4-cache + +### IntelliJ IDEA ### +.idea +*.iws +*.iml +*.ipr + +### NetBeans ### +/nbproject/private/ +/nbbuild/ +/dist/ +/nbdist/ +/.nb-gradle/ +build/ + +### VS Code ### +.vscode/ diff --git a/ms/blueprintsprocessor/modules/inbounds/health-api-common/pom.xml b/ms/blueprintsprocessor/modules/inbounds/health-api-common/pom.xml new file mode 100644 index 000000000..2bd6782a7 --- /dev/null +++ b/ms/blueprintsprocessor/modules/inbounds/health-api-common/pom.xml @@ -0,0 +1,51 @@ +<?xml version="1.0" encoding="UTF-8"?> +<!-- + ~ Copyright © 2019-2020 Orange. + + ~ + ~ 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. + --> +<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> + + <parent> + <groupId>org.onap.ccsdk.cds.blueprintsprocessor</groupId> + <artifactId>inbounds</artifactId> + <version>0.7.0-SNAPSHOT</version> + </parent> + + <artifactId>health-api-common</artifactId> + <packaging>jar</packaging> + + <name>Blueprints Processor Health API common </name> + <description>checking system check health endpoints</description> + + <dependencies> + <dependency> + <groupId>org.onap.ccsdk.cds.blueprintsprocessor</groupId> + <artifactId>rest-lib</artifactId> + </dependency> + + + <dependency> + <groupId>org.springframework.boot</groupId> + <artifactId>spring-boot-starter-actuator</artifactId> + <exclusions> + <exclusion> + <groupId>org.springframework.boot</groupId> + <artifactId>spring-boot-starter-logging</artifactId> + </exclusion> + </exclusions> + </dependency> + </dependencies> +</project> diff --git a/ms/blueprintsprocessor/modules/inbounds/health-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/configuration/BasicAuthRestClientServiceConfiguration.kt b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/configuration/BasicAuthRestClientServiceConfiguration.kt index 0a97d37c5..0c6099a1a 100644 --- a/ms/blueprintsprocessor/modules/inbounds/health-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/configuration/BasicAuthRestClientServiceConfiguration.kt +++ b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/configuration/BasicAuthRestClientServiceConfiguration.kt @@ -25,7 +25,7 @@ import org.springframework.context.annotation.PropertySource @Configuration @PropertySource("classpath:application.properties") -open class BasicAuthRestClientServiceConfiguration { +open class BasicAuthRestClientServiceConfiguration(private val securityConfiguration: SecurityEncryptionConfiguration) { @Value("\${endpoints.user.name}") private val username: String? = null @@ -36,8 +36,8 @@ open class BasicAuthRestClientServiceConfiguration { @Bean open fun getBasicAuthRestClientProperties(): BasicAuthRestClientProperties { val basicAuthRestClientProperties = BasicAuthRestClientProperties() - basicAuthRestClientProperties.username = username.toString() - basicAuthRestClientProperties.password = password.toString() + basicAuthRestClientProperties.username = securityConfiguration.decrypt(username!!)!! + basicAuthRestClientProperties.password = securityConfiguration.decrypt(password!!)!! return basicAuthRestClientProperties } @@ -46,5 +46,4 @@ open class BasicAuthRestClientServiceConfiguration { return BasicAuthRestClientService(getBasicAuthRestClientProperties()) } - } diff --git a/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/configuration/HealthCheckProperties.kt b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/configuration/HealthCheckProperties.kt new file mode 100644 index 000000000..c63952d80 --- /dev/null +++ b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/configuration/HealthCheckProperties.kt @@ -0,0 +1,92 @@ +/* + * Copyright © 2019-2020 Orange. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.healthapi.configuration + +import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain.ServiceEndpoint +import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain.ServiceName +import org.springframework.beans.factory.annotation.Value +import org.springframework.context.annotation.Configuration +import org.springframework.context.annotation.PropertySource + +@Configuration +@PropertySource("classpath:application.properties") +open class HealthCheckProperties { + + @Value("\${blueprintprocessor.healthcheck.baseUrl}") + private val bluePrintProcessorBaseURL: String? = null + + @Value("#{'\${blueprintprocessor.healthcheck.mapping-service-name-with-service-link}'.split(']')}") + private val blueprintprocessorServiceMapping: List<String>? = null + + @Value("\${cdslistener.healthcheck.baseUrl}") + private val cdsListenerBaseURL: String? = null + + @Value("#{'\${cdslistener.healthcheck.mapping-service-name-with-service-link}'.split(']')}") + private val cdsListenerServiceMapping: List<String>? = null + + open fun getBluePrintBaseURL(): String? { + return bluePrintProcessorBaseURL + } + + open fun getCDSListenerBaseURL(): String? { + return cdsListenerBaseURL + } + + open fun getBluePrintServiceInformation(): List<ServiceEndpoint> { + val serviceName = ServiceName.BLUEPRINT + return getListOfServiceEndPoints(blueprintprocessorServiceMapping, serviceName) + } + + open fun getCDSListenerServiceInformation(): List<ServiceEndpoint> { + val serviceName = ServiceName.BLUEPRINT + return getListOfServiceEndPoints(cdsListenerServiceMapping, serviceName) + + } + + private fun getListOfServiceEndPoints(serviceMapping: List<String>?, serviceName: ServiceName): MutableList<ServiceEndpoint> { + val serviceEndpoints = mutableListOf<ServiceEndpoint>() + if (serviceMapping != null) { + for (element in serviceMapping) { + fillListOfService(serviceName, element, serviceEndpoints) + } + } + return serviceEndpoints + } + + private fun fillListOfService(serviceName: ServiceName , element: String, listOfCDSListenerServiceEndpoint: MutableList<ServiceEndpoint>) { + val serviceEndpointInfo = element.split(",/") + val serviceEndpoint = getServiceEndpoint(serviceEndpointInfo) + if (serviceName.equals(ServiceName.CDSLISTENER)) + serviceEndpoint.serviceLink = cdsListenerBaseURL + serviceEndpoint.serviceLink + else if (serviceName.equals(ServiceName.BLUEPRINT)) + serviceEndpoint.serviceLink = bluePrintProcessorBaseURL + serviceEndpoint.serviceLink + listOfCDSListenerServiceEndpoint.add(serviceEndpoint) + } + + + private fun getServiceEndpoint(serviceEndpointInfo: List<String>): ServiceEndpoint { + return ServiceEndpoint(removeSpecialCharacter(serviceEndpointInfo.get(0)) + , removeSpecialCharacter(serviceEndpointInfo.get(1)) + ) + } + + private fun removeSpecialCharacter(value:String):String{ + return value.replaceFirst(",[","") + .replace("[","") + .replace("]","") + } +} diff --git a/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/configuration/SecurityEncryptionConfiguration.kt b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/configuration/SecurityEncryptionConfiguration.kt new file mode 100644 index 000000000..94021207a --- /dev/null +++ b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/configuration/SecurityEncryptionConfiguration.kt @@ -0,0 +1,63 @@ +/* + * Copyright © 2019-2020 Orange. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.healthapi.configuration + + +import org.apache.commons.net.util.Base64 +import org.springframework.stereotype.Component +import org.springframework.stereotype.Service +import javax.crypto.Cipher +import javax.crypto.spec.IvParameterSpec +import javax.crypto.spec.SecretKeySpec + + +@Component +class SecurityEncryptionConfiguration { + private val key = "aesEncryptionKey" + private val initVector = "encryptionIntVec" + + fun encrypt(value: String): String? { + try { + val (iv, skeySpec, cipher) = initChiper() + cipher.init(Cipher.ENCRYPT_MODE, skeySpec, iv) + val encrypted = cipher.doFinal(value.toByteArray()) + return Base64.encodeBase64String(encrypted) + } catch (ex: Exception) { + ex.printStackTrace() + } + return String() + } + + open fun decrypt(encrypted: String): String? { + try { + val (iv, skeySpec, cipher) = initChiper() + cipher.init(Cipher.DECRYPT_MODE, skeySpec, iv) + val original = cipher.doFinal(Base64.decodeBase64(encrypted)) + return String(original) + } catch (ex: Exception) { + ex.printStackTrace() + } + return String() + } + + private fun initChiper(): Triple<IvParameterSpec, SecretKeySpec, Cipher> { + val iv = IvParameterSpec(initVector.toByteArray(charset("UTF-8"))) + val secretKeySpec = SecretKeySpec(key.toByteArray(charset("UTF-8")), "AES") + val cipher = Cipher.getInstance("AES/CBC/PKCS5PADDING") + return Triple(iv, secretKeySpec, cipher) + } +} diff --git a/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/ActuatorCheckResponse.kt b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/ActuatorCheckResponse.kt new file mode 100644 index 000000000..1b82083dd --- /dev/null +++ b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/ActuatorCheckResponse.kt @@ -0,0 +1,19 @@ +/* + * Copyright © 2019-2020 Orange. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain + +data class ActuatorCheckResponse(val serviceName: String, val details: Any) diff --git a/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/ActuatorEndpointType.kt b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/ActuatorEndpointType.kt new file mode 100644 index 000000000..ee186b1b9 --- /dev/null +++ b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/ActuatorEndpointType.kt @@ -0,0 +1,21 @@ +/* + * Copyright © 2019-2020 Orange. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain + +enum class ActuatorEndpointType { + METRICS(), LOGGERS(), MAPPING() +} diff --git a/ms/blueprintsprocessor/modules/commons/processor-core/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/core/BluePrintProperties.kt b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/ApplicationHealth.kt index e2a4808a6..f66e8774c 100644 --- a/ms/blueprintsprocessor/modules/commons/processor-core/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/core/BluePrintProperties.kt +++ b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/ApplicationHealth.kt @@ -1,5 +1,5 @@ /* - * Copyright © 2017-2018 AT&T Intellectual Property. + * Copyright © 2019-2020 Orange. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -14,16 +14,12 @@ * limitations under the License. */ -package org.onap.ccsdk.cds.blueprintsprocessor.core +package org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain -import org.springframework.boot.context.properties.bind.Bindable -import org.springframework.boot.context.properties.bind.Binder -import org.springframework.stereotype.Service +import org.springframework.boot.actuate.health.Status + +data class ApplicationHealth(val status: Status?, val details: Map<String, Any>?) { + constructor() : this(null, HashMap()) +} -@Service -open class BluePrintProperties(var bluePrintPropertyBinder: Binder) { - fun <T> propertyBeanType(prefix: String, type: Class<T>): T { - return bluePrintPropertyBinder.bind(prefix, Bindable.of(type)).get() - } -}
\ No newline at end of file diff --git a/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/HealthApiResponse.kt b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/HealthApiResponse.kt new file mode 100644 index 000000000..61d8120d4 --- /dev/null +++ b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/HealthApiResponse.kt @@ -0,0 +1,23 @@ +/* + * Copyright © 2019-2020 Orange. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain + + +data class HealthApiResponse(val status: HealthCheckStatus, val checks: List<ServicesCheckResponse> +) + + diff --git a/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/HealthCheckStatus.kt b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/HealthCheckStatus.kt new file mode 100644 index 000000000..b60669d01 --- /dev/null +++ b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/HealthCheckStatus.kt @@ -0,0 +1,22 @@ +/* + * Copyright © 2019-2020 Orange. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain + +enum class HealthCheckStatus { + UP, + DOWN +} diff --git a/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/Metrics.kt b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/Metrics.kt new file mode 100644 index 000000000..d9f1c79d4 --- /dev/null +++ b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/Metrics.kt @@ -0,0 +1,22 @@ +/* + * Copyright © 2019-2020 Orange. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain + + +data class Metrics(val names: ArrayList<Any>?) { + constructor() : this(ArrayList()) +} diff --git a/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/MetricsInfo.kt b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/MetricsInfo.kt new file mode 100644 index 000000000..0c2779861 --- /dev/null +++ b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/MetricsInfo.kt @@ -0,0 +1,19 @@ +/* + * Copyright © 2019-2020 Orange. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain + +data class MetricsInfo(val health: List<ActuatorCheckResponse>) diff --git a/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/MetricsResponse.kt b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/MetricsResponse.kt new file mode 100644 index 000000000..b3796c91a --- /dev/null +++ b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/MetricsResponse.kt @@ -0,0 +1,21 @@ +/* + * Copyright © 2019-2020 Orange. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain + +data class MetricsResponse(val maps: HashMap<String, String>) { + +} diff --git a/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/ServiceEndpoint.kt b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/ServiceEndpoint.kt new file mode 100644 index 000000000..ce95a5c0c --- /dev/null +++ b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/ServiceEndpoint.kt @@ -0,0 +1,19 @@ +/* + * Copyright © 2019-2020 Orange. + * + * 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. + */ +package org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain + + +data class ServiceEndpoint(val serviceName: String, var serviceLink: String) diff --git a/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/ServiceName.kt b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/ServiceName.kt new file mode 100644 index 000000000..1a78a5d10 --- /dev/null +++ b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/ServiceName.kt @@ -0,0 +1,21 @@ +/* + * Copyright © 2019-2020 Orange. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain + +enum class ServiceName(s: String) { + BLUEPRINT("Blue Print service"),CDSLISTENER("CDS Listener service") +} diff --git a/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/ServicesCheckResponse.kt b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/ServicesCheckResponse.kt new file mode 100644 index 000000000..391d7f38a --- /dev/null +++ b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/ServicesCheckResponse.kt @@ -0,0 +1,22 @@ +/* + * Copyright © 2019-2020 Orange. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain + + +data class ServicesCheckResponse(val name: String, val status: HealthCheckStatus) + + diff --git a/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/WebClientEnpointResponse.kt b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/WebClientEnpointResponse.kt new file mode 100644 index 000000000..03e864a9d --- /dev/null +++ b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/WebClientEnpointResponse.kt @@ -0,0 +1,22 @@ +/* + * Copyright © 2019-2020 Orange. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain + +import org.onap.ccsdk.cds.blueprintsprocessor.rest.service.BlueprintWebClientService + +data class WebClientEnpointResponse (val response:BlueprintWebClientService.WebClientResponse<String>?) { +} diff --git a/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/service/EndPointExecution.kt b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/service/EndPointExecution.kt new file mode 100644 index 000000000..72fa6c849 --- /dev/null +++ b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/service/EndPointExecution.kt @@ -0,0 +1,70 @@ +/* + * Copyright © 2019-2020 Orange. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.healthapi.service + + +import com.fasterxml.jackson.databind.ObjectMapper +import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain.ApplicationHealth +import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain.ServiceEndpoint +import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain.WebClientEnpointResponse +import org.onap.ccsdk.cds.blueprintsprocessor.rest.BasicAuthRestClientProperties +import org.onap.ccsdk.cds.blueprintsprocessor.rest.service.BasicAuthRestClientService +import org.onap.ccsdk.cds.blueprintsprocessor.rest.service.BlueprintWebClientService +import org.slf4j.LoggerFactory +import org.springframework.http.HttpMethod +import org.springframework.stereotype.Service + +/** + * Service for executing services endpoint with rest-lib project . + * + * @author Shaaban Ebrahim + * @version 1.0 + */ +@Service +open class EndPointExecution(private val basicAuthRestClientService: BasicAuthRestClientService + , private val restClientProperties: BasicAuthRestClientProperties) { + + private var logger = LoggerFactory.getLogger(EndPointExecution::class.java) + + open fun retrieveWebClientResponse(serviceEndpoint: ServiceEndpoint): WebClientEnpointResponse? { + try { + addClientPropertiesConfiguration(serviceEndpoint) + val result = basicAuthRestClientService.exchangeResource(HttpMethod.GET.name, "", "") + if (result.status == 200) + return WebClientEnpointResponse(result) + + } catch (e: Exception) { + logger.error("service name ${serviceEndpoint.serviceName} is down ${e.message}") + } + return WebClientEnpointResponse(BlueprintWebClientService.WebClientResponse(500,"")) + } + + private fun addClientPropertiesConfiguration(serviceEndpoint: ServiceEndpoint) { + restClientProperties.url = serviceEndpoint.serviceLink + } + + + open fun getHealthFromWebClientEnpointResponse(webClientEnpointResponse: WebClientEnpointResponse): ApplicationHealth? { + return mappingMetricsToDTO(webClientEnpointResponse?.response?.body.toString()) + + } + + private fun mappingMetricsToDTO(body: String): ApplicationHealth { + return ObjectMapper().readValue(body, ApplicationHealth::class.java) + } +} + diff --git a/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/service/health/AbstractHealthCheck.kt b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/service/health/AbstractHealthCheck.kt new file mode 100644 index 000000000..f793754e3 --- /dev/null +++ b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/service/health/AbstractHealthCheck.kt @@ -0,0 +1,74 @@ +/* + * Copyright © 2019-2020 Orange. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.healthapi.service.health + +import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain.* +import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.service.EndPointExecution +import org.slf4j.LoggerFactory + +/** + *Abstract class to execute provided Service Endpoint from class that extends it + * by implementing setupServiceEndpoint method + * + * @author Shaaban Ebrahim + * @version 1.0 + */ +abstract class AbstractHealthCheck (private val endPointExecution: EndPointExecution) { + + private var logger = LoggerFactory.getLogger(BluePrintProcessorHealthCheck::class.java) + + private fun retrieveSystemStatus(list: List<ServiceEndpoint>): HealthApiResponse { + val healthApiResponse: HealthApiResponse + val listOfResponse = mutableListOf<ServicesCheckResponse>() + var systemStatus: HealthCheckStatus = HealthCheckStatus.UP + + for (serviceEndpoint in list) { + val serviceStatus: HealthCheckStatus = retrieveServiceStatus(serviceEndpoint) + if (serviceStatus.equals(HealthCheckStatus.DOWN)) + systemStatus = HealthCheckStatus.DOWN + + listOfResponse.add(ServicesCheckResponse(serviceEndpoint.serviceName, serviceStatus)) + } + healthApiResponse = HealthApiResponse(systemStatus, listOfResponse) + return healthApiResponse + + } + + + private fun retrieveServiceStatus(serviceEndpoint: ServiceEndpoint): HealthCheckStatus { + var serviceStatus: HealthCheckStatus = HealthCheckStatus.UP + try { + val result: WebClientEnpointResponse? = endPointExecution?.retrieveWebClientResponse(serviceEndpoint) + if (result == null || result.response?.status != 200) { + serviceStatus = HealthCheckStatus.DOWN + } + } catch (e: Exception) { + logger.error("service name ${serviceEndpoint.serviceName} is down ${e.message}") + serviceStatus = HealthCheckStatus.DOWN + + } + return serviceStatus + } + + + open fun retrieveEndpointExecutionStatus(): HealthApiResponse { + return retrieveSystemStatus(setupServiceEndpoint()) + } + + abstract fun setupServiceEndpoint(): List<ServiceEndpoint> + +} diff --git a/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/service/health/BluePrintProcessorHealthCheck.kt b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/service/health/BluePrintProcessorHealthCheck.kt new file mode 100644 index 000000000..d661b32b5 --- /dev/null +++ b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/service/health/BluePrintProcessorHealthCheck.kt @@ -0,0 +1,38 @@ +/* + * Copyright © 2019-2020 Orange. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.healthapi.service.health + +import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.configuration.HealthCheckProperties +import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain.ServiceEndpoint +import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.service.EndPointExecution +import org.springframework.stereotype.Service + +/** + * Service for checking health for other CDS services . + * + * @author Shaaban Ebrahim + * @version 1.0 + */ +@Service +open class BluePrintProcessorHealthCheck(private val endPointExecution: EndPointExecution + , private val healthCheckProperties: HealthCheckProperties) + : AbstractHealthCheck(endPointExecution) { + + override fun setupServiceEndpoint(): List<ServiceEndpoint> { + return healthCheckProperties.getBluePrintServiceInformation() + } +} diff --git a/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/service/health/SDCListenerHealthCheck.kt b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/service/health/SDCListenerHealthCheck.kt new file mode 100644 index 000000000..0a7c5e092 --- /dev/null +++ b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/service/health/SDCListenerHealthCheck.kt @@ -0,0 +1,46 @@ +/* + * Copyright © 2019-2020 Orange. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.healthapi.service.health + +import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.configuration.HealthCheckProperties +import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain.HealthApiResponse +import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain.HealthCheckStatus +import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain.ServiceEndpoint +import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain.ServicesCheckResponse +import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.service.EndPointExecution +import org.onap.ccsdk.cds.blueprintsprocessor.rest.service.BlueprintWebClientService +import org.slf4j.LoggerFactory +import org.springframework.beans.factory.annotation.Autowired +import org.springframework.stereotype.Service + +/** + * Service for checking health for other CDS listener services . + * + * @author Shaaban Ebrahim + * @version 1.0 + */ +@Service +open class SDCListenerHealthCheck (private val endPointExecution: EndPointExecution + ,private val healthCheckProperties: HealthCheckProperties) + : AbstractHealthCheck(endPointExecution) { + + override fun setupServiceEndpoint(): List<ServiceEndpoint> { + return healthCheckProperties.getCDSListenerServiceInformation() + } + + +} diff --git a/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/HealthCheckServiceTest.kt b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/HealthCheckServiceTest.kt new file mode 100644 index 000000000..c4a8d1235 --- /dev/null +++ b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/HealthCheckServiceTest.kt @@ -0,0 +1,167 @@ +/* + * Copyright © 2019-2020 Orange. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.healthapi + +import org.junit.Assert.assertEquals +import org.junit.Assert.assertNotNull +import org.mockito.ArgumentMatchers.any +import org.mockito.ArgumentMatchers.eq +import org.mockito.Mockito.anyString +import org.mockito.Mockito.mock + +import java.util.Arrays +import org.junit.Assert +import org.junit.Before +import org.junit.Test +import org.junit.runner.RunWith +import org.mockito.ArgumentMatchers +import org.mockito.InjectMocks +import org.mockito.Mock +import org.mockito.Mockito +import org.mockito.junit.MockitoJUnitRunner +import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.configuration.HealthCheckProperties +import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain.HealthApiResponse +import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain.HealthCheckStatus +import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain.ServiceEndpoint +import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.service.EndPointExecution +import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.service.health.BluePrintProcessorHealthCheck +import org.onap.ccsdk.cds.blueprintsprocessor.rest.BasicAuthRestClientProperties +import org.onap.ccsdk.cds.blueprintsprocessor.rest.service.BasicAuthRestClientService +import org.onap.ccsdk.cds.blueprintsprocessor.rest.service.BlueprintWebClientService +import org.onap.ccsdk.cds.blueprintsprocessor.rest.service.BlueprintWebClientService.WebClientResponse +import org.springframework.http.HttpMethod + +@RunWith(MockitoJUnitRunner::class) +class HealthCheckServiceTest { + + @Mock + private val basicAuthRestClientService: BasicAuthRestClientService? = null + + @Mock + private val restClientProperties: BasicAuthRestClientProperties? = null + + @Mock + private val healthCheckProperties: HealthCheckProperties? = null + + @InjectMocks + private var endPointExecution: EndPointExecution? = null + + private var bluePrintProcessorHealthCheck: BluePrintProcessorHealthCheck? = null + + + @Before + fun setup() { + endPointExecution = Mockito.spy(endPointExecution!!) + Mockito.`when`(healthCheckProperties!!.getBluePrintServiceInformation()).thenReturn(Arrays.asList( + ServiceEndpoint("Execution service ", "http://cds-blueprints-processor-http:8080/api/v1/execution-service/health-check"), + ServiceEndpoint("Resources service", "http://cds-blueprints-processor-http:8080/api/v1/resources/health-check"), ServiceEndpoint("Template service", "http://cds-blueprints-processor-http:8080/api/v1/template/health-check") + )) + + bluePrintProcessorHealthCheck = BluePrintProcessorHealthCheck(endPointExecution!!, healthCheckProperties) + } + + @Test + fun testSystemIsCompletelyDown() { + + Mockito.`when`(basicAuthRestClientService!!.exchangeResource( + anyString(), + anyString(), + anyString())).thenThrow(RuntimeException()) + val healthApiResponse = bluePrintProcessorHealthCheck!!.retrieveEndpointExecutionStatus() + assertNotNull(healthApiResponse) + Assert.assertEquals(HealthCheckStatus.DOWN, healthApiResponse.status) + healthApiResponse.checks.forEach { serviceEndpoint -> + assertNotNull(serviceEndpoint) + assertEquals(HealthCheckStatus.DOWN, serviceEndpoint.status) + + } + + } + + @Test + fun testSystemIsUPAndRunning() { + + Mockito.`when`(basicAuthRestClientService!! + .exchangeResource( + anyString(), + anyString(), + anyString())).thenReturn(BlueprintWebClientService.WebClientResponse(200, "Success")) + val healthApiResponse = bluePrintProcessorHealthCheck!!.retrieveEndpointExecutionStatus() + assertNotNull(healthApiResponse) + assertEquals(HealthCheckStatus.UP, healthApiResponse.status) + healthApiResponse.checks.forEach { serviceEndpoint -> + assertNotNull(serviceEndpoint) + assertEquals(HealthCheckStatus.UP, serviceEndpoint.status) + + } + + } + + @Test + fun testServiceIsNotFound() { + Mockito.`when`(basicAuthRestClientService!!.exchangeResource( + anyString(), + anyString(), + anyString())).thenReturn(BlueprintWebClientService.WebClientResponse(404, "failure")) + val healthApiResponse = bluePrintProcessorHealthCheck!!.retrieveEndpointExecutionStatus() + assertNotNull(healthApiResponse) + assertEquals(HealthCheckStatus.DOWN, healthApiResponse.status) + healthApiResponse.checks.forEach { serviceEndpoint -> + assertNotNull(serviceEndpoint) + assertEquals(HealthCheckStatus.DOWN, serviceEndpoint.status) + + } + + } + + + @Test + fun testServiceInternalServerError() { + Mockito.`when`(basicAuthRestClientService!!.exchangeResource( + anyString(), + anyString(), + anyString())) + .thenReturn(BlueprintWebClientService.WebClientResponse(500, "failure")) + val healthApiResponse = bluePrintProcessorHealthCheck!!.retrieveEndpointExecutionStatus() + assertNotNull(healthApiResponse) + assertEquals(HealthCheckStatus.DOWN, healthApiResponse.status) + healthApiResponse.checks.forEach { serviceEndpoint -> + assertNotNull(serviceEndpoint) + assertEquals(HealthCheckStatus.DOWN, serviceEndpoint.status) + + } + + } + + @Test + fun testServiceIsRedirected() { + Mockito.`when`(basicAuthRestClientService!!. + exchangeResource( + anyString(), + anyString(), + anyString())) + .thenReturn(BlueprintWebClientService.WebClientResponse(300, "failure")) + val healthApiResponse = bluePrintProcessorHealthCheck!!.retrieveEndpointExecutionStatus() + assertNotNull(healthApiResponse) + assertEquals(HealthCheckStatus.DOWN, healthApiResponse.status) + healthApiResponse.checks.forEach { serviceEndpoint -> + assertNotNull(serviceEndpoint) + assertEquals(HealthCheckStatus.DOWN, serviceEndpoint.status) + + } + } +} diff --git a/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/SecurityConfigurationTest.kt b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/SecurityConfigurationTest.kt new file mode 100644 index 000000000..e1f7abdb7 --- /dev/null +++ b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/SecurityConfigurationTest.kt @@ -0,0 +1,34 @@ +/* + * Copyright © 2019-2020 Orange. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.healthapi + +import org.junit.Assert +import org.junit.Test +import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.configuration.SecurityEncryptionConfiguration + + +class SecurityConfigurationTest { + + @Test + fun testEncryption() { + val passWord = "ccsdkapps" + val securityConfiguration = SecurityEncryptionConfiguration() + val encryptedValue = securityConfiguration.encrypt(passWord) + println(encryptedValue) + Assert.assertEquals(passWord, securityConfiguration.decrypt(encryptedValue!!)) + } +} diff --git a/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/test/resources/application-test.properties b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/test/resources/application-test.properties new file mode 100644 index 000000000..edf5760db --- /dev/null +++ b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/test/resources/application-test.properties @@ -0,0 +1,29 @@ +# +# Copyright © 2019-2020 Orange. +# 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 Licens +blueprintsprocessor.db.url=jdbc:h2:mem:testdb;DB_CLOSE_DELAY=-1 +blueprintsprocessor.db.username=sa +blueprintsprocessor.db.password= +blueprintsprocessor.db.driverClassName=org.h2.Driver +blueprintsprocessor.db.hibernateHbm2ddlAuto=create-drop +blueprintsprocessor.db.hibernateDDLAuto=update +blueprintsprocessor.db.hibernateNamingStrategy=org.hibernate.cfg.ImprovedNamingStrategy +blueprintsprocessor.db.hibernateDialect=org.hibernate.dialect.H2Dialect +# Controller Blueprints Core Configuration +blueprintsprocessor.blueprintDeployPath=./target/blueprints/deploy +blueprintsprocessor.blueprintWorkingPath=./target/blueprints/work +blueprintsprocessor.blueprintArchivePath=./target/blueprints/archive +# Python executor +blueprints.processor.functions.python.executor.executionPath=./../../../../components/scripts/python/ccsdk_blueprints +blueprints.processor.functions.python.executor.modulePaths=./../../../../components/scripts/python/ccsdk_blueprints +server.socket=localhost:8080 +endpoints.user.name=eHbVUbJAj4AG2522cSbrOQ== +endpoints.user.password=eHbVUbJAj4AG2522cSbrOQ== diff --git a/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/test/resources/logback.xml b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/test/resources/logback.xml new file mode 100644 index 000000000..0656cad76 --- /dev/null +++ b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/test/resources/logback.xml @@ -0,0 +1,35 @@ +<!-- + /* + * Copyright © 2019-2020 Orange. + * + * 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. + */ + --> +<configuration> + <appender name="STDOUT" class="ch.qos.logback.core.ConsoleAppender"> + <!-- encoders are assigned the type + ch.qos.logback.classic.encoder.PatternLayoutEncoder by default --> + <encoder> + <pattern>%d{HH:mm:ss.SSS} %-5level %logger{100} - %msg%n</pattern> + </encoder> + </appender> + + <logger name="org.springframework" level="warn"/> + <logger name="org.hibernate" level="info"/> + <logger name="org.onap.ccsdk.cds.blueprintsprocessor" level="info"/> + + <root level="info"> + <appender-ref ref="STDOUT"/> + </root> + +</configuration> diff --git a/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/test/resources/mockito-extensions/org.mockito.plugins.MockMaker b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/test/resources/mockito-extensions/org.mockito.plugins.MockMaker new file mode 100644 index 000000000..1f0955d45 --- /dev/null +++ b/ms/blueprintsprocessor/modules/inbounds/health-api-common/src/test/resources/mockito-extensions/org.mockito.plugins.MockMaker @@ -0,0 +1 @@ +mock-maker-inline diff --git a/ms/blueprintsprocessor/modules/inbounds/health-api/.gitignore b/ms/blueprintsprocessor/modules/inbounds/health-api/.gitignore new file mode 100644 index 000000000..a2a3040aa --- /dev/null +++ b/ms/blueprintsprocessor/modules/inbounds/health-api/.gitignore @@ -0,0 +1,31 @@ +HELP.md +target/ +!.mvn/wrapper/maven-wrapper.jar +!**/src/main/** +!**/src/test/** + +### STS ### +.apt_generated +.classpath +.factorypath +.project +.settings +.springBeans +.sts4-cache + +### IntelliJ IDEA ### +.idea +*.iws +*.iml +*.ipr + +### NetBeans ### +/nbproject/private/ +/nbbuild/ +/dist/ +/nbdist/ +/.nb-gradle/ +build/ + +### VS Code ### +.vscode/ diff --git a/ms/blueprintsprocessor/modules/inbounds/health-api/pom.xml b/ms/blueprintsprocessor/modules/inbounds/health-api/pom.xml index 01903a4c6..2635cfbb4 100644 --- a/ms/blueprintsprocessor/modules/inbounds/health-api/pom.xml +++ b/ms/blueprintsprocessor/modules/inbounds/health-api/pom.xml @@ -31,9 +31,11 @@ <description>checking system check health endpoints</description> <dependencies> + <dependency> <groupId>org.onap.ccsdk.cds.blueprintsprocessor</groupId> - <artifactId>rest-lib</artifactId> + <artifactId>health-api-common</artifactId> + <version>0.7.0-SNAPSHOT</version> </dependency> </dependencies> </project> diff --git a/ms/blueprintsprocessor/modules/inbounds/health-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/controller/HealthCheckController.kt b/ms/blueprintsprocessor/modules/inbounds/health-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/controller/CombinedHealth.kt index 1283ac5ac..54c85a0fc 100644 --- a/ms/blueprintsprocessor/modules/inbounds/health-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/controller/HealthCheckController.kt +++ b/ms/blueprintsprocessor/modules/inbounds/health-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/controller/CombinedHealth.kt @@ -18,9 +18,8 @@ package org.onap.ccsdk.cds.blueprintsprocessor.healthapi.controller import io.swagger.annotations.Api import io.swagger.annotations.ApiOperation -import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain.HealthApiResponse -import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.service.HealthCheckService -import org.springframework.beans.factory.annotation.Autowired +import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain.ApplicationHealth +import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.service.CombinedHealthService import org.springframework.http.MediaType import org.springframework.http.ResponseEntity import org.springframework.web.bind.annotation.RequestMapping @@ -28,21 +27,26 @@ import org.springframework.web.bind.annotation.RequestMethod import org.springframework.web.bind.annotation.ResponseBody import org.springframework.web.bind.annotation.RestController +/** + * Exposes API for checking health for other services . + * + * @author Shaaban Ebrahim + * @version 1.0 + */ @RestController -@RequestMapping("/api/v1/health") -@Api(value = "/api/v1/health", +@RequestMapping("/api/v1/combinedHealth") +@Api(value = "/api/v1/combinedHealth", description = "gather all HealthCheckResponses for HealthChecks known to the runtime") -open class HealthCheckController { - - @Autowired - lateinit var healthApiService: HealthCheckService +open class CombinedHealth(private val combinedHealthService: CombinedHealthService) { @RequestMapping(path = [""], method = [RequestMethod.GET], produces = [MediaType.APPLICATION_JSON_VALUE]) @ResponseBody @ApiOperation(value = "Health Check", hidden = true) - fun getSystemHealthCheckResponse(): ResponseEntity<HealthApiResponse> { - return ResponseEntity.ok().body(healthApiService.retrieveSystemStatus()) + fun getSystemHealthCheckResponse(): ResponseEntity<List<ApplicationHealth?>> { + return ResponseEntity.ok().body(combinedHealthService.getCombinedHealthCheck()) + } } + diff --git a/ms/blueprintsprocessor/modules/inbounds/health-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/controller/CombinedMetrics.kt b/ms/blueprintsprocessor/modules/inbounds/health-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/controller/CombinedMetrics.kt new file mode 100644 index 000000000..785def524 --- /dev/null +++ b/ms/blueprintsprocessor/modules/inbounds/health-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/controller/CombinedMetrics.kt @@ -0,0 +1,52 @@ +/* + * Copyright © 2019-2020 Orange. + * + * 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. + */ + +package org.onap.ccsdk.cds.blueprintsprocessor.healthapi.controller + +import io.swagger.annotations.Api +import io.swagger.annotations.ApiOperation +import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain.MetricsInfo +import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.service.CombinedMetricsService +import org.springframework.http.MediaType +import org.springframework.http.ResponseEntity +import org.springframework.web.bind.annotation.RequestMapping +import org.springframework.web.bind.annotation.RequestMethod +import org.springframework.web.bind.annotation.ResponseBody +import org.springframework.web.bind.annotation.RestController + +/** + * Exposes API for checking Metrics of BluePrint processor and CDSListener. + * + * @author Shaaban Ebrahim + * @version 1.0 + */ +@RestController +@RequestMapping("/api/v1/combinedMetrics") +@Api(value = "/api/v1/combinedMetrics", + description = "gather all Metrics info from BluePrint and CDSListener") +open class CombinedMetrics(private val combinedMetricsService: CombinedMetricsService) { + + @RequestMapping(path = [""], + method = [RequestMethod.GET], + produces = [MediaType.APPLICATION_JSON_VALUE]) + @ResponseBody + @ApiOperation(value = " Metrics Check", hidden = true) + fun getMetricsHealthCheckResponse(): ResponseEntity<MetricsInfo?> { + return ResponseEntity.ok().body(combinedMetricsService.metricsInfo) + + } + +} diff --git a/ms/blueprintsprocessor/modules/inbounds/health-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/HealthApiResponse.kt b/ms/blueprintsprocessor/modules/inbounds/health-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/HealthApiResponse.kt deleted file mode 100644 index 4dac178e5..000000000 --- a/ms/blueprintsprocessor/modules/inbounds/health-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/HealthApiResponse.kt +++ /dev/null @@ -1,6 +0,0 @@ -package org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain - - -data class HealthApiResponse(val status: HealthCheckStatus, val checks:List<HealthCheckResponse>) - - diff --git a/ms/blueprintsprocessor/modules/inbounds/health-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/HealthCheckResponse.kt b/ms/blueprintsprocessor/modules/inbounds/health-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/HealthCheckResponse.kt deleted file mode 100644 index acac867cb..000000000 --- a/ms/blueprintsprocessor/modules/inbounds/health-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/HealthCheckResponse.kt +++ /dev/null @@ -1,6 +0,0 @@ -package org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain - - -data class HealthCheckResponse(val name: String, val status: HealthCheckStatus) - - diff --git a/ms/blueprintsprocessor/modules/inbounds/health-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/HealthCheckStatus.kt b/ms/blueprintsprocessor/modules/inbounds/health-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/HealthCheckStatus.kt deleted file mode 100644 index a891a40d3..000000000 --- a/ms/blueprintsprocessor/modules/inbounds/health-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/HealthCheckStatus.kt +++ /dev/null @@ -1,6 +0,0 @@ -package org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain - -enum class HealthCheckStatus { - UP, - DOWN -}
\ No newline at end of file diff --git a/ms/blueprintsprocessor/modules/inbounds/health-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/ServiceEndpoint.kt b/ms/blueprintsprocessor/modules/inbounds/health-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/ServiceEndpoint.kt deleted file mode 100644 index 8fbc33b47..000000000 --- a/ms/blueprintsprocessor/modules/inbounds/health-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/domain/ServiceEndpoint.kt +++ /dev/null @@ -1,5 +0,0 @@ -package org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain - - - -data class ServiceEndpoint(val serviceName: String, val serviceLink: String) diff --git a/ms/blueprintsprocessor/modules/inbounds/health-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/service/CombinedHealthService.kt b/ms/blueprintsprocessor/modules/inbounds/health-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/service/CombinedHealthService.kt new file mode 100644 index 000000000..786048ce4 --- /dev/null +++ b/ms/blueprintsprocessor/modules/inbounds/health-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/service/CombinedHealthService.kt @@ -0,0 +1,58 @@ +/* + * Copyright © 2019-2020 Orange. + * + * 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. + */ +package org.onap.ccsdk.cds.blueprintsprocessor.healthapi.service + +import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.configuration.HealthCheckProperties +import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain.ApplicationHealth +import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain.ServiceEndpoint +import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain.WebClientEnpointResponse +import org.springframework.boot.actuate.health.Status +import org.springframework.stereotype.Service + + +/** + *Service for combined health (BluePrintProcessor and CDSListener) + * + * @author Shaaban Ebrahim + * @version 1.0 + */ +@Service +open class CombinedHealthService(private val endPointExecution: EndPointExecution + , private val healthCheckProperties: HealthCheckProperties) { + + private fun setupServiceEndpoint(): List<ServiceEndpoint> { + return listOf( + ServiceEndpoint("BluePrintProcessor Health Check ", healthCheckProperties.getBluePrintBaseURL() + "actuator/health") + , ServiceEndpoint("CDSListener Health Check", healthCheckProperties.getCDSListenerBaseURL() + "actuator/health") + ) + } + + open fun getCombinedHealthCheck(): List<ApplicationHealth?> { + val listOfResponse = ArrayList<ApplicationHealth?>() + for (serviceEndpoint in setupServiceEndpoint().parallelStream()) { + val result: WebClientEnpointResponse? = endPointExecution?.retrieveWebClientResponse(serviceEndpoint) + if (result?.response != null && + result.response!!.status?.equals(200)!!) { + listOfResponse.add(endPointExecution?.getHealthFromWebClientEnpointResponse(result)) + } else { + listOfResponse.add(ApplicationHealth(Status.DOWN, + hashMapOf(serviceEndpoint.serviceLink to serviceEndpoint.serviceLink))) + } + } + return listOfResponse + } + +} diff --git a/ms/blueprintsprocessor/modules/inbounds/health-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/service/CombinedMetricsService.kt b/ms/blueprintsprocessor/modules/inbounds/health-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/service/CombinedMetricsService.kt new file mode 100644 index 000000000..a23c9925b --- /dev/null +++ b/ms/blueprintsprocessor/modules/inbounds/health-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/service/CombinedMetricsService.kt @@ -0,0 +1,72 @@ +/* + * Copyright © 2019-2020 Orange. + * + * 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. + */ +package org.onap.ccsdk.cds.blueprintsprocessor.healthapi.service + +import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.configuration.HealthCheckProperties +import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain.* +import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.utils.ObjectMappingUtils +import org.onap.ccsdk.cds.blueprintsprocessor.rest.service.BlueprintWebClientService +import org.springframework.stereotype.Service + +/** + *Service for combined Metrics for CDS Listener and BluePrintProcessor + * + * @author Shaaban Ebrahim + * @version 1.0 + */ +@Service +open class CombinedMetricsService(private val endPointExecution: EndPointExecution + , private val healthCheckProperties: HealthCheckProperties + , private val objectMappingUtils: ObjectMappingUtils<Metrics>) { + + private fun setupServiceEndpoint(): List<ServiceEndpoint> { + return listOf( + ServiceEndpoint("BluePrintProcessor metrics", healthCheckProperties.getBluePrintBaseURL() + "/actuator/metrics") + , ServiceEndpoint("CDS Listener metrics", healthCheckProperties.getCDSListenerBaseURL() + "/actuator/metrics") + ) + } + + open val metricsInfo: MetricsInfo + get() { + val containerHealthChecks = mutableListOf<ActuatorCheckResponse>() + for (serviceEndpoint in setupServiceEndpoint().parallelStream()) { + val webClientResponse = endPointExecution?.retrieveWebClientResponse(serviceEndpoint) + var actuatorsHealthResponse: ActuatorCheckResponse? = null + actuatorsHealthResponse = if (webClientResponse?.response != null && + webClientResponse.response!!.status?.equals(200)!!) { + var body = gettingCustomizedBody(serviceEndpoint, webClientResponse.response!!) + ActuatorCheckResponse(serviceEndpoint.serviceName, body) + } else { + ActuatorCheckResponse(serviceEndpoint.serviceName, HealthCheckStatus.DOWN) + } + containerHealthChecks.add(actuatorsHealthResponse) + } + return MetricsInfo(containerHealthChecks) + } + + private fun gettingCustomizedBody(serviceEndpoint: ServiceEndpoint?, webClientResponse: BlueprintWebClientService.WebClientResponse<String>): Any { + var body: Any + val metrics: Metrics = objectMappingUtils.getObjectFromBody(webClientResponse.body, Metrics::class.java) + val mapOfMetricsInfo = HashMap<String, String>() + for (name in metrics.names!!) { + mapOfMetricsInfo.put(name.toString(), serviceEndpoint?.serviceLink + "/" + name) + } + body = MetricsResponse(mapOfMetricsInfo) + + return body + } +} + diff --git a/ms/blueprintsprocessor/modules/inbounds/health-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/service/HealthCheckService.kt b/ms/blueprintsprocessor/modules/inbounds/health-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/service/HealthCheckService.kt deleted file mode 100644 index 09fdb67f2..000000000 --- a/ms/blueprintsprocessor/modules/inbounds/health-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/service/HealthCheckService.kt +++ /dev/null @@ -1,91 +0,0 @@ -/* - * Copyright © 2019-2020 Orange. - * - * 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. - */ - -package org.onap.ccsdk.cds.blueprintsprocessor.healthapi.service - -import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain.HealthApiResponse -import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain.HealthCheckResponse -import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain.HealthCheckStatus -import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain.ServiceEndpoint -import org.onap.ccsdk.cds.blueprintsprocessor.rest.BasicAuthRestClientProperties -import org.onap.ccsdk.cds.blueprintsprocessor.rest.service.BasicAuthRestClientService -import org.onap.ccsdk.cds.blueprintsprocessor.rest.service.BlueprintWebClientService -import org.slf4j.LoggerFactory -import org.springframework.beans.factory.annotation.Autowired -import org.springframework.http.HttpMethod -import org.springframework.stereotype.Service - - -@Service -class HealthCheckService { - - private var logger = LoggerFactory.getLogger(HealthCheckService::class.java) - - @Autowired - lateinit var basicAuthRestClientService: BasicAuthRestClientService - - @Autowired - lateinit var restClientProperties: BasicAuthRestClientProperties - - - open fun setupServiceEndpoint(): List<ServiceEndpoint> { - return listOf(ServiceEndpoint("Execution service", "http://cds-blueprints-processor-http:8080/api/v1/execution-service/health-check"), - ServiceEndpoint("Template service", "http://cds-blueprints-processor-http:8080/api/v1/template/health-check"), - ServiceEndpoint("Resources service", "http://cds-blueprints-processor-http:8080/api/v1/resources/health-check"), - ServiceEndpoint("SDC Listener service", "http://cds-sdc-listener:8080/api/v1/sdclistener/health-check") - ) - } - - fun retrieveSystemStatus(): HealthApiResponse { - logger.info("Retrieve System Status") - var healthApiResponse: HealthApiResponse - val listOfResponse = mutableListOf<HealthCheckResponse>() - var systemStatus: HealthCheckStatus = HealthCheckStatus.UP - - for (serviceEndpoint in setupServiceEndpoint().parallelStream()) { - var serviceStatus: HealthCheckStatus = retrieveServiceStatus(serviceEndpoint) - if (serviceStatus.equals(HealthCheckStatus.DOWN)) - systemStatus = HealthCheckStatus.DOWN - - listOfResponse.add(HealthCheckResponse(serviceEndpoint.serviceName, serviceStatus)) - } - healthApiResponse = HealthApiResponse(systemStatus, listOfResponse) - return healthApiResponse - } - - private fun retrieveServiceStatus(serviceEndpoint: ServiceEndpoint): HealthCheckStatus { - var serviceStatus: HealthCheckStatus = HealthCheckStatus.UP - try { - addClientPropertiesConfiguration(serviceEndpoint) - val result: BlueprintWebClientService.WebClientResponse<String> = basicAuthRestClientService.exchangeResource(HttpMethod.GET.name, "", "") - if (result == null || result.status != 200) { - serviceStatus = HealthCheckStatus.DOWN - - } - } catch (e: Exception) { - logger.error("service is down" + e) - serviceStatus = HealthCheckStatus.DOWN - - } - return serviceStatus - } - - private fun addClientPropertiesConfiguration(serviceEndpoint: ServiceEndpoint) { - restClientProperties.url = serviceEndpoint.serviceLink - } - - -} diff --git a/ms/blueprintsprocessor/modules/inbounds/health-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/utils/ObjectMappingUtils.kt b/ms/blueprintsprocessor/modules/inbounds/health-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/utils/ObjectMappingUtils.kt new file mode 100644 index 000000000..9964c4518 --- /dev/null +++ b/ms/blueprintsprocessor/modules/inbounds/health-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/utils/ObjectMappingUtils.kt @@ -0,0 +1,13 @@ +package org.onap.ccsdk.cds.blueprintsprocessor.healthapi.utils + +import com.fasterxml.jackson.databind.ObjectMapper +import org.springframework.stereotype.Service + +@Service +class ObjectMappingUtils<T> { + + @Throws(java.io.IOException::class) + open fun getObjectFromBody(body: String, mappingClass: Class<T>): T { + return ObjectMapper().readValue(body, mappingClass) as T + } +} diff --git a/ms/blueprintsprocessor/modules/inbounds/health-api/src/main/resources/application.properties b/ms/blueprintsprocessor/modules/inbounds/health-api/src/main/resources/application.properties index aca95b481..de4b8f8f9 100644 --- a/ms/blueprintsprocessor/modules/inbounds/health-api/src/main/resources/application.properties +++ b/ms/blueprintsprocessor/modules/inbounds/health-api/src/main/resources/application.properties @@ -13,6 +13,5 @@ # See the License for the specific language governing permissions and # limitations under the License. # - -endpoints.user.name=ccsdkapps -endpoints.user.password=ccsdkapps +#endpoints.user.name=eHbVUbJAj4AG2522cSbrOQ== +#endpoints.user.password=eHbVUbJAj4AG2522cSbrOQ== diff --git a/ms/blueprintsprocessor/modules/inbounds/health-api/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/HealthCheckApplicationTests.kt b/ms/blueprintsprocessor/modules/inbounds/health-api/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/HealthCheckApplicationTests.kt index cd02b65dc..b1d629da7 100644 --- a/ms/blueprintsprocessor/modules/inbounds/health-api/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/HealthCheckApplicationTests.kt +++ b/ms/blueprintsprocessor/modules/inbounds/health-api/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/HealthCheckApplicationTests.kt @@ -20,7 +20,9 @@ package org.onap.ccsdk.cds.blueprintsprocessor.healthapi import org.junit.Test import org.junit.runner.RunWith import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintCoreConfiguration +import org.onap.ccsdk.cds.blueprintsprocessor.services.execution.ComponentScriptExecutor import org.onap.ccsdk.cds.controllerblueprints.core.interfaces.BluePrintCatalogService +import org.onap.ccsdk.cds.controllerblueprints.core.service.BluePrintRuntimeService import org.springframework.beans.factory.annotation.Autowired import org.springframework.boot.autoconfigure.security.SecurityProperties import org.springframework.boot.test.autoconfigure.web.reactive.WebFluxTest @@ -30,25 +32,36 @@ import org.springframework.test.context.TestPropertySource import org.springframework.test.context.junit4.SpringRunner import org.springframework.test.web.reactive.server.WebTestClient - +/** + *Unit tests for making sure that two endpoints is up and running + * + * @author Shaaban Ebrahim + * @version 1.0 + */ @RunWith(SpringRunner::class) @WebFluxTest -@ContextConfiguration(classes = [BluePrintCoreConfiguration::class, - BluePrintCatalogService::class, SecurityProperties::class]) +@ContextConfiguration(classes = [BluePrintRuntimeService::class, BluePrintCoreConfiguration::class, + BluePrintCatalogService::class, SecurityProperties::class, ComponentScriptExecutor::class]) @ComponentScan(basePackages = ["org.onap.ccsdk.cds.blueprintsprocessor", "org.onap.ccsdk.cds.controllerblueprints"]) @TestPropertySource(locations = ["classpath:application-test.properties"]) class HealthCheckApplicationTests { - @Autowired lateinit var webTestClient: WebTestClient @Test fun testHealthApiUp() { - val result = webTestClient.get().uri("/api/v1/health") + webTestClient.get().uri("/api/v1/combinedHealth") + .exchange() + .expectStatus().is2xxSuccessful + + } + + @Test + fun testMetricsApiUp() { + webTestClient.get().uri("/api/v1/combinedMetrics") .exchange() .expectStatus().is2xxSuccessful - println(result) } diff --git a/ms/blueprintsprocessor/modules/inbounds/health-api/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/HealthCheckServiceTest.java b/ms/blueprintsprocessor/modules/inbounds/health-api/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/HealthCheckServiceTest.java deleted file mode 100644 index 128c80adf..000000000 --- a/ms/blueprintsprocessor/modules/inbounds/health-api/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/healthapi/HealthCheckServiceTest.java +++ /dev/null @@ -1,136 +0,0 @@ -/* - * Copyright © 2019-2020 Orange. - * - * 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. - */ - -package org.onap.ccsdk.cds.blueprintsprocessor.healthapi; - -import org.junit.Assert; -import org.junit.Before; -import org.junit.Test; -import org.junit.runner.RunWith; -import org.mockito.InjectMocks; -import org.mockito.Mock; -import org.mockito.Mockito; -import org.mockito.junit.MockitoJUnitRunner; -import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain.HealthApiResponse; -import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain.HealthCheckStatus; -import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.service.HealthCheckService; -import org.onap.ccsdk.cds.blueprintsprocessor.rest.BasicAuthRestClientProperties; -import org.onap.ccsdk.cds.blueprintsprocessor.rest.service.BasicAuthRestClientService; -import org.onap.ccsdk.cds.blueprintsprocessor.rest.service.BlueprintWebClientService.WebClientResponse; -import org.springframework.http.HttpMethod; - -import static org.junit.Assert.assertEquals; -import static org.junit.Assert.assertNotNull; -import static org.mockito.ArgumentMatchers.any; -import static org.mockito.ArgumentMatchers.eq; -import static org.mockito.Mockito.anyString; - -@RunWith(MockitoJUnitRunner.class) -public class HealthCheckServiceTest { - - @Mock - private BasicAuthRestClientService basicAuthRestClientService; - - @Mock - private BasicAuthRestClientProperties restClientProperties; - - @InjectMocks - private HealthCheckService healthCheckService = new HealthCheckService(); - - @Before - public void setup() { - } - - @Test - public void testSystemIsCompletelyDown() { - - Mockito.when(basicAuthRestClientService.exchangeResource(anyString(), anyString(), anyString())). - thenThrow(new RuntimeException()); - HealthApiResponse healthApiResponse = healthCheckService.retrieveSystemStatus(); - assertNotNull(healthApiResponse); - Assert.assertEquals(healthApiResponse.getStatus(), HealthCheckStatus.DOWN); - healthApiResponse.getChecks().stream().forEach(serviceEndpoint -> { - assertNotNull(serviceEndpoint); - assertEquals(serviceEndpoint.getStatus(), HealthCheckStatus.DOWN); - - }); - - } - - - @Test - public void testSystemIsUPAndRunning() { - - Mockito.when(basicAuthRestClientService.exchangeResource(eq(HttpMethod.GET.name()), anyString(), anyString())). - thenReturn(new WebClientResponse<>(200, "Success")); - HealthApiResponse healthApiResponse = healthCheckService.retrieveSystemStatus(); - assertNotNull(healthApiResponse); - assertEquals(healthApiResponse.getStatus(), HealthCheckStatus.UP); - healthApiResponse.getChecks().stream().forEach(serviceEndpoint -> { - assertNotNull(serviceEndpoint); - assertEquals(serviceEndpoint.getStatus(), HealthCheckStatus.UP); - - }); - - } - - @Test - public void testServiceIsNotFound() { - Mockito.when(basicAuthRestClientService.exchangeResource(eq(HttpMethod.GET.name()), any(), anyString())). - thenReturn(new WebClientResponse<>(404, "failure")); - HealthApiResponse healthApiResponse = healthCheckService.retrieveSystemStatus(); - assertNotNull(healthApiResponse); - assertEquals(healthApiResponse.getStatus(), HealthCheckStatus.DOWN); - healthApiResponse.getChecks().stream().forEach(serviceEndpoint -> { - assertNotNull(serviceEndpoint); - assertEquals(serviceEndpoint.getStatus(), HealthCheckStatus.DOWN); - - }); - - } - - - @Test - public void testServiceInternalServerError() { - Mockito.when(basicAuthRestClientService.exchangeResource(eq(HttpMethod.GET.name()), any(), anyString())) - .thenReturn(new WebClientResponse<>(500, "failure")); - HealthApiResponse healthApiResponse = healthCheckService.retrieveSystemStatus(); - assertNotNull(healthApiResponse); - assertEquals(healthApiResponse.getStatus(), HealthCheckStatus.DOWN); - healthApiResponse.getChecks().stream().forEach(serviceEndpoint -> { - assertNotNull(serviceEndpoint); - assertEquals(serviceEndpoint.getStatus(), HealthCheckStatus.DOWN); - - }); - - } - - @Test - public void testServiceIsRedirected() { - Mockito.when(basicAuthRestClientService.exchangeResource(eq(HttpMethod.GET.name()), any(), anyString())) - .thenReturn(new WebClientResponse<>(300, "failure")); - HealthApiResponse healthApiResponse = healthCheckService.retrieveSystemStatus(); - assertNotNull(healthApiResponse); - assertEquals(healthApiResponse.getStatus(), HealthCheckStatus.DOWN); - healthApiResponse.getChecks().stream().forEach(serviceEndpoint -> { - assertNotNull(serviceEndpoint); - assertEquals(serviceEndpoint.getStatus(), HealthCheckStatus.DOWN); - - }); - - } - -} diff --git a/ms/blueprintsprocessor/modules/inbounds/health-api/src/test/resources/application-test.properties b/ms/blueprintsprocessor/modules/inbounds/health-api/src/test/resources/application-test.properties index c9a5700c1..8eb6db352 100644 --- a/ms/blueprintsprocessor/modules/inbounds/health-api/src/test/resources/application-test.properties +++ b/ms/blueprintsprocessor/modules/inbounds/health-api/src/test/resources/application-test.properties @@ -1,16 +1,14 @@ -# Copyright © 2019 Bell Canada. # -# 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. +# Copyright © 2019-2020 Orange. +# 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. blueprintsprocessor.db.url=jdbc:h2:mem:testdb;DB_CLOSE_DELAY=-1 blueprintsprocessor.db.username=sa @@ -24,8 +22,9 @@ blueprintsprocessor.db.hibernateDialect=org.hibernate.dialect.H2Dialect blueprintsprocessor.blueprintDeployPath=./target/blueprints/deploy blueprintsprocessor.blueprintWorkingPath=./target/blueprints/work blueprintsprocessor.blueprintArchivePath=./target/blueprints/archive - # Python executor blueprints.processor.functions.python.executor.executionPath=./../../../../components/scripts/python/ccsdk_blueprints blueprints.processor.functions.python.executor.modulePaths=./../../../../components/scripts/python/ccsdk_blueprints server.socket=localhost:8080 +endpoints.user.name=eHbVUbJAj4AG2522cSbrOQ== +endpoints.user.password=eHbVUbJAj4AG2522cSbrOQ== diff --git a/ms/blueprintsprocessor/modules/inbounds/health-api/src/test/resources/logback.xml b/ms/blueprintsprocessor/modules/inbounds/health-api/src/test/resources/logback.xml index c97e1cd29..11582a301 100644 --- a/ms/blueprintsprocessor/modules/inbounds/health-api/src/test/resources/logback.xml +++ b/ms/blueprintsprocessor/modules/inbounds/health-api/src/test/resources/logback.xml @@ -1,23 +1,23 @@ <!-- - ~ Copyright © 2019 Bell Canada - ~ - ~ 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. + /* + * Copyright © 2019-2020 Orange. + * + * 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. + */ --> <configuration> <appender name="STDOUT" class="ch.qos.logback.core.ConsoleAppender"> - <!-- encoders are assigned the type - ch.qos.logback.classic.encoder.PatternLayoutEncoder by default --> <encoder> <pattern>%d{HH:mm:ss.SSS} %-5level %logger{100} - %msg%n</pattern> </encoder> diff --git a/ms/blueprintsprocessor/modules/inbounds/pom.xml b/ms/blueprintsprocessor/modules/inbounds/pom.xml index 81ffea176..6dc39a7ff 100644 --- a/ms/blueprintsprocessor/modules/inbounds/pom.xml +++ b/ms/blueprintsprocessor/modules/inbounds/pom.xml @@ -35,7 +35,8 @@ <module>designer-api</module> <module>resource-api</module> <module>selfservice-api</module> - <!--<module>health-api</module>--> + <module>health-api</module> + <module>health-api-common</module> </modules> <dependencies> @@ -51,16 +52,7 @@ <groupId>org.onap.ccsdk.cds.blueprintsprocessor.functions</groupId> <artifactId>resource-resolution</artifactId> </dependency> - <dependency> - <groupId>org.springframework.boot</groupId> - <artifactId>spring-boot-starter-actuator</artifactId> - <exclusions> - <exclusion> - <groupId>org.springframework.boot</groupId> - <artifactId>spring-boot-starter-logging</artifactId> - </exclusion> - </exclusions> - </dependency> + <!-- Test Dependencies --> <dependency> diff --git a/ms/blueprintsprocessor/modules/inbounds/selfservice-api/pom.xml b/ms/blueprintsprocessor/modules/inbounds/selfservice-api/pom.xml index 1a9b5fc80..9f45c0f35 100755 --- a/ms/blueprintsprocessor/modules/inbounds/selfservice-api/pom.xml +++ b/ms/blueprintsprocessor/modules/inbounds/selfservice-api/pom.xml @@ -33,11 +33,6 @@ <description>Blueprints Processor Selfservice API</description> <dependencies> - - <dependency> - <groupId>org.onap.ccsdk.cds.controllerblueprints</groupId> - <artifactId>blueprint-proto</artifactId> - </dependency> <dependency> <groupId>org.onap.ccsdk.cds.controllerblueprints</groupId> <artifactId>blueprint-core</artifactId> diff --git a/ms/blueprintsprocessor/modules/inbounds/selfservice-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/selfservice/api/BluePrintProcessingGRPCHandler.kt b/ms/blueprintsprocessor/modules/inbounds/selfservice-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/selfservice/api/BluePrintProcessingGRPCHandler.kt index 636a55423..b25acd148 100644 --- a/ms/blueprintsprocessor/modules/inbounds/selfservice-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/selfservice/api/BluePrintProcessingGRPCHandler.kt +++ b/ms/blueprintsprocessor/modules/inbounds/selfservice-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/selfservice/api/BluePrintProcessingGRPCHandler.kt @@ -20,7 +20,7 @@ package org.onap.ccsdk.cds.blueprintsprocessor.selfservice.api import io.grpc.stub.StreamObserver import kotlinx.coroutines.runBlocking import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintCoreConfiguration -import org.onap.ccsdk.cds.blueprintsprocessor.selfservice.api.utils.toJava +import org.onap.ccsdk.cds.blueprintsprocessor.core.utils.toJava import org.onap.ccsdk.cds.controllerblueprints.processing.api.BluePrintProcessingServiceGrpc import org.onap.ccsdk.cds.controllerblueprints.processing.api.ExecutionServiceInput import org.onap.ccsdk.cds.controllerblueprints.processing.api.ExecutionServiceOutput diff --git a/ms/blueprintsprocessor/modules/inbounds/selfservice-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/selfservice/api/ExecutionServiceHandler.kt b/ms/blueprintsprocessor/modules/inbounds/selfservice-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/selfservice/api/ExecutionServiceHandler.kt index ade47cf3f..356f0f7ee 100644 --- a/ms/blueprintsprocessor/modules/inbounds/selfservice-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/selfservice/api/ExecutionServiceHandler.kt +++ b/ms/blueprintsprocessor/modules/inbounds/selfservice-api/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/selfservice/api/ExecutionServiceHandler.kt @@ -22,7 +22,7 @@ import kotlinx.coroutines.Dispatchers import kotlinx.coroutines.GlobalScope import kotlinx.coroutines.launch import org.onap.ccsdk.cds.blueprintsprocessor.core.api.data.* -import org.onap.ccsdk.cds.blueprintsprocessor.selfservice.api.utils.toProto +import org.onap.ccsdk.cds.blueprintsprocessor.core.utils.toProto import org.onap.ccsdk.cds.blueprintsprocessor.services.execution.AbstractServiceFunction import org.onap.ccsdk.cds.controllerblueprints.common.api.EventType import org.onap.ccsdk.cds.controllerblueprints.core.BluePrintConstants diff --git a/ms/blueprintsprocessor/modules/inbounds/selfservice-api/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/selfservice/api/BluePrintProcessingKafkaConsumerTest.kt b/ms/blueprintsprocessor/modules/inbounds/selfservice-api/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/selfservice/api/BluePrintProcessingKafkaConsumerTest.kt index 7d43f533f..01199c131 100644 --- a/ms/blueprintsprocessor/modules/inbounds/selfservice-api/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/selfservice/api/BluePrintProcessingKafkaConsumerTest.kt +++ b/ms/blueprintsprocessor/modules/inbounds/selfservice-api/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/selfservice/api/BluePrintProcessingKafkaConsumerTest.kt @@ -22,8 +22,8 @@ import kotlinx.coroutines.delay import kotlinx.coroutines.launch import kotlinx.coroutines.runBlocking import org.junit.runner.RunWith -import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintProperties -import org.onap.ccsdk.cds.blueprintsprocessor.core.BlueprintPropertyConfiguration +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertiesService +import org.onap.ccsdk.cds.blueprintsprocessor.core.BluePrintPropertyConfiguration import org.onap.ccsdk.cds.blueprintsprocessor.message.BluePrintMessageLibConfiguration import org.onap.ccsdk.cds.blueprintsprocessor.message.service.BluePrintMessageLibPropertyService import org.springframework.beans.factory.annotation.Autowired @@ -35,7 +35,7 @@ import kotlin.test.assertNotNull @RunWith(SpringRunner::class) @ContextConfiguration(classes = [BluePrintMessageLibConfiguration::class, - BlueprintPropertyConfiguration::class, BluePrintProperties::class]) + BluePrintPropertyConfiguration::class, BluePrintPropertiesService::class]) @TestPropertySource(locations = ["classpath:application-test.properties"]) class BluePrintProcessingKafkaConsumerTest { diff --git a/ms/blueprintsprocessor/modules/services/workflow-service/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/services/workflow/ImperativeWorkflowExecutionService.kt b/ms/blueprintsprocessor/modules/services/workflow-service/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/services/workflow/ImperativeWorkflowExecutionService.kt index 6bee17f4b..d296ec6e6 100644 --- a/ms/blueprintsprocessor/modules/services/workflow-service/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/services/workflow/ImperativeWorkflowExecutionService.kt +++ b/ms/blueprintsprocessor/modules/services/workflow-service/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/services/workflow/ImperativeWorkflowExecutionService.kt @@ -20,6 +20,7 @@ import kotlinx.coroutines.CompletableDeferred import org.onap.ccsdk.cds.blueprintsprocessor.core.api.data.ExecutionServiceInput import org.onap.ccsdk.cds.blueprintsprocessor.core.api.data.ExecutionServiceOutput import org.onap.ccsdk.cds.blueprintsprocessor.core.api.data.Status +import org.onap.ccsdk.cds.controllerblueprints.common.api.EventType import org.onap.ccsdk.cds.controllerblueprints.core.* import org.onap.ccsdk.cds.controllerblueprints.core.data.EdgeLabel import org.onap.ccsdk.cds.controllerblueprints.core.data.Graph @@ -93,6 +94,7 @@ open class ImperativeBluePrintWorkflowService(private val nodeTemplateExecutionS } else { message = BluePrintConstants.STATUS_SUCCESS } + eventType = EventType.EVENT_COMPONENT_EXECUTED.name } return ExecutionServiceOutput().apply { commonHeader = executionServiceInput.commonHeader diff --git a/ms/blueprintsprocessor/modules/services/workflow-service/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/services/workflow/ImperativeWorkflowExecutionServiceTest.kt b/ms/blueprintsprocessor/modules/services/workflow-service/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/services/workflow/ImperativeWorkflowExecutionServiceTest.kt index becd22857..b7fcae1d1 100644 --- a/ms/blueprintsprocessor/modules/services/workflow-service/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/services/workflow/ImperativeWorkflowExecutionServiceTest.kt +++ b/ms/blueprintsprocessor/modules/services/workflow-service/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/services/workflow/ImperativeWorkflowExecutionServiceTest.kt @@ -26,6 +26,8 @@ import org.onap.ccsdk.cds.blueprintsprocessor.core.api.data.ExecutionServiceInpu import org.onap.ccsdk.cds.blueprintsprocessor.services.execution.nodeTypeComponentScriptExecutor import org.onap.ccsdk.cds.blueprintsprocessor.services.workflow.mock.MockComponentFunction import org.onap.ccsdk.cds.blueprintsprocessor.services.workflow.mock.mockNodeTemplateComponentScriptExecutor +import org.onap.ccsdk.cds.controllerblueprints.common.api.EventType +import org.onap.ccsdk.cds.controllerblueprints.core.BluePrintConstants import org.onap.ccsdk.cds.controllerblueprints.core.BluePrintTypes import org.onap.ccsdk.cds.controllerblueprints.core.data.ServiceTemplate import org.onap.ccsdk.cds.controllerblueprints.core.dsl.serviceTemplate @@ -36,6 +38,7 @@ import org.onap.ccsdk.cds.controllerblueprints.core.service.BluePrintDependencyS import org.onap.ccsdk.cds.controllerblueprints.core.utils.BluePrintMetadataUtils import org.onap.ccsdk.cds.controllerblueprints.core.utils.JacksonUtils import kotlin.test.Test +import kotlin.test.assertEquals import kotlin.test.assertNotNull class ImperativeWorkflowExecutionServiceTest { @@ -99,7 +102,10 @@ class ImperativeWorkflowExecutionServiceTest { val imperativeWorkflowExecutionService = ImperativeWorkflowExecutionService(bluePrintWorkFlowService) val output = imperativeWorkflowExecutionService .executeBluePrintWorkflow(bluePrintRuntimeService, executionServiceInput, hashMapOf()) - assertNotNull(output) + assertNotNull(output, "failed to get imperative workflow output") + assertNotNull(output.status, "failed to get imperative workflow output status") + assertEquals(output.status.message, BluePrintConstants.STATUS_SUCCESS) + assertEquals(output.status.eventType, EventType.EVENT_COMPONENT_EXECUTED.name) } } }
\ No newline at end of file diff --git a/ms/blueprintsprocessor/pom.xml b/ms/blueprintsprocessor/pom.xml index cf9d88885..658e5c417 100755 --- a/ms/blueprintsprocessor/pom.xml +++ b/ms/blueprintsprocessor/pom.xml @@ -22,7 +22,7 @@ <groupId>org.onap.ccsdk.cds</groupId> <artifactId>ms</artifactId> <version>0.7.0-SNAPSHOT</version> - <relativePath>..</relativePath> + <relativePath>../parent</relativePath> </parent> <artifactId>blueprintsprocessor</artifactId> diff --git a/ms/controllerblueprints/modules/blueprint-core/src/main/kotlin/org/onap/ccsdk/cds/controllerblueprints/core/dsl/BluePrintTypeDSLBuilder.kt b/ms/controllerblueprints/modules/blueprint-core/src/main/kotlin/org/onap/ccsdk/cds/controllerblueprints/core/dsl/BluePrintTypeDSLBuilder.kt index 6dc5647da..8d96e7110 100644 --- a/ms/controllerblueprints/modules/blueprint-core/src/main/kotlin/org/onap/ccsdk/cds/controllerblueprints/core/dsl/BluePrintTypeDSLBuilder.kt +++ b/ms/controllerblueprints/modules/blueprint-core/src/main/kotlin/org/onap/ccsdk/cds/controllerblueprints/core/dsl/BluePrintTypeDSLBuilder.kt @@ -384,6 +384,13 @@ class PropertyDefinitionBuilder(private val id: String, propertyDefinition.defaultValue = defaultValue } + fun metadata(name: String, value: String) { + if (propertyDefinition.metadata == null) { + propertyDefinition.metadata = hashMapOf() + } + propertyDefinition.metadata!![name] = value + } + fun value(value: Any) { value(value.asJsonType()) } diff --git a/ms/controllerblueprints/modules/blueprint-proto/pom.xml b/ms/controllerblueprints/modules/blueprint-proto/pom.xml index 91097b9d9..fef6cb7ac 100644 --- a/ms/controllerblueprints/modules/blueprint-proto/pom.xml +++ b/ms/controllerblueprints/modules/blueprint-proto/pom.xml @@ -14,7 +14,6 @@ ~ See the License for the specific language governing permissions and ~ limitations under the License. --> - <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> diff --git a/ms/py-executor/pom.xml b/ms/py-executor/pom.xml index ef528989b..9ede1b21b 100644 --- a/ms/py-executor/pom.xml +++ b/ms/py-executor/pom.xml @@ -14,7 +14,6 @@ ~ See the License for the specific language governing permissions and ~ limitations under the License. --> - <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> diff --git a/ms/sdclistener/application/pom.xml b/ms/sdclistener/application/pom.xml index 2e6c183a9..5f359575f 100644 --- a/ms/sdclistener/application/pom.xml +++ b/ms/sdclistener/application/pom.xml @@ -53,6 +53,14 @@ <scope>test</scope> </dependency> + + + <dependency> + <groupId>org.onap.ccsdk.cds.blueprintsprocessor</groupId> + <artifactId>health-api-common</artifactId> + <version>0.7.0-SNAPSHOT</version> + </dependency> + <!-- SDC Distribution client dependency --> <dependency> <groupId>org.onap.sdc.sdc-distribution-client</groupId> diff --git a/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/actuator/indicator/SDCListenerCustomIndicator.java b/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/actuator/indicator/SDCListenerCustomIndicator.java new file mode 100644 index 000000000..11fd2c24c --- /dev/null +++ b/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/actuator/indicator/SDCListenerCustomIndicator.java @@ -0,0 +1,48 @@ +/* + * Copyright © 2019-2020 Orange. + * + * 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. + */ + +package org.onap.ccsdk.cds.sdclistener.actuator.indicator; + + +import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain.HealthApiResponse; +import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.domain.HealthCheckStatus; +import org.onap.ccsdk.cds.blueprintsprocessor.healthapi.service.health.SDCListenerHealthCheck; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.boot.actuate.health.AbstractHealthIndicator; +import org.springframework.boot.actuate.health.Health.Builder; +import org.springframework.stereotype.Component; +/** + * Health Indicator for SDCListener. + * @author Shaaban Ebrahim + * @version 1.0 + */ +@Component +public class SDCListenerCustomIndicator extends AbstractHealthIndicator { + + @Autowired + private SDCListenerHealthCheck sDCListenerHealthCheck; + + @Override + protected void doHealthCheck(Builder builder) { + HealthApiResponse healthAPIResponse = sDCListenerHealthCheck.retrieveEndpointExecutionStatus(); + if (healthAPIResponse.getStatus() == HealthCheckStatus.UP) { + builder.up(); + } else { + builder.down(); + } + builder.withDetail("Services", healthAPIResponse.getChecks()); + } +} @@ -21,7 +21,7 @@ limitations under the License. <parent> <groupId>org.onap.ccsdk.parent</groupId> <artifactId>spring-boot-starter-parent</artifactId> - <version>1.5.0-SNAPSHOT</version> + <version>1.5.0</version> <relativePath/> </parent> @@ -38,8 +38,8 @@ limitations under the License. </organization> <modules> - <module>cds-ui</module> <module>ms</module> + <module>cds-ui</module> </modules> <properties> |