Feature mgmtapi add sha256 to softwaremodules (#918)

* Add sha256 hash to softwaremodules in mgmt api

Signed-off-by: Sebastian Firsching <sebastian.firsching@bosch-si.com>

* Adapt rest docs

Signed-off-by: Sebastian Firsching <sebastian.firsching@bosch-si.com>

* Edit comments

Signed-off-by: Sebastian Firsching <sebastian.firsching@bosch-si.com>

* Add proper license header

Signed-off-by: Sebastian Firsching <sebastian.firsching@bosch-si.com>
This commit is contained in:
Sebastian Firsching
2020-01-13 12:36:14 +01:00
committed by Dominic Schabel
parent 0e9caf3a88
commit 5feb5873c4
14 changed files with 134 additions and 33 deletions

View File

@@ -23,6 +23,9 @@ public class MgmtArtifactHash {
@JsonProperty
private String md5;
@JsonProperty
private String sha256;
/**
* Default constructor.
*/
@@ -33,9 +36,10 @@ public class MgmtArtifactHash {
/**
* Public constructor.
*/
public MgmtArtifactHash(final String sha1, final String md5) {
public MgmtArtifactHash(final String sha1, final String md5, final String sha256) {
this.sha1 = sha1;
this.md5 = md5;
this.sha256 = sha256;
}
public String getSha1() {
@@ -46,4 +50,8 @@ public class MgmtArtifactHash {
return md5;
}
public String getSha256() {
return sha256;
}
}

View File

@@ -52,6 +52,8 @@ public interface MgmtSoftwareModuleRestApi {
* checksum for uploaded content check
* @param sha1Sum
* checksum for uploaded content check
* @param sha256Sum
* checksum for uploaded content check
*
* @return In case all sets could successful be created the ResponseEntity
* with status code 201 - Created but without ResponseBody. In any
@@ -64,7 +66,8 @@ public interface MgmtSoftwareModuleRestApi {
@RequestPart("file") final MultipartFile file,
@RequestParam(value = "filename", required = false) final String optionalFileName,
@RequestParam(value = "md5sum", required = false) final String md5Sum,
@RequestParam(value = "sha1sum", required = false) final String sha1Sum);
@RequestParam(value = "sha1sum", required = false) final String sha1Sum,
@RequestParam(value = "sha256sum", required = false) final String sha256sum);
/**
* Handles the GET request of retrieving all meta data of artifacts assigned

View File

@@ -132,7 +132,8 @@ public final class MgmtSoftwareModuleMapper {
final MgmtArtifact artifactRest = new MgmtArtifact();
artifactRest.setArtifactId(artifact.getId());
artifactRest.setSize(artifact.getSize());
artifactRest.setHashes(new MgmtArtifactHash(artifact.getSha1Hash(), artifact.getMd5Hash()));
artifactRest.setHashes(
new MgmtArtifactHash(artifact.getSha1Hash(), artifact.getMd5Hash(), artifact.getSha256Hash()));
artifactRest.setProvidedFilename(artifact.getFilename());

View File

@@ -74,7 +74,8 @@ public class MgmtSoftwareModuleResource implements MgmtSoftwareModuleRestApi {
@RequestPart("file") final MultipartFile file,
@RequestParam(value = "filename", required = false) final String optionalFileName,
@RequestParam(value = "md5sum", required = false) final String md5Sum,
@RequestParam(value = "sha1sum", required = false) final String sha1Sum) {
@RequestParam(value = "sha1sum", required = false) final String sha1Sum,
@RequestParam(value = "sha256sum", required = false) final String sha256Sum) {
if (file.isEmpty()) {
return ResponseEntity.badRequest().build();
@@ -87,8 +88,8 @@ public class MgmtSoftwareModuleResource implements MgmtSoftwareModuleRestApi {
try (InputStream in = file.getInputStream()) {
final Artifact result = artifactManagement.create(new ArtifactUpload(in, softwareModuleId, fileName,
md5Sum == null ? null : md5Sum.toLowerCase(), sha1Sum == null ? null : sha1Sum.toLowerCase(), false,
file.getContentType(), file.getSize()));
md5Sum == null ? null : md5Sum.toLowerCase(), sha1Sum == null ? null : sha1Sum.toLowerCase(),
sha256Sum == null ? null : sha256Sum.toLowerCase(), false, file.getContentType(), file.getSize()));
final MgmtArtifact reponse = MgmtSoftwareModuleMapper.toResponse(result);
MgmtSoftwareModuleMapper.addLinks(result, reponse);

View File

@@ -165,6 +165,7 @@ public class MgmtSoftwareModuleResourceTest extends AbstractManagementApiIntegra
final byte random[] = randomBytes(5 * 1024);
final String md5sum = HashGeneratorUtils.generateMD5(random);
final String sha1sum = HashGeneratorUtils.generateSHA1(random);
final String sha256sum = HashGeneratorUtils.generateSHA256(random);
final MockMultipartFile file = new MockMultipartFile("file", "origFilename", null, random);
// upload
@@ -175,6 +176,7 @@ public class MgmtSoftwareModuleResourceTest extends AbstractManagementApiIntegra
.andExpect(content().contentType(MediaType.APPLICATION_JSON_UTF8_VALUE))
.andExpect(jsonPath("$.hashes.md5", equalTo(md5sum)))
.andExpect(jsonPath("$.hashes.sha1", equalTo(sha1sum)))
.andExpect(jsonPath("$.hashes.sha256", equalTo(sha256sum)))
.andExpect(jsonPath("$.size", equalTo(random.length)))
.andExpect(jsonPath("$.providedFilename", equalTo("origFilename"))).andReturn();
@@ -247,6 +249,9 @@ public class MgmtSoftwareModuleResourceTest extends AbstractManagementApiIntegra
assertThat(artifactManagement.getByFilename("origFilename").get().getMd5Hash()).as("Wrong md5 hash")
.isEqualTo(HashGeneratorUtils.generateMD5(random));
assertThat(artifactManagement.getByFilename("origFilename").get().getSha256Hash()).as("Wrong sha256 hash")
.isEqualTo(HashGeneratorUtils.generateSHA256(random));
// metadata
assertThat(softwareModuleManagement.get(sm.getId()).get().getArtifacts().get(0).getFilename())
.as("wrong metadata of the filename").isEqualTo("origFilename");
@@ -275,6 +280,7 @@ public class MgmtSoftwareModuleResourceTest extends AbstractManagementApiIntegra
final byte random[] = randomBytes(5 * 1024);
final String md5sum = HashGeneratorUtils.generateMD5(random);
final String sha1sum = HashGeneratorUtils.generateSHA1(random);
final String sha256sum = HashGeneratorUtils.generateSHA256(random);
final MockMultipartFile file = new MockMultipartFile("file", "orig", null, random);
mvc.perform(fileUpload("/rest/v1/softwaremodules/{smId}/artifacts", sm.getId()).file(file)
@@ -282,6 +288,7 @@ public class MgmtSoftwareModuleResourceTest extends AbstractManagementApiIntegra
.andExpect(content().contentType(MediaType.APPLICATION_JSON_UTF8_VALUE))
.andExpect(jsonPath("$.hashes.md5", equalTo(md5sum)))
.andExpect(jsonPath("$.hashes.sha1", equalTo(sha1sum)))
.andExpect(jsonPath("$.hashes.sha256", equalTo(sha256sum)))
.andExpect(jsonPath("$.providedFilename", equalTo("orig"))).andExpect(status().isCreated());
mvc.perform(fileUpload("/rest/v1/softwaremodules/{smId}/artifacts", sm.getId()).file(file))
@@ -322,13 +329,14 @@ public class MgmtSoftwareModuleResourceTest extends AbstractManagementApiIntegra
final byte random[] = randomBytes(5 * 1024);
final String md5sum = HashGeneratorUtils.generateMD5(random);
final String sha1sum = HashGeneratorUtils.generateSHA1(random);
final String sha256sum = HashGeneratorUtils.generateSHA256(random);
final MockMultipartFile file = new MockMultipartFile("file", "origFilename", null, random);
// upload
// wrong sha1
MvcResult mvcResult = mvc
.perform(fileUpload("/rest/v1/softwaremodules/{smId}/artifacts", sm.getId()).file(file)
.param("md5sum", md5sum).param("sha1sum", "afsdff"))
.param("md5sum", md5sum).param("sha1sum", "afsdff").param("sha256sum", sha256sum))
.andDo(MockMvcResultPrinter.print()).andExpect(status().isBadRequest()).andReturn();
// check error result
@@ -336,10 +344,21 @@ public class MgmtSoftwareModuleResourceTest extends AbstractManagementApiIntegra
assertThat(exceptionInfo.getErrorCode()).as("Exception contains wrong error code")
.isEqualTo(SpServerError.SP_ARTIFACT_UPLOAD_FAILED_SHA1_MATCH.getKey());
// wrong sha256
mvcResult = mvc
.perform(fileUpload("/rest/v1/softwaremodules/{smId}/artifacts", sm.getId()).file(file)
.param("md5sum", md5sum).param("sha1sum", sha1sum).param("sha256sum", "jdshfsd"))
.andDo(MockMvcResultPrinter.print()).andExpect(status().isBadRequest()).andReturn();
// check error result
exceptionInfo = ResourceUtility.convertException(mvcResult.getResponse().getContentAsString());
assertThat(exceptionInfo.getErrorCode()).as("Exception contains wrong error code")
.isEqualTo(SpServerError.SP_ARTIFACT_UPLOAD_FAILED_SHA256_MATCH.getKey());
// wrong md5
mvcResult = mvc
.perform(fileUpload("/rest/v1/softwaremodules/{smId}/artifacts", sm.getId()).file(file)
.param("md5sum", "sdfsdfs").param("sha1sum", sha1sum))
.param("md5sum", "sdfsdfs").param("sha1sum", sha1sum).param("sha256sum", sha256sum))
.andDo(MockMvcResultPrinter.print()).andExpect(status().isBadRequest()).andReturn();
// check error result
@@ -366,6 +385,7 @@ public class MgmtSoftwareModuleResourceTest extends AbstractManagementApiIntegra
final byte random[] = randomBytes(5 * 1024);
final String md5sum = HashGeneratorUtils.generateMD5(random);
final String sha1sum = HashGeneratorUtils.generateSHA1(random);
final String sha256sum = HashGeneratorUtils.generateSHA256(random);
final MockMultipartFile file = new MockMultipartFile("file", "origFilename" + i, null, random);
// upload
@@ -375,14 +395,13 @@ public class MgmtSoftwareModuleResourceTest extends AbstractManagementApiIntegra
.andExpect(content().contentType(MediaType.APPLICATION_JSON_UTF8_VALUE))
.andExpect(jsonPath("$.hashes.md5", equalTo(md5sum)))
.andExpect(jsonPath("$.hashes.sha1", equalTo(sha1sum)))
.andExpect(jsonPath("$.hashes.sha256", equalTo(sha256sum)))
.andExpect(jsonPath("$.size", equalTo(random.length)))
.andExpect(jsonPath("$.providedFilename", equalTo("origFilename" + i))).andReturn();
}
// upload one more file to cause the quota to be exceeded
final byte random[] = randomBytes(5 * 1024);
HashGeneratorUtils.generateMD5(random);
HashGeneratorUtils.generateSHA1(random);
final MockMultipartFile file = new MockMultipartFile("file", "origFilename_final", null, random);
// upload
@@ -409,6 +428,7 @@ public class MgmtSoftwareModuleResourceTest extends AbstractManagementApiIntegra
final byte random[] = randomBytes(artifactSize);
final String md5sum = HashGeneratorUtils.generateMD5(random);
final String sha1sum = HashGeneratorUtils.generateSHA1(random);
final String sha256sum = HashGeneratorUtils.generateSHA256(random);
final MockMultipartFile file = new MockMultipartFile("file", "origFilename" + i, null, random);
// upload
@@ -419,14 +439,13 @@ public class MgmtSoftwareModuleResourceTest extends AbstractManagementApiIntegra
.andExpect(content().contentType(MediaType.APPLICATION_JSON_UTF8_VALUE))
.andExpect(jsonPath("$.hashes.md5", equalTo(md5sum)))
.andExpect(jsonPath("$.hashes.sha1", equalTo(sha1sum)))
.andExpect(jsonPath("$.hashes.sha256", equalTo(sha256sum)))
.andExpect(jsonPath("$.size", equalTo(random.length)))
.andExpect(jsonPath("$.providedFilename", equalTo("origFilename" + i))).andReturn();
}
// upload one more file to cause the quota to be exceeded
final byte random[] = randomBytes(artifactSize);
HashGeneratorUtils.generateMD5(random);
HashGeneratorUtils.generateSHA1(random);
final MockMultipartFile file = new MockMultipartFile("file", "origFilename_final", null, random);
// upload
@@ -490,6 +509,7 @@ public class MgmtSoftwareModuleResourceTest extends AbstractManagementApiIntegra
.andExpect(jsonPath("$.size", equalTo(random.length)))
.andExpect(jsonPath("$.hashes.md5", equalTo(artifact.getMd5Hash())))
.andExpect(jsonPath("$.hashes.sha1", equalTo(artifact.getSha1Hash())))
.andExpect(jsonPath("$.hashes.sha256", equalTo(artifact.getSha256Hash())))
.andExpect(jsonPath("$.providedFilename", equalTo("file1")))
.andExpect(jsonPath("$._links.download.href",
equalTo("http://localhost/rest/v1/softwaremodules/" + sm.getId() + "/artifacts/"
@@ -518,6 +538,7 @@ public class MgmtSoftwareModuleResourceTest extends AbstractManagementApiIntegra
.andExpect(jsonPath("$.[0].size", equalTo(random.length)))
.andExpect(jsonPath("$.[0].hashes.md5", equalTo(artifact.getMd5Hash())))
.andExpect(jsonPath("$.[0].hashes.sha1", equalTo(artifact.getSha1Hash())))
.andExpect(jsonPath("$.[0].hashes.sha256", equalTo(artifact.getSha256Hash())))
.andExpect(jsonPath("$.[0].providedFilename", equalTo("file1")))
.andExpect(jsonPath("$.[0]._links.self.href",
equalTo("http://localhost/rest/v1/softwaremodules/" + sm.getId() + "/artifacts/"
@@ -525,6 +546,7 @@ public class MgmtSoftwareModuleResourceTest extends AbstractManagementApiIntegra
.andExpect(jsonPath("$.[1].id", equalTo(artifact2.getId().intValue())))
.andExpect(jsonPath("$.[1].hashes.md5", equalTo(artifact2.getMd5Hash())))
.andExpect(jsonPath("$.[1].hashes.sha1", equalTo(artifact2.getSha1Hash())))
.andExpect(jsonPath("$.[1].hashes.sha256", equalTo(artifact2.getSha256Hash())))
.andExpect(jsonPath("$.[1].providedFilename", equalTo("file2")))
.andExpect(jsonPath("$.[1]._links.self.href", equalTo(
"http://localhost/rest/v1/softwaremodules/" + sm.getId() + "/artifacts/" + artifact2.getId())));
@@ -759,7 +781,7 @@ public class MgmtSoftwareModuleResourceTest extends AbstractManagementApiIntegra
}
@Test
@Description("Verfies that the system answers as defined in case of a wnon extsing field used in filter. Expected result: BAD REQUEST with error description.")
@Description("Verfies that the system answers as defined in case of a non existing field used in filter. Expected result: BAD REQUEST with error description.")
public void getSoftwareModulesWithUnknownFieldErrorFilterParameter() throws Exception {
mvc.perform(get("/rest/v1/softwaremodules?q=wrongField==abc").accept(MediaType.APPLICATION_JSON))
.andDo(MockMvcResultPrinter.print()).andExpect(status().isBadRequest())

View File

@@ -57,6 +57,7 @@ public class ResponseExceptionHandler {
ERROR_TO_HTTP_STATUS.put(SpServerError.SP_INSUFFICIENT_PERMISSION, HttpStatus.FORBIDDEN);
ERROR_TO_HTTP_STATUS.put(SpServerError.SP_ARTIFACT_UPLOAD_FAILED, HttpStatus.INTERNAL_SERVER_ERROR);
ERROR_TO_HTTP_STATUS.put(SpServerError.SP_ARTIFACT_UPLOAD_FAILED_SHA1_MATCH, HttpStatus.BAD_REQUEST);
ERROR_TO_HTTP_STATUS.put(SpServerError.SP_ARTIFACT_UPLOAD_FAILED_SHA256_MATCH, HttpStatus.BAD_REQUEST);
ERROR_TO_HTTP_STATUS.put(SpServerError.SP_ARTIFACT_UPLOAD_FAILED_MD5_MATCH, HttpStatus.BAD_REQUEST);
ERROR_TO_HTTP_STATUS.put(SpServerError.SP_ARTIFACT_DELETE_FAILED, HttpStatus.INTERNAL_SERVER_ERROR);
ERROR_TO_HTTP_STATUS.put(SpServerError.SP_ARTIFACT_LOAD_FAILED, HttpStatus.INTERNAL_SERVER_ERROR);
@@ -118,9 +119,10 @@ public class ResponseExceptionHandler {
/**
* Method for handling exception of type HttpMessageNotReadableException and
* MethodArgumentNotValidException which are thrown in case the request body is
* not well formed (e.g. syntax failures, missing/invalid parameters) and cannot
* be deserialized. Called by the Spring-Framework for exception handling.
* MethodArgumentNotValidException which are thrown in case the request body
* is not well formed (e.g. syntax failures, missing/invalid parameters) and
* cannot be deserialized. Called by the Spring-Framework for exception
* handling.
*
* @param request
* the Http request
@@ -129,7 +131,7 @@ public class ResponseExceptionHandler {
* @return the entity to be responded containing the exception information
* as entity.
*/
@ExceptionHandler({HttpMessageNotReadableException.class, MethodArgumentNotValidException.class})
@ExceptionHandler({ HttpMessageNotReadableException.class, MethodArgumentNotValidException.class })
public ResponseEntity<ExceptionInfo> handleExceptionCausedByIncorrectRequestBody(final HttpServletRequest request,
final Exception ex) {
logRequest(request, ex);

View File

@@ -47,6 +47,7 @@ public final class MgmtApiModelProperties {
public static final String ARTIFACT_PROVIDED_FILENAME = "Filename of the artifact.";
public static final String ARTIFACT_HASHES_SHA1 = "SHA1 hash of the artifact.";
public static final String ARTIFACT_HASHES_MD5 = "MD5 hash of the artifact.";
public static final String ARTIFACT_HASHES_SHA256 = "SHA256 hash of the artifact.";
public static final String ARTIFACT_DOWNLOAD_LINK = "Download link of the artifact.";

View File

@@ -266,6 +266,8 @@ public class SoftwaremodulesDocumentationTest extends AbstractApiRestDocumentati
fieldWithPath("[].hashes.md5").description(MgmtApiModelProperties.ARTIFACT_HASHES_MD5),
fieldWithPath("[].hashes.sha1")
.description(MgmtApiModelProperties.ARTIFACT_HASHES_SHA1),
fieldWithPath("[].hashes.sha256")
.description(MgmtApiModelProperties.ARTIFACT_HASHES_SHA256),
fieldWithPath("[].providedFilename")
.description(MgmtApiModelProperties.ARTIFACT_PROVIDED_FILENAME),
fieldWithPath("[]._links.self").ignored())));
@@ -299,6 +301,8 @@ public class SoftwaremodulesDocumentationTest extends AbstractApiRestDocumentati
.description(MgmtApiModelProperties.ARTIFACT_DOWNLOAD_LINK),
fieldWithPath("hashes.md5").description(MgmtApiModelProperties.ARTIFACT_HASHES_MD5),
fieldWithPath("hashes.sha1").description(MgmtApiModelProperties.ARTIFACT_HASHES_SHA1),
fieldWithPath("hashes.sha256")
.description(MgmtApiModelProperties.ARTIFACT_HASHES_SHA256),
fieldWithPath("providedFilename")
.description(MgmtApiModelProperties.ARTIFACT_PROVIDED_FILENAME)))
@@ -374,6 +378,8 @@ public class SoftwaremodulesDocumentationTest extends AbstractApiRestDocumentati
fieldWithPath("lastModifiedAt").description(ApiModelPropertiesGeneric.LAST_MODIFIED_AT),
fieldWithPath("hashes.md5").description(MgmtApiModelProperties.ARTIFACT_HASHES_MD5),
fieldWithPath("hashes.sha1").description(MgmtApiModelProperties.ARTIFACT_HASHES_SHA1),
fieldWithPath("hashes.sha256")
.description(MgmtApiModelProperties.ARTIFACT_HASHES_SHA256),
fieldWithPath("providedFilename")
.description(MgmtApiModelProperties.ARTIFACT_PROVIDED_FILENAME),
fieldWithPath("_links.self").ignored(), fieldWithPath("_links.download")