Mercurial > hg > nginx-tests
comparison h2_server_push.t @ 1348:8cb66a4d3ca2
Tests: fixed HTTP/2 server push expectations, adjusted TODO.
author | Sergey Kandaurov <pluknet@nginx.com> |
---|---|
date | Thu, 14 Jun 2018 14:01:50 +0300 |
parents | da711694bbd7 |
children | 97c8280de681 |
comparison
equal
deleted
inserted
replaced
1347:106d9f806288 | 1348:8cb66a4d3ca2 |
---|---|
136 | 136 |
137 $t->try_run('no http2_push')->plan(42); | 137 $t->try_run('no http2_push')->plan(42); |
138 | 138 |
139 ############################################################################### | 139 ############################################################################### |
140 | 140 |
141 # 6.6. PUSH_PROMISE | |
142 # PUSH_PROMISE frames MUST only be sent on a peer-initiated stream that | |
143 # is in either the "open" or "half-closed (remote)" state. | |
144 | |
141 # preload & format | 145 # preload & format |
142 | 146 |
143 my $s = Test::Nginx::HTTP2->new(); | 147 my $s = Test::Nginx::HTTP2->new(); |
144 my $sid = $s->new_stream({ path => '/preload' }); | 148 my $sid = $s->new_stream({ path => '/preload' }); |
145 my $frames = $s->read(all => [{ sid => 1, fin => 1 }, { sid => 2, fin => 1 }]); | 149 my $frames = $s->read(all => [{ sid => 1, fin => 1 }, { sid => 2, fin => 1 }]); |
159 ($frame) = grep { $_->{type} eq "HEADERS" && $_->{sid} eq $sid } @$frames; | 163 ($frame) = grep { $_->{type} eq "HEADERS" && $_->{sid} eq $sid } @$frames; |
160 is($frame->{headers}->{'x-link'}, '</push>; rel=preload', 'sent_http_link'); | 164 is($frame->{headers}->{'x-link'}, '</push>; rel=preload', 'sent_http_link'); |
161 | 165 |
162 $s = Test::Nginx::HTTP2->new(); | 166 $s = Test::Nginx::HTTP2->new(); |
163 $sid = $s->new_stream({ path => '/preload2' }); | 167 $sid = $s->new_stream({ path => '/preload2' }); |
164 $frames = $s->read(all => [{ sid => 8, fin => 1 }], wait => 0.5); | 168 $frames = $s->read(all => [{ sid => $sid, fin => 1 }]); |
165 is(grep({ $_->{type} eq "PUSH_PROMISE" } @$frames), 4, 'preload 2'); | 169 is(grep({ $_->{type} eq "PUSH_PROMISE" } @$frames), 4, 'preload 2'); |
166 | 170 |
167 $s = Test::Nginx::HTTP2->new(); | 171 $s = Test::Nginx::HTTP2->new(); |
168 $sid = $s->new_stream({ path => '/preload/many' }); | 172 $sid = $s->new_stream({ path => '/preload/many' }); |
169 $frames = $s->read(all => [{ sid => 8, fin => 1 }], wait => 0.5); | 173 $frames = $s->read(all => [{ sid => $sid, fin => 1 }]); |
170 is(grep({ $_->{type} eq "PUSH_PROMISE" } @$frames), 3, 'preload many'); | 174 is(grep({ $_->{type} eq "PUSH_PROMISE" } @$frames), 3, 'preload many'); |
171 | 175 |
172 # preload proxy | 176 # preload proxy |
173 | 177 |
174 $s = Test::Nginx::HTTP2->new(); | 178 $s = Test::Nginx::HTTP2->new(); |
175 $sid = $s->new_stream({ path => '/preload/proxy' }); | 179 $sid = $s->new_stream({ path => '/preload/proxy' }); |
176 $frames = $s->read(all => [{ sid => 8, fin => 1 }], wait => 0.5); | 180 $frames = $s->read(all => [{ sid => $sid, fin => 1 }]); |
177 is(grep({ $_->{type} eq "PUSH_PROMISE" } @$frames), 2, 'preload proxy'); | 181 is(grep({ $_->{type} eq "PUSH_PROMISE" } @$frames), 2, 'preload proxy'); |
178 | 182 |
179 # both h2_push & preload | 183 # both h2_push & preload |
180 | 184 |
181 $s = Test::Nginx::HTTP2->new(); | 185 $s = Test::Nginx::HTTP2->new(); |
182 $sid = $s->new_stream({ path => '/both' }); | 186 $sid = $s->new_stream({ path => '/both' }); |
183 $frames = $s->read(all => [{ sid => 8, fin => 1 }], wait => 0.5); | 187 $frames = $s->read(all => [{ sid => $sid, fin => 1 }]); |
184 is(grep({ $_->{type} eq "PUSH_PROMISE" } @$frames), 2, 'h2_push and preload'); | 188 is(grep({ $_->{type} eq "PUSH_PROMISE" } @$frames), 2, 'h2_push and preload'); |
185 | 189 |
186 # h2_push | 190 # h2_push |
187 | 191 |
188 $s = Test::Nginx::HTTP2->new(); | 192 $s = Test::Nginx::HTTP2->new(); |
189 $sid = $s->new_stream({ path => '/expl' }); | 193 $sid = $s->new_stream({ path => '/expl' }); |
190 $frames = $s->read(all => [{ sid => 1, fin => 1 }, { sid => 2, fin => 1 }]); | 194 $frames = $s->read(all => [{ sid => $sid, fin => 1 }]); |
191 | 195 |
192 ($frame) = grep { $_->{type} eq "PUSH_PROMISE" } @$frames; | 196 ($frame) = grep { $_->{type} eq "PUSH_PROMISE" } @$frames; |
193 ok($frame, 'h2_push only'); | 197 ok($frame, 'h2_push only'); |
194 | 198 |
195 # h2_push off | 199 # h2_push off |
196 | 200 |
197 $s = Test::Nginx::HTTP2->new(); | 201 $s = Test::Nginx::HTTP2->new(); |
198 $sid = $s->new_stream({ path => '/expl/off' }); | 202 $sid = $s->new_stream({ path => '/expl/off' }); |
199 $frames = $s->read(all => [{ type => 'PUSH_PROMISE' }], wait => 0.2); | 203 $frames = $s->read(all => [{ sid => $sid, fin => 1 }]); |
200 | 204 |
201 ($frame) = grep { $_->{type} eq "PUSH_PROMISE" } @$frames; | 205 ($frame) = grep { $_->{type} eq "PUSH_PROMISE" } @$frames; |
202 ok(!$frame, 'h2_push off'); | 206 ok(!$frame, 'h2_push off'); |
203 | 207 |
204 # h2_push $var | 208 # h2_push $var |
205 | 209 |
206 $s = Test::Nginx::HTTP2->new(); | 210 $s = Test::Nginx::HTTP2->new(); |
207 $sid = $s->new_stream({ path => '/arg?push=/push' }); | 211 $sid = $s->new_stream({ path => '/arg?push=/push' }); |
208 $frames = $s->read(all => [{ type => 'PUSH_PROMISE' }], wait => 0.2); | 212 $frames = $s->read(all => [{ sid => $sid, fin => 1 }]); |
209 ($frame) = grep { $_->{type} eq "PUSH_PROMISE" } @$frames; | 213 ($frame) = grep { $_->{type} eq "PUSH_PROMISE" } @$frames; |
210 ok($frame, 'h2_push variable'); | 214 ok($frame, 'h2_push variable'); |
211 | 215 |
212 $sid = $s->new_stream({ path => '/arg?push=' }); | 216 $sid = $s->new_stream({ path => '/arg?push=' }); |
213 $frames = $s->read(all => [{ type => 'PUSH_PROMISE' }], wait => 0.2); | 217 $frames = $s->read(all => [{ sid => $sid, fin => 1 }]); |
214 ($frame) = grep { $_->{type} eq "PUSH_PROMISE" } @$frames; | 218 ($frame) = grep { $_->{type} eq "PUSH_PROMISE" } @$frames; |
215 ok(!$frame, 'h2_push variable empty'); | 219 ok(!$frame, 'h2_push variable empty'); |
216 | 220 |
217 $sid = $s->new_stream({ path => '/arg?push=off' }); | 221 $sid = $s->new_stream({ path => '/arg?push=off' }); |
218 $frames = $s->read(all => [{ type => 'PUSH_PROMISE' }], wait => 0.2); | 222 $frames = $s->read(all => [{ sid => $sid, fin => 1 }]); |
219 ($frame) = grep { $_->{type} eq "PUSH_PROMISE" } @$frames; | 223 ($frame) = grep { $_->{type} eq "PUSH_PROMISE" } @$frames; |
220 ok(!$frame, 'h2_push variable off'); | 224 ok(!$frame, 'h2_push variable off'); |
221 | 225 |
222 $sid = $s->new_stream({ path => '/arg?push=foo' }); | 226 $sid = $s->new_stream({ path => '/arg?push=foo' }); |
223 $frames = $s->read(all => [{ type => 'PUSH_PROMISE' }], wait => 0.2); | 227 $frames = $s->read(all => [{ sid => $sid, fin => 1 }]); |
224 ($frame) = grep { $_->{type} eq "PUSH_PROMISE" } @$frames; | 228 ($frame) = grep { $_->{type} eq "PUSH_PROMISE" } @$frames; |
225 ok(!$frame, 'h2_push variable relative path'); | 229 ok(!$frame, 'h2_push variable relative path'); |
226 | 230 |
227 # SETTINGS_ENABLE_PUSH | 231 # SETTINGS_ENABLE_PUSH |
228 | 232 |
229 $s = Test::Nginx::HTTP2->new(); | 233 $s = Test::Nginx::HTTP2->new(); |
230 $s->h2_settings(0, 0x2 => 0); | 234 $s->h2_settings(0, 0x2 => 0); |
231 $sid = $s->new_stream({ path => '/expl' }); | 235 $sid = $s->new_stream({ path => '/expl' }); |
232 $frames = $s->read(all => [{ type => 'PUSH_PROMISE' }], wait => 0.2); | 236 $frames = $s->read(all => [{ sid => $sid, fin => 1 }]); |
233 | 237 |
234 ($frame) = grep { $_->{type} eq "PUSH_PROMISE" } @$frames; | 238 ($frame) = grep { $_->{type} eq "PUSH_PROMISE" } @$frames; |
235 ok(!$frame, 'push setting disabled'); | 239 ok(!$frame, 'push setting disabled'); |
236 | 240 |
237 $s->h2_settings(0, 0x2 => 1); | 241 $s->h2_settings(0, 0x2 => 1); |
238 $sid = $s->new_stream({ path => '/expl' }); | 242 $sid = $s->new_stream({ path => '/expl' }); |
239 $frames = $s->read(all => [{ sid => $sid, fin => 1 }, { sid => 2, fin => 1 }]); | 243 $frames = $s->read(all => [{ sid => $sid, fin => 1 }]); |
240 | 244 |
241 ($frame) = grep { $_->{type} eq "PUSH_PROMISE" } @$frames; | 245 ($frame) = grep { $_->{type} eq "PUSH_PROMISE" } @$frames; |
242 ok($frame, 'push setting enabled'); | 246 ok($frame, 'push setting enabled'); |
243 | 247 |
244 $s->h2_settings(0, 0x2 => 42); | 248 $s->h2_settings(0, 0x2 => 42); |
250 | 254 |
251 # SETTINGS_MAX_CONCURRENT_STREAMS | 255 # SETTINGS_MAX_CONCURRENT_STREAMS |
252 | 256 |
253 $s = Test::Nginx::HTTP2->new(); | 257 $s = Test::Nginx::HTTP2->new(); |
254 $sid = $s->new_stream({ path => '/expl' }); | 258 $sid = $s->new_stream({ path => '/expl' }); |
255 $frames = $s->read(all => [ | 259 $frames = $s->read(all => [{ sid => $sid, fin => 1 }]); |
256 { sid => 1, fin => 1 }, | |
257 { sid => 2, fin => 1 }, | |
258 { sid => 4, fin => 1 }]); | |
259 is(grep({ $_->{type} eq "PUSH_PROMISE" } @$frames), 2, 'max pushes default'); | 260 is(grep({ $_->{type} eq "PUSH_PROMISE" } @$frames), 2, 'max pushes default'); |
260 | 261 |
261 $s = Test::Nginx::HTTP2->new(); | 262 $s = Test::Nginx::HTTP2->new(); |
262 $s->h2_settings(0, 0x3 => 1); | 263 $s->h2_settings(0, 0x3 => 1); |
263 $sid = $s->new_stream({ path => '/expl' }); | 264 $sid = $s->new_stream({ path => '/expl' }); |
264 $frames = $s->read(all => [{ sid => 1, fin => 1 }, { sid => 2, fin => 1 }]); | 265 $frames = $s->read(all => [{ sid => $sid, fin => 1 }]); |
265 is(grep({ $_->{type} eq "PUSH_PROMISE" } @$frames), 1, 'max pushes limited'); | 266 is(grep({ $_->{type} eq "PUSH_PROMISE" } @$frames), 1, 'max pushes limited'); |
266 | 267 |
267 $s = Test::Nginx::HTTP2->new(); | 268 $s = Test::Nginx::HTTP2->new(); |
268 $s->h2_settings(0, 0x3 => 0); | 269 $s->h2_settings(0, 0x3 => 0); |
269 $sid = $s->new_stream({ path => '/expl' }); | 270 $sid = $s->new_stream({ path => '/expl' }); |
270 $frames = $s->read(all => [{ type => 'PUSH_PROMISE' }], wait => 0.2); | 271 $frames = $s->read(all => [{ sid => $sid, fin => 1 }]); |
271 is(grep({ $_->{type} eq "PUSH_PROMISE" } @$frames), 0, 'max pushes disabled'); | 272 is(grep({ $_->{type} eq "PUSH_PROMISE" } @$frames), 0, 'max pushes disabled'); |
272 | 273 |
273 TODO: { | 274 TODO: { |
274 local $TODO = 'not yet' if $t->read_file('nginx.conf') =~ /aio on/ | 275 todo_skip 'long tests with aio', 6 unless $ENV{TEST_NGINX_UNSAFE} |
275 or $t->read_file('nginx.conf') =~ /aio threads/; | 276 or $t->read_file('nginx.conf') !~ /aio (on|threads)/; |
277 local $TODO = 'not yet' if $t->read_file('nginx.conf') =~ /aio (on|threads)/; | |
276 | 278 |
277 # server push flow control & rst | 279 # server push flow control & rst |
278 | 280 |
279 $s = Test::Nginx::HTTP2->new(); | 281 $s = Test::Nginx::HTTP2->new(); |
280 $sid = $s->new_stream({ path => '/explf' }); | 282 $sid = $s->new_stream({ path => '/explf' }); |
302 | 304 |
303 $s->h2_rst(4, 7); | 305 $s->h2_rst(4, 7); |
304 $s->h2_window(2**16); | 306 $s->h2_window(2**16); |
305 | 307 |
306 $frames = $s->read(all => [{ sid => 2, length => 1 }]); | 308 $frames = $s->read(all => [{ sid => 2, length => 1 }]); |
307 push @$frames, @{ $s->read(all => [{ sid => 4, fin => 1 }], wait => 0.5) }; | 309 push @$frames, @{ $s->read(all => [{ sid => 4, fin => 1 }], wait => 0.2) }; |
308 | 310 |
309 ($frame) = grep { $_->{type} eq "DATA" && $_->{sid} == 2 } @$frames; | 311 ($frame) = grep { $_->{type} eq "DATA" && $_->{sid} == 2 } @$frames; |
310 is($frame->{length}, 1, 'pushed response flow control'); | 312 is($frame->{length}, 1, 'pushed response flow control'); |
311 is($frame->{flags}, 1, 'pushed response END_STREAM'); | 313 is($frame->{flags}, 1, 'pushed response END_STREAM'); |
312 | 314 |
314 | 316 |
315 ($frame) = grep { $_->{type} eq "DATA" && $_->{sid} == 4 } @$frames; | 317 ($frame) = grep { $_->{type} eq "DATA" && $_->{sid} == 4 } @$frames; |
316 ok(!$frame, 'rst pushed stream'); | 318 ok(!$frame, 'rst pushed stream'); |
317 | 319 |
318 TODO: { | 320 TODO: { |
319 local $TODO = 'not yet' if $t->read_file('nginx.conf') =~ /aio on/ | 321 todo_skip 'long tests with aio', 2 unless $ENV{TEST_NGINX_UNSAFE} |
320 or $t->read_file('nginx.conf') =~ /aio threads/; | 322 or $t->read_file('nginx.conf') !~ /aio (on|threads)/; |
323 local $TODO = 'not yet' if $t->read_file('nginx.conf') =~ /aio (on|threads)/; | |
321 | 324 |
322 # priority | 325 # priority |
323 | 326 |
324 $s = Test::Nginx::HTTP2->new(); | 327 $s = Test::Nginx::HTTP2->new(); |
325 $sid = $s->new_stream({ path => '/prio' }); | 328 $sid = $s->new_stream({ path => '/prio' }); |
357 $sid = $s->new_stream({ headers => [ | 360 $sid = $s->new_stream({ headers => [ |
358 { name => ':method', value => 'GET', mode => 0 }, | 361 { name => ':method', value => 'GET', mode => 0 }, |
359 { name => ':scheme', value => 'http', mode => 0 }, | 362 { name => ':scheme', value => 'http', mode => 0 }, |
360 { name => ':path', value => '/', mode => 0 }, | 363 { name => ':path', value => '/', mode => 0 }, |
361 { name => ':authority', value => 'max_pushes', mode => 1 }]}); | 364 { name => ':authority', value => 'max_pushes', mode => 1 }]}); |
362 $frames = $s->read(all => [{ sid => $sid, fin => 1 }, | 365 $frames = $s->read(all => [{ sid => $sid, fin => 1 }]); |
363 { sid => 2, fin => 1 }, { sid => 4, fin => 1 }]); | |
364 push @$frames, @{ $s->read(all => [{ sid => 6, fin => 1 }], wait => 0.2) }; | |
365 is(grep({ $_->{type} eq "PUSH_PROMISE" } @$frames), 2, 'http2 max pushes lim'); | 366 is(grep({ $_->{type} eq "PUSH_PROMISE" } @$frames), 2, 'http2 max pushes lim'); |
366 | 367 |
367 $s = Test::Nginx::HTTP2->new(port(8082)); | 368 $s = Test::Nginx::HTTP2->new(port(8082)); |
368 $s->h2_settings(0, 0x3 => 1); | 369 $s->h2_settings(0, 0x3 => 1); |
369 $sid = $s->new_stream({ headers => [ | 370 $sid = $s->new_stream({ headers => [ |
370 { name => ':method', value => 'GET', mode => 0 }, | 371 { name => ':method', value => 'GET', mode => 0 }, |
371 { name => ':scheme', value => 'http', mode => 0 }, | 372 { name => ':scheme', value => 'http', mode => 0 }, |
372 { name => ':path', value => '/', mode => 0 }, | 373 { name => ':path', value => '/', mode => 0 }, |
373 { name => ':authority', value => 'max_pushes', mode => 1 }]}); | 374 { name => ':authority', value => 'max_pushes', mode => 1 }]}); |
374 $frames = $s->read(all => [{ sid => $sid, fin => 1 }, { sid => 2, fin => 1 }]); | 375 $frames = $s->read(all => [{ sid => $sid, fin => 1 }]); |
375 push @$frames, @{ $s->read(all => [{ sid => 4, fin => 1 }], wait => 0.2) }; | |
376 is(grep({ $_->{type} eq "PUSH_PROMISE" } @$frames), 1, 'http2 max pushes 2'); | 376 is(grep({ $_->{type} eq "PUSH_PROMISE" } @$frames), 1, 'http2 max pushes 2'); |
377 | 377 |
378 # missing request header ':authority' | 378 # missing request header ':authority' |
379 | 379 |
380 $s = Test::Nginx::HTTP2->new(port(8082)); | 380 $s = Test::Nginx::HTTP2->new(port(8082)); |