SSI in static POST
Igor Sysoev
is at rambler-co.ru
Thu Mar 5 00:29:10 MSK 2009
Прилагаемый патч для 0.7.39 разрешает POST в статический файл с последующей
обработкой POST'а в SSI. Первый include, которому необходимо тело POST,
должен иметь параметр wait="yes". Если кому-то это нужно, пусть тестирует:
в 0.7 я пока это включать не хочу.
--
Игорь Сысоев
http://sysoev.ru
-------------- next part --------------
Index: src/http/ngx_http_request.c
===================================================================
--- src/http/ngx_http_request.c (revision 1864)
+++ src/http/ngx_http_request.c (working copy)
@@ -2225,6 +2225,19 @@
r->lingering_time = ngx_time() + (time_t) (clcf->lingering_time / 1000);
ngx_add_timer(rev, clcf->lingering_timeout);
return;
+
+ } else {
+
+ r->expect_tested = 1;
+
+ if (ngx_http_discard_request_body(r) != NGX_OK) {
+ ngx_http_close_connection(c);
+ return;
+ }
+
+ if (r->discard_body) {
+ return;
+ }
}
c->log->action = "closing request";
Index: src/http/ngx_http_core_module.c
===================================================================
--- src/http/ngx_http_core_module.c (revision 1864)
+++ src/http/ngx_http_core_module.c (working copy)
@@ -686,9 +686,6 @@
};
-static ngx_str_t ngx_http_core_get_method = { 3, (u_char *) "GET " };
-
-
void
ngx_http_handler(ngx_http_request_t *r)
{
@@ -2019,9 +2016,7 @@
ngx_http_clear_accept_ranges(sr);
ngx_http_clear_last_modified(sr);
- sr->request_body = r->request_body;
-
- sr->method = NGX_HTTP_GET;
+ sr->method = r->method;
sr->http_version = r->http_version;
sr->request_line = r->request_line;
@@ -2039,7 +2034,7 @@
sr->waited = (flags & NGX_HTTP_SUBREQUEST_WAITED) != 0;
sr->unparsed_uri = r->unparsed_uri;
- sr->method_name = ngx_http_core_get_method;
+ sr->method_name = r->method_name;
sr->http_protocol = r->http_protocol;
if (ngx_http_set_exten(sr) != NGX_OK) {
Index: src/http/ngx_http_upstream.c
===================================================================
--- src/http/ngx_http_upstream.c (revision 1864)
+++ src/http/ngx_http_upstream.c (working copy)
@@ -356,8 +356,8 @@
}
}
- if (r->request_body) {
- u->request_bufs = r->request_body->bufs;
+ if (r->main->request_body) {
+ u->request_bufs = r->main->request_body->bufs;
}
if (u->create_request(r) != NGX_OK) {
@@ -720,9 +720,10 @@
static void
ngx_http_upstream_connect(ngx_http_request_t *r, ngx_http_upstream_t *u)
{
- ngx_int_t rc;
- ngx_time_t *tp;
- ngx_connection_t *c;
+ ngx_int_t rc;
+ ngx_time_t *tp;
+ ngx_connection_t *c;
+ ngx_http_request_body_t *rb;
r->connection->log->action = "connecting to upstream";
@@ -804,14 +805,14 @@
}
}
- if (r->request_body
- && r->request_body->buf
- && r->request_body->temp_file
- && r == r->main)
- {
+ rb = r->main->request_body;
+
+ if (r == r->main && rb && rb->buf && rb->temp_file) {
+
/*
- * the r->request_body->buf can be reused for one request only,
- * the subrequests should allocate their own temporay bufs
+ * the r->main->request_body->buf can be reused in ngx_output_chain()
+ * for reading file in single request only, therefore
+ * subrequests should allocate their own temporary bufs
*/
u->output.free = ngx_alloc_chain_link(r->pool);
@@ -821,13 +822,13 @@
return;
}
- u->output.free->buf = r->request_body->buf;
+ u->output.free->buf = rb->buf;
u->output.free->next = NULL;
u->output.allocated = 1;
- r->request_body->buf->pos = r->request_body->buf->start;
- r->request_body->buf->last = r->request_body->buf->start;
- r->request_body->buf->tag = u->output.tag;
+ rb->buf->pos = rb->buf->start;
+ rb->buf->last = rb->buf->start;
+ rb->buf->tag = u->output.tag;
}
u->request_sent = 0;
@@ -948,8 +949,8 @@
/* reinit the subrequest's ngx_output_chain() context */
- if (r->request_body && r->request_body->temp_file
- && r != r->main && u->output.buf)
+ if (r != r->main && u->output.buf
+ && r->main->request_body && r->main->request_body->temp_file)
{
u->output.free = ngx_alloc_chain_link(r->pool);
if (u->output.free == NULL) {
@@ -1639,6 +1640,7 @@
ngx_connection_t *c;
ngx_pool_cleanup_t *cl;
ngx_pool_cleanup_file_t *clf;
+ ngx_http_request_body_t *rb;
ngx_http_core_loc_conf_t *clcf;
rc = ngx_http_send_header(r);
@@ -1650,15 +1652,19 @@
u->header_sent = 1;
- if (r->request_body && r->request_body->temp_file) {
+ rb = r->main->request_body;
+
+ if (rb && rb->temp_file) {
+
for (cl = r->pool->cleanup; cl; cl = cl->next) {
+
if (cl->handler == ngx_pool_cleanup_file) {
clf = cl->data;
- if (clf->fd == r->request_body->temp_file->file.fd) {
+ if (clf->fd == rb->temp_file->file.fd) {
cl->handler(clf);
cl->handler = NULL;
- r->request_body->temp_file->file.fd = NGX_INVALID_FILE;
+ rb->temp_file->file.fd = NGX_INVALID_FILE;
break;
}
}
Index: src/http/ngx_http_request_body.c
===================================================================
--- src/http/ngx_http_request_body.c (revision 1864)
+++ src/http/ngx_http_request_body.c (working copy)
@@ -20,7 +20,7 @@
/*
* on completion ngx_http_read_client_request_body() adds to
- * r->request_body->bufs one or two bufs:
+ * r->main->request_body->bufs one or two bufs:
* *) one memory buf that was preread in r->header_in;
* *) one memory or file buf that contains the rest of the body
*/
@@ -34,44 +34,47 @@
ngx_buf_t *b;
ngx_chain_t *cl, **next;
ngx_temp_file_t *tf;
+ ngx_http_request_t *mr;
ngx_http_request_body_t *rb;
ngx_http_core_loc_conf_t *clcf;
- if (r->request_body || r->discard_body) {
+ mr = r->main;
+
+ if (mr->request_body || mr->discard_body) {
post_handler(r);
return NGX_OK;
}
- if (ngx_http_test_expect(r) != NGX_OK) {
+ if (ngx_http_test_expect(mr) != NGX_OK) {
return NGX_HTTP_INTERNAL_SERVER_ERROR;
}
- rb = ngx_pcalloc(r->pool, sizeof(ngx_http_request_body_t));
+ rb = ngx_pcalloc(mr->pool, sizeof(ngx_http_request_body_t));
if (rb == NULL) {
return NGX_HTTP_INTERNAL_SERVER_ERROR;
}
- r->request_body = rb;
+ mr->request_body = rb;
- if (r->headers_in.content_length_n < 0) {
+ if (mr->headers_in.content_length_n < 0) {
post_handler(r);
return NGX_OK;
}
clcf = ngx_http_get_module_loc_conf(r, ngx_http_core_module);
- if (r->headers_in.content_length_n == 0) {
+ if (mr->headers_in.content_length_n == 0) {
if (r->request_body_in_file_only) {
- tf = ngx_pcalloc(r->pool, sizeof(ngx_temp_file_t));
+ tf = ngx_pcalloc(mr->pool, sizeof(ngx_temp_file_t));
if (tf == NULL) {
return NGX_HTTP_INTERNAL_SERVER_ERROR;
}
tf->file.fd = NGX_INVALID_FILE;
- tf->file.log = r->connection->log;
+ tf->file.log = mr->connection->log;
tf->path = clcf->client_body_temp_path;
- tf->pool = r->pool;
+ tf->pool = mr->pool;
tf->warn = "a client request body is buffered to a temporary file";
tf->log_level = r->request_body_file_log_level;
tf->persistent = r->request_body_in_persistent_file;
@@ -106,27 +109,27 @@
* rb->rest = 0;
*/
- preread = r->header_in->last - r->header_in->pos;
+ preread = mr->header_in->last - mr->header_in->pos;
if (preread) {
/* there is the pre-read part of the request body */
- ngx_log_debug1(NGX_LOG_DEBUG_HTTP, r->connection->log, 0,
+ ngx_log_debug1(NGX_LOG_DEBUG_HTTP, mr->connection->log, 0,
"http client request body preread %uz", preread);
- b = ngx_calloc_buf(r->pool);
+ b = ngx_calloc_buf(mr->pool);
if (b == NULL) {
return NGX_HTTP_INTERNAL_SERVER_ERROR;
}
b->temporary = 1;
- b->start = r->header_in->pos;
- b->pos = r->header_in->pos;
- b->last = r->header_in->last;
- b->end = r->header_in->end;
+ b->start = mr->header_in->pos;
+ b->pos = mr->header_in->pos;
+ b->last = mr->header_in->last;
+ b->end = mr->header_in->end;
- rb->bufs = ngx_alloc_chain_link(r->pool);
+ rb->bufs = ngx_alloc_chain_link(mr->pool);
if (rb->bufs == NULL) {
return NGX_HTTP_INTERNAL_SERVER_ERROR;
}
@@ -136,15 +139,15 @@
rb->buf = b;
- if ((off_t) preread >= r->headers_in.content_length_n) {
+ if ((off_t) preread >= mr->headers_in.content_length_n) {
/* the whole request body was pre-read */
- r->header_in->pos += (size_t) r->headers_in.content_length_n;
- r->request_length += r->headers_in.content_length_n;
+ mr->header_in->pos += (size_t) mr->headers_in.content_length_n;
+ mr->request_length += mr->headers_in.content_length_n;
- if (r->request_body_in_file_only) {
- if (ngx_http_write_request_body(r, rb->bufs) != NGX_OK) {
+ if (mr->request_body_in_file_only) {
+ if (ngx_http_write_request_body(mr, rb->bufs) != NGX_OK) {
return NGX_HTTP_INTERNAL_SERVER_ERROR;
}
}
@@ -158,11 +161,11 @@
* to not consider the body as pipelined request in
* ngx_http_set_keepalive()
*/
- r->header_in->pos = r->header_in->last;
+ mr->header_in->pos = mr->header_in->last;
- r->request_length += preread;
+ mr->request_length += preread;
- rb->rest = r->headers_in.content_length_n - preread;
+ rb->rest = mr->headers_in.content_length_n - preread;
if (rb->rest <= (off_t) (b->end - b->last)) {
@@ -179,7 +182,7 @@
} else {
b = NULL;
- rb->rest = r->headers_in.content_length_n;
+ rb->rest = mr->headers_in.content_length_n;
next = &rb->bufs;
}
@@ -200,12 +203,12 @@
b = NULL;
}
- rb->buf = ngx_create_temp_buf(r->pool, size);
+ rb->buf = ngx_create_temp_buf(mr->pool, size);
if (rb->buf == NULL) {
return NGX_HTTP_INTERNAL_SERVER_ERROR;
}
- cl = ngx_alloc_chain_link(r->pool);
+ cl = ngx_alloc_chain_link(mr->pool);
if (cl == NULL) {
return NGX_HTTP_INTERNAL_SERVER_ERROR;
}
@@ -250,7 +253,7 @@
rc = ngx_http_do_read_client_request_body(r);
if (rc >= NGX_HTTP_SPECIAL_RESPONSE) {
- ngx_http_finalize_request(r, rc);
+ ngx_http_finalize_request(r->main, rc);
}
}
@@ -262,11 +265,13 @@
ssize_t n;
ngx_buf_t *b;
ngx_connection_t *c;
+ ngx_http_request_t *mr;
ngx_http_request_body_t *rb;
ngx_http_core_loc_conf_t *clcf;
c = r->connection;
- rb = r->request_body;
+ mr = r->main;
+ rb = mr->request_body;
ngx_log_debug0(NGX_LOG_DEBUG_HTTP, c->log, 0,
"http read client request body");
@@ -275,7 +280,7 @@
for ( ;; ) {
if (rb->buf->last == rb->buf->end) {
- if (ngx_http_write_request_body(r, rb->to_write) != NGX_OK) {
+ if (ngx_http_write_request_body(mr, rb->to_write) != NGX_OK) {
return NGX_HTTP_INTERNAL_SERVER_ERROR;
}
@@ -310,7 +315,7 @@
rb->buf->last += n;
rb->rest -= n;
- r->request_length += n;
+ mr->request_length += n;
if (rb->rest == 0) {
break;
@@ -348,7 +353,7 @@
/* save the last part */
- if (ngx_http_write_request_body(r, rb->to_write) != NGX_OK) {
+ if (ngx_http_write_request_body(mr, rb->to_write) != NGX_OK) {
return NGX_HTTP_INTERNAL_SERVER_ERROR;
}
Index: src/http/ngx_http_variables.c
===================================================================
--- src/http/ngx_http_variables.c (revision 1864)
+++ src/http/ngx_http_variables.c (working copy)
@@ -1481,17 +1481,21 @@
ngx_http_variable_request_body_file(ngx_http_request_t *r,
ngx_http_variable_value_t *v, uintptr_t data)
{
- if (r->request_body == NULL || r->request_body->temp_file == NULL) {
+ ngx_http_request_body_t *rb;
+
+ rb = r->request_body;
+
+ if (rb == NULL || rb->temp_file == NULL) {
v->not_found = 1;
return NGX_OK;
}
- v->len = r->request_body->temp_file->file.name.len;
+ v->len = rb->temp_file->file.name.len;
v->valid = 1;
v->no_cacheable = 0;
v->not_found = 0;
- v->data = r->request_body->temp_file->file.name.data;
+ v->data = rb->temp_file->file.name.data;
return NGX_OK;
}
Index: src/http/modules/ngx_http_dav_module.c
===================================================================
--- src/http/modules/ngx_http_dav_module.c (revision 1864)
+++ src/http/modules/ngx_http_dav_module.c (working copy)
@@ -220,7 +220,7 @@
ngx_log_debug1(NGX_LOG_DEBUG_HTTP, r->connection->log, 0,
"http put filename: \"%s\"", path.data);
- temp = &r->request_body->temp_file->file.name;
+ temp = &r->main->request_body->temp_file->file.name;
if (ngx_file_info(path.data, &fi) == -1) {
status = NGX_HTTP_CREATED;
@@ -259,7 +259,7 @@
if (date != NGX_ERROR) {
ext.time = date;
- ext.fd = r->request_body->temp_file->file.fd;
+ ext.fd = r->main->request_body->temp_file->file.fd;
}
}
Index: src/http/modules/ngx_http_static_module.c
===================================================================
--- src/http/modules/ngx_http_static_module.c (revision 1864)
+++ src/http/modules/ngx_http_static_module.c (working copy)
@@ -197,14 +197,13 @@
#endif
- if (r->method & NGX_HTTP_POST) {
- return NGX_HTTP_NOT_ALLOWED;
- }
+ if (r->method & (NGX_HTTP_GET|NGX_HTTP_HEAD)) {
- rc = ngx_http_discard_request_body(r);
+ rc = ngx_http_discard_request_body(r);
- if (rc != NGX_OK) {
- return rc;
+ if (rc != NGX_OK) {
+ return rc;
+ }
}
log->action = "sending response to client";
Index: src/http/modules/perl/nginx.xs
===================================================================
--- src/http/modules/perl/nginx.xs (revision 1864)
+++ src/http/modules/perl/nginx.xs (working copy)
@@ -384,25 +384,25 @@
CODE:
dXSTARG;
- ngx_http_request_t *r;
- size_t len;
+ ngx_http_request_t *r;
+ ngx_http_request_body_t *rb;
+ size_t len;
ngx_http_perl_set_request(r);
- if (r->request_body == NULL
- || r->request_body->temp_file
- || r->request_body->bufs == NULL)
- {
+ rb = r->main->request_body;
+
+ if (rb == NULL || rb->temp_file || rb->bufs == NULL) {
XSRETURN_UNDEF;
}
- len = r->request_body->bufs->buf->last - r->request_body->bufs->buf->pos;
+ len = rb->bufs->buf->last - rb->bufs->buf->pos;
if (len == 0) {
XSRETURN_UNDEF;
}
- ngx_http_perl_set_targ(r->request_body->bufs->buf->pos, len);
+ ngx_http_perl_set_targ(rb->bufs->buf->pos, len);
ST(0) = TARG;
@@ -412,16 +412,19 @@
CODE:
dXSTARG;
- ngx_http_request_t *r;
+ ngx_http_request_t *r;
+ ngx_http_request_body_t *rb;
ngx_http_perl_set_request(r);
- if (r->request_body == NULL || r->request_body->temp_file == NULL) {
+ rb = r->main->request_body;
+
+ if (rb == NULL || rb->temp_file == NULL) {
XSRETURN_UNDEF;
}
- ngx_http_perl_set_targ(r->request_body->temp_file->file.name.data,
- r->request_body->temp_file->file.name.len);
+ ngx_http_perl_set_targ(rb->temp_file->file.name.data,
+ rb->temp_file->file.name.len);
ST(0) = TARG;
More information about the nginx-ru
mailing list