summaryrefslogtreecommitdiffstats
path: root/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/CsarValidationUtils.java
diff options
context:
space:
mode:
Diffstat (limited to 'catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/CsarValidationUtils.java')
-rw-r--r--catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/CsarValidationUtils.java587
1 files changed, 287 insertions, 300 deletions
diff --git a/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/CsarValidationUtils.java b/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/CsarValidationUtils.java
index 53dceb8112..6fbc22454d 100644
--- a/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/CsarValidationUtils.java
+++ b/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/CsarValidationUtils.java
@@ -20,19 +20,7 @@
package org.openecomp.sdc.be.components.impl;
-import java.io.ByteArrayInputStream;
-import java.io.IOException;
-import java.io.StringReader;
-import java.util.ArrayList;
-import java.util.Arrays;
-import java.util.List;
-import java.util.Map;
-import java.util.Optional;
-import java.util.Properties;
-import java.util.regex.Matcher;
-import java.util.regex.Pattern;
-import java.util.stream.Collectors;
-
+import fj.data.Either;
import org.apache.commons.lang3.tuple.ImmutablePair;
import org.openecomp.sdc.be.config.BeEcompErrorManager;
import org.openecomp.sdc.be.config.BeEcompErrorManager.ErrorSeverity;
@@ -44,35 +32,40 @@ import org.openecomp.sdc.exception.ResponseFormat;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
-import fj.data.Either;
+import java.io.ByteArrayInputStream;
+import java.io.IOException;
+import java.io.StringReader;
+import java.util.*;
+import java.util.regex.Matcher;
+import java.util.regex.Pattern;
+import java.util.stream.Collectors;
public class CsarValidationUtils {
- private static Logger log = LoggerFactory.getLogger(CsarValidationUtils.class.getName());
+ private static final Logger log = LoggerFactory.getLogger(CsarValidationUtils.class);
- private static final String TOSCA_META_FILE_VERSION = "TOSCA-Meta-File-Version";
+ private static final String TOSCA_META_FILE_VERSION = "TOSCA-Meta-File-Version";
- private static final String CSAR_VERSION = "CSAR-Version";
+ private static final String CSAR_VERSION = "CSAR-Version";
- private static final String CREATED_BY = "Created-By";
+ private static final String CREATED_BY = "Created-By";
- private static final String NEW_LINE_DELM = "\n";
+ private static final String NEW_LINE_DELM = "\n";
- //public final static String TOSCA_METADATA_FILE = "TOSCA-Metadata/TOSCA.meta";
- public final static String TOSCA_METADATA = "TOSCA-Metadata";
- public final static String TOSCA_FILE = "TOSCA.meta";
- public final static String DEL_PATTERN = "([/\\\\]+)";
- public static final String TOSCA_METADATA_PATH_PATTERN = TOSCA_METADATA +
- // Artifact Group (i.e Deployment/Informational)
- DEL_PATTERN + TOSCA_FILE;
+ public final static String TOSCA_METADATA = "TOSCA-Metadata";
+ public final static String TOSCA_FILE = "TOSCA.meta";
+ public final static String DEL_PATTERN = "([/\\\\]+)";
+ public static final String TOSCA_METADATA_PATH_PATTERN = TOSCA_METADATA +
+ // Artifact Group (i.e Deployment/Informational)
+ DEL_PATTERN + TOSCA_FILE;
- public static final String TOSCA_META_ENTRY_DEFINITIONS = "Entry-Definitions";
+ public static final String TOSCA_META_ENTRY_DEFINITIONS = "Entry-Definitions";
- private static final String[] TOSCA_METADATA_FIELDS = { TOSCA_META_FILE_VERSION, CSAR_VERSION, CREATED_BY, TOSCA_META_ENTRY_DEFINITIONS };
+ private static final String[] TOSCA_METADATA_FIELDS = { TOSCA_META_FILE_VERSION, CSAR_VERSION, CREATED_BY, TOSCA_META_ENTRY_DEFINITIONS };
- public final static String ARTIFACTS_METADATA_FILE = "HEAT.meta";
+ public final static String ARTIFACTS_METADATA_FILE = "HEAT.meta";
- public static final String TOSCA_CSAR_EXTENSION = ".csar";
+ public static final String TOSCA_CSAR_EXTENSION = ".csar";
/**
* Validates Csar
* @param csar
@@ -80,275 +73,269 @@ public class CsarValidationUtils {
* @param componentsUtils
* @return
*/
- public static Either<Boolean, ResponseFormat> validateCsar(Map<String, byte[]> csar, String csarUUID, ComponentsUtils componentsUtils) {
- Either<Boolean, ResponseFormat> validateStatus = validateIsTOSCAMetadataExist(csar, csarUUID, componentsUtils);
- if (validateStatus.isRight()) {
- return Either.right(validateStatus.right().value());
- }
-
- removeNonUniqueArtifactsFromCsar(csar);
-
- log.trace("TOSCA-Metadata/TOSCA.meta file found, CSAR id {}", csarUUID);
- validateStatus = validateTOSCAMetadataFile(csar, csarUUID, componentsUtils);
- if (validateStatus.isRight()) {
- return Either.right(validateStatus.right().value());
- }
- return Either.left(true);
- }
-
- private static void removeNonUniqueArtifactsFromCsar(Map<String, byte[]> csar) {
-
- List<String> nonUniqueArtifactsToRemove = new ArrayList<>();
- String[] paths = csar.keySet().toArray(new String[csar.keySet().size()]);
- int numberOfArtifacts = paths.length;
- for(int i = 0; i < numberOfArtifacts; ++i ){
- collectNonUniqueArtifact(paths, i, numberOfArtifacts, nonUniqueArtifactsToRemove);
- }
- nonUniqueArtifactsToRemove.stream().forEach(path->csar.remove(path));
- }
-
- private static void collectNonUniqueArtifact( String[] paths, int currInd, int numberOfArtifacts, List<String> nonUniqueArtifactsToRemove) {
-
- String[] parsedPath = paths[currInd].split("/");
- String[] otherParsedPath;
- int artifactNameInd = parsedPath.length - 1;
- for(int j = currInd + 1; j < numberOfArtifacts; ++j ){
- otherParsedPath = paths[j].split("/");
- if(parsedPath.length == otherParsedPath.length && parsedPath.length > 3 && isEqualArtifactNames(parsedPath, otherParsedPath)){
- log.error("Can't upload two artifact with the same name {}. The artifact with path {} will be handled, and the artifact with path {} will be ignored. ",
- parsedPath[artifactNameInd], paths[currInd], paths[j]);
- nonUniqueArtifactsToRemove.add(paths[j]);
- }
- }
- }
-
- private static boolean isEqualArtifactNames(String[] parsedPath, String[] otherParsedPath) {
- boolean isEqualArtifactNames = false;
- int artifactNameInd = parsedPath.length - 1;
- int artifactGroupTypeInd = parsedPath.length - 3;
- String groupType = parsedPath[artifactGroupTypeInd];
- String artifactName = parsedPath[artifactNameInd];
- String otherGroupType = otherParsedPath[artifactGroupTypeInd];
- String otherArtifactName = otherParsedPath[artifactNameInd];
- String vfcToscaName = parsedPath.length == 5 ? parsedPath[1] : null;
-
- if(artifactName.equalsIgnoreCase(otherArtifactName) && groupType.equalsIgnoreCase(otherGroupType)){
- isEqualArtifactNames = vfcToscaName == null ? true : vfcToscaName.equalsIgnoreCase(otherParsedPath[1]);
- }
- return isEqualArtifactNames;
- }
-
- public static Either<ImmutablePair<String, String>, ResponseFormat> getToscaYaml(Map<String, byte[]> csar, String csarUUID, ComponentsUtils componentsUtils) {
- Either<Boolean, ResponseFormat> validateStatus = validateIsTOSCAMetadataExist(csar, csarUUID, componentsUtils);
- if (validateStatus.isRight()) {
- return Either.right(validateStatus.right().value());
- }
- Pattern pattern = Pattern.compile(TOSCA_METADATA_PATH_PATTERN);
- Optional<String> keyOp = csar.keySet().stream().filter(k -> pattern.matcher(k).matches()).findAny();
- if(!keyOp.isPresent()){
- log.debug("TOSCA-Metadata/TOSCA.meta file is not in expected key-value form in csar, csar ID {}", csarUUID);
- BeEcompErrorManager.getInstance().logInternalDataError("TOSCA-Metadata/TOSCA.meta file not in expected key-value form in CSAR with id " + csarUUID, "CSAR internals are invalid", ErrorSeverity.ERROR);
- return Either.right(componentsUtils.getResponseFormat(ActionStatus.CSAR_INVALID_FORMAT, csarUUID));
- }
- byte[] toscaMetaBytes = csar.get(keyOp.get());
- Properties props = new Properties();
- try {
- //props.load(new ByteArrayInputStream(toscaMetaBytes));
- String propStr = new String(toscaMetaBytes);
- props.load(new StringReader(propStr.replace("\\","\\\\")));
- } catch (IOException e) {
- log.debug("TOSCA-Metadata/TOSCA.meta file is not in expected key-value form in csar, csar ID {}", csarUUID, e);
- BeEcompErrorManager.getInstance().logInternalDataError("TOSCA-Metadata/TOSCA.meta file not in expected key-value form in CSAR with id " + csarUUID, "CSAR internals are invalid", ErrorSeverity.ERROR);
- return Either.right(componentsUtils.getResponseFormat(ActionStatus.CSAR_INVALID_FORMAT, csarUUID));
- }
-
- String yamlFileName = props.getProperty(TOSCA_META_ENTRY_DEFINITIONS);
- String[] ops = yamlFileName.split(DEL_PATTERN);
- List<String> list = Arrays.asList(ops);
- String result = list.stream().map(x -> x).collect(Collectors.joining(DEL_PATTERN));
- keyOp = csar.keySet().stream().filter(k -> Pattern.compile(result).matcher(k).matches()).findAny();
- if(!keyOp.isPresent()){
- log.debug("Entry-Definitions entry not found in TOSCA-Metadata/TOSCA.meta file, csar ID {}", csarUUID);
- BeEcompErrorManager.getInstance().logInternalDataError("Entry-Definitions entry not found in TOSCA-Metadata/TOSCA.meta file in CSAR with id " + csarUUID, "CSAR internals are invalid", ErrorSeverity.ERROR);
- return Either.right(componentsUtils.getResponseFormat(ActionStatus.YAML_NOT_FOUND_IN_CSAR, csarUUID, yamlFileName));
- }
-
- log.trace("Found Entry-Definitions property in TOSCA-Metadata/TOSCA.meta, Entry-Definitions: {}, CSAR id: {}", yamlFileName, csarUUID);
- byte[] yamlFileBytes = csar.get(yamlFileName);
- if (yamlFileBytes == null) {
- log.debug("Entry-Definitions {} file not found in csar, csar ID {}", yamlFileName, csarUUID);
- BeEcompErrorManager.getInstance().logInternalDataError("Entry-Definitions " + yamlFileName + " file not found in CSAR with id " + csarUUID, "CSAR structure is invalid", ErrorSeverity.ERROR);
- return Either.right(componentsUtils.getResponseFormat(ActionStatus.YAML_NOT_FOUND_IN_CSAR, csarUUID, yamlFileName));
- }
-
- String yamlFileContents = new String(yamlFileBytes);
-
- return Either.left(new ImmutablePair<String, String>(yamlFileName, yamlFileContents));
- }
-
- public static Either<ImmutablePair<String, String>, ResponseFormat> getArtifactsMeta(Map<String, byte[]> csar, String csarUUID, ComponentsUtils componentsUtils) {
-
- if( !csar.containsKey(CsarUtils.ARTIFACTS_PATH + ARTIFACTS_METADATA_FILE) ) {
- log.debug("Entry-Definitions entry not found in TOSCA-Metadata/TOSCA.meta file, csar ID {}", csarUUID);
- BeEcompErrorManager.getInstance().logInternalDataError("Entry-Definitions entry not found in TOSCA-Metadata/TOSCA.meta file in CSAR with id " + csarUUID, "CSAR internals are invalid", ErrorSeverity.ERROR);
- return Either.right(componentsUtils.getResponseFormat(ActionStatus.YAML_NOT_FOUND_IN_CSAR, csarUUID, ARTIFACTS_METADATA_FILE));
- }
-
- log.trace("Found Entry-Definitions property in TOSCA-Metadata/TOSCA.meta, Entry-Definitions: {}, CSAR id: {}", ARTIFACTS_METADATA_FILE, csarUUID);
- byte[] artifactsMetaBytes = csar.get(CsarUtils.ARTIFACTS_PATH + ARTIFACTS_METADATA_FILE);
- if (artifactsMetaBytes == null) {
- log.debug("Entry-Definitions {}{} file not found in csar, csar ID {}", CsarUtils.ARTIFACTS_PATH, ARTIFACTS_METADATA_FILE, csarUUID);
- BeEcompErrorManager.getInstance().logInternalDataError("Entry-Definitions " + CsarUtils.ARTIFACTS_PATH + ARTIFACTS_METADATA_FILE + " file not found in CSAR with id " + csarUUID, "CSAR structure is invalid", ErrorSeverity.ERROR);
- return Either.right(componentsUtils.getResponseFormat(ActionStatus.YAML_NOT_FOUND_IN_CSAR, csarUUID, CsarUtils.ARTIFACTS_PATH + ARTIFACTS_METADATA_FILE));
- }
-
- String artifactsFileContents = new String(artifactsMetaBytes);
-
- return Either.left(new ImmutablePair<String, String>(CsarUtils.ARTIFACTS_PATH + ARTIFACTS_METADATA_FILE, artifactsFileContents));
- }
-
- public static Either<ImmutablePair<String, byte[]>, ResponseFormat> getArtifactsContent(String csarUUID, Map<String, byte[]> csar, String artifactPath, String artifactName, ComponentsUtils componentsUtils) {
- if (!csar.containsKey(artifactPath)) {
- log.debug("Entry-Definitions entry not found in Artifacts/HEAT.meta file, csar ID {}", csarUUID);
- BeEcompErrorManager.getInstance().logInternalDataError("Entry-Definitions entry not found in TOSCA-Metadata/TOSCA.meta file in CSAR with id " + csarUUID, "CSAR internals are invalid", ErrorSeverity.ERROR);
- return Either.right(componentsUtils.getResponseFormat(ActionStatus.ARTIFACT_NOT_FOUND_IN_CSAR, CsarUtils.ARTIFACTS_PATH + artifactName, csarUUID));
- }
-
- log.trace("Found Entry-Definitions property in Artifacts/HEAT.meta, Entry-Definitions: {}, CSAR id: {}", artifactPath, csarUUID);
- byte[] artifactFileBytes = csar.get(artifactPath);
- if (artifactFileBytes == null) {
- log.debug("Entry-Definitions {}{} file not found in csar, csar ID {}", CsarUtils.ARTIFACTS_PATH, artifactName, csarUUID);
- BeEcompErrorManager.getInstance().logInternalDataError("Entry-Definitions " + artifactPath + " file not found in CSAR with id " + csarUUID, "CSAR structure is invalid", ErrorSeverity.ERROR);
- return Either.right(componentsUtils.getResponseFormat(ActionStatus.ARTIFACT_NOT_FOUND_IN_CSAR, artifactPath, csarUUID));
- }
-
- return Either.left(new ImmutablePair<String, byte[]>(artifactName, artifactFileBytes));
- }
-
- private static Either<Boolean, ResponseFormat> validateTOSCAMetadataFile(Map<String, byte[]> csar, String csarUUID, ComponentsUtils componentsUtils) {
-
- Pattern pattern = Pattern.compile(TOSCA_METADATA_PATH_PATTERN);
- Optional<String> keyOp = csar.keySet().stream().filter(k -> pattern.matcher(k).matches()).findAny();
- if(!keyOp.isPresent()){
- log.debug("TOSCA-Metadata/TOSCA.meta file is not in expected key-value form in csar, csar ID {}", csarUUID);
- BeEcompErrorManager.getInstance().logInternalDataError("TOSCA-Metadata/TOSCA.meta file not in expected key-value form in CSAR with id " + csarUUID, "CSAR internals are invalid", ErrorSeverity.ERROR);
- return Either.right(componentsUtils.getResponseFormat(ActionStatus.CSAR_INVALID_FORMAT, csarUUID));
- }
-
- byte[] toscaMetaBytes = csar.get(keyOp.get());
- String toscaMetadata = new String(toscaMetaBytes);
- String[] splited = toscaMetadata.split(NEW_LINE_DELM);
- if (splited == null || splited.length < TOSCA_METADATA_FIELDS.length) {
- log.debug("TOSCA-Metadata/TOSCA.meta file is not in expected key-value form in csar, csar ID {}", csarUUID);
- BeEcompErrorManager.getInstance().logInternalDataError("TOSCA-Metadata/TOSCA.meta file not in expected key-value form in CSAR with id " + csarUUID, "CSAR internals are invalid", ErrorSeverity.ERROR);
- return Either.right(componentsUtils.getResponseFormat(ActionStatus.CSAR_INVALID_FORMAT, csarUUID));
- }
- /*
- * if(splited.length == TOSCA_METADATA_FIELDS.length){ if(!toscaMetadata.endsWith(NEW_LINE_DELM)){ log. debug("TOSCA-Metadata/TOSCA.meta file is not in expected key-value form in csar, csar ID {}" , csarUUID);
- * BeEcompErrorManager.getInstance(). logInternalDataError("TOSCA-Metadata/TOSCA.meta file not in expected key-value form in CSAR with id " +csarUUID, "CSAR internals are invalid", ErrorSeverity.ERROR); return
- * Either.right(componentsUtils.getResponseFormat(ActionStatus. CSAR_INVALID_FORMAT, csarUUID)); } }
- */
-
- Either<Boolean, ResponseFormat> block_0Status = validateBlock_0(csarUUID, splited, componentsUtils);
- if (block_0Status.isRight()) {
- return Either.right(block_0Status.right().value());
- }
-
- return Either.left(true);
-
- }
-
- private static Either<Boolean, ResponseFormat> validateBlock_0(String csarUUID, String[] splited, ComponentsUtils componentsUtils) {
- int index = 0;
- for (String toscaField : TOSCA_METADATA_FIELDS) {
-
- Properties props = new Properties();
-
- try {
- props.load(new ByteArrayInputStream(splited[index].getBytes()));
- } catch (IOException e) {
- log.debug("TOSCA-Metadata/TOSCA.meta file is not in expected key-value form in csar, csar ID {}", csarUUID, e);
- BeEcompErrorManager.getInstance().logInternalDataError("TOSCA-Metadata/TOSCA.meta file not in expected key-value form in CSAR with id " + csarUUID, "CSAR internals are invalid", ErrorSeverity.ERROR);
- return Either.right(componentsUtils.getResponseFormat(ActionStatus.CSAR_INVALID_FORMAT, csarUUID));
- }
- if (!props.containsKey(toscaField)) {
- log.debug("TOSCA.meta file format is invalid: No new line after block_0 as expected in csar, csar ID {}", csarUUID);
- BeEcompErrorManager.getInstance().logInternalDataError("TOSCA-Metadata/TOSCA.meta file not in expected key-value form in CSAR with id " + csarUUID, "CSAR internals are invalid", ErrorSeverity.ERROR);
- return Either.right(componentsUtils.getResponseFormat(ActionStatus.CSAR_INVALID_FORMAT, csarUUID));
- }
- String value = props.getProperty(toscaField);
- if (value == null || value.isEmpty()) {
- log.debug("TOSCA-Metadata/TOSCA.meta file is not in expected key-value form in csar, csar ID {}", csarUUID);
- BeEcompErrorManager.getInstance().logInternalDataError("TOSCA-Metadata/TOSCA.meta file not in expected key-value form in CSAR with id " + csarUUID, "CSAR internals are invalid", ErrorSeverity.ERROR);
- return Either.right(componentsUtils.getResponseFormat(ActionStatus.CSAR_INVALID_FORMAT, csarUUID));
- }
-
- // TOSCA-Meta-File-Version & CSAR-Version : digit.digit - format
- // validation
- if (toscaField.equals(TOSCA_META_FILE_VERSION) || toscaField.equals(CSAR_VERSION)) {
- if (!validateTOSCAMetaProperty(value)) {
- log.debug("TOSCA-Metadata/TOSCA.meta file contains {} in wrong format (digit.digit), csar ID {}", toscaField, csarUUID);
- BeEcompErrorManager.getInstance().logInternalDataError("TOSCA-Metadata/TOSCA.meta file not in expected key-value form in CSAR with id " + csarUUID, "CSAR internals are invalid", ErrorSeverity.ERROR);
- return Either.right(componentsUtils.getResponseFormat(ActionStatus.CSAR_INVALID_FORMAT, csarUUID));
- }
- }
- index++;
- }
- return Either.left(true);
- }
-
- private static boolean validateTOSCAMetaProperty(String toscaProperty) {
- final String FLOAT_STRING = "^\\d{1}[.]\\d{1}$";
- final Pattern FLOAT_PATTERN = Pattern.compile(FLOAT_STRING);
-
- Matcher floatMatcher = FLOAT_PATTERN.matcher(toscaProperty);
- return floatMatcher.matches();
- }
-
- private static Either<Boolean, ResponseFormat> validateIsTOSCAMetadataExist(Map<String, byte[]> csar, String csarUUID, ComponentsUtils componentsUtils) {
- if (csar == null || csar.isEmpty()) {
- log.debug("Error when fetching csar with ID {}", csarUUID);
- BeEcompErrorManager.getInstance().logBeDaoSystemError("Creating resource from CSAR: fetching CSAR with id " + csarUUID + " failed");
- ResponseFormat responseFormat = componentsUtils.getResponseFormat(ActionStatus.CSAR_INVALID, csarUUID);
- return Either.right(responseFormat);
- }
-
- Pattern pattern = Pattern.compile(TOSCA_METADATA_PATH_PATTERN);
- Optional<String> keyOp = csar.keySet().stream().filter(k -> pattern.matcher(k).matches()).findAny();
- if(!keyOp.isPresent()){
-
- log.debug("TOSCA-Metadata/TOSCA.meta file not found in csar, csar ID {}", csarUUID);
- BeEcompErrorManager.getInstance().logInternalDataError("TOSCA-Metadata/TOSCA.meta file not found in CSAR with id " + csarUUID, "CSAR structure is invalid", ErrorSeverity.ERROR);
- return Either.right(componentsUtils.getResponseFormat(ActionStatus.CSAR_INVALID, csarUUID));
- }
- byte[] toscaMetaBytes = csar.get(keyOp.get());
- // && exchanged for ||
- if (toscaMetaBytes == null || toscaMetaBytes.length == 0) {
- log.debug("TOSCA-Metadata/TOSCA.meta file not found in csar, csar ID {}", csarUUID);
- BeEcompErrorManager.getInstance().logInternalDataError("TOSCA-Metadata/TOSCA.meta file not found in CSAR with id " + csarUUID, "CSAR structure is invalid", ErrorSeverity.ERROR);
- return Either.right(componentsUtils.getResponseFormat(ActionStatus.CSAR_INVALID, csarUUID));
- }
-
- return Either.left(Boolean.TRUE);
- }
-
- public static Either<String, ResponseFormat> getToscaYamlChecksum(Map<String, byte[]> csar, String csarUUID, ComponentsUtils componentsUtils) {
-
- Either<ImmutablePair<String, String>, ResponseFormat> toscaYamlRes = getToscaYaml(csar, csarUUID, componentsUtils);
- if (toscaYamlRes.isRight() || toscaYamlRes.left().value() == null || toscaYamlRes.left().value().getRight() == null) {
- log.debug("Faild to create toscaYamlChecksum for csar, csar ID {}", csarUUID);
- return Either.right(toscaYamlRes.right().value());
- }
-
- String newCheckSum = GeneralUtility.calculateMD5Base64EncodedByByteArray(toscaYamlRes.left().value().getRight().getBytes());
- return Either.left(newCheckSum);
-
- }
-
- public static boolean isCsarPayloadName(String payloadName) {
- if (payloadName == null)
- return false;
- return payloadName.toLowerCase().endsWith(TOSCA_CSAR_EXTENSION);
- }
+ public static Either<Boolean, ResponseFormat> validateCsar(Map<String, byte[]> csar, String csarUUID, ComponentsUtils componentsUtils) {
+ Either<Boolean, ResponseFormat> validateStatus = validateIsTOSCAMetadataExist(csar, csarUUID, componentsUtils);
+ if (validateStatus.isRight()) {
+ return Either.right(validateStatus.right().value());
+ }
+
+ removeNonUniqueArtifactsFromCsar(csar);
+
+ log.trace("TOSCA-Metadata/TOSCA.meta file found, CSAR id {}", csarUUID);
+ validateStatus = validateTOSCAMetadataFile(csar, csarUUID, componentsUtils);
+ if (validateStatus.isRight()) {
+ return Either.right(validateStatus.right().value());
+ }
+ return Either.left(true);
+ }
+
+ private static void removeNonUniqueArtifactsFromCsar(Map<String, byte[]> csar) {
+
+ List<String> nonUniqueArtifactsToRemove = new ArrayList<>();
+ String[] paths = csar.keySet().toArray(new String[csar.keySet().size()]);
+ int numberOfArtifacts = paths.length;
+ for(int i = 0; i < numberOfArtifacts; ++i ){
+ collectNonUniqueArtifact(paths, i, numberOfArtifacts, nonUniqueArtifactsToRemove);
+ }
+ nonUniqueArtifactsToRemove.stream().forEach(path->csar.remove(path));
+ }
+
+ private static void collectNonUniqueArtifact( String[] paths, int currInd, int numberOfArtifacts, List<String> nonUniqueArtifactsToRemove) {
+
+ String[] parsedPath = paths[currInd].split("/");
+ String[] otherParsedPath;
+ int artifactNameInd = parsedPath.length - 1;
+ for(int j = currInd + 1; j < numberOfArtifacts; ++j ){
+ otherParsedPath = paths[j].split("/");
+ if(parsedPath.length == otherParsedPath.length && parsedPath.length > 3 && isEqualArtifactNames(parsedPath, otherParsedPath)){
+ log.error("Can't upload two artifact with the same name {}. The artifact with path {} will be handled, and the artifact with path {} will be ignored. ",
+ parsedPath[artifactNameInd], paths[currInd], paths[j]);
+ nonUniqueArtifactsToRemove.add(paths[j]);
+ }
+ }
+ }
+
+ private static boolean isEqualArtifactNames(String[] parsedPath, String[] otherParsedPath) {
+ boolean isEqualArtifactNames = false;
+ int artifactNameInd = parsedPath.length - 1;
+ int artifactGroupTypeInd = parsedPath.length - 3;
+ String groupType = parsedPath[artifactGroupTypeInd];
+ String artifactName = parsedPath[artifactNameInd];
+ String otherGroupType = otherParsedPath[artifactGroupTypeInd];
+ String otherArtifactName = otherParsedPath[artifactNameInd];
+ String vfcToscaName = parsedPath.length == 5 ? parsedPath[1] : null;
+
+ if(artifactName.equalsIgnoreCase(otherArtifactName) && groupType.equalsIgnoreCase(otherGroupType)){
+ isEqualArtifactNames = vfcToscaName == null ? true : vfcToscaName.equalsIgnoreCase(otherParsedPath[1]);
+ }
+ return isEqualArtifactNames;
+ }
+
+ public static Either<ImmutablePair<String, String>, ResponseFormat> getToscaYaml(Map<String, byte[]> csar, String csarUUID, ComponentsUtils componentsUtils) {
+ Either<Boolean, ResponseFormat> validateStatus = validateIsTOSCAMetadataExist(csar, csarUUID, componentsUtils);
+ if (validateStatus.isRight()) {
+ return Either.right(validateStatus.right().value());
+ }
+ Pattern pattern = Pattern.compile(TOSCA_METADATA_PATH_PATTERN);
+ Optional<String> keyOp = csar.keySet().stream().filter(k -> pattern.matcher(k).matches()).findAny();
+ if(!keyOp.isPresent()){
+ log.debug("TOSCA-Metadata/TOSCA.meta file is not in expected key-value form in csar, csar ID {}", csarUUID);
+ BeEcompErrorManager.getInstance().logInternalDataError("TOSCA-Metadata/TOSCA.meta file not in expected key-value form in CSAR with id " + csarUUID, "CSAR internals are invalid", ErrorSeverity.ERROR);
+ return Either.right(componentsUtils.getResponseFormat(ActionStatus.CSAR_INVALID_FORMAT, csarUUID));
+ }
+ byte[] toscaMetaBytes = csar.get(keyOp.get());
+ Properties props = new Properties();
+ try {
+ String propStr = new String(toscaMetaBytes);
+ props.load(new StringReader(propStr.replace("\\","\\\\")));
+ } catch (IOException e) {
+ log.debug("TOSCA-Metadata/TOSCA.meta file is not in expected key-value form in csar, csar ID {}", csarUUID, e);
+ BeEcompErrorManager.getInstance().logInternalDataError("TOSCA-Metadata/TOSCA.meta file not in expected key-value form in CSAR with id " + csarUUID, "CSAR internals are invalid", ErrorSeverity.ERROR);
+ return Either.right(componentsUtils.getResponseFormat(ActionStatus.CSAR_INVALID_FORMAT, csarUUID));
+ }
+
+ String yamlFileName = props.getProperty(TOSCA_META_ENTRY_DEFINITIONS);
+ String[] ops = yamlFileName.split(DEL_PATTERN);
+ List<String> list = Arrays.asList(ops);
+ String result = list.stream().map(x -> x).collect(Collectors.joining(DEL_PATTERN));
+ keyOp = csar.keySet().stream().filter(k -> Pattern.compile(result).matcher(k).matches()).findAny();
+ if(!keyOp.isPresent()){
+ log.debug("Entry-Definitions entry not found in TOSCA-Metadata/TOSCA.meta file, csar ID {}", csarUUID);
+ BeEcompErrorManager.getInstance().logInternalDataError("Entry-Definitions entry not found in TOSCA-Metadata/TOSCA.meta file in CSAR with id " + csarUUID, "CSAR internals are invalid", ErrorSeverity.ERROR);
+ return Either.right(componentsUtils.getResponseFormat(ActionStatus.YAML_NOT_FOUND_IN_CSAR, csarUUID, yamlFileName));
+ }
+
+ log.trace("Found Entry-Definitions property in TOSCA-Metadata/TOSCA.meta, Entry-Definitions: {}, CSAR id: {}", yamlFileName, csarUUID);
+ byte[] yamlFileBytes = csar.get(yamlFileName);
+ if (yamlFileBytes == null) {
+ log.debug("Entry-Definitions {} file not found in csar, csar ID {}", yamlFileName, csarUUID);
+ BeEcompErrorManager.getInstance().logInternalDataError("Entry-Definitions " + yamlFileName + " file not found in CSAR with id " + csarUUID, "CSAR structure is invalid", ErrorSeverity.ERROR);
+ return Either.right(componentsUtils.getResponseFormat(ActionStatus.YAML_NOT_FOUND_IN_CSAR, csarUUID, yamlFileName));
+ }
+
+ String yamlFileContents = new String(yamlFileBytes);
+
+ return Either.left(new ImmutablePair<String, String>(yamlFileName, yamlFileContents));
+ }
+
+ public static Either<ImmutablePair<String, String>, ResponseFormat> getArtifactsMeta(Map<String, byte[]> csar, String csarUUID, ComponentsUtils componentsUtils) {
+
+ if( !csar.containsKey(CsarUtils.ARTIFACTS_PATH + ARTIFACTS_METADATA_FILE) ) {
+ log.debug("Entry-Definitions entry not found in TOSCA-Metadata/TOSCA.meta file, csar ID {}", csarUUID);
+ BeEcompErrorManager.getInstance().logInternalDataError("Entry-Definitions entry not found in TOSCA-Metadata/TOSCA.meta file in CSAR with id " + csarUUID, "CSAR internals are invalid", ErrorSeverity.ERROR);
+ return Either.right(componentsUtils.getResponseFormat(ActionStatus.YAML_NOT_FOUND_IN_CSAR, csarUUID, ARTIFACTS_METADATA_FILE));
+ }
+
+ log.trace("Found Entry-Definitions property in TOSCA-Metadata/TOSCA.meta, Entry-Definitions: {}, CSAR id: {}", ARTIFACTS_METADATA_FILE, csarUUID);
+ byte[] artifactsMetaBytes = csar.get(CsarUtils.ARTIFACTS_PATH + ARTIFACTS_METADATA_FILE);
+ if (artifactsMetaBytes == null) {
+ log.debug("Entry-Definitions {}{} file not found in csar, csar ID {}", CsarUtils.ARTIFACTS_PATH, ARTIFACTS_METADATA_FILE, csarUUID);
+ BeEcompErrorManager.getInstance().logInternalDataError("Entry-Definitions " + CsarUtils.ARTIFACTS_PATH + ARTIFACTS_METADATA_FILE + " file not found in CSAR with id " + csarUUID, "CSAR structure is invalid", ErrorSeverity.ERROR);
+ return Either.right(componentsUtils.getResponseFormat(ActionStatus.YAML_NOT_FOUND_IN_CSAR, csarUUID, CsarUtils.ARTIFACTS_PATH + ARTIFACTS_METADATA_FILE));
+ }
+
+ String artifactsFileContents = new String(artifactsMetaBytes);
+
+ return Either.left(new ImmutablePair<String, String>(CsarUtils.ARTIFACTS_PATH + ARTIFACTS_METADATA_FILE, artifactsFileContents));
+ }
+
+ public static Either<ImmutablePair<String, byte[]>, ResponseFormat> getArtifactsContent(String csarUUID, Map<String, byte[]> csar, String artifactPath, String artifactName, ComponentsUtils componentsUtils) {
+ if (!csar.containsKey(artifactPath)) {
+ log.debug("Entry-Definitions entry not found in Artifacts/HEAT.meta file, csar ID {}", csarUUID);
+ BeEcompErrorManager.getInstance().logInternalDataError("Entry-Definitions entry not found in TOSCA-Metadata/TOSCA.meta file in CSAR with id " + csarUUID, "CSAR internals are invalid", ErrorSeverity.ERROR);
+ return Either.right(componentsUtils.getResponseFormat(ActionStatus.ARTIFACT_NOT_FOUND_IN_CSAR, CsarUtils.ARTIFACTS_PATH + artifactName, csarUUID));
+ }
+
+ log.trace("Found Entry-Definitions property in Artifacts/HEAT.meta, Entry-Definitions: {}, CSAR id: {}", artifactPath, csarUUID);
+ byte[] artifactFileBytes = csar.get(artifactPath);
+ if (artifactFileBytes == null) {
+ log.debug("Entry-Definitions {}{} file not found in csar, csar ID {}", CsarUtils.ARTIFACTS_PATH, artifactName, csarUUID);
+ BeEcompErrorManager.getInstance().logInternalDataError("Entry-Definitions " + artifactPath + " file not found in CSAR with id " + csarUUID, "CSAR structure is invalid", ErrorSeverity.ERROR);
+ return Either.right(componentsUtils.getResponseFormat(ActionStatus.ARTIFACT_NOT_FOUND_IN_CSAR, artifactPath, csarUUID));
+ }
+
+ return Either.left(new ImmutablePair<String, byte[]>(artifactName, artifactFileBytes));
+ }
+
+ private static Either<Boolean, ResponseFormat> validateTOSCAMetadataFile(Map<String, byte[]> csar, String csarUUID, ComponentsUtils componentsUtils) {
+
+ Pattern pattern = Pattern.compile(TOSCA_METADATA_PATH_PATTERN);
+ Optional<String> keyOp = csar.keySet().stream().filter(k -> pattern.matcher(k).matches()).findAny();
+ if(!keyOp.isPresent()){
+ log.debug("TOSCA-Metadata/TOSCA.meta file is not in expected key-value form in csar, csar ID {}", csarUUID);
+ BeEcompErrorManager.getInstance().logInternalDataError("TOSCA-Metadata/TOSCA.meta file not in expected key-value form in CSAR with id " + csarUUID, "CSAR internals are invalid", ErrorSeverity.ERROR);
+ return Either.right(componentsUtils.getResponseFormat(ActionStatus.CSAR_INVALID_FORMAT, csarUUID));
+ }
+
+ byte[] toscaMetaBytes = csar.get(keyOp.get());
+ String toscaMetadata = new String(toscaMetaBytes);
+ String[] splited = toscaMetadata.split(NEW_LINE_DELM);
+ if (splited == null || splited.length < TOSCA_METADATA_FIELDS.length) {
+ log.debug("TOSCA-Metadata/TOSCA.meta file is not in expected key-value form in csar, csar ID {}", csarUUID);
+ BeEcompErrorManager.getInstance().logInternalDataError("TOSCA-Metadata/TOSCA.meta file not in expected key-value form in CSAR with id " + csarUUID, "CSAR internals are invalid", ErrorSeverity.ERROR);
+ return Either.right(componentsUtils.getResponseFormat(ActionStatus.CSAR_INVALID_FORMAT, csarUUID));
+ }
+
+ Either<Boolean, ResponseFormat> block_0Status = validateBlock_0(csarUUID, splited, componentsUtils);
+ if (block_0Status.isRight()) {
+ return Either.right(block_0Status.right().value());
+ }
+
+ return Either.left(true);
+
+ }
+
+ private static Either<Boolean, ResponseFormat> validateBlock_0(String csarUUID, String[] splited, ComponentsUtils componentsUtils) {
+ int index = 0;
+ for (String toscaField : TOSCA_METADATA_FIELDS) {
+
+ Properties props = new Properties();
+
+ try {
+ props.load(new ByteArrayInputStream(splited[index].getBytes()));
+ } catch (IOException e) {
+ log.debug("TOSCA-Metadata/TOSCA.meta file is not in expected key-value form in csar, csar ID {}", csarUUID, e);
+ BeEcompErrorManager.getInstance().logInternalDataError("TOSCA-Metadata/TOSCA.meta file not in expected key-value form in CSAR with id " + csarUUID, "CSAR internals are invalid", ErrorSeverity.ERROR);
+ return Either.right(componentsUtils.getResponseFormat(ActionStatus.CSAR_INVALID_FORMAT, csarUUID));
+ }
+ if (!props.containsKey(toscaField)) {
+ log.debug("TOSCA.meta file format is invalid: No new line after block_0 as expected in csar, csar ID {}", csarUUID);
+ BeEcompErrorManager.getInstance().logInternalDataError("TOSCA-Metadata/TOSCA.meta file not in expected key-value form in CSAR with id " + csarUUID, "CSAR internals are invalid", ErrorSeverity.ERROR);
+ return Either.right(componentsUtils.getResponseFormat(ActionStatus.CSAR_INVALID_FORMAT, csarUUID));
+ }
+ String value = props.getProperty(toscaField);
+ if (value == null || value.isEmpty()) {
+ log.debug("TOSCA-Metadata/TOSCA.meta file is not in expected key-value form in csar, csar ID {}", csarUUID);
+ BeEcompErrorManager.getInstance().logInternalDataError("TOSCA-Metadata/TOSCA.meta file not in expected key-value form in CSAR with id " + csarUUID, "CSAR internals are invalid", ErrorSeverity.ERROR);
+ return Either.right(componentsUtils.getResponseFormat(ActionStatus.CSAR_INVALID_FORMAT, csarUUID));
+ }
+
+ // TOSCA-Meta-File-Version & CSAR-Version : digit.digit - format
+ // validation
+ if (toscaField.equals(TOSCA_META_FILE_VERSION) || toscaField.equals(CSAR_VERSION)) {
+ if (!validateTOSCAMetaProperty(value)) {
+ log.debug("TOSCA-Metadata/TOSCA.meta file contains {} in wrong format (digit.digit), csar ID {}", toscaField, csarUUID);
+ BeEcompErrorManager.getInstance().logInternalDataError("TOSCA-Metadata/TOSCA.meta file not in expected key-value form in CSAR with id " + csarUUID, "CSAR internals are invalid", ErrorSeverity.ERROR);
+ return Either.right(componentsUtils.getResponseFormat(ActionStatus.CSAR_INVALID_FORMAT, csarUUID));
+ }
+ }
+ index++;
+ }
+ return Either.left(true);
+ }
+
+ private static boolean validateTOSCAMetaProperty(String toscaProperty) {
+ final String FLOAT_STRING = "^\\d{1}[.]\\d{1}$";
+ final Pattern FLOAT_PATTERN = Pattern.compile(FLOAT_STRING);
+
+ Matcher floatMatcher = FLOAT_PATTERN.matcher(toscaProperty);
+ return floatMatcher.matches();
+ }
+
+ private static Either<Boolean, ResponseFormat> validateIsTOSCAMetadataExist(Map<String, byte[]> csar, String csarUUID, ComponentsUtils componentsUtils) {
+ if (csar == null || csar.isEmpty()) {
+ log.debug("Error when fetching csar with ID {}", csarUUID);
+ BeEcompErrorManager.getInstance().logBeDaoSystemError("Creating resource from CSAR: fetching CSAR with id " + csarUUID + " failed");
+ ResponseFormat responseFormat = componentsUtils.getResponseFormat(ActionStatus.CSAR_INVALID, csarUUID);
+ return Either.right(responseFormat);
+ }
+
+ Pattern pattern = Pattern.compile(TOSCA_METADATA_PATH_PATTERN);
+ Optional<String> keyOp = csar.keySet().stream().filter(k -> pattern.matcher(k).matches()).findAny();
+ if(!keyOp.isPresent()){
+
+ log.debug("TOSCA-Metadata/TOSCA.meta file not found in csar, csar ID {}", csarUUID);
+ BeEcompErrorManager.getInstance().logInternalDataError("TOSCA-Metadata/TOSCA.meta file not found in CSAR with id " + csarUUID, "CSAR structure is invalid", ErrorSeverity.ERROR);
+ return Either.right(componentsUtils.getResponseFormat(ActionStatus.CSAR_INVALID, csarUUID));
+ }
+ byte[] toscaMetaBytes = csar.get(keyOp.get());
+ // && exchanged for ||
+ if (toscaMetaBytes == null || toscaMetaBytes.length == 0) {
+ log.debug("TOSCA-Metadata/TOSCA.meta file not found in csar, csar ID {}", csarUUID);
+ BeEcompErrorManager.getInstance().logInternalDataError("TOSCA-Metadata/TOSCA.meta file not found in CSAR with id " + csarUUID, "CSAR structure is invalid", ErrorSeverity.ERROR);
+ return Either.right(componentsUtils.getResponseFormat(ActionStatus.CSAR_INVALID, csarUUID));
+ }
+
+ return Either.left(Boolean.TRUE);
+ }
+
+ public static Either<String, ResponseFormat> getToscaYamlChecksum(Map<String, byte[]> csar, String csarUUID, ComponentsUtils componentsUtils) {
+
+ Either<ImmutablePair<String, String>, ResponseFormat> toscaYamlRes = getToscaYaml(csar, csarUUID, componentsUtils);
+ if (toscaYamlRes.isRight() || toscaYamlRes.left().value() == null || toscaYamlRes.left().value().getRight() == null) {
+ log.debug("Faild to create toscaYamlChecksum for csar, csar ID {}", csarUUID);
+ return Either.right(toscaYamlRes.right().value());
+ }
+
+ String newCheckSum = GeneralUtility.calculateMD5Base64EncodedByByteArray(toscaYamlRes.left().value().getRight().getBytes());
+ return Either.left(newCheckSum);
+
+ }
+
+ public static boolean isCsarPayloadName(String payloadName) {
+ if (payloadName == null)
+ return false;
+ return payloadName.toLowerCase().endsWith(TOSCA_CSAR_EXTENSION);
+ }
}