Browse Source

Fix timing issue with obtaining async result

Issue: SPR-11516
pull/482/head
Rossen Stoyanchev 11 years ago
parent
commit
705efc5bdf
  1. 27
      spring-test/src/main/java/org/springframework/test/web/servlet/DefaultMvcResult.java
  2. 24
      spring-test/src/test/java/org/springframework/test/web/servlet/samples/standalone/AsyncTests.java

27
spring-test/src/main/java/org/springframework/test/web/servlet/DefaultMvcResult.java

@ -1,5 +1,5 @@ @@ -1,5 +1,5 @@
/*
* Copyright 2002-2012 the original author or authors.
* Copyright 2002-2014 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@ -36,6 +36,9 @@ import org.springframework.web.servlet.support.RequestContextUtils; @@ -36,6 +36,9 @@ import org.springframework.web.servlet.support.RequestContextUtils;
*/
class DefaultMvcResult implements MvcResult {
private static final Object RESULT_NONE = new Object();
private final MockHttpServletRequest mockRequest;
private final MockHttpServletResponse mockResponse;
@ -48,7 +51,7 @@ class DefaultMvcResult implements MvcResult { @@ -48,7 +51,7 @@ class DefaultMvcResult implements MvcResult {
private Exception resolvedException;
private Object asyncResult;
private Object asyncResult = RESULT_NONE;
private CountDownLatch asyncResultLatch;
@ -123,18 +126,18 @@ class DefaultMvcResult implements MvcResult { @@ -123,18 +126,18 @@ class DefaultMvcResult implements MvcResult {
@Override
public Object getAsyncResult(long timeout) {
// MockHttpServletRequest type doesn't have async methods
HttpServletRequest request = this.mockRequest;
if ((timeout != 0) && request.isAsyncStarted()) {
if (timeout == -1) {
timeout = request.getAsyncContext().getTimeout();
}
if (!awaitAsyncResult(timeout)) {
throw new IllegalStateException(
"Gave up waiting on async result from handler [" + this.handler + "] to complete");
if (this.asyncResult == RESULT_NONE) {
if ((timeout != 0) && this.mockRequest.isAsyncStarted()) {
if (timeout == -1) {
timeout = this.mockRequest.getAsyncContext().getTimeout();
}
if (!awaitAsyncResult(timeout) && this.asyncResult == RESULT_NONE) {
throw new IllegalStateException(
"Gave up waiting on async result from handler [" + this.handler + "] to complete");
}
}
}
return this.asyncResult;
return (this.asyncResult == RESULT_NONE ? null : this.asyncResult);
}
private boolean awaitAsyncResult(long timeout) {

24
spring-test/src/test/java/org/springframework/test/web/servlet/samples/standalone/AsyncTests.java

@ -1,5 +1,5 @@ @@ -1,5 +1,5 @@
/*
* Copyright 2002-2012 the original author or authors.
* Copyright 2002-2014 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@ -89,6 +89,20 @@ public class AsyncTests { @@ -89,6 +89,20 @@ public class AsyncTests {
.andExpect(content().string("{\"name\":\"Joe\",\"someDouble\":0.0,\"someBoolean\":false}"));
}
@Test
@Ignore
public void testDeferredResultWithSetValue() throws Exception {
MvcResult mvcResult = this.mockMvc.perform(get("/1").param("deferredResultWithSetValue", "true"))
.andExpect(request().asyncStarted())
.andExpect(request().asyncResult(new Person("Joe")))
.andReturn();
this.mockMvc.perform(asyncDispatch(mvcResult))
.andExpect(status().isOk())
.andExpect(content().contentType(MediaType.APPLICATION_JSON))
.andExpect(content().string("{\"name\":\"Joe\",\"someDouble\":0.0,\"someBoolean\":false}"));
}
@Controller
private static class AsyncController {
@ -115,6 +129,14 @@ public class AsyncTests { @@ -115,6 +129,14 @@ public class AsyncTests {
return deferredResult;
}
@RequestMapping(value="/{id}", params="deferredResultWithSetValue", produces="application/json")
@ResponseBody
public DeferredResult<Person> getDeferredResultWithSetValue() {
DeferredResult<Person> deferredResult = new DeferredResult<Person>();
deferredResult.setResult(new Person("Joe"));
return deferredResult;
}
public void onMessage(String name) {
for (DeferredResult<Person> deferredResult : this.deferredResults) {
deferredResult.setResult(new Person(name));

Loading…
Cancel
Save