2 * Copyright © 2016-2018 European Support Limited
3 * Modifications copyright (c) 2021 Nokia
5 * Licensed under the Apache License, Version 2.0 (the "License");
6 * you may not use this file except in compliance with the License.
7 * You may obtain a copy of the License at
9 * http://www.apache.org/licenses/LICENSE-2.0
11 * Unless required by applicable law or agreed to in writing, software
12 * distributed under the License is distributed on an "AS IS" BASIS,
13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 * See the License for the specific language governing permissions and
15 * limitations under the License.
18 package org.openecomp.sdc.vendorsoftwareproduct.services.impl.filedatastructuremodule;
20 import static org.openecomp.core.validation.errors.ErrorMessagesFormatBuilder.getErrorWithParameters;
22 import java.io.ByteArrayInputStream;
23 import java.io.ByteArrayOutputStream;
24 import java.io.IOException;
25 import java.io.InputStream;
26 import java.nio.ByteBuffer;
27 import java.nio.charset.StandardCharsets;
28 import java.util.ArrayList;
29 import java.util.HashSet;
30 import java.util.List;
32 import java.util.Objects;
33 import java.util.Optional;
35 import java.util.stream.Collectors;
36 import java.util.zip.ZipEntry;
37 import java.util.zip.ZipInputStream;
38 import java.util.zip.ZipOutputStream;
39 import org.apache.commons.collections4.CollectionUtils;
40 import org.openecomp.core.utilities.file.FileContentHandler;
41 import org.openecomp.core.utilities.json.JsonUtil;
42 import org.openecomp.core.utilities.orchestration.OnboardingTypesEnum;
43 import org.openecomp.sdc.common.errors.CoreException;
44 import org.openecomp.sdc.common.errors.ErrorCategory;
45 import org.openecomp.sdc.common.errors.ErrorCode;
46 import org.openecomp.sdc.common.errors.Messages;
47 import org.openecomp.sdc.common.utils.SdcCommon;
48 import org.openecomp.sdc.common.zip.ZipUtils;
49 import org.openecomp.sdc.common.zip.exception.ZipSlipException;
50 import org.openecomp.sdc.datatypes.error.ErrorLevel;
51 import org.openecomp.sdc.datatypes.error.ErrorMessage;
52 import org.openecomp.sdc.heat.datatypes.manifest.FileData;
53 import org.openecomp.sdc.heat.datatypes.manifest.ManifestContent;
54 import org.openecomp.sdc.heat.datatypes.structure.Artifact;
55 import org.openecomp.sdc.heat.datatypes.structure.HeatStructureTree;
56 import org.openecomp.sdc.heat.datatypes.structure.ValidationStructureList;
57 import org.openecomp.sdc.vendorsoftwareproduct.dao.OrchestrationTemplateCandidateDao;
58 import org.openecomp.sdc.vendorsoftwareproduct.dao.OrchestrationTemplateCandidateDaoFactory;
59 import org.openecomp.sdc.vendorsoftwareproduct.dao.type.OrchestrationTemplateCandidateData;
60 import org.openecomp.sdc.vendorsoftwareproduct.dao.type.VspDetails;
61 import org.openecomp.sdc.vendorsoftwareproduct.errors.utils.ErrorsUtil;
62 import org.openecomp.sdc.vendorsoftwareproduct.services.HeatFileAnalyzer;
63 import org.openecomp.sdc.vendorsoftwareproduct.services.filedatastructuremodule.CandidateService;
64 import org.openecomp.sdc.vendorsoftwareproduct.services.filedatastructuremodule.ManifestCreator;
65 import org.openecomp.sdc.vendorsoftwareproduct.services.utils.CandidateServiceValidator;
66 import org.openecomp.sdc.vendorsoftwareproduct.types.CandidateDataEntityTo;
67 import org.openecomp.sdc.vendorsoftwareproduct.types.candidateheat.AnalyzedZipHeatFiles;
68 import org.openecomp.sdc.vendorsoftwareproduct.types.candidateheat.FilesDataStructure;
69 import org.openecomp.sdc.vendorsoftwareproduct.types.candidateheat.Module;
70 import org.openecomp.sdc.versioning.dao.types.Version;
71 import org.slf4j.Logger;
72 import org.slf4j.LoggerFactory;
74 public class CandidateServiceImpl implements CandidateService {
75 private static final Logger logger = LoggerFactory.getLogger(CandidateServiceImpl.class);
76 private CandidateServiceValidator candidateServiceValidator = new CandidateServiceValidator();
77 private ManifestCreator manifestCreator;
78 private OrchestrationTemplateCandidateDao orchestrationTemplateCandidateDao;
80 public CandidateServiceImpl(ManifestCreator manifestCreator,
81 OrchestrationTemplateCandidateDao orchestrationTemplateCandidateDao) {
82 this.manifestCreator = manifestCreator;
83 this.orchestrationTemplateCandidateDao = orchestrationTemplateCandidateDao;
86 public CandidateServiceImpl() {
90 public Optional<ErrorMessage> validateNonEmptyFileToUpload(InputStream fileToUpload,
93 getErrorWithParameters(Messages.NO_FILE_WAS_UPLOADED_OR_FILE_NOT_EXIST.getErrorMessage(),
96 if (Objects.isNull(fileToUpload)) {
97 return Optional.of(new ErrorMessage(ErrorLevel.ERROR,
101 int available = fileToUpload.available();
102 if (available == 0) {
103 return Optional.of(new ErrorMessage(ErrorLevel.ERROR,
106 } catch (IOException e) {
107 logger.debug(e.getMessage(), e);
108 return Optional.of(new ErrorMessage(ErrorLevel.ERROR,
112 return Optional.empty();
116 public Optional<ErrorMessage> validateRawZipData(String fileSuffix,
117 byte[] uploadedFileData) {
118 if (Objects.isNull(uploadedFileData)) {
119 return Optional.of(new ErrorMessage(ErrorLevel.ERROR,
120 getErrorWithParameters(Messages.NO_FILE_WAS_UPLOADED_OR_FILE_NOT_EXIST.getErrorMessage(),
123 return Optional.empty();
126 private String heatStructureTreeToFileDataStructure(HeatStructureTree tree,
127 FileContentHandler zipContentMap,
128 Map<String, List<ErrorMessage>> uploadErrors,
129 AnalyzedZipHeatFiles analyzedZipHeatFiles) {
130 FilesDataStructure structure = new FilesDataStructure();
131 Set<String> usedEnvFiles = new HashSet<>();
132 addHeatsToFileDataStructure(tree, usedEnvFiles, structure, uploadErrors,
133 analyzedZipHeatFiles);
134 handleOtherResources(tree, usedEnvFiles, structure);
135 FilesDataStructure fileDataStructureFromManifest =
136 createFileDataStructureFromManifest(zipContentMap.getFileContentAsStream(SdcCommon.MANIFEST_NAME));
137 List<String> structureArtifacts = structure.getArtifacts();
138 structureArtifacts.addAll(fileDataStructureFromManifest.getArtifacts().stream().filter
139 (artifact -> isNotStrctureArtifact(structureArtifacts, artifact))
140 .collect(Collectors.toList()));
141 handleArtifactsFromTree(tree, structure);
143 return JsonUtil.object2Json(structure);
146 private boolean isNotStrctureArtifact(List<String> structureArtifacts, String artifact) {
147 return !structureArtifacts.contains(artifact);
151 public OrchestrationTemplateCandidateData createCandidateDataEntity(
152 CandidateDataEntityTo candidateDataEntityTo, InputStream zipFileManifest,
153 AnalyzedZipHeatFiles analyzedZipHeatFiles) {
154 FileContentHandler zipContentMap = candidateDataEntityTo.getContentMap();
155 FilesDataStructure filesDataStructure;
156 String dataStructureJson;
158 if (zipFileManifest != null) {
159 // create data structure from manifest
160 filesDataStructure = createFileDataStructureFromManifest(zipFileManifest);
161 Set<String> zipFileList = zipContentMap.getFileList();
162 balanceManifestFilesWithZipFiles(filesDataStructure,
163 zipContentMap, analyzedZipHeatFiles);
164 Set<String> filesDataStructureFiles = getFlatFileNames(filesDataStructure);
165 filesDataStructure.getUnassigned().addAll(zipFileList.stream()
166 .filter(fileName -> (!filesDataStructureFiles.contains(fileName)
167 && !filesDataStructure.getNested().contains(fileName)
168 && !fileName.equals(SdcCommon.MANIFEST_NAME)))
169 .collect(Collectors.toList()));
170 dataStructureJson = JsonUtil.object2Json(filesDataStructure);
172 // create data structure from based on naming convention
174 heatStructureTreeToFileDataStructure(candidateDataEntityTo.getTree(), zipContentMap,
175 candidateDataEntityTo.getErrors(), analyzedZipHeatFiles);
178 OrchestrationTemplateCandidateData candidateData = new OrchestrationTemplateCandidateData();
179 candidateData.setContentData(ByteBuffer.wrap(candidateDataEntityTo.getUploadedFileData()));
180 candidateData.setFilesDataStructure(dataStructureJson);
181 return candidateData;
184 private void balanceManifestFilesWithZipFiles(
185 FilesDataStructure filesDataStructure,
186 FileContentHandler fileContentHandler, AnalyzedZipHeatFiles analyzedZipHeatFiles) {
187 Set<String> zipFileList = fileContentHandler.getFileList();
188 filesDataStructure.getNested().addAll(analyzedZipHeatFiles.getNestedFiles());
189 List<Module> modules = filesDataStructure.getModules();
190 if (CollectionUtils.isEmpty(modules)) {
194 for (int i = 0; i < modules.size(); i++) {
195 Module module = modules.get(i);
196 if (!isFileExistInZipContains(zipFileList, module.getYaml())) {
197 addFileToUnassigned(filesDataStructure, zipFileList, module.getEnv());
198 addFileToUnassigned(filesDataStructure, zipFileList, module.getVol());
199 addFileToUnassigned(filesDataStructure, zipFileList, module.getVolEnv());
201 } else if (Objects.nonNull(module.getVol()) && !zipFileList.contains(module.getVol())) {
204 .addIgnoreNull(filesDataStructure.getUnassigned(), module.getVolEnv());
206 if (filesDataStructure.getNested().contains(module.getYaml())) {
207 moveModuleFileToNested(filesDataStructure, i--, module);
213 private void addFileToUnassigned(FilesDataStructure filesDataStructure, Set<String> zipFileList,
215 if (isFileExistInZipContains(zipFileList, fileName)) {
216 filesDataStructure.getUnassigned().add(fileName);
220 private boolean isFileExistInZipContains(Set<String> zipFileList, String fileName) {
221 return Objects.nonNull(fileName) && zipFileList.contains(fileName);
224 private void moveModuleFileToNested(FilesDataStructure filesDataStructure, int i,
226 if (!filesDataStructure.getNested().contains(module.getYaml())) {
227 filesDataStructure.getNested().add(module.getYaml());
229 if (Objects.nonNull(module.getEnv())) {
230 filesDataStructure.getNested().add(module.getEnv());
232 if (Objects.nonNull(module.getVol())) {
233 filesDataStructure.getNested().add(module.getVol());
235 if (Objects.nonNull(module.getVolEnv())) {
236 filesDataStructure.getNested().add(module.getVolEnv());
238 filesDataStructure.getModules().remove(i);
241 private Set<String> getFlatFileNames(FilesDataStructure filesDataStructure) {
242 Set<String> fileNames = new HashSet<>();
243 if (!CollectionUtils.isEmpty(filesDataStructure.getModules())) {
244 for (Module module : filesDataStructure.getModules()) {
245 CollectionUtils.addIgnoreNull(fileNames, module.getEnv());
246 CollectionUtils.addIgnoreNull(fileNames, module.getVol());
247 CollectionUtils.addIgnoreNull(fileNames, module.getVolEnv());
248 CollectionUtils.addIgnoreNull(fileNames, module.getYaml());
251 fileNames.addAll(filesDataStructure.getArtifacts());
252 fileNames.addAll(filesDataStructure.getNested());
253 fileNames.addAll(filesDataStructure.getUnassigned());
258 private FilesDataStructure createFileDataStructureFromManifest(InputStream isManifestContent) {
259 ManifestContent manifestContent =
260 JsonUtil.json2Object(isManifestContent, ManifestContent.class);
261 FilesDataStructure structure = new FilesDataStructure();
262 for (FileData fileData : manifestContent.getData()) {
263 if (Objects.nonNull(fileData.getType()) &&
264 fileData.getType().equals(FileData.Type.HEAT)) {
265 Module module = new Module();
266 module.setType(FileData.Type.HEAT);
267 module.setYaml(fileData.getFile());
268 module.setIsBase(fileData.getBase());
269 addHeatDependenciesToModule(module, fileData.getData());
270 structure.getModules().add(module);
271 }else if (Objects.nonNull(fileData.getType()) &&
272 fileData.getType().equals(FileData.Type.HELM)) {
273 Module module = new Module();
274 module.setType(FileData.Type.HELM);
275 module.setYaml(fileData.getFile());
276 module.setIsBase(fileData.getBase());
277 structure.getModules().add(module);
279 else if (HeatFileAnalyzer.isYamlOrEnvFile(fileData.getFile()) &&
280 !FileData.Type.isArtifact(fileData.getType())) {
281 structure.getUnassigned().add(fileData.getFile());
283 structure.getArtifacts().add(fileData.getFile());
289 private void addHeatDependenciesToModule(Module module, List<FileData> data) {
290 if (CollectionUtils.isEmpty(data)) {
294 for (FileData fileData : data) {
295 if (fileData.getType().equals(FileData.Type.HEAT_ENV)) {
296 module.setEnv(fileData.getFile());
297 } else if (fileData.getType().equals(FileData.Type.HEAT_VOL)) { // must be volume
298 module.setVol(fileData.getFile());
299 if (!CollectionUtils.isEmpty(fileData.getData())) {
300 FileData volEnv = fileData.getData().get(0);
301 if (volEnv.getType().equals(FileData.Type.HEAT_ENV)) {
302 module.setVolEnv(volEnv.getFile());
304 throw new CoreException((new ErrorCode.ErrorCodeBuilder())
305 .withMessage(Messages.ILLEGAL_MANIFEST.getErrorMessage())
306 .withId(Messages.ILLEGAL_MANIFEST.getErrorMessage())
307 .withCategory(ErrorCategory.APPLICATION).build());
311 throw new CoreException((new ErrorCode.ErrorCodeBuilder())
312 .withMessage(Messages.FILE_TYPE_NOT_LEGAL.getErrorMessage())
313 .withId(Messages.FILE_TYPE_NOT_LEGAL.getErrorMessage())
314 .withCategory(ErrorCategory.APPLICATION).build());
320 public void updateCandidateUploadData(final String vspId, final Version version,
321 final OrchestrationTemplateCandidateData uploadData) {
322 orchestrationTemplateCandidateDao.update(vspId, version, uploadData);
326 public Optional<FilesDataStructure> getOrchestrationTemplateCandidateFileDataStructure(
327 String vspId, Version version) {
328 Optional<String> jsonFileDataStructure =
329 orchestrationTemplateCandidateDao.getStructure(vspId, version);
331 if (jsonFileDataStructure.isPresent() && JsonUtil.isValidJson(jsonFileDataStructure.get())) {
333 .of(JsonUtil.json2Object(jsonFileDataStructure.get(), FilesDataStructure.class));
335 return Optional.empty();
340 public void updateOrchestrationTemplateCandidateFileDataStructure(String vspId, Version version,
341 FilesDataStructure fileDataStructure) {
342 OrchestrationTemplateCandidateDaoFactory.getInstance().createInterface()
343 .updateStructure(vspId, version, fileDataStructure);
347 public Optional<OrchestrationTemplateCandidateData> getOrchestrationTemplateCandidate(String vspId,
349 return orchestrationTemplateCandidateDao.get(vspId, version);
353 public Optional<OrchestrationTemplateCandidateData> getOrchestrationTemplateCandidateInfo(
356 return orchestrationTemplateCandidateDao.getInfo(vspId, version);
360 public String createManifest(VspDetails vspDetails, FilesDataStructure structure) {
361 return JsonUtil.object2Json(manifestCreator.createManifest(vspDetails, structure)
362 .orElseThrow(() -> new CoreException(new ErrorCode.ErrorCodeBuilder()
363 .withMessage(Messages.CREATE_MANIFEST_FROM_ZIP.getErrorMessage()).build())));
367 public String createManifestFromExisting(VspDetails vspDetails, FilesDataStructure structure, ManifestContent existingManifest) {
368 return JsonUtil.object2Json(manifestCreator.createManifestFromExisting(vspDetails, structure, existingManifest)
369 .orElseThrow(() -> new CoreException(new ErrorCode.ErrorCodeBuilder()
370 .withMessage(Messages.CREATE_MANIFEST_FROM_ZIP.getErrorMessage()).build())));
374 public Optional<ManifestContent> createManifest(VspDetails vspDetails,
375 FileContentHandler fileContentHandler,
376 AnalyzedZipHeatFiles analyzedZipHeatFiles) {
377 return manifestCreator.createManifest(vspDetails, fileContentHandler, analyzedZipHeatFiles);
381 public Optional<ByteArrayInputStream> fetchZipFileByteArrayInputStream(String vspId,
382 OrchestrationTemplateCandidateData candidateDataEntity,
384 OnboardingTypesEnum type,
385 Map<String, List<ErrorMessage>> uploadErrors) {
387 ByteArrayInputStream byteArrayInputStream = null;
389 file = replaceManifestInZip(candidateDataEntity.getContentData(), manifest, type);
390 byteArrayInputStream = new ByteArrayInputStream(
391 Objects.isNull(file) ? candidateDataEntity.getContentData().array()
393 } catch (IOException e) {
394 ErrorMessage errorMessage =
395 new ErrorMessage(ErrorLevel.ERROR,
396 Messages.CANDIDATE_PROCESS_FAILED.getErrorMessage());
397 logger.error(errorMessage.getMessage(), e);
399 .addStructureErrorToErrorMap(SdcCommon.UPLOAD_FILE, errorMessage, uploadErrors);
401 return Optional.ofNullable(byteArrayInputStream);
405 public byte[] replaceManifestInZip(ByteBuffer contentData, String manifest,
406 OnboardingTypesEnum type)
408 ByteArrayOutputStream baos = new ByteArrayOutputStream();
410 try (final ZipOutputStream zos = new ZipOutputStream(baos);
411 ZipInputStream zipStream = new ZipInputStream(
412 new ByteArrayInputStream(contentData.array()))) {
414 boolean manifestWritten = false;
415 while ((zipEntry = zipStream.getNextEntry()) != null) {
416 if (!zipEntry.getName().equalsIgnoreCase(SdcCommon.MANIFEST_NAME)) {
417 ZipEntry loc_ze = new ZipEntry(zipEntry.getName());
418 zos.putNextEntry(loc_ze);
419 byte[] buf = new byte[1024];
421 while ((len = zipStream.read(buf)) > 0) {
422 zos.write(buf, 0, (len < buf.length) ? len : buf.length);
425 manifestWritten = true;
426 writeManifest(manifest, type, zos);
430 if (!manifestWritten) {
431 writeManifest(manifest, type, zos);
435 return baos.toByteArray();
439 public byte[] getZipData(ByteBuffer contentData)
441 ByteArrayOutputStream baos = new ByteArrayOutputStream();
443 try (final ZipOutputStream zos = new ZipOutputStream(baos);
444 ZipInputStream zipStream = new ZipInputStream(
445 new ByteArrayInputStream(contentData.array()))) {
447 while ((zipEntry = zipStream.getNextEntry()) != null) {
449 ZipUtils.checkForZipSlipInRead(zipEntry);
450 } catch (ZipSlipException e) {
451 throw new IOException(e);
453 ZipEntry locZipEntry = new ZipEntry(zipEntry.getName());
454 zos.putNextEntry(locZipEntry);
455 byte[] buf = new byte[1024];
457 while ((len = zipStream.read(buf)) > 0) {
458 zos.write(buf, 0, (len < buf.length) ? len : buf.length);
463 return baos.toByteArray();
467 public Optional<List<ErrorMessage>> validateFileDataStructure(
468 FilesDataStructure filesDataStructure) {
469 return candidateServiceValidator.validateFileDataStructure(filesDataStructure);
473 public void deleteOrchestrationTemplateCandidate(String vspId, Version versionId) {
474 orchestrationTemplateCandidateDao.delete(vspId, versionId);
478 public void updateValidationData(String vspId, Version version, ValidationStructureList
480 orchestrationTemplateCandidateDao.updateValidationData(vspId, version, validationData);
483 private void writeManifest(String manifest,
484 OnboardingTypesEnum type,
485 ZipOutputStream zos) throws IOException {
487 if (isManifestNeedsToGetWritten(type)) {
491 zos.putNextEntry(new ZipEntry(SdcCommon.MANIFEST_NAME));
492 try (InputStream manifestStream = new ByteArrayInputStream(
493 manifest.getBytes(StandardCharsets.UTF_8))) {
494 byte[] buf = new byte[1024];
496 while ((len = (manifestStream.read(buf))) > 0) {
497 zos.write(buf, 0, (len < buf.length) ? len : buf.length);
502 private boolean isManifestNeedsToGetWritten(OnboardingTypesEnum type) {
503 return type.equals(OnboardingTypesEnum.CSAR);
506 private void handleArtifactsFromTree(HeatStructureTree tree, FilesDataStructure structure) {
508 if (Objects.isNull(tree) || Objects.isNull(tree.getArtifacts())) {
512 if (CollectionUtils.isNotEmpty(tree.getArtifacts())) {
513 structure.getArtifacts().addAll(
516 .map(Artifact::getFileName)
517 .filter(fileName -> !structure.getArtifacts().contains(fileName))
518 .collect(Collectors.toList()));
522 private void handleOtherResources(HeatStructureTree tree, Set<String> usedEnvFiles,
523 FilesDataStructure structure) {
524 Set<HeatStructureTree> others = tree.getOther();
525 if (Objects.isNull(others)) {
529 List<String> artifacts = new ArrayList<>();
530 List<String> unassigned = new ArrayList<>();
531 for (HeatStructureTree other : others) {
532 if (HeatFileAnalyzer.isYamlOrEnvFile(other.getFileName())) {
533 if (isEnvFileUsedByHeatFile(usedEnvFiles, other)) {
536 unassigned.add(other.getFileName());
538 artifacts.add(other.getFileName());
540 handleArtifactsFromTree(other, structure);
542 structure.getArtifacts().addAll(artifacts);
543 structure.getUnassigned().addAll(unassigned);
546 private boolean isEnvFileUsedByHeatFile(Set<String> usedEnvFiles, HeatStructureTree other) {
547 return HeatFileAnalyzer.isEnvFile(other.getFileName()) &&
548 usedEnvFiles.contains(other.getFileName());
551 private void addHeatsToFileDataStructure(HeatStructureTree tree, Set<String> usedEnvFiles,
552 FilesDataStructure structure,
553 Map<String, List<ErrorMessage>> uploadErrors,
554 AnalyzedZipHeatFiles analyzedZipHeatFiles) {
555 List<Module> modules = new ArrayList<>();
556 Set<HeatStructureTree> heatsSet = tree.getHeat();
557 if (Objects.isNull(heatsSet)) {
560 for (HeatStructureTree heat : heatsSet) {
561 if (isFileBaseFile(heat.getFileName())) {
562 handleSingleHeat(structure, modules, heat, uploadErrors);
563 } else if (isFileModuleFile(heat.getFileName(),
564 analyzedZipHeatFiles.getModuleFiles())) {
565 handleSingleHeat(structure, modules, heat, uploadErrors);
567 structure.getUnassigned().add(heat.getFileName());
568 addNestedToFileDataStructure(heat, structure);
570 if (!Objects.isNull(heat.getEnv())) {
571 usedEnvFiles.add(heat.getEnv() == null ? null : heat.getEnv().getFileName());
574 structure.setModules(modules);
578 private boolean isFileModuleFile(String fileName, Set<String> modulesFileNames) {
579 return modulesFileNames.contains(fileName);
582 private boolean isFileBaseFile(String fileName) {
583 return manifestCreator.isFileBaseFile(fileName);
586 private void handleSingleHeat(FilesDataStructure structure, List<Module> modules,
587 HeatStructureTree heat,
588 Map<String, List<ErrorMessage>> uploadErrors) {
589 Module module = new Module();
590 module.setYaml(heat.getFileName());
591 module.setIsBase(heat.getBase());
592 addNestedToFileDataStructure(heat, structure);
593 Set<HeatStructureTree> volumeSet = heat.getVolume();
595 if (Objects.nonNull(volumeSet)) {
596 handleVolumes(module, volumeSet, structure, inx, uploadErrors);
598 handleEnv(module, heat, false, structure);
602 private void handleVolumes(Module module, Set<HeatStructureTree> volumeSet,
603 FilesDataStructure structure, int inx,
604 Map<String, List<ErrorMessage>> uploadErrors) {
605 for (HeatStructureTree volume : volumeSet) {
606 Objects.requireNonNull(volume, "volume cannot be null!");
608 ErrorsUtil.addStructureErrorToErrorMap(SdcCommon.UPLOAD_FILE,
609 new ErrorMessage(ErrorLevel.WARNING,
610 Messages.MORE_THEN_ONE_VOL_FOR_HEAT.getErrorMessage()), uploadErrors);
613 handleArtifactsFromTree(volume, structure);
614 module.setVol(volume.getFileName());
615 handleEnv(module, volume, true, structure);
616 addNestedToFileDataStructure(volume, structure);
620 private void handleEnv(Module module, HeatStructureTree tree, boolean isVolEnv,
621 FilesDataStructure structure) {
622 if (Objects.nonNull(tree.getEnv())) {
624 module.setVolEnv(tree.getEnv().getFileName());
626 module.setEnv(tree.getEnv().getFileName());
628 handleArtifactsFromTree(tree.getEnv(), structure);
632 private void addNestedToFileDataStructure(HeatStructureTree heat,
633 FilesDataStructure structure) {
634 Set<HeatStructureTree> nestedSet = heat.getNested();
635 if (Objects.isNull(nestedSet)) {
638 for (HeatStructureTree nested : nestedSet) {
639 if (structure.getNested().contains(nested.getFileName())) {
642 structure.getNested().add(nested.getFileName());
643 if (CollectionUtils.isNotEmpty(nested.getArtifacts())) {
644 handleArtifactsFromTree(nested, structure);
646 addNestedToFileDataStructure(nested, structure);