Skip to content

Commit f086e28

Browse files
committed
bugfix: the request body was not discarded properly in the content handler when the request body was not read yet. thanks Peter Sabaini for the report in openresty/openresty#32. bugfix: ensure that subrequests never read the main request's request body by automatically reading the main request body before initiating subrequests.
1 parent 82139f8 commit f086e28

File tree

3 files changed

+146
-4
lines changed

3 files changed

+146
-4
lines changed

src/ngx_http_echo_handler.c

Lines changed: 40 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -239,21 +239,53 @@ ngx_http_echo_run_cmds(ngx_http_request_t *r)
239239
break;
240240

241241
case echo_opcode_echo_location_async:
242+
if (!r->request_body) {
243+
/* we require reading the request body before doing
244+
* subrequests */
245+
246+
ctx->next_handler_cmd--; /* re-run the current cmd */
247+
goto read_request_body;
248+
}
249+
242250
dd("found opcode echo location async...");
243251
rc = ngx_http_echo_exec_echo_location_async(r, ctx,
244252
computed_args);
245253
break;
246254

247255
case echo_opcode_echo_location:
256+
if (!r->request_body) {
257+
/* we require reading the request body before doing
258+
* subrequests */
259+
260+
ctx->next_handler_cmd--; /* re-run the current cmd */
261+
goto read_request_body;
262+
}
263+
248264
return ngx_http_echo_exec_echo_location(r, ctx, computed_args);
249265

250266
case echo_opcode_echo_subrequest_async:
267+
if (!r->request_body) {
268+
/* we require reading the request body before doing
269+
* subrequests */
270+
271+
ctx->next_handler_cmd--; /* re-run the current cmd */
272+
goto read_request_body;
273+
}
274+
251275
dd("found opcode echo subrequest async...");
252276
rc = ngx_http_echo_exec_echo_subrequest_async(r, ctx,
253277
computed_args);
254278
break;
255279

256280
case echo_opcode_echo_subrequest:
281+
if (!r->request_body) {
282+
/* we require reading the request body before doing
283+
* subrequests */
284+
285+
ctx->next_handler_cmd--; /* re-run the current cmd */
286+
goto read_request_body;
287+
}
288+
257289
return ngx_http_echo_exec_echo_subrequest(r, ctx, computed_args);
258290

259291
case echo_opcode_echo_sleep:
@@ -277,6 +309,8 @@ ngx_http_echo_run_cmds(ngx_http_request_t *r)
277309
break;
278310

279311
case echo_opcode_echo_read_request_body:
312+
313+
read_request_body:
280314
ctx->wait_read_request_body = 0;
281315

282316
rc = ngx_http_echo_exec_echo_read_request_body(r, ctx);
@@ -329,6 +363,12 @@ ngx_http_echo_run_cmds(ngx_http_request_t *r)
329363
return rc;
330364
}
331365

366+
if (!r->request_body) {
367+
if (ngx_http_discard_request_body(r) != NGX_OK) {
368+
return NGX_ERROR;
369+
}
370+
}
371+
332372
return NGX_OK;
333373
}
334374

t/echo.t

Lines changed: 33 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3,9 +3,9 @@
33
use lib 'lib';
44
use Test::Nginx::Socket;
55

6-
repeat_each(1);
6+
repeat_each(2);
77

8-
plan tests => repeat_each() * (2 * blocks() + 1);
8+
plan tests => repeat_each() * (2 * blocks() + 5);
99

1010
#$Test::Nginx::LWP::LogLevel = 'debug';
1111

@@ -338,3 +338,34 @@ world
338338
HEAD /echo
339339
--- response_body
340340
341+
342+
343+
=== TEST 24: POST
344+
--- config
345+
location /echo {
346+
echo hello;
347+
echo world;
348+
}
349+
--- pipelined_requests eval
350+
["POST /echo
351+
blah blah", "POST /echo
352+
foo bar baz"]
353+
--- response_body eval
354+
["hello\nworld\n","hello\nworld\n"]
355+
356+
357+
358+
=== TEST 25: POST
359+
--- config
360+
location /echo {
361+
echo_sleep 0.001;
362+
echo hello;
363+
echo world;
364+
}
365+
--- pipelined_requests eval
366+
["POST /echo
367+
blah blah", "POST /echo
368+
foo bar baz"]
369+
--- response_body eval
370+
["hello\nworld\n","hello\nworld\n"]
371+

t/request-info.t

Lines changed: 73 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -427,10 +427,9 @@ Content-Length: 5\r
427427
428428
429429
430-
=== TEST 20: small header (POST body) - in subrequests
430+
=== TEST 20: small header (POST body) - in subrequests (location)
431431
--- config
432432
location /t {
433-
echo_read_request_body;
434433
echo -n $echo_client_request_headers;
435434
}
436435
location /main {
@@ -535,3 +534,75 @@ Cookie: " . ("C" x 1200) . "\r\n\r\n"
535534
--- no_error_log
536535
[error]
537536
537+
538+
539+
=== TEST 24: small header (POST body) - in subrequests (location_async)
540+
--- config
541+
location /t {
542+
echo -n $echo_client_request_headers;
543+
}
544+
location /main {
545+
echo_location_async /t;
546+
}
547+
548+
--- request
549+
POST /main
550+
hello
551+
--- response_body eval
552+
qq{POST /main HTTP/1.1\r
553+
Host: localhost\r
554+
Connection: Close\r
555+
Content-Length: 5\r
556+
\r
557+
}
558+
--- no_error_log
559+
[error]
560+
561+
562+
563+
=== TEST 25: small header (POST body) - in subrequests (subrequest)
564+
--- config
565+
location /t {
566+
echo -n $echo_client_request_headers;
567+
}
568+
location /main {
569+
echo_subrequest GET /t;
570+
}
571+
572+
--- request
573+
POST /main
574+
hello
575+
--- response_body eval
576+
qq{POST /main HTTP/1.1\r
577+
Host: localhost\r
578+
Connection: Close\r
579+
Content-Length: 5\r
580+
\r
581+
}
582+
--- no_error_log
583+
[error]
584+
585+
586+
587+
=== TEST 26: small header (POST body) - in subrequests (subrequest_async)
588+
--- config
589+
location /t {
590+
echo -n $echo_client_request_headers;
591+
}
592+
location /main {
593+
echo_subrequest_async GET /t;
594+
}
595+
596+
--- request
597+
POST /main
598+
hello
599+
--- response_body eval
600+
qq{POST /main HTTP/1.1\r
601+
Host: localhost\r
602+
Connection: Close\r
603+
Content-Length: 5\r
604+
\r
605+
}
606+
--- no_error_log
607+
[error]
608+

0 commit comments

Comments
 (0)