Mercurial > hg > nginx-quic
comparison src/http/v2/ngx_http_v2_module.c @ 7201:641306096f5b
HTTP/2: server push.
Resources to be pushed are configured with the "http2_push" directive.
Also, preload links from the Link response headers, as described in
https://www.w3.org/TR/preload/#server-push-http-2, can be pushed, if
enabled with the "http2_push_preload" directive.
Only relative URIs with absolute paths can be pushed.
The number of concurrent pushes is normally limited by a client, but
cannot exceed a hard limit set by the "http2_max_concurrent_pushes"
directive.
author | Ruslan Ermilov <ru@nginx.com> |
---|---|
date | Thu, 08 Feb 2018 09:55:03 +0300 |
parents | 2a288909abc6 |
children | de0b6f1fe4e4 |
comparison
equal
deleted
inserted
replaced
7200:cadb43014c7c | 7201:641306096f5b |
---|---|
24 static char *ngx_http_v2_merge_srv_conf(ngx_conf_t *cf, void *parent, | 24 static char *ngx_http_v2_merge_srv_conf(ngx_conf_t *cf, void *parent, |
25 void *child); | 25 void *child); |
26 static void *ngx_http_v2_create_loc_conf(ngx_conf_t *cf); | 26 static void *ngx_http_v2_create_loc_conf(ngx_conf_t *cf); |
27 static char *ngx_http_v2_merge_loc_conf(ngx_conf_t *cf, void *parent, | 27 static char *ngx_http_v2_merge_loc_conf(ngx_conf_t *cf, void *parent, |
28 void *child); | 28 void *child); |
29 | |
30 static char *ngx_http_v2_push(ngx_conf_t *cf, ngx_command_t *cmd, void *conf); | |
29 | 31 |
30 static char *ngx_http_v2_recv_buffer_size(ngx_conf_t *cf, void *post, | 32 static char *ngx_http_v2_recv_buffer_size(ngx_conf_t *cf, void *post, |
31 void *data); | 33 void *data); |
32 static char *ngx_http_v2_pool_size(ngx_conf_t *cf, void *post, void *data); | 34 static char *ngx_http_v2_pool_size(ngx_conf_t *cf, void *post, void *data); |
33 static char *ngx_http_v2_preread_size(ngx_conf_t *cf, void *post, void *data); | 35 static char *ngx_http_v2_preread_size(ngx_conf_t *cf, void *post, void *data); |
71 ngx_conf_set_num_slot, | 73 ngx_conf_set_num_slot, |
72 NGX_HTTP_SRV_CONF_OFFSET, | 74 NGX_HTTP_SRV_CONF_OFFSET, |
73 offsetof(ngx_http_v2_srv_conf_t, concurrent_streams), | 75 offsetof(ngx_http_v2_srv_conf_t, concurrent_streams), |
74 NULL }, | 76 NULL }, |
75 | 77 |
78 { ngx_string("http2_max_concurrent_pushes"), | |
79 NGX_HTTP_MAIN_CONF|NGX_HTTP_SRV_CONF|NGX_CONF_TAKE1, | |
80 ngx_conf_set_num_slot, | |
81 NGX_HTTP_SRV_CONF_OFFSET, | |
82 offsetof(ngx_http_v2_srv_conf_t, concurrent_pushes), | |
83 NULL }, | |
84 | |
76 { ngx_string("http2_max_requests"), | 85 { ngx_string("http2_max_requests"), |
77 NGX_HTTP_MAIN_CONF|NGX_HTTP_SRV_CONF|NGX_CONF_TAKE1, | 86 NGX_HTTP_MAIN_CONF|NGX_HTTP_SRV_CONF|NGX_CONF_TAKE1, |
78 ngx_conf_set_num_slot, | 87 ngx_conf_set_num_slot, |
79 NGX_HTTP_SRV_CONF_OFFSET, | 88 NGX_HTTP_SRV_CONF_OFFSET, |
80 offsetof(ngx_http_v2_srv_conf_t, max_requests), | 89 offsetof(ngx_http_v2_srv_conf_t, max_requests), |
126 NGX_HTTP_MAIN_CONF|NGX_HTTP_SRV_CONF|NGX_HTTP_LOC_CONF|NGX_CONF_TAKE1, | 135 NGX_HTTP_MAIN_CONF|NGX_HTTP_SRV_CONF|NGX_HTTP_LOC_CONF|NGX_CONF_TAKE1, |
127 ngx_conf_set_size_slot, | 136 ngx_conf_set_size_slot, |
128 NGX_HTTP_LOC_CONF_OFFSET, | 137 NGX_HTTP_LOC_CONF_OFFSET, |
129 offsetof(ngx_http_v2_loc_conf_t, chunk_size), | 138 offsetof(ngx_http_v2_loc_conf_t, chunk_size), |
130 &ngx_http_v2_chunk_size_post }, | 139 &ngx_http_v2_chunk_size_post }, |
140 | |
141 { ngx_string("http2_push_preload"), | |
142 NGX_HTTP_MAIN_CONF|NGX_HTTP_SRV_CONF|NGX_HTTP_LOC_CONF|NGX_CONF_FLAG, | |
143 ngx_conf_set_flag_slot, | |
144 NGX_HTTP_LOC_CONF_OFFSET, | |
145 offsetof(ngx_http_v2_loc_conf_t, push_preload), | |
146 NULL }, | |
147 | |
148 { ngx_string("http2_push"), | |
149 NGX_HTTP_MAIN_CONF|NGX_HTTP_SRV_CONF|NGX_HTTP_LOC_CONF|NGX_CONF_TAKE1, | |
150 ngx_http_v2_push, | |
151 NGX_HTTP_LOC_CONF_OFFSET, | |
152 0, | |
153 NULL }, | |
131 | 154 |
132 { ngx_string("spdy_recv_buffer_size"), | 155 { ngx_string("spdy_recv_buffer_size"), |
133 NGX_HTTP_MAIN_CONF|NGX_CONF_TAKE1, | 156 NGX_HTTP_MAIN_CONF|NGX_CONF_TAKE1, |
134 ngx_http_v2_spdy_deprecated, | 157 ngx_http_v2_spdy_deprecated, |
135 NGX_HTTP_MAIN_CONF_OFFSET, | 158 NGX_HTTP_MAIN_CONF_OFFSET, |
327 } | 350 } |
328 | 351 |
329 h2scf->pool_size = NGX_CONF_UNSET_SIZE; | 352 h2scf->pool_size = NGX_CONF_UNSET_SIZE; |
330 | 353 |
331 h2scf->concurrent_streams = NGX_CONF_UNSET_UINT; | 354 h2scf->concurrent_streams = NGX_CONF_UNSET_UINT; |
355 h2scf->concurrent_pushes = NGX_CONF_UNSET_UINT; | |
332 h2scf->max_requests = NGX_CONF_UNSET_UINT; | 356 h2scf->max_requests = NGX_CONF_UNSET_UINT; |
333 | 357 |
334 h2scf->max_field_size = NGX_CONF_UNSET_SIZE; | 358 h2scf->max_field_size = NGX_CONF_UNSET_SIZE; |
335 h2scf->max_header_size = NGX_CONF_UNSET_SIZE; | 359 h2scf->max_header_size = NGX_CONF_UNSET_SIZE; |
336 | 360 |
353 | 377 |
354 ngx_conf_merge_size_value(conf->pool_size, prev->pool_size, 4096); | 378 ngx_conf_merge_size_value(conf->pool_size, prev->pool_size, 4096); |
355 | 379 |
356 ngx_conf_merge_uint_value(conf->concurrent_streams, | 380 ngx_conf_merge_uint_value(conf->concurrent_streams, |
357 prev->concurrent_streams, 128); | 381 prev->concurrent_streams, 128); |
382 ngx_conf_merge_uint_value(conf->concurrent_pushes, | |
383 prev->concurrent_pushes, 10); | |
358 ngx_conf_merge_uint_value(conf->max_requests, prev->max_requests, 1000); | 384 ngx_conf_merge_uint_value(conf->max_requests, prev->max_requests, 1000); |
359 | 385 |
360 ngx_conf_merge_size_value(conf->max_field_size, prev->max_field_size, | 386 ngx_conf_merge_size_value(conf->max_field_size, prev->max_field_size, |
361 4096); | 387 4096); |
362 ngx_conf_merge_size_value(conf->max_header_size, prev->max_header_size, | 388 ngx_conf_merge_size_value(conf->max_header_size, prev->max_header_size, |
384 h2lcf = ngx_pcalloc(cf->pool, sizeof(ngx_http_v2_loc_conf_t)); | 410 h2lcf = ngx_pcalloc(cf->pool, sizeof(ngx_http_v2_loc_conf_t)); |
385 if (h2lcf == NULL) { | 411 if (h2lcf == NULL) { |
386 return NULL; | 412 return NULL; |
387 } | 413 } |
388 | 414 |
415 /* | |
416 * set by ngx_pcalloc(): | |
417 * | |
418 * h2lcf->pushes = NULL; | |
419 */ | |
420 | |
389 h2lcf->chunk_size = NGX_CONF_UNSET_SIZE; | 421 h2lcf->chunk_size = NGX_CONF_UNSET_SIZE; |
422 | |
423 h2lcf->push_preload = NGX_CONF_UNSET; | |
424 h2lcf->push = NGX_CONF_UNSET; | |
390 | 425 |
391 return h2lcf; | 426 return h2lcf; |
392 } | 427 } |
393 | 428 |
394 | 429 |
397 { | 432 { |
398 ngx_http_v2_loc_conf_t *prev = parent; | 433 ngx_http_v2_loc_conf_t *prev = parent; |
399 ngx_http_v2_loc_conf_t *conf = child; | 434 ngx_http_v2_loc_conf_t *conf = child; |
400 | 435 |
401 ngx_conf_merge_size_value(conf->chunk_size, prev->chunk_size, 8 * 1024); | 436 ngx_conf_merge_size_value(conf->chunk_size, prev->chunk_size, 8 * 1024); |
437 | |
438 ngx_conf_merge_value(conf->push, prev->push, 1); | |
439 | |
440 if (conf->push && conf->pushes == NULL) { | |
441 conf->pushes = prev->pushes; | |
442 } | |
443 | |
444 ngx_conf_merge_value(conf->push_preload, prev->push_preload, 0); | |
445 | |
446 return NGX_CONF_OK; | |
447 } | |
448 | |
449 | |
450 static char * | |
451 ngx_http_v2_push(ngx_conf_t *cf, ngx_command_t *cmd, void *conf) | |
452 { | |
453 ngx_http_v2_loc_conf_t *h2lcf = conf; | |
454 | |
455 ngx_str_t *value; | |
456 ngx_http_complex_value_t *cv; | |
457 ngx_http_compile_complex_value_t ccv; | |
458 | |
459 value = cf->args->elts; | |
460 | |
461 if (ngx_strcmp(value[1].data, "off") == 0) { | |
462 | |
463 if (h2lcf->pushes) { | |
464 return "\"off\" parameter cannot be used with URI"; | |
465 } | |
466 | |
467 if (h2lcf->push == 0) { | |
468 return "is duplicate"; | |
469 } | |
470 | |
471 h2lcf->push = 0; | |
472 return NGX_CONF_OK; | |
473 } | |
474 | |
475 if (h2lcf->push == 0) { | |
476 return "URI cannot be used with \"off\" parameter"; | |
477 } | |
478 | |
479 h2lcf->push = 1; | |
480 | |
481 if (h2lcf->pushes == NULL) { | |
482 h2lcf->pushes = ngx_array_create(cf->pool, 1, | |
483 sizeof(ngx_http_complex_value_t)); | |
484 if (h2lcf->pushes == NULL) { | |
485 return NGX_CONF_ERROR; | |
486 } | |
487 } | |
488 | |
489 cv = ngx_array_push(h2lcf->pushes); | |
490 if (cv == NULL) { | |
491 return NGX_CONF_ERROR; | |
492 } | |
493 | |
494 ngx_memzero(&ccv, sizeof(ngx_http_compile_complex_value_t)); | |
495 | |
496 ccv.cf = cf; | |
497 ccv.value = &value[1]; | |
498 ccv.complex_value = cv; | |
499 | |
500 if (ngx_http_compile_complex_value(&ccv) != NGX_OK) { | |
501 return NGX_CONF_ERROR; | |
502 } | |
402 | 503 |
403 return NGX_CONF_OK; | 504 return NGX_CONF_OK; |
404 } | 505 } |
405 | 506 |
406 | 507 |