diff options
author | adheli.tavares <adheli.tavares@est.tech> | 2022-05-12 13:58:48 +0100 |
---|---|---|
committer | adheli.tavares <adheli.tavares@est.tech> | 2022-05-12 15:25:14 +0100 |
commit | 2a58e25bee3bf029e1696a443f23495e119c5855 (patch) | |
tree | cdb4ff9f1113251f0ea3a5ad7c667cfd0452c665 /plugins/reception-plugins/src | |
parent | 1537b4665f9050bb2efe6f4f0aba2fb38d52a0ef (diff) |
Security issues from sonar cloud fixes
Issue-ID: POLICY-4168
Change-Id: Iedac6c95be452be81e8c73055193b4707735ef56
Signed-off-by: adheli.tavares <adheli.tavares@est.tech>
Diffstat (limited to 'plugins/reception-plugins/src')
10 files changed, 209 insertions, 221 deletions
diff --git a/plugins/reception-plugins/src/main/java/org/onap/policy/distribution/reception/decoding/policy/file/AutomationCompositionDecoderFileInCsar.java b/plugins/reception-plugins/src/main/java/org/onap/policy/distribution/reception/decoding/policy/file/AutomationCompositionDecoderFileInCsar.java index fb7a8d99..7087d7ca 100644 --- a/plugins/reception-plugins/src/main/java/org/onap/policy/distribution/reception/decoding/policy/file/AutomationCompositionDecoderFileInCsar.java +++ b/plugins/reception-plugins/src/main/java/org/onap/policy/distribution/reception/decoding/policy/file/AutomationCompositionDecoderFileInCsar.java @@ -20,14 +20,10 @@ package org.onap.policy.distribution.reception.decoding.policy.file; -import java.io.IOException; import java.util.ArrayList; import java.util.Collection; -import java.util.List; -import java.util.Optional; -import java.util.stream.Collectors; -import java.util.zip.ZipEntry; -import java.util.zip.ZipFile; +import java.util.HashMap; +import java.util.Map; import org.onap.policy.common.parameters.ParameterService; import org.onap.policy.common.utils.coder.CoderException; import org.onap.policy.distribution.model.Csar; @@ -72,53 +68,28 @@ public class AutomationCompositionDecoderFileInCsar implements PolicyDecoder<Csa public Collection<ToscaEntity> decode(final Csar csar) throws PolicyDecodingException { final Collection<ToscaEntity> automationCompositionList = new ArrayList<>(); - try (var zipFile = new ZipFile(csar.getCsarFilePath())) { - final List<? extends ZipEntry> entries = zipFile.stream() - .filter(entry -> entry.getName().contains(decoderParameters.getAutomationCompositionType())) - .collect(Collectors.toList()); - - for (ZipEntry entry : entries) { - ReceptionUtil.validateZipEntry(entry.getName(), csar.getCsarFilePath(), entry.getSize()); - final ToscaServiceTemplate automationComposition = ReceptionUtil.decodeFile(zipFile, entry); + try { + Map<String, ToscaServiceTemplate> templates = new HashMap<>(); + ReceptionUtil.unzip(csar.getCsarFilePath(), templates, + decoderParameters.getAutomationCompositionType(), NODE_TYPES, DATA_TYPES); - if (null != automationComposition.getToscaTopologyTemplate()) { - validateTypes(zipFile, NODE_TYPES) - .ifPresent(node -> automationComposition.setNodeTypes(node.getNodeTypes())); + var node = templates.get(NODE_TYPES); + var data = templates.get(DATA_TYPES); - validateTypes(zipFile, DATA_TYPES) - .ifPresent(data -> automationComposition.setDataTypes(data.getDataTypes())); + templates.forEach((entry, t) -> { + if (entry.contains(decoderParameters.getAutomationCompositionType()) + && t.getToscaTopologyTemplate() != null) { + t.setNodeTypes(node != null ? node.getNodeTypes() : null); + t.setDataTypes(data != null ? data.getDataTypes() : null); - automationCompositionList.add(automationComposition); + automationCompositionList.add(t); } - } - } catch (final IOException | CoderException exp) { + }); + + } catch (final CoderException exp) { throw new PolicyDecodingException("Failed decoding the acm", exp); } return automationCompositionList; } - - /** - * Decode and validate if node or data type is available withing ACM csar file. - * - * @param zipFile full csar file - * @return tosca template with parsed node/data type - * @throws CoderException if file can't be parsed - */ - private Optional<ToscaServiceTemplate> validateTypes(final ZipFile zipFile, String type) - throws CoderException { - - try { - ToscaServiceTemplate template = null; - final Optional<? extends ZipEntry> file = zipFile.stream() - .filter(entry -> entry.getName().contains(type)).findFirst(); - - if (file.isPresent()) { - template = ReceptionUtil.decodeFile(zipFile, file.get()); - } - return Optional.ofNullable(template); - } catch (final IOException | CoderException exp) { - throw new CoderException("Couldn't decode " + type + " type", exp); - } - } } diff --git a/plugins/reception-plugins/src/main/java/org/onap/policy/distribution/reception/decoding/policy/file/PolicyDecoderFileInCsarToPolicy.java b/plugins/reception-plugins/src/main/java/org/onap/policy/distribution/reception/decoding/policy/file/PolicyDecoderFileInCsarToPolicy.java index 8d0a554a..86f857a8 100644 --- a/plugins/reception-plugins/src/main/java/org/onap/policy/distribution/reception/decoding/policy/file/PolicyDecoderFileInCsarToPolicy.java +++ b/plugins/reception-plugins/src/main/java/org/onap/policy/distribution/reception/decoding/policy/file/PolicyDecoderFileInCsarToPolicy.java @@ -23,13 +23,10 @@ package org.onap.policy.distribution.reception.decoding.policy.file; -import java.io.IOException; import java.util.ArrayList; import java.util.Collection; -import java.util.List; -import java.util.stream.Collectors; -import java.util.zip.ZipEntry; -import java.util.zip.ZipFile; +import java.util.HashMap; +import java.util.Map; import org.onap.policy.common.parameters.ParameterService; import org.onap.policy.common.utils.coder.CoderException; import org.onap.policy.distribution.model.Csar; @@ -70,19 +67,15 @@ public class PolicyDecoderFileInCsarToPolicy implements PolicyDecoder<Csar, Tosc */ @Override public Collection<ToscaEntity> decode(final Csar csar) throws PolicyDecodingException { - final Collection<ToscaEntity> policyList = new ArrayList<>(); + final Collection<ToscaEntity> policyList; - try (var zipFile = new ZipFile(csar.getCsarFilePath())) { - final List<? extends ZipEntry> entries = zipFile.stream() - .filter(entry -> entry.getName().contains(decoderParameters.getPolicyTypeFileName()) - || entry.getName().contains(decoderParameters.getPolicyFileName())).collect(Collectors.toList()); + try { + Map<String, ToscaServiceTemplate> templates = new HashMap<>(); + ReceptionUtil.unzip(csar.getCsarFilePath(), templates, decoderParameters.getPolicyFileName(), + decoderParameters.getPolicyTypeFileName()); + policyList = new ArrayList<>(templates.values()); - for (ZipEntry entry : entries) { - ReceptionUtil.validateZipEntry(entry.getName(), csar.getCsarFilePath(), entry.getSize()); - final ToscaServiceTemplate policy = ReceptionUtil.decodeFile(zipFile, entry); - policyList.add(policy); - } - } catch (final IOException | CoderException exp) { + } catch (final CoderException exp) { throw new PolicyDecodingException("Failed decoding the policy", exp); } diff --git a/plugins/reception-plugins/src/main/java/org/onap/policy/distribution/reception/handling/sdc/SdcReceptionHandler.java b/plugins/reception-plugins/src/main/java/org/onap/policy/distribution/reception/handling/sdc/SdcReceptionHandler.java index 5fd76bea..ff915613 100644 --- a/plugins/reception-plugins/src/main/java/org/onap/policy/distribution/reception/handling/sdc/SdcReceptionHandler.java +++ b/plugins/reception-plugins/src/main/java/org/onap/policy/distribution/reception/handling/sdc/SdcReceptionHandler.java @@ -1,7 +1,7 @@ /*- * ============LICENSE_START======================================================= * Copyright (C) 2018 Ericsson. All rights reserved. - * Copyright (C) 2019 Nordix Foundation. + * Copyright (C) 2019, 2022 Nordix Foundation. * Modifications Copyright (C) 2020-2021 AT&T Intellectual Property. All rights reserved. * Modifications Copyright (C) 2021 Bell Canada. All rights reserved. * ================================================================================ @@ -28,6 +28,7 @@ import java.io.FileOutputStream; import java.io.IOException; import java.nio.file.Files; import java.nio.file.Path; +import java.util.Optional; import java.util.concurrent.atomic.AtomicInteger; import org.onap.policy.common.parameters.ParameterService; import org.onap.policy.distribution.model.Csar; @@ -62,7 +63,7 @@ public class SdcReceptionHandler extends AbstractReceptionHandler implements INo private SdcReceptionHandlerStatus sdcReceptionHandlerStatus = SdcReceptionHandlerStatus.STOPPED; private IDistributionClient distributionClient; private SdcConfiguration sdcConfig; - private AtomicInteger nbOfNotificationsOngoing = new AtomicInteger(); + private final AtomicInteger nbOfNotificationsOngoing = new AtomicInteger(); private int retryDelay; private SdcClientHandler sdcClientHandler; @@ -73,7 +74,7 @@ public class SdcReceptionHandler extends AbstractReceptionHandler implements INo @Override protected void initializeReception(final String parameterGroupName) { final SdcReceptionHandlerConfigurationParameterGroup handlerParameters = - ParameterService.get(parameterGroupName); + ParameterService.get(parameterGroupName); retryDelay = handlerParameters.getRetryDelay() < 30 ? 30 : handlerParameters.getRetryDelay(); sdcConfig = new SdcConfiguration(handlerParameters); distributionClient = createSdcDistributionClient(); @@ -101,7 +102,7 @@ public class SdcReceptionHandler extends AbstractReceptionHandler implements INo * * @param newStatus the new status */ - private final synchronized void changeSdcReceptionHandlerStatus(final SdcReceptionHandlerStatus newStatus) { + private synchronized void changeSdcReceptionHandlerStatus(final SdcReceptionHandlerStatus newStatus) { switch (newStatus) { case INIT: case STOPPED: @@ -130,7 +131,6 @@ public class SdcReceptionHandler extends AbstractReceptionHandler implements INo /** * Method to initialize the SDC client. - * */ protected void initializeSdcClient() { @@ -142,7 +142,7 @@ public class SdcReceptionHandler extends AbstractReceptionHandler implements INo final IDistributionClientResult clientResult = distributionClient.init(sdcConfig, this); if (!clientResult.getDistributionActionResult().equals(DistributionActionResultEnum.SUCCESS)) { LOGGER.error("SDC client initialization failed with reason: {}. Initialization will be retried after {} {}", - clientResult.getDistributionMessageResult(), retryDelay, SECONDS); + clientResult.getDistributionMessageResult(), retryDelay, SECONDS); return; } LOGGER.debug("SDC Client is initialized successfully"); @@ -151,7 +151,6 @@ public class SdcReceptionHandler extends AbstractReceptionHandler implements INo /** * Method to start the SDC client. - * */ protected void startSdcClient() { @@ -163,7 +162,7 @@ public class SdcReceptionHandler extends AbstractReceptionHandler implements INo final IDistributionClientResult clientResult = distributionClient.start(); if (!clientResult.getDistributionActionResult().equals(DistributionActionResultEnum.SUCCESS)) { LOGGER.error("SDC client start failed with reason: {}. Start will be retried after {} {}", - clientResult.getDistributionMessageResult(), retryDelay, SECONDS); + clientResult.getDistributionMessageResult(), retryDelay, SECONDS); return; } LOGGER.debug("SDC Client is started successfully"); @@ -173,14 +172,13 @@ public class SdcReceptionHandler extends AbstractReceptionHandler implements INo /** * Method to stop the SDC client. - * */ protected void stopSdcClient() { LOGGER.debug("Going to stop the SDC Client..."); final IDistributionClientResult clientResult = distributionClient.stop(); if (!clientResult.getDistributionActionResult().equals(DistributionActionResultEnum.SUCCESS)) { LOGGER.error("SDC client stop failed with reason: {}. Stop will be retried after {} {}", - clientResult.getDistributionMessageResult(), retryDelay, SECONDS); + clientResult.getDistributionMessageResult(), retryDelay, SECONDS); return; } LOGGER.debug("SDC Client is stopped successfully"); @@ -199,29 +197,29 @@ public class SdcReceptionHandler extends AbstractReceptionHandler implements INo for (final IArtifactInfo artifact : notificationData.getServiceArtifacts()) { try { final IDistributionClientDownloadResult resultArtifact = - downloadTheArtifact(artifact, notificationData); + downloadTheArtifact(artifact, notificationData); final var filePath = writeArtifactToFile(artifact, resultArtifact); final var csarObject = new Csar(filePath.toString()); inputReceived(csarObject); sendDistributionStatus(DistributionStatusType.DEPLOY, artifact.getArtifactURL(), - notificationData.getDistributionID(), DistributionStatusEnum.DEPLOY_OK, null); + notificationData.getDistributionID(), DistributionStatusEnum.DEPLOY_OK, null); deleteArtifactFile(filePath); } catch (final ArtifactDownloadException | PolicyDecodingException exp) { LOGGER.error("Failed to process csar service artifacts ", exp); artifactsProcessedSuccessfully = false; sendDistributionStatus(DistributionStatusType.DEPLOY, artifact.getArtifactURL(), - notificationData.getDistributionID(), DistributionStatusEnum.DEPLOY_ERROR, - "Failed to deploy the artifact due to: " + exp.getMessage()); + notificationData.getDistributionID(), DistributionStatusEnum.DEPLOY_ERROR, + "Failed to deploy the artifact due to: " + exp.getMessage()); } } if (artifactsProcessedSuccessfully) { DistributionStatisticsManager.updateDistributionSuccessCount(); sendComponentDoneStatus(notificationData.getDistributionID(), DistributionStatusEnum.COMPONENT_DONE_OK, - null); + null); } else { DistributionStatisticsManager.updateDistributionFailureCount(); sendComponentDoneStatus(notificationData.getDistributionID(), DistributionStatusEnum.COMPONENT_DONE_ERROR, - "Failed to process the artifact"); + "Failed to process the artifact"); } } @@ -233,38 +231,42 @@ public class SdcReceptionHandler extends AbstractReceptionHandler implements INo * @throws ArtifactDownloadException if download fails */ private IDistributionClientDownloadResult downloadTheArtifact(final IArtifactInfo artifact, - final INotificationData notificationData) throws ArtifactDownloadException { + final INotificationData notificationData) + throws ArtifactDownloadException { DistributionStatisticsManager.updateTotalDownloadCount(); final IDistributionClientDownloadResult downloadResult = distributionClient.download(artifact); if (!downloadResult.getDistributionActionResult().equals(DistributionActionResultEnum.SUCCESS)) { DistributionStatisticsManager.updateDownloadFailureCount(); final String message = "Failed to download artifact with name: " + artifact.getArtifactName() + " due to: " - + downloadResult.getDistributionMessageResult(); + + downloadResult.getDistributionMessageResult(); LOGGER.error(message); sendDistributionStatus(DistributionStatusType.DOWNLOAD, artifact.getArtifactURL(), - notificationData.getDistributionID(), DistributionStatusEnum.DOWNLOAD_ERROR, message); + notificationData.getDistributionID(), DistributionStatusEnum.DOWNLOAD_ERROR, message); throw new ArtifactDownloadException(message); } DistributionStatisticsManager.updateDownloadSuccessCount(); sendDistributionStatus(DistributionStatusType.DOWNLOAD, artifact.getArtifactURL(), - notificationData.getDistributionID(), DistributionStatusEnum.DOWNLOAD_OK, null); + notificationData.getDistributionID(), DistributionStatusEnum.DOWNLOAD_OK, null); return downloadResult; } /** * Method to write the downloaded distribution artifact to local file system. * - * @param artifact the notification artifact + * @param artifact the notification artifact * @param resultArtifact the download result artifact * @return the local path of written file * @throws ArtifactDownloadException if error occurs while writing the artifact */ private Path writeArtifactToFile(final IArtifactInfo artifact, - final IDistributionClientDownloadResult resultArtifact) throws ArtifactDownloadException { + final IDistributionClientDownloadResult resultArtifact) + throws ArtifactDownloadException { try { final byte[] payloadBytes = resultArtifact.getArtifactPayload(); - final var tempArtifactFile = File.createTempFile(artifact.getArtifactName(), ".csar"); + + final var tempArtifactFile = Optional.ofNullable(safelyCreateFile(artifact.getArtifactName())) + .orElseThrow(() -> new ArtifactDownloadException("Failed to create temporary file.")); try (var fileOutputStream = new FileOutputStream(tempArtifactFile)) { fileOutputStream.write(payloadBytes, 0, payloadBytes.length); return tempArtifactFile.toPath(); @@ -290,19 +292,20 @@ public class SdcReceptionHandler extends AbstractReceptionHandler implements INo /** * Sends the distribution status to SDC using the input values. * - * @param statusType the status type - * @param artifactUrl the artifact url + * @param statusType the status type + * @param artifactUrl the artifact url * @param distributionId the distribution id - * @param status the status - * @param errorReason the error reason + * @param status the status + * @param errorReason the error reason */ private void sendDistributionStatus(final DistributionStatusType statusType, final String artifactUrl, - final String distributionId, final DistributionStatusEnum status, final String errorReason) { + final String distributionId, final DistributionStatusEnum status, + final String errorReason) { IDistributionClientResult clientResult; final IDistributionStatusMessage message = DistributionStatusMessage.builder().artifactUrl(artifactUrl) - .consumerId(sdcConfig.getConsumerID()).distributionId(distributionId).distributionStatus(status) - .timestamp(System.currentTimeMillis()).build(); + .consumerId(sdcConfig.getConsumerID()).distributionId(distributionId).distributionStatus(status) + .timestamp(System.currentTimeMillis()).build(); if (DistributionStatusType.DOWNLOAD.equals(statusType)) { if (errorReason != null) { clientResult = distributionClient.sendDownloadStatus(message, errorReason); @@ -318,8 +321,8 @@ public class SdcReceptionHandler extends AbstractReceptionHandler implements INo } final var loggerMessage = new StringBuilder(); loggerMessage.append("distribution status to SDC with values - ").append("DistributionId") - .append(distributionId).append(" Artifact: ").append(artifactUrl).append(" StatusType: ") - .append(statusType.name()).append(" Status: ").append(status.name()); + .append(distributionId).append(" Artifact: ").append(artifactUrl).append(" StatusType: ") + .append(statusType.name()).append(" Status: ").append(status.name()); if (errorReason != null) { loggerMessage.append(" ErrorReason: ").append(errorReason); } @@ -336,15 +339,15 @@ public class SdcReceptionHandler extends AbstractReceptionHandler implements INo * Sends the component done status to SDC using the input values. * * @param distributionId the distribution Id - * @param status the distribution status - * @param errorReason the error reason + * @param status the distribution status + * @param errorReason the error reason */ private void sendComponentDoneStatus(final String distributionId, final DistributionStatusEnum status, - final String errorReason) { + final String errorReason) { IDistributionClientResult clientResult; final IComponentDoneStatusMessage message = ComponentDoneStatusMessage.builder() - .consumerId(sdcConfig.getConsumerID()).distributionId(distributionId).distributionStatus(status) - .timestamp(System.currentTimeMillis()).build(); + .consumerId(sdcConfig.getConsumerID()).distributionId(distributionId).distributionStatus(status) + .timestamp(System.currentTimeMillis()).build(); if (errorReason == null) { clientResult = distributionClient.sendComponentDoneStatus(message); } else { @@ -353,7 +356,7 @@ public class SdcReceptionHandler extends AbstractReceptionHandler implements INo final var loggerMessage = new StringBuilder(); loggerMessage.append("component done status to SDC with values - ").append("DistributionId") - .append(distributionId).append(" Status: ").append(status.name()); + .append(distributionId).append(" Status: ").append(status.name()); if (errorReason != null) { loggerMessage.append(" ErrorReason: ").append(errorReason); } @@ -374,4 +377,13 @@ public class SdcReceptionHandler extends AbstractReceptionHandler implements INo sdcReceptionHandlerStatus = newStatus; } } + + private File safelyCreateFile(String prefix) throws IOException { + File file = Files.createTempFile(prefix, ".csar").toFile(); + if (file.setReadable(true, false) + && file.setWritable(true, true)) { + return file; + } + return null; + } } diff --git a/plugins/reception-plugins/src/main/java/org/onap/policy/distribution/reception/util/ReceptionUtil.java b/plugins/reception-plugins/src/main/java/org/onap/policy/distribution/reception/util/ReceptionUtil.java index c26286da..6b0c762a 100644 --- a/plugins/reception-plugins/src/main/java/org/onap/policy/distribution/reception/util/ReceptionUtil.java +++ b/plugins/reception-plugins/src/main/java/org/onap/policy/distribution/reception/util/ReceptionUtil.java @@ -20,9 +20,13 @@ package org.onap.policy.distribution.reception.util; +import java.io.BufferedInputStream; import java.io.IOException; +import java.io.InputStream; import java.io.InvalidClassException; import java.nio.file.Path; +import java.util.Enumeration; +import java.util.Map; import java.util.zip.ZipEntry; import java.util.zip.ZipFile; import org.onap.policy.common.utils.coder.CoderException; @@ -44,25 +48,20 @@ public class ReceptionUtil { private static final StandardCoder coder = new StandardCoder(); private static final StandardYamlCoder yamlCoder = new StandardYamlCoder(); - private static final long MAX_FILE_SIZE = 512L * 1024; + private static final long THRESHOLD_SIZE = 512L * 1024; + private static final int THRESHOLD_ENTRIES = 10000; + private static final double THRESHOLD_RATIO = 20; /** * Method to ensure validation of entries in the Zipfile. Attempts to solve path * injection java security issues. * * @param entryName name of the ZipEntry to check - * @param csarPath Absolute path to the csar the ZipEntry is in - * @param entrySize size of the ZipEntry + * @param csarPath Absolute path to the csar the ZipEntry is in * @throws PolicyDecodingException if the file size is too large */ - public static void validateZipEntry(String entryName, String csarPath, long entrySize) - throws PolicyDecodingException { - // - // Check file size - // - if (entrySize > MAX_FILE_SIZE) { - throw new PolicyDecodingException("Zip entry for " + entryName + " is too large " + entrySize); - } + public static void validateZipEntry(String entryName, String csarPath) + throws PolicyDecodingException { // // Now ensure that there is no path injection // @@ -78,19 +77,85 @@ public class ReceptionUtil { /** * Method to decode either a json or yaml file into an object. * - * @param zipFile the zip file - * @param entry the entry to read in the zip file. + * @param zipEntryName the zip file name. + * @param entryData the data from entry to decode. * @return the decoded ToscaServiceTemplate object. * @throws CoderException IOException if the file decoding fails. */ - public static ToscaServiceTemplate decodeFile(ZipFile zipFile, final ZipEntry entry) - throws IOException, CoderException { + public static ToscaServiceTemplate decodeFile(String zipEntryName, InputStream entryData) throws CoderException { ToscaServiceTemplate toscaServiceTemplate = null; - if (entry.getName().endsWith(".json")) { - toscaServiceTemplate = coder.decode(zipFile.getInputStream(entry), ToscaServiceTemplate.class); - } else if (entry.getName().endsWith(".yml")) { - toscaServiceTemplate = yamlCoder.decode(zipFile.getInputStream(entry), ToscaServiceTemplate.class); + if (zipEntryName.endsWith(".json")) { + toscaServiceTemplate = coder.decode(entryData, ToscaServiceTemplate.class); + } else if (zipEntryName.endsWith(".yml")) { + toscaServiceTemplate = yamlCoder.decode(entryData, ToscaServiceTemplate.class); } return toscaServiceTemplate; } + + /** + * Unzip the csar file following the security recommendations from sonar cloud to avoid a zip bomb attack. + * + * @param csarFilename csar file which is a zip file. + * @param unzippedTemplates the templates which should be unzipped. + * @param filter contains the keywords for the entry name. + * @throws PolicyDecodingException in case zip file can't be read + * @throws CoderException in case files can't be decoded to a template + */ + public static void unzip(String csarFilename, Map<String, ToscaServiceTemplate> unzippedTemplates, String... filter) + throws PolicyDecodingException, CoderException { + try (var zipFile = new ZipFile(csarFilename)) { + int totalSizeArchive = 0; + int totalEntryArchive = 0; + + Enumeration<? extends ZipEntry> entries = zipFile.entries(); + + while (entries.hasMoreElements()) { + ZipEntry entry = entries.nextElement(); + totalEntryArchive++; + + if (checkEntryFilter(entry.getName(), filter)) { + validateZipEntry(entry.getName(), csarFilename); + InputStream entryData = new BufferedInputStream(zipFile.getInputStream(entry)); + + int bufferedBytes; + byte[] buffer = new byte[2048]; + int totalSizeEntry = 0; + + boolean isValidThreshold = true; + while ((bufferedBytes = entryData.read(buffer)) > 0 && isValidThreshold) { + totalSizeEntry += bufferedBytes; + totalSizeArchive += bufferedBytes; + + double compressionRatio = Math.floorDiv(totalSizeEntry, entry.getCompressedSize()); + isValidThreshold = compressionRatio <= THRESHOLD_RATIO; + } + + unzippedTemplates.put(entry.getName(), decodeFile(entry.getName(), zipFile.getInputStream(entry))); + } + + if (totalSizeArchive > THRESHOLD_SIZE || totalEntryArchive > THRESHOLD_ENTRIES) { + // the uncompressed data size is too much for the application resource capacity + break; + } + } + } catch (IOException exception) { + throw new PolicyDecodingException("Couldn't read the zipFile", exception); + } + } + + /** + * Check if entry is the one to be unzipped based on the filter. + * + * @param entryName zip file entry name. + * @param filter the list of filter to be looked up on entry names. + * @return true if entry is in filter, false otherwise. + */ + public static boolean checkEntryFilter(String entryName, String... filter) { + for (String f : filter) { + if (entryName.contains(f)) { + return true; + } + } + return false; + } } diff --git a/plugins/reception-plugins/src/test/java/org/onap/policy/distribution/reception/decoding/policy/file/AutomationCompositionDecoderFileInCsarTest.java b/plugins/reception-plugins/src/test/java/org/onap/policy/distribution/reception/decoding/policy/file/AutomationCompositionDecoderFileInCsarTest.java index 80c520a4..ac8a75df 100644 --- a/plugins/reception-plugins/src/test/java/org/onap/policy/distribution/reception/decoding/policy/file/AutomationCompositionDecoderFileInCsarTest.java +++ b/plugins/reception-plugins/src/test/java/org/onap/policy/distribution/reception/decoding/policy/file/AutomationCompositionDecoderFileInCsarTest.java @@ -92,6 +92,6 @@ public class AutomationCompositionDecoderFileInCsarTest { assertTrue(decoder.canHandle(csar)); assertThatThrownBy(() -> decoder.decode(csar)).isInstanceOf(PolicyDecodingException.class) - .hasMessageContaining("Failed decoding the acm"); + .hasMessageContaining("Couldn't read the zipFile"); } } diff --git a/plugins/reception-plugins/src/test/java/org/onap/policy/distribution/reception/decoding/policy/file/PolicyDecoderFileInCsarToPolicyTest.java b/plugins/reception-plugins/src/test/java/org/onap/policy/distribution/reception/decoding/policy/file/PolicyDecoderFileInCsarToPolicyTest.java index e76e9f38..45dd167c 100644 --- a/plugins/reception-plugins/src/test/java/org/onap/policy/distribution/reception/decoding/policy/file/PolicyDecoderFileInCsarToPolicyTest.java +++ b/plugins/reception-plugins/src/test/java/org/onap/policy/distribution/reception/decoding/policy/file/PolicyDecoderFileInCsarToPolicyTest.java @@ -1,7 +1,7 @@ /*- * ============LICENSE_START======================================================= * Copyright (C) 2018 Ericsson. All rights reserved. - * Modifications Copyright (C) 2019-2020 Nordix Foundation. + * Modifications Copyright (C) 2019-2020, 2022 Nordix Foundation. * ================================================================================ * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -105,7 +105,7 @@ public class PolicyDecoderFileInCsarToPolicyTest { assertTrue(decoder.canHandle(csar)); assertThatThrownBy(() -> decoder.decode(csar)).isInstanceOf(PolicyDecodingException.class) - .hasMessageContaining("Failed decoding the policy"); + .hasMessageContaining("Couldn't read the zipFile"); } diff --git a/plugins/reception-plugins/src/test/java/org/onap/policy/distribution/reception/handling/file/TestFileSystemReceptionHandler.java b/plugins/reception-plugins/src/test/java/org/onap/policy/distribution/reception/handling/file/TestFileSystemReceptionHandler.java index c9debdd9..e7a97a24 100644 --- a/plugins/reception-plugins/src/test/java/org/onap/policy/distribution/reception/handling/file/TestFileSystemReceptionHandler.java +++ b/plugins/reception-plugins/src/test/java/org/onap/policy/distribution/reception/handling/file/TestFileSystemReceptionHandler.java @@ -1,8 +1,7 @@ /*- * ============LICENSE_START======================================================= * Copyright (C) 2018 Intel. All rights reserved. - * Copyright (C) 2019 Nordix Foundation. - * Modifications Copyright (C) 2020 Nordix Foundation + * Copyright (C) 2019-2020, 2022 Nordix Foundation. * ================================================================================ * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -39,11 +38,9 @@ import org.junit.Test; import org.junit.rules.TemporaryFolder; import org.junit.runner.RunWith; import org.mockito.Mockito; -import org.mockito.invocation.InvocationOnMock; import org.mockito.runners.MockitoJUnitRunner; import org.mockito.stubbing.Answer; import org.onap.policy.common.parameters.ParameterService; -import org.onap.policy.distribution.reception.decoding.PolicyDecodingException; import org.onap.policy.distribution.reception.statistics.DistributionStatisticsManager; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -68,13 +65,10 @@ public class TestFileSystemReceptionHandler { * * @throws IOException if it occurs * @throws SecurityException if it occurs - * @throws NoSuchFieldException if it occurs - * @throws IllegalAccessException if it occurs * @throws IllegalArgumentException if it occurs */ @Before - public final void init() throws IOException, NoSuchFieldException, SecurityException, IllegalArgumentException, - IllegalAccessException { + public final void init() throws IOException, SecurityException, IllegalArgumentException { DistributionStatisticsManager.resetAllStatistics(); final Gson gson = new GsonBuilder().create(); @@ -90,7 +84,7 @@ public class TestFileSystemReceptionHandler { } @Test - public final void testInit() throws IOException, InterruptedException { + public final void testInit() throws IOException { final FileSystemReceptionHandler sypHandler = Mockito.spy(fileSystemHandler); Mockito.doNothing().when(sypHandler).initFileWatcher(Mockito.isA(String.class), Mockito.anyInt()); @@ -110,9 +104,9 @@ public class TestFileSystemReceptionHandler { } @Test - public void testMain() throws IOException, PolicyDecodingException { + public void testMain() throws IOException { final Object lock = new Object(); - final String watchPath = tempFolder.getRoot().getAbsolutePath().toString(); + final String watchPath = tempFolder.getRoot().getAbsolutePath(); class Processed { public boolean processed = false; @@ -121,15 +115,12 @@ public class TestFileSystemReceptionHandler { final Processed cond = new Processed(); final FileSystemReceptionHandler sypHandler = Mockito.spy(fileSystemHandler); - Mockito.doAnswer(new Answer<Object>() { - @Override - public Object answer(final InvocationOnMock invocation) { - synchronized (lock) { - cond.processed = true; - lock.notifyAll(); - } - return null; + Mockito.doAnswer((Answer<Object>) invocation -> { + synchronized (lock) { + cond.processed = true; + lock.notifyAll(); } + return null; }).when(sypHandler).createPolicyInputAndCallHandler(Mockito.isA(String.class)); final Thread th = new Thread(() -> { diff --git a/plugins/reception-plugins/src/test/java/org/onap/policy/distribution/reception/handling/sdc/DummyDecoder.java b/plugins/reception-plugins/src/test/java/org/onap/policy/distribution/reception/handling/sdc/DummyDecoder.java index f8b87f82..6c9b8bd0 100644 --- a/plugins/reception-plugins/src/test/java/org/onap/policy/distribution/reception/handling/sdc/DummyDecoder.java +++ b/plugins/reception-plugins/src/test/java/org/onap/policy/distribution/reception/handling/sdc/DummyDecoder.java @@ -3,6 +3,7 @@ * Copyright (C) 2018 Ericsson. All rights reserved. * Modifications Copyright (C) 2020 AT&T Intellectual Property. All rights reserved. * Modifications Copyright (C) 2021 Bell Canada. All rights reserved. + * Modifications Copyright (C) 2022 Nordix Foundation. * ================================================================================ * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -22,12 +23,11 @@ package org.onap.policy.distribution.reception.handling.sdc; -import java.util.Arrays; import java.util.Collection; +import java.util.List; import org.onap.policy.distribution.model.Csar; import org.onap.policy.distribution.model.PolicyInput; import org.onap.policy.distribution.reception.decoding.PolicyDecoder; -import org.onap.policy.distribution.reception.decoding.PolicyDecodingException; /** * Class to create a dummy decoder for test cases. @@ -50,10 +50,10 @@ public class DummyDecoder implements PolicyDecoder<Csar, DummyPolicy> { * {@inheritDoc}. */ @Override - public Collection<DummyPolicy> decode(final Csar input) throws PolicyDecodingException { + public Collection<DummyPolicy> decode(final Csar input) { final DummyPolicy dummyPolicy = new DummyPolicy(input.getCsarFilePath()); decodedPolicy = dummyPolicy; - return Arrays.asList(dummyPolicy); + return List.of(dummyPolicy); } /** diff --git a/plugins/reception-plugins/src/test/java/org/onap/policy/distribution/reception/handling/sdc/TestSdcReceptionHandler.java b/plugins/reception-plugins/src/test/java/org/onap/policy/distribution/reception/handling/sdc/TestSdcReceptionHandler.java index 58933c1f..3e8f4a63 100644 --- a/plugins/reception-plugins/src/test/java/org/onap/policy/distribution/reception/handling/sdc/TestSdcReceptionHandler.java +++ b/plugins/reception-plugins/src/test/java/org/onap/policy/distribution/reception/handling/sdc/TestSdcReceptionHandler.java @@ -1,7 +1,7 @@ /*- * ============LICENSE_START======================================================= * Copyright (C) 2018 Intel. All rights reserved. - * Copyright (C) 2019 Nordix Foundation. + * Copyright (C) 2019, 2022 Nordix Foundation. * Modifications Copyright (C) 2020 Nordix Foundation * ================================================================================ * Licensed under the Apache License, Version 2.0 (the "License"); @@ -24,6 +24,7 @@ package org.onap.policy.distribution.reception.handling.sdc; import static org.assertj.core.api.Assertions.assertThatCode; import static org.junit.Assert.assertEquals; +import static org.junit.Assert.assertNull; import static org.junit.Assert.assertTrue; import static org.mockito.Matchers.any; @@ -33,9 +34,9 @@ import java.io.FileReader; import java.io.IOException; import java.lang.reflect.Field; import java.util.ArrayList; -import java.util.Arrays; import java.util.Collection; import java.util.HashMap; +import java.util.List; import java.util.Map; import org.junit.After; import org.junit.Before; @@ -92,19 +93,16 @@ public class TestSdcReceptionHandler { /** * Setup for the test cases. * - * @throws IOException if it occurs - * @throws SecurityException if it occurs - * @throws NoSuchFieldException if it occurs - * @throws IllegalAccessException if it occurs + * @throws IOException if it occurs + * @throws SecurityException if it occurs * @throws IllegalArgumentException if it occurs */ @Before - public final void init() throws IOException, NoSuchFieldException, SecurityException, IllegalArgumentException, - IllegalAccessException { + public final void init() throws IOException, SecurityException, IllegalArgumentException { DistributionStatisticsManager.resetAllStatistics(); final Gson gson = new GsonBuilder().create(); pssdConfigParameters = gson.fromJson(new FileReader("src/test/resources/handling-sdc.json"), - SdcReceptionHandlerConfigurationParameterGroup.class); + SdcReceptionHandlerConfigurationParameterGroup.class); ParameterService.register(pssdConfigParameters); final SdcReceptionHandler sdcHandler = new SdcReceptionHandler(); sypHandler = Mockito.spy(sdcHandler); @@ -120,15 +118,15 @@ public class TestSdcReceptionHandler { Mockito.when(distributionClient.sendDeploymentStatus(any())).thenReturn(successfulClientInitResult); Mockito.when(distributionClient.sendDeploymentStatus(any(), any())).thenReturn(successfulClientInitResult); Mockito.when(distributionClient.download(any())).thenReturn(successfulClientDownloadResult); - Mockito.when(notificationData.getServiceArtifacts()).thenReturn(Arrays.asList(artifactInfo)); + Mockito.when(notificationData.getServiceArtifacts()).thenReturn(List.of(artifactInfo)); Mockito.when(artifactInfo.getArtifactName()).thenReturn(DUMMY_SERVICE_CSAR); Mockito.when(successfulClientDownloadResult.getArtifactPayload()).thenReturn(new byte[1]); Mockito.when(successfulClientInitResult.getDistributionActionResult()) - .thenReturn(DistributionActionResultEnum.SUCCESS); + .thenReturn(DistributionActionResultEnum.SUCCESS); Mockito.when(successfulClientDownloadResult.getDistributionActionResult()) - .thenReturn(DistributionActionResultEnum.SUCCESS); + .thenReturn(DistributionActionResultEnum.SUCCESS); Mockito.when(failureClientInitResult.getDistributionActionResult()) - .thenReturn(DistributionActionResultEnum.FAIL); + .thenReturn(DistributionActionResultEnum.FAIL); } @@ -139,7 +137,7 @@ public class TestSdcReceptionHandler { @Test public final void testInitializeSdcClient() { - assertThatCode(() -> sypHandler.initializeReception(pssdConfigParameters.getName())) + assertThatCode(() -> sypHandler.initializeReception(pssdConfigParameters.getName())) .doesNotThrowAnyException(); } @@ -147,7 +145,7 @@ public class TestSdcReceptionHandler { public final void testInitializeSdcClient_Failure() { Mockito.when(successfulClientInitResult.getDistributionActionResult()) - .thenReturn(DistributionActionResultEnum.FAIL).thenReturn(DistributionActionResultEnum.SUCCESS); + .thenReturn(DistributionActionResultEnum.FAIL).thenReturn(DistributionActionResultEnum.SUCCESS); assertThatCode(() -> sypHandler.initializeReception(pssdConfigParameters.getName())) .doesNotThrowAnyException(); } @@ -156,7 +154,7 @@ public class TestSdcReceptionHandler { public final void testStartSdcClient_Failure() { assertThatCode(() -> { Mockito.when(distributionClient.start()).thenReturn(failureClientInitResult) - .thenReturn(successfulClientInitResult); + .thenReturn(successfulClientInitResult); sypHandler.initializeReception(pssdConfigParameters.getName()); }).doesNotThrowAnyException(); } @@ -170,10 +168,10 @@ public class TestSdcReceptionHandler { } @Test - public final void testStopSdcClient_Failure() throws PluginInitializationException { + public final void testStopSdcClient_Failure() { sypHandler.initializeReception(pssdConfigParameters.getName()); Mockito.when(distributionClient.stop()).thenReturn(failureClientInitResult) - .thenReturn(successfulClientInitResult); + .thenReturn(successfulClientInitResult); assertThatCode(() -> sypHandler.destroy()).doesNotThrowAnyException(); } @@ -184,7 +182,7 @@ public class TestSdcReceptionHandler { @Test public void testNotificationCallBack() throws NoSuchFieldException, SecurityException, IllegalArgumentException, - IllegalAccessException, PluginInitializationException { + IllegalAccessException, PluginInitializationException { final DummyDecoder policyDecoder = new DummyDecoder(); final Collection<PolicyDecoder<Csar, DummyPolicy>> policyDecoders = new ArrayList<>(); @@ -211,10 +209,10 @@ public class TestSdcReceptionHandler { @Test public void testDownloadArtifactFailure() throws NoSuchFieldException, SecurityException, IllegalArgumentException, - IllegalAccessException, PluginInitializationException { + IllegalAccessException, PluginInitializationException { Mockito.when(successfulClientDownloadResult.getDistributionActionResult()) - .thenReturn(DistributionActionResultEnum.FAIL); + .thenReturn(DistributionActionResultEnum.FAIL); final DummyDecoder policyDecoder = new DummyDecoder(); final Collection<PolicyDecoder<Csar, DummyPolicy>> policyDecoders = new ArrayList<>(); @@ -228,7 +226,7 @@ public class TestSdcReceptionHandler { sypHandler.initializeReception(pssdConfigParameters.getName()); sypHandler.activateCallback(notificationData); - assertEquals(null, policyDecoder.getDecodedPolicy()); + assertNull(policyDecoder.getDecodedPolicy()); assertEquals(0, policyForwarder.getNumberOfPoliciesReceived()); assertEquals(1, DistributionStatisticsManager.getTotalDistributionCount()); assertEquals(0, DistributionStatisticsManager.getDistributionSuccessCount()); @@ -240,10 +238,10 @@ public class TestSdcReceptionHandler { @Test public void testSendDistributionStatusFailure() throws NoSuchFieldException, SecurityException, - IllegalArgumentException, IllegalAccessException, PluginInitializationException { + IllegalArgumentException, IllegalAccessException, PluginInitializationException { Mockito.when(successfulClientDownloadResult.getDistributionActionResult()) - .thenReturn(DistributionActionResultEnum.FAIL); + .thenReturn(DistributionActionResultEnum.FAIL); Mockito.when(distributionClient.sendDownloadStatus(any(), any())).thenReturn(failureClientInitResult); Mockito.when(distributionClient.sendDeploymentStatus(any(), any())).thenReturn(failureClientInitResult); Mockito.when(distributionClient.sendComponentDoneStatus(any(), any())).thenReturn(failureClientInitResult); @@ -260,14 +258,15 @@ public class TestSdcReceptionHandler { sypHandler.initializeReception(pssdConfigParameters.getName()); sypHandler.activateCallback(notificationData); - assertEquals(null, policyDecoder.getDecodedPolicy()); + assertNull(policyDecoder.getDecodedPolicy()); assertEquals(0, policyForwarder.getNumberOfPoliciesReceived()); } private void setUpPlugins(final AbstractReceptionHandler receptionHandler, - final Collection<PolicyDecoder<Csar, DummyPolicy>> decoders, final Collection<PolicyForwarder> forwarders) - throws NoSuchFieldException, SecurityException, IllegalArgumentException, IllegalAccessException, - PluginInitializationException { + final Collection<PolicyDecoder<Csar, DummyPolicy>> decoders, + final Collection<PolicyForwarder> forwarders) + throws NoSuchFieldException, SecurityException, IllegalArgumentException, IllegalAccessException, + PluginInitializationException { final PluginHandlerParameters pluginParameters = getPluginHandlerParameters(); pluginParameters.setName("DummyDistributionGroup"); ParameterService.register(pluginParameters); @@ -290,24 +289,21 @@ public class TestSdcReceptionHandler { private PluginHandlerParameters getPluginHandlerParameters() { final Map<String, PolicyDecoderParameters> policyDecoders = getPolicyDecoders(); final Map<String, PolicyForwarderParameters> policyForwarders = getPolicyForwarders(); - final PluginHandlerParameters pluginHandlerParameters = - new PluginHandlerParameters(policyDecoders, policyForwarders); - return pluginHandlerParameters; + return new PluginHandlerParameters(policyDecoders, policyForwarders); } private Map<String, PolicyDecoderParameters> getPolicyDecoders() { - final Map<String, PolicyDecoderParameters> policyDecoders = new HashMap<String, PolicyDecoderParameters>(); + final Map<String, PolicyDecoderParameters> policyDecoders = new HashMap<>(); final PolicyDecoderParameters pDParameters = new PolicyDecoderParameters("DummyDecoder", - "org.onap.policy.distribution.reception.handling.sdc.DummyDecoder", "DummyDecoderConfiguration"); + "org.onap.policy.distribution.reception.handling.sdc.DummyDecoder", "DummyDecoderConfiguration"); policyDecoders.put("DummyDecoderKey", pDParameters); return policyDecoders; } private Map<String, PolicyForwarderParameters> getPolicyForwarders() { - final Map<String, PolicyForwarderParameters> policyForwarders = - new HashMap<String, PolicyForwarderParameters>(); + final Map<String, PolicyForwarderParameters> policyForwarders = new HashMap<>(); final PolicyForwarderParameters pFParameters = new PolicyForwarderParameters("DummyForwarder", - "org.onap.policy.distribution.reception.handling.sdc.DummyPolicyForwarder", "DummyConfiguration"); + "org.onap.policy.distribution.reception.handling.sdc.DummyPolicyForwarder", "DummyConfiguration"); policyForwarders.put("DummyForwarderKey", pFParameters); return policyForwarders; } diff --git a/plugins/reception-plugins/src/test/java/org/onap/policy/distribution/reception/util/ReceptionUtilTest.java b/plugins/reception-plugins/src/test/java/org/onap/policy/distribution/reception/util/ReceptionUtilTest.java deleted file mode 100644 index 6747618e..00000000 --- a/plugins/reception-plugins/src/test/java/org/onap/policy/distribution/reception/util/ReceptionUtilTest.java +++ /dev/null @@ -1,40 +0,0 @@ -/*- - * ============LICENSE_START======================================================= - * Copyright (C) 2022 Nordix Foundation. - * ================================================================================ - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - * - * SPDX-License-Identifier: Apache-2.0 - * ============LICENSE_END========================================================= - */ - -package org.onap.policy.distribution.reception.util; - -import org.assertj.core.api.Assertions; -import org.junit.Test; - -/** - * Class for testing {@link ReceptionUtil}. - */ - -public class ReceptionUtilTest { - - @Test - public void testValidateZipEntry_InvalidSize() { - long invalidFileSize = 512L * 2048; - - Assertions.assertThatThrownBy(() -> - ReceptionUtil.validateZipEntry("entryName", "csarPath", invalidFileSize)) - .hasMessage("Zip entry for entryName is too large " + invalidFileSize); - } -} |