summaryrefslogtreecommitdiffstats
path: root/dcae-analytics/dcae-analytics-tca-web
diff options
context:
space:
mode:
Diffstat (limited to 'dcae-analytics/dcae-analytics-tca-web')
-rw-r--r--dcae-analytics/dcae-analytics-tca-web/Dockerfile15
-rw-r--r--dcae-analytics/dcae-analytics-tca-web/docker/Dockerfile15
-rw-r--r--dcae-analytics/dcae-analytics-tca-web/docker/logback.xml52
-rw-r--r--dcae-analytics/dcae-analytics-tca-web/pom.xml140
-rw-r--r--dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/TcaAppMain.java42
-rw-r--r--dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/TcaAppProperties.java86
-rw-r--r--dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/aai/TcaAaiEnrichmentContextImpl.java50
-rw-r--r--dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/aai/TcaAaiEnrichmentServiceImpl.java273
-rw-r--r--dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/aai/TcaAaiRestClientPreferences.java48
-rw-r--r--dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/abatement/mongo/MongoAbatementContextImpl.java58
-rw-r--r--dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/abatement/mongo/MongoAbatementEntity.java59
-rw-r--r--dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/abatement/mongo/MongoAbatementRepository.java36
-rw-r--r--dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/abatement/simple/SimpleAbatementContextImpl.java62
-rw-r--r--dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/abatement/simple/SimpleAbatementEntity.java58
-rw-r--r--dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/abatement/simple/SimpleAbatementRepository.java89
-rw-r--r--dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/config/ControllerConfig.java41
-rw-r--r--dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/config/SwaggerConfig.java63
-rw-r--r--dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/config/TcaAaiConfig.java67
-rw-r--r--dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/config/TcaMongoAbatementConfig.java48
-rw-r--r--dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/config/TcaMrConfig.java114
-rw-r--r--dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/config/TcaSimpleAbatementConfig.java50
-rw-r--r--dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/config/TcaWebConfig.java84
-rw-r--r--dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/controller/TcaRestController.java114
-rw-r--r--dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/domain/TcaPolicyWrapper.java98
-rw-r--r--dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/integration/TcaAlertTransformer.java159
-rw-r--r--dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/integration/TcaPublisherResponseHandler.java101
-rw-r--r--dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/service/TcaProcessingService.java49
-rw-r--r--dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/service/TcaProcessingServiceImpl.java87
-rw-r--r--dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/util/TcaUtils.java92
-rw-r--r--dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/util/function/TcaAppPropsToAaiRestClientPrefsFunction.java61
-rw-r--r--dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/util/function/TcaAppPropsToMrPublisherPrefsFunction.java83
-rw-r--r--dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/util/function/TcaAppPropsToMrSubscriberPrefsFunction.java115
-rw-r--r--dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/validation/ConfigPropertiesAaiValidator.java88
-rw-r--r--dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/validation/TcaAppPropertiesValidator.java186
-rw-r--r--dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/validation/TcaPolicyValidator.java133
-rw-r--r--dcae-analytics/dcae-analytics-tca-web/src/main/resources/config/application-dev.yaml50
-rw-r--r--dcae-analytics/dcae-analytics-tca-web/src/main/resources/config/application-mongo.yaml4
-rw-r--r--dcae-analytics/dcae-analytics-tca-web/src/main/resources/config/application.yaml53
-rw-r--r--dcae-analytics/dcae-analytics-tca-web/src/main/resources/config/bootstrap.yaml4
-rw-r--r--dcae-analytics/dcae-analytics-tca-web/src/test/java/org/onap/dcae/analytics/tca/web/BaseTcaWebSpringBootIT.java54
-rw-r--r--dcae-analytics/dcae-analytics-tca-web/src/test/java/org/onap/dcae/analytics/tca/web/config/TcaWebTestConfig.java34
-rw-r--r--dcae-analytics/dcae-analytics-tca-web/src/test/java/org/onap/dcae/analytics/tca/web/service/TcaProcessingServiceImplTest.java72
42 files changed, 3187 insertions, 0 deletions
diff --git a/dcae-analytics/dcae-analytics-tca-web/Dockerfile b/dcae-analytics/dcae-analytics-tca-web/Dockerfile
new file mode 100644
index 0000000..83136ad
--- /dev/null
+++ b/dcae-analytics/dcae-analytics-tca-web/Dockerfile
@@ -0,0 +1,15 @@
+# NOTE: This Dockerfile is auto generated and filtered via maven resources plugin.
+# Edits to generated Dockerfile will NOT be saved.
+# Only changes made in docker/Dockerfile template file will be persistent
+FROM openjdk:8-jre-alpine
+MAINTAINER Rajiv Singla <rs153v@att.com>
+ENTRYPOINT ["java", \
+ "-Djava.security.egd=file:/dev/./urandom", \
+ "-Dlogging.config=logback.xml", \
+ "-Dlogging.file=logs/dcae-analytics-tca-web.log", \
+ "-Dspring.profiles.active=dev", \
+ "-jar", "dcae-analytics-tca-web.jar"]
+EXPOSE 9091
+VOLUME /tmp
+ADD docker/logback.xml logback.xml
+ADD target/dcae-analytics-tca-web-3.0.0-SNAPSHOT.jar dcae-analytics-tca-web.jar
diff --git a/dcae-analytics/dcae-analytics-tca-web/docker/Dockerfile b/dcae-analytics/dcae-analytics-tca-web/docker/Dockerfile
new file mode 100644
index 0000000..fcbc5ac
--- /dev/null
+++ b/dcae-analytics/dcae-analytics-tca-web/docker/Dockerfile
@@ -0,0 +1,15 @@
+# NOTE: This Dockerfile is auto generated and filtered via maven resources plugin.
+# Edits to generated Dockerfile will NOT be saved.
+# Only changes made in docker/Dockerfile template file will be persistent
+FROM openjdk:8-jre-alpine
+MAINTAINER Rajiv Singla <rs153v@att.com>
+ENTRYPOINT ["java", \
+ "-Djava.security.egd=file:/dev/./urandom", \
+ "-Dlogging.config=logback.xml", \
+ "-Dlogging.file=logs/${project.artifactId}.log", \
+ "-Dspring.profiles.active=dev", \
+ "-jar", "${project.artifactId}.jar"]
+EXPOSE 9091
+VOLUME /tmp
+ADD docker/logback.xml logback.xml
+ADD target/${project.build.finalName}.jar ${project.artifactId}.jar
diff --git a/dcae-analytics/dcae-analytics-tca-web/docker/logback.xml b/dcae-analytics/dcae-analytics-tca-web/docker/logback.xml
new file mode 100644
index 0000000..cba7e63
--- /dev/null
+++ b/dcae-analytics/dcae-analytics-tca-web/docker/logback.xml
@@ -0,0 +1,52 @@
+<!--
+ ~ ================================================================================
+ ~ Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ ~ ================================================================================
+ ~ Licensed under the Apache License, Version 2.0 (the "License");
+ ~ you may not use this file except in compliance with the License.
+ ~ You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing, software
+ ~ distributed under the License is distributed on an "AS IS" BASIS,
+ ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ ~ See the License for the specific language governing permissions and
+ ~ limitations under the License.
+ ~ ============LICENSE_END=========================================================
+ ~
+ -->
+
+<configuration>
+
+ <!-- SET ECOMP COMPONENT NAME -->
+ <property scope="context" name="componentName" value="dcae-analytics-tca"/>
+ <contextName>${componentName}</contextName>
+
+ <include resource="ecomp-logback.xml"/>
+ <include resource="org/springframework/boot/logging/logback/base.xml"/>
+
+ <logger name="org.springframework" level="INFO"/>
+ <logger name="org.hibernate" level="WARN"/>
+ <logger name="springfox" level="INFO"/>
+ <logger name="org.xnio" level="INFO"/>
+ <logger name="io.undertow" level="INFO"/>
+ <logger name="org.apache" level="INFO"/>
+ <logger name="sun.rmi" level="INFO"/>
+ <logger name="org.mongodb" level="INFO"/>
+ <logger name="com.jayway" level="INFO"/>
+
+ <logger name="org.springframework.retry" level="INFO"/>
+ <logger name="org.onap.dcae.analytics" level="INFO"/>
+
+ <root level="INFO">
+ <!-- required appenders -->
+ <appender-ref ref="auditLogAppender"/>
+ <appender-ref ref="metricLogAppender"/>
+ <appender-ref ref="errorLogAppender"/>
+
+ <!-- app properties -->
+ <appender-ref ref="FILE"/>
+ </root>
+
+</configuration>
diff --git a/dcae-analytics/dcae-analytics-tca-web/pom.xml b/dcae-analytics/dcae-analytics-tca-web/pom.xml
new file mode 100644
index 0000000..e884f39
--- /dev/null
+++ b/dcae-analytics/dcae-analytics-tca-web/pom.xml
@@ -0,0 +1,140 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--
+ ~ ================================================================================
+ ~ Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ ~ ================================================================================
+ ~ Licensed under the Apache License, Version 2.0 (the "License");
+ ~ you may not use this file except in compliance with the License.
+ ~ You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing, software
+ ~ distributed under the License is distributed on an "AS IS" BASIS,
+ ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ ~ See the License for the specific language governing permissions and
+ ~ limitations under the License.
+ ~ ============LICENSE_END=========================================================
+ ~
+ -->
+
+<project xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xmlns="http://maven.apache.org/POM/4.0.0"
+ 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.dcaegen2.analytics</groupId>
+ <artifactId>dcae-analytics</artifactId>
+ <version>3.0.0-SNAPSHOT</version>
+ </parent>
+
+ <artifactId>dcae-analytics-tca-web</artifactId>
+ <packaging>jar</packaging>
+
+ <!-- THE MODULE CONTAINS WEB RELATED CODE FOR TCA -->
+ <name>DCAE Analytics TCA Web</name>
+ <description>Contains Web related code for TCA</description>
+
+ <properties>
+ <main.basedir>${project.parent.basedir}</main.basedir>
+ </properties>
+
+ <dependencies>
+
+ <!-- PROJECT DEPENDENCIES -->
+ <dependency>
+ <groupId>${project.groupId}</groupId>
+ <artifactId>dcae-analytics-web</artifactId>
+ </dependency>
+ <dependency>
+ <groupId>${project.groupId}</groupId>
+ <artifactId>dcae-analytics-tca-core</artifactId>
+ </dependency>
+
+
+ <!-- SPRING DEPENDENCIES -->
+ <dependency>
+ <groupId>org.springframework.boot</groupId>
+ <artifactId>spring-boot-starter-actuator</artifactId>
+ </dependency>
+ <dependency>
+ <groupId>io.micrometer</groupId>
+ <artifactId>micrometer-registry-prometheus</artifactId>
+ </dependency>
+
+
+ <!-- SPRING CONFIGURATION META DATA ANNOTATION PROCESSOR -->
+ <dependency>
+ <groupId>org.springframework.boot</groupId>
+ <artifactId>spring-boot-configuration-processor</artifactId>
+ <optional>true</optional>
+ </dependency>
+
+ <!-- CODE GENERATION -->
+ <dependency>
+ <groupId>org.projectlombok</groupId>
+ <artifactId>lombok</artifactId>
+ <scope>provided</scope>
+ </dependency>
+
+ <!-- FIND BUGS -->
+ <dependency>
+ <groupId>com.google.code.findbugs</groupId>
+ <artifactId>jsr305</artifactId>
+ </dependency>
+ <dependency>
+ <groupId>com.google.code.findbugs</groupId>
+ <artifactId>annotations</artifactId>
+ </dependency>
+
+ <!-- REST API SWAGGER -->
+ <dependency>
+ <groupId>io.springfox</groupId>
+ <artifactId>springfox-swagger2</artifactId>
+ </dependency>
+ <dependency>
+ <groupId>io.springfox</groupId>
+ <artifactId>springfox-swagger-ui</artifactId>
+ </dependency>
+
+ <!-- TEST DEPENDENCIES -->
+ <dependency>
+ <groupId>${project.groupId}</groupId>
+ <artifactId>dcae-analytics-test</artifactId>
+ </dependency>
+
+ </dependencies>
+
+
+ <build>
+ <resources>
+ <resource>
+ <directory>${project.basedir}/src/main/resources</directory>
+ </resource>
+ <resource>
+ <directory>${project.build.directory}/git</directory>
+ </resource>
+ <resource>
+ <directory>docker</directory>
+ <includes>
+ <include>Dockerfile</include>
+ </includes>
+ <targetPath>${project.basedir}</targetPath>
+ <filtering>true</filtering>
+ </resource>
+ </resources>
+
+ <plugins>
+ <plugin>
+ <groupId>pl.project13.maven</groupId>
+ <artifactId>git-commit-id-plugin</artifactId>
+ </plugin>
+ <plugin>
+ <groupId>org.springframework.boot</groupId>
+ <artifactId>spring-boot-maven-plugin</artifactId>
+ </plugin>
+ </plugins>
+ </build>
+</project>
diff --git a/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/TcaAppMain.java b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/TcaAppMain.java
new file mode 100644
index 0000000..5b8c8ea
--- /dev/null
+++ b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/TcaAppMain.java
@@ -0,0 +1,42 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.analytics.tca.web;
+
+import org.onap.dcae.analytics.tca.web.config.TcaWebConfig;
+import org.springframework.boot.SpringApplication;
+import org.springframework.boot.SpringBootConfiguration;
+import org.springframework.boot.autoconfigure.EnableAutoConfiguration;
+import org.springframework.context.annotation.Import;
+import org.springframework.integration.config.EnableIntegration;
+
+/**
+ * @author Rajiv Singla
+ */
+@Import(value = {TcaWebConfig.class})
+@EnableIntegration
+@SpringBootConfiguration
+@EnableAutoConfiguration
+public class TcaAppMain {
+
+ public static void main(String[] args) {
+ SpringApplication.run(TcaAppMain.class, args);
+ }
+
+}
diff --git a/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/TcaAppProperties.java b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/TcaAppProperties.java
new file mode 100644
index 0000000..9ee625a
--- /dev/null
+++ b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/TcaAppProperties.java
@@ -0,0 +1,86 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.analytics.tca.web;
+
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import lombok.ToString;
+
+import org.onap.dcae.analytics.model.TcaModelConstants;
+import org.onap.dcae.analytics.model.configbindingservice.BaseConfigBindingServiceProperties;
+import org.onap.dcae.analytics.model.configbindingservice.ConfigBindingServiceConstants;
+import org.onap.dcae.analytics.model.configbindingservice.ConfigBindingServiceModel;
+import org.springframework.boot.context.properties.ConfigurationProperties;
+import org.springframework.validation.annotation.Validated;
+
+/**
+ * @author Rajiv Singla
+ */
+@Data
+@EqualsAndHashCode(callSuper = true)
+@ConfigurationProperties(ConfigBindingServiceConstants.CONFIG_BINDING_SERVICE_PROPERTIES_KEY)
+@Validated
+public class TcaAppProperties extends BaseConfigBindingServiceProperties {
+
+ private static final long serialVersionUID = 1L;
+
+ private Tca tca;
+
+ /**
+ * TCA Application properties
+ */
+ @Data
+ public static class Tca implements ConfigBindingServiceModel {
+
+ private static final long serialVersionUID = 1L;
+
+ private String policy;
+ private Integer processingBatchSize = TcaModelConstants.DEFAULT_TCA_PROCESSING_BATCH_SIZE;
+ private Boolean enableAbatement = TcaModelConstants.DEFAULT_ABATEMENT_ENABLED;
+ private Boolean enableEcompLogging = TcaModelConstants.DEFAULT_ECOMP_LOGGING_ENABLED;
+ private Aai aai = new Aai();
+
+ }
+
+
+ /**
+ * A&amp;AI properties
+ */
+ @Data
+ @ToString(exclude = "password")
+ public static class Aai implements ConfigBindingServiceModel {
+
+ private static final long serialVersionUID = 1L;
+
+ private Boolean enableEnrichment = TcaModelConstants.DEFAULT_AAI_ENRICHMENT_ENABLED;
+ private String url;
+ private String username;
+ private String password;
+
+ private String proxyUrl = null;
+ private Boolean ignoreSSLValidation = TcaModelConstants.DEFAULT_TCA_AAI_IGNORE_SSL_VALIDATION;
+
+ private String genericVnfPath = TcaModelConstants.DEFAULT_TCA_AAI_GENERIC_VNF_PATH;
+ private String nodeQueryPath = TcaModelConstants.DEFAULT_TCA_AAI_NODE_QUERY_PATH;
+
+ }
+
+
+}
diff --git a/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/aai/TcaAaiEnrichmentContextImpl.java b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/aai/TcaAaiEnrichmentContextImpl.java
new file mode 100644
index 0000000..73a600a
--- /dev/null
+++ b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/aai/TcaAaiEnrichmentContextImpl.java
@@ -0,0 +1,50 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.analytics.tca.web.aai;
+
+import org.onap.dcae.analytics.tca.core.service.TcaAaiEnrichmentContext;
+import org.onap.dcae.analytics.tca.core.service.TcaAaiEnrichmentService;
+import org.onap.dcae.analytics.tca.web.TcaAppProperties;
+
+/**
+ * @author Rajiv Singla
+ */
+public class TcaAaiEnrichmentContextImpl implements TcaAaiEnrichmentContext {
+
+ private final TcaAppProperties tcaAppProperties;
+ private final TcaAaiEnrichmentService tcaAaiEnrichmentService;
+
+ public TcaAaiEnrichmentContextImpl(final TcaAppProperties tcaAppProperties,
+ final TcaAaiEnrichmentService tcaAaiEnrichmentService) {
+ this.tcaAppProperties = tcaAppProperties;
+ this.tcaAaiEnrichmentService = tcaAaiEnrichmentService;
+ }
+
+
+ @Override
+ public boolean isAaiEnrichmentEnabled() {
+ return tcaAppProperties.getTca().getAai().getEnableEnrichment();
+ }
+
+ @Override
+ public TcaAaiEnrichmentService getAaiEnrichmentService() {
+ return tcaAaiEnrichmentService;
+ }
+}
diff --git a/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/aai/TcaAaiEnrichmentServiceImpl.java b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/aai/TcaAaiEnrichmentServiceImpl.java
new file mode 100644
index 0000000..d38bd23
--- /dev/null
+++ b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/aai/TcaAaiEnrichmentServiceImpl.java
@@ -0,0 +1,273 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.analytics.tca.web.aai;
+
+import static org.onap.dcae.analytics.tca.model.util.json.TcaModelJsonConversion.TCA_OBJECT_MAPPER;
+
+import com.fasterxml.jackson.databind.JsonNode;
+
+import java.io.IOException;
+import java.net.URI;
+import java.util.Collections;
+import java.util.Iterator;
+import java.util.Map;
+import java.util.Set;
+
+import org.onap.dcae.analytics.model.AnalyticsHttpConstants;
+import org.onap.dcae.analytics.model.TcaModelConstants;
+import org.onap.dcae.analytics.tca.core.service.TcaAaiEnrichmentService;
+import org.onap.dcae.analytics.tca.core.service.TcaExecutionContext;
+import org.onap.dcae.analytics.tca.model.facade.Aai;
+import org.onap.dcae.analytics.tca.model.facade.TcaAlert;
+import org.onap.dcae.analytics.tca.web.TcaAppProperties;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+import org.springframework.http.HttpEntity;
+import org.springframework.http.HttpHeaders;
+import org.springframework.http.HttpMethod;
+import org.springframework.http.ResponseEntity;
+import org.springframework.util.StringUtils;
+import org.springframework.web.client.RestTemplate;
+import org.springframework.web.util.UriComponentsBuilder;
+
+/**
+ * @author Rajiv Singla
+ */
+public class TcaAaiEnrichmentServiceImpl implements TcaAaiEnrichmentService {
+
+ private static final Logger logger = LoggerFactory.getLogger(TcaAaiEnrichmentServiceImpl.class);
+
+ private final TcaAppProperties tcaAppProperties;
+ private final RestTemplate aaiRestTemplate;
+
+ public TcaAaiEnrichmentServiceImpl(final TcaAppProperties tcaAppProperties,
+ final RestTemplate aaiRestTemplate) {
+ this.tcaAppProperties = tcaAppProperties;
+ this.aaiRestTemplate = aaiRestTemplate;
+ }
+
+
+ @Override
+ public TcaAlert doAaiEnrichment(final TcaExecutionContext tcaExecutionContext) {
+
+ final TcaAlert tcaAlert = tcaExecutionContext.getTcaResultContext().getTcaAlert();
+
+ // do aai enrichment
+ if (isVNFAlert(tcaAlert)) {
+ // do vnf enrichment
+ doAaiVnfEnrichment(tcaExecutionContext, aaiRestTemplate, tcaAppProperties);
+ } else {
+ // do vm enrichment
+ doAaiVmEnrichment(tcaExecutionContext, aaiRestTemplate, tcaAppProperties);
+ }
+
+ return tcaAlert;
+ }
+
+ private static void doAaiVmEnrichment(final TcaExecutionContext tcaExecutionContext,
+ final RestTemplate aaiRestTemplate,
+ final TcaAppProperties tcaAppProperties) {
+
+ final TcaAlert tcaAlert = tcaExecutionContext.getTcaResultContext().getTcaAlert();
+ final String requestId = tcaExecutionContext.getRequestId();
+ final String transactionId = tcaExecutionContext.getTransactionId();
+ final String vServerName = tcaAlert.getAai().getGenericServerName();
+
+ // create new node query uri
+ final TcaAppProperties.Aai aai = tcaAppProperties.getTca().getAai();
+ final URI nodeQueryUri = UriComponentsBuilder.fromHttpUrl(aai.getUrl())
+ .path(aai.getNodeQueryPath())
+ .queryParam("search-node-type", "vserver")
+ .queryParam("filter", "vserver-name:EQUALS:" + vServerName)
+ .build(Collections.emptyMap());
+
+ // get resource link
+ final String resourceLink =
+ getVMResourceLink(getAAIRestAPIResponse(aaiRestTemplate, nodeQueryUri, requestId, transactionId));
+ if (resourceLink == null) {
+ return;
+ }
+
+ // create virtual server enrichment uri
+ final URI vServerEnrichmentUri = UriComponentsBuilder.fromHttpUrl(aai.getUrl())
+ .path(resourceLink)
+ .build(Collections.emptyMap());
+
+ // fetch virtual server enrichment details
+ final String vServerEnrichmentDetails =
+ getAAIRestAPIResponse(aaiRestTemplate, vServerEnrichmentUri, requestId, transactionId);
+
+ // do aai enrichment
+ enrichAAI(vServerEnrichmentDetails, tcaAlert, TcaModelConstants.AAI_VSERVER_KEY_PREFIX);
+ }
+
+ private static void doAaiVnfEnrichment(final TcaExecutionContext tcaExecutionContext,
+ final RestTemplate aaiRestTemplate,
+ final TcaAppProperties tcaAppProperties) {
+
+ final TcaAlert tcaAlert = tcaExecutionContext.getTcaResultContext().getTcaAlert();
+ final String requestId = tcaExecutionContext.getRequestId();
+ final String transactionId = tcaExecutionContext.getTransactionId();
+ final String genericVnfName = tcaAlert.getAai().getGenericVNFName();
+
+ // create new generic vnf uri
+ final TcaAppProperties.Aai aai = tcaAppProperties.getTca().getAai();
+ final URI genericVnfUri = UriComponentsBuilder.fromHttpUrl(aai.getUrl())
+ .path(aai.getGenericVnfPath())
+ .queryParam("vnf-name", genericVnfName)
+ .build(Collections.emptyMap());
+
+ // fetch response
+ final String aaiResponse = getAAIRestAPIResponse(aaiRestTemplate, genericVnfUri, requestId, transactionId);
+
+ // do AAI enrichment
+ enrichAAI(aaiResponse, tcaAlert, TcaModelConstants.AAI_VNF_KEY_PREFIX);
+ }
+
+
+ /**
+ * Fetch response from A&AI Rest API as json string for given aai uri. Returns null if unable to fetch response
+ * from A&AI API
+ *
+ * @param aaiRestTemplate aai rest template
+ * @param aaiUri aai uri
+ *
+ * @return A&AI API response as json string
+ */
+ private static String getAAIRestAPIResponse(final RestTemplate aaiRestTemplate, final URI aaiUri,
+ final String requestId, final String transactionId) {
+ // fetch response
+ ResponseEntity<String> aaiResponseEntity = null;
+ try {
+ final HttpHeaders headers = new HttpHeaders();
+ headers.add(AnalyticsHttpConstants.REQUEST_ID_HEADER_KEY, requestId);
+ headers.add(AnalyticsHttpConstants.REQUEST_TRANSACTION_ID_HEADER_KEY, transactionId);
+ final HttpEntity<String> httpEntity = new HttpEntity<>(headers);
+ aaiResponseEntity = aaiRestTemplate.exchange(aaiUri, HttpMethod.GET, httpEntity, String.class);
+ } catch (Exception e) {
+ logger.debug("Request id: " + requestId + ". Unable to get A&AI enrichment details", e);
+ }
+
+ if (aaiResponseEntity != null && aaiResponseEntity.getStatusCode().is2xxSuccessful()) {
+ return aaiResponseEntity.getBody();
+ }
+
+ return null;
+ }
+
+
+ /**
+ * Populates A&AI details retrieved from A&AI Enrichment API into Alerts A&AI Object
+ *
+ * @param aaiEnrichmentDetails A&AI Enrichment API fetched JSON String
+ * @param tcaAlert tca alert
+ * @param keyPrefix Key prefix that needs to be added to each fetched A&AI Enrichment record
+ *
+ * @return true if A&AI enrichment completed successfully
+ */
+ private static boolean enrichAAI(final String aaiEnrichmentDetails, final TcaAlert tcaAlert,
+ final String keyPrefix) {
+
+ final Aai preEnrichmentAAI = tcaAlert.getAai();
+ if (aaiEnrichmentDetails == null) {
+ logger.warn("Request id: {}. No A&AI Enrichment possible. A&AI Enrichment details are absent.",
+ tcaAlert.getRequestId());
+ return false;
+ }
+
+ final Aai enrichedAAI = getNewEnrichedAAI(aaiEnrichmentDetails);
+
+ if (enrichedAAI != null) {
+ final Set<Map.Entry<String, Object>> enrichedAAIEntrySet =
+ enrichedAAI.getDynamicProperties().entrySet();
+ final Map<String, Object> preEnrichmentAAIDynamicProperties = preEnrichmentAAI.getDynamicProperties();
+
+ // populate Alert A&AI Enrichment details and add prefix to key
+ for (Map.Entry<String, Object> enrichedAAIEntry : enrichedAAIEntrySet) {
+ preEnrichmentAAIDynamicProperties.put(
+ keyPrefix + enrichedAAIEntry.getKey(), enrichedAAIEntry.getValue());
+ }
+
+ logger.debug("Request id: {}. A&AI Enrichment was completed successfully.", tcaAlert.getRequestId());
+ return true;
+ } else {
+ logger.warn("Request id: {}. No A&AI Enrichment possible. Skipped - Invalid A&AI Response.",
+ tcaAlert.getRequestId());
+ return false;
+ }
+
+ }
+
+ /**
+ * Creates a new A&AI object with only top level A&AI Enrichment details
+ *
+ * @param aaiEnrichmentDetails A&AI Enrichment details
+ *
+ * @return new A&AI with only top level A&AI Enrichment details
+ */
+ private static Aai getNewEnrichedAAI(final String aaiEnrichmentDetails) {
+ try {
+ final JsonNode rootNode = TCA_OBJECT_MAPPER.readTree(aaiEnrichmentDetails);
+ final Iterator<Map.Entry<String, JsonNode>> fieldsIterator = rootNode.fields();
+ while (fieldsIterator.hasNext()) {
+ final Map.Entry<String, JsonNode> fieldEntry = fieldsIterator.next();
+ final JsonNode jsonNode = fieldEntry.getValue();
+ // remove all arrays, objects from A&AI Enrichment Json
+ if (jsonNode.isPojo() || jsonNode.isObject() || jsonNode.isArray()) {
+ fieldsIterator.remove();
+ }
+ }
+ return TCA_OBJECT_MAPPER.treeToValue(rootNode, Aai.class);
+ } catch (IOException e) {
+ logger.error(
+ "Failed to Parse AAI Enrichment Details from JSON: {}, Exception: {}.", aaiEnrichmentDetails, e);
+ }
+ return null;
+ }
+
+ /**
+ * Fetches VM Object Resource Link from A&AI Resource Link Json
+ *
+ * @param vmAAIResourceLinkDetails VM Object Resource Link from A&AI Resource Link Json
+ *
+ * @return object resource link String
+ */
+ private static String getVMResourceLink(final String vmAAIResourceLinkDetails) {
+ if (StringUtils.hasText(vmAAIResourceLinkDetails)) {
+ try {
+ final JsonNode jsonNode = TCA_OBJECT_MAPPER.readTree(vmAAIResourceLinkDetails);
+ final JsonNode resourceLinkJsonNode = jsonNode.findPath("resource-link");
+ if (!resourceLinkJsonNode.isMissingNode()) {
+ return resourceLinkJsonNode.asText();
+ }
+ } catch (IOException e) {
+ logger.error("Unable to determine VM Object link inside AAI Resource Link Response JSON: {}",
+ vmAAIResourceLinkDetails, e);
+ }
+ }
+ return null;
+ }
+
+
+ private static boolean isVNFAlert(final TcaAlert tcaAlert) {
+ return tcaAlert.getTargetType().equals(TcaModelConstants.TCA_ALERT_VNF_TARGET_TYPE);
+ }
+
+}
diff --git a/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/aai/TcaAaiRestClientPreferences.java b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/aai/TcaAaiRestClientPreferences.java
new file mode 100644
index 0000000..93a54a9
--- /dev/null
+++ b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/aai/TcaAaiRestClientPreferences.java
@@ -0,0 +1,48 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.analytics.tca.web.aai;
+
+import java.net.URL;
+
+import javax.annotation.Nonnull;
+import javax.annotation.Nullable;
+
+import org.onap.dcae.analytics.web.http.BaseHttpClientPreferences;
+import org.springframework.http.HttpHeaders;
+
+/**
+ * @author Rajiv Singla
+ */
+public class TcaAaiRestClientPreferences extends BaseHttpClientPreferences {
+
+ private static final long serialVersionUID = 1L;
+
+ public TcaAaiRestClientPreferences(@Nonnull final String requestURL,
+ @Nullable final String httpClientId,
+ @Nullable final HttpHeaders httpHeaders,
+ @Nullable final String username,
+ @Nullable final String password,
+ @Nullable final URL proxyURL,
+ @Nullable final Boolean ignoreSSLValidation,
+ @Nullable final Boolean enableEcompAuditLogging) {
+ super(requestURL, httpClientId, httpHeaders, username, password, proxyURL, ignoreSSLValidation,
+ enableEcompAuditLogging);
+ }
+}
diff --git a/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/abatement/mongo/MongoAbatementContextImpl.java b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/abatement/mongo/MongoAbatementContextImpl.java
new file mode 100644
index 0000000..a4784e0
--- /dev/null
+++ b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/abatement/mongo/MongoAbatementContextImpl.java
@@ -0,0 +1,58 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.analytics.tca.web.abatement.mongo;
+
+import org.onap.dcae.analytics.tca.core.service.TcaAbatementContext;
+import org.onap.dcae.analytics.tca.core.service.TcaAbatementEntity;
+import org.onap.dcae.analytics.tca.core.service.TcaAbatementRepository;
+import org.onap.dcae.analytics.tca.web.TcaAppProperties;
+
+/**
+ * An implementation of {@link TcaAbatementContext} backed by mongo database as persistence provider
+ *
+ * @author Rajiv Singla
+ */
+public class MongoAbatementContextImpl implements TcaAbatementContext {
+
+ private TcaAppProperties tcaAppProperties;
+ private MongoAbatementRepository mongoAbatementRepository;
+
+ public MongoAbatementContextImpl(final TcaAppProperties tcaAppProperties,
+ final MongoAbatementRepository mongoAbatementRepository) {
+ this.tcaAppProperties = tcaAppProperties;
+ this.mongoAbatementRepository = mongoAbatementRepository;
+ }
+
+ @Override
+ public boolean isAbatementEnabled() {
+ return tcaAppProperties.getTca().getEnableAbatement();
+ }
+
+ @Override
+ public TcaAbatementRepository getTcaAbatementRepository() {
+ return mongoAbatementRepository;
+ }
+
+ @Override
+ public TcaAbatementEntity create(final String lookupKey, final String requestId,
+ final boolean isAbatementAlertSent) {
+ return new MongoAbatementEntity(lookupKey, requestId, isAbatementAlertSent);
+ }
+}
diff --git a/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/abatement/mongo/MongoAbatementEntity.java b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/abatement/mongo/MongoAbatementEntity.java
new file mode 100644
index 0000000..562c918
--- /dev/null
+++ b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/abatement/mongo/MongoAbatementEntity.java
@@ -0,0 +1,59 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.analytics.tca.web.abatement.mongo;
+
+import lombok.Data;
+import lombok.NoArgsConstructor;
+
+import java.util.Date;
+
+import org.onap.dcae.analytics.tca.core.service.TcaAbatementEntity;
+import org.onap.dcae.analytics.tca.model.TcaModel;
+import org.springframework.data.annotation.CreatedDate;
+import org.springframework.data.annotation.Id;
+import org.springframework.data.annotation.LastModifiedDate;
+import org.springframework.data.mongodb.core.mapping.Document;
+
+/**
+ * @author Rajiv Singla
+ */
+@Data
+@NoArgsConstructor
+@Document(collection = "tca_abatement")
+public class MongoAbatementEntity implements TcaAbatementEntity, TcaModel {
+
+ private static final long serialVersionUID = 1L;
+
+ @Id
+ private String lookupKey;
+ private String requestId;
+ private boolean isAbatementAlertSent;
+
+ @LastModifiedDate
+ private Date lastModificationDate;
+ @CreatedDate
+ private Date createdDate;
+
+ MongoAbatementEntity(final String lookupKey, final String requestId, final boolean isAbatementAlertSent) {
+ this.lookupKey = lookupKey;
+ this.requestId = requestId;
+ this.isAbatementAlertSent = isAbatementAlertSent;
+ }
+}
diff --git a/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/abatement/mongo/MongoAbatementRepository.java b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/abatement/mongo/MongoAbatementRepository.java
new file mode 100644
index 0000000..6727007
--- /dev/null
+++ b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/abatement/mongo/MongoAbatementRepository.java
@@ -0,0 +1,36 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.analytics.tca.web.abatement.mongo;
+
+import java.util.List;
+
+import org.bson.types.ObjectId;
+import org.onap.dcae.analytics.tca.core.service.TcaAbatementEntity;
+import org.onap.dcae.analytics.tca.core.service.TcaAbatementRepository;
+import org.springframework.data.mongodb.repository.MongoRepository;
+
+/**
+ * @author Rajiv Singla
+ */
+public interface MongoAbatementRepository extends
+ TcaAbatementRepository, MongoRepository<MongoAbatementEntity, ObjectId> {
+
+ List<TcaAbatementEntity> findByLookupKey(final String lookUpKey);
+}
diff --git a/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/abatement/simple/SimpleAbatementContextImpl.java b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/abatement/simple/SimpleAbatementContextImpl.java
new file mode 100644
index 0000000..6c17039
--- /dev/null
+++ b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/abatement/simple/SimpleAbatementContextImpl.java
@@ -0,0 +1,62 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.analytics.tca.web.abatement.simple;
+
+import org.onap.dcae.analytics.tca.core.service.TcaAbatementContext;
+import org.onap.dcae.analytics.tca.core.service.TcaAbatementEntity;
+import org.onap.dcae.analytics.tca.core.service.TcaAbatementRepository;
+import org.onap.dcae.analytics.tca.web.TcaAppProperties;
+
+/**
+ * A simple implementation for {@link TcaAbatementContext} which should be used for testing and development
+ * purposes only.
+ *
+ * @author Rajiv Singla
+ */
+public class SimpleAbatementContextImpl implements TcaAbatementContext {
+
+
+ private final TcaAppProperties tcaAppProperties;
+ private final TcaAbatementRepository tcaAbatementRepository;
+
+ public SimpleAbatementContextImpl(final TcaAppProperties tcaAppProperties,
+ final TcaAbatementRepository tcaAbatementRepository) {
+ this.tcaAppProperties = tcaAppProperties;
+ this.tcaAbatementRepository = tcaAbatementRepository;
+ }
+
+
+ @Override
+ public boolean isAbatementEnabled() {
+ return tcaAppProperties.getTca().getEnableAbatement();
+ }
+
+ @Override
+ public TcaAbatementRepository getTcaAbatementRepository() {
+ return tcaAbatementRepository;
+ }
+
+ @Override
+ public TcaAbatementEntity create(final String lookupKey, final String requestId,
+ final boolean isAbatementAlertSent) {
+ return new SimpleAbatementEntity(lookupKey, requestId, isAbatementAlertSent);
+ }
+
+}
diff --git a/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/abatement/simple/SimpleAbatementEntity.java b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/abatement/simple/SimpleAbatementEntity.java
new file mode 100644
index 0000000..c12306f
--- /dev/null
+++ b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/abatement/simple/SimpleAbatementEntity.java
@@ -0,0 +1,58 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.analytics.tca.web.abatement.simple;
+
+import lombok.Data;
+import lombok.NoArgsConstructor;
+
+import java.util.Date;
+
+import org.onap.dcae.analytics.tca.core.service.TcaAbatementEntity;
+import org.onap.dcae.analytics.tca.model.TcaModel;
+
+/**
+ * @author Rajiv Singla
+ */
+@Data
+@NoArgsConstructor
+public class SimpleAbatementEntity implements TcaAbatementEntity, TcaModel {
+
+ private static final long serialVersionUID = 1L;
+
+ protected String lookupKey;
+ protected String requestId;
+ protected boolean isAbatementAlertSent;
+ protected Date lastModificationDate;
+
+ SimpleAbatementEntity(final String lookupKey, final String requestId, final boolean isAbatementAlertSent) {
+ this.lookupKey = lookupKey;
+ this.requestId = requestId;
+ this.isAbatementAlertSent = isAbatementAlertSent;
+ this.lastModificationDate = new Date();
+ }
+
+ public Date getLastModificationDate() {
+ return new Date(lastModificationDate.getTime());
+ }
+
+ public void setLastModificationDate(final Date lastModificationDate) {
+ this.lastModificationDate = new Date(lastModificationDate.getTime());
+ }
+}
diff --git a/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/abatement/simple/SimpleAbatementRepository.java b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/abatement/simple/SimpleAbatementRepository.java
new file mode 100644
index 0000000..452f07f
--- /dev/null
+++ b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/abatement/simple/SimpleAbatementRepository.java
@@ -0,0 +1,89 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.analytics.tca.web.abatement.simple;
+
+import static org.onap.dcae.analytics.model.TcaModelConstants.TCA_ABATEMENT_SIMPLE_REPOSITORY_MAX_ENTITY_COUNT;
+import static org.onap.dcae.analytics.model.TcaModelConstants.TCA_ABATEMENT_SIMPLE_REPOSITORY_REMOVE_ENTITY_COUNT;
+
+import java.util.Collections;
+import java.util.List;
+import java.util.concurrent.ConcurrentHashMap;
+import java.util.concurrent.ConcurrentLinkedQueue;
+
+import org.onap.dcae.analytics.tca.core.service.TcaAbatementEntity;
+import org.onap.dcae.analytics.tca.core.service.TcaAbatementRepository;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+/**
+ * A simple implementation for {@link TcaAbatementRepository} which should be used for testing and development
+ * purposes only.
+ *
+ * @author Rajiv Singla
+ */
+public class SimpleAbatementRepository implements TcaAbatementRepository {
+
+ private static final Logger logger = LoggerFactory.getLogger(SimpleAbatementRepository.class);
+
+ private final ConcurrentLinkedQueue<String> lookupKeysQueue;
+ private final ConcurrentHashMap<String, SimpleAbatementEntity> repository;
+
+ public SimpleAbatementRepository() {
+ this.lookupKeysQueue = new ConcurrentLinkedQueue<>();
+ this.repository = new ConcurrentHashMap<>(TCA_ABATEMENT_SIMPLE_REPOSITORY_MAX_ENTITY_COUNT);
+ }
+
+
+ @Override
+ public synchronized void save(final TcaAbatementEntity tcaAbatementEntity) {
+
+ // remove entries from repository if required
+ if (lookupKeysQueue.size() == TCA_ABATEMENT_SIMPLE_REPOSITORY_MAX_ENTITY_COUNT) {
+
+ logger.warn("Simple Abatement Repository reached its max allowed size: {}, " +
+ "Removing last inserted {} entries",
+ TCA_ABATEMENT_SIMPLE_REPOSITORY_MAX_ENTITY_COUNT,
+ TCA_ABATEMENT_SIMPLE_REPOSITORY_REMOVE_ENTITY_COUNT);
+
+ for (int i = 0; i < TCA_ABATEMENT_SIMPLE_REPOSITORY_REMOVE_ENTITY_COUNT; i++) {
+ final String lookupKey = lookupKeysQueue.poll();
+ logger.warn("Removing Abatement Lookup key: {} from Simple Abatement Repository", lookupKey);
+ repository.remove(lookupKey);
+ }
+
+ }
+
+ lookupKeysQueue.add(tcaAbatementEntity.getLookupKey());
+ final SimpleAbatementEntity simpleAbatementEntity =
+ new SimpleAbatementEntity(tcaAbatementEntity.getLookupKey(), tcaAbatementEntity.getRequestId(),
+ tcaAbatementEntity.isAbatementAlertSent());
+ repository.put(tcaAbatementEntity.getLookupKey(), simpleAbatementEntity);
+
+ }
+
+ @Override
+ public List<TcaAbatementEntity> findByLookupKey(final String lookUpKey) {
+ final SimpleAbatementEntity repoEntity = repository.getOrDefault(lookUpKey, null);
+ if (repoEntity == null) {
+ return Collections.emptyList();
+ }
+ return Collections.singletonList(repoEntity);
+ }
+}
diff --git a/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/config/ControllerConfig.java b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/config/ControllerConfig.java
new file mode 100644
index 0000000..930786e
--- /dev/null
+++ b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/config/ControllerConfig.java
@@ -0,0 +1,41 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.analytics.tca.web.config;
+
+import org.onap.dcae.analytics.tca.web.controller.TcaRestController;
+import org.onap.dcae.analytics.tca.web.domain.TcaPolicyWrapper;
+import org.onap.dcae.analytics.tca.web.service.TcaProcessingService;
+import org.springframework.context.annotation.Bean;
+import org.springframework.context.annotation.Configuration;
+
+/**
+ * @author Rajiv Singla
+ */
+@Configuration
+public class ControllerConfig {
+
+ @Bean
+ public TcaRestController tcaRestController(final TcaPolicyWrapper tcaPolicyWrapper,
+ final TcaProcessingService tcaProcessingService) {
+ return new TcaRestController(tcaProcessingService, tcaPolicyWrapper);
+ }
+
+
+}
diff --git a/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/config/SwaggerConfig.java b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/config/SwaggerConfig.java
new file mode 100644
index 0000000..11fa97c
--- /dev/null
+++ b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/config/SwaggerConfig.java
@@ -0,0 +1,63 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.analytics.tca.web.config;
+
+import static org.onap.dcae.analytics.model.TcaModelConstants.TCA_REST_API_PREFIX;
+
+import springfox.documentation.builders.ApiInfoBuilder;
+import springfox.documentation.builders.PathSelectors;
+import springfox.documentation.builders.RequestHandlerSelectors;
+import springfox.documentation.service.ApiInfo;
+import springfox.documentation.spi.DocumentationType;
+import springfox.documentation.spring.web.plugins.Docket;
+import springfox.documentation.swagger2.annotations.EnableSwagger2;
+
+import org.springframework.context.annotation.Bean;
+import org.springframework.context.annotation.Configuration;
+
+/**
+ * @author Rajiv Singla
+ */
+@Configuration
+@EnableSwagger2
+public class SwaggerConfig {
+
+ @Bean
+ public Docket apiDocker() {
+ return new Docket(DocumentationType.SWAGGER_2)
+ .apiInfo(getApiInfo())
+ .useDefaultResponseMessages(false)
+ .select()
+ .apis(RequestHandlerSelectors.basePackage("org.onap.dcae.analytics.tca.web.controller"))
+ .paths(PathSelectors.ant(TCA_REST_API_PREFIX + "**"))
+ .build();
+ }
+
+
+ private static ApiInfo getApiInfo() {
+ return new ApiInfoBuilder()
+ .title("TCA (Threshold Crossing Alert) Analytics RESTful API")
+ .description("RESTful API for Threshold Crossing Alerts Analytics")
+ .license("Apache License Version 2.0")
+ .version("3.0")
+ .build();
+ }
+
+}
diff --git a/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/config/TcaAaiConfig.java b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/config/TcaAaiConfig.java
new file mode 100644
index 0000000..773b9d3
--- /dev/null
+++ b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/config/TcaAaiConfig.java
@@ -0,0 +1,67 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.analytics.tca.web.config;
+
+import org.onap.dcae.analytics.tca.core.service.TcaAaiEnrichmentContext;
+import org.onap.dcae.analytics.tca.core.service.TcaAaiEnrichmentService;
+import org.onap.dcae.analytics.tca.web.TcaAppProperties;
+import org.onap.dcae.analytics.tca.web.aai.TcaAaiEnrichmentContextImpl;
+import org.onap.dcae.analytics.tca.web.aai.TcaAaiEnrichmentServiceImpl;
+import org.onap.dcae.analytics.tca.web.aai.TcaAaiRestClientPreferences;
+import org.onap.dcae.analytics.tca.web.util.function.TcaAppPropsToAaiRestClientPrefsFunction;
+import org.onap.dcae.analytics.web.http.HttpClientPreferencesCustomizer;
+import org.springframework.boot.web.client.RestTemplateBuilder;
+import org.springframework.context.annotation.Bean;
+import org.springframework.context.annotation.Configuration;
+import org.springframework.web.client.RestTemplate;
+
+/**
+ * @author Rajiv Singla
+ */
+@Configuration
+public class TcaAaiConfig {
+
+ @Bean
+ public TcaAaiRestClientPreferences aaiRestClientPreferences(final TcaAppProperties tcaAppProperties) {
+ return new TcaAppPropsToAaiRestClientPrefsFunction().apply(tcaAppProperties);
+ }
+
+ @Bean
+ public RestTemplate aaiRestTemplate(final TcaAaiRestClientPreferences aaiRestClientPreferences,
+ final RestTemplateBuilder restTemplateBuilder) {
+ return restTemplateBuilder
+ .additionalCustomizers(new HttpClientPreferencesCustomizer<>(aaiRestClientPreferences))
+ .build();
+ }
+
+ @Bean
+ public TcaAaiEnrichmentService aaiEnrichmentService(final TcaAppProperties tcaAppProperties,
+ final RestTemplate aaiRestTemplate) {
+ return new TcaAaiEnrichmentServiceImpl(tcaAppProperties, aaiRestTemplate);
+ }
+
+
+ @Bean
+ public TcaAaiEnrichmentContext tcaAaiEnrichmentContext(final TcaAppProperties tcaAppProperties,
+ final TcaAaiEnrichmentService aaiEnrichmentService) {
+ return new TcaAaiEnrichmentContextImpl(tcaAppProperties, aaiEnrichmentService);
+ }
+
+}
diff --git a/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/config/TcaMongoAbatementConfig.java b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/config/TcaMongoAbatementConfig.java
new file mode 100644
index 0000000..7b29f15
--- /dev/null
+++ b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/config/TcaMongoAbatementConfig.java
@@ -0,0 +1,48 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.analytics.tca.web.config;
+
+import org.onap.dcae.analytics.model.AnalyticsProfile;
+import org.onap.dcae.analytics.tca.core.service.TcaAbatementContext;
+import org.onap.dcae.analytics.tca.web.TcaAppProperties;
+import org.onap.dcae.analytics.tca.web.abatement.mongo.MongoAbatementContextImpl;
+import org.onap.dcae.analytics.tca.web.abatement.mongo.MongoAbatementRepository;
+import org.springframework.context.annotation.Bean;
+import org.springframework.context.annotation.Configuration;
+import org.springframework.context.annotation.Profile;
+import org.springframework.data.mongodb.config.EnableMongoAuditing;
+import org.springframework.data.mongodb.repository.config.EnableMongoRepositories;
+
+/**
+ * @author Rajiv Singla
+ */
+@Configuration
+@Profile(AnalyticsProfile.MONGO_PROFILE_NAME)
+@EnableMongoRepositories("org.onap.dcae.analytics.tca.web.abatement.mongo")
+@EnableMongoAuditing
+public class TcaMongoAbatementConfig {
+
+ @Bean
+ public TcaAbatementContext mongoAbatementContext(final TcaAppProperties tcaAppProperties,
+ final MongoAbatementRepository mongoAbatementRepository) {
+ return new MongoAbatementContextImpl(tcaAppProperties, mongoAbatementRepository);
+ }
+
+}
diff --git a/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/config/TcaMrConfig.java b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/config/TcaMrConfig.java
new file mode 100644
index 0000000..64cb6eb
--- /dev/null
+++ b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/config/TcaMrConfig.java
@@ -0,0 +1,114 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.analytics.tca.web.config;
+
+import static org.onap.dcae.analytics.model.AnalyticsHttpConstants.REQUEST_ID_HEADER_KEY;
+import static org.onap.dcae.analytics.model.AnalyticsHttpConstants.REQUEST_TRANSACTION_ID_HEADER_KEY;
+
+import java.util.List;
+import java.util.Map;
+
+import org.onap.dcae.analytics.model.AnalyticsProfile;
+import org.onap.dcae.analytics.model.DmaapMrConstants;
+import org.onap.dcae.analytics.tca.web.TcaAppProperties;
+import org.onap.dcae.analytics.tca.web.domain.TcaPolicyWrapper;
+import org.onap.dcae.analytics.tca.web.integration.TcaAlertTransformer;
+import org.onap.dcae.analytics.tca.web.integration.TcaPublisherResponseHandler;
+import org.onap.dcae.analytics.tca.web.service.TcaProcessingService;
+import org.onap.dcae.analytics.tca.web.util.function.TcaAppPropsToMrPublisherPrefsFunction;
+import org.onap.dcae.analytics.tca.web.util.function.TcaAppPropsToMrSubscriberPrefsFunction;
+import org.onap.dcae.analytics.web.dmaap.MrPublisherPreferences;
+import org.onap.dcae.analytics.web.dmaap.MrSubscriberPreferences;
+import org.springframework.context.annotation.Bean;
+import org.springframework.context.annotation.Configuration;
+import org.springframework.context.annotation.Profile;
+import org.springframework.integration.channel.DirectChannel;
+import org.springframework.integration.channel.NullChannel;
+import org.springframework.integration.channel.QueueChannel;
+import org.springframework.integration.dsl.IntegrationFlow;
+import org.springframework.integration.dsl.IntegrationFlows;
+import org.springframework.messaging.MessageHeaders;
+
+/**
+ * @author Rajiv Singla
+ */
+@Profile({AnalyticsProfile.DMAAP_PROFILE_NAME})
+@Configuration
+public class TcaMrConfig {
+
+ @Bean
+ public MrSubscriberPreferences mrSubscriberPreferences(final TcaAppProperties tcaAppProperties) {
+ return new TcaAppPropsToMrSubscriberPrefsFunction().apply(tcaAppProperties);
+ }
+
+ @Bean
+ public MrPublisherPreferences mrPublisherPreferences(final TcaAppProperties tcaAppProperties) {
+ return new TcaAppPropsToMrPublisherPrefsFunction().apply(tcaAppProperties);
+ }
+
+ @Bean
+ public Integer processingBatchSize(final TcaAppProperties tcaAppProperties) {
+ return tcaAppProperties.getTca().getProcessingBatchSize();
+ }
+
+ @Bean
+ public TcaAlertTransformer tcaAlertTransformer(final TcaAppProperties tcaAppProperties) {
+ return new TcaAlertTransformer(tcaAppProperties);
+ }
+
+
+ @Bean
+ public IntegrationFlow tcaMrFlow(final TcaPolicyWrapper tcaPolicyWrapper,
+ final QueueChannel mrSubscriberOutputChannel,
+ final DirectChannel mrPublisherInputChannel,
+ final TcaProcessingService tcaProcessingService,
+ final TcaAlertTransformer tcaAlertTransformer) {
+ // get messages from dmaap subscriber channel
+ return IntegrationFlows.from(mrSubscriberOutputChannel)
+ // handle incoming message from dmaap
+ .handle((List<String> cefMessages, Map<String, Object> headers) ->
+ tcaProcessingService.getTcaExecutionResults(
+ headers.getOrDefault(REQUEST_ID_HEADER_KEY, headers.get(MessageHeaders.ID)).toString(),
+ headers.getOrDefault(REQUEST_TRANSACTION_ID_HEADER_KEY, "").toString(),
+ tcaPolicyWrapper.getTcaPolicy(), cefMessages))
+ // transform tca execution results to alerts - if not alerts are detected terminate further processing
+ .transform(tcaAlertTransformer, c -> c.requiresReply(false))
+ // post messages to dmaap publisher input channel
+ .channel(mrPublisherInputChannel)
+ .get();
+ }
+
+
+ @Bean
+ public TcaPublisherResponseHandler tcaPublisherResponseHandler(final TcaAppProperties tcaAppProperties) {
+ return new TcaPublisherResponseHandler(tcaAppProperties);
+ }
+
+ @Bean
+ public IntegrationFlow tcaPublisherResponseFlow(final TcaPublisherResponseHandler tcaPublisherResponseHandler) {
+ return IntegrationFlows.from(DmaapMrConstants.DMAAP_MR_PUBLISHER_OUTPUT_CHANNEL)
+ // log response from dmaap publisher output channel
+ .handle(tcaPublisherResponseHandler)
+ // finish processing
+ .channel(new NullChannel())
+ .get();
+ }
+
+}
diff --git a/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/config/TcaSimpleAbatementConfig.java b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/config/TcaSimpleAbatementConfig.java
new file mode 100644
index 0000000..9f8cb92
--- /dev/null
+++ b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/config/TcaSimpleAbatementConfig.java
@@ -0,0 +1,50 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.analytics.tca.web.config;
+
+import org.onap.dcae.analytics.model.AnalyticsProfile;
+import org.onap.dcae.analytics.tca.core.service.TcaAbatementContext;
+import org.onap.dcae.analytics.tca.core.service.TcaAbatementRepository;
+import org.onap.dcae.analytics.tca.web.TcaAppProperties;
+import org.onap.dcae.analytics.tca.web.abatement.simple.SimpleAbatementContextImpl;
+import org.onap.dcae.analytics.tca.web.abatement.simple.SimpleAbatementRepository;
+import org.springframework.context.annotation.Bean;
+import org.springframework.context.annotation.Configuration;
+import org.springframework.context.annotation.Profile;
+
+/**
+ * @author Rajiv Singla
+ */
+@Configuration
+@Profile(AnalyticsProfile.NOT_MONGO_PROFILE_NAME)
+public class TcaSimpleAbatementConfig {
+
+ @Bean
+ public TcaAbatementRepository simpleAbatementRepository() {
+ return new SimpleAbatementRepository();
+ }
+
+ @Bean
+ public TcaAbatementContext tcaAbatementContext(final TcaAppProperties tcaAppProperties,
+ final TcaAbatementRepository tcaAbatementRepository) {
+ return new SimpleAbatementContextImpl(tcaAppProperties, tcaAbatementRepository);
+ }
+
+}
diff --git a/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/config/TcaWebConfig.java b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/config/TcaWebConfig.java
new file mode 100644
index 0000000..7be20cc
--- /dev/null
+++ b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/config/TcaWebConfig.java
@@ -0,0 +1,84 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.analytics.tca.web.config;
+
+import com.fasterxml.jackson.databind.ObjectMapper;
+
+import java.util.stream.Stream;
+
+import org.onap.dcae.analytics.model.AnalyticsProfile;
+import org.onap.dcae.analytics.model.common.ConfigSource;
+import org.onap.dcae.analytics.tca.core.service.TcaAaiEnrichmentContext;
+import org.onap.dcae.analytics.tca.core.service.TcaAbatementContext;
+import org.onap.dcae.analytics.tca.model.util.json.TcaModelJsonConversion;
+import org.onap.dcae.analytics.tca.web.TcaAppProperties;
+import org.onap.dcae.analytics.tca.web.domain.TcaPolicyWrapper;
+import org.onap.dcae.analytics.tca.web.service.TcaProcessingService;
+import org.onap.dcae.analytics.tca.web.service.TcaProcessingServiceImpl;
+import org.onap.dcae.analytics.tca.web.validation.TcaAppPropertiesValidator;
+import org.onap.dcae.analytics.web.config.AnalyticsWebConfig;
+import org.springframework.boot.context.properties.EnableConfigurationProperties;
+import org.springframework.context.annotation.Bean;
+import org.springframework.context.annotation.Configuration;
+import org.springframework.context.annotation.Import;
+import org.springframework.core.env.Environment;
+import org.springframework.validation.Validator;
+
+/**
+ * @author Rajiv Singla
+ */
+@Configuration
+@EnableConfigurationProperties(value = TcaAppProperties.class)
+@Import(value = {AnalyticsWebConfig.class, TcaMrConfig.class, TcaAaiConfig.class,
+ TcaMongoAbatementConfig.class, TcaSimpleAbatementConfig.class, SwaggerConfig.class, ControllerConfig.class})
+public class TcaWebConfig {
+
+ @Bean
+ public static Validator configurationPropertiesValidator() {
+ return new TcaAppPropertiesValidator();
+ }
+
+ @Bean
+ public ObjectMapper objectMapper() {
+ return TcaModelJsonConversion.TCA_OBJECT_MAPPER;
+ }
+
+ @Bean
+ public TcaPolicyWrapper tcaPolicyWrapper(final TcaAppProperties tcaAppProperties,
+ final Environment environment) {
+ final String policy = tcaAppProperties.getTca().getPolicy();
+ final boolean isConfigBindingServiceProfileActive =
+ Stream.of(environment.getActiveProfiles())
+ .anyMatch(profile ->
+ profile.equalsIgnoreCase(AnalyticsProfile.CONFIG_BINDING_SERVICE_PROFILE_NAME));
+ if (isConfigBindingServiceProfileActive) {
+ return new TcaPolicyWrapper(policy, ConfigSource.CONFIG_BINDING_SERVICE);
+ } else {
+ return new TcaPolicyWrapper(policy, ConfigSource.CLASSPATH);
+ }
+ }
+
+ @Bean
+ public TcaProcessingService tcaProcessingService(final TcaAbatementContext tcaAbatementContext,
+ final TcaAaiEnrichmentContext tcaAaiEnrichmentContext) {
+ return new TcaProcessingServiceImpl(tcaAbatementContext, tcaAaiEnrichmentContext);
+ }
+
+}
diff --git a/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/controller/TcaRestController.java b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/controller/TcaRestController.java
new file mode 100644
index 0000000..eb9eb13
--- /dev/null
+++ b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/controller/TcaRestController.java
@@ -0,0 +1,114 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.analytics.tca.web.controller;
+
+import io.swagger.annotations.Api;
+import io.swagger.annotations.ApiOperation;
+
+import java.time.format.DateTimeFormatter;
+import java.util.List;
+import java.util.stream.Collectors;
+
+import org.onap.dcae.analytics.model.TcaModelConstants;
+import org.onap.dcae.analytics.model.common.ConfigSource;
+import org.onap.dcae.analytics.tca.core.service.TcaExecutionContext;
+import org.onap.dcae.analytics.tca.core.service.TcaResultContext;
+import org.onap.dcae.analytics.tca.model.policy.TcaPolicy;
+import org.onap.dcae.analytics.tca.model.restapi.TcaExecutionRequest;
+import org.onap.dcae.analytics.tca.model.restapi.TcaExecutionResponse;
+import org.onap.dcae.analytics.tca.web.domain.TcaPolicyWrapper;
+import org.onap.dcae.analytics.tca.web.service.TcaProcessingService;
+import org.onap.dcae.analytics.tca.web.util.TcaUtils;
+import org.springframework.http.MediaType;
+import org.springframework.http.ResponseEntity;
+import org.springframework.web.bind.annotation.GetMapping;
+import org.springframework.web.bind.annotation.PostMapping;
+import org.springframework.web.bind.annotation.RequestBody;
+import org.springframework.web.bind.annotation.RequestMapping;
+import org.springframework.web.bind.annotation.RestController;
+
+/**
+ * @author Rajiv Singla
+ */
+@RestController
+@RequestMapping(TcaModelConstants.TCA_REST_API_PREFIX)
+@Api(value = "Provides endpoints for TCA micro service")
+public class TcaRestController {
+
+ private final TcaProcessingService tcaProcessingService;
+ private final TcaPolicyWrapper tcaPolicyWrapper;
+
+
+ public TcaRestController(final TcaProcessingService tcaProcessingService,
+ final TcaPolicyWrapper tcaPolicyWrapper) {
+ this.tcaProcessingService = tcaProcessingService;
+ this.tcaPolicyWrapper = tcaPolicyWrapper;
+ }
+
+ @GetMapping(value = TcaModelConstants.TCA_POLICY_ENDPOINT, produces = MediaType.APPLICATION_JSON_VALUE)
+ @ApiOperation(value = "Provides current TCA Policy")
+ public ResponseEntity<TcaPolicy> getTcaPolicy() {
+ return getTcaPolicyResponse(tcaPolicyWrapper);
+ }
+
+ @PostMapping(value = TcaModelConstants.TCA_POLICY_ENDPOINT, produces = MediaType.APPLICATION_JSON_VALUE,
+ consumes = MediaType.APPLICATION_JSON_VALUE)
+ @ApiOperation(value = "Sets new value for TCA Policy and returns current Policy")
+ public ResponseEntity<TcaPolicy> setTcaPolicy(@RequestBody final TcaPolicy tcaPolicy) {
+ tcaPolicyWrapper.setTcaPolicy(tcaPolicy, ConfigSource.REST_API);
+ return getTcaPolicyResponse(tcaPolicyWrapper);
+ }
+
+
+ @PostMapping(value = TcaModelConstants.TCA_EXECUTION_ENDPOINT, produces = MediaType.APPLICATION_JSON_VALUE,
+ consumes = MediaType.APPLICATION_JSON_VALUE)
+ @ApiOperation(value = "Applies TCA to provided execution request and generated TCA execution response")
+ public ResponseEntity<List<TcaExecutionResponse>> execute(@RequestBody final TcaExecutionRequest
+ tcaExecutionRequest) {
+ // process tca execution request
+ final List<TcaExecutionContext> executionContexts = tcaProcessingService.getTcaExecutionResults(
+ tcaExecutionRequest.getRequestId(), tcaExecutionRequest.getTransactionId(),
+ tcaExecutionRequest.getTcaPolicy(), TcaUtils.getCefMessagesFromEventListeners
+ (tcaExecutionRequest.getEventListeners()));
+ // create execution response
+ final List<TcaExecutionResponse> tcaExecutionResponses = executionContexts.stream().map(tcaExecutionContext -> {
+ final TcaExecutionResponse tcaExecutionResponse = new TcaExecutionResponse();
+ tcaExecutionResponse.setRequestId(tcaExecutionContext.getRequestId());
+ tcaExecutionResponse.setTransactionId(tcaExecutionContext.getTransactionId());
+ final TcaResultContext tcaResultContext = tcaExecutionContext.getTcaResultContext();
+ tcaExecutionResponse.setViolatedMetricsPerEventName(tcaResultContext.getViolatedMetricsPerEventName());
+ tcaExecutionResponse.setTcaAlert(tcaResultContext.getTcaAlert());
+ return tcaExecutionResponse;
+ }).collect(Collectors.toList());
+
+ return ResponseEntity.ok().body(tcaExecutionResponses);
+ }
+
+
+ private static ResponseEntity<TcaPolicy> getTcaPolicyResponse(final TcaPolicyWrapper tcaPolicyWrapper) {
+ return ResponseEntity.ok()
+ .header(TcaModelConstants.TCA_POLICY_SOURCE_HEADER_KEY, tcaPolicyWrapper.getConfigSource().name())
+ .header(TcaModelConstants.TCA_POLICY_CREATION_HEADER_KEY,
+ tcaPolicyWrapper.getCreationTime().format(DateTimeFormatter.ISO_OFFSET_DATE_TIME))
+ .header(TcaModelConstants.TCA_POLICY_VERSION_HEADER_KEY, tcaPolicyWrapper.getPolicyVersion())
+ .body(tcaPolicyWrapper.getTcaPolicy());
+ }
+
+}
diff --git a/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/domain/TcaPolicyWrapper.java b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/domain/TcaPolicyWrapper.java
new file mode 100644
index 0000000..e85932a
--- /dev/null
+++ b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/domain/TcaPolicyWrapper.java
@@ -0,0 +1,98 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.analytics.tca.web.domain;
+
+import static org.onap.dcae.analytics.tca.model.util.json.TcaModelJsonConversion.TCA_POLICY_JSON_FUNCTION;
+
+import lombok.Getter;
+import lombok.ToString;
+
+import java.time.ZonedDateTime;
+import java.util.concurrent.atomic.AtomicInteger;
+
+import org.onap.dcae.analytics.model.common.ConfigSource;
+import org.onap.dcae.analytics.tca.model.policy.TcaPolicy;
+import org.onap.dcae.analytics.tca.model.policy.TcaPolicyModel;
+import org.onap.dcae.analytics.tca.web.validation.TcaPolicyValidator;
+import org.onap.dcae.analytics.web.exception.AnalyticsParsingException;
+import org.onap.dcae.analytics.web.util.ValidationUtils;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+/**
+ * @author Rajiv Singla
+ */
+@Getter
+@ToString
+public class TcaPolicyWrapper implements TcaPolicyModel {
+
+ private static final long serialVersionUID = 1L;
+
+ private static final Logger logger = LoggerFactory.getLogger(TcaPolicyWrapper.class);
+
+ private final ZonedDateTime creationTime;
+ private ZonedDateTime updateDateTime;
+ private TcaPolicy tcaPolicy;
+ private ConfigSource configSource;
+ private AtomicInteger policyUpdateSequence;
+ private String policyVersion;
+
+ public TcaPolicyWrapper(final String tcaPolicyString, final ConfigSource configSource) {
+ createOrUpdatePolicy(getTcaPolicy(tcaPolicyString), configSource);
+ this.creationTime = ZonedDateTime.now();
+ }
+
+ public void setTcaPolicy(final String tcaPolicyString, final ConfigSource configSource) {
+ createOrUpdatePolicy(getTcaPolicy(tcaPolicyString), configSource);
+ }
+
+ public void setTcaPolicy(final TcaPolicy tcaPolicy, final ConfigSource configSource) {
+ createOrUpdatePolicy(tcaPolicy, configSource);
+ }
+
+ private void createOrUpdatePolicy(final TcaPolicy tcaPolicy, final ConfigSource configSource) {
+ ValidationUtils.validate(tcaPolicy, new TcaPolicyValidator());
+ this.tcaPolicy = tcaPolicy;
+ this.configSource = configSource;
+ this.updateDateTime = ZonedDateTime.now();
+ if (policyUpdateSequence == null) {
+ policyUpdateSequence = new AtomicInteger(0);
+ } else {
+ policyUpdateSequence.getAndUpdate(sequence -> sequence + 1);
+ }
+ this.policyVersion = getPolicyVersion(policyUpdateSequence);
+ final String configSourceName = configSource.name();
+ logger.info("Updated Tca Policy Wrapper with policy: {}, from Source: {}, policy Version: {}",
+ tcaPolicy, configSourceName, policyVersion);
+ }
+
+
+ private TcaPolicy getTcaPolicy(final String tcaPolicyString) {
+ return TCA_POLICY_JSON_FUNCTION.apply(tcaPolicyString).orElseThrow(
+ () -> new AnalyticsParsingException("Unable to parse Tca Policy String: " + tcaPolicyString,
+ new IllegalArgumentException()));
+ }
+
+
+ private static String getPolicyVersion(final AtomicInteger policyUpdateSequence) {
+ return "version-" + policyUpdateSequence.intValue();
+ }
+
+}
diff --git a/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/integration/TcaAlertTransformer.java b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/integration/TcaAlertTransformer.java
new file mode 100644
index 0000000..59acd2d
--- /dev/null
+++ b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/integration/TcaAlertTransformer.java
@@ -0,0 +1,159 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.analytics.tca.web.integration;
+
+import java.util.Date;
+import java.util.List;
+import java.util.Objects;
+import java.util.function.Predicate;
+import java.util.stream.Collectors;
+
+import org.onap.dcae.analytics.model.AnalyticsHttpConstants;
+import org.onap.dcae.analytics.model.TcaModelConstants;
+import org.onap.dcae.analytics.model.ecomplogger.AnalyticsErrorType;
+import org.onap.dcae.analytics.tca.core.service.TcaExecutionContext;
+import org.onap.dcae.analytics.tca.model.facade.TcaAlert;
+import org.onap.dcae.analytics.tca.web.TcaAppProperties;
+import org.onap.dcae.analytics.tca.web.util.TcaUtils;
+import org.onap.dcae.analytics.web.util.AnalyticsHttpUtils;
+import org.onap.dcae.utils.eelf.logger.api.info.ErrorLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.info.ResponseLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.info.TargetServiceLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.log.EELFLogFactory;
+import org.onap.dcae.utils.eelf.logger.api.log.EELFLogger;
+import org.onap.dcae.utils.eelf.logger.model.info.ErrorLogInfoImpl;
+import org.onap.dcae.utils.eelf.logger.model.info.RequestIdLogInfoImpl;
+import org.onap.dcae.utils.eelf.logger.model.info.RequestTimingLogInfoImpl;
+import org.onap.dcae.utils.eelf.logger.model.info.ResponseLogInfoImpl;
+import org.onap.dcae.utils.eelf.logger.model.info.TargetServiceLogInfoImpl;
+import org.onap.dcae.utils.eelf.logger.model.spec.AuditLogSpecImpl;
+import org.onap.dcae.utils.eelf.logger.model.spec.ErrorLogSpecImpl;
+import org.springframework.integration.transformer.AbstractTransformer;
+import org.springframework.messaging.Message;
+
+/**
+ * @author Rajiv Singla
+ */
+public class TcaAlertTransformer extends AbstractTransformer {
+
+ private static final EELFLogger logger = EELFLogFactory.getLogger(TcaAlertTransformer.class);
+
+ private static final Predicate<TcaExecutionContext> ERROR_EXECUTION_CONTEXT_PREDICATE =
+ executionContext -> executionContext.getTcaProcessingContext().getErrorMessage() != null;
+ private static final Predicate<TcaExecutionContext> EARLY_TERMINATION_CONTEXT_PREDICATE =
+ tcaExecutionContext -> tcaExecutionContext.getTcaProcessingContext().getEarlyTerminationMessage() != null;
+ private static final Predicate<TcaExecutionContext> ABATED_EXECUTION_CONTEXT_PREDICATE =
+ tcaExecutionContext -> tcaExecutionContext.getTcaResultContext().getPreviousRequestId() != null;
+
+ private final TcaAppProperties tcaAppProperties;
+
+ public TcaAlertTransformer(final TcaAppProperties tcaAppProperties) {
+ this.tcaAppProperties = tcaAppProperties;
+ }
+
+
+ @Override
+ @SuppressWarnings("unchecked")
+ protected Object doTransform(final Message<?> message) throws Exception {
+
+ final Object messagePayload = message.getPayload();
+
+ final String requestId = AnalyticsHttpUtils.getRequestId(message.getHeaders());
+ final String transactionId = AnalyticsHttpUtils.getTransactionId(message.getHeaders());
+ final Date requestBeginTimestamp = AnalyticsHttpUtils.getTimestampFromHeaders(message.getHeaders(),
+ AnalyticsHttpConstants.REQUEST_BEGIN_TS_HEADER_KEY);
+
+ if (messagePayload instanceof List) {
+ // get execution contexts with alerts
+ final List<TcaExecutionContext> tcaExecutionContexts = (List<TcaExecutionContext>) messagePayload;
+ final List<TcaAlert> tcaAlerts =
+ tcaExecutionContexts.stream()
+ .map(e -> e.getTcaResultContext().getTcaAlert())
+ .filter(Objects::nonNull).collect(Collectors.toList());
+
+ // do ecomp logging
+ if (tcaAppProperties.getTca().getEnableEcompLogging()) {
+ final List<TcaExecutionContext> errorExecutionContexts =
+ tcaExecutionContexts.stream().filter(ERROR_EXECUTION_CONTEXT_PREDICATE)
+ .collect(Collectors.toList());
+ createAuditLog(requestId, transactionId, requestBeginTimestamp, tcaExecutionContexts, tcaAlerts,
+ errorExecutionContexts);
+ createErrorLog(requestId, transactionId, errorExecutionContexts);
+ }
+
+ // if no alerts terminate further processing
+ return tcaAlerts.isEmpty() ? null : tcaAlerts;
+ } else {
+ return null;
+ }
+ }
+
+
+ private static void createErrorLog(final String requestId,
+ final String transactionId,
+ final List<TcaExecutionContext> errorExecutionContexts) {
+ // no error log generated - if there was no error during tca processing
+ if (!errorExecutionContexts.isEmpty()) {
+ for (TcaExecutionContext errorExecutionContext : errorExecutionContexts) {
+ final RequestIdLogInfoImpl requestIdLogInfo =
+ new RequestIdLogInfoImpl(errorExecutionContext.getRequestId());
+ final TargetServiceLogInfo targetServiceLogInfo = new TargetServiceLogInfoImpl(
+ "DCAE-TCA", TcaModelConstants.TCA_SERVICE_NAME, "");
+ final ErrorLogInfo errorLogInfo =
+ new ErrorLogInfoImpl(AnalyticsErrorType.SCHEMA_ERROR.getErrorCode(),
+ AnalyticsErrorType.SCHEMA_ERROR.getErrorDescription());
+ final ErrorLogSpecImpl errorLogSpec = new ErrorLogSpecImpl(requestIdLogInfo,
+ TcaUtils.TCA_SERVICE_LOG_INFO, targetServiceLogInfo, errorLogInfo);
+ logger.errorLog().error("Request Id: {}, Transaction Id: {}, Error Message: {} ",
+ errorLogSpec, requestId, transactionId, errorExecutionContext.getTcaProcessingContext()
+ .getErrorMessage());
+ }
+ }
+ }
+
+ private static void createAuditLog(final String requestId,
+ final String transactionId,
+ final Date requestBeginTimestamp,
+ final List<TcaExecutionContext> tcaExecutionContexts,
+ final List<TcaAlert> tcaAlerts,
+ final List<TcaExecutionContext> errorExecutionContexts) {
+ final List<TcaExecutionContext> earlyTerminationExecutionContexts =
+ tcaExecutionContexts.stream().filter(EARLY_TERMINATION_CONTEXT_PREDICATE)
+ .collect(Collectors.toList());
+ final List<TcaExecutionContext> abatedExecutionContexts =
+ tcaExecutionContexts.stream().filter(ABATED_EXECUTION_CONTEXT_PREDICATE)
+ .collect(Collectors.toList());
+ final RequestIdLogInfoImpl requestIdLogInfo = new RequestIdLogInfoImpl(requestId);
+ final Date endTimestamp = new Date();
+ final RequestTimingLogInfoImpl requestTimingLogInfo = new RequestTimingLogInfoImpl(requestBeginTimestamp,
+ endTimestamp, endTimestamp.getTime() - requestBeginTimestamp.getTime());
+ final ResponseLogInfo responseLogInfo =
+ new ResponseLogInfoImpl(AnalyticsErrorType.SUCCESSFUL.getErrorCode(),
+ AnalyticsErrorType.SUCCESSFUL.getErrorDescription());
+ final AuditLogSpecImpl auditLogSpec = new AuditLogSpecImpl(requestIdLogInfo, TcaUtils.TCA_SERVICE_LOG_INFO,
+ requestTimingLogInfo, responseLogInfo);
+ logger.auditLog().info("Request Id: {}, Transaction Id: {}, " +
+ "Message counts - Received: {}, Errors: {}, Terminated Early: {}, Abated: {}, Alerts: {}",
+ auditLogSpec, requestId, transactionId,
+ Integer.toString(tcaExecutionContexts.size()), Integer.toString(errorExecutionContexts.size()),
+ Integer.toString(earlyTerminationExecutionContexts.size()),
+ Integer.toString(abatedExecutionContexts.size()), Integer.toString(tcaAlerts.size()));
+ }
+}
diff --git a/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/integration/TcaPublisherResponseHandler.java b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/integration/TcaPublisherResponseHandler.java
new file mode 100644
index 0000000..0e81a28
--- /dev/null
+++ b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/integration/TcaPublisherResponseHandler.java
@@ -0,0 +1,101 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.analytics.tca.web.integration;
+
+
+import static org.onap.dcae.analytics.model.AnalyticsHttpConstants.REQUEST_BEGIN_TS_HEADER_KEY;
+import static org.onap.dcae.analytics.model.AnalyticsHttpConstants.REQUEST_END_TS_HEADER_KEY;
+
+import java.util.Date;
+import java.util.Map;
+
+import org.onap.dcae.analytics.model.ecomplogger.AnalyticsErrorType;
+import org.onap.dcae.analytics.tca.web.TcaAppProperties;
+import org.onap.dcae.analytics.tca.web.util.TcaUtils;
+import org.onap.dcae.analytics.web.util.AnalyticsHttpUtils;
+import org.onap.dcae.utils.eelf.logger.api.info.ResponseLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.log.EELFLogFactory;
+import org.onap.dcae.utils.eelf.logger.api.log.EELFLogger;
+import org.onap.dcae.utils.eelf.logger.model.info.RequestIdLogInfoImpl;
+import org.onap.dcae.utils.eelf.logger.model.info.RequestTimingLogInfoImpl;
+import org.onap.dcae.utils.eelf.logger.model.info.ResponseLogInfoImpl;
+import org.onap.dcae.utils.eelf.logger.model.spec.AuditLogSpecImpl;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+import org.springframework.integration.handler.GenericHandler;
+import org.springframework.messaging.MessageHeaders;
+
+/**
+ * TCA Publisher Response Handler is used to do logging of response received from DMaaP MR Publisher. It does not do
+ * any changes to payload or headers
+ *
+ * @author Rajiv Singla
+ */
+public class TcaPublisherResponseHandler implements GenericHandler<String> {
+
+ private static final EELFLogger ECOMP_LOGGER = EELFLogFactory.getLogger(TcaPublisherResponseHandler.class);
+ private static final Logger logger = LoggerFactory.getLogger(TcaPublisherResponseHandler.class);
+
+ private final TcaAppProperties tcaAppProperties;
+
+ public TcaPublisherResponseHandler(final TcaAppProperties tcaAppProperties) {
+ this.tcaAppProperties = tcaAppProperties;
+ }
+
+ @Override
+ public Object handle(final String payload, final Map<String, Object> headers) {
+
+ final MessageHeaders messageHeaders = new MessageHeaders(headers);
+ final String requestId = AnalyticsHttpUtils.getRequestId(messageHeaders);
+ final String transactionId = AnalyticsHttpUtils.getTransactionId(messageHeaders);
+ final Date beginTimestamp = AnalyticsHttpUtils.getTimestampFromHeaders(headers, REQUEST_BEGIN_TS_HEADER_KEY);
+ final Date endTimestamp = AnalyticsHttpUtils.getTimestampFromHeaders(headers, REQUEST_END_TS_HEADER_KEY);
+
+ if (tcaAppProperties.getTca().getEnableEcompLogging()) {
+ createAuditLog(requestId, transactionId, beginTimestamp, endTimestamp, payload);
+ } else {
+ logger.info("Request Id: {}, Transaction Id: {}, Transaction completion Time: {} ms, " +
+ "DMaaP MR Publisher Response: {}", requestId, transactionId,
+ endTimestamp.getTime() - beginTimestamp.getTime(), payload);
+ }
+ return payload;
+
+ }
+
+ private static void createAuditLog(final String requestId,
+ final String transactionId,
+ final Date requestBeginTimestamp,
+ final Date requestEndTimestamp,
+ final String tcaPublisherResponse) {
+ final RequestIdLogInfoImpl requestIdLogInfo = new RequestIdLogInfoImpl(requestId);
+ final long elapsedTime = requestEndTimestamp.getTime() - requestBeginTimestamp.getTime();
+ final RequestTimingLogInfoImpl requestTimingLogInfo = new RequestTimingLogInfoImpl(requestBeginTimestamp,
+ requestEndTimestamp, elapsedTime);
+ final ResponseLogInfo responseLogInfo =
+ new ResponseLogInfoImpl(AnalyticsErrorType.SUCCESSFUL.getErrorCode(),
+ AnalyticsErrorType.SUCCESSFUL.getErrorDescription());
+ final AuditLogSpecImpl auditLogSpec = new AuditLogSpecImpl(requestIdLogInfo, TcaUtils.TCA_SERVICE_LOG_INFO,
+ requestTimingLogInfo, responseLogInfo);
+ ECOMP_LOGGER.auditLog().info("Request Id: {}, Transaction Id: {}, " +
+ "Transaction completion Time: {} ms, DMaaP MR Publisher Response: {}",
+ auditLogSpec, requestId, transactionId, Long.toString(elapsedTime), tcaPublisherResponse);
+ }
+
+}
diff --git a/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/service/TcaProcessingService.java b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/service/TcaProcessingService.java
new file mode 100644
index 0000000..39a985c
--- /dev/null
+++ b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/service/TcaProcessingService.java
@@ -0,0 +1,49 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.analytics.tca.web.service;
+
+import java.util.List;
+
+import org.onap.dcae.analytics.tca.core.service.TcaExecutionContext;
+import org.onap.dcae.analytics.tca.model.policy.TcaPolicy;
+
+/**
+ * Provides TCA functionality
+ *
+ * @author Rajiv Singla
+ */
+public interface TcaProcessingService {
+
+ /**
+ * Apply policy thresholds to CEF messages and generate TCA execution results
+ *
+ * @param requestId request id associated with tca execution request
+ * @param transactionId transaction id associated with the tca execution request
+ * @param tcaPolicy tca policy that needs to be applied to CEF messages
+ * @param cefMessages list of CEF messages that needs to be processed by TCA
+ *
+ * @return results of TCA Processing
+ */
+ List<TcaExecutionContext> getTcaExecutionResults(String requestId, String transactionId,
+ TcaPolicy tcaPolicy,
+ List<String> cefMessages);
+
+
+}
diff --git a/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/service/TcaProcessingServiceImpl.java b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/service/TcaProcessingServiceImpl.java
new file mode 100644
index 0000000..3bb742a
--- /dev/null
+++ b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/service/TcaProcessingServiceImpl.java
@@ -0,0 +1,87 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.analytics.tca.web.service;
+
+import static org.onap.dcae.analytics.web.util.AnalyticsWebUtils.RANDOM_ID_SUPPLIER;
+import static org.onap.dcae.analytics.web.util.AnalyticsWebUtils.REQUEST_ID_SUPPLIER;
+import static org.onap.dcae.analytics.web.util.ValidationUtils.isPresent;
+
+import java.util.List;
+import java.util.stream.Collectors;
+import java.util.stream.IntStream;
+
+import org.onap.dcae.analytics.model.AnalyticsModelConstants;
+import org.onap.dcae.analytics.tca.core.service.GenericTcaExecutionContext;
+import org.onap.dcae.analytics.tca.core.service.GenericTcaProcessingContext;
+import org.onap.dcae.analytics.tca.core.service.GenericTcaResultContext;
+import org.onap.dcae.analytics.tca.core.service.TcaAaiEnrichmentContext;
+import org.onap.dcae.analytics.tca.core.service.TcaAbatementContext;
+import org.onap.dcae.analytics.tca.core.service.TcaExecutionContext;
+import org.onap.dcae.analytics.tca.core.util.function.calculation.TcaCalculator;
+import org.onap.dcae.analytics.tca.model.policy.TcaPolicy;
+import org.onap.dcae.analytics.tca.web.util.TcaUtils;
+
+/**
+ * @author Rajiv Singla
+ */
+public class TcaProcessingServiceImpl implements TcaProcessingService {
+
+ private final TcaAbatementContext tcaAbatementContext;
+ private final TcaAaiEnrichmentContext tcaAaiEnrichmentContext;
+
+ public TcaProcessingServiceImpl(final TcaAbatementContext tcaAbatementContext,
+ final TcaAaiEnrichmentContext tcaAaiEnrichmentContext) {
+ this.tcaAbatementContext = tcaAbatementContext;
+ this.tcaAaiEnrichmentContext = tcaAaiEnrichmentContext;
+ }
+
+
+ @Override
+ public List<TcaExecutionContext> getTcaExecutionResults(final String requestId,
+ final String transactionId,
+ final TcaPolicy tcaPolicy,
+ final List<String> cefMessages) {
+ // create tca policy deep copy as it should be same for current execution
+ final TcaPolicy tcaPolicyDeepCopy = TcaUtils.getTcaPolicyDeepCopy(tcaPolicy);
+ // create new request id if not present
+ final String executionRequestId = isPresent(requestId) ? requestId : REQUEST_ID_SUPPLIER.get();
+ // create transaction id if not present
+ final String executionTransactionId = isPresent(transactionId) ? transactionId : RANDOM_ID_SUPPLIER.get();
+
+ return IntStream.range(0, cefMessages.size())
+ // generate initial Processing contexts
+ .mapToObj(cefMessageIndex -> GenericTcaExecutionContext.builder()
+ .requestId(executionRequestId +
+ AnalyticsModelConstants.ANALYTICS_REQUEST_ID_DELIMITER + cefMessageIndex)
+ .transactionId(executionTransactionId)
+ .messageIndex(cefMessageIndex)
+ .cefMessage(cefMessages.get(cefMessageIndex))
+ .tcaPolicy(tcaPolicyDeepCopy)
+ .tcaProcessingContext(new GenericTcaProcessingContext())
+ .tcaAbatementContext(tcaAbatementContext)
+ .tcaAaiEnrichmentContext(tcaAaiEnrichmentContext)
+ .tcaResultContext(new GenericTcaResultContext())
+ .build())
+ // apply tca calculator
+ .map(new TcaCalculator())
+ // return result
+ .collect(Collectors.toList());
+ }
+}
diff --git a/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/util/TcaUtils.java b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/util/TcaUtils.java
new file mode 100644
index 0000000..6744cee
--- /dev/null
+++ b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/util/TcaUtils.java
@@ -0,0 +1,92 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.analytics.tca.web.util;
+
+import static org.onap.dcae.analytics.tca.model.util.json.TcaModelJsonConversion.TCA_OBJECT_MAPPER;
+
+import com.fasterxml.jackson.core.JsonProcessingException;
+
+import java.util.Collections;
+import java.util.List;
+import java.util.Optional;
+import java.util.stream.Collectors;
+
+import org.onap.dcae.analytics.model.TcaModelConstants;
+import org.onap.dcae.analytics.model.cef.EventListener;
+import org.onap.dcae.analytics.tca.model.policy.TcaPolicy;
+import org.onap.dcae.analytics.web.exception.AnalyticsParsingException;
+import org.onap.dcae.utils.eelf.logger.model.info.ServiceLogInfoImpl;
+
+/**
+ * @author Rajiv Singla
+ */
+public abstract class TcaUtils {
+
+ /**
+ * TCA Service Log Info for ECOMP Logging
+ */
+ public static final ServiceLogInfoImpl TCA_SERVICE_LOG_INFO =
+ new ServiceLogInfoImpl(TcaModelConstants.TCA_SERVICE_NAME, System.getProperty("user.name"), "");
+
+ /**
+ * Creates a deep copy of Tca Policy
+ *
+ * @param tcaPolicy source tca policy object
+ *
+ * @return deep copy of provided tca policy
+ */
+ public static TcaPolicy getTcaPolicyDeepCopy(final TcaPolicy tcaPolicy) {
+ if (tcaPolicy != null) {
+ try {
+ return TCA_OBJECT_MAPPER.treeToValue(TCA_OBJECT_MAPPER.valueToTree(tcaPolicy), TcaPolicy.class);
+ } catch (JsonProcessingException e) {
+ throw new AnalyticsParsingException("Unable to create deep copy of TCA Policy: " + tcaPolicy, e);
+ }
+ } else {
+ final String errorMessage = "Invalid application state. TCA Policy must not be null";
+ throw new AnalyticsParsingException(errorMessage, new IllegalStateException(errorMessage));
+ }
+ }
+
+
+ /**
+ * Converts given event Listeners to list of CEF Message String
+ *
+ * @param eventListeners event listeners object
+ *
+ * @return cef messages as string
+ */
+ public static List<String> getCefMessagesFromEventListeners(final List<EventListener> eventListeners) {
+ if (!Optional.ofNullable(eventListeners).isPresent()) {
+ return Collections.emptyList();
+ }
+ return eventListeners.stream().map(eventListener -> {
+ try {
+ return TCA_OBJECT_MAPPER.writeValueAsString(eventListener);
+ } catch (JsonProcessingException e) {
+ throw new AnalyticsParsingException("Unable to parse EventLister to String: " + eventListener, e);
+ }
+ }).collect(Collectors.toList());
+ }
+
+ private TcaUtils() {
+ // private constructor
+ }
+}
diff --git a/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/util/function/TcaAppPropsToAaiRestClientPrefsFunction.java b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/util/function/TcaAppPropsToAaiRestClientPrefsFunction.java
new file mode 100644
index 0000000..759d5dd
--- /dev/null
+++ b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/util/function/TcaAppPropsToAaiRestClientPrefsFunction.java
@@ -0,0 +1,61 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.analytics.tca.web.util.function;
+
+import java.util.Optional;
+import java.util.function.Function;
+
+import org.onap.dcae.analytics.model.util.function.StringToURLFunction;
+import org.onap.dcae.analytics.tca.web.TcaAppProperties;
+import org.onap.dcae.analytics.tca.web.aai.TcaAaiRestClientPreferences;
+import org.onap.dcae.analytics.web.util.AnalyticsHttpUtils;
+import org.springframework.http.HttpHeaders;
+
+/**
+ * @author Rajiv Singla
+ */
+public class TcaAppPropsToAaiRestClientPrefsFunction implements Function<TcaAppProperties,
+ TcaAaiRestClientPreferences> {
+
+ @Override
+ public TcaAaiRestClientPreferences apply(final TcaAppProperties tcaAppProperties) {
+
+ final TcaAppProperties.Aai aai = tcaAppProperties.getTca().getAai();
+
+ // if aai enrichment is not enabled no need to configure aai Rest client template
+ if (!tcaAppProperties.getTca().getAai().getEnableEnrichment()) {
+ return null;
+ }
+
+ final HttpHeaders aaiHeaders = AnalyticsHttpUtils.createDefaultHttpHeaders();
+ aaiHeaders.add("Real-Time", "true");
+
+ return new TcaAaiRestClientPreferences(
+ tcaAppProperties.getTca().getAai().getUrl(),
+ "aai-rest-client",
+ aaiHeaders,
+ aai.getUsername(),
+ aai.getPassword(),
+ Optional.ofNullable(aai.getProxyUrl()).flatMap(new StringToURLFunction()).orElse(null),
+ aai.getIgnoreSSLValidation(),
+ tcaAppProperties.getTca().getEnableEcompLogging()
+ );
+ }
+}
diff --git a/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/util/function/TcaAppPropsToMrPublisherPrefsFunction.java b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/util/function/TcaAppPropsToMrPublisherPrefsFunction.java
new file mode 100644
index 0000000..fbdbac4
--- /dev/null
+++ b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/util/function/TcaAppPropsToMrPublisherPrefsFunction.java
@@ -0,0 +1,83 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.analytics.tca.web.util.function;
+
+import java.net.URL;
+import java.util.List;
+import java.util.Map;
+import java.util.Optional;
+import java.util.function.Function;
+import java.util.stream.Collectors;
+
+import org.onap.dcae.analytics.model.configbindingservice.BaseConfigBindingServiceProperties.PublisherDetails;
+import org.onap.dcae.analytics.model.configbindingservice.ConfigBindingServiceConstants;
+import org.onap.dcae.analytics.model.util.function.StringToURLFunction;
+import org.onap.dcae.analytics.tca.web.TcaAppProperties;
+import org.onap.dcae.analytics.web.dmaap.MrPublisherPreferences;
+import org.onap.dcae.analytics.web.util.AnalyticsHttpUtils;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+import org.springframework.http.HttpHeaders;
+
+/**
+ * @author Rajiv Singla
+ */
+public class TcaAppPropsToMrPublisherPrefsFunction implements Function<TcaAppProperties, MrPublisherPreferences> {
+
+ private static final Logger logger = LoggerFactory.getLogger(TcaAppPropsToMrPublisherPrefsFunction.class);
+
+ @Override
+ public MrPublisherPreferences apply(final TcaAppProperties tcaAppProperties) {
+
+ final Map<String, PublisherDetails> streamsPublishes = tcaAppProperties.getStreamsPublishes();
+
+ final List<Map.Entry<String, PublisherDetails>> messageRouterPublishes =
+ streamsPublishes.entrySet().stream()
+ .filter(ConfigBindingServiceConstants.MESSAGE_ROUTER_PREDICATE)
+ .collect(Collectors.toList());
+
+ // Use first publisher properties
+ final Map.Entry<String, PublisherDetails> firstPublisherProperties = messageRouterPublishes.get(0);
+
+ if (messageRouterPublishes.size() > 1) {
+ logger.warn("Expected only one DMaaP MR publisher properties but found: {}.", streamsPublishes.size());
+ }
+
+ final String publisherPropertiesKey = firstPublisherProperties.getKey();
+ final PublisherDetails publisherDetails = firstPublisherProperties.getValue();
+
+ logger.info("Creating DMaaP MR Publisher from config properties key: {}, props: {}",
+ publisherPropertiesKey, publisherDetails);
+
+ final String requestURL = publisherDetails.getDmaapInfo().getTopicUrl();
+ final HttpHeaders httpHeaders = AnalyticsHttpUtils.createDefaultHttpHeaders();
+ final String username = publisherDetails.getAafUsername();
+ final String password = publisherDetails.getAafPassword();
+
+ final URL proxyUrl = Optional.ofNullable(publisherDetails.getProxyUrl())
+ .flatMap(new StringToURLFunction()).orElse(null);
+
+ final Boolean ignoreSSLValidation = publisherDetails.getIgnoreSSLValidation();
+
+ return new MrPublisherPreferences(requestURL, publisherPropertiesKey, httpHeaders, username, password,
+ proxyUrl, ignoreSSLValidation, tcaAppProperties.getTca().getEnableEcompLogging());
+
+ }
+}
diff --git a/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/util/function/TcaAppPropsToMrSubscriberPrefsFunction.java b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/util/function/TcaAppPropsToMrSubscriberPrefsFunction.java
new file mode 100644
index 0000000..14e06a1
--- /dev/null
+++ b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/util/function/TcaAppPropsToMrSubscriberPrefsFunction.java
@@ -0,0 +1,115 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.analytics.tca.web.util.function;
+
+import java.net.URL;
+import java.util.List;
+import java.util.Map;
+import java.util.Optional;
+import java.util.function.Function;
+import java.util.stream.Collectors;
+
+import org.onap.dcae.analytics.model.configbindingservice.BaseConfigBindingServiceProperties.AutoAdjusting;
+import org.onap.dcae.analytics.model.configbindingservice.BaseConfigBindingServiceProperties.SubscriberDetails;
+import org.onap.dcae.analytics.model.configbindingservice.ConfigBindingServiceConstants;
+import org.onap.dcae.analytics.model.util.function.StringToURLFunction;
+import org.onap.dcae.analytics.tca.web.TcaAppProperties;
+import org.onap.dcae.analytics.web.dmaap.MrSubscriberPollingPreferences;
+import org.onap.dcae.analytics.web.dmaap.MrSubscriberPreferences;
+import org.onap.dcae.analytics.web.util.AnalyticsHttpUtils;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+import org.springframework.http.HttpHeaders;
+
+/**
+ * @author Rajiv Singla
+ */
+public class TcaAppPropsToMrSubscriberPrefsFunction implements Function<TcaAppProperties, MrSubscriberPreferences> {
+
+ private static final Logger logger = LoggerFactory.getLogger(TcaAppPropsToMrSubscriberPrefsFunction.class);
+
+ @Override
+ public MrSubscriberPreferences apply(final TcaAppProperties tcaAppProperties) {
+
+ final Map<String, SubscriberDetails> streamsSubscribes = tcaAppProperties.getStreamsSubscribes();
+
+ final List<Map.Entry<String, SubscriberDetails>> messageRouterSubscribers =
+ streamsSubscribes.entrySet().stream()
+ .filter(ConfigBindingServiceConstants.MESSAGE_ROUTER_PREDICATE)
+ .collect(Collectors.toList());
+
+ // Use first subscriber properties
+ final Map.Entry<String, SubscriberDetails> firstSubscriberProperties = messageRouterSubscribers.get(0);
+
+ if (messageRouterSubscribers.size() > 1) {
+ logger.warn("Expected one DMaaP MR subscriber properties but found: {}.", messageRouterSubscribers.size());
+ }
+
+ final String subscriberPropertiesKey = firstSubscriberProperties.getKey();
+ final SubscriberDetails subscriberDetails = firstSubscriberProperties.getValue();
+
+ logger.info("Creating DMaaP MR Subscriber from config properties key: {}, props: {}",
+ subscriberPropertiesKey, subscriberDetails);
+
+ final String requestURL = subscriberDetails.getDmaapInfo().getTopicUrl();
+ final HttpHeaders httpHeaders = AnalyticsHttpUtils.createDefaultHttpHeaders();
+ final String username = subscriberDetails.getAafUsername();
+ final String password = subscriberDetails.getAafPassword();
+ final URL proxyUrl = Optional.ofNullable(subscriberDetails.getProxyUrl())
+ .flatMap(new StringToURLFunction()).orElse(null);
+ final Boolean ignoreSSLValidation = subscriberDetails.getIgnoreSSLValidation();
+
+ final String consumerGroup = subscriberDetails.getConsumerGroup();
+ final List<String> consumerIds = subscriberDetails.getConsumerIds();
+ final Integer messageLimit = subscriberDetails.getMessageLimit();
+ final Integer timeout = subscriberDetails.getTimeout();
+
+ final Boolean enableEcompLogging = tcaAppProperties.getTca().getEnableEcompLogging();
+
+ if (subscriberDetails.getPolling() == null) {
+
+ return new MrSubscriberPreferences(requestURL, subscriberPropertiesKey, httpHeaders, username, password,
+ proxyUrl, ignoreSSLValidation, enableEcompLogging, consumerGroup, consumerIds, messageLimit,
+ timeout, null);
+ }
+
+ final Integer fixedRate = subscriberDetails.getPolling().getFixedRate();
+
+ if (fixedRate != null && fixedRate != 0) {
+ logger.info("Fixed Rate polling will be used for DMaaP MR Subscriber: {}", subscriberPropertiesKey);
+ final MrSubscriberPollingPreferences pollingPreferences =
+ new MrSubscriberPollingPreferences(fixedRate, 0, fixedRate, 0);
+ return new MrSubscriberPreferences(requestURL, subscriberPropertiesKey, httpHeaders, username, password,
+ proxyUrl, ignoreSSLValidation, enableEcompLogging, consumerGroup, consumerIds, messageLimit,
+ timeout, pollingPreferences);
+ }
+
+ final AutoAdjusting autoAdjusting = subscriberDetails.getPolling().getAutoAdjusting();
+ logger.info("Selecting Auto Adjusting polling rate for DMaaP MR Subscriber: {}", subscriberPropertiesKey);
+
+ final MrSubscriberPollingPreferences pollingPreferences =
+ new MrSubscriberPollingPreferences(autoAdjusting.getMin(), autoAdjusting.getStepUp(),
+ autoAdjusting.getMax(), autoAdjusting.getStepDown());
+ return new MrSubscriberPreferences(requestURL, subscriberPropertiesKey, httpHeaders, username, password,
+ proxyUrl, ignoreSSLValidation, enableEcompLogging, consumerGroup, consumerIds, messageLimit, timeout,
+ pollingPreferences);
+
+ }
+}
diff --git a/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/validation/ConfigPropertiesAaiValidator.java b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/validation/ConfigPropertiesAaiValidator.java
new file mode 100644
index 0000000..5b04e92
--- /dev/null
+++ b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/validation/ConfigPropertiesAaiValidator.java
@@ -0,0 +1,88 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.analytics.tca.web.validation;
+
+
+import org.onap.dcae.analytics.tca.web.TcaAppProperties;
+import org.onap.dcae.analytics.web.util.ValidationUtils;
+import org.onap.dcae.analytics.web.validation.AnalyticsValidator;
+import org.onap.dcae.analytics.web.validation.GenericValidationResponse;
+import org.springframework.lang.Nullable;
+import org.springframework.validation.Errors;
+
+/**
+ * @author Rajiv Singla
+ */
+public class ConfigPropertiesAaiValidator implements
+ AnalyticsValidator<TcaAppProperties.Aai, GenericValidationResponse> {
+
+ private static final long serialVersionUID = 1L;
+
+ @Override
+ public GenericValidationResponse apply(final TcaAppProperties.Aai aai) {
+
+ final GenericValidationResponse validationResponse = new GenericValidationResponse();
+
+ final String genericVnfPath = aai.getGenericVnfPath();
+ if (ValidationUtils.isEmpty(genericVnfPath)) {
+ validationResponse.addErrorMessage("generic_vnf_path", "AAI Generic vnf path must be present");
+ }
+
+ final String nodeQueryPath = aai.getNodeQueryPath();
+ if (ValidationUtils.isEmpty(nodeQueryPath)) {
+ validationResponse.addErrorMessage("node_query_path", "AAI Node Query Path must be present");
+ }
+
+
+ final String url = aai.getUrl();
+ if (ValidationUtils.isEmpty(url)) {
+ validationResponse.addErrorMessage("url", "AAI url must be present");
+ }
+
+ return validationResponse;
+ }
+
+ @Override
+ public boolean supports(final Class<?> type) {
+ return type == TcaAppProperties.Aai.class;
+ }
+
+ @Override
+ public void validate(@Nullable final Object target, final Errors errors) {
+
+ // if aai is not present - assuming no aai enrichment is required
+ if (target == null) {
+ return;
+ }
+ final TcaAppProperties.Aai aai = (TcaAppProperties.Aai) target;
+
+ // skip validation if aai enrichment is not enabled
+ if (aai.getEnableEnrichment() == null || !aai.getEnableEnrichment()) {
+ return;
+ }
+
+ final GenericValidationResponse validationResponse = apply(aai);
+
+ if (validationResponse.hasErrors()) {
+ errors.rejectValue("aai", validationResponse.getAllErrorMessage());
+ }
+
+ }
+}
diff --git a/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/validation/TcaAppPropertiesValidator.java b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/validation/TcaAppPropertiesValidator.java
new file mode 100644
index 0000000..4204e41
--- /dev/null
+++ b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/validation/TcaAppPropertiesValidator.java
@@ -0,0 +1,186 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.analytics.tca.web.validation;
+
+
+import java.net.MalformedURLException;
+import java.net.URL;
+import java.util.LinkedList;
+import java.util.List;
+import java.util.Map;
+import java.util.stream.Collectors;
+
+import org.onap.dcae.analytics.model.configbindingservice.BaseConfigBindingServiceProperties.PubSubCommonDetails;
+import org.onap.dcae.analytics.model.configbindingservice.BaseConfigBindingServiceProperties.PublisherDetails;
+import org.onap.dcae.analytics.model.configbindingservice.BaseConfigBindingServiceProperties.SubscriberDetails;
+import org.onap.dcae.analytics.model.configbindingservice.ConfigBindingServiceConstants;
+import org.onap.dcae.analytics.tca.web.TcaAppProperties;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+import org.springframework.lang.Nullable;
+import org.springframework.validation.Errors;
+import org.springframework.validation.Validator;
+
+/**
+ * Validator for {@link TcaAppProperties}. This validator is used by spring at start up time to validate
+ * TCA Application properties
+ *
+ * @author Rajiv Singla
+ */
+public class TcaAppPropertiesValidator implements Validator {
+
+ private static final Logger logger = LoggerFactory.getLogger(TcaAppPropertiesValidator.class);
+
+ @Override
+ public boolean supports(final Class<?> type) {
+ return type == TcaAppProperties.class;
+ }
+
+ @Override
+ public void validate(@Nullable final Object props, final Errors errors) {
+
+ if (props == null) {
+ errors.rejectValue(ConfigBindingServiceConstants.CONFIG_BINDING_SERVICE_PROPERTIES_KEY,
+ "TCA App Properties are not present");
+ return;
+ }
+
+ final TcaAppProperties tcaAppProperties = (TcaAppProperties) props;
+
+ logger.info("Validating TCA App Properties: {}", tcaAppProperties);
+
+ final Map<String, PublisherDetails> streamsPublishes = tcaAppProperties.getStreamsPublishes();
+ final Map<String, SubscriberDetails> streamsSubscribes = tcaAppProperties.getStreamsSubscribes();
+
+ // Validate that stream publishes has at least 1 publisher and subscriber
+ if (!validatePubSubArePresent(errors, streamsPublishes, streamsSubscribes)) {
+ return;
+ }
+
+ // Validate that streams publishes and subscribes has at least one message router
+ List<? super PubSubCommonDetails> pubSubMRCommonDetails =
+ validatePubSubHasMRDetails(errors, streamsPublishes, streamsSubscribes);
+ if (pubSubMRCommonDetails.isEmpty()) {
+ return;
+ }
+
+ //Confirm each message router has dmaap info and their url is present and valid
+ validateMRProperties(errors, pubSubMRCommonDetails);
+
+ // validated aai properties
+ validateAAIProperties(errors, tcaAppProperties.getTca().getAai());
+
+ logger.info("Validation of TCA App Properties completed successfully");
+
+ }
+
+
+ private void validateAAIProperties(final Errors errors, final TcaAppProperties.Aai aai) {
+ new ConfigPropertiesAaiValidator().validate(aai, errors);
+ }
+
+ private void validateMRProperties(final Errors errors,
+ final List<? super PubSubCommonDetails> pubSubMRCommonDetails) {
+
+ for (Object pubSubMRCommonDetail : pubSubMRCommonDetails) {
+ final PubSubCommonDetails mrDetails = (PubSubCommonDetails) pubSubMRCommonDetail;
+
+ if (mrDetails.getDmaapInfo() == null || mrDetails.getDmaapInfo().getTopicUrl() == null) {
+ errors.rejectValue("dmaap_info",
+ "dmaap_info url not present for MR configuration properties: " + mrDetails);
+ }
+
+ if (mrDetails.getDmaapInfo() != null && mrDetails.getDmaapInfo().getTopicUrl() != null
+ && !isURLValid(mrDetails.getDmaapInfo().getTopicUrl())) {
+ errors.rejectValue("topic_url",
+ "Invalid MR Topic URL in configuration properties:" + mrDetails);
+
+ }
+
+ if (mrDetails.getProxyUrl() != null && !mrDetails.getProxyUrl().trim().isEmpty()
+ && !isURLValid(mrDetails.getProxyUrl())) {
+ errors.rejectValue("proxy_url",
+ "Invalid Proxy url in configuration properties:" + mrDetails);
+ }
+ }
+
+ }
+
+ private List<? super PubSubCommonDetails> validatePubSubHasMRDetails(
+ final Errors errors,
+ final Map<String, PublisherDetails> streamsPublishes,
+ final Map<String, SubscriberDetails> streamsSubscribes) {
+
+ final List<Map.Entry<String, PublisherDetails>> messageRouterPublishers =
+ streamsPublishes.entrySet().stream()
+ .filter(ConfigBindingServiceConstants.MESSAGE_ROUTER_PREDICATE)
+ .collect(Collectors.toList());
+ if (messageRouterPublishers.isEmpty()) {
+ errors.rejectValue("stream_publishes",
+ "Stream publishes must contain at least 1 message router publisher");
+ }
+
+ final List<Map.Entry<String, SubscriberDetails>> messageRouterSubscribers =
+ streamsSubscribes.entrySet().stream()
+ .filter(ConfigBindingServiceConstants.MESSAGE_ROUTER_PREDICATE)
+ .collect(Collectors.toList());
+ if (messageRouterSubscribers.isEmpty()) {
+ errors.rejectValue("stream_subscribes",
+ "Stream subscriber must contain at least 1 message router subscriber");
+ }
+
+ // create common pub sub MR list
+ final List<? super PubSubCommonDetails> pubSubMRCommonDetails = new LinkedList<>();
+ pubSubMRCommonDetails.addAll(messageRouterPublishers.stream()
+ .map(Map.Entry::getValue).collect(Collectors.toList()));
+ pubSubMRCommonDetails.addAll(messageRouterSubscribers.stream()
+ .map(Map.Entry::getValue).collect(Collectors.toList())
+ );
+
+ return pubSubMRCommonDetails;
+ }
+
+ private boolean validatePubSubArePresent(final Errors errors,
+ final Map<String, PublisherDetails> streamsPublishes,
+ final Map<String, SubscriberDetails>
+ streamsSubscribes) {
+ if (streamsPublishes.isEmpty()) {
+ errors.rejectValue("streams_publishes", "Streams publishes must define at least 1 publisher");
+ return false;
+ }
+ if (streamsSubscribes.isEmpty()) {
+ errors.rejectValue("streams_subscribes", "Streams subscribes must define at least 1 subscriber");
+ return false;
+ }
+
+ return true;
+ }
+
+ private static boolean isURLValid(final String urlString) {
+ try {
+ new URL(urlString);
+ return true;
+ } catch (MalformedURLException ex) {
+ return false;
+ }
+ }
+
+
+}
diff --git a/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/validation/TcaPolicyValidator.java b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/validation/TcaPolicyValidator.java
new file mode 100644
index 0000000..f380699
--- /dev/null
+++ b/dcae-analytics/dcae-analytics-tca-web/src/main/java/org/onap/dcae/analytics/tca/web/validation/TcaPolicyValidator.java
@@ -0,0 +1,133 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.analytics.tca.web.validation;
+
+
+import static org.onap.dcae.analytics.web.util.ValidationUtils.isEmpty;
+
+import java.util.List;
+
+import org.onap.dcae.analytics.model.cef.EventSeverity;
+import org.onap.dcae.analytics.tca.model.policy.ClosedLoopEventStatus;
+import org.onap.dcae.analytics.tca.model.policy.ControlLoopSchemaType;
+import org.onap.dcae.analytics.tca.model.policy.Direction;
+import org.onap.dcae.analytics.tca.model.policy.MetricsPerEventName;
+import org.onap.dcae.analytics.tca.model.policy.TcaPolicy;
+import org.onap.dcae.analytics.tca.model.policy.Threshold;
+import org.onap.dcae.analytics.web.validation.AnalyticsValidator;
+import org.onap.dcae.analytics.web.validation.GenericValidationResponse;
+import org.springframework.lang.Nullable;
+import org.springframework.validation.Errors;
+
+
+/**
+ * TCA Policy Validator validates {@link TcaPolicy}
+ *
+ * @author Rajiv Singla
+ */
+public class TcaPolicyValidator implements AnalyticsValidator<TcaPolicy, GenericValidationResponse> {
+
+ private static final long serialVersionUID = 1L;
+
+ @Override
+ public GenericValidationResponse apply(final TcaPolicy tcaPolicy) {
+
+ final GenericValidationResponse validationResponse = new GenericValidationResponse();
+
+ // validate TCA Policy must domain present
+ final String domain = tcaPolicy.getDomain();
+ if (isEmpty(domain)) {
+ validationResponse.addErrorMessage("domain", "TCA Policy must have only one domain present");
+ }
+
+ // validate TCA Policy must have at lease one metrics per event name
+ final List<MetricsPerEventName> metricsPerEventNames = tcaPolicy.getMetricsPerEventName();
+ if (metricsPerEventNames == null || metricsPerEventNames.isEmpty()) {
+ validationResponse
+ .addErrorMessage("metricsPerEventName", "TCA Policy metricsPerEventName is empty");
+ return validationResponse;
+ }
+
+ // validate Metrics Per Event Name
+ for (MetricsPerEventName metricsPerEventName : metricsPerEventNames) {
+
+ // event name must be present
+ final String eventName = metricsPerEventName.getEventName();
+ if (isEmpty(eventName)) {
+ validationResponse.addErrorMessage("eventName",
+ "TCA Policy eventName is not present for metricsPerEventNames:" + metricsPerEventName);
+ }
+
+ // control Loop Schema type must be present
+ final ControlLoopSchemaType controlLoopSchemaType = metricsPerEventName.getControlLoopSchemaType();
+ if (controlLoopSchemaType == null) {
+ validationResponse.addErrorMessage("controlLoopEventType",
+ "TCA Policy controlLoopSchemaType is not present for metricsPerEventNames:"
+ + metricsPerEventName);
+ }
+
+ // must have at least 1 threshold defined
+ final List<Threshold> thresholds = metricsPerEventName.getThresholds();
+ if (thresholds == null || thresholds.isEmpty()) {
+ validationResponse.addErrorMessage("thresholds",
+ "TCA Policy event Name must have at least one threshold. " +
+ "Event Name causing this validation error:" + metricsPerEventName);
+ } else {
+ // validate each threshold must have non null - fieldPath, thresholdValue, direction and severity
+ for (Threshold eventNameThreshold : thresholds) {
+ final String fieldPath = eventNameThreshold.getFieldPath();
+ final Long thresholdValue = eventNameThreshold.getThresholdValue();
+ final Direction direction = eventNameThreshold.getDirection();
+ final EventSeverity severity = eventNameThreshold.getSeverity();
+ final ClosedLoopEventStatus closedLoopEventStatus = eventNameThreshold.getClosedLoopEventStatus();
+ if (isEmpty(fieldPath) || thresholdValue == null || direction == null || severity == null ||
+ closedLoopEventStatus == null) {
+ validationResponse.addErrorMessage("threshold",
+ "TCA Policy threshold must have fieldPath,thresholdValue,direction, " +
+ "closedLoopEventStatus and severity defined." +
+ "Threshold causing this validation error:" + eventNameThreshold);
+ }
+ }
+ }
+ }
+
+ return validationResponse;
+ }
+
+ @Override
+ public boolean supports(final Class<?> type) {
+ return type == TcaPolicy.class;
+ }
+
+ @Override
+ public void validate(@Nullable final Object target, final Errors errors) {
+
+ if (target == null) {
+ errors.rejectValue("tcaPolicy", "TCA Policy must not be null");
+ return;
+ }
+
+ final TcaPolicy tcaPolicy = (TcaPolicy) target;
+ final GenericValidationResponse validationResponse = apply(tcaPolicy);
+ if (validationResponse.hasErrors()) {
+ errors.rejectValue("tca policy", validationResponse.getAllErrorMessage());
+ }
+ }
+}
diff --git a/dcae-analytics/dcae-analytics-tca-web/src/main/resources/config/application-dev.yaml b/dcae-analytics/dcae-analytics-tca-web/src/main/resources/config/application-dev.yaml
new file mode 100644
index 0000000..e8f2fe8
--- /dev/null
+++ b/dcae-analytics/dcae-analytics-tca-web/src/main/resources/config/application-dev.yaml
@@ -0,0 +1,50 @@
+# DEV PROFILE SETTINGS
+config-binding-service:
+ tca:
+ policy: "{\"domain\":\"measurementsForVfScaling\",\"metricsPerEventName\":[{\"eventName\":\"Mfvs_eNodeB_RANKPI\",\"controlLoopSchemaType\":\"VNF\",\"policyScope\":\"resource=vFirewall;type=configuration\",\"policyName\":\"configuration.dcae.microservice.tca.xml\",\"policyVersion\":\"v0.0.1\",\"thresholds\":[{\"closedLoopControlName\":\"CL-FRWL-LOW-TRAFFIC-SIG-d925ed73-8231-4d02-9545-db4e101f88f8\",\"closedLoopEventStatus\":\"ONSET\",\"version\":\"1.0.2\",\"fieldPath\":\"$.event.measurementsForVfScalingFields.vNicPerformanceArray[*].receivedBroadcastPacketsAccumulated\",\"thresholdValue\":4000,\"direction\":\"LESS_OR_EQUAL\",\"severity\":\"MAJOR\"},{\"closedLoopControlName\":\"CL-FRWL-HIGH-TRAFFIC-SIG-EA36FE84-9342-5E13-A656-EC5F21309A09\",\"closedLoopEventStatus\":\"ONSET\",\"version\":\"1.0.2\",\"fieldPath\":\"$.event.measurementsForVfScalingFields.vNicPerformanceArray[*].receivedBroadcastPacketsAccumulated\",\"thresholdValue\":20000,\"direction\":\"GREATER_OR_EQUAL\",\"severity\":\"CRITICAL\"},{\"closedLoopControlName\":\"CL-FRWL-HIGH-TRAFFIC-SIG-EA36FE84-9342-5E13-A656-EC5F21309A09\",\"closedLoopEventStatus\":\"ABATED\",\"version\":\"1.0.2\",\"fieldPath\":\"$.event.measurementsForVfScalingFields.vNicPerformanceArray[*].receivedBroadcastPacketsAccumulated\",\"thresholdValue\":0,\"direction\":\"EQUAL\",\"severity\":\"CRITICAL\"}]},{\"eventName\":\"vLoadBalancer\",\"controlLoopSchemaType\":\"VNF\",\"policyScope\":\"resource=vLoadBalancer;type=configuration\",\"policyName\":\"configuration.dcae.microservice.tca.xml\",\"policyVersion\":\"v0.0.1\",\"thresholds\":[{\"closedLoopControlName\":\"CL-LBAL-LOW-TRAFFIC-SIG-FB480F95-A453-6F24-B767-FD703241AB1A\",\"closedLoopEventStatus\":\"ONSET\",\"version\":\"1.0.2\",\"fieldPath\":\"$.event.measurementsForVfScalingFields.vNicPerformanceArray[*].receivedBroadcastPacketsAccumulated\",\"thresholdValue\":500,\"direction\":\"LESS_OR_EQUAL\",\"severity\":\"MAJOR\"},{\"closedLoopControlName\":\"CL-LBAL-LOW-TRAFFIC-SIG-0C5920A6-B564-8035-C878-0E814352BC2B\",\"closedLoopEventStatus\":\"ONSET\",\"version\":\"1.0.2\",\"fieldPath\":\"$.event.measurementsForVfScalingFields.vNicPerformanceArray[*].receivedBroadcastPacketsAccumulated\",\"thresholdValue\":5000,\"direction\":\"GREATER_OR_EQUAL\",\"severity\":\"CRITICAL\"}]},{\"eventName\":\"virtualVMEventName\",\"controlLoopSchemaType\":\"VM\",\"policyScope\":\"resource=virtualVM;type=configuration\",\"policyName\":\"configuration.dcae.microservice.tca.xml\",\"policyVersion\":\"v0.0.1\",\"thresholds\":[{\"closedLoopControlName\":\"CL-LBAL-LOW-TRAFFIC-SIG-FB480F95-A453-6F24-B767-FD703241AB1A\",\"closedLoopEventStatus\":\"ONSET\",\"version\":\"1.0.2\",\"fieldPath\":\"$.event.measurementsForVfScalingFields.vNicPerformanceArray[*].receivedBroadcastPacketsAccumulated\",\"thresholdValue\":500,\"direction\":\"LESS_OR_EQUAL\",\"severity\":\"MAJOR\"}]}]}"
+ processing_batch_size: 10000
+ enable_abatement: true
+ enable_ecomp_logging: true
+ aai:
+ enable_enrichment: true
+ url: "http://localhost:8443"
+ username: "DCAE"
+ password: "DCAE"
+ generic_vnf_path: "aai/v11/network/generic-vnfs/generic-vnf"
+ node_query_path: "aai/v11/search/nodes-query"
+ service_calls:
+ aai_broker_handle:
+ - "135.205.226.128:32768"
+ streams_publishes:
+ tca_handle_out:
+ type: "message_router"
+ aaf_username: "USER"
+ aaf_password: "PASSWORD"
+ dmaap_info:
+ client_role: "publisher"
+ client_id: "tca-pub-0"
+ location: "ecomp"
+ topic_url: "http://localhost:8080/events/PubTopic"
+ streams_subscribes:
+ tca_handle_in:
+ type: "message_router"
+ aaf_username: "USER"
+ aaf_password : "PASSWORD"
+ dmaap_info:
+ client_role: "subscriber"
+ client_id: "tca-sub-0"
+ location: "ecomp"
+ topic_url: "http://localhost:8080/events/SubTopic"
+ consumer_group: "cg1"
+ consumer_ids:
+ - "c0"
+ - "c1"
+ message_limit: 50000
+ timeout: -1
+ polling:
+ fixed_rate: 0
+ auto_adjusting:
+ min: 30000
+ step_up: 10000
+ max: 60000
+ step_down: 30000
diff --git a/dcae-analytics/dcae-analytics-tca-web/src/main/resources/config/application-mongo.yaml b/dcae-analytics/dcae-analytics-tca-web/src/main/resources/config/application-mongo.yaml
new file mode 100644
index 0000000..6727518
--- /dev/null
+++ b/dcae-analytics/dcae-analytics-tca-web/src/main/resources/config/application-mongo.yaml
@@ -0,0 +1,4 @@
+spring:
+ data:
+ mongodb:
+ uri: "mongodb://localhost:27017/analytics-tca"
diff --git a/dcae-analytics/dcae-analytics-tca-web/src/main/resources/config/application.yaml b/dcae-analytics/dcae-analytics-tca-web/src/main/resources/config/application.yaml
new file mode 100644
index 0000000..1fdb070
--- /dev/null
+++ b/dcae-analytics/dcae-analytics-tca-web/src/main/resources/config/application.yaml
@@ -0,0 +1,53 @@
+# SPRING SETTINGS
+spring:
+ application:
+ name: "dcae-analytics-tca"
+ main:
+ banner-mode: "off"
+ profiles:
+ active: dev
+ servlet:
+ multipart:
+ # Enable multi part file uploads / download
+ enabled: true
+ # Threshold after which files are written to disk.
+ file-size-threshold: 100KB
+ # Max file size
+ max-file-size: 512MB
+ # Max Request size
+ max-request-size: 600MB
+ output:
+ ansi:
+ enabled: always
+
+# ENDPOINTS
+management:
+ endpoint:
+ health:
+ show-details: always
+ shutdown:
+ enabled: true
+ endpoints:
+ web:
+ exposure:
+ include: '*'
+ info:
+ git:
+ mode: full
+ health:
+ redis:
+ enabled: false
+ mongo:
+ enabled: false
+
+# SERVER
+server:
+ port: 9091
+ compression:
+ # Enable gzip compression of response
+ enabled: true
+ mime-types: application/json,text/plain
+ min-response-size: 4096
+ http2:
+ enabled: true
+
diff --git a/dcae-analytics/dcae-analytics-tca-web/src/main/resources/config/bootstrap.yaml b/dcae-analytics/dcae-analytics-tca-web/src/main/resources/config/bootstrap.yaml
new file mode 100644
index 0000000..b17d963
--- /dev/null
+++ b/dcae-analytics/dcae-analytics-tca-web/src/main/resources/config/bootstrap.yaml
@@ -0,0 +1,4 @@
+spring:
+ cloud:
+ config:
+ enabled: false
diff --git a/dcae-analytics/dcae-analytics-tca-web/src/test/java/org/onap/dcae/analytics/tca/web/BaseTcaWebSpringBootIT.java b/dcae-analytics/dcae-analytics-tca-web/src/test/java/org/onap/dcae/analytics/tca/web/BaseTcaWebSpringBootIT.java
new file mode 100644
index 0000000..e331c95
--- /dev/null
+++ b/dcae-analytics/dcae-analytics-tca-web/src/test/java/org/onap/dcae/analytics/tca/web/BaseTcaWebSpringBootIT.java
@@ -0,0 +1,54 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.analytics.tca.web;
+
+import org.onap.dcae.analytics.model.AnalyticsProfile;
+import org.onap.dcae.analytics.tca.web.config.TcaWebTestConfig;
+import org.onap.dcae.analytics.test.BaseAnalyticsSpringBootIT;
+import org.springframework.test.context.ActiveProfiles;
+import org.springframework.test.context.ContextConfiguration;
+
+/**
+ * @author Rajiv Singla
+ */
+@ActiveProfiles({AnalyticsProfile.DEV_PROFILE_NAME})
+@ContextConfiguration(classes = {TcaWebTestConfig.class})
+public abstract class BaseTcaWebSpringBootIT extends BaseAnalyticsSpringBootIT {
+
+ protected static final String TEST_POLICY_JSON_STRING;
+ protected static final String TEST_CEF_EVENT_LISTENER_STRING;
+ protected static final String TEST_CEF_JSON_MESSAGE_WITH_VIOLATION_STRING;
+ protected static final String TEST_CEF_JSON_MESSAGE_WITH_ABATEMENT_STRING;
+ protected static final String TEST_CEF_JSON_MESSAGE_WITH_INAPPLICABLE_EVENT_NAME;
+ protected static final String TEST_REQUEST_ID = "testRequestId";
+ protected static final String TEST_TRANSACTION_ID = "testTransactionId";
+
+ static {
+
+ TEST_POLICY_JSON_STRING = fromStream(TestFileLocation.TCA_POLICY_JSON);
+ TEST_CEF_EVENT_LISTENER_STRING = fromStream(TestFileLocation.CEF_JSON_MESSAGE);
+ TEST_CEF_JSON_MESSAGE_WITH_VIOLATION_STRING = fromStream(TestFileLocation.CEF_JSON_MESSAGE_WITH_VIOLATION);
+ TEST_CEF_JSON_MESSAGE_WITH_ABATEMENT_STRING = fromStream(TestFileLocation.CEF_JSON_MESSAGE_WITH_ABATEMENT);
+ TEST_CEF_JSON_MESSAGE_WITH_INAPPLICABLE_EVENT_NAME = fromStream(TestFileLocation
+ .CEF_JSON_MESSAGE_WITH_INAPPLICABLE_EVENT_NAME);
+
+ }
+
+}
diff --git a/dcae-analytics/dcae-analytics-tca-web/src/test/java/org/onap/dcae/analytics/tca/web/config/TcaWebTestConfig.java b/dcae-analytics/dcae-analytics-tca-web/src/test/java/org/onap/dcae/analytics/tca/web/config/TcaWebTestConfig.java
new file mode 100644
index 0000000..ccd5d97
--- /dev/null
+++ b/dcae-analytics/dcae-analytics-tca-web/src/test/java/org/onap/dcae/analytics/tca/web/config/TcaWebTestConfig.java
@@ -0,0 +1,34 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.analytics.tca.web.config;
+
+import org.springframework.boot.autoconfigure.EnableAutoConfiguration;
+import org.springframework.context.annotation.Configuration;
+import org.springframework.context.annotation.Import;
+
+/**
+ * @author Rajiv Singla
+ */
+@Configuration
+@EnableAutoConfiguration
+@Import(value = {TcaWebConfig.class})
+public class TcaWebTestConfig {
+
+}
diff --git a/dcae-analytics/dcae-analytics-tca-web/src/test/java/org/onap/dcae/analytics/tca/web/service/TcaProcessingServiceImplTest.java b/dcae-analytics/dcae-analytics-tca-web/src/test/java/org/onap/dcae/analytics/tca/web/service/TcaProcessingServiceImplTest.java
new file mode 100644
index 0000000..5723160
--- /dev/null
+++ b/dcae-analytics/dcae-analytics-tca-web/src/test/java/org/onap/dcae/analytics/tca/web/service/TcaProcessingServiceImplTest.java
@@ -0,0 +1,72 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.analytics.tca.web.service;
+
+import com.fasterxml.jackson.databind.ObjectMapper;
+
+import java.util.Arrays;
+import java.util.List;
+
+import org.junit.jupiter.api.Test;
+import org.onap.dcae.analytics.tca.core.service.TcaExecutionContext;
+import org.onap.dcae.analytics.tca.model.facade.TcaAlert;
+import org.onap.dcae.analytics.tca.web.BaseTcaWebSpringBootIT;
+import org.onap.dcae.analytics.tca.web.domain.TcaPolicyWrapper;
+import org.springframework.beans.factory.annotation.Autowired;
+
+/**
+ * @author Rajiv Singla
+ */
+class TcaProcessingServiceImplTest extends BaseTcaWebSpringBootIT {
+
+ @Autowired
+ private TcaProcessingService tcaProcessingService;
+
+ @Autowired
+ private TcaPolicyWrapper tcaPolicyWrapper;
+
+ @Autowired
+ private ObjectMapper objectMapper;
+
+ @Test
+ void getTcaExecutionResults() throws Exception {
+
+ final List<TcaExecutionContext> tcaExecutionResults =
+ tcaProcessingService.getTcaExecutionResults
+ (TEST_REQUEST_ID, TEST_TRANSACTION_ID, tcaPolicyWrapper.getTcaPolicy(),
+ Arrays.asList(TEST_CEF_EVENT_LISTENER_STRING,
+ TEST_CEF_JSON_MESSAGE_WITH_VIOLATION_STRING,
+ TEST_CEF_JSON_MESSAGE_WITH_ABATEMENT_STRING,
+ TEST_CEF_JSON_MESSAGE_WITH_INAPPLICABLE_EVENT_NAME));
+
+
+ for (TcaExecutionContext tcaExecutionResult : tcaExecutionResults) {
+ final TcaAlert tcaAlert = tcaExecutionResult.getTcaResultContext().getTcaAlert();
+ String tcaAlertString = "";
+ if (tcaAlert != null) {
+ tcaAlertString = objectMapper.writeValueAsString(tcaAlert);
+ }
+ logger.debug("{} -> {}", tcaExecutionResult.getRequestId(), tcaAlertString);
+
+ }
+
+ }
+
+}