Skip to content

Commit

Permalink
Support CompletionStage<Response>
Browse files Browse the repository at this point in the history
Signed-off-by: jansupol <jan.supol@oracle.com>
  • Loading branch information
jansupol committed Aug 1, 2022
1 parent 82e89ac commit 8cf7cab
Show file tree
Hide file tree
Showing 3 changed files with 32 additions and 6 deletions.
@@ -1,5 +1,5 @@
/*
* Copyright (c) 2011, 2020 Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 2011, 2022 Oracle and/or its affiliates. All rights reserved.
*
* This program and the accompanying materials are made available under the
* terms of the Eclipse Public License v. 2.0, which is available at
Expand Down Expand Up @@ -85,6 +85,7 @@ public class ResourceMethodInvoker implements Endpoint, ResourceInfo {
private final Type invocableResponseType;
private final boolean canUseInvocableResponseType;
private final boolean isCompletionStageResponseType;
private final boolean isCompletionStageResponseResponseType; // CompletionStage<Response>
private final Type completionStageResponseType;
private final ResourceMethodDispatcher dispatcher;
private final Method resourceMethod;
Expand Down Expand Up @@ -313,6 +314,8 @@ protected void configure() {
&& CompletionStage.class.isAssignableFrom((Class<?>) ((ParameterizedType) invocableResponseType).getRawType());
this.completionStageResponseType =
isCompletionStageResponseType ? ((ParameterizedType) invocableResponseType).getActualTypeArguments()[0] : null;
this.isCompletionStageResponseResponseType = Class.class.isInstance(completionStageResponseType)
&& Response.class.isAssignableFrom((Class<?>) completionStageResponseType);
}

private <T> void addNameBoundProviders(
Expand Down Expand Up @@ -465,7 +468,7 @@ private Response invoke(final RequestProcessingContext context, final Object res
if (canUseInvocableResponseType
&& response.hasEntity()
&& !(response.getEntityType() instanceof ParameterizedType)) {
response.setEntityType(unwrapInvocableResponseType(context.request()));
response.setEntityType(unwrapInvocableResponseType(context.request(), response.getEntityType()));
}

return response;
Expand All @@ -484,10 +487,10 @@ private Response invoke(final RequestProcessingContext context, final Object res
return jaxrsResponse;
}

private Type unwrapInvocableResponseType(ContainerRequest request) {
private Type unwrapInvocableResponseType(ContainerRequest request, Type entityType) {
if (isCompletionStageResponseType
&& request.resolveProperty(ServerProperties.UNWRAP_COMPLETION_STAGE_IN_WRITER_ENABLE, Boolean.FALSE)) {
return completionStageResponseType;
return isCompletionStageResponseResponseType ? entityType : completionStageResponseType;
}
return invocableResponseType;
}
Expand Down
5 changes: 5 additions & 0 deletions tests/e2e-server/pom.xml
Expand Up @@ -100,6 +100,11 @@
<artifactId>jersey-media-json-processing</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.glassfish.jersey.media</groupId>
<artifactId>jersey-media-json-binding</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.glassfish.jersey.media</groupId>
<artifactId>jersey-media-json-gson</artifactId>
Expand Down
@@ -1,5 +1,5 @@
/*
* Copyright (c) 2017, 2020 Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 2017, 2022 Oracle and/or its affiliates. All rights reserved.
*
* This program and the accompanying materials are made available under the
* terms of the Eclipse Public License v. 2.0, which is available at
Expand All @@ -18,6 +18,7 @@

import org.glassfish.jersey.server.ResourceConfig;
import org.glassfish.jersey.server.ServerProperties;
import org.glassfish.jersey.server.ServerRuntime;
import org.glassfish.jersey.test.JerseyTest;
import org.junit.Test;

Expand Down Expand Up @@ -64,7 +65,8 @@ public class CompletionStageTest extends JerseyTest {

@Override
protected Application configure() {
return new ResourceConfig(CompletionStageResource.class, DataBeanWriter.class);
return new ResourceConfig(CompletionStageResource.class, DataBeanWriter.class)
.property(ServerProperties.UNWRAP_COMPLETION_STAGE_IN_WRITER_ENABLE, Boolean.TRUE);
}

@Test
Expand Down Expand Up @@ -104,6 +106,14 @@ public void testGetCompletedAsync() {
assertThat(response.readEntity(String.class), is(ENTITY));
}

@Test
public void testGetCompletedAsyncResponse() {
Response response = target("cs/completedAsyncResponse").request().get();

assertThat(response.getStatus(), is(200));
assertThat(response.readEntity(List.class).get(0), is(ENTITY));
}

@Test
public void testGetException400Async() {
Response response = target("cs/exception400Async").request().get();
Expand Down Expand Up @@ -213,6 +223,14 @@ public CompletionStage<String> getCompletedAsync() {
return cs;
}

@GET
@Path("/completedAsyncResponse")
public CompletionStage<Response> getCompletedAsyncResponse() {
CompletableFuture<Response> cs = new CompletableFuture<>();
delaySubmit(() -> cs.complete(Response.ok().entity(Collections.singletonList(ENTITY)).build()));
return cs;
}

@GET
@Path("/exception400Async")
public CompletionStage<String> getException400Async() {
Expand Down

0 comments on commit 8cf7cab

Please sign in to comment.