summaryrefslogtreecommitdiffstats
path: root/ms/sdclistener/application/src/main
diff options
context:
space:
mode:
authorOleg Mitsura <oleg.mitsura@amdocs.com>2019-04-22 17:47:33 -0400
committerOleg Mitsura <oleg.mitsura@amdocs.com>2019-04-23 11:07:55 -0400
commitd5339481d3c3f24dd5faccb44dccd4addfd58499 (patch)
treedacae59a21608341fcce9cc0060399b15d487f47 /ms/sdclistener/application/src/main
parentf332e6ecd2c0a9f26451f977c941f03ed8ab84dc (diff)
SDC Listner Docker touchup
1.Reworked Dockerization of SDC Listener to follow application/distribution+parent style; 2.Renamed CDS-SDClistener to just SDCListener Issue-ID: CCSDK-1145 Change-Id: I007373d3a48fb8eb7042150bdbb37fc7fec346b3 Signed-off-by: Oleg Mitsura <oleg.mitsura@amdocs.com>
Diffstat (limited to 'ms/sdclistener/application/src/main')
-rw-r--r--ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/SdcListenerApplication.java28
-rw-r--r--ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/SdcListenerConfiguration.java143
-rw-r--r--ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/SdcListenerNotificationCallback.java129
-rw-r--r--ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/client/SdcListenerAuthClientInterceptor.java54
-rw-r--r--ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/client/SdcListenerClient.java95
-rw-r--r--ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/controller/HealthCheck.java35
-rw-r--r--ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/dto/SdcListenerDto.java70
-rw-r--r--ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/exceptions/SdcListenerException.java34
-rw-r--r--ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/handler/BluePrintProcesssorHandler.java64
-rw-r--r--ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/service/ListenerService.java47
-rw-r--r--ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/service/ListenerServiceImpl.java202
-rw-r--r--ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/status/DistributionStatusMessage.java55
-rw-r--r--ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/status/SdcListenerStatus.java82
-rw-r--r--ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/util/BuilderUtil.java33
-rw-r--r--ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/util/FileUtil.java61
-rw-r--r--ms/sdclistener/application/src/main/resources/application.yml27
-rw-r--r--ms/sdclistener/application/src/main/resources/logback.xml33
17 files changed, 1192 insertions, 0 deletions
diff --git a/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/SdcListenerApplication.java b/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/SdcListenerApplication.java
new file mode 100644
index 000000000..253b576d2
--- /dev/null
+++ b/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/SdcListenerApplication.java
@@ -0,0 +1,28 @@
+/*
+ * Copyright © 2019 Bell Canada
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.onap.ccsdk.cds.sdclistener;
+
+import org.springframework.boot.SpringApplication;
+import org.springframework.boot.autoconfigure.SpringBootApplication;
+import org.springframework.boot.context.properties.EnableConfigurationProperties;
+
+@SpringBootApplication
+@EnableConfigurationProperties(SdcListenerConfiguration.class)
+public class SdcListenerApplication {
+ public static void main(String[] args) {
+ SpringApplication.run(SdcListenerApplication.class, args);
+ }
+}
diff --git a/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/SdcListenerConfiguration.java b/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/SdcListenerConfiguration.java
new file mode 100644
index 000000000..06e2a0342
--- /dev/null
+++ b/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/SdcListenerConfiguration.java
@@ -0,0 +1,143 @@
+/*
+ * Copyright © 2019 Bell Canada
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.onap.ccsdk.cds.sdclistener;
+
+import java.util.List;
+import org.onap.sdc.api.consumer.IConfiguration;
+import org.springframework.beans.factory.annotation.Value;
+import org.springframework.boot.context.properties.ConfigurationProperties;
+
+/**
+ * In order to initiate a SDC distribution client we need to supply some pre-configuration values that
+ * distribution client needs.
+ */
+@ConfigurationProperties("listenerservice")
+public class SdcListenerConfiguration implements IConfiguration {
+
+ public static final String TOSCA_CSAR = "TOSCA_CSAR";
+
+ @Value("${listenerservice.config.asdcAddress}")
+ private String asdcAddress;
+
+ @Value("${listenerservice.config.messageBusAddress}")
+ private List<String> messageBusAddress;
+
+ @Value("${listenerservice.config.user}")
+ private String user;
+
+ @Value("${listenerservice.config.password}")
+ private String password;
+
+ @Value("${listenerservice.config.pollingTimeout}")
+ private int pollingTimeout;
+
+ @Value("${listenerservice.config.pollingInterval}")
+ private int pollingInterval;
+
+ @Value("${listenerservice.config.relevantArtifactTypes}")
+ private List<String> relevantArtifactTypes;
+
+ @Value("${listenerservice.config.consumerGroup}")
+ private String consumerGroup;
+
+ @Value("${listenerservice.config.environmentName}")
+ private String envName;
+
+ @Value("${listenerservice.config.consumerId}")
+ private String consumerId;
+
+ @Value("${listenerservice.config.activateServerTLSAuth}")
+ private boolean activateServerTLSAuth;
+
+ @Value("${listenerservice.config.isUseHttpsWithDmaap}")
+ private boolean isUseHttpsWithDmaap;
+
+ @Override
+ public String getAsdcAddress() {
+ return asdcAddress;
+ }
+
+ @Override
+ public List<String> getMsgBusAddress() {
+ return messageBusAddress;
+ }
+
+ @Override
+ public String getUser() {
+ return user;
+ }
+
+ @Override
+ public String getPassword() {
+ return password;
+ }
+
+ @Override
+ public int getPollingInterval() {
+ return pollingInterval;
+ }
+
+ @Override
+ public int getPollingTimeout() {
+ return pollingTimeout;
+ }
+
+ @Override
+ public List<String> getRelevantArtifactTypes() {
+ return relevantArtifactTypes;
+ }
+
+ @Override
+ public String getConsumerGroup() {
+ return consumerGroup;
+ }
+
+ @Override
+ public String getEnvironmentName() {
+ return envName;
+ }
+
+ @Override
+ public String getConsumerID() {
+ return consumerId;
+ }
+
+ @Override
+ public String getKeyStorePath() {
+ return null;
+ }
+
+ @Override
+ public String getKeyStorePassword() {
+ return null;
+ }
+
+ @Override
+ public boolean activateServerTLSAuth() {
+ return activateServerTLSAuth;
+ }
+
+ @Override
+ public boolean isFilterInEmptyResources() {
+ return false;
+ }
+
+ @Override
+ public Boolean isUseHttpsWithDmaap() {
+ return isUseHttpsWithDmaap;
+ }
+}
+
diff --git a/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/SdcListenerNotificationCallback.java b/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/SdcListenerNotificationCallback.java
new file mode 100644
index 000000000..eb339aef7
--- /dev/null
+++ b/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/SdcListenerNotificationCallback.java
@@ -0,0 +1,129 @@
+/*
+ * Copyright © 2019 Bell Canada
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.onap.ccsdk.cds.sdclistener;
+
+import static org.onap.sdc.utils.DistributionActionResultEnum.SUCCESS;
+import java.io.File;
+import java.nio.file.Path;
+import java.nio.file.Paths;
+import java.util.List;
+import java.util.Objects;
+import java.util.Optional;
+import org.onap.ccsdk.cds.sdclistener.dto.SdcListenerDto;
+import org.onap.ccsdk.cds.sdclistener.service.ListenerService;
+import org.onap.ccsdk.cds.sdclistener.status.SdcListenerStatus;
+import org.onap.ccsdk.cds.sdclistener.util.FileUtil;
+import org.onap.sdc.api.IDistributionClient;
+import org.onap.sdc.api.consumer.INotificationCallback;
+import org.onap.sdc.api.notification.IArtifactInfo;
+import org.onap.sdc.api.notification.INotificationData;
+import org.onap.sdc.api.results.IDistributionClientDownloadResult;
+import org.onap.sdc.utils.DistributionStatusEnum;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.beans.factory.annotation.Value;
+import org.springframework.boot.context.properties.ConfigurationProperties;
+import org.springframework.context.annotation.ComponentScan;
+import org.springframework.stereotype.Component;
+
+@ConfigurationProperties("listenerservice")
+@Component
+@ComponentScan("org.onap.ccsdk.cds.cdssdclistener.dto")
+public class SdcListenerNotificationCallback implements INotificationCallback {
+
+ @Autowired
+ private SdcListenerDto sdcListenerDto;
+
+ @Autowired
+ private ListenerService listenerService;
+
+ @Value("${listenerservice.config.archivePath}")
+ private String pathToStoreArchives;
+
+ @Autowired
+ private SdcListenerStatus listenerStatus;
+
+ private static final Logger LOGGER = LoggerFactory.getLogger(SdcListenerNotificationCallback.class);
+
+ @Override
+ public void activateCallback(INotificationData notificationData) {
+ final String distributionId = notificationData.getDistributionID();
+ sdcListenerDto.setDistributionId(distributionId);
+ LOGGER.info("Received service distribution from SDC with the id {}", distributionId);
+ processNotification(notificationData);
+ }
+
+ private void processNotification(INotificationData notificationData) {
+ final IDistributionClient distributionClient = sdcListenerDto.getDistributionClient();
+ notificationData.getServiceArtifacts()
+ .forEach(artifactInfo -> downloadCsarArtifacts(artifactInfo, distributionClient));
+ }
+
+ /**
+ * Download the TOSCA CSAR artifact and process it.
+ *
+ * @param info - Artifact information
+ * @param distributionClient - SDC distribution client
+ */
+ private void downloadCsarArtifacts(IArtifactInfo info, IDistributionClient distributionClient) {
+ final String url = info.getArtifactURL();
+ final String id = info.getArtifactUUID();
+
+ if (Objects.equals(info.getArtifactType(), SdcListenerConfiguration.TOSCA_CSAR)) {
+ LOGGER.info("Trying to download the artifact from : {} and UUID is {} ", url, id);
+
+ // Download the artifact
+ IDistributionClientDownloadResult result = distributionClient.download(info);
+
+ if (!Objects.equals(result.getDistributionActionResult(), SUCCESS)) {
+ String errorMessage = String.format("Failed to download the artifact from : %s due to %s ", url,
+ result.getDistributionActionResult());
+ listenerStatus.sendResponseStatusBackToSDC(sdcListenerDto.getDistributionId(),
+ DistributionStatusEnum.COMPONENT_DONE_ERROR, errorMessage);
+ LOGGER.error(errorMessage);
+ } else {
+ LOGGER.info("Trying to write CSAR artifact to file with URL {} and UUID {}", url, id);
+ processCsarArtifact(result);
+ }
+ }
+ }
+
+ public void processCsarArtifact(IDistributionClientDownloadResult result) {
+ Path cbaArchivePath = Paths.get(pathToStoreArchives, "cba-archive");
+ Path csarArchivePath = Paths.get(pathToStoreArchives, "csar-archive");
+
+ // Extract and store the CSAR archive into local disk.
+ listenerService.extractCsarAndStore(result, csarArchivePath.toString());
+
+ Optional<List<File>> csarFiles = FileUtil.getFilesFromDisk(csarArchivePath);
+
+ if (csarFiles.isPresent()) {
+ //Extract CBA archive from CSAR package and store it into local disk.
+ List<File> files = csarFiles.get();
+
+ if (!files.isEmpty()) {
+ final String archivePath = cbaArchivePath.toString();
+ files.forEach(file -> listenerService.extractBluePrint(file.getAbsolutePath(), archivePath));
+ files.forEach(file -> FileUtil.deleteFile(file, archivePath));
+ } else {
+ LOGGER.error("The CSAR file is not present at this location {}", csarArchivePath);
+ }
+ }
+
+ listenerService.saveBluePrintToCdsDatabase(cbaArchivePath, sdcListenerDto.getManagedChannelForGrpc());
+ }
+}
diff --git a/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/client/SdcListenerAuthClientInterceptor.java b/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/client/SdcListenerAuthClientInterceptor.java
new file mode 100644
index 000000000..6f782d10a
--- /dev/null
+++ b/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/client/SdcListenerAuthClientInterceptor.java
@@ -0,0 +1,54 @@
+/*
+ * Copyright © 2019 Bell Canada
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.onap.ccsdk.cds.sdclistener.client;
+
+import io.grpc.CallOptions;
+import io.grpc.Channel;
+import io.grpc.ClientCall;
+import io.grpc.ClientInterceptor;
+import io.grpc.ForwardingClientCall;
+import io.grpc.Metadata;
+import io.grpc.Metadata.Key;
+import io.grpc.MethodDescriptor;
+import org.springframework.beans.factory.annotation.Value;
+import org.springframework.boot.context.properties.ConfigurationProperties;
+import org.springframework.stereotype.Component;
+
+/**
+ * To provide authentication with GRPC server.
+ */
+@ConfigurationProperties("listenerservice")
+@Component
+public class SdcListenerAuthClientInterceptor implements ClientInterceptor {
+
+ @Value("${listenerservice.config.authHeader}")
+ private String basicAuth;
+
+ @Override
+ public <ReqT, RespT> ClientCall<ReqT, RespT> interceptCall(MethodDescriptor<ReqT, RespT> methodDescriptor,
+ CallOptions callOptions, Channel channel) {
+ Key<String> authHeader = Key.of("Authorization", Metadata.ASCII_STRING_MARSHALLER);
+ return new ForwardingClientCall.SimpleForwardingClientCall<ReqT, RespT>(
+ channel.newCall(methodDescriptor, callOptions)) {
+ @Override
+ public void start(Listener<RespT> responseListener, Metadata headers) {
+ headers.put(authHeader, basicAuth);
+ super.start(responseListener, headers);
+ }
+ };
+ }
+}
diff --git a/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/client/SdcListenerClient.java b/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/client/SdcListenerClient.java
new file mode 100644
index 000000000..973f950bc
--- /dev/null
+++ b/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/client/SdcListenerClient.java
@@ -0,0 +1,95 @@
+/*
+ * Copyright © 2019 Bell Canada
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.onap.ccsdk.cds.sdclistener.client;
+
+import java.util.Optional;
+import org.onap.ccsdk.cds.sdclistener.SdcListenerConfiguration;
+import org.onap.ccsdk.cds.sdclistener.dto.SdcListenerDto;
+import org.onap.ccsdk.cds.sdclistener.SdcListenerNotificationCallback;
+import org.onap.ccsdk.cds.sdclistener.exceptions.SdcListenerException;
+import org.onap.sdc.api.IDistributionClient;
+import org.onap.sdc.api.results.IDistributionClientResult;
+import org.onap.sdc.impl.DistributionClientFactory;
+import org.onap.sdc.utils.DistributionActionResultEnum;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.boot.context.event.ApplicationReadyEvent;
+import org.springframework.context.annotation.ComponentScan;
+import org.springframework.context.event.EventListener;
+import org.springframework.stereotype.Component;
+
+@Component
+@ComponentScan("org.onap.ccsdk.cds.cdssdclistener.dto")
+public class SdcListenerClient {
+
+ private static Logger LOG = LoggerFactory.getLogger(SdcListenerClient.class);
+
+ @Autowired
+ private SdcListenerConfiguration configuration;
+
+ @Autowired
+ private SdcListenerNotificationCallback notification;
+
+ @Autowired
+ private SdcListenerDto listenerDto;
+
+ private IDistributionClient distributionClient;
+
+ /**
+ * This method initializes the SDC Distribution client.
+ */
+ @EventListener(ApplicationReadyEvent.class)
+ public void initSdcClient() throws SdcListenerException {
+ LOG.info("Initialize the SDC distribution client");
+
+ distributionClient = Optional.of(DistributionClientFactory.createDistributionClient())
+ .orElseThrow(() -> new SdcListenerException("Could not able to create SDC Distribution client"));
+
+ listenerDto.setManagedChannelForGrpc();
+
+ listenerDto.setDistributionClient(distributionClient);
+
+ IDistributionClientResult result = distributionClient.init(configuration, notification);
+ startSdcClientBasedOnTheResult(result);
+ }
+
+ private void startSdcClientBasedOnTheResult(IDistributionClientResult result) throws SdcListenerException {
+ if (!result.getDistributionActionResult().equals(DistributionActionResultEnum.SUCCESS)) {
+ throw new SdcListenerException(
+ "SDC distribution client init failed with reason:" + result.getDistributionMessageResult());
+ }
+
+ LOG.info("Initialization of the SDC distribution client is complete");
+
+ // Start the client.
+ result = this.distributionClient.start();
+
+ if (!result.getDistributionActionResult().equals(DistributionActionResultEnum.SUCCESS)) {
+ throw new SdcListenerException(
+ "Startup of the SDC distribution client failed with reason: " + result.getDistributionMessageResult());
+ }
+ }
+
+ private void closeSdcDistributionclient() throws SdcListenerException {
+ LOG.info("Closing SDC distribution client");
+ IDistributionClientResult status = this.distributionClient.stop();
+ if (status.getDistributionActionResult().equals(DistributionActionResultEnum.SUCCESS)) {
+ throw new SdcListenerException(
+ "Failed to close the SDC distribution client due to : " + status.getDistributionMessageResult());
+ }
+ }
+}
diff --git a/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/controller/HealthCheck.java b/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/controller/HealthCheck.java
new file mode 100644
index 000000000..a9e51ac12
--- /dev/null
+++ b/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/controller/HealthCheck.java
@@ -0,0 +1,35 @@
+/*
+ * Copyright © 2019 Bell Canada
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.onap.ccsdk.cds.sdclistener.controller;
+
+import org.springframework.http.MediaType;
+import org.springframework.web.bind.annotation.RequestMapping;
+import org.springframework.web.bind.annotation.RequestMethod;
+import org.springframework.web.bind.annotation.ResponseBody;
+import org.springframework.web.bind.annotation.RestController;
+import reactor.core.publisher.Mono;
+
+@RestController
+@RequestMapping("/api/v1/sdclistener")
+public class HealthCheck {
+
+ @RequestMapping(path = "/healthcheck", method = RequestMethod.GET, produces = MediaType.APPLICATION_JSON_VALUE)
+ public @ResponseBody
+ Mono<String> ping() {
+ return Mono.just("{\"status\":\"UP\"}");
+ }
+}
diff --git a/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/dto/SdcListenerDto.java b/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/dto/SdcListenerDto.java
new file mode 100644
index 000000000..c7c3d4829
--- /dev/null
+++ b/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/dto/SdcListenerDto.java
@@ -0,0 +1,70 @@
+/*
+ * Copyright © 2019 Bell Canada
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.onap.ccsdk.cds.sdclistener.dto;
+
+import io.grpc.ManagedChannel;
+import io.grpc.ManagedChannelBuilder;
+import org.onap.ccsdk.cds.sdclistener.client.SdcListenerAuthClientInterceptor;
+import org.onap.sdc.api.IDistributionClient;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.beans.factory.annotation.Value;
+import org.springframework.boot.context.properties.ConfigurationProperties;
+import org.springframework.stereotype.Component;
+
+@Component
+@ConfigurationProperties("listenerservice")
+public class SdcListenerDto {
+
+ @Value("${listenerservice.config.grpcAddress}")
+ private String grpcAddress;
+
+ @Value("${listenerservice.config.grpcPort}")
+ private int grpcPort;
+
+ @Autowired
+ private SdcListenerAuthClientInterceptor sdcListenerAuthClientInterceptor;
+
+ private IDistributionClient distributionClient;
+ private ManagedChannel managedChannel;
+ private String distributionId;
+
+ public IDistributionClient getDistributionClient() {
+ return distributionClient;
+ }
+
+ public void setDistributionClient(IDistributionClient distributionClient) {
+ this.distributionClient = distributionClient;
+ }
+
+ public void setDistributionId(String id) {
+ this.distributionId = id;
+ }
+
+ public String getDistributionId() {
+ return distributionId;
+ }
+
+ public void setManagedChannelForGrpc() {
+ managedChannel = ManagedChannelBuilder.forAddress(grpcAddress, grpcPort)
+ .usePlaintext()
+ .intercept(sdcListenerAuthClientInterceptor)
+ .build();
+ }
+
+ public ManagedChannel getManagedChannelForGrpc() {
+ return managedChannel;
+ }
+}
diff --git a/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/exceptions/SdcListenerException.java b/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/exceptions/SdcListenerException.java
new file mode 100644
index 000000000..23f669f1e
--- /dev/null
+++ b/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/exceptions/SdcListenerException.java
@@ -0,0 +1,34 @@
+/*
+ * Copyright © 2019 Bell Canada
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.onap.ccsdk.cds.sdclistener.exceptions;
+
+public class SdcListenerException extends Exception {
+
+ /**
+ * @param message The message to dump
+ */
+ public SdcListenerException(final String message) {
+ super(message);
+ }
+
+ /**
+ * @param message The message to dump
+ * @param cause The Throwable cause object
+ */
+ public SdcListenerException(final String message, final Throwable cause) {
+ super(message, cause);
+ }
+}
diff --git a/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/handler/BluePrintProcesssorHandler.java b/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/handler/BluePrintProcesssorHandler.java
new file mode 100644
index 000000000..96b2ff081
--- /dev/null
+++ b/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/handler/BluePrintProcesssorHandler.java
@@ -0,0 +1,64 @@
+/*
+ * Copyright © 2019 Bell Canada
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.onap.ccsdk.cds.sdclistener.handler;
+
+import io.grpc.ManagedChannel;
+import org.onap.ccsdk.cds.controllerblueprints.common.api.Status;
+import org.onap.ccsdk.cds.controllerblueprints.management.api.BluePrintManagementOutput;
+import org.onap.ccsdk.cds.controllerblueprints.management.api.BluePrintManagementServiceGrpc;
+import org.onap.ccsdk.cds.controllerblueprints.management.api.BluePrintManagementServiceGrpc.BluePrintManagementServiceBlockingStub;
+import org.onap.ccsdk.cds.controllerblueprints.management.api.BluePrintUploadInput;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+import org.springframework.boot.context.properties.ConfigurationProperties;
+import org.springframework.stereotype.Component;
+
+@ConfigurationProperties("listenerservice")
+@Component
+public class BluePrintProcesssorHandler implements AutoCloseable {
+
+ private static final Logger LOGGER = LoggerFactory.getLogger(BluePrintProcesssorHandler.class);
+
+ private ManagedChannel channel;
+
+ /**
+ * Sending CBA archive to CDS backend to store into its Database.
+ *
+ * @param request BluePrintManagementInput object holds CBA archive, its version and blueprints.
+ * @param managedChannel - ManagedChannel object helps to access the server or application end point.
+ * @return A response object
+ */
+ public Status sendRequest(BluePrintUploadInput request, ManagedChannel managedChannel) {
+ LOGGER.info("Sending request to blueprint processor");
+
+ this.channel = managedChannel;
+
+ final BluePrintManagementServiceBlockingStub syncStub = BluePrintManagementServiceGrpc.newBlockingStub(channel);
+
+ // Send the request to CDS backend.
+ final BluePrintManagementOutput response = syncStub.uploadBlueprint(request);
+
+ return response.getStatus();
+ }
+
+ @Override
+ public void close() {
+ if (channel != null) {
+ channel.shutdown();
+ }
+ LOGGER.info("Stopping GRPC connection to CDS backend");
+ }
+}
diff --git a/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/service/ListenerService.java b/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/service/ListenerService.java
new file mode 100644
index 000000000..446c3e621
--- /dev/null
+++ b/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/service/ListenerService.java
@@ -0,0 +1,47 @@
+/*
+ * Copyright © 2019 Bell Canada
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.onap.ccsdk.cds.sdclistener.service;
+
+import io.grpc.ManagedChannel;
+import java.nio.file.Path;
+import org.onap.sdc.api.results.IDistributionClientDownloadResult;
+
+public interface ListenerService {
+
+ /**
+ * Get the controller blueprint archive from CSAR package.
+ *
+ * @param csarArchivePath The path where CSAR archive is stored.
+ * @param cbaArchivePath The destination path where CBA will be stored.
+ */
+ void extractBluePrint(String csarArchivePath, String cbaArchivePath);
+
+ /**
+ * Store the Zip file into CDS database.
+ *
+ * @param path path where zip file exists.
+ * @param managedChannel To access the blueprint processor application end point
+ */
+ void saveBluePrintToCdsDatabase(Path path, ManagedChannel managedChannel);
+
+ /**
+ * Extract and store the csar package to local disk.
+ *
+ * @param result - IDistributionClientDownloadResult contains payload.
+ * @param csarArchivePath The destination path where CSAR will be stored.
+ */
+ void extractCsarAndStore(IDistributionClientDownloadResult result, String csarArchivePath);
+}
diff --git a/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/service/ListenerServiceImpl.java b/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/service/ListenerServiceImpl.java
new file mode 100644
index 000000000..9a6ae8779
--- /dev/null
+++ b/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/service/ListenerServiceImpl.java
@@ -0,0 +1,202 @@
+/*
+ * Copyright © 2017-2019 AT&T, Bell Canada
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.onap.ccsdk.cds.sdclistener.service;
+
+import static java.nio.file.Files.walk;
+import static org.onap.sdc.utils.DistributionStatusEnum.COMPONENT_DONE_ERROR;
+import static org.onap.sdc.utils.DistributionStatusEnum.COMPONENT_DONE_OK;
+import com.google.protobuf.ByteString;
+import io.grpc.ManagedChannel;
+import java.io.File;
+import java.io.FileOutputStream;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.OutputStream;
+import java.nio.file.Files;
+import java.nio.file.Path;
+import java.nio.file.Paths;
+import java.util.Enumeration;
+import java.util.List;
+import java.util.Optional;
+import java.util.regex.Pattern;
+import java.util.zip.ZipEntry;
+import java.util.zip.ZipFile;
+import org.apache.commons.io.FileUtils;
+import org.apache.tomcat.util.http.fileupload.IOUtils;
+import org.onap.ccsdk.cds.sdclistener.client.SdcListenerAuthClientInterceptor;
+import org.onap.ccsdk.cds.sdclistener.dto.SdcListenerDto;
+import org.onap.ccsdk.cds.sdclistener.handler.BluePrintProcesssorHandler;
+import org.onap.ccsdk.cds.sdclistener.status.SdcListenerStatus;
+import org.onap.ccsdk.cds.sdclistener.util.FileUtil;
+import org.onap.ccsdk.cds.controllerblueprints.common.api.Status;
+import org.onap.ccsdk.cds.controllerblueprints.management.api.BluePrintUploadInput;
+import org.onap.ccsdk.cds.controllerblueprints.management.api.FileChunk;
+import org.onap.sdc.api.results.IDistributionClientDownloadResult;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.beans.factory.annotation.Value;
+import org.springframework.boot.context.properties.ConfigurationProperties;
+import org.springframework.stereotype.Component;
+
+@Component
+@ConfigurationProperties("listenerservice")
+public class ListenerServiceImpl implements ListenerService {
+
+ @Autowired
+ private BluePrintProcesssorHandler bluePrintProcesssorHandler;
+
+ @Autowired
+ private SdcListenerAuthClientInterceptor sdcListenerAuthClientInterceptor;
+
+ @Autowired
+ private SdcListenerStatus listenerStatus;
+
+ @Autowired
+ private SdcListenerDto sdcListenerDto;
+
+ @Value("${listenerservice.config.grpcAddress}")
+ private String grpcAddress;
+
+ @Value("${listenerservice.config.grpcPort}")
+ private int grpcPort;
+
+ private static final String CBA_ZIP_PATH = "Artifacts/Resources/[a-zA-Z0-9-_]+/Deployment/CONTROLLER_BLUEPRINT_ARCHIVE/[a-zA-Z0-9-_]+[.]zip";
+ private static final int SUCCESS_CODE = 200;
+ private static final Logger LOGGER = LoggerFactory.getLogger(ListenerServiceImpl.class);
+
+ @Override
+ public void extractBluePrint(String csarArchivePath, String cbaArchivePath) {
+ Path cbaStorageDir = getStorageDirectory(cbaArchivePath);
+ try (ZipFile zipFile = new ZipFile(csarArchivePath)) {
+ Enumeration<? extends ZipEntry> entries = zipFile.entries();
+ while (entries.hasMoreElements()) {
+ ZipEntry entry = entries.nextElement();
+ String fileName = entry.getName();
+ if (Pattern.matches(CBA_ZIP_PATH, fileName)) {
+ final String cbaArchiveName = Paths.get(fileName).getFileName().toString();
+ LOGGER.info("Storing the CBA archive {}", cbaArchiveName);
+ storeBluePrint(zipFile, cbaArchiveName, cbaStorageDir, entry);
+ }
+ }
+
+ } catch (Exception e) {
+ LOGGER.error("Failed to extract blueprint {}", e);
+ }
+ }
+
+ private void storeBluePrint(ZipFile zipFile, String fileName, Path cbaArchivePath, ZipEntry entry) {
+ Path targetLocation = cbaArchivePath.resolve(fileName);
+ LOGGER.info("The target location for zip file is {}", targetLocation);
+ File targetZipFile = new File(targetLocation.toString());
+
+ try {
+ targetZipFile.createNewFile();
+ } catch (IOException e) {
+ LOGGER.error("Could not able to create file {}", targetZipFile, e);
+ }
+
+ try (InputStream inputStream = zipFile.getInputStream(entry); OutputStream out = new FileOutputStream(
+ targetZipFile)) {
+ IOUtils.copy(inputStream, out);
+ LOGGER.info("Successfully store the CBA archive {} at this location", targetZipFile);
+ } catch (Exception e) {
+ LOGGER.error("Failed to put zip file into target location {}, {}", targetLocation, e);
+ }
+ }
+
+ @Override
+ public void saveBluePrintToCdsDatabase(Path cbaArchivePath, ManagedChannel channel) {
+ Optional<List<File>> zipFiles = FileUtil.getFilesFromDisk(cbaArchivePath);
+ zipFiles.ifPresent(files -> prepareRequestForCdsBackend(files, channel, cbaArchivePath.toString()));
+ }
+
+ @Override
+ public void extractCsarAndStore(IDistributionClientDownloadResult result, String csarArchivePath) {
+
+ // Create CSAR storage directory
+ Path csarStorageDir = getStorageDirectory(csarArchivePath);
+ byte[] payload = result.getArtifactPayload();
+ String csarFileName = result.getArtifactFilename();
+ Path targetLocation = csarStorageDir.resolve(csarFileName);
+
+ LOGGER.info("The target location for the CSAR file is {}", targetLocation);
+
+ File targetCsarFile = new File(targetLocation.toString());
+
+ try (FileOutputStream outFile = new FileOutputStream(targetCsarFile)) {
+ outFile.write(payload, 0, payload.length);
+ } catch (Exception e) {
+ LOGGER.error("Failed to put CSAR file into target location {}, {}", targetLocation, e);
+ }
+ }
+
+ private Path getStorageDirectory(String path) {
+ Path fileStorageLocation = Paths.get(path).toAbsolutePath().normalize();
+
+ if (!fileStorageLocation.toFile().exists()) {
+ try {
+ return Files.createDirectories(fileStorageLocation);
+ } catch (IOException e) {
+ LOGGER.error("Fail to create directory {}, {}", e, fileStorageLocation);
+ }
+ }
+ return fileStorageLocation;
+ }
+
+ private void prepareRequestForCdsBackend(List<File> files, ManagedChannel managedChannel, String path) {
+ final String distributionId = sdcListenerDto.getDistributionId();
+
+ files.forEach(zipFile -> {
+ try {
+ final BluePrintUploadInput request = generateBluePrintUploadInputBuilder(zipFile);
+
+ // Send request to CDS Backend.
+ final Status responseStatus = bluePrintProcesssorHandler.sendRequest(request, managedChannel);
+
+ if (responseStatus.getCode() != SUCCESS_CODE) {
+ final String errorMessage = String.format("Failed to store the CBA archive into CDS DB due to %s",
+ responseStatus.getErrorMessage());
+ listenerStatus.sendResponseStatusBackToSDC(distributionId,
+ COMPONENT_DONE_ERROR, errorMessage);
+ LOGGER.error(errorMessage);
+
+ } else {
+ LOGGER.info(responseStatus.getMessage());
+ listenerStatus.sendResponseStatusBackToSDC(distributionId,
+ COMPONENT_DONE_OK, null);
+ }
+
+ } catch (Exception e) {
+ final String errorMessage = String.format("Failure due to %s", e.getMessage());
+ listenerStatus.sendResponseStatusBackToSDC(distributionId, COMPONENT_DONE_ERROR, errorMessage);
+ LOGGER.error("Failure due to {}", e);
+ } finally {
+ FileUtil.deleteFile(zipFile, path);
+ }
+ });
+ }
+
+ private BluePrintUploadInput generateBluePrintUploadInputBuilder(File file) throws IOException {
+ byte[] bytes = FileUtils.readFileToByteArray(file);
+ FileChunk fileChunk = FileChunk.newBuilder().setChunk(ByteString.copyFrom(bytes)).build();
+
+ return BluePrintUploadInput.newBuilder()
+ .setFileChunk(fileChunk)
+ .build();
+ }
+}
diff --git a/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/status/DistributionStatusMessage.java b/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/status/DistributionStatusMessage.java
new file mode 100644
index 000000000..60463762b
--- /dev/null
+++ b/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/status/DistributionStatusMessage.java
@@ -0,0 +1,55 @@
+/*
+ * Copyright © 2019 Bell Canada
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.onap.ccsdk.cds.sdclistener.status;
+
+import org.onap.sdc.api.consumer.IFinalDistrStatusMessage;
+import org.onap.sdc.utils.DistributionStatusEnum;
+
+public class DistributionStatusMessage implements IFinalDistrStatusMessage {
+
+ public String componentName;
+
+ public String consumerID;
+
+ public String distributionID;
+
+ public DistributionStatusEnum status;
+
+ @Override
+ public String getDistributionID() {
+ return distributionID;
+ }
+
+ @Override
+ public long getTimestamp() {
+ return 0;
+ }
+
+ @Override
+ public DistributionStatusEnum getStatus() {
+ return status;
+ }
+
+ @Override
+ public String getConsumerID() {
+ return consumerID;
+ }
+
+ @Override
+ public String getComponentName() {
+ return componentName;
+ }
+}
diff --git a/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/status/SdcListenerStatus.java b/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/status/SdcListenerStatus.java
new file mode 100644
index 000000000..ff64c0d0c
--- /dev/null
+++ b/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/status/SdcListenerStatus.java
@@ -0,0 +1,82 @@
+/*
+ * Copyright © 2019 Bell Canada
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.onap.ccsdk.cds.sdclistener.status;
+
+import static org.onap.sdc.utils.DistributionActionResultEnum.SUCCESS;
+import java.util.Objects;
+import org.onap.ccsdk.cds.sdclistener.dto.SdcListenerDto;
+import org.onap.ccsdk.cds.sdclistener.util.BuilderUtil;
+import org.onap.sdc.api.IDistributionClient;
+import org.onap.sdc.api.consumer.IFinalDistrStatusMessage;
+import org.onap.sdc.api.results.IDistributionClientResult;
+import org.onap.sdc.utils.DistributionStatusEnum;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.beans.factory.annotation.Value;
+import org.springframework.boot.context.properties.ConfigurationProperties;
+import org.springframework.context.annotation.ComponentScan;
+import org.springframework.stereotype.Component;
+
+@Component
+@ConfigurationProperties("listenerservice")
+@ComponentScan("org.onap.ccsdk.cds.cdssdclistener.dto")
+public class SdcListenerStatus {
+
+ private static final Logger LOGGER = LoggerFactory.getLogger(SdcListenerStatus.class);
+ private static final String COMPONENT_NAME = "cds";
+
+ @Value("${listenerservice.config.consumerId}")
+ private String consumerId;
+
+ @Autowired
+ private SdcListenerDto sdcListenerDto;
+
+ /**
+ * Send the response back to SDC.
+ *
+ * @param distributionID SDC Distribution ID
+ * @param status Distribution status
+ * @param errorReason Reason of failure
+ */
+ public void sendResponseStatusBackToSDC(String distributionID, DistributionStatusEnum status, String errorReason) {
+
+ final IDistributionClient distributionClient = sdcListenerDto.getDistributionClient();
+
+ IFinalDistrStatusMessage finalDistribution = new BuilderUtil<>(new DistributionStatusMessage())
+ .build(builder -> {
+ builder.distributionID = distributionID;
+ builder.status = status;
+ builder.consumerID = consumerId;
+ builder.componentName = COMPONENT_NAME;
+ }).create();
+
+ if (errorReason == null) {
+ checkResponseStatusFromSdc(distributionClient.sendFinalDistrStatus(finalDistribution));
+ } else {
+ checkResponseStatusFromSdc(distributionClient.sendFinalDistrStatus(finalDistribution, errorReason));
+ }
+ }
+
+ private void checkResponseStatusFromSdc(IDistributionClientResult result) {
+ if (!Objects.equals(result.getDistributionActionResult(), SUCCESS)) {
+ LOGGER.error("SDC failed to receive the response from cds-sdc listener due to {}",
+ result.getDistributionMessageResult());
+ } else {
+ LOGGER.info("SDC successfully received the response");
+ }
+ }
+}
diff --git a/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/util/BuilderUtil.java b/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/util/BuilderUtil.java
new file mode 100644
index 000000000..1f546d107
--- /dev/null
+++ b/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/util/BuilderUtil.java
@@ -0,0 +1,33 @@
+/*
+ * Copyright (C) 2019 Bell Canada. All rights reserved.
+ *
+ * NOTICE: All the intellectual and technical concepts contained herein are
+ * proprietary to Bell Canada and are protected by trade secret or copyright law.
+ * Unauthorized copying of this file, via any medium is strictly prohibited.
+ */
+package org.onap.ccsdk.cds.sdclistener.util;
+
+import java.util.function.Consumer;
+
+/**
+ * A generic builder for constructing an object.
+ *
+ * @param <T> - Any object
+ */
+public class BuilderUtil<T> {
+
+ private final T object;
+
+ public BuilderUtil(T instance) {
+ this.object = instance;
+ }
+
+ public BuilderUtil<T> build(Consumer<T> consumer) {
+ consumer.accept(object);
+ return this;
+ }
+
+ public T create() {
+ return object;
+ }
+}
diff --git a/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/util/FileUtil.java b/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/util/FileUtil.java
new file mode 100644
index 000000000..967e854d7
--- /dev/null
+++ b/ms/sdclistener/application/src/main/java/org/onap/ccsdk/cds/sdclistener/util/FileUtil.java
@@ -0,0 +1,61 @@
+/*
+ * Copyright (C) 2019 Bell Canada. All rights reserved.
+ *
+ * NOTICE: All the intellectual and technical concepts contained herein are
+ * proprietary to Bell Canada and are protected by trade secret or copyright law.
+ * Unauthorized copying of this file, via any medium is strictly prohibited.
+ */
+
+package org.onap.ccsdk.cds.sdclistener.util;
+
+import static java.nio.file.Files.walk;
+import java.io.File;
+import java.io.IOException;
+import java.nio.file.Files;
+import java.nio.file.Path;
+import java.util.List;
+import java.util.Optional;
+import java.util.stream.Collectors;
+import java.util.stream.Stream;
+import org.apache.commons.io.FileUtils;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+public final class FileUtil {
+ private static final Logger LOGGER = LoggerFactory.getLogger(FileUtils.class);
+
+ private FileUtil() {
+
+ }
+
+ /**
+ * Delete the file.
+ *
+ * @param file - Given file
+ * @param path - Given path
+ */
+ public static void deleteFile(File file, String path) {
+ boolean value = file.delete();
+ if (!value) {
+ LOGGER.error("Failed to delete the file {} at the location {}", file, path);
+ }
+ }
+
+ /**
+ * Extract files from the given path
+ *
+ * @param path where files reside.
+ * @return list of files.
+ */
+ public static Optional<List<File>> getFilesFromDisk(Path path) {
+ try (Stream<Path> fileTree = walk(path)) {
+ // Get the list of files from the path
+ return Optional.of(fileTree.filter(Files::isRegularFile)
+ .map(Path::toFile)
+ .collect(Collectors.toList()));
+ } catch (IOException e) {
+ LOGGER.error("Failed to find the file due to", e);
+ }
+ return Optional.empty();
+ }
+}
diff --git a/ms/sdclistener/application/src/main/resources/application.yml b/ms/sdclistener/application/src/main/resources/application.yml
new file mode 100644
index 000000000..b3f8443eb
--- /dev/null
+++ b/ms/sdclistener/application/src/main/resources/application.yml
@@ -0,0 +1,27 @@
+listenerservice:
+ config:
+ asdcAddress: ${asdcAddress:localhost:8443}
+ messageBusAddress: ${messageBusAddress:localhost}
+ user: ${sdcusername:vid}
+ password: ${password:Kp8bJ4SXszM0WXlhak3eHlcse2gAw84vaoGGmJvUy2U}
+ pollingInterval: ${pollingInterval:15}
+ pollingTimeout: ${pollingTimeout:60}
+ relevantArtifactTypes: ${relevantArtifactTypes:TOSCA_CSAR}
+ consumerGroup: ${consumerGroup:cds-id-local}
+ environmentName: ${environmentName:AUTO}
+ consumerId: ${consumerId:cds-id-local}
+ keyStorePassword: ${keyStorePassword}
+ keyStorePath: ${keyStorePath}
+ activateServerTLSAuth : ${activateServerTLSAuth:false}
+ isUseHttpsWithDmaap: ${isUseHttpsWithDmaap:false}
+ archivePath: ${archivePath:/opt/app/onap/cds-sdc-listener/}
+ grpcAddress: ${grpcAddress:localhost}
+ grpcPort: ${grpcPort:9111}
+ authHeader: ${authHeader:Basic Y2NzZGthcHBzOmNjc2RrYXBwcw==}
+#port needed by Liveness probe
+server:
+ port: ${healthcheckPort:9000}
+#set spring.main.web-environment=false if you want to NOT to open a port for healthcheck.
+spring:
+ main:
+ web-environment: ${sprintWebListenerEnabled:true}
diff --git a/ms/sdclistener/application/src/main/resources/logback.xml b/ms/sdclistener/application/src/main/resources/logback.xml
new file mode 100644
index 000000000..b26cbcbe4
--- /dev/null
+++ b/ms/sdclistener/application/src/main/resources/logback.xml
@@ -0,0 +1,33 @@
+<!--
+Copyright (C) 2019 Bell Canada
+
+Unless otherwise specified, all software contained herein is licensed
+under the Apache License, Version 2.0 (the License);
+you may not use this software except in compliance with the License.
+You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing, software
+distributed under the License is distributed on an "AS IS" BASIS,
+WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+See the License for the specific language governing permissions and
+limitations under the License.
+-->
+
+<configuration>
+ <appender name="STDOUT" class="ch.qos.logback.core.ConsoleAppender">
+ <encoder>
+ <pattern>%d{HH:mm:ss.SSS} [%thread] %-5level %logger{50} - %msg%n</pattern>
+ </encoder>
+ </appender>
+
+ <root level="info">
+ <appender-ref ref="STDOUT"/>
+ </root>
+
+ <logger name="org.springframework" level="info"/>
+ <logger name="org.springframework.web" level="info"/>
+ <logger name="org.onap.ccsdk.cds" level="info"/>
+
+</configuration>