idnits 2.17.1 draft-ietf-httpbis-header-structure-12.txt: Checking boilerplate required by RFC 5378 and the IETF Trust (see https://trustee.ietf.org/license-info): ---------------------------------------------------------------------------- No issues found here. Checking nits according to https://www.ietf.org/id-info/1id-guidelines.txt: ---------------------------------------------------------------------------- No issues found here. Checking nits according to https://www.ietf.org/id-info/checklist : ---------------------------------------------------------------------------- ** There is 1 instance of too long lines in the document, the longest one being 1 character in excess of 72. ** The abstract seems to contain references ([2], [3], [4], [5], [1]), which it shouldn't. Please replace those with straight textual mentions of the documents in question. Miscellaneous warnings: ---------------------------------------------------------------------------- == The copyright year in the IETF Trust and authors Copyright Line does not match the current year -- The document date (August 19, 2019) is 1712 days in the past. Is this intentional? Checking references for intended status: Proposed Standard ---------------------------------------------------------------------------- (See RFCs 3967 and 4897 for information about using normative references to lower-maturity documents in RFCs) -- Looks like a reference, but probably isn't: '1' on line 1322 -- Looks like a reference, but probably isn't: '2' on line 1324 -- Looks like a reference, but probably isn't: '3' on line 1326 -- Looks like a reference, but probably isn't: '4' on line 1328 -- Looks like a reference, but probably isn't: '5' on line 1330 == Missing Reference: 'RFCxxxx' is mentioned on line 255, but not defined == Missing Reference: 'RFC3986' is mentioned on line 268, but not defined -- Looks like a reference, but probably isn't: '6' on line 1332 -- Looks like a reference, but probably isn't: '7' on line 1414 ** Obsolete normative reference: RFC 7230 (Obsoleted by RFC 9110, RFC 9112) -- Obsolete informational reference (is this intentional?): RFC 7231 (Obsoleted by RFC 9110) -- Obsolete informational reference (is this intentional?): RFC 7540 (Obsoleted by RFC 9113) Summary: 3 errors (**), 0 flaws (~~), 3 warnings (==), 10 comments (--). Run idnits with the --verbose option for more detailed information about the items above. -------------------------------------------------------------------------------- 2 HTTP M. Nottingham 3 Internet-Draft Fastly 4 Intended status: Standards Track P-H. Kamp 5 Expires: February 20, 2020 The Varnish Cache Project 6 August 19, 2019 8 Structured Headers for HTTP 9 draft-ietf-httpbis-header-structure-12 11 Abstract 13 This document describes a set of data types and associated algorithms 14 that are intended to make it easier and safer to define and handle 15 HTTP header fields. It is intended for use by specifications of new 16 HTTP header fields that wish to use a common syntax that is more 17 restrictive than traditional HTTP field values. 19 Note to Readers 21 _RFC EDITOR: please remove this section before publication_ 23 Discussion of this draft takes place on the HTTP working group 24 mailing list (ietf-http-wg@w3.org), which is archived at 25 https://lists.w3.org/Archives/Public/ietf-http-wg/ [1]. 27 Working Group information can be found at https://httpwg.github.io/ 28 [2]; source code and issues list for this draft can be found at 29 https://github.com/httpwg/http-extensions/labels/header-structure 30 [3]. 32 Tests for implementations are collected at https://github.com/httpwg/ 33 structured-header-tests [4]. 35 Implementations are tracked at https://github.com/httpwg/wiki/wiki/ 36 Structured-Headers [5]. 38 Status of This Memo 40 This Internet-Draft is submitted in full conformance with the 41 provisions of BCP 78 and BCP 79. 43 Internet-Drafts are working documents of the Internet Engineering 44 Task Force (IETF). Note that other groups may also distribute 45 working documents as Internet-Drafts. The list of current Internet- 46 Drafts is at https://datatracker.ietf.org/drafts/current/. 48 Internet-Drafts are draft documents valid for a maximum of six months 49 and may be updated, replaced, or obsoleted by other documents at any 50 time. It is inappropriate to use Internet-Drafts as reference 51 material or to cite them other than as "work in progress." 53 This Internet-Draft will expire on February 20, 2020. 55 Copyright Notice 57 Copyright (c) 2019 IETF Trust and the persons identified as the 58 document authors. All rights reserved. 60 This document is subject to BCP 78 and the IETF Trust's Legal 61 Provisions Relating to IETF Documents 62 (https://trustee.ietf.org/license-info) in effect on the date of 63 publication of this document. Please review these documents 64 carefully, as they describe your rights and restrictions with respect 65 to this document. Code Components extracted from this document must 66 include Simplified BSD License text as described in Section 4.e of 67 the Trust Legal Provisions and are provided without warranty as 68 described in the Simplified BSD License. 70 Table of Contents 72 1. Introduction . . . . . . . . . . . . . . . . . . . . . . . . 3 73 1.1. Intentionally Strict Processing . . . . . . . . . . . . . 4 74 1.2. Notational Conventions . . . . . . . . . . . . . . . . . 4 75 2. Defining New Structured Headers . . . . . . . . . . . . . . . 5 76 3. Structured Header Data Types . . . . . . . . . . . . . . . . 6 77 3.1. Lists . . . . . . . . . . . . . . . . . . . . . . . . . . 6 78 3.2. Dictionaries . . . . . . . . . . . . . . . . . . . . . . 8 79 3.3. Items . . . . . . . . . . . . . . . . . . . . . . . . . . 9 80 3.4. Integers . . . . . . . . . . . . . . . . . . . . . . . . 9 81 3.5. Floats . . . . . . . . . . . . . . . . . . . . . . . . . 9 82 3.6. Strings . . . . . . . . . . . . . . . . . . . . . . . . . 10 83 3.7. Tokens . . . . . . . . . . . . . . . . . . . . . . . . . 10 84 3.8. Byte Sequences . . . . . . . . . . . . . . . . . . . . . 11 85 3.9. Booleans . . . . . . . . . . . . . . . . . . . . . . . . 11 86 4. Working With Structured Headers in Textual HTTP Headers . . . 11 87 4.1. Serializing Structured Headers . . . . . . . . . . . . . 11 88 4.2. Parsing Header Fields into Structured Headers . . . . . . 18 89 5. IANA Considerations . . . . . . . . . . . . . . . . . . . . . 27 90 6. Security Considerations . . . . . . . . . . . . . . . . . . . 27 91 7. References . . . . . . . . . . . . . . . . . . . . . . . . . 27 92 7.1. Normative References . . . . . . . . . . . . . . . . . . 27 93 7.2. Informative References . . . . . . . . . . . . . . . . . 28 94 7.3. URIs . . . . . . . . . . . . . . . . . . . . . . . . . . 28 95 Appendix A. Acknowledgements . . . . . . . . . . . . . . . . . . 29 96 Appendix B. Frequently Asked Questions . . . . . . . . . . . . . 29 97 B.1. Why not JSON? . . . . . . . . . . . . . . . . . . . . . . 29 98 B.2. Structured Headers don't "fit" my data. . . . . . . . . . 30 99 Appendix C. Implementation Notes . . . . . . . . . . . . . . . . 30 100 Appendix D. Changes . . . . . . . . . . . . . . . . . . . . . . 31 101 D.1. Since draft-ietf-httpbis-header-structure-11 . . . . . . 31 102 D.2. Since draft-ietf-httpbis-header-structure-10 . . . . . . 31 103 D.3. Since draft-ietf-httpbis-header-structure-09 . . . . . . 31 104 D.4. Since draft-ietf-httpbis-header-structure-08 . . . . . . 31 105 D.5. Since draft-ietf-httpbis-header-structure-07 . . . . . . 32 106 D.6. Since draft-ietf-httpbis-header-structure-06 . . . . . . 32 107 D.7. Since draft-ietf-httpbis-header-structure-05 . . . . . . 32 108 D.8. Since draft-ietf-httpbis-header-structure-04 . . . . . . 33 109 D.9. Since draft-ietf-httpbis-header-structure-03 . . . . . . 33 110 D.10. Since draft-ietf-httpbis-header-structure-02 . . . . . . 33 111 D.11. Since draft-ietf-httpbis-header-structure-01 . . . . . . 33 112 D.12. Since draft-ietf-httpbis-header-structure-00 . . . . . . 33 113 Authors' Addresses . . . . . . . . . . . . . . . . . . . . . . . 34 115 1. Introduction 117 Specifying the syntax of new HTTP header fields is an onerous task; 118 even with the guidance in [RFC7231], Section 8.3.1, there are many 119 decisions - and pitfalls - for a prospective HTTP header field 120 author. 122 Once a header field is defined, bespoke parsers and serializers often 123 need to be written, because each header has slightly different 124 handling of what looks like common syntax. 126 This document introduces a set of common data structures for use in 127 definitions of new HTTP header field values to address these 128 problems. In particular, it defines a generic, abstract model for 129 header field values, along with a concrete serialisation for 130 expressing that model in textual HTTP [RFC7230] header fields. 132 HTTP headers that are defined as "Structured Headers" use the types 133 defined in this specification to define their syntax and basic 134 handling rules, thereby simplifying both their definition by 135 specification writers and handling by implementations. 137 Additionally, future versions of HTTP can define alternative 138 serialisations of the abstract model of these structures, allowing 139 headers that use it to be transmitted more efficiently without being 140 redefined. 142 Note that it is not a goal of this document to redefine the syntax of 143 existing HTTP headers; the mechanisms described herein are only 144 intended to be used with headers that explicitly opt into them. 146 Section 2 describes how to specify a Structured Header. 148 Section 3 defines a number of abstract data types that can be used in 149 Structured Headers. Those abstract types can be serialized into and 150 parsed from textual HTTP headers using the algorithms described in 151 Section 4. 153 1.1. Intentionally Strict Processing 155 This specification intentionally defines strict parsing and 156 serialisation behaviours using step-by-step algorithms; the only 157 error handling defined is to fail the operation altogether. 159 It is designed to encourage faithful implementation and therefore 160 good interoperability. Therefore, an implementation that tried to be 161 "helpful" by being more tolerant of input would make interoperability 162 worse, since that would create pressure on other implementations to 163 implement similar (but likely subtly different) workarounds. 165 In other words, strict processing is an intentional feature of this 166 specification; it allows non-conformant input to be discovered and 167 corrected by the producer early, and avoids both interoperability and 168 security issues that might otherwise result. 170 Note that as a result of this strictness, if a header field is 171 appended to by multiple parties (e.g., intermediaries, or different 172 components in the sender), an error in one party's value is likely to 173 cause the entire header field to fail parsing. 175 1.2. Notational Conventions 177 The key words "MUST", "MUST NOT", "REQUIRED", "SHALL", "SHALL NOT", 178 "SHOULD", "SHOULD NOT", "RECOMMENDED", "NOT RECOMMENDED", "MAY", and 179 "OPTIONAL" in this document are to be interpreted as described in BCP 180 14 [RFC2119] [RFC8174] when, and only when, they appear in all 181 capitals, as shown here. 183 This document uses algorithms to specify parsing and serialisation 184 behaviours, and the Augmented Backus-Naur Form (ABNF) notation of 185 [RFC5234] to illustrate expected syntax in textual HTTP header 186 fields. In doing so, uses the VCHAR, SP, DIGIT, ALPHA and DQUOTE 187 rules from [RFC5234]. It also includes the OWS rule from [RFC7230]. 189 When parsing from textual HTTP header fields, implementations MUST 190 follow the algorithms, but MAY vary in implementation so as the 191 behaviours are indistinguishable from specified behaviour. If there 192 is disagreement between the parsing algorithms and ABNF, the 193 specified algorithms take precedence. In some places, the algorithms 194 are "greedy" with whitespace, but this should not affect conformance. 196 For serialisation to textual header fields, the ABNF illustrates the 197 range of acceptable wire representations with as much fidelity as 198 possible, and the algorithms define the recommended way to produce 199 them. Implementations MAY vary from the specified behaviour so long 200 as the output still matches the ABNF. 202 2. Defining New Structured Headers 204 To define a HTTP header as a structured header, its specification 205 needs to: 207 o Reference this specification. Recipients and generators of the 208 header need to know that the requirements of this document are in 209 effect. 211 o Specify the header field's allowed syntax for values, in terms of 212 the types described in Section 3, along with their associated 213 semantics. Syntax definitions are encouraged to use the ABNF 214 rules beginning with "sh-" defined in this specification. 216 o Specify any additional constraints upon the syntax of the 217 structured used, as well as the consequences when those 218 constraints are violated. When Structured Headers parsing fails, 219 the header is discarded (see Section 4.2); in most situations, 220 header-specific constraints should do likewise. 222 Note that a header field definition cannot relax the requirements of 223 this specification because doing so would preclude handling by 224 generic software; they can only add additional constraints (for 225 example, on the numeric range of integers and floats, the format of 226 strings and tokens, or the number of items in a list). Likewise, 227 header field definitions should use Structured Headers for the entire 228 header field value, not a portion thereof. 230 This specification defines minimums for the length or number of 231 various structures supported by Structured Headers implementations. 232 It does not specify maximum sizes in most cases, but header authors 233 should be aware that HTTP implementations do impose various limits on 234 the size of individual header fields, the total number of fields, 235 and/or the size of the entire header block. 237 For example, 239 42. Foo-Example Header 241 The Foo-Example HTTP header field conveys information about how 242 much Foo the message has. 244 Foo-Example is a Structured Header [RFCxxxx]. Its value MUST be a 245 dictionary ([RFCxxxx], Section Y.Y). Its ABNF is: 247 Foo-Example = sh-dictionary 249 The dictionary MUST contain: 251 * Exactly one member whose name is "foo", and whose value is an 252 integer ([RFCxxxx], Section Y.Y), indicating the number of foos 253 in the message. 254 * Exactly one member whose name is "barUrl", and whose value is a 255 string ([RFCxxxx], Section Y.Y), conveying the Bar URL for the 256 message. See below for processing requirements. 258 If the parsed header field does not contain both, it MUST be 259 ignored. 261 "foo" MUST be between 0 and 10, inclusive; other values MUST cause 262 the header to be ignored. 264 "barUrl" contains a URI-reference ([RFC3986], Section 4.1). 266 If barURL is not a valid URI-reference, it MUST be ignored. 267 If barURL is a relative reference ([RFC3986], Section 4.2), 268 it MUST be resolved ([RFC3986], Section 5) before being used. 270 3. Structured Header Data Types 272 This section defines the abstract value types that can be composed 273 into Structured Headers. The ABNF provided represents the on-wire 274 format in HTTP. 276 3.1. Lists 278 Lists are arrays of zero or more members, each of which can be an 279 item (Section 3.3) or an inner list (an array of zero or more items). 281 Each member of the top-level list can also have associated parameters 282 - an ordered map of key-value pairs where the keys are short, textual 283 strings and the values are items (Section 3.3). There can be zero or 284 more parameters on a member, and their keys are required to be unique 285 within that scope. 287 The ABNF for lists is: 289 sh-list = list-member *( OWS "," OWS list-member ) 290 list-member = ( sh-item / inner-list ) *parameter 291 inner-list = "(" OWS [ sh-item *( SP sh-item ) OWS ] ")" 292 parameter = OWS ";" OWS param-name [ "=" param-value ] 293 param-name = key 294 key = lcalpha *( lcalpha / DIGIT / "_" / "-" / "*" ) 295 lcalpha = %x61-7A ; a-z 296 param-value = sh-item 298 In textual HTTP headers, each member is separated by a comma and 299 optional whitespace. For example, a header field whose value is 300 defined as a list of strings could look like: 302 Example-StrListHeader: "foo", "bar", "It was the best of times." 304 In textual HTTP headers, inner lists are denoted by surrounding 305 parenthesis, and have their values delimited by a single space. A 306 header field whose value is defined as a list of lists of strings 307 could look like: 309 Example-StrListListHeader: ("foo" "bar"), ("baz"), ("bat" "one"), () 311 Note that the last member in this example is an empty inner list. 313 In textual HTTP headers, members' parameters are separated from the 314 member and each other by semicolons. For example: 316 Example-ParamListHeader: abc_123;a=1;b=2; cdef_456, (ghi jkl);q="9";r="w" 318 In textual HTTP headers, an empty list is denoted by not serialising 319 the header at all. 321 Parsers MUST support lists containing at least 1024 members, support 322 members with at least 256 parameters, support inner-lists containing 323 at least 256 members, and support parameter keys with at least 64 324 characters. 326 Header specifications can constrain the types of individual list 327 values (including that of individual inner-list members and 328 parameters) if necessary. 330 3.2. Dictionaries 332 Dictionaries are ordered maps of name-value pairs, where the names 333 are short, textual strings and the values are items (Section 3.3) or 334 arrays of items. There can be zero or more members, and their names 335 are required to be unique within the scope of the dictionary they 336 occur within. 338 Each member of the dictionary can also have associated parameters - 339 an ordered map of key-value pairs where the keys are short, textual 340 strings and the values are items (Section 3.3). There can be zero or 341 more parameters on a member, and their keys are required to be unique 342 within that scope. 344 Implementations MUST provide access to dictionaries both by index and 345 by name. Specifications MAY use either means of accessing the 346 members. 348 The ABNF for dictionaries in textual HTTP headers is: 350 sh-dictionary = dict-member *( OWS "," OWS dict-member ) 351 dict-member = member-name "=" member-value *parameter 352 member-name = key 353 member-value = sh-item / inner-list 355 In textual HTTP headers, members are separated by a comma with 356 optional whitespace, while names and values are separated by "=" 357 (without whitespace). For example: 359 Example-DictHeader: en="Applepie", da=*w4ZibGV0w6ZydGU=* 361 A dictionary with a member whose value is an inner-list of tokens: 363 Example-DictListHeader: rating=1.5, feelings=(joy sadness) 365 A dictionary with a mix of singular and list values, some with 366 parameters: 368 Example-MixDict: a=(1,2), b=3, c=4;aa=bb, d=(5,6);valid=?T 370 As with lists, an empty dictionary is represented in textual HTTP 371 headers by omitting the entire header field. 373 Typically, a header field specification will define the semantics 374 using individual member names, as well as whether their presence is 375 required or optional. Recipients MUST ignore names that are 376 undefined or unknown, unless the header field's specification 377 specifically disallows them. 379 Parsers MUST support dictionaries containing at least 1024 name/value 380 pairs, and names with at least 64 characters. 382 3.3. Items 384 An item is can be a integer (Section 3.4), float (Section 3.5), 385 string (Section 3.6), token (Section 3.7), byte sequence 386 (Section 3.8), or Boolean (Section 3.9). 388 The ABNF for items in textual HTTP headers is: 390 sh-item = sh-integer / sh-float / sh-string / sh-token / sh-binary 391 / sh-boolean 393 3.4. Integers 395 Integers have a range of -999,999,999,999,999 to 999,999,999,999,999 396 inclusive (i.e., up to fifteen digits, signed), for IEEE 754 397 compatibility ([IEEE754]). 399 The ABNF for integers in textual HTTP headers is: 401 sh-integer = ["-"] 1*15DIGIT 403 For example: 405 Example-IntegerHeader: 42 407 Note that commas in integers are used in this section's prose only 408 for readability; they are not valid in the wire format. 410 3.5. Floats 412 Floats are decimal numbers with an integer and a fractional 413 component. The fractional component has at most six digits of 414 precision. Additionally, like integers, it can have no more than 415 fifteen digits in total, which in some cases further constrains its 416 precision. 418 The ABNF for floats in textual HTTP headers is: 420 sh-float = ["-"] (1*9DIGIT "." 1*6DIGIT / 421 10DIGIT "." 1*5DIGIT / 422 11DIGIT "." 1*4DIGIT / 423 12DIGIT "." 1*3DIGIT / 424 13DIGIT "." 1*2DIGIT / 425 14DIGIT "." 1DIGIT ) 427 For example, a header whose value is defined as a float could look 428 like: 430 Example-FloatHeader: 4.5 432 3.6. Strings 434 Strings are zero or more printable ASCII [RFC0020] characters (i.e., 435 the range 0x20 to 0x7E). Note that this excludes tabs, newlines, 436 carriage returns, etc. 438 The ABNF for strings in textual HTTP headers is: 440 sh-string = DQUOTE *(chr) DQUOTE 441 chr = unescaped / escaped 442 unescaped = %x20-21 / %x23-5B / %x5D-7E 443 escaped = "\" ( DQUOTE / "\" ) 445 In textual HTTP headers, strings are delimited with double quotes, 446 using a backslash ("\") to escape double quotes and backslashes. For 447 example: 449 Example-StringHeader: "hello world" 451 Note that strings only use DQUOTE as a delimiter; single quotes do 452 not delimit strings. Furthermore, only DQUOTE and "\" can be 453 escaped; other sequences MUST cause parsing to fail. 455 Unicode is not directly supported in this document, because it causes 456 a number of interoperability issues, and - with few exceptions - 457 header values do not require it. 459 When it is necessary for a field value to convey non-ASCII string 460 content, a byte sequence (Section 3.8) SHOULD be specified, along 461 with a character encoding (preferably UTF-8). 463 Parsers MUST support strings with at least 1024 characters. 465 3.7. Tokens 467 Tokens are short textual words; their abstract model is identical to 468 their expression in the textual HTTP serialisation. 470 The ABNF for tokens in textual HTTP headers is: 472 sh-token = ALPHA 473 *( ALPHA / DIGIT / "_" / "-" / "." / ":" / "%" 474 / "*" / "/" ) 476 Parsers MUST support tokens with at least 512 characters. 478 Note that a Structured Header token is not the same as the "token" 479 ABNF rule defined in [RFC7230]. 481 3.8. Byte Sequences 483 Byte sequences can be conveyed in Structured Headers. 485 The ABNF for a byte sequence in textual HTTP headers is: 487 sh-binary = "*" *(base64) "*" 488 base64 = ALPHA / DIGIT / "+" / "/" / "=" 490 In textual HTTP headers, a byte sequence is delimited with asterisks 491 and encoded using base64 ([RFC4648], Section 4). For example: 493 Example-BinaryHdr: *cHJldGVuZCB0aGlzIGlzIGJpbmFyeSBjb250ZW50Lg==* 495 Parsers MUST support byte sequences with at least 16384 octets after 496 decoding. 498 3.9. Booleans 500 Boolean values can be conveyed in Structured Headers. 502 The ABNF for a Boolean in textual HTTP headers is: 504 sh-boolean = "?" boolean 505 boolean = "0" / "1" 507 In textual HTTP headers, a boolean is indicated with a leading "?" 508 character. For example: 510 Example-BoolHdr: ?1 512 4. Working With Structured Headers in Textual HTTP Headers 514 This section defines how to serialize and parse Structured Headers in 515 textual header fields, and protocols compatible with them (e.g., in 516 HTTP/2 [RFC7540] before HPACK [RFC7541] is applied). 518 4.1. Serializing Structured Headers 520 Given a structure defined in this specification: 522 1. If the structure is a dictionary or list and its value is empty 523 (i.e., it has no members), do not send the serialize field at all 524 (i.e., omit both the field-name and field-value). 526 2. If the structure is a dictionary, let output_string be the result 527 of Serializing a Dictionary (Section 4.1.2). 529 3. Else if the structure is a list, let output_string be the result 530 of Serializing a List (Section 4.1.1). 532 4. Else if the structure is an item, let output_string be the result 533 of Serializing an Item (Section 4.1.3). 535 5. Else, fail serialisation. 537 6. Return output_string converted into an array of bytes, using 538 ASCII encoding [RFC0020]. 540 4.1.1. Serializing a List 542 Given a list of (member, parameters) as input_list: 544 1. Let output be an empty string. 546 2. For each (member, parameters) of input_list: 548 1. If member is an array, let mem_value be the result of 549 applying Serialising an Inner List (Section 4.1.1.1) to 550 member. 552 2. Otherwise, let mem_value be the result of applying 553 Serializing an Item (Section 4.1.3) to member. 555 3. Append mem_value to output. 557 4. Append the result of Serializing Parameters Section 4.1.1.2 558 with parameters to output. 560 5. If more members remain in input_plist: 562 1. Append a COMMA to output. 564 2. Append a single WS to output. 566 3. Return output. 568 4.1.1.1. Serialising an Inner List 570 Given an array inner_list: 572 1. Let output be the string "(". 574 2. For each member mem of inner_list: 576 1. Let value be the result of applying Serializing an Item 577 (Section 4.1.3) to mem. 579 2. Append value to output. 581 3. If inner_list is not empty, append a single WS to output. 583 3. Append ")" to output. 585 4. Return output. 587 4.1.1.2. Serializing Parameters 589 Given an ordered dictionary parameters: 591 1. Let output be an empty string. 593 2. For each parameter in parameters: 595 3. Append ";" to output. 597 4. Let name be the result of applying Serializing a Key 598 (Section 4.1.1.3) to parameter's param-name. 600 5. Append name to output. 602 6. If parameter has a param-value: 604 1. Let value be the result of applying Serializing an Item 605 (Section 4.1.3) to parameter's param-value. 607 2. Append "=" to output. 609 3. Append value to output. 611 7. Return output. 613 4.1.1.3. Serializing a Key 615 Given a key as input_key: 617 1. If input_key is not a sequence of characters, or contains 618 characters not allowed in the ABNF for key, fail serialisation. 620 2. Let output be an empty string. 622 3. Append input_key to output. 624 4. Return output. 626 4.1.2. Serializing a Dictionary 628 Given a dictionary as input_dictionary: 630 1. Let output be an empty string. 632 2. For each (member, parameters) of input_dictionary: 634 1. Let name be the result of applying Serializing a Key 635 (Section 4.1.1.3) to member's member-name. 637 2. Append name to output. 639 3. Append "=" to output. 641 4. If member is an array, let value be the result of applying 642 Serialising an Inner List (Section 4.1.1.1) to member. 644 5. Otherwise, let value be the result of applying Serializing an 645 Item (Section 4.1.3) to member. 647 6. Append value to output. 649 7. Append the result of Serializing Parameters Section 4.1.1.2 650 with parameters to output. 652 8. If more members remain in input_dictionary: 654 1. Append a COMMA to output. 656 2. Append a single WS to output. 658 3. Return output. 660 4.1.3. Serializing an Item 662 Given an item as input_item: 664 1. If input_item is an integer, return the result of applying 665 Serializing an Integer (Section 4.1.4) to input_item. 667 2. If input_item is a float, return the result of applying 668 Serializing a Float (Section 4.1.5) to input_item. 670 3. If input_item is a string, return the result of applying 671 Serializing a String (Section 4.1.6) to input_item. 673 4. If input_item is a token, return the result of Serializing a 674 Token (Section 4.1.7) to input_item. 676 5. If input_item is a Boolean, return the result of applying 677 Serializing a Boolean (Section 4.1.9) to input_item. 679 6. If input_item is a byte sequence, return the result of applying 680 Serializing a Byte Sequence (Section 4.1.8) to input_item. 682 7. Otherwise, fail serialisation. 684 4.1.4. Serializing an Integer 686 Given an integer as input_integer: 688 1. If input_integer is not an integer in the range of 689 -999,999,999,999,999 to 999,999,999,999,999 inclusive, fail 690 serialisation. 692 2. Let output be an empty string. 694 3. If input_integer is less than (but not equal to) 0, append "-" to 695 output. 697 4. Append input_integer's numeric value represented in base 10 using 698 only decimal digits to output. 700 5. Return output. 702 4.1.5. Serializing a Float 704 Given a float as input_float: 706 1. If input_float's fractional component has more than six digits of 707 precision, fail serialisation. 709 2. If the number of digits of precision in input_float's fractional 710 component plus those in its integer component add to more than 711 fifteen digits, fail serialisation. 713 3. Let output be an empty string. 715 4. If input_float is less than (but not equal to) 0, append "-" to 716 output. 718 5. Append input_float's integer component represented in base 10 719 using only decimal digits to output; if it is zero, append "0". 721 6. Append "." to output. 723 7. Append input_float's fractional component represented in base 10 724 using only decimal digits to output; if it is zero, append "0". 726 8. Return output. 728 4.1.6. Serializing a String 730 Given a string as input_string: 732 1. If input_string is not a sequence of characters, or contains 733 characters outside the range allowed by VCHAR or SP, fail 734 serialisation. 736 2. Let output be an empty string. 738 3. Append DQUOTE to output. 740 4. For each character char in input_string: 742 1. If char is "\" or DQUOTE: 744 1. Append "\" to output. 746 2. Append char to output. 748 5. Append DQUOTE to output. 750 6. Return output. 752 4.1.7. Serializing a Token 754 Given a token as input_token: 756 1. If input_token is not a sequence of characters, or contains 757 characters not allowed in Section 3.7, fail serialisation. 759 2. Let output be an empty string. 761 3. Append input_token to output. 763 4. Return output. 765 4.1.8. Serializing a Byte Sequence 767 Given a byte sequence as input_bytes: 769 1. If input_bytes is not a sequence of bytes, fail serialisation. 771 2. Let output be an empty string. 773 3. Append "*" to output. 775 4. Append the result of base64-encoding input_bytes as per 776 [RFC4648], Section 4, taking account of the requirements below. 778 5. Append "*" to output. 780 6. Return output. 782 The encoded data is required to be padded with "=", as per [RFC4648], 783 Section 3.2. 785 Likewise, encoded data SHOULD have pad bits set to zero, as per 786 [RFC4648], Section 3.5, unless it is not possible to do so due to 787 implementation constraints. 789 4.1.9. Serializing a Boolean 791 Given a Boolean as input_boolean: 793 1. If input_boolean is not a boolean, fail serialisation. 795 2. Let output be an empty string. 797 3. Append "?" to output. 799 4. If input_boolean is true, append "1" to output. 801 5. If input_boolean is false, append "0" to output. 803 6. Return output. 805 4.2. Parsing Header Fields into Structured Headers 807 When a receiving implementation parses textual HTTP header fields 808 that are known to be Structured Headers, it is important that care be 809 taken, as there are a number of edge cases that can cause 810 interoperability or even security problems. This section specifies 811 the algorithm for doing so. 813 Given an array of bytes input_bytes that represents the chosen 814 header's field-value (which is an empty string if that header is not 815 present), and header_type (one of "dictionary", "list", or "item"), 816 return the parsed header value. 818 1. Convert input_bytes into an ASCII string input_string; if 819 conversion fails, fail parsing. 821 2. Discard any leading OWS from input_string. 823 3. If header_type is "list", let output be the result of Parsing a 824 List from Text (Section 4.2.1). 826 4. If header_type is "dictionary", let output be the result of 827 Parsing a Dictionary from Text (Section 4.2.2). 829 5. If header_type is "item", let output be the result of Parsing an 830 Item from Text (Section 4.2.4). 832 6. Discard any leading OWS from input_string. 834 7. If input_string is not empty, fail parsing. 836 8. Otherwise, return output. 838 When generating input_bytes, parsers MUST combine all instances of 839 the target header field into one comma-separated field-value, as per 840 [RFC7230], Section 3.2.2; this assures that the header is processed 841 correctly. 843 For Lists and Dictionaries, this has the effect of correctly 844 concatenating all instances of the header field, as long as 845 individual individual members of the top-level data structure are not 846 split across multiple header instances. 848 Strings split across multiple header instances will have 849 unpredictable results, because comma(s) and whitespace inserted upon 850 combination will become part of the string output by the parser. 851 Since concatenation might be done by an upstream intermediary, the 852 results are not under the control of the serializer or the parser. 854 Tokens, Integers, Floats and Byte Sequences cannot be split across 855 multiple headers because the inserted commas will cause parsing to 856 fail. 858 If parsing fails - including when calling another algorithm - the 859 entire header field's value MUST be discarded. This is intentionally 860 strict, to improve interoperability and safety, and specifications 861 referencing this document are not allowed to loosen this requirement. 863 4.2.1. Parsing a List from Text 865 Given an ASCII string input_string, return an array of (member, 866 parameters). input_string is modified to remove the parsed value. 868 1. Let members be an empty array. 870 2. While input_string is not empty: 872 1. Let member be the result of running Parsing a Parameterized 873 Member from Text (Section 4.2.1.1) with input_string. 875 2. Append member to members. 877 3. Discard any leading OWS from input_string. 879 4. If input_string is empty, return members. 881 5. Consume the first character of input_string; if it is not 882 COMMA, fail parsing. 884 6. Discard any leading OWS from input_string. 886 7. If input_string is empty, there is a trailing comma; fail 887 parsing. 889 3. No structured data has been found; return members (which is 890 empty). 892 4.2.1.1. Parsing a Parameterized Member from Text 894 Given an ASCII string input_string, return an token with an ordered 895 map of parameters. input_string is modified to remove the parsed 896 value. 898 1. If the first character of input_string is "(", let member be the 899 result of running Parsing an Inner List (Section 4.2.1.2) with 900 input_string. 902 2. Else, let member be the result of running Parsing an Item 903 (Section 4.2.4) with input_string. 905 3. Let parameters be an empty, ordered map. 907 4. In a loop: 909 1. Discard any leading OWS from input_string. 911 2. If the first character of input_string is not ";", exit the 912 loop. 914 3. Consume a ";" character from the beginning of input_string. 916 4. Discard any leading OWS from input_string. 918 5. let param_name be the result of Parsing a key from Text 919 (Section 4.2.3) from input_string. 921 6. If param_name is already present in parameters, there is a 922 duplicate; fail parsing. 924 7. Let param_value be a null value. 926 8. If the first character of input_string is "=": 928 1. Consume the "=" character at the beginning of 929 input_string. 931 2. Let param_value be the result of Parsing an Item from 932 Text (Section 4.2.4) from input_string. 934 9. Append key param_name with value param_value to parameters. 936 5. Return the tuple (member, parameters). 938 4.2.1.2. Parsing an Inner List 940 Given an ASCII string input_string, return an array of items. 941 input_string is modified to remove the parsed value. 943 1. Consume the first character of input_string; if it is not "(", 944 fail parsing. 946 2. Let inner_list be an empty array. 948 3. While input_string is not empty: 950 1. Discard any leading OWS from input_string. 952 2. If the first character of input_string is ")": 954 1. Consume the first character of input_string. 956 2. Return inner_list. 958 3. Let item be the result of running Parsing an Item from Text 959 (Section 4.2.4) with input_string. 961 4. Append item to inner_list. 963 5. If the first character of input_string is not SP or ")", fail 964 parsing. 966 4. The end of the inner list was not found; fail parsing. 968 4.2.2. Parsing a Dictionary from Text 970 Given an ASCII string input_string, return an ordered map of (key, 971 item). input_string is modified to remove the parsed value. 973 1. Let dictionary be an empty, ordered map. 975 2. While input_string is not empty: 977 1. Let this_key be the result of running Parsing a Key from 978 Text (Section 4.2.3) with input_string. 980 2. If dictionary already contains the name this_key, there is a 981 duplicate; fail parsing. 983 3. Consume the first character of input_string; if it is not 984 "=", fail parsing. 986 4. Let member be the result of running Parsing a Parameterized 987 Member from Text (Section 4.2.1.1) with input_string. 989 5. Add name this_key with value member to dictionary. 991 6. Discard any leading OWS from input_string. 993 7. If input_string is empty, return dictionary. 995 8. Consume the first character of input_string; if it is not 996 COMMA, fail parsing. 998 9. Discard any leading OWS from input_string. 1000 10. If input_string is empty, there is a trailing comma; fail 1001 parsing. 1003 3. No structured data has been found; return dictionary (which is 1004 empty). 1006 4.2.3. Parsing a Key from Text 1008 Given an ASCII string input_string, return a key. input_string is 1009 modified to remove the parsed value. 1011 1. If the first character of input_string is not lcalpha, fail 1012 parsing. 1014 2. Let output_string be an empty string. 1016 3. While input_string is not empty: 1018 1. Let char be the result of removing the first character of 1019 input_string. 1021 2. If char is not one of lcalpha, DIGIT, "*", "_", or "-": 1023 1. Prepend char to input_string. 1025 2. Return output_string. 1027 3. Append char to output_string. 1029 4. Return output_string. 1031 4.2.4. Parsing an Item from Text 1033 Given an ASCII string input_string, return an item. input_string is 1034 modified to remove the parsed value. 1036 1. If the first character of input_string is a "-" or a DIGIT, 1037 process input_string as a number (Section 4.2.5) and return the 1038 result. 1040 2. If the first character of input_string is a DQUOTE, process 1041 input_string as a string (Section 4.2.6) and return the result. 1043 3. If the first character of input_string is "*", process 1044 input_string as a byte sequence (Section 4.2.8) and return the 1045 result. 1047 4. If the first character of input_string is "?", process 1048 input_string as a Boolean (Section 4.2.9) and return the result. 1050 5. If the first character of input_string is an ALPHA, process 1051 input_string as a token (Section 4.2.7) and return the result. 1053 6. Otherwise, the item type is unrecognized; fail parsing. 1055 4.2.5. Parsing a Number from Text 1057 Given an ASCII string input_string, return a number. input_string is 1058 modified to remove the parsed value. 1060 NOTE: This algorithm parses both Integers (Section 3.4) and Floats 1061 (Section 3.5), and returns the corresponding structure. 1063 1. Let type be "integer". 1065 2. Let sign be 1. 1067 3. Let input_number be an empty string. 1069 4. If the first character of input_string is "-", consume it and 1070 set sign to -1. 1072 5. If input_string is empty, there is an empty integer; fail 1073 parsing. 1075 6. If the first character of input_string is not a DIGIT, fail 1076 parsing. 1078 7. While input_string is not empty: 1080 1. Let char be the result of consuming the first character of 1081 input_string. 1083 2. If char is a DIGIT, append it to input_number. 1085 3. Else, if type is "integer" and char is ".", append char to 1086 input_number and set type to "float". 1088 4. Otherwise, prepend char to input_string, and exit the loop. 1090 5. If type is "integer" and input_number contains more than 15 1091 characters, fail parsing. 1093 6. If type is "float" and input_number contains more than 16 1094 characters, fail parsing. 1096 8. If type is "integer": 1098 1. Parse input_number as an integer and let output_number be 1099 the product of the result and sign. 1101 2. If output_number is outside the range defined in 1102 Section 3.4, fail parsing. 1104 9. Otherwise: 1106 1. If the final character of input_number is ".", fail parsing. 1108 2. If the number of characters after "." in input_number is 1109 greater than six, fail parsing. 1111 3. Parse input_number as a float and let output_number be the 1112 product of the result and sign. 1114 10. Return output_number. 1116 4.2.6. Parsing a String from Text 1118 Given an ASCII string input_string, return an unquoted string. 1119 input_string is modified to remove the parsed value. 1121 1. Let output_string be an empty string. 1123 2. If the first character of input_string is not DQUOTE, fail 1124 parsing. 1126 3. Discard the first character of input_string. 1128 4. While input_string is not empty: 1130 1. Let char be the result of consuming the first character of 1131 input_string. 1133 2. If char is a backslash ("\"): 1135 1. If input_string is now empty, fail parsing. 1137 2. Else: 1139 1. Let next_char be the result of consuming the first 1140 character of input_string. 1142 2. If next_char is not DQUOTE or "\", fail parsing. 1144 3. Append next_char to output_string. 1146 3. Else, if char is DQUOTE, return output_string. 1148 4. Else, if char is in the range %x00-1f or %x7f (i.e., is not 1149 in VCHAR or SP), fail parsing. 1151 5. Else, append char to output_string. 1153 5. Reached the end of input_string without finding a closing DQUOTE; 1154 fail parsing. 1156 4.2.7. Parsing a Token from Text 1158 Given an ASCII string input_string, return a token. input_string is 1159 modified to remove the parsed value. 1161 1. If the first character of input_string is not ALPHA, fail 1162 parsing. 1164 2. Let output_string be an empty string. 1166 3. While input_string is not empty: 1168 1. Let char be the result of consuming the first character of 1169 input_string. 1171 2. If char is not one of ALPHA, DIGIT, "_", "-", ".", ":", "%", 1172 "*" or "/": 1174 1. Prepend char to input_string. 1176 2. Return output_string. 1178 3. Append char to output_string. 1180 4. Return output_string. 1182 4.2.8. Parsing a Byte Sequence from Text 1184 Given an ASCII string input_string, return a byte sequence. 1185 input_string is modified to remove the parsed value. 1187 1. If the first character of input_string is not "*", fail parsing. 1189 2. Discard the first character of input_string. 1191 3. If there is not a "*" character before the end of input_string, 1192 fail parsing. 1194 4. Let b64_content be the result of consuming content of 1195 input_string up to but not including the first instance of the 1196 character "*". 1198 5. Consume the "*" character at the beginning of input_string. 1200 6. If b64_content contains a character not included in ALPHA, DIGIT, 1201 "+", "/" and "=", fail parsing. 1203 7. Let binary_content be the result of Base 64 Decoding [RFC4648] 1204 b64_content, synthesizing padding if necessary (note the 1205 requirements about recipient behaviour below). 1207 8. Return binary_content. 1209 Because some implementations of base64 do not allow reject of encoded 1210 data that is not properly "=" padded (see [RFC4648], Section 3.2), 1211 parsers SHOULD NOT fail when it is not present, unless they cannot be 1212 configured to do so. 1214 Because some implementations of base64 do not allow rejection of 1215 encoded data that has non-zero pad bits (see [RFC4648], Section 3.5), 1216 parsers SHOULD NOT fail when it is present, unless they cannot be 1217 configured to do so. 1219 This specification does not relax the requirements in [RFC4648], 1220 Section 3.1 and 3.3; therefore, parsers MUST fail on characters 1221 outside the base64 alphabet, and on line feeds in encoded data. 1223 4.2.9. Parsing a Boolean from Text 1225 Given an ASCII string input_string, return a Boolean. input_string is 1226 modified to remove the parsed value. 1228 1. If the first character of input_string is not "?", fail parsing. 1230 2. Discard the first character of input_string. 1232 3. If the first character of input_string matches "1", discard the 1233 first character, and return true. 1235 4. If the first character of input_string matches "0", discard the 1236 first character, and return false. 1238 5. No value has matched; fail parsing. 1240 5. IANA Considerations 1242 This draft has no actions for IANA. 1244 6. Security Considerations 1246 The size of most types defined by Structured Headers is not limited; 1247 as a result, extremely large header fields could be an attack vector 1248 (e.g., for resource consumption). Most HTTP implementations limit 1249 the sizes of individual header fields as well as the overall header 1250 block size to mitigate such attacks. 1252 It is possible for parties with the ability to inject new HTTP header 1253 fields to change the meaning of a Structured Header. In some 1254 circumstances, this will cause parsing to fail, but it is not 1255 possible to reliably fail in all such circumstances. 1257 7. References 1259 7.1. Normative References 1261 [RFC0020] Cerf, V., "ASCII format for network interchange", STD 80, 1262 RFC 20, DOI 10.17487/RFC0020, October 1969, 1263 . 1265 [RFC2119] Bradner, S., "Key words for use in RFCs to Indicate 1266 Requirement Levels", BCP 14, RFC 2119, 1267 DOI 10.17487/RFC2119, March 1997, 1268 . 1270 [RFC4648] Josefsson, S., "The Base16, Base32, and Base64 Data 1271 Encodings", RFC 4648, DOI 10.17487/RFC4648, October 2006, 1272 . 1274 [RFC5234] Crocker, D., Ed. and P. Overell, "Augmented BNF for Syntax 1275 Specifications: ABNF", STD 68, RFC 5234, 1276 DOI 10.17487/RFC5234, January 2008, 1277 . 1279 [RFC7230] Fielding, R., Ed. and J. Reschke, Ed., "Hypertext Transfer 1280 Protocol (HTTP/1.1): Message Syntax and Routing", 1281 RFC 7230, DOI 10.17487/RFC7230, June 2014, 1282 . 1284 [RFC8174] Leiba, B., "Ambiguity of Uppercase vs Lowercase in RFC 1285 2119 Key Words", BCP 14, RFC 8174, DOI 10.17487/RFC8174, 1286 May 2017, . 1288 7.2. Informative References 1290 [IEEE754] IEEE, "IEEE Standard for Floating-Point Arithmetic", 1291 IEEE 754-2008, DOI 10.1109/IEEESTD.2008.4610935, 1292 ISBN 978-0-7381-5752-8, August 2008, 1293 . 1295 See also http://grouper.ieee.org/groups/754/ [6]. 1297 [RFC7231] Fielding, R., Ed. and J. Reschke, Ed., "Hypertext Transfer 1298 Protocol (HTTP/1.1): Semantics and Content", RFC 7231, 1299 DOI 10.17487/RFC7231, June 2014, 1300 . 1302 [RFC7493] Bray, T., Ed., "The I-JSON Message Format", RFC 7493, 1303 DOI 10.17487/RFC7493, March 2015, 1304 . 1306 [RFC7540] Belshe, M., Peon, R., and M. Thomson, Ed., "Hypertext 1307 Transfer Protocol Version 2 (HTTP/2)", RFC 7540, 1308 DOI 10.17487/RFC7540, May 2015, 1309 . 1311 [RFC7541] Peon, R. and H. Ruellan, "HPACK: Header Compression for 1312 HTTP/2", RFC 7541, DOI 10.17487/RFC7541, May 2015, 1313 . 1315 [RFC8259] Bray, T., Ed., "The JavaScript Object Notation (JSON) Data 1316 Interchange Format", STD 90, RFC 8259, 1317 DOI 10.17487/RFC8259, December 2017, 1318 . 1320 7.3. URIs 1322 [1] https://lists.w3.org/Archives/Public/ietf-http-wg/ 1324 [2] https://httpwg.github.io/ 1326 [3] https://github.com/httpwg/http-extensions/labels/header-structure 1328 [4] https://github.com/httpwg/structured-header-tests 1330 [5] https://github.com/httpwg/wiki/wiki/Structured-Headers 1332 [6] https://github.com/httpwg/structured-header-tests 1334 Appendix A. Acknowledgements 1336 Many thanks to Matthew Kerwin for his detailed feedback and careful 1337 consideration during the development of this specification. 1339 Appendix B. Frequently Asked Questions 1341 B.1. Why not JSON? 1343 Earlier proposals for structured headers were based upon JSON 1344 [RFC8259]. However, constraining its use to make it suitable for 1345 HTTP header fields required senders and recipients to implement 1346 specific additional handling. 1348 For example, JSON has specification issues around large numbers and 1349 objects with duplicate members. Although advice for avoiding these 1350 issues is available (e.g., [RFC7493]), it cannot be relied upon. 1352 Likewise, JSON strings are by default Unicode strings, which have a 1353 number of potential interoperability issues (e.g., in comparison). 1354 Although implementers can be advised to avoid non-ASCII content where 1355 unnecessary, this is difficult to enforce. 1357 Another example is JSON's ability to nest content to arbitrary 1358 depths. Since the resulting memory commitment might be unsuitable 1359 (e.g., in embedded and other limited server deployments), it's 1360 necessary to limit it in some fashion; however, existing JSON 1361 implementations have no such limits, and even if a limit is 1362 specified, it's likely that some header field definition will find a 1363 need to violate it. 1365 Because of JSON's broad adoption and implementation, it is difficult 1366 to impose such additional constraints across all implementations; 1367 some deployments would fail to enforce them, thereby harming 1368 interoperability. In short, if it looks like JSON, people will be 1369 tempted to use a JSON parser / serialiser on header fields. 1371 Since a major goal for Structured Headers is to improve 1372 interoperability and simplify implementation, these concerns led to a 1373 format that requires a dedicated parser and serializer. 1375 Additionally, there were widely shared feelings that JSON doesn't 1376 "look right" in HTTP headers. 1378 B.2. Structured Headers don't "fit" my data. 1380 Structured headers intentionally limits the complexity of data 1381 structures, to assure that it can be processed in a performant manner 1382 with little overhead. This means that work is necessary to fit some 1383 data types into them. 1385 Sometimes, this can be achieved by creating limited substructures in 1386 values, and/or using more than one header. For example, consider: 1388 Example-Thing: name="Widget", cost=89.2, descriptions=(foo bar) 1389 Example-Description: foo; url="https://example.net"; context=123, 1390 bar; url="https://example.org"; context=456 1392 Since the description contains an array of key/value pairs, we use a 1393 List to represent them, with the token for each item in the array 1394 used to identify it in the "descriptions" member of the Example-Thing 1395 header. 1397 When specifying more than one header, it's important to remember to 1398 describe what a processor's behaviour should be when one of the 1399 headers is missing. 1401 If you need to fit arbitrarily complex data into a header, Structured 1402 Headers is probably a poor fit for your use case. 1404 Appendix C. Implementation Notes 1406 A generic implementation of this specification should expose the top- 1407 level parse (Section 4.2) and serialize (Section 4.1) functions. 1408 They need not be functions; for example, it could be implemented as 1409 an object, with methods for each of the different top-level types. 1411 For interoperability, it's important that generic implementations be 1412 complete and follow the algorithms closely; see Section 1.1. To aid 1413 this, a common test suite is being maintained by the community; see 1414 https://github.com/httpwg/structured-header-tests [7]. 1416 Implementers should note that dictionaries and parameters are order- 1417 preserving maps. Some headers may not convey meaning in the ordering 1418 of these data types, but it should still be exposed so that 1419 applications which need to use it will have it available. 1421 Likewise, implementations should note that it's important to preserve 1422 the distinction between tokens and strings. While most programming 1423 languages have native types that map to the other types well, it may 1424 be necessary to create a wrapper "token" object or use a parameter on 1425 functions to assure that these types remain separate. 1427 Appendix D. Changes 1429 _RFC Editor: Please remove this section before publication._ 1431 D.1. Since draft-ietf-httpbis-header-structure-11 1433 o Allow * in key (#844). 1435 o Constrain floats to six digits of precision (#848). 1437 o Allow dictionary members to have parameters (#842). 1439 D.2. Since draft-ietf-httpbis-header-structure-10 1441 o Update abstract (#799). 1443 o Input and output are now arrays of bytes (#662). 1445 o Implementations need to preserve difference between token and 1446 string (#790). 1448 o Allow empty dictionaries and lists (#781). 1450 o Change parameterized lists to have primary items (#797). 1452 o Allow inner lists in both dictionaries and lists; removes lists of 1453 lists (#816). 1455 o Subsume Parameterised Lists into Lists (#839). 1457 D.3. Since draft-ietf-httpbis-header-structure-09 1459 o Changed Boolean from T/F to 1/0 (#784). 1461 o Parameters are now ordered maps (#765). 1463 o Clamp integers to 15 digits (#737). 1465 D.4. Since draft-ietf-httpbis-header-structure-08 1467 o Disallow whitespace before items properly (#703). 1469 o Created "key" for use in dictionaries and parameters, rather than 1470 relying on identifier (#702). Identifiers have a separate minimum 1471 supported size. 1473 o Expanded the range of special characters allowed in identifier to 1474 include all of ALPHA, ".", ":", and "%" (#702). 1476 o Use "?" instead of "!" to indicate a Boolean (#719). 1478 o Added "Intentionally Strict Processing" (#684). 1480 o Gave better names for referring specs to use in Parameterised 1481 Lists (#720). 1483 o Added Lists of Lists (#721). 1485 o Rename Identifier to Token (#725). 1487 o Add implementation guidance (#727). 1489 D.5. Since draft-ietf-httpbis-header-structure-07 1491 o Make Dictionaries ordered mappings (#659). 1493 o Changed "binary content" to "byte sequence" to align with Infra 1494 specification (#671). 1496 o Changed "mapping" to "map" for #671. 1498 o Don't fail if byte sequences aren't "=" padded (#658). 1500 o Add Booleans (#683). 1502 o Allow identifiers in items again (#629). 1504 o Disallowed whitespace before items (#703). 1506 o Explain the consequences of splitting a string across multiple 1507 headers (#686). 1509 D.6. Since draft-ietf-httpbis-header-structure-06 1511 o Add a FAQ. 1513 o Allow non-zero pad bits. 1515 o Explicitly check for integers that violate constraints. 1517 D.7. Since draft-ietf-httpbis-header-structure-05 1519 o Reorganise specification to separate parsing out. 1521 o Allow referencing specs to use ABNF. 1523 o Define serialisation algorithms. 1525 o Refine relationship between ABNF, parsing and serialisation 1526 algorithms. 1528 D.8. Since draft-ietf-httpbis-header-structure-04 1530 o Remove identifiers from item. 1532 o Remove most limits on sizes. 1534 o Refine number parsing. 1536 D.9. Since draft-ietf-httpbis-header-structure-03 1538 o Strengthen language around failure handling. 1540 D.10. Since draft-ietf-httpbis-header-structure-02 1542 o Split Numbers into Integers and Floats. 1544 o Define number parsing. 1546 o Tighten up binary parsing and give it an explicit end delimiter. 1548 o Clarify that mappings are unordered. 1550 o Allow zero-length strings. 1552 o Improve string parsing algorithm. 1554 o Improve limits in algorithms. 1556 o Require parsers to combine header fields before processing. 1558 o Throw an error on trailing garbage. 1560 D.11. Since draft-ietf-httpbis-header-structure-01 1562 o Replaced with draft-nottingham-structured-headers. 1564 D.12. Since draft-ietf-httpbis-header-structure-00 1566 o Added signed 64bit integer type. 1568 o Drop UTF8, and settle on BCP137 ::EmbeddedUnicodeChar for h1- 1569 unicode-string. 1571 o Change h1_blob delimiter to ":" since "'" is valid t_char 1573 Authors' Addresses 1575 Mark Nottingham 1576 Fastly 1578 Email: mnot@mnot.net 1579 URI: https://www.mnot.net/ 1581 Poul-Henning Kamp 1582 The Varnish Cache Project 1584 Email: phk@varnish-cache.org