GeezerVison is showing github.com — http: expose http.validate-header-name/value · nodejs/node@f33e866
File treeExpand file treeCollapse file tree Open diff view settings Expand file treeCollapse file tree Open diff view settings Collapse file Copy file name to clipboardExpand all lines: doc/api/http.md +70Lines changed: 70 additions & 0 deletions - Display the source diff
- Display the rich diff
| Original file line number | Diff line number | Diff line change |
|---|
@@ -2465,6 +2465,76 @@ events will be emitted in the following order: | 2465 | 2465 | Setting the `timeout` option or using the `setTimeout()` function will | 2466 | 2466 | not abort the request or do anything besides add a `'timeout'` event. | 2467 | 2467 |
| | 2468 | +## `http.validateHeaderName(name)` | | 2469 | +<!-- YAML | | 2470 | +added: REPLACEME | | 2471 | +--> | | 2472 | + | | 2473 | +* `name` {string} | | 2474 | + | | 2475 | +Performs the low-level validations on the provided `name` that are done when | | 2476 | +`res.setHeader(name, value)` is called. | | 2477 | + | | 2478 | +Passing illegal value as `name` will result in a [`TypeError`][] being thrown, | | 2479 | +identified by `code: 'ERR_INVALID_HTTP_TOKEN'`. | | 2480 | + | | 2481 | +It is not necessary to use this method before passing headers to an HTTP request | | 2482 | +or response. The HTTP module will automatically validate such headers. | | 2483 | +Examples: | | 2484 | + | | 2485 | +Example: | | 2486 | +```js | | 2487 | +const { validateHeaderName } = require('http'); | | 2488 | + | | 2489 | +try { | | 2490 | + validateHeaderName(''); | | 2491 | +} catch (err) { | | 2492 | + err instanceof TypeError; // --> true | | 2493 | + err.code; // --> 'ERR_INVALID_HTTP_TOKEN' | | 2494 | + err.message; // --> 'Header name must be a valid HTTP token [""]' | | 2495 | +} | | 2496 | +``` | | 2497 | + | | 2498 | +## `http.validateHeaderValue(name, value)` | | 2499 | +<!-- YAML | | 2500 | +added: REPLACEME | | 2501 | +--> | | 2502 | + | | 2503 | +* `name` {string} | | 2504 | +* `value` {any} | | 2505 | + | | 2506 | +Performs the low-level validations on the provided `value` that are done when | | 2507 | +`res.setHeader(name, value)` is called. | | 2508 | + | | 2509 | +Passing illegal value as `value` will result in a [`TypeError`][] being thrown. | | 2510 | +* Undefined value error is identified by `code: 'ERR_HTTP_INVALID_HEADER_VALUE'`. | | 2511 | +* Invalid value character error is identified by `code: 'ERR_INVALID_CHAR'`. | | 2512 | + | | 2513 | +It is not necessary to use this method before passing headers to an HTTP request | | 2514 | +or response. The HTTP module will automatically validate such headers. | | 2515 | + | | 2516 | +Examples: | | 2517 | + | | 2518 | +```js | | 2519 | +const { validateHeaderValue } = require('http'); | | 2520 | + | | 2521 | +try { | | 2522 | + validateHeaderValue('x-my-header', undefined); | | 2523 | +} catch (err) { | | 2524 | + err instanceof TypeError; // --> true | | 2525 | + err.code === 'ERR_HTTP_INVALID_HEADER_VALUE'; // --> true | | 2526 | + err.message; // --> 'Invalid value "undefined" for header "x-my-header"' | | 2527 | +} | | 2528 | + | | 2529 | +try { | | 2530 | + validateHeaderValue('x-my-header', 'oʊmɪɡə'); | | 2531 | +} catch (err) { | | 2532 | + err instanceof TypeError; // --> true | | 2533 | + err.code === 'ERR_INVALID_CHAR'; // --> true | | 2534 | + err.message; // --> 'Invalid character in header content ["x-my-header"]' | | 2535 | +} | | 2536 | +``` | | 2537 | + | 2468 | 2538 | [`--insecure-http-parser`]: cli.html#cli_insecure_http_parser | 2469 | 2539 | [`--max-http-header-size`]: cli.html#cli_max_http_header_size_size | 2470 | 2540 | [`'checkContinue'`]: #http_event_checkcontinue | |
Collapse file Copy file name to clipboardExpand all lines: lib/_http_outgoing.js +3Lines changed: 3 additions & 0 deletions | Original file line number | Diff line number | Diff line change |
|---|
@@ -909,6 +909,9 @@ function(err, event) { | 909 | 909 | this.destroy(err); | 910 | 910 | }; | 911 | 911 |
| | 912 | +OutgoingMessage.validateHeaderName = validateHeaderName; | | 913 | +OutgoingMessage.validateHeaderValue = validateHeaderValue; | | 914 | + | 912 | 915 | module.exports = { | 913 | 916 | OutgoingMessage | 914 | 917 | }; |
Collapse file Copy file name to clipboardExpand all lines: lib/http.js +3Lines changed: 3 additions & 0 deletions | Original file line number | Diff line number | Diff line change |
|---|
@@ -30,6 +30,7 @@ const { ClientRequest } = require('_http_client'); | 30 | 30 | const { methods } = require('_http_common'); | 31 | 31 | const { IncomingMessage } = require('_http_incoming'); | 32 | 32 | const { OutgoingMessage } = require('_http_outgoing'); | | 33 | +const { validateHeaderName, validateHeaderValue } = OutgoingMessage; | 33 | 34 | const { | 34 | 35 | _connectionListener, | 35 | 36 | STATUS_CODES, | @@ -63,6 +64,8 @@ module.exports = { | 63 | 64 | Server, | 64 | 65 | ServerResponse, | 65 | 66 | createServer, | | 67 | + validateHeaderName, | | 68 | + validateHeaderValue, | 66 | 69 | get, | 67 | 70 | request | 68 | 71 | }; | |
Collapse file Copy file name to clipboard +62Lines changed: 62 additions & 0 deletions | Original file line number | Diff line number | Diff line change |
|---|
| | 1 | +'use strict'; | | 2 | +require('../common'); | | 3 | +const assert = require('assert'); | | 4 | +const { validateHeaderName, validateHeaderValue } = require('http'); | | 5 | + | | 6 | +// Expected static methods | | 7 | +isFunc(validateHeaderName, 'validateHeaderName'); | | 8 | +isFunc(validateHeaderValue, 'validateHeaderValue'); | | 9 | + | | 10 | +// Expected to be useful as static methods | | 11 | +console.log('validateHeaderName'); | | 12 | +// - when used with valid header names - should not throw | | 13 | +[ | | 14 | + 'user-agent', | | 15 | + 'USER-AGENT', | | 16 | + 'User-Agent', | | 17 | + 'x-forwarded-for' | | 18 | +].forEach((name) => { | | 19 | + console.log('does not throw for "%s"', name); | | 20 | + validateHeaderName(name); | | 21 | +}); | | 22 | + | | 23 | +// - when used with invalid header names: | | 24 | +[ | | 25 | + 'איקס-פורוורד-פור', | | 26 | + 'x-forwarded-fםr', | | 27 | +].forEach((name) => { | | 28 | + console.log('throws for: "%s"', name.slice(0, 50)); | | 29 | + assert.throws( | | 30 | + () => validateHeaderName(name), | | 31 | + { code: 'ERR_INVALID_HTTP_TOKEN' } | | 32 | + ); | | 33 | +}); | | 34 | + | | 35 | +console.log('validateHeaderValue'); | | 36 | +// - when used with valid header values - should not throw | | 37 | +[ | | 38 | + ['x-valid', 1], | | 39 | + ['x-valid', '1'], | | 40 | + ['x-valid', 'string'], | | 41 | +].forEach(([name, value]) => { | | 42 | + console.log('does not throw for "%s"', name); | | 43 | + validateHeaderValue(name, value); | | 44 | +}); | | 45 | + | | 46 | +// - when used with invalid header values: | | 47 | +[ | | 48 | + // [header, value, expectedCode] | | 49 | + ['x-undefined', undefined, 'ERR_HTTP_INVALID_HEADER_VALUE'], | | 50 | + ['x-bad-char', 'לא תקין', 'ERR_INVALID_CHAR'], | | 51 | +].forEach(([name, value, code]) => { | | 52 | + console.log('throws %s for: "%s: %s"', code, name, value); | | 53 | + assert.throws( | | 54 | + () => validateHeaderValue(name, value), | | 55 | + { code } | | 56 | + ); | | 57 | +}); | | 58 | + | | 59 | +// Misc. | | 60 | +function isFunc(v, ttl) { | | 61 | + assert.ok(v.constructor === Function, `${ttl} is expected to be a function`); | | 62 | +} |
|