RED-9771 - Fixes for updating component mappings
This commit is contained in:
parent
66f1a86c77
commit
0f15e68623
@ -249,6 +249,36 @@ public class DossierTemplateControllerV2 implements DossierTemplateResource {
|
||||
|
||||
dossierTemplatePersistenceService.checkDossierTemplateExistsOrElseThrow404(dossierTemplateId);
|
||||
|
||||
String nameToUse = validateFileName(file, name);
|
||||
|
||||
if (Strings.isNullOrEmpty(delimiter)) {
|
||||
throw new BadRequestException("The provided delimiter is not valid! Can't be null or empty.");
|
||||
} else if (delimiter.length() != 1) {
|
||||
throw new BadRequestException(format("The provided delimiter %s is not valid! Only a single character is allowed.", delimiter));
|
||||
}
|
||||
char cleanDelimiter = delimiter.charAt(0);
|
||||
|
||||
|
||||
Path mappingFile = saveToFile(file);
|
||||
|
||||
try {
|
||||
ComponentMappingMetadata resultMetaData = componentMappingService.update(dossierTemplateId,
|
||||
componentMappingId,
|
||||
nameToUse,
|
||||
encoding,
|
||||
cleanDelimiter,
|
||||
mappingFile.toFile(),
|
||||
file.getOriginalFilename());
|
||||
|
||||
return componentMappingMapper.toModel(resultMetaData);
|
||||
} finally {
|
||||
Files.deleteIfExists(mappingFile);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
private static String validateFileName(MultipartFile file, String name) {
|
||||
|
||||
if (Strings.isNullOrEmpty(file.getOriginalFilename()) || !file.getOriginalFilename().endsWith(".csv")) {
|
||||
throw new BadRequestException(format("File name \"%s\" does not end with .csv", file.getOriginalFilename()));
|
||||
}
|
||||
@ -260,32 +290,7 @@ public class DossierTemplateControllerV2 implements DossierTemplateResource {
|
||||
if (Strings.isNullOrEmpty(nameToUse)) {
|
||||
throw new BadRequestException(format("The provided file name \"%s\" is not valid!", nameToUse));
|
||||
}
|
||||
|
||||
if (Strings.isNullOrEmpty(delimiter)) {
|
||||
throw new BadRequestException("The provided delimiter is not valid! Can't be null or empty.");
|
||||
} else if (delimiter.length() != 1) {
|
||||
throw new BadRequestException(format("The provided delimiter %s is not valid! Only a single character is allowed.", delimiter));
|
||||
}
|
||||
char cleanDelimiter = delimiter.charAt(0);
|
||||
|
||||
if (Strings.isNullOrEmpty(delimiter) || delimiter.length() != 1) {
|
||||
throw new BadRequestException("The provided delimiter is not valid! Only a single character is allowed.");
|
||||
}
|
||||
|
||||
Path mappingFile = saveToFile(file);
|
||||
|
||||
try {
|
||||
ComponentMappingMetadata resultMetaData = componentMappingService.update(dossierTemplateId,
|
||||
componentMappingId,
|
||||
nameToUse,
|
||||
encoding,
|
||||
cleanDelimiter,
|
||||
mappingFile.toFile());
|
||||
|
||||
return componentMappingMapper.toModel(resultMetaData);
|
||||
} finally {
|
||||
Files.deleteIfExists(mappingFile);
|
||||
}
|
||||
return nameToUse;
|
||||
}
|
||||
|
||||
|
||||
|
||||
@ -62,11 +62,11 @@ public class ComponentMappingService {
|
||||
|
||||
|
||||
@SneakyThrows
|
||||
public ComponentMappingMetadata update(String dossierTemplateId, String mappingId, String name, String encoding, char delimiter, File mappingFile) {
|
||||
public ComponentMappingMetadata update(String dossierTemplateId, String mappingId, String name, String encoding, char delimiter, File mappingFile, String fileName) {
|
||||
|
||||
ComponentMappingEntity entity = componentMappingPersistenceService.getEntityById(dossierTemplateId, mappingId);
|
||||
|
||||
return updateOrCreate(entity, name, encoding, delimiter, mappingFile);
|
||||
return updateOrCreate(entity, name, encoding, delimiter, mappingFile, fileName);
|
||||
}
|
||||
|
||||
|
||||
@ -86,13 +86,13 @@ public class ComponentMappingService {
|
||||
.fileName(fileName)
|
||||
.build();
|
||||
|
||||
return updateOrCreate(entity, name, encoding, delimiter, mappingFile);
|
||||
return updateOrCreate(entity, name, encoding, delimiter, mappingFile, fileName);
|
||||
|
||||
}
|
||||
|
||||
|
||||
@SneakyThrows
|
||||
private ComponentMappingMetadata updateOrCreate(ComponentMappingEntity entity, String name, String encoding, char delimiter, File mappingFile) {
|
||||
private ComponentMappingMetadata updateOrCreate(ComponentMappingEntity entity, String name, String encoding, char delimiter, File mappingFile, String fileName) {
|
||||
|
||||
Charset charset = resolveCharset(encoding);
|
||||
|
||||
@ -104,6 +104,7 @@ public class ComponentMappingService {
|
||||
entity.setNumberOfLines(stats.numberOfLines());
|
||||
entity.setColumnLabels(stats.columnLabels());
|
||||
entity.setVersion(entity.getVersion() + 1);
|
||||
entity.setFileName(fileName);
|
||||
|
||||
componentMappingPersistenceService.updateOrCreate(entity.getStorageId(), mappingFile, entity);
|
||||
|
||||
@ -139,6 +140,10 @@ public class ComponentMappingService {
|
||||
|
||||
List<String[]> rows = reader.readAll();
|
||||
|
||||
if (rows.isEmpty()) {
|
||||
throw new BadRequestException("CSV file can not be empty!");
|
||||
}
|
||||
|
||||
columnLabels = rows.remove(0); // remove header row
|
||||
|
||||
if (Arrays.stream(columnLabels)
|
||||
|
||||
@ -0,0 +1,98 @@
|
||||
package com.iqser.red.service.peristence.v1.server.integration.tests;
|
||||
|
||||
import static org.junit.jupiter.api.Assertions.assertEquals;
|
||||
import static org.junit.jupiter.api.Assertions.assertThrows;
|
||||
import static org.junit.jupiter.api.Assertions.assertTrue;
|
||||
import static org.mockito.ArgumentMatchers.anyString;
|
||||
import static org.mockito.Mockito.when;
|
||||
|
||||
import org.apache.commons.io.IOUtils;
|
||||
import org.junit.jupiter.api.Test;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.boot.test.mock.mockito.MockBean;
|
||||
import org.springframework.core.io.ClassPathResource;
|
||||
import org.springframework.data.jpa.repository.config.EnableJpaAuditing;
|
||||
import org.springframework.mock.web.MockMultipartFile;
|
||||
|
||||
import com.iqser.red.service.peristence.v1.server.integration.client.DossierTemplateExternalClient;
|
||||
import com.iqser.red.service.peristence.v1.server.integration.service.DossierTemplateTesterAndProvider;
|
||||
import com.iqser.red.service.peristence.v1.server.integration.service.DossierTesterAndProvider;
|
||||
import com.iqser.red.service.peristence.v1.server.integration.utils.AbstractPersistenceServerServiceTest;
|
||||
import com.iqser.red.service.persistence.management.v1.processor.entity.ComponentMappingEntity;
|
||||
import com.iqser.red.service.persistence.management.v1.processor.entity.dossier.DossierTemplateEntity;
|
||||
import com.iqser.red.service.persistence.management.v1.processor.service.ComponentMappingPersistenceService;
|
||||
import com.iqser.red.service.persistence.service.v2.api.external.model.ComponentMappingMetadataModel;
|
||||
|
||||
import feign.FeignException;
|
||||
import lombok.SneakyThrows;
|
||||
|
||||
@EnableJpaAuditing
|
||||
public class ComponentMappingTest extends AbstractPersistenceServerServiceTest {
|
||||
|
||||
@Autowired
|
||||
private DossierTesterAndProvider dossierTesterAndProvider;
|
||||
|
||||
@Autowired
|
||||
private DossierTemplateTesterAndProvider dossierTemplateTesterAndProvider;
|
||||
|
||||
@Autowired
|
||||
private DossierTemplateExternalClient dossierTemplateExternalClient;
|
||||
|
||||
@MockBean
|
||||
private ComponentMappingPersistenceService componentMappingPersistenceService;
|
||||
|
||||
|
||||
@Test
|
||||
@SneakyThrows
|
||||
public void testComponentMappingUpdate() {
|
||||
|
||||
var dossierTemplate = dossierTemplateTesterAndProvider.provideTestTemplate();
|
||||
|
||||
var mockMultipartFile = new MockMultipartFile("file.csv",
|
||||
"file.csv",
|
||||
"application/csv",
|
||||
IOUtils.toByteArray(new ClassPathResource("files/componentmapping/file.csv").getInputStream()));
|
||||
|
||||
ComponentMappingMetadataModel componentMappingMetadataModel = dossierTemplateExternalClient.uploadMapping(dossierTemplate.getId(), mockMultipartFile, "file", "UTF-8", ",");
|
||||
|
||||
assertEquals(componentMappingMetadataModel.getFileName(), mockMultipartFile.getOriginalFilename());
|
||||
|
||||
var updateMockMultipartFile = new MockMultipartFile("update_file.csv",
|
||||
"update_file.csv",
|
||||
"application/csv",
|
||||
IOUtils.toByteArray(new ClassPathResource("files/componentmapping/update_file.csv").getInputStream()));
|
||||
|
||||
when(componentMappingPersistenceService.getEntityById(anyString(), anyString())).thenReturn(ComponentMappingEntity.builder()
|
||||
.id(componentMappingMetadataModel.getId())
|
||||
.dossierTemplate(new DossierTemplateEntity())
|
||||
.storageId(buildStorageId(dossierTemplate.getId(), componentMappingMetadataModel.getId(), "file", "update_file.csv"))
|
||||
.fileName("update_file.csv")
|
||||
.build());
|
||||
|
||||
componentMappingMetadataModel = dossierTemplateExternalClient.updateMapping(dossierTemplate.getId(), componentMappingMetadataModel.getId(), updateMockMultipartFile, "file", "UTF-8", ",");
|
||||
|
||||
assertEquals(componentMappingMetadataModel.getFileName(), updateMockMultipartFile.getOriginalFilename());
|
||||
}
|
||||
|
||||
|
||||
@Test
|
||||
@SneakyThrows
|
||||
public void testCreateComponentMappingWithEmptyCsv() {
|
||||
|
||||
var dossierTemplate = dossierTemplateTesterAndProvider.provideTestTemplate();
|
||||
|
||||
var mockMultipartFile = new MockMultipartFile("file.csv",
|
||||
"empty.csv",
|
||||
"application/csv",
|
||||
IOUtils.toByteArray(new ClassPathResource("files/componentmapping/empty.csv").getInputStream()));
|
||||
|
||||
var result = assertThrows(FeignException.class, () -> dossierTemplateExternalClient.uploadMapping(dossierTemplate.getId(), mockMultipartFile, "file", "UTF-8", ","));
|
||||
assertTrue(result.getMessage().contains("CSV file can not be empty!"));
|
||||
}
|
||||
|
||||
|
||||
public static String buildStorageId(String dossierTemplateId, String id, String name, String fileName) {
|
||||
|
||||
return dossierTemplateId + "/" + id + "_" + name + "_" + fileName;
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,10 @@
|
||||
1,"Eldon Base for stackable storage shelf, platinum",Muhammed MacIntyre,3,-213.25,38.94,35,Nunavut,Storage & Organization,0.8
|
||||
2,"1.7 Cubic Foot Compact ""Cube"" Office Refrigerators",Barry French,293,457.81,208.16,68.02,Nunavut,Appliances,0.58
|
||||
3,"Cardinal Slant-D Ring Binder, Heavy Gauge Vinyl",Barry French,293,46.71,8.69,2.99,Nunavut,Binders and Binder Accessories,0.39
|
||||
4,R380,Clay Rozendal,483,1198.97,195.99,3.99,Nunavut,Telephones and Communication,0.58
|
||||
5,Holmes HEPA Air Purifier,Carlos Soltero,515,30.94,21.78,5.94,Nunavut,Appliances,0.5
|
||||
6,G.E. Longer-Life Indoor Recessed Floodlight Bulbs,Carlos Soltero,515,4.43,6.64,4.95,Nunavut,Office Furnishings,0.37
|
||||
7,"Angle-D Binders with Locking Rings, Label Holders",Carl Jackson,613,-54.04,7.3,7.72,Nunavut,Binders and Binder Accessories,0.38
|
||||
8,"SAFCO Mobile Desk Side File, Wire Frame",Carl Jackson,613,127.70,42.76,6.22,Nunavut,Storage & Organization,
|
||||
9,"SAFCO Commercial Wire Shelving, Black",Monica Federle,643,-695.26,138.14,35,Nunavut,Storage & Organization,
|
||||
10,Xerox 198,Dorothy Badders,678,-226.36,4.98,8.33,Nunavut,Paper,0.38
|
||||
|
@ -0,0 +1,5 @@
|
||||
1,"Eldon Base for stackable storage shelf, platinum",Muhammed MacIntyre,3,-213.25,38.94,35,Nunavut,Storage & Organization,0.8
|
||||
2,"1.7 Cubic Foot Compact ""Cube"" Office Refrigerators",Barry French,293,457.81,208.16,68.02,Nunavut,Appliances,0.58
|
||||
3,"Cardinal Slant-D<> Ring Binder, Heavy Gauge Vinyl",Barry French,293,46.71,8.69,2.99,Nunavut,Binders and Binder Accessories,0.39
|
||||
4,R380,Clay Rozendal,483,1198.97,195.99,3.99,Nunavut,Telephones and Communication,0.58
|
||||
5,Holmes HEPA Air Purifier,Carlos Soltero,515,30.94,21.78,5.94,Nunavut,Appliances,0.5
|
||||
|
Loading…
x
Reference in New Issue
Block a user