From d1d093cdd4cdfdef7ec88df4083ebf64b1e24301 Mon Sep 17 00:00:00 2001 From: "francesco.mangiacrapa" Date: Wed, 2 Oct 2019 12:43:35 +0200 Subject: [PATCH] Support to Content-Disposition as query parameter Added to Storage Resolvers link support to content-disposition as input query parameter. --- .../resolver/ConstantsResolver.java | 29 +++--- .../requesthandler/RequestHandler.java | 6 +- .../resolver/services/SMPIDResolver.java | 14 ++- .../resolver/services/SMPResolver.java | 12 ++- .../resolver/services/StorageHubResolver.java | 23 ++--- .../resolver/services/StorageIDResolver.java | 92 +++++++++++-------- .../StorageHubMetadataResponseBuilder.java | 12 ++- .../util/ValidateContentDisposition.java | 53 +++++++++++ 8 files changed, 165 insertions(+), 76 deletions(-) rename src/main/java/org/gcube/datatransfer/resolver/{util => shub}/StorageHubMetadataResponseBuilder.java (89%) create mode 100644 src/main/java/org/gcube/datatransfer/resolver/util/ValidateContentDisposition.java diff --git a/src/main/java/org/gcube/datatransfer/resolver/ConstantsResolver.java b/src/main/java/org/gcube/datatransfer/resolver/ConstantsResolver.java index 13af130..c14b38b 100644 --- a/src/main/java/org/gcube/datatransfer/resolver/ConstantsResolver.java +++ b/src/main/java/org/gcube/datatransfer/resolver/ConstantsResolver.java @@ -7,30 +7,35 @@ package org.gcube.datatransfer.resolver; * The Class ConstantsResolver. * * @author Francesco Mangiacrapa at ISTI-CNR (francesco.mangiacrapa@isti.cnr.it) - * Oct 19, 2018 + * Oct 19, 2018 */ public class ConstantsResolver { public static final String CONTENT_DISPOSITION = "Content-Disposition"; - public static enum CONTENT_DISPOSITION_VALUE {inline, attachment}; + + public static enum CONTENT_DISPOSITION_VALUE { + inline, attachment + }; + public static final String CONTENT_LENGTH = "Content-Length"; - public static final String CONTENT_TYPE= "Content-Type"; - - public static final String QUERY_PARAM_CONTENTDISPOSITION = "content-disposition"; + public static final String CONTENT_TYPE = "Content-Type"; + public static final String DEFAULT_CONTENTTYPE_UNKNOWN_UNKNOWN = "unknown/unknown"; public static final String DEFAULT_FILENAME_FROM_STORAGE_MANAGER = "fromStorageManager"; - public static final String HPC = "hproxycheck"; //for hproxycheck + public static final String HPC = "hproxycheck"; // for hproxycheck + public static final String QUERY_PARAM_CONTENTDISPOSITION = "content-disposition"; public static final String QUERY_PARAM_VALIDATION = "validation"; public static final String QUERY_PARAM_CONTENT_TYPE = "contentType"; public static final String QUERY_PARAM_FILE_NAME = "fileName"; - - public static final String[] resourcesHardCoded = {"ctlg"}; - - //The default resource candidate to manage the input requests not matching any resolver services - public static final String defaultServiceToRedirect= "storage"; - + + public static final String[] resourcesHardCoded = { "ctlg" }; + + // The default resource candidate to manage the input requests not matching any + // resolver services + public static final String defaultServiceToRedirect = "storage"; + public static final String SCOPE_SEPARATOR = "/"; } diff --git a/src/main/java/org/gcube/datatransfer/resolver/requesthandler/RequestHandler.java b/src/main/java/org/gcube/datatransfer/resolver/requesthandler/RequestHandler.java index 15b16eb..98e3935 100644 --- a/src/main/java/org/gcube/datatransfer/resolver/requesthandler/RequestHandler.java +++ b/src/main/java/org/gcube/datatransfer/resolver/requesthandler/RequestHandler.java @@ -74,6 +74,7 @@ public class RequestHandler implements ContainerRequestFilter, ContainerResponse log.debug("The resources are: {}", listOfPath); String path = reqContext.getUriInfo().getPath(); + log.debug("The path is: {}", path); //HOW TO READ THE QUERY STRING /*MultivaluedMap queryParameters = reqContext.getUriInfo().getQueryParameters(); @@ -86,10 +87,7 @@ public class RequestHandler implements ContainerRequestFilter, ContainerResponse } log.debug("The query string is: {}", queryString); */ - - log.debug("The path is: {}", path); - - + if(path==null || path.isEmpty()) { log.debug("The path is null or empty, redirecting to /index"); URI newRequestURI = reqContext.getUriInfo().getBaseUriBuilder().path("/index").build(); diff --git a/src/main/java/org/gcube/datatransfer/resolver/services/SMPIDResolver.java b/src/main/java/org/gcube/datatransfer/resolver/services/SMPIDResolver.java index 60fa8e5..1c8c073 100644 --- a/src/main/java/org/gcube/datatransfer/resolver/services/SMPIDResolver.java +++ b/src/main/java/org/gcube/datatransfer/resolver/services/SMPIDResolver.java @@ -13,7 +13,9 @@ import javax.ws.rs.core.Context; import javax.ws.rs.core.Response; import org.gcube.datatransfer.resolver.ConstantsResolver; +import org.gcube.datatransfer.resolver.ConstantsResolver.CONTENT_DISPOSITION_VALUE; import org.gcube.datatransfer.resolver.services.error.ExceptionManager; +import org.gcube.datatransfer.resolver.util.ValidateContentDisposition; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -53,7 +55,9 @@ public class SMPIDResolver { @QueryParam(SMP_ID) @Nullable String smpId, @QueryParam(ConstantsResolver.QUERY_PARAM_FILE_NAME) String fileName, @QueryParam(ConstantsResolver.QUERY_PARAM_CONTENT_TYPE) String contentType, - @QueryParam(ConstantsResolver.QUERY_PARAM_VALIDATION) Boolean validation) throws WebApplicationException{ + @QueryParam(ConstantsResolver.QUERY_PARAM_CONTENTDISPOSITION) String contentDisposition, + @QueryParam(ConstantsResolver.QUERY_PARAM_VALIDATION) boolean validation) throws WebApplicationException{ + logger.info(this.getClass().getSimpleName()+" GET starts..."); try{ @@ -62,8 +66,14 @@ public class SMPIDResolver { logger.error(SMP_ID+" not found"); throw ExceptionManager.badRequestException(req, "Missing mandatory parameter "+SMP_ID, SMPIDResolver.class, helpURI); } + + + //Checking the optional parameter "Content-Disposition" + CONTENT_DISPOSITION_VALUE dispositionValue = CONTENT_DISPOSITION_VALUE.attachment; + //Validating the Content-Disposition value + dispositionValue = ValidateContentDisposition.validValue(req, this.getClass(), helpURI, contentDisposition); - return StorageIDResolver.resolveStorageId(req, smpId, fileName, contentType, validation); + return StorageIDResolver.resolveStorageId(req, smpId, fileName, contentType, dispositionValue, validation); }catch (Exception e) { diff --git a/src/main/java/org/gcube/datatransfer/resolver/services/SMPResolver.java b/src/main/java/org/gcube/datatransfer/resolver/services/SMPResolver.java index 2a36a64..8cb7c99 100644 --- a/src/main/java/org/gcube/datatransfer/resolver/services/SMPResolver.java +++ b/src/main/java/org/gcube/datatransfer/resolver/services/SMPResolver.java @@ -13,7 +13,9 @@ import javax.ws.rs.core.Context; import javax.ws.rs.core.Response; import org.gcube.datatransfer.resolver.ConstantsResolver; +import org.gcube.datatransfer.resolver.ConstantsResolver.CONTENT_DISPOSITION_VALUE; import org.gcube.datatransfer.resolver.services.error.ExceptionManager; +import org.gcube.datatransfer.resolver.util.ValidateContentDisposition; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -54,7 +56,8 @@ public class SMPResolver { String smpURI, @QueryParam(ConstantsResolver.QUERY_PARAM_FILE_NAME) String fileName, @QueryParam(ConstantsResolver.QUERY_PARAM_CONTENT_TYPE) String contentType, - @QueryParam(ConstantsResolver.QUERY_PARAM_VALIDATION) Boolean validation) throws WebApplicationException{ + @QueryParam(ConstantsResolver.QUERY_PARAM_CONTENTDISPOSITION) String contentDisposition, + @QueryParam(ConstantsResolver.QUERY_PARAM_VALIDATION) boolean validation) throws WebApplicationException{ logger.info(this.getClass().getSimpleName()+" GET starts..."); @@ -64,8 +67,13 @@ public class SMPResolver { logger.error(SMP_URI+" not found"); throw ExceptionManager.badRequestException(req, "Missing mandatory parameter "+SMP_URI, SMPResolver.class, helpURI); } + + //Checking the optional parameter "Content-Disposition" + CONTENT_DISPOSITION_VALUE dispositionValue = CONTENT_DISPOSITION_VALUE.attachment; + //Validating the Content-Disposition value + dispositionValue = ValidateContentDisposition.validValue(req, this.getClass(), helpURI, contentDisposition); - return StorageIDResolver.resolveStorageId(req, smpURI, fileName, contentType, validation); + return StorageIDResolver.resolveStorageId(req, smpURI, fileName, contentType, dispositionValue, validation); }catch (Exception e) { diff --git a/src/main/java/org/gcube/datatransfer/resolver/services/StorageHubResolver.java b/src/main/java/org/gcube/datatransfer/resolver/services/StorageHubResolver.java index f299436..481168f 100644 --- a/src/main/java/org/gcube/datatransfer/resolver/services/StorageHubResolver.java +++ b/src/main/java/org/gcube/datatransfer/resolver/services/StorageHubResolver.java @@ -6,6 +6,7 @@ import javax.ws.rs.GET; import javax.ws.rs.HEAD; import javax.ws.rs.Path; import javax.ws.rs.PathParam; +import javax.ws.rs.QueryParam; import javax.ws.rs.WebApplicationException; import javax.ws.rs.core.Context; import javax.ws.rs.core.Response; @@ -17,7 +18,8 @@ import org.gcube.common.storagehub.client.proxies.ItemManagerClient; import org.gcube.datatransfer.resolver.ConstantsResolver; import org.gcube.datatransfer.resolver.ConstantsResolver.CONTENT_DISPOSITION_VALUE; import org.gcube.datatransfer.resolver.services.error.ExceptionManager; -import org.gcube.datatransfer.resolver.util.StorageHubMetadataResponseBuilder; +import org.gcube.datatransfer.resolver.shub.StorageHubMetadataResponseBuilder; +import org.gcube.datatransfer.resolver.util.ValidateContentDisposition; import org.gcube.smartgears.utils.InnerMethodName; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -101,7 +103,7 @@ public class StorageHubResolver { */ @GET @Path("/{id}") - public Response download(@Context HttpServletRequest req) { + public Response download(@Context HttpServletRequest req, @QueryParam(ConstantsResolver.QUERY_PARAM_CONTENTDISPOSITION) String contentDisposition) { logger.info(this.getClass().getSimpleName()+" GET download called"); try{ @@ -114,20 +116,9 @@ public class StorageHubResolver { } //Checking the optional parameter "Content-Disposition" - String contDisp = req.getParameter(ConstantsResolver.QUERY_PARAM_CONTENTDISPOSITION); - CONTENT_DISPOSITION_VALUE dispValue = CONTENT_DISPOSITION_VALUE.attachment; + CONTENT_DISPOSITION_VALUE dispositionValue = CONTENT_DISPOSITION_VALUE.attachment; //Validating the Content-Disposition value - if(contDisp!=null && !contDisp.isEmpty()) { - try { - //It must have a value of: "inline" or "attachement" - dispValue = ConstantsResolver.CONTENT_DISPOSITION_VALUE.valueOf(contDisp); - }catch (Exception e) { - String allowedValues = String.format("{%s,%s}", CONTENT_DISPOSITION_VALUE.inline,CONTENT_DISPOSITION_VALUE.attachment); - String msg = String.format("Wrong parameter: '%s=%s'. Valid '%s' values are: %s",ConstantsResolver.QUERY_PARAM_CONTENTDISPOSITION,contDisp,ConstantsResolver.QUERY_PARAM_CONTENTDISPOSITION,allowedValues); - logger.error(msg); - throw ExceptionManager.wrongParameterException(req, msg, StorageHubResolver.class, help); - } - } + dispositionValue = ValidateContentDisposition.validValue(req, this.getClass(), help, contentDisposition); try{ @@ -135,7 +126,7 @@ public class StorageHubResolver { StreamDescriptor descriptor = client.resolvePublicLink(id); ResponseBuilder response = Response.ok(descriptor.getStream()); - response = new StorageHubMetadataResponseBuilder(req, response).fillMetadata(descriptor, id, dispValue); + response = new StorageHubMetadataResponseBuilder(req, response).fillMetadata(descriptor, id, dispositionValue); return response.build(); }catch(Exception e){ diff --git a/src/main/java/org/gcube/datatransfer/resolver/services/StorageIDResolver.java b/src/main/java/org/gcube/datatransfer/resolver/services/StorageIDResolver.java index 2589801..ccc76cf 100644 --- a/src/main/java/org/gcube/datatransfer/resolver/services/StorageIDResolver.java +++ b/src/main/java/org/gcube/datatransfer/resolver/services/StorageIDResolver.java @@ -23,10 +23,12 @@ import org.gcube.contentmanager.storageclient.wrapper.AccessType; import org.gcube.contentmanager.storageclient.wrapper.MemoryType; import org.gcube.contentmanager.storageclient.wrapper.StorageClient; import org.gcube.datatransfer.resolver.ConstantsResolver; +import org.gcube.datatransfer.resolver.ConstantsResolver.CONTENT_DISPOSITION_VALUE; import org.gcube.datatransfer.resolver.services.error.ExceptionManager; import org.gcube.datatransfer.resolver.storage.StorageClientInstance; import org.gcube.datatransfer.resolver.storage.StorageMetadataFile; import org.gcube.datatransfer.resolver.util.SingleFileStreamingOutput; +import org.gcube.datatransfer.resolver.util.ValidateContentDisposition; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -47,7 +49,7 @@ public class StorageIDResolver { protected static final String STORAGEID_RESOLVER = "storageid-resolver"; private static final String STORAGE_ID = "storage-id"; - private static final Logger logger = LoggerFactory.getLogger(StorageIDResolver.class); + private static final Logger LOG = LoggerFactory.getLogger(StorageIDResolver.class); private static String help = "https://wiki.gcube-system.org/gcube/URI_Resolver#STORAGE-ID_Resolver"; @@ -69,16 +71,22 @@ public class StorageIDResolver { @PathParam(STORAGE_ID) String storageId, @QueryParam(ConstantsResolver.QUERY_PARAM_FILE_NAME) String fileName, @QueryParam(ConstantsResolver.QUERY_PARAM_CONTENT_TYPE) String contentType, - @QueryParam(ConstantsResolver.QUERY_PARAM_VALIDATION) Boolean validation) throws WebApplicationException { + @QueryParam(ConstantsResolver.QUERY_PARAM_CONTENTDISPOSITION) String contentDisposition, + @QueryParam(ConstantsResolver.QUERY_PARAM_VALIDATION) boolean validation) throws WebApplicationException { - logger.info(this.getClass().getSimpleName()+" GET starts..."); + LOG.info(this.getClass().getSimpleName()+" GET starts..."); + + //Checking the optional parameter "Content-Disposition" + CONTENT_DISPOSITION_VALUE dispositionValue = CONTENT_DISPOSITION_VALUE.attachment; + //Validating the Content-Disposition value + dispositionValue = ValidateContentDisposition.validValue(req, this.getClass(), help, contentDisposition); try{ if(storageId==null || storageId.isEmpty()){ - logger.error(STORAGE_ID+" not found"); + LOG.error(STORAGE_ID+" not found"); throw ExceptionManager.badRequestException(req, "Missing mandatory path parameter "+STORAGE_ID, StorageIDResolver.class, help); } - return resolveStorageId(req, storageId, fileName, contentType, validation); + return resolveStorageId(req, storageId, fileName, contentType, dispositionValue, validation); }catch (Exception e) { if(!(e instanceof WebApplicationException)){ @@ -89,7 +97,7 @@ public class StorageIDResolver { throw ExceptionManager.internalErrorException(req, error, this.getClass(), help); } //ALREADY MANAGED AS WebApplicationException - logger.error("Exception:", e); + LOG.error("Exception:", e); throw (WebApplicationException) e; } } @@ -106,13 +114,13 @@ public class StorageIDResolver { * @return the response * @throws Exception the exception */ - protected static Response resolveStorageId(HttpServletRequest httpRequest, String storageId, String fileName, String contentType, Boolean validation) throws Exception{ + protected static Response resolveStorageId(HttpServletRequest httpRequest, String storageId, String fileName, String contentType, CONTENT_DISPOSITION_VALUE contentDisposition, boolean validation) throws Exception{ - logger.info("storage-id: "+storageId+", fileName: "+fileName+", contentType: "+contentType+", validation: "+validation); + LOG.info("storage-id: "+storageId+", fileName: "+fileName+", contentType: "+contentType+", validation: "+validation); //Checking mandatory parameter storageId if (storageId == null || storageId.isEmpty()) { - logger.error("storageId not found"); + LOG.error("storageId not found"); throw ExceptionManager.badRequestException(httpRequest, "Missing mandatory path parameter "+STORAGE_ID, StorageIDResolver.class, help); } @@ -120,18 +128,18 @@ public class StorageIDResolver { String toSEID = null; IClient iClient = null; storageId = scInstance.getStorageId(); //IT SHOULD BE CHANGED es. removing the suffix '-VLT' - logger.info("I'm using the storageId {}",storageId); + LOG.info("I'm using the storageId {}",storageId); try{ iClient = scInstance.getStorageClient().getClient(); toSEID = iClient.getId(storageId); //to Storage Encrypted ID - logger.info("Decoded ID"+" = "+ toSEID); + LOG.info("Decoded ID"+" = "+ toSEID); }catch(Exception e){ - logger.error("Storage Client Exception when getting file from storage: ", e); + LOG.error("Storage Client Exception when getting file from storage: ", e); throw ExceptionManager.notFoundException(httpRequest, "Storage Client Exception when getting file from storage with id: "+storageId, StorageIDResolver.class, help); } if(toSEID==null || toSEID.isEmpty()){ - logger.error("Decrypted id for storageId: "+storageId +" is null or empty!"); + LOG.error("Decrypted id for storageId: "+storageId +" is null or empty!"); throw ExceptionManager.notFoundException(httpRequest, "Error on decrypting the "+STORAGE_ID+ " '"+storageId+"'. Is it a valid id?", StorageIDResolver.class, help); } @@ -140,27 +148,32 @@ public class StorageIDResolver { //READING THE METADATA OF FILE FROM STORAGE StorageMetadataFile metaFile = getStorageMetadataFile(iClient,toSEID); - logger.debug("MetaFile retrieved from storage? "+ (metaFile!=null)); + LOG.debug("MetaFile retrieved from storage? "+ (metaFile!=null)); if(metaFile!=null) { //Reading the fileName from Storage Metadata only if the passed fileName is null - if(fileName==null || fileName.isEmpty()) + if(fileName==null || fileName.isEmpty()) { fileName= metaFile.getName(); + LOG.debug("Read filename {} from {}", fileName, StorageMetadataFile.class.getSimpleName()); + } //Reading the contentType from Storage Metadata only if the passed contentType is null - if(contentType==null || contentType.isEmpty()) + if(contentType==null || contentType.isEmpty()) { contentType = metaFile.getMimeType(); + LOG.debug("Read contentType {} from {}", contentType, StorageMetadataFile.class.getSimpleName()); + } //Reading the content size size = metaFile.getSize(); + LOG.debug("Read size {} from {}", size, StorageMetadataFile.class.getSimpleName()); } //CHECKING TO DEFAULT METADATA fileName = fileName==null || fileName.isEmpty()?ConstantsResolver.DEFAULT_FILENAME_FROM_STORAGE_MANAGER:fileName; - logger.info("filename retrieved is {}",fileName); + LOG.info("filename retrieved is {}",fileName); contentType = contentType==null || contentType.isEmpty()?ConstantsResolver.DEFAULT_CONTENTTYPE_UNKNOWN_UNKNOWN:contentType; - logger.info("contentType used is {}",contentType); + LOG.info("contentType used is {}",contentType); //Building the response InputStream streamToWrite=iClient.get().RFileAsInputStream(toSEID); //input stream @@ -168,7 +181,7 @@ public class StorageIDResolver { ResponseBuilder response = Response .ok(so) - .header(ConstantsResolver.CONTENT_DISPOSITION,"attachment; filename=\""+fileName+"\"") + .header(ConstantsResolver.CONTENT_DISPOSITION, contentDisposition.name()+"; filename=\""+fileName+"\"") .header(ConstantsResolver.CONTENT_LENGTH, size) .header("Content-Type",contentType); @@ -195,14 +208,14 @@ public class StorageIDResolver { @PathParam(STORAGE_ID) String storageId, @QueryParam(ConstantsResolver.HPC) boolean hproxycheck) throws WebApplicationException { - logger.info(this.getClass().getSimpleName()+" HEAD starts..."); - logger.info("The query string is: {}", req.getQueryString()); - logger.info("Query parameter {} is {}", ConstantsResolver.HPC, hproxycheck); + LOG.info(this.getClass().getSimpleName()+" HEAD starts..."); + LOG.info("The query string is: {}", req.getQueryString()); + LOG.info("Query parameter {} is {}", ConstantsResolver.HPC, hproxycheck); try{ //THIS IS FOR HPROXY CHECK if(hproxycheck){ - logger.trace("returning status 200 for Hproxy check"); + LOG.trace("returning status 200 for Hproxy check"); ResponseBuilder response = Response.status(HttpStatus.SC_OK); return response.build(); } @@ -219,7 +232,7 @@ public class StorageIDResolver { throw ExceptionManager.internalErrorException(req, error, this.getClass(), help); } //ALREADY MANAGED AS WebApplicationException - logger.error("Exception:", e); + LOG.error("Exception:", e); throw (WebApplicationException) e; } } @@ -234,30 +247,30 @@ public class StorageIDResolver { * @throws Exception the exception */ protected Response validationPayload(HttpServletRequest httpRequest, String storageId) throws Exception{ - logger.info("validationPayload called"); + LOG.info("validationPayload called"); //Checking mandatory parameter storageId if (storageId == null || storageId.isEmpty()) { - logger.warn("storageId not found"); + LOG.warn("storageId not found"); throw ExceptionManager.badRequestException(httpRequest, "Storage Client Exception when getting file from storage with id: "+storageId, this.getClass(), help); } StorageClientInstance client = buildStorageClientInstance(storageId); String toSEID = null; IClient iClient = null; storageId = client.getStorageId(); //IT SHOULD BE CHANGED es. removing the suffix '-VLT' - logger.info("I'm using the storageId {}",storageId); + LOG.info("I'm using the storageId {}",storageId); try{ iClient = client.getStorageClient().getClient(); toSEID = iClient.getId(storageId); //to Storage Encrypted ID - logger.debug("Decoded ID"+" = "+ toSEID); + LOG.debug("Decoded ID"+" = "+ toSEID); }catch(Exception e){ - logger.error("Storage Client Exception when getting file from storage: ", e); + LOG.error("Storage Client Exception when getting file from storage: ", e); throw ExceptionManager.internalErrorException(httpRequest, "Storage Client Exception when getting file from storage with id: "+storageId, StorageIDResolver.class, help); } if(toSEID==null || toSEID.isEmpty()){ - logger.error("Decrypted id for storageId: "+storageId +" is null or empty!"); + LOG.error("Decrypted id for storageId: "+storageId +" is null or empty!"); throw ExceptionManager.notFoundException(httpRequest, "Error on decrypting the "+STORAGE_ID+ " '"+storageId+"'. Is it a valid id?", StorageIDResolver.class, help); } @@ -266,20 +279,25 @@ public class StorageIDResolver { String contentType = ConstantsResolver.DEFAULT_CONTENTTYPE_UNKNOWN_UNKNOWN; //READING THE METADATA OF FILE FROM STORAGE StorageMetadataFile metadataFile = getStorageMetadataFile(iClient,toSEID); - logger.debug("MetaFile retrieved from storage? "+ (metadataFile!=null)); + LOG.debug("MetaFile retrieved from storage? "+ (metadataFile!=null)); long size = 0; if (metadataFile != null) { // Reading the fileName from Storage Metadata only if it is not null - if (metadataFile.getName() != null) + if (metadataFile.getName() != null) { fileName = metadataFile.getName(); + LOG.debug("Read filename {} from {}", fileName, StorageMetadataFile.class.getSimpleName()); + } // Reading the contentType from Storage Metadata only if it is not null - if (metadataFile.getMimeType() != null) + if (metadataFile.getMimeType() != null) { contentType = metadataFile.getMimeType(); + LOG.debug("Read contentType {} from {}", contentType, StorageMetadataFile.class.getSimpleName()); + } size = metadataFile.getSize(); + LOG.debug("Read size {} from {}", size, StorageMetadataFile.class.getSimpleName()); } //Building the response @@ -290,16 +308,16 @@ public class StorageIDResolver { ResponseBuilder response = null; try { c = streamToWrite.read(bytes); - logger.info(c+" byte read from InputStream"); + LOG.info(c+" byte read from InputStream"); if(c>0){ - logger.info("at least 1 byte read, returning status 200"); + LOG.info("at least 1 byte read, returning status 200"); IOUtils.closeQuietly(streamToWrite); response = Response.status(HttpStatus.SC_OK); }else throw ExceptionManager.notFoundException(httpRequest, "The file with id: "+storageId+" is missing in the storage", StorageIDResolver.class, help); } catch (IOException e2) { - logger.error("Error on validating the file: ",e2); + LOG.error("Error on validating the file: ",e2); throw ExceptionManager.internalErrorException(httpRequest, "Error on validating the file with id: "+storageId, StorageIDResolver.class, help); } @@ -364,7 +382,7 @@ public class StorageIDResolver { return new StorageMetadataFile(myFile, size); }catch (Exception e) { - logger.warn("Error on getting file metadata from storage, printing this warning and trying to continue..", e); + LOG.warn("Error on getting file metadata from storage, printing this warning and trying to continue..", e); return null; } diff --git a/src/main/java/org/gcube/datatransfer/resolver/util/StorageHubMetadataResponseBuilder.java b/src/main/java/org/gcube/datatransfer/resolver/shub/StorageHubMetadataResponseBuilder.java similarity index 89% rename from src/main/java/org/gcube/datatransfer/resolver/util/StorageHubMetadataResponseBuilder.java rename to src/main/java/org/gcube/datatransfer/resolver/shub/StorageHubMetadataResponseBuilder.java index c4384e1..c05d2a4 100644 --- a/src/main/java/org/gcube/datatransfer/resolver/util/StorageHubMetadataResponseBuilder.java +++ b/src/main/java/org/gcube/datatransfer/resolver/shub/StorageHubMetadataResponseBuilder.java @@ -1,7 +1,7 @@ /** * */ -package org.gcube.datatransfer.resolver.util; +package org.gcube.datatransfer.resolver.shub; import javax.servlet.http.HttpServletRequest; import javax.ws.rs.core.Response.ResponseBuilder; @@ -11,6 +11,7 @@ import org.gcube.common.storagehub.client.plugins.AbstractPlugin; import org.gcube.common.storagehub.client.proxies.ItemManagerClient; import org.gcube.datatransfer.resolver.ConstantsResolver; import org.gcube.datatransfer.resolver.ConstantsResolver.CONTENT_DISPOSITION_VALUE; +import org.gcube.datatransfer.resolver.util.Util; /** @@ -36,7 +37,7 @@ public class StorageHubMetadataResponseBuilder { this.request = req; this.responseBuilder = responseBuilder; } - + /** * Fill metadata. @@ -58,7 +59,12 @@ public class StorageHubMetadataResponseBuilder { //Managing "Content-Type" if (streamDescriptor.getContentType()!= null && !streamDescriptor.getContentType().isEmpty()) - responseBuilder.header("Content-Type", streamDescriptor.getContentType()+"; charset=utf-8"); + responseBuilder.header("Content-Type", streamDescriptor.getContentType()); + + //Managing "Content-Lenght" + if(streamDescriptor.getContentLenght()>0) { + responseBuilder.header("Content-Length", streamDescriptor.getContentLenght()); + } //Managing "ETag" //Here is not feasible because the entityId is cripted diff --git a/src/main/java/org/gcube/datatransfer/resolver/util/ValidateContentDisposition.java b/src/main/java/org/gcube/datatransfer/resolver/util/ValidateContentDisposition.java new file mode 100644 index 0000000..634924b --- /dev/null +++ b/src/main/java/org/gcube/datatransfer/resolver/util/ValidateContentDisposition.java @@ -0,0 +1,53 @@ +package org.gcube.datatransfer.resolver.util; + +import javax.servlet.http.HttpServletRequest; + +import org.gcube.datatransfer.resolver.ConstantsResolver; +import org.gcube.datatransfer.resolver.ConstantsResolver.CONTENT_DISPOSITION_VALUE; +import org.gcube.datatransfer.resolver.services.error.ExceptionManager; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + + +/** + * The Class ValidateContentDisposition. + * + * @author Francesco Mangiacrapa at ISTI-CNR (francesco.mangiacrapa@isti.cnr.it) + * + * Oct 2, 2019 + */ +public class ValidateContentDisposition { + + public static Logger LOG = LoggerFactory.getLogger(GetResponseRecordFilter.class); + + + /** + * Valid value. + * + * @param req the req + * @param resolverClass the resolver class + * @param helpURI the help URI + * @param contentDispositionValue the content disposition value + * @return the content disposition value + */ + public static CONTENT_DISPOSITION_VALUE validValue(HttpServletRequest req, Class resolverClass, String helpURI, String contentDispositionValue){ + + CONTENT_DISPOSITION_VALUE toDispositionValue = CONTENT_DISPOSITION_VALUE.attachment; + //Validating the Content-Disposition value + if(contentDispositionValue!=null && !contentDispositionValue.isEmpty()) { + try { + //It must have a value of: "inline" or "attachement" + toDispositionValue = ConstantsResolver.CONTENT_DISPOSITION_VALUE.valueOf(contentDispositionValue); + }catch (Exception e) { + String allowedValues = String.format("{%s,%s}", CONTENT_DISPOSITION_VALUE.inline,CONTENT_DISPOSITION_VALUE.attachment); + String msg = String.format("Wrong parameter: '%s=%s'. Valid '%s' values are: %s",ConstantsResolver.QUERY_PARAM_CONTENTDISPOSITION,contentDispositionValue,ConstantsResolver.QUERY_PARAM_CONTENTDISPOSITION,allowedValues); + LOG.error(msg); + throw ExceptionManager.wrongParameterException(req, msg, resolverClass, helpURI); + } + } + + return toDispositionValue; + + } + +}