1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28 package org.apache.http.nio.integration;
29
30 import java.io.IOException;
31 import java.net.InetSocketAddress;
32 import java.util.Arrays;
33 import java.util.Collection;
34 import java.util.Queue;
35 import java.util.concurrent.ConcurrentLinkedQueue;
36 import java.util.concurrent.Future;
37 import java.util.concurrent.TimeUnit;
38
39 import org.apache.http.HttpException;
40 import org.apache.http.HttpHeaders;
41 import org.apache.http.HttpHost;
42 import org.apache.http.HttpRequest;
43 import org.apache.http.HttpRequestInterceptor;
44 import org.apache.http.HttpResponse;
45 import org.apache.http.HttpStatus;
46 import org.apache.http.HttpVersion;
47 import org.apache.http.ProtocolVersion;
48 import org.apache.http.entity.ContentType;
49 import org.apache.http.message.BasicHttpEntityEnclosingRequest;
50 import org.apache.http.message.BasicHttpRequest;
51 import org.apache.http.message.BasicHttpResponse;
52 import org.apache.http.nio.entity.NStringEntity;
53 import org.apache.http.nio.protocol.BasicAsyncRequestConsumer;
54 import org.apache.http.nio.protocol.BasicAsyncRequestHandler;
55 import org.apache.http.nio.protocol.BasicAsyncResponseProducer;
56 import org.apache.http.nio.protocol.HttpAsyncExchange;
57 import org.apache.http.nio.protocol.HttpAsyncExpectationVerifier;
58 import org.apache.http.nio.protocol.HttpAsyncRequestConsumer;
59 import org.apache.http.nio.protocol.HttpAsyncRequestHandler;
60 import org.apache.http.nio.reactor.ListenerEndpoint;
61 import org.apache.http.nio.testserver.HttpCoreNIOTestBase;
62 import org.apache.http.protocol.BasicHttpContext;
63 import org.apache.http.protocol.HTTP;
64 import org.apache.http.protocol.HttpContext;
65 import org.apache.http.protocol.HttpRequestHandler;
66 import org.apache.http.protocol.ImmutableHttpProcessor;
67 import org.apache.http.protocol.RequestConnControl;
68 import org.apache.http.protocol.RequestExpectContinue;
69 import org.apache.http.protocol.RequestTargetHost;
70 import org.apache.http.protocol.RequestUserAgent;
71 import org.apache.http.protocol.ResponseServer;
72 import org.apache.http.util.EntityUtils;
73 import org.junit.After;
74 import org.junit.Assert;
75 import org.junit.Before;
76 import org.junit.Test;
77 import org.junit.runner.RunWith;
78 import org.junit.runners.Parameterized;
79
80
81
82
83 @RunWith(Parameterized.class)
84 public class TestHttpAsyncHandlers extends HttpCoreNIOTestBase {
85
86 private final static long RESULT_TIMEOUT_SEC = 30;
87 private final static int REQ_NUM = 25;
88
89 @Parameterized.Parameters(name = "{0}")
90 public static Collection<Object[]> protocols() {
91 return Arrays.asList(new Object[][]{
92 { ProtocolScheme.http },
93 { ProtocolScheme.https },
94 });
95 }
96
97 public TestHttpAsyncHandlers(final ProtocolScheme scheme) {
98 super(scheme);
99 }
100
101 @Before
102 public void setUp() throws Exception {
103 initServer();
104 initClient();
105 }
106
107 @After
108 public void tearDown() throws Exception {
109 shutDownClient();
110 shutDownServer();
111 }
112
113 private HttpHost start() throws IOException, InterruptedException {
114 this.server.start();
115 this.client.start();
116
117 final ListenerEndpoint endpoint = this.server.getListenerEndpoint();
118 endpoint.waitFor();
119
120 final InetSocketAddress address = (InetSocketAddress) endpoint.getAddress();
121 return new HttpHost("localhost", address.getPort(), getScheme().name());
122 }
123
124 private static String createRequestUri(final String pattern, final int count) {
125 return pattern + "x" + count;
126 }
127
128 private static String createExpectedString(final String pattern, final int count) {
129 final StringBuilder buffer = new StringBuilder();
130 for (int i = 0; i < count; i++) {
131 buffer.append(pattern);
132 }
133 return buffer.toString();
134 }
135
136 @Test
137 public void testHttpGets() throws Exception {
138 this.server.registerHandler("*", new BasicAsyncRequestHandler(new SimpleRequestHandler()));
139 final HttpHost target = start();
140
141 this.client.setMaxPerRoute(3);
142 this.client.setMaxTotal(3);
143
144 final String pattern = RndTestPatternGenerator.generateText();
145 final int count = RndTestPatternGenerator.generateCount(1000);
146
147 final String expectedPattern = createExpectedString(pattern, count);
148
149 final Queue<Future<HttpResponse>> queue = new ConcurrentLinkedQueue<Future<HttpResponse>>();
150 for (int i = 0; i < REQ_NUM; i++) {
151 final BasicHttpRequest request = new BasicHttpRequest("GET", createRequestUri(pattern, count));
152 final Future<HttpResponse> future = this.client.execute(target, request);
153 queue.add(future);
154 }
155
156 while (!queue.isEmpty()) {
157 final Future<HttpResponse> future = queue.remove();
158 final HttpResponse response = future.get(RESULT_TIMEOUT_SEC, TimeUnit.SECONDS);
159 Assert.assertNotNull(response);
160 Assert.assertEquals(expectedPattern, EntityUtils.toString(response.getEntity()));
161 }
162 }
163
164 @Test
165 public void testHttpGetsCloseConnection() throws Exception {
166 this.server.registerHandler("*", new BasicAsyncRequestHandler(new SimpleRequestHandler()));
167 final HttpHost target = start();
168
169 this.client.setMaxPerRoute(3);
170 this.client.setMaxTotal(3);
171
172 final String pattern = RndTestPatternGenerator.generateText();
173 final int count = RndTestPatternGenerator.generateCount(1000);
174
175 final String expectedPattern = createExpectedString(pattern, count);
176
177 final Queue<Future<HttpResponse>> queue = new ConcurrentLinkedQueue<Future<HttpResponse>>();
178 for (int i = 0; i < REQ_NUM; i++) {
179 final BasicHttpRequest request = new BasicHttpRequest("GET", createRequestUri(pattern, count));
180 request.addHeader(HttpHeaders.CONNECTION, "Close");
181 final Future<HttpResponse> future = this.client.execute(target, request);
182 queue.add(future);
183 }
184
185 while (!queue.isEmpty()) {
186 final Future<HttpResponse> future = queue.remove();
187 final HttpResponse response = future.get(RESULT_TIMEOUT_SEC, TimeUnit.SECONDS);
188 Assert.assertNotNull(response);
189 Assert.assertEquals(expectedPattern, EntityUtils.toString(response.getEntity()));
190 }
191 }
192
193 @Test
194 public void testHttpGetIdentityTransfer() throws Exception {
195 this.server.setHttpProcessor(new ImmutableHttpProcessor(new ResponseServer("TEST-SERVER/1.1")));
196 this.server.registerHandler("*", new BasicAsyncRequestHandler(new SimpleRequestHandler()));
197 final HttpHost target = start();
198
199 this.client.setMaxPerRoute(3);
200 this.client.setMaxTotal(3);
201
202 final String pattern = RndTestPatternGenerator.generateText();
203 final int count = RndTestPatternGenerator.generateCount(1000);
204
205 final String expectedPattern = createExpectedString(pattern, count);
206
207 final Queue<Future<HttpResponse>> queue = new ConcurrentLinkedQueue<Future<HttpResponse>>();
208 for (int i = 0; i < REQ_NUM; i++) {
209 final BasicHttpRequest request = new BasicHttpRequest("GET", createRequestUri(pattern, count));
210 final Future<HttpResponse> future = this.client.execute(target, request);
211 queue.add(future);
212 }
213
214 while (!queue.isEmpty()) {
215 final Future<HttpResponse> future = queue.remove();
216 final HttpResponse response = future.get(RESULT_TIMEOUT_SEC, TimeUnit.SECONDS);
217 Assert.assertNotNull(response);
218 Assert.assertEquals(expectedPattern, EntityUtils.toString(response.getEntity()));
219 }
220 }
221
222 @Test
223 public void testHttpHeads() throws Exception {
224 this.server.registerHandler("*", new BasicAsyncRequestHandler(new SimpleRequestHandler()));
225 final HttpHost target = start();
226
227 this.client.setMaxPerRoute(3);
228 this.client.setMaxTotal(3);
229
230 final String pattern = RndTestPatternGenerator.generateText();
231 final int count = RndTestPatternGenerator.generateCount(1000);
232
233 final Queue<Future<HttpResponse>> queue = new ConcurrentLinkedQueue<Future<HttpResponse>>();
234 for (int i = 0; i < REQ_NUM; i++) {
235 final BasicHttpRequest request = new BasicHttpRequest("HEAD", createRequestUri(pattern, count));
236 final Future<HttpResponse> future = this.client.execute(target, request);
237 queue.add(future);
238 }
239
240 while (!queue.isEmpty()) {
241 final Future<HttpResponse> future = queue.remove();
242 final HttpResponse response = future.get(RESULT_TIMEOUT_SEC, TimeUnit.SECONDS);
243 Assert.assertNotNull(response);
244 Assert.assertEquals(HttpStatus.SC_OK, response.getStatusLine().getStatusCode());
245 }
246 }
247
248 @Test
249 public void testHttpHeadsCloseConnection() throws Exception {
250 this.server.registerHandler("*", new BasicAsyncRequestHandler(new SimpleRequestHandler()));
251 final HttpHost target = start();
252
253 this.client.setMaxPerRoute(3);
254 this.client.setMaxTotal(3);
255
256 final String pattern = RndTestPatternGenerator.generateText();
257 final int count = RndTestPatternGenerator.generateCount(1000);
258
259 final Queue<Future<HttpResponse>> queue = new ConcurrentLinkedQueue<Future<HttpResponse>>();
260 for (int i = 0; i < REQ_NUM; i++) {
261 final BasicHttpRequest request = new BasicHttpRequest("HEAD", createRequestUri(pattern, count));
262 request.addHeader(HttpHeaders.CONNECTION, "Close");
263 final Future<HttpResponse> future = this.client.execute(target, request);
264 queue.add(future);
265 }
266
267 while (!queue.isEmpty()) {
268 final Future<HttpResponse> future = queue.remove();
269 final HttpResponse response = future.get(RESULT_TIMEOUT_SEC, TimeUnit.SECONDS);
270 Assert.assertNotNull(response);
271 Assert.assertEquals(HttpStatus.SC_OK, response.getStatusLine().getStatusCode());
272 Assert.assertNull(response.getEntity());
273 }
274 }
275
276 @Test
277 public void testHttpPostsWithContentLength() throws Exception {
278 this.server.registerHandler("*", new BasicAsyncRequestHandler(new SimpleRequestHandler()));
279 final HttpHost target = start();
280
281 this.client.setMaxPerRoute(3);
282 this.client.setMaxTotal(3);
283
284 final String pattern = RndTestPatternGenerator.generateText();
285 final int count = RndTestPatternGenerator.generateCount(1000);
286
287 final String expectedPattern = createExpectedString(pattern, count);
288
289 final Queue<Future<HttpResponse>> queue = new ConcurrentLinkedQueue<Future<HttpResponse>>();
290 for (int i = 0; i < REQ_NUM; i++) {
291 final BasicHttpEntityEnclosingRequest request = new BasicHttpEntityEnclosingRequest(
292 "POST", createRequestUri(pattern, count));
293 final NStringEntity entity = new NStringEntity(expectedPattern, ContentType.DEFAULT_TEXT);
294 request.setEntity(entity);
295 final Future<HttpResponse> future = this.client.execute(target, request);
296 queue.add(future);
297 }
298
299 while (!queue.isEmpty()) {
300 final Future<HttpResponse> future = queue.remove();
301 final HttpResponse response = future.get(RESULT_TIMEOUT_SEC, TimeUnit.SECONDS);
302 Assert.assertNotNull(response);
303 Assert.assertEquals(expectedPattern, EntityUtils.toString(response.getEntity()));
304 }
305 }
306
307 @Test
308 public void testHttpPostsChunked() throws Exception {
309 this.server.registerHandler("*", new BasicAsyncRequestHandler(new SimpleRequestHandler()));
310 final HttpHost target = start();
311
312 this.client.setMaxPerRoute(3);
313 this.client.setMaxTotal(3);
314
315 final String pattern = RndTestPatternGenerator.generateText();
316 final int count = RndTestPatternGenerator.generateCount(1000);
317
318 final String expectedPattern = createExpectedString(pattern, count);
319
320 final Queue<Future<HttpResponse>> queue = new ConcurrentLinkedQueue<Future<HttpResponse>>();
321 for (int i = 0; i < REQ_NUM; i++) {
322 final BasicHttpEntityEnclosingRequest request = new BasicHttpEntityEnclosingRequest(
323 "POST", createRequestUri(pattern, count));
324 final NStringEntity entity = new NStringEntity(expectedPattern, ContentType.DEFAULT_TEXT);
325 entity.setChunked(true);
326 request.setEntity(entity);
327 final Future<HttpResponse> future = this.client.execute(target, request);
328 queue.add(future);
329 }
330
331 while (!queue.isEmpty()) {
332 final Future<HttpResponse> future = queue.remove();
333 final HttpResponse response = future.get(RESULT_TIMEOUT_SEC, TimeUnit.SECONDS);
334 Assert.assertNotNull(response);
335 Assert.assertEquals(expectedPattern, EntityUtils.toString(response.getEntity()));
336 }
337 }
338
339 @Test
340 public void testHttpPostsHTTP10() throws Exception {
341 this.server.registerHandler("*", new BasicAsyncRequestHandler(new SimpleRequestHandler()));
342 final HttpHost target = start();
343
344 this.client.setMaxPerRoute(3);
345 this.client.setMaxTotal(3);
346
347 final String pattern = RndTestPatternGenerator.generateText();
348 final int count = RndTestPatternGenerator.generateCount(1000);
349
350 final String expectedPattern = createExpectedString(pattern, count);
351
352 final Queue<Future<HttpResponse>> queue = new ConcurrentLinkedQueue<Future<HttpResponse>>();
353 for (int i = 0; i < REQ_NUM; i++) {
354 final BasicHttpEntityEnclosingRequest request = new BasicHttpEntityEnclosingRequest(
355 "POST", createRequestUri(pattern, count), HttpVersion.HTTP_1_0);
356 final NStringEntity entity = new NStringEntity(expectedPattern, ContentType.DEFAULT_TEXT);
357 request.setEntity(entity);
358 final Future<HttpResponse> future = this.client.execute(target, request);
359 queue.add(future);
360 }
361
362 while (!queue.isEmpty()) {
363 final Future<HttpResponse> future = queue.remove();
364 final HttpResponse response = future.get(RESULT_TIMEOUT_SEC, TimeUnit.SECONDS);
365 Assert.assertNotNull(response);
366 Assert.assertEquals(expectedPattern, EntityUtils.toString(response.getEntity()));
367 }
368 }
369
370 @Test
371 public void testHttpPostsNoEntity() throws Exception {
372 this.server.registerHandler("*", new BasicAsyncRequestHandler(new SimpleRequestHandler()));
373 final HttpHost target = start();
374
375 this.client.setMaxPerRoute(3);
376 this.client.setMaxTotal(3);
377
378 final String pattern = RndTestPatternGenerator.generateText();
379 final int count = RndTestPatternGenerator.generateCount(1000);
380
381 final Queue<Future<HttpResponse>> queue = new ConcurrentLinkedQueue<Future<HttpResponse>>();
382 for (int i = 0; i < REQ_NUM; i++) {
383 final BasicHttpEntityEnclosingRequest request = new BasicHttpEntityEnclosingRequest(
384 "POST", createRequestUri(pattern, count));
385 request.setEntity(null);
386 final Future<HttpResponse> future = this.client.execute(target, request);
387 queue.add(future);
388 }
389
390 while (!queue.isEmpty()) {
391 final Future<HttpResponse> future = queue.remove();
392 final HttpResponse response = future.get(RESULT_TIMEOUT_SEC, TimeUnit.SECONDS);
393 Assert.assertNotNull(response);
394 Assert.assertEquals(HttpStatus.SC_OK, response.getStatusLine().getStatusCode());
395 }
396 }
397
398 @Test
399 public void testHttpPostNoContentLength() throws Exception {
400 this.server.registerHandler("*", new BasicAsyncRequestHandler(new SimpleRequestHandler()));
401
402 this.client.setHttpProcessor(new ImmutableHttpProcessor(
403 new RequestTargetHost(),
404 new RequestConnControl(),
405 new RequestUserAgent(),
406 new RequestExpectContinue(true)));
407
408 final HttpHost target = start();
409
410 this.client.setMaxPerRoute(3);
411 this.client.setMaxTotal(3);
412
413 final String pattern = RndTestPatternGenerator.generateText();
414 final int count = RndTestPatternGenerator.generateCount(1000);
415
416 final BasicHttpEntityEnclosingRequest request = new BasicHttpEntityEnclosingRequest(
417 "POST", createRequestUri(pattern, count));
418 request.setEntity(null);
419
420 final Future<HttpResponse> future = this.client.execute(target, request);
421
422 final HttpResponse response = future.get(RESULT_TIMEOUT_SEC, TimeUnit.SECONDS);
423 Assert.assertNotNull(response);
424 Assert.assertEquals(HttpStatus.SC_OK, response.getStatusLine().getStatusCode());
425 }
426
427 @Test
428 public void testHttpPostIdentity() throws Exception {
429 this.server.registerHandler("*", new BasicAsyncRequestHandler(new SimpleRequestHandler()));
430
431 this.client.setHttpProcessor(new ImmutableHttpProcessor(
432 new HttpRequestInterceptor() {
433
434 @Override
435 public void process(
436 final HttpRequest request,
437 final HttpContext context) throws HttpException, IOException {
438 request.addHeader(HTTP.TRANSFER_ENCODING, "identity");
439 }
440
441 },
442 new RequestTargetHost(),
443 new RequestConnControl(),
444 new RequestUserAgent(),
445 new RequestExpectContinue(true)));
446
447 final HttpHost target = start();
448
449 this.client.setMaxPerRoute(3);
450 this.client.setMaxTotal(3);
451
452 final String pattern = RndTestPatternGenerator.generateText();
453 final int count = RndTestPatternGenerator.generateCount(1000);
454
455 final BasicHttpEntityEnclosingRequest request = new BasicHttpEntityEnclosingRequest(
456 "POST", createRequestUri(pattern, count));
457 request.setEntity(null);
458
459 final Future<HttpResponse> future = this.client.execute(target, request);
460
461 final HttpResponse response = future.get(RESULT_TIMEOUT_SEC, TimeUnit.SECONDS);
462 Assert.assertNotNull(response);
463 Assert.assertEquals(HttpStatus.SC_BAD_REQUEST, response.getStatusLine().getStatusCode());
464 }
465
466 @Test
467 public void testHttpPostsWithExpectContinue() throws Exception {
468 this.server.registerHandler("*", new BasicAsyncRequestHandler(new SimpleRequestHandler()));
469 final HttpHost target = start();
470
471 this.client.setMaxPerRoute(3);
472 this.client.setMaxTotal(3);
473
474 final String pattern = RndTestPatternGenerator.generateText();
475 final int count = RndTestPatternGenerator.generateCount(1000);
476
477 final String expectedPattern = createExpectedString(pattern, count);
478
479 final Queue<Future<HttpResponse>> queue = new ConcurrentLinkedQueue<Future<HttpResponse>>();
480 for (int i = 0; i < REQ_NUM; i++) {
481 final BasicHttpEntityEnclosingRequest request = new BasicHttpEntityEnclosingRequest(
482 "POST", createRequestUri(pattern, count));
483 final NStringEntity entity = new NStringEntity(expectedPattern, ContentType.DEFAULT_TEXT);
484 request.setEntity(entity);
485
486 final HttpContext context = new BasicHttpContext();
487 final Future<HttpResponse> future = this.client.execute(target, request, context);
488 queue.add(future);
489 }
490
491 while (!queue.isEmpty()) {
492 final Future<HttpResponse> future = queue.remove();
493 final HttpResponse response = future.get(RESULT_TIMEOUT_SEC, TimeUnit.SECONDS);
494 Assert.assertNotNull(response);
495 Assert.assertEquals(expectedPattern, EntityUtils.toString(response.getEntity()));
496 }
497 }
498
499 @Test
500 public void testHttpPostsWithExpectationVerification() throws Exception {
501 this.server.registerHandler("*", new BasicAsyncRequestHandler(new SimpleRequestHandler()));
502 this.server.setExpectationVerifier(new HttpAsyncExpectationVerifier() {
503
504 @Override
505 public void verify(
506 final HttpAsyncExchange httpexchange,
507 final HttpContext context) throws HttpException {
508 final HttpRequest request = httpexchange.getRequest();
509 ProtocolVersion ver = request.getRequestLine().getProtocolVersion();
510 final String s = request.getRequestLine().getUri();
511 if (!s.equals("AAAAAx10")) {
512 if (!ver.lessEquals(HttpVersion.HTTP_1_1)) {
513 ver = HttpVersion.HTTP_1_1;
514 }
515 final BasicHttpResponse response = new BasicHttpResponse(ver,
516 HttpStatus.SC_EXPECTATION_FAILED, "Expectation failed");
517 response.setEntity(new NStringEntity("Expectation failed", ContentType.TEXT_PLAIN));
518 httpexchange.submitResponse(new BasicAsyncResponseProducer(response));
519 } else {
520 httpexchange.submitResponse();
521 }
522 }
523
524 });
525
526 final HttpHost target = start();
527
528 final BasicHttpEntityEnclosingRequest request1 = new BasicHttpEntityEnclosingRequest(
529 "POST", createRequestUri("AAAAA", 10));
530 request1.setEntity(new NStringEntity(createExpectedString("AAAAA", 10)));
531 final BasicHttpEntityEnclosingRequest request2 = new BasicHttpEntityEnclosingRequest(
532 "POST", createRequestUri("AAAAA", 10));
533 request2.setEntity(new NStringEntity(createExpectedString("AAAAA", 10)));
534 final BasicHttpEntityEnclosingRequest request3 = new BasicHttpEntityEnclosingRequest(
535 "POST", createRequestUri("BBBBB", 10));
536 request3.setEntity(new NStringEntity(createExpectedString("BBBBB", 10)));
537
538 final HttpRequest[] requests = new HttpRequest[] { request1, request2, request3 };
539
540 final Queue<Future<HttpResponse>> queue = new ConcurrentLinkedQueue<Future<HttpResponse>>();
541 for (final HttpRequest request : requests) {
542 final HttpContext context = new BasicHttpContext();
543 final Future<HttpResponse> future = this.client.execute(target, request, context);
544 queue.add(future);
545 }
546
547 final Future<HttpResponse> future1 = queue.remove();
548 final HttpResponse response1 = future1.get();
549 Assert.assertEquals(HttpStatus.SC_OK, response1.getStatusLine().getStatusCode());
550
551 final Future<HttpResponse> future2 = queue.remove();
552 final HttpResponse response2 = future2.get();
553 Assert.assertEquals(HttpStatus.SC_OK, response2.getStatusLine().getStatusCode());
554
555 final Future<HttpResponse> future3 = queue.remove();
556 final HttpResponse response3 = future3.get();
557 Assert.assertEquals(HttpStatus.SC_EXPECTATION_FAILED, response3.getStatusLine().getStatusCode());
558 }
559
560 @Test
561 public void testHttpHeadsDelayedResponse() throws Exception {
562
563 class DelayedRequestHandler implements HttpAsyncRequestHandler<HttpRequest> {
564
565 private final SimpleRequestHandler requestHandler;
566
567 public DelayedRequestHandler() {
568 super();
569 this.requestHandler = new SimpleRequestHandler();
570 }
571
572 @Override
573 public HttpAsyncRequestConsumer<HttpRequest> processRequest(
574 final HttpRequest request,
575 final HttpContext context) {
576 return new BasicAsyncRequestConsumer();
577 }
578
579 @Override
580 public void handle(
581 final HttpRequest request,
582 final HttpAsyncExchange httpexchange,
583 final HttpContext context) throws HttpException, IOException {
584 ProtocolVersion ver = request.getRequestLine().getProtocolVersion();
585 if (!ver.lessEquals(HttpVersion.HTTP_1_1)) {
586 ver = HttpVersion.HTTP_1_1;
587 }
588 final BasicHttpResponse response = new BasicHttpResponse(ver, HttpStatus.SC_OK, "OK");
589 new Thread() {
590 @Override
591 public void run() {
592
593 try { Thread.sleep(100); } catch(final InterruptedException ie) {}
594
595 try {
596 requestHandler.handle(request, response, context);
597 } catch (final Exception ex) {
598 response.setStatusCode(HttpStatus.SC_INTERNAL_SERVER_ERROR);
599 }
600 httpexchange.submitResponse(new BasicAsyncResponseProducer(response));
601 }
602 }.start();
603 }
604
605 }
606
607 this.server.registerHandler("*", new DelayedRequestHandler());
608 final HttpHost target = start();
609
610 this.client.setMaxPerRoute(3);
611 this.client.setMaxTotal(3);
612
613 final String pattern = RndTestPatternGenerator.generateText();
614 final int count = RndTestPatternGenerator.generateCount(1000);
615
616 final Queue<Future<HttpResponse>> queue = new ConcurrentLinkedQueue<Future<HttpResponse>>();
617 for (int i = 0; i < REQ_NUM; i++) {
618 final BasicHttpRequest request = new BasicHttpRequest("HEAD", createRequestUri(pattern, count));
619 final Future<HttpResponse> future = this.client.execute(target, request);
620 queue.add(future);
621 }
622
623 while (!queue.isEmpty()) {
624 final Future<HttpResponse> future = queue.remove();
625 final HttpResponse response = future.get(RESULT_TIMEOUT_SEC, TimeUnit.SECONDS);
626 Assert.assertNotNull(response);
627 Assert.assertEquals(HttpStatus.SC_OK, response.getStatusLine().getStatusCode());
628 }
629 }
630
631 @Test
632 public void testHttpPostsWithExpectationVerificationDelayedResponse() throws Exception {
633 this.server.registerHandler("*", new BasicAsyncRequestHandler(new SimpleRequestHandler()));
634 this.server.setExpectationVerifier(new HttpAsyncExpectationVerifier() {
635
636 @Override
637 public void verify(
638 final HttpAsyncExchange httpexchange,
639 final HttpContext context) throws HttpException {
640 new Thread() {
641 @Override
642 public void run() {
643
644 try {
645 Thread.sleep(100);
646 } catch (final InterruptedException ie) {
647 }
648
649 final HttpRequest request = httpexchange.getRequest();
650 ProtocolVersion ver = request.getRequestLine().getProtocolVersion();
651 final String s = request.getRequestLine().getUri();
652 if (!s.equals("AAAAAx10")) {
653 if (!ver.lessEquals(HttpVersion.HTTP_1_1)) {
654 ver = HttpVersion.HTTP_1_1;
655 }
656 final BasicHttpResponse response = new BasicHttpResponse(ver,
657 HttpStatus.SC_EXPECTATION_FAILED, "Expectation failed");
658 response.setEntity(new NStringEntity("Expectation failed", ContentType.TEXT_PLAIN));
659 httpexchange.submitResponse(new BasicAsyncResponseProducer(response));
660 } else {
661 httpexchange.submitResponse();
662 }
663 }
664 }.start();
665 }
666
667 });
668 final HttpHost target = start();
669
670 final BasicHttpEntityEnclosingRequest request1 = new BasicHttpEntityEnclosingRequest(
671 "POST", createRequestUri("AAAAA", 10));
672 request1.setEntity(new NStringEntity(createExpectedString("AAAAA", 10)));
673 final BasicHttpEntityEnclosingRequest request2 = new BasicHttpEntityEnclosingRequest(
674 "POST", createRequestUri("AAAAA", 10));
675 request2.setEntity(new NStringEntity(createExpectedString("AAAAA", 10)));
676 final BasicHttpEntityEnclosingRequest request3 = new BasicHttpEntityEnclosingRequest(
677 "POST", createRequestUri("BBBBB", 10));
678 request3.setEntity(new NStringEntity(createExpectedString("BBBBB", 10)));
679
680 final HttpRequest[] requests = new HttpRequest[] { request1, request2, request3 };
681
682 final Queue<Future<HttpResponse>> queue = new ConcurrentLinkedQueue<Future<HttpResponse>>();
683 for (final HttpRequest request : requests) {
684 final HttpContext context = new BasicHttpContext();
685 final Future<HttpResponse> future = this.client.execute(target, request, context);
686 queue.add(future);
687 }
688
689 final Future<HttpResponse> future1 = queue.remove();
690 final HttpResponse response1 = future1.get();
691 Assert.assertEquals(HttpStatus.SC_OK, response1.getStatusLine().getStatusCode());
692
693 final Future<HttpResponse> future2 = queue.remove();
694 final HttpResponse response2 = future2.get();
695 Assert.assertEquals(HttpStatus.SC_OK, response2.getStatusLine().getStatusCode());
696
697 final Future<HttpResponse> future3 = queue.remove();
698 final HttpResponse response3 = future3.get();
699 Assert.assertEquals(HttpStatus.SC_EXPECTATION_FAILED, response3.getStatusLine().getStatusCode());
700 }
701
702 @Test
703 public void testHttpExceptionInHandler() throws Exception {
704
705 class FailingRequestHandler implements HttpAsyncRequestHandler<HttpRequest> {
706
707 public FailingRequestHandler() {
708 super();
709 }
710
711 @Override
712 public HttpAsyncRequestConsumer<HttpRequest> processRequest(
713 final HttpRequest request,
714 final HttpContext context) {
715 return new BasicAsyncRequestConsumer();
716 }
717
718 @Override
719 public void handle(
720 final HttpRequest request,
721 final HttpAsyncExchange httpexchange,
722 final HttpContext context) throws HttpException, IOException {
723 throw new HttpException("Boom");
724 }
725
726 }
727
728 this.server.registerHandler("*", new FailingRequestHandler());
729 final HttpHost target = start();
730
731 this.client.setMaxPerRoute(3);
732 this.client.setMaxTotal(3);
733
734 final String pattern = RndTestPatternGenerator.generateText();
735 final int count = RndTestPatternGenerator.generateCount(1000);
736
737 final Queue<Future<HttpResponse>> queue = new ConcurrentLinkedQueue<Future<HttpResponse>>();
738 for (int i = 0; i < 1; i++) {
739 final BasicHttpRequest request = new BasicHttpRequest("GET", createRequestUri(pattern, count));
740 final Future<HttpResponse> future = this.client.execute(target, request);
741 queue.add(future);
742 }
743
744 while (!queue.isEmpty()) {
745 final Future<HttpResponse> future = queue.remove();
746 final HttpResponse response = future.get(RESULT_TIMEOUT_SEC, TimeUnit.SECONDS);
747 Assert.assertNotNull(response);
748 Assert.assertEquals(HttpStatus.SC_INTERNAL_SERVER_ERROR, response.getStatusLine().getStatusCode());
749 }
750 }
751
752 @Test
753 public void testNoServiceHandler() throws Exception {
754 final HttpHost target = start();
755
756 this.client.setMaxPerRoute(3);
757 this.client.setMaxTotal(3);
758
759 final String pattern = RndTestPatternGenerator.generateText();
760 final int count = RndTestPatternGenerator.generateCount(1000);
761
762 final Queue<Future<HttpResponse>> queue = new ConcurrentLinkedQueue<Future<HttpResponse>>();
763 for (int i = 0; i < REQ_NUM; i++) {
764 final BasicHttpRequest request = new BasicHttpRequest("GET", createRequestUri(pattern, count));
765 final Future<HttpResponse> future = this.client.execute(target, request);
766 queue.add(future);
767 }
768
769 while (!queue.isEmpty()) {
770 final Future<HttpResponse> future = queue.remove();
771 final HttpResponse response = future.get(RESULT_TIMEOUT_SEC, TimeUnit.SECONDS);
772 Assert.assertNotNull(response);
773 Assert.assertEquals(HttpStatus.SC_NOT_IMPLEMENTED, response.getStatusLine().getStatusCode());
774 }
775 }
776
777 @Test
778 public void testResponseNoContent() throws Exception {
779 this.server.registerHandler("*", new BasicAsyncRequestHandler(new HttpRequestHandler() {
780
781 @Override
782 public void handle(
783 final HttpRequest request,
784 final HttpResponse response,
785 final HttpContext context) throws HttpException, IOException {
786 response.setStatusCode(HttpStatus.SC_NO_CONTENT);
787 }
788
789 }));
790 final HttpHost target = start();
791
792 this.client.setMaxPerRoute(3);
793 this.client.setMaxTotal(3);
794
795 final Queue<Future<HttpResponse>> queue = new ConcurrentLinkedQueue<Future<HttpResponse>>();
796 for (int i = 0; i < REQ_NUM; i++) {
797 final BasicHttpRequest request = new BasicHttpRequest("GET", "/");
798 final Future<HttpResponse> future = this.client.execute(target, request);
799 queue.add(future);
800 }
801
802 while (!queue.isEmpty()) {
803 final Future<HttpResponse> future = queue.remove();
804 final HttpResponse response = future.get(RESULT_TIMEOUT_SEC, TimeUnit.SECONDS);
805 Assert.assertNotNull(response);
806 Assert.assertNull(response.getEntity());
807 }
808 }
809
810 }