11cb0ef41Sopenharmony_ci'use strict'; 21cb0ef41Sopenharmony_ci 31cb0ef41Sopenharmony_ciconst common = require('../common'); 41cb0ef41Sopenharmony_ciif (!common.hasCrypto) 51cb0ef41Sopenharmony_ci common.skip('missing crypto'); 61cb0ef41Sopenharmony_ciconst assert = require('assert'); 71cb0ef41Sopenharmony_ciconst h2 = require('http2'); 81cb0ef41Sopenharmony_ci 91cb0ef41Sopenharmony_ciconst server = h2.createServer(); 101cb0ef41Sopenharmony_ci 111cb0ef41Sopenharmony_ci// We use the lower-level API here 121cb0ef41Sopenharmony_ciserver.on('stream', common.mustCall(onStream)); 131cb0ef41Sopenharmony_ci 141cb0ef41Sopenharmony_ciconst status101regex = 151cb0ef41Sopenharmony_ci /^HTTP status code 101 \(Switching Protocols\) is forbidden in HTTP\/2$/; 161cb0ef41Sopenharmony_ciconst afterRespondregex = 171cb0ef41Sopenharmony_ci /^Cannot specify additional headers after response initiated$/; 181cb0ef41Sopenharmony_ci 191cb0ef41Sopenharmony_cifunction onStream(stream, headers, flags) { 201cb0ef41Sopenharmony_ci 211cb0ef41Sopenharmony_ci assert.throws(() => stream.additionalHeaders({ ':status': 201 }), 221cb0ef41Sopenharmony_ci { 231cb0ef41Sopenharmony_ci code: 'ERR_HTTP2_INVALID_INFO_STATUS', 241cb0ef41Sopenharmony_ci name: 'RangeError', 251cb0ef41Sopenharmony_ci message: /^Invalid informational status code: 201$/ 261cb0ef41Sopenharmony_ci }); 271cb0ef41Sopenharmony_ci 281cb0ef41Sopenharmony_ci assert.throws(() => stream.additionalHeaders({ ':status': 101 }), 291cb0ef41Sopenharmony_ci { 301cb0ef41Sopenharmony_ci code: 'ERR_HTTP2_STATUS_101', 311cb0ef41Sopenharmony_ci name: 'Error', 321cb0ef41Sopenharmony_ci message: status101regex 331cb0ef41Sopenharmony_ci }); 341cb0ef41Sopenharmony_ci 351cb0ef41Sopenharmony_ci assert.throws( 361cb0ef41Sopenharmony_ci () => stream.additionalHeaders({ ':method': 'POST' }), 371cb0ef41Sopenharmony_ci { 381cb0ef41Sopenharmony_ci code: 'ERR_HTTP2_INVALID_PSEUDOHEADER', 391cb0ef41Sopenharmony_ci name: 'TypeError', 401cb0ef41Sopenharmony_ci message: '":method" is an invalid pseudoheader or is used incorrectly' 411cb0ef41Sopenharmony_ci } 421cb0ef41Sopenharmony_ci ); 431cb0ef41Sopenharmony_ci 441cb0ef41Sopenharmony_ci // Can send more than one 451cb0ef41Sopenharmony_ci stream.additionalHeaders({ ':status': 100 }); 461cb0ef41Sopenharmony_ci stream.additionalHeaders({ ':status': 100 }); 471cb0ef41Sopenharmony_ci 481cb0ef41Sopenharmony_ci stream.respond({ 491cb0ef41Sopenharmony_ci 'content-type': 'text/html', 501cb0ef41Sopenharmony_ci ':status': 200 511cb0ef41Sopenharmony_ci }); 521cb0ef41Sopenharmony_ci 531cb0ef41Sopenharmony_ci assert.throws(() => stream.additionalHeaders({ abc: 123 }), 541cb0ef41Sopenharmony_ci { 551cb0ef41Sopenharmony_ci code: 'ERR_HTTP2_HEADERS_AFTER_RESPOND', 561cb0ef41Sopenharmony_ci name: 'Error', 571cb0ef41Sopenharmony_ci message: afterRespondregex 581cb0ef41Sopenharmony_ci }); 591cb0ef41Sopenharmony_ci 601cb0ef41Sopenharmony_ci stream.end('hello world'); 611cb0ef41Sopenharmony_ci} 621cb0ef41Sopenharmony_ci 631cb0ef41Sopenharmony_ciserver.listen(0); 641cb0ef41Sopenharmony_ci 651cb0ef41Sopenharmony_ciserver.on('listening', common.mustCall(() => { 661cb0ef41Sopenharmony_ci 671cb0ef41Sopenharmony_ci const client = h2.connect(`http://localhost:${server.address().port}`); 681cb0ef41Sopenharmony_ci 691cb0ef41Sopenharmony_ci const req = client.request({ ':path': '/' }); 701cb0ef41Sopenharmony_ci 711cb0ef41Sopenharmony_ci // The additionalHeaders method does not exist on client stream 721cb0ef41Sopenharmony_ci assert.strictEqual(req.additionalHeaders, undefined); 731cb0ef41Sopenharmony_ci 741cb0ef41Sopenharmony_ci // Additional informational headers 751cb0ef41Sopenharmony_ci req.on('headers', common.mustCall((headers) => { 761cb0ef41Sopenharmony_ci assert.notStrictEqual(headers, undefined); 771cb0ef41Sopenharmony_ci assert.strictEqual(headers[':status'], 100); 781cb0ef41Sopenharmony_ci }, 2)); 791cb0ef41Sopenharmony_ci 801cb0ef41Sopenharmony_ci // Response headers 811cb0ef41Sopenharmony_ci req.on('response', common.mustCall((headers) => { 821cb0ef41Sopenharmony_ci assert.notStrictEqual(headers, undefined); 831cb0ef41Sopenharmony_ci assert.strictEqual(headers[':status'], 200); 841cb0ef41Sopenharmony_ci assert.strictEqual(headers['content-type'], 'text/html'); 851cb0ef41Sopenharmony_ci })); 861cb0ef41Sopenharmony_ci 871cb0ef41Sopenharmony_ci req.resume(); 881cb0ef41Sopenharmony_ci 891cb0ef41Sopenharmony_ci req.on('end', common.mustCall(() => { 901cb0ef41Sopenharmony_ci server.close(); 911cb0ef41Sopenharmony_ci client.close(); 921cb0ef41Sopenharmony_ci })); 931cb0ef41Sopenharmony_ci req.end(); 941cb0ef41Sopenharmony_ci 951cb0ef41Sopenharmony_ci})); 96