Mercurial > hg > nginx-ranges
comparison src/http/ngx_http_upstream.c @ 420:b246022ef454 NGINX_0_7_18
nginx 0.7.18
*) Change: the "underscores_in_headers" directive; now nginx does not
allows underscores in a client request header line names.
*) Feature: the ngx_http_secure_link_module.
*) Feature: the "real_ip_header" directive supports any header.
*) Feature: the "log_subrequest" directive.
*) Feature: the $realpath_root variable.
*) Feature: the "http_502" and "http_504" parameters of the
"proxy_next_upstream" directive.
*) Bugfix: the "http_503" parameter of the "proxy_next_upstream" or
"fastcgi_next_upstream" directives did not work.
*) Bugfix: nginx might send a "Transfer-Encoding: chunked" heaer line
for HEAD requests.
*) Bugfix: now accept threshold depends on worker_connections.
author | Igor Sysoev <http://sysoev.ru> |
---|---|
date | Mon, 13 Oct 2008 00:00:00 +0400 |
parents | a8e3f1441eec |
children | b4f69f2ef02c |
comparison
equal
deleted
inserted
replaced
417:b453a4324c60 | 420:b246022ef454 |
---|---|
20 ngx_http_upstream_t *u); | 20 ngx_http_upstream_t *u); |
21 static void ngx_http_upstream_send_request(ngx_http_request_t *r, | 21 static void ngx_http_upstream_send_request(ngx_http_request_t *r, |
22 ngx_http_upstream_t *u); | 22 ngx_http_upstream_t *u); |
23 static void ngx_http_upstream_send_request_handler(ngx_event_t *wev); | 23 static void ngx_http_upstream_send_request_handler(ngx_event_t *wev); |
24 static void ngx_http_upstream_process_header(ngx_event_t *rev); | 24 static void ngx_http_upstream_process_header(ngx_event_t *rev); |
25 static ngx_int_t ngx_http_upstream_test_next(ngx_http_request_t *r, | |
26 ngx_http_upstream_t *u); | |
27 static ngx_int_t ngx_http_upstream_intercept_errors(ngx_http_request_t *r, | |
28 ngx_http_upstream_t *u); | |
25 static ngx_int_t ngx_http_upstream_test_connect(ngx_connection_t *c); | 29 static ngx_int_t ngx_http_upstream_test_connect(ngx_connection_t *c); |
26 static void ngx_http_upstream_process_body_in_memory(ngx_event_t *rev); | 30 static void ngx_http_upstream_process_body_in_memory(ngx_event_t *rev); |
27 static void ngx_http_upstream_send_response(ngx_http_request_t *r, | 31 static void ngx_http_upstream_send_response(ngx_http_request_t *r, |
28 ngx_http_upstream_t *u); | 32 ngx_http_upstream_t *u); |
29 static void | 33 static void |
280 | 284 |
281 { ngx_null_string, NULL, NULL, 0, 0, 0 } | 285 { ngx_null_string, NULL, NULL, 0, 0, 0 } |
282 }; | 286 }; |
283 | 287 |
284 | 288 |
289 static ngx_http_upstream_next_t ngx_http_upstream_next_errors[] = { | |
290 { 500, NGX_HTTP_UPSTREAM_FT_HTTP_500 }, | |
291 { 502, NGX_HTTP_UPSTREAM_FT_HTTP_502 }, | |
292 { 503, NGX_HTTP_UPSTREAM_FT_HTTP_503 }, | |
293 { 504, NGX_HTTP_UPSTREAM_FT_HTTP_504 }, | |
294 { 404, NGX_HTTP_UPSTREAM_FT_HTTP_404 }, | |
295 { 0, 0 } | |
296 }; | |
297 | |
285 void | 298 void |
286 ngx_http_upstream_init(ngx_http_request_t *r) | 299 ngx_http_upstream_init(ngx_http_request_t *r) |
287 { | 300 { |
288 ngx_str_t *host; | 301 ngx_str_t *host; |
289 ngx_uint_t i; | 302 ngx_uint_t i; |
1045 ngx_list_part_t *part; | 1058 ngx_list_part_t *part; |
1046 ngx_table_elt_t *h; | 1059 ngx_table_elt_t *h; |
1047 ngx_connection_t *c; | 1060 ngx_connection_t *c; |
1048 ngx_http_request_t *r; | 1061 ngx_http_request_t *r; |
1049 ngx_http_upstream_t *u; | 1062 ngx_http_upstream_t *u; |
1050 ngx_http_err_page_t *err_page; | |
1051 ngx_http_core_loc_conf_t *clcf; | |
1052 ngx_http_upstream_header_t *hh; | 1063 ngx_http_upstream_header_t *hh; |
1053 ngx_http_upstream_main_conf_t *umcf; | 1064 ngx_http_upstream_main_conf_t *umcf; |
1054 | 1065 |
1055 c = rev->data; | 1066 c = rev->data; |
1056 r = c->data; | 1067 r = c->data; |
1172 return; | 1183 return; |
1173 } | 1184 } |
1174 | 1185 |
1175 /* rc == NGX_OK */ | 1186 /* rc == NGX_OK */ |
1176 | 1187 |
1177 if (u->headers_in.status_n >= NGX_HTTP_BAD_REQUEST | 1188 if (u->headers_in.status_n >= NGX_HTTP_BAD_REQUEST) { |
1178 && r->subrequest_in_memory) | 1189 |
1179 { | 1190 if (r->subrequest_in_memory) { |
1180 u->buffer.last = u->buffer.pos; | 1191 u->buffer.last = u->buffer.pos; |
1181 } | 1192 } |
1182 | 1193 |
1183 if (u->headers_in.status_n == NGX_HTTP_INTERNAL_SERVER_ERROR) { | 1194 if (ngx_http_upstream_test_next(r, u) == NGX_OK) { |
1184 | 1195 return; |
1185 if (u->peer.tries > 1 | 1196 } |
1186 && (u->conf->next_upstream & NGX_HTTP_UPSTREAM_FT_HTTP_500)) | 1197 |
1187 { | 1198 if (ngx_http_upstream_intercept_errors(r, u) == NGX_OK) { |
1188 ngx_http_upstream_next(r, u, NGX_HTTP_UPSTREAM_FT_HTTP_500); | 1199 return; |
1189 return; | |
1190 } | |
1191 | |
1192 #if (NGX_HTTP_CACHE) | |
1193 | |
1194 if (u->peer.tries == 0 | |
1195 && u->stale | |
1196 && (u->conf->use_stale & NGX_HTTP_UPSTREAM_FT_HTTP_500)) | |
1197 { | |
1198 ngx_http_upstream_finalize_request(r, u, | |
1199 ngx_http_send_cached_response(r)); | |
1200 return; | |
1201 } | |
1202 | |
1203 #endif | |
1204 } | |
1205 | |
1206 if (u->headers_in.status_n == NGX_HTTP_NOT_FOUND) { | |
1207 | |
1208 if (u->peer.tries > 1 | |
1209 && u->conf->next_upstream & NGX_HTTP_UPSTREAM_FT_HTTP_404) | |
1210 { | |
1211 ngx_http_upstream_next(r, u, NGX_HTTP_UPSTREAM_FT_HTTP_404); | |
1212 return; | |
1213 } | |
1214 | |
1215 if (u->conf->intercept_404) { | |
1216 ngx_http_upstream_finalize_request(r, u, NGX_HTTP_NOT_FOUND); | |
1217 return; | |
1218 } | |
1219 } | |
1220 | |
1221 | |
1222 if (u->headers_in.status_n >= NGX_HTTP_BAD_REQUEST | |
1223 && u->conf->intercept_errors) | |
1224 { | |
1225 clcf = ngx_http_get_module_loc_conf(r, ngx_http_core_module); | |
1226 | |
1227 if (clcf->error_pages) { | |
1228 | |
1229 err_page = clcf->error_pages->elts; | |
1230 for (i = 0; i < clcf->error_pages->nelts; i++) { | |
1231 if (err_page[i].status == (ngx_int_t) u->headers_in.status_n) { | |
1232 | |
1233 if (u->headers_in.status_n == NGX_HTTP_UNAUTHORIZED) { | |
1234 | |
1235 r->headers_out.www_authenticate = | |
1236 ngx_list_push(&r->headers_out.headers); | |
1237 | |
1238 if (r->headers_out.www_authenticate == NULL) { | |
1239 ngx_http_upstream_finalize_request(r, u, | |
1240 NGX_HTTP_INTERNAL_SERVER_ERROR); | |
1241 return; | |
1242 } | |
1243 | |
1244 *r->headers_out.www_authenticate = | |
1245 *u->headers_in.www_authenticate; | |
1246 } | |
1247 | |
1248 ngx_http_upstream_finalize_request(r, u, | |
1249 u->headers_in.status_n); | |
1250 return; | |
1251 } | |
1252 } | |
1253 } | 1200 } |
1254 } | 1201 } |
1255 | 1202 |
1256 umcf = ngx_http_get_module_main_conf(r, ngx_http_upstream_module); | 1203 umcf = ngx_http_get_module_main_conf(r, ngx_http_upstream_module); |
1257 | 1204 |
1401 } | 1348 } |
1402 | 1349 |
1403 rev->handler = ngx_http_upstream_process_body_in_memory; | 1350 rev->handler = ngx_http_upstream_process_body_in_memory; |
1404 | 1351 |
1405 ngx_http_upstream_process_body_in_memory(rev); | 1352 ngx_http_upstream_process_body_in_memory(rev); |
1353 } | |
1354 | |
1355 | |
1356 static ngx_int_t | |
1357 ngx_http_upstream_test_next(ngx_http_request_t *r, ngx_http_upstream_t *u) | |
1358 { | |
1359 ngx_uint_t status; | |
1360 ngx_http_upstream_next_t *un; | |
1361 | |
1362 if (!(u->conf->next_upstream & NGX_HTTP_UPSTREAM_FT_STATUS)) { | |
1363 return NGX_DECLINED; | |
1364 } | |
1365 | |
1366 status = u->headers_in.status_n; | |
1367 | |
1368 for (un = ngx_http_upstream_next_errors; un->status; un++) { | |
1369 | |
1370 if (status != un->status) { | |
1371 continue; | |
1372 } | |
1373 | |
1374 if (u->peer.tries > 1 && (u->conf->next_upstream & un->mask)) { | |
1375 ngx_http_upstream_next(r, u, un->mask); | |
1376 return NGX_OK; | |
1377 } | |
1378 | |
1379 if (status == NGX_HTTP_NOT_FOUND && u->conf->intercept_404) { | |
1380 ngx_http_upstream_finalize_request(r, u, NGX_HTTP_NOT_FOUND); | |
1381 return NGX_OK; | |
1382 } | |
1383 | |
1384 #if (NGX_HTTP_CACHE) | |
1385 | |
1386 if (u->peer.tries == 0 && u->stale && (u->conf->use_stale & un->mask)) { | |
1387 ngx_http_upstream_finalize_request(r, u, | |
1388 ngx_http_send_cached_response(r)); | |
1389 return NGX_OK; | |
1390 } | |
1391 | |
1392 #endif | |
1393 } | |
1394 | |
1395 return NGX_DECLINED; | |
1396 } | |
1397 | |
1398 | |
1399 static ngx_int_t | |
1400 ngx_http_upstream_intercept_errors(ngx_http_request_t *r, | |
1401 ngx_http_upstream_t *u) | |
1402 { | |
1403 ngx_int_t status; | |
1404 ngx_uint_t i; | |
1405 ngx_table_elt_t *h; | |
1406 ngx_http_err_page_t *err_page; | |
1407 ngx_http_core_loc_conf_t *clcf; | |
1408 | |
1409 if (!u->conf->intercept_errors) { | |
1410 return NGX_DECLINED; | |
1411 } | |
1412 | |
1413 clcf = ngx_http_get_module_loc_conf(r, ngx_http_core_module); | |
1414 | |
1415 if (clcf->error_pages == NULL) { | |
1416 return NGX_DECLINED; | |
1417 } | |
1418 | |
1419 status = u->headers_in.status_n; | |
1420 | |
1421 err_page = clcf->error_pages->elts; | |
1422 for (i = 0; i < clcf->error_pages->nelts; i++) { | |
1423 | |
1424 if (err_page[i].status == status) { | |
1425 | |
1426 if (status == NGX_HTTP_UNAUTHORIZED) { | |
1427 | |
1428 h = ngx_list_push(&r->headers_out.headers); | |
1429 | |
1430 if (h == NULL) { | |
1431 ngx_http_upstream_finalize_request(r, u, | |
1432 NGX_HTTP_INTERNAL_SERVER_ERROR); | |
1433 return NGX_OK; | |
1434 } | |
1435 | |
1436 *h = *u->headers_in.www_authenticate; | |
1437 | |
1438 r->headers_out.www_authenticate = h; | |
1439 } | |
1440 | |
1441 ngx_http_upstream_finalize_request(r, u, status); | |
1442 | |
1443 return NGX_OK; | |
1444 } | |
1445 } | |
1446 | |
1447 return NGX_DECLINED; | |
1406 } | 1448 } |
1407 | 1449 |
1408 | 1450 |
1409 static ngx_int_t | 1451 static ngx_int_t |
1410 ngx_http_upstream_test_connect(ngx_connection_t *c) | 1452 ngx_http_upstream_test_connect(ngx_connection_t *c) |