diff --git a/app/src/main/java/gateway/controller/CtrlFileDelete.java b/app/src/main/java/gateway/controller/CtrlFileDelete.java new file mode 100644 index 0000000..597a195 --- /dev/null +++ b/app/src/main/java/gateway/controller/CtrlFileDelete.java @@ -0,0 +1,70 @@ +package gateway.controller; + +import gateway.config.Config; +import gateway.services.ServiceAuth; +import gateway.services.UtilValidator; +import gateway.soap.request.ReqFileDelete; +import gateway.soap.response.ResStatus; +import java.net.URI; +import java.net.http.HttpClient; +import java.net.http.HttpRequest; +import java.net.http.HttpResponse; +import java.util.UUID; +import org.json.JSONObject; + +public class CtrlFileDelete +{ + public static ResStatus file_delete (ReqFileDelete args) + { + + // Create a new ResStatus object to hold the response data + ResStatus resStatus = new ResStatus (); + + // Check fields of ReqFileDelete + ResStatus resValidate = UtilValidator.validate (args); + if (resValidate.error) { + return resValidate; + } + + // Auth + ResStatus resAuth = ServiceAuth.authenticate (args.token); + if (resAuth.error) { + return resAuth; + } + + // obtain uuid from user + UUID userUUID = UUID.fromString (ServiceAuth.tokenGetClaim (args.token, "uuid")); + + try { + HttpResponse response = HttpClient.newHttpClient ().send ( + HttpRequest.newBuilder () + .uri (URI.create (String.format ( + "%s/files/delete/%s/%s", Config.getMetadataBaseUrl (), userUUID.toString (), + args.fileUUID.toString ()))) + .DELETE () + .build (), + HttpResponse.BodyHandlers.ofString ()); + // Get the HTTP status code from the response + resStatus.code = response.statusCode (); + resStatus.error = true; + if (resStatus.code == 204) { + // If the response code is 204, the request was successful + resStatus.error = false; + } else { + // If the response code is not 204, there was an error + JSONObject responseBody = new JSONObject (response.body ()); + resStatus.msg = responseBody.getString ("message"); + return resStatus; + } + } catch (Exception e) { + // In case of an exception, handle the error + e.printStackTrace (); + resStatus.code = 500; + resStatus.error = true; + resStatus.msg = "Internal server error. Try again later"; + return resStatus; + } + + return resStatus; + } +} diff --git a/app/src/main/java/gateway/soap/request/ReqFileDelete.java b/app/src/main/java/gateway/soap/request/ReqFileDelete.java index 7ea4673..0c97708 100644 --- a/app/src/main/java/gateway/soap/request/ReqFileDelete.java +++ b/app/src/main/java/gateway/soap/request/ReqFileDelete.java @@ -5,5 +5,5 @@ public class ReqFileDelete extends Authorization { - @NotNull public UUID[] fileUUID; // 1+ + @NotNull public UUID fileUUID; } diff --git a/app/src/test/java/gateway/TIFileDelete.java b/app/src/test/java/gateway/TIFileDelete.java new file mode 100644 index 0000000..eff783b --- /dev/null +++ b/app/src/test/java/gateway/TIFileDelete.java @@ -0,0 +1,89 @@ +package gateway; + +import static org.junit.jupiter.api.Assertions.assertEquals; + +import gateway.config.Config; +import gateway.controller.CtrlAccountRegister; +import gateway.controller.CtrlFileDelete; +import gateway.controller.CtrlFileUpload; +import gateway.soap.request.Credentials; +import gateway.soap.request.ReqFileDelete; +import gateway.soap.request.ReqFileUpload; +import gateway.soap.response.ResFileNew; +import gateway.soap.response.ResSession; +import gateway.testutils.TestUtilConfig; +import gateway.testutils.TestUtilGenerator; +import java.util.UUID; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +public class TIFileDelete +{ + @BeforeEach void setup () { Config.initializeFromEnv (); } + + @Test void fileDelete () throws InterruptedException + { + // Register + Credentials cred = new Credentials (UUID.randomUUID ().toString (), "pass"); + ResSession resSession = CtrlAccountRegister.account_register (cred); + assertEquals (201, resSession.code, "User registered successfully"); + + // Upload file + ReqFileUpload reqFileUpload = new ReqFileUpload (); + reqFileUpload.fileContent = TestUtilGenerator.randomBytes (1); + reqFileUpload.fileName = UUID.randomUUID ().toString (); + reqFileUpload.location = null; + reqFileUpload.token = resSession.auth.token; + + ResFileNew resFileNew = CtrlFileUpload.file_upload (reqFileUpload); + assertEquals (201, resFileNew.code, "File upload success"); + + Thread.sleep (1000); // wait for upload + + // Bad Request + ReqFileDelete reqFileDelete = new ReqFileDelete (); + reqFileDelete.token = "invalid token"; + reqFileDelete.fileUUID = null; + assertEquals ( + 400, CtrlFileDelete.file_delete (reqFileDelete).code, "Bad Request: Invalid Field"); + + // Authorization failed + reqFileDelete.fileUUID = resFileNew.fileUUID; + assertEquals (401, CtrlFileDelete.file_delete (reqFileDelete).code, "Authorization failed"); + + // Delete File + reqFileDelete.token = resSession.auth.token; + assertEquals (204, CtrlFileDelete.file_delete (reqFileDelete).code, "Delete File"); + + // File not found + assertEquals (404, CtrlFileDelete.file_delete (reqFileDelete).code, "File not found"); + + // Register another user + Credentials credAnotherUser = + new Credentials (UUID.randomUUID ().toString (), "anotherUser"); + ResSession resSessionAnotherUser = CtrlAccountRegister.account_register (credAnotherUser); + assertEquals (201, resSessionAnotherUser.code, "Another User registered successfully"); + + // Upload file of another user + ReqFileUpload reqFileUploadAnotherUser = new ReqFileUpload (); + reqFileUploadAnotherUser.fileContent = TestUtilGenerator.randomBytes (1); + reqFileUploadAnotherUser.fileName = UUID.randomUUID ().toString (); + reqFileUploadAnotherUser.location = null; + reqFileUploadAnotherUser.token = resSessionAnotherUser.auth.token; + + ResFileNew resFileNewAnotherUser = CtrlFileUpload.file_upload (reqFileUploadAnotherUser); + assertEquals (201, resFileNewAnotherUser.code, "File upload success"); + + Thread.sleep (1000); // wait for upload + + // The user tried to delete a file that not own + reqFileDelete.fileUUID = resFileNewAnotherUser.fileUUID; + assertEquals ( + 403, CtrlFileDelete.file_delete (reqFileDelete).code, + "The user tried to delete a file that not own"); + + // Can't reach metadata + TestUtilConfig.makeInvalidMetadata (); + assertEquals (500, CtrlFileDelete.file_delete (reqFileDelete).code, "Can't reach metadata"); + } +} diff --git a/docs/spec.openapi.yml b/docs/spec.openapi.yml index 98fb572..ca0eb0d 100644 --- a/docs/spec.openapi.yml +++ b/docs/spec.openapi.yml @@ -311,8 +311,9 @@ paths: /file_delete: post: - tags: ["File"] - description: Delete one or multiple files from the user account. + tags: + - File + description: Delete one file from the user account. requestBody: content: Object: @@ -639,10 +640,8 @@ components: - type: object properties: fileUUID: - type: array - items: - type: string - example: 5295d524-aafc-407c-96ed-adae2cd5047a + type: string + example: 5295d524-aafc-407c-96ed-adae2cd5047a - $ref: '#/components/schemas/Authorization' ResFileDownload: