Skip to content

Commit

Permalink
ALS-7014: Implement handling of signed URLs from HPDS (#202)
Browse files Browse the repository at this point in the history
  • Loading branch information
ramari16 authored Sep 6, 2024
1 parent 755015a commit e24ff0b
Show file tree
Hide file tree
Showing 15 changed files with 159 additions and 20 deletions.
2 changes: 1 addition & 1 deletion pic-sure-api-data/pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@
<parent>
<groupId>edu.harvard.hms.dbmi.avillach</groupId>
<artifactId>pic-sure-api</artifactId>
<version>2.1.0-SNAPSHOT</version>
<version>2.2.0-SNAPSHOT</version>
</parent>
<artifactId>pic-sure-api-data</artifactId>
<name>pic-sure-api-data</name>
Expand Down
2 changes: 1 addition & 1 deletion pic-sure-api-war/pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@
<parent>
<groupId>edu.harvard.hms.dbmi.avillach</groupId>
<artifactId>pic-sure-api</artifactId>
<version>2.1.0-SNAPSHOT</version>
<version>2.2.0-SNAPSHOT</version>
</parent>
<artifactId>pic-sure-api-war</artifactId>
<name>PIC-SURE API war</name>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -154,20 +154,37 @@ public QueryStatus queryStatus(
@POST
@Path("/query/{queryId}/result")
@Operation(
summary = "Returns result for given query",
responses = {@ApiResponse(
responseCode = "200", description = "Query result", content = @Content(schema = @Schema(implementation = Response.class))
)}
summary = "Returns result for given query",
responses = {@ApiResponse(
responseCode = "200", description = "Query result", content = @Content(schema = @Schema(implementation = Response.class))
)}
)
@Produces(MediaType.APPLICATION_OCTET_STREAM)
public Response queryResult(
@Parameter(
description = "The UUID of the query to fetch the status of. The UUID is "
+ "returned by the /query endpoint as the \"picsureResultId\" in the response object"
) @PathParam("queryId") UUID queryId, @Parameter QueryRequest credentialsQueryRequest, @Context HttpHeaders headers
@Parameter(
description = "The UUID of the query to fetch the status of. The UUID is "
+ "returned by the /query endpoint as the \"picsureResultId\" in the response object"
) @PathParam("queryId") UUID queryId, @Parameter QueryRequest credentialsQueryRequest, @Context HttpHeaders headers
) {
return queryService.queryResult(queryId, credentialsQueryRequest, headers);
}
@POST
@Path("/query/{queryId}/signed-url")
@Operation(
summary = "Returns a signed url for given query",
responses = {@ApiResponse(
responseCode = "200", description = "Query result", content = @Content(schema = @Schema(implementation = Response.class))
)}
)
@Produces(MediaType.APPLICATION_JSON)
public Response queryResultSignedUrl(
@Parameter(
description = "The UUID of the query to fetch the status of. The UUID is "
+ "returned by the /query endpoint as the \"picsureResultId\" in the response object"
) @PathParam("queryId") UUID queryId, @Parameter QueryRequest credentialsQueryRequest, @Context HttpHeaders headers
) {
return queryService.queryResultSignedUrl(queryId, credentialsQueryRequest, headers);
}

@POST
@Path("/query/sync")
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -149,15 +149,55 @@ public Response queryResult(UUID queryId, QueryRequest credentialsQueryRequest,
}

logger.info(
"path=/query/{queryId}/result, resourceId={}, requestSource={}, queryRequest={}", queryId,
Utilities.getRequestSourceFromHeader(headers), Utilities.convertQueryRequestToString(mapper, credentialsQueryRequest)
"path=/query/{queryId}/result, resourceId={}, requestSource={}, queryRequest={}", queryId,
Utilities.getRequestSourceFromHeader(headers), Utilities.convertQueryRequestToString(mapper, credentialsQueryRequest)
);


credentialsQueryRequest.getResourceCredentials().put(ResourceWebClient.BEARER_TOKEN_KEY, resource.getToken());
return resourceWebClient.queryResult(resource.getResourceRSPath(), query.getResourceResultId(), credentialsQueryRequest);
}

/**
* Returns a signed URL from HPDS that is a reference to the query result
*
* @param queryId - id of target resource
* @param credentialsQueryRequest - contains resource specific credentials object
* @return Response containing a signed URL
*/
@Transactional
public Response queryResultSignedUrl(UUID queryId, QueryRequest credentialsQueryRequest, HttpHeaders headers) {
if (queryId == null) {
throw new ProtocolException(ProtocolException.MISSING_QUERY_ID);
}
Query query = queryRepo.getById(queryId);
if (query == null) {
throw new ProtocolException(ProtocolException.QUERY_NOT_FOUND + queryId.toString());
}
Resource resource = query.getResource();
if (resource == null) {
throw new ApplicationException(ApplicationException.MISSING_RESOURCE);
}
if (resource.getResourceRSPath() == null) {
throw new ApplicationException(ApplicationException.MISSING_RESOURCE_PATH);
}
if (credentialsQueryRequest == null) {
throw new ProtocolException(ProtocolException.MISSING_DATA);
}
if (credentialsQueryRequest.getResourceCredentials() == null) {
credentialsQueryRequest.setResourceCredentials(new HashMap<>());
}

logger.info(
"path=/query/{queryId}/signed-url, resourceId={}, requestSource={}, queryRequest={}", queryId,
Utilities.getRequestSourceFromHeader(headers), Utilities.convertQueryRequestToString(mapper, credentialsQueryRequest)
);


credentialsQueryRequest.getResourceCredentials().put(ResourceWebClient.BEARER_TOKEN_KEY, resource.getToken());
return resourceWebClient.queryResultSignedUrl(resource.getResourceRSPath(), query.getResourceResultId(), credentialsQueryRequest);
}

/**
* Streams the result for a query by looking up the target resource from the database and calling the target resource for a result.
*
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@
<parent>
<groupId>edu.harvard.hms.dbmi.avillach</groupId>
<artifactId>pic-sure-resources</artifactId>
<version>2.1.0-SNAPSHOT</version>
<version>2.2.0-SNAPSHOT</version>
</parent>
<artifactId>pic-sure-aggregate-data-sharing-resource</artifactId>
<name>pic-sure-aggregate-data-sharing-resource</name>
Expand Down
2 changes: 1 addition & 1 deletion pic-sure-resources/pic-sure-ga4gh-dos/pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@
<parent>
<groupId>edu.harvard.hms.dbmi.avillach</groupId>
<artifactId>pic-sure-resources</artifactId>
<version>2.1.0-SNAPSHOT</version>
<version>2.2.0-SNAPSHOT</version>
</parent>
<artifactId>pic-sure-ga4gh-dos</artifactId>
<name>pic-sure-ga4gh-dos</name>
Expand Down
2 changes: 1 addition & 1 deletion pic-sure-resources/pic-sure-passthrough-resource/pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@
<parent>
<groupId>edu.harvard.hms.dbmi.avillach</groupId>
<artifactId>pic-sure-resources</artifactId>
<version>2.1.0-SNAPSHOT</version>
<version>2.2.0-SNAPSHOT</version>
</parent>
<artifactId>pic-sure-passthrough-resource</artifactId>
<name>pic-sure-passthrough-resource</name>
Expand Down
2 changes: 1 addition & 1 deletion pic-sure-resources/pic-sure-resource-api/pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@
<parent>
<groupId>edu.harvard.hms.dbmi.avillach</groupId>
<artifactId>pic-sure-resources</artifactId>
<version>2.1.0-SNAPSHOT</version>
<version>2.2.0-SNAPSHOT</version>
</parent>
<artifactId>pic-sure-resource-api</artifactId>
<name>pic-sure-resource-api</name>
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
package edu.harvard.dbmi.avillach.domain;

import com.fasterxml.jackson.annotation.JsonCreator;
import com.fasterxml.jackson.annotation.JsonProperty;

import java.util.Objects;

public class SignedUrlResponse {

private final String signedUrl;

@JsonCreator
public SignedUrlResponse(@JsonProperty("signedUrl") String signedUrl) {
this.signedUrl = signedUrl;
}

public String getSignedUrl() {
return signedUrl;
}

@Override
public boolean equals(Object o) {
if (this == o) return true;
if (o == null || getClass() != o.getClass()) return false;
SignedUrlResponse that = (SignedUrlResponse) o;
return Objects.equals(signedUrl, that.signedUrl);
}

@Override
public int hashCode() {
return Objects.hash(signedUrl);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -211,6 +211,37 @@ public Response queryResult(String rsURL, String queryId, QueryRequest queryRequ
throw new ResourceInterfaceException("Error getting results", e);
}
}

public Response queryResultSignedUrl(String rsURL, String queryId, QueryRequest queryRequest){
logger.debug("Calling ResourceWebClient querySignedUrl()");
try {
if (queryRequest == null){
throw new ProtocolException(ProtocolException.MISSING_DATA);
}
if (queryRequest.getResourceCredentials() == null){
throw new NotAuthorizedException("Missing credentials");
}
if (rsURL == null){
throw new ApplicationException(ApplicationException.MISSING_RESOURCE_PATH);
}
if (queryId == null){
throw new ProtocolException(ProtocolException.MISSING_QUERY_ID);
}
String pathName = "/query/" + queryId + "/signed-url";
String body = json.writeValueAsString(queryRequest);
HttpResponse resourcesResponse = retrievePostResponse(composeURL(rsURL, pathName), createHeaders(queryRequest.getResourceCredentials()), body);
if (resourcesResponse.getStatusLine().getStatusCode() != 200) {
logger.error("ResourceRS did not return a 200");
throwResponseError(resourcesResponse, rsURL);
}
return Response.ok(resourcesResponse.getEntity().getContent()).build();
} catch (JsonProcessingException e){
logger.error("Unable to encode resource credentials");
throw new NotAuthorizedException("Unable to encode resource credentials", e);
} catch (IOException e){
throw new ResourceInterfaceException("Error getting results", e);
}
}


public Response queryFormat(String rsURL, QueryRequest queryRequest){
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
package edu.harvard.dbmi.avillach.domain;

import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.ObjectMapper;
import org.junit.Test;
import static org.junit.Assert.*;

public class SignedUrlResponseTest {

@Test
public void testJacksonSerialization() throws JsonProcessingException {
SignedUrlResponse signedUrlResponse = new SignedUrlResponse("http://google.com/");
ObjectMapper objectMapper = new ObjectMapper();
String serialized = objectMapper.writeValueAsString(signedUrlResponse);
SignedUrlResponse deserialized = objectMapper.readValue(serialized, SignedUrlResponse.class);
assertEquals(signedUrlResponse.getSignedUrl(), deserialized.getSignedUrl());
}
}
2 changes: 1 addition & 1 deletion pic-sure-resources/pic-sure-visualization-resource/pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@
<parent>
<groupId>edu.harvard.hms.dbmi.avillach</groupId>
<artifactId>pic-sure-resources</artifactId>
<version>2.1.0-SNAPSHOT</version>
<version>2.2.0-SNAPSHOT</version>
</parent>
<artifactId>pic-sure-visualization-resource</artifactId>
<name>PIC-SURE Visualization Resource</name>
Expand Down
2 changes: 1 addition & 1 deletion pic-sure-resources/pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
<parent>
<artifactId>pic-sure-api</artifactId>
<groupId>edu.harvard.hms.dbmi.avillach</groupId>
<version>2.1.0-SNAPSHOT</version>
<version>2.2.0-SNAPSHOT</version>
</parent>
<artifactId>pic-sure-resources</artifactId>
<packaging>pom</packaging>
Expand Down
2 changes: 1 addition & 1 deletion pic-sure-util/pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@
<parent>
<artifactId>pic-sure-api</artifactId>
<groupId>edu.harvard.hms.dbmi.avillach</groupId>
<version>2.1.0-SNAPSHOT</version>
<version>2.2.0-SNAPSHOT</version>
</parent>
<modelVersion>4.0.0</modelVersion>
<artifactId>pic-sure-util</artifactId>
Expand Down
2 changes: 1 addition & 1 deletion pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
<modelVersion>4.0.0</modelVersion>
<groupId>edu.harvard.hms.dbmi.avillach</groupId>
<artifactId>pic-sure-api</artifactId>
<version>2.1.0-SNAPSHOT</version>
<version>2.2.0-SNAPSHOT</version>
<packaging>pom</packaging>
<name>pic-sure-api</name>
<modules>
Expand Down

0 comments on commit e24ff0b

Please sign in to comment.