From 34cc0cb631aec135e2d33f2d565b95597326eea7 Mon Sep 17 00:00:00 2001 From: "Henry H. Andrews" Date: Thu, 20 Jun 2024 11:43:54 -0700 Subject: [PATCH 1/7] Start consolidating media / encoding guidance (3.1.1 port of 3923 1/6) This just moves (and occasionally copies) blocks of text and/or examples in preparation form more substantial streamlining. No modifications were made to any block. --- versions/3.1.1.md | 198 +++++++++++++++++++++++----------------------- 1 file changed, 101 insertions(+), 97 deletions(-) diff --git a/versions/3.1.1.md b/versions/3.1.1.md index 10f5f6742f..a16418c5b6 100644 --- a/versions/3.1.1.md +++ b/versions/3.1.1.md @@ -1550,6 +1550,8 @@ Field Name | Type | Description This object MAY be extended with [Specification Extensions](#specificationExtensions). +An `encoding` attribute is introduced to give you control over the serialization of parts of `multipart` request bodies. This attribute is _only_ applicable to request bodies, and _only_ for `multipart` and `application/x-www-form-urlencoded` media types. + ##### Media Type Examples ```json @@ -1657,21 +1659,60 @@ requestBody: To upload multiple files, a `multipart` media type MUST be used: -```yaml -requestBody: - content: - multipart/form-data: - schema: - properties: - # The property name 'file' will be used for all files. - file: - type: array - items: {} -``` +##### Support for x-www-form-urlencoded Request Bodies -As seen in the section on `multipart/form-data` below, the empty schema for `items` indicates a media type of `application/octet-stream`. +##### Special Considerations for `multipart` Content -##### Support for x-www-form-urlencoded Request Bodies +#### Encoding Object + +A single encoding definition applied to a single schema property. +See [Appendix B](#dataTypeConversion) for a discussion of converting values of various types to string representations. + +Properties are correlated with `multipart` parts using the `name` parameter to `Content-Disposition: form-data`, and with `application/x-www-form-urlencoded` using the query string parameter names. +In both cases, their order is implementation-defined. + +See [Appendix E](#percentEncodingAndFormMediaTypes) for a detailed examination of percent-encoding concerns for form media types. + +###### Common Fixed Fields + +These fields MAY be used either with or without the RFC6570-style serialization fields defined in the next section below. + +Field Name | Type | Description +---|:---:|--- +contentType | `string` | The `Content-Type` for encoding a specific property. The value is a comma-separated list, each element of which is either a specific media type (e.g. `image/png`) or a wildcard media type (e.g. `image/*`). Default value depends on the property type as shown in the table below. +headers | Map[`string`, [Header Object](#headerObject) \| [Reference Object](#referenceObject)] | A map allowing additional information to be provided as headers. `Content-Type` is described separately and SHALL be ignored in this section. This property SHALL be ignored if the request body media type is not a `multipart`. + +This object MAY be extended with [Specification Extensions](#specificationExtensions). + +The default values for `contentType` are as follows, where an _n/a_ in the `contentEncoding` column means that the presence or value of `contentEncoding` is irrelevant: + +Property `type` | Property `contentEncoding` | Default `contentType` +--------------- | -------------------------- | --------------------- +_absent_ | _n/a_ | `application/octet-stream` +`string` | _present_ | `application/octet-stream` +`string` | _absent_ | `text/plain` +`number`, `integer`, or `boolean` | _n/a_ | `text/plain` +`object` | _n/a_ | `application/json` +`array` | _n/a_ | according to the `type` of the `items` schema + +Determining how to handle a `type` value of `null` depends on how `null` values are being serialized. +If `null` values are entirely omitted, then the `contentType` is irrelevant. +See [Appendix B](#dataTypeConversion) for a discussion of data type conversion options. + +##### Fixed Fields for RFC6570-style Serialization + +Field Name | Type | Description +---|:---:|--- +style | `string` | Describes how a specific property value will be serialized depending on its type. See [Parameter Object](#parameterObject) for details on the [`style`](#parameterStyle) property. The behavior follows the same values as `query` parameters, including default values. Note that the initial `?` used in query strings is not used in `application/x-www-form-urlencoded` message bodies, and MUST be removed (if using an RFC6570 implementation) or simply not added (if constructing the string manually). This property SHALL be ignored if the request body media type is not `application/x-www-form-urlencoded` or `multipart/form-data`. If a value is explicitly defined, then the value of [`contentType`](#encodingContentType) (implicit or explicit) SHALL be ignored. +explode | `boolean` | When this is true, property values of type `array` or `object` generate separate parameters for each value of the array, or key-value-pair of the map. For other types of properties this property has no effect. When [`style`](#encodingStyle) is `form`, the default value is `true`. For all other styles, the default value is `false`. Note that despite `false` being the default for `deepObject`, the combination of `false` with `deepObject` is undefined. This property SHALL be ignored if the request body media type is not `application/x-www-form-urlencoded` or `multipart/form-data`. If a value is explicitly defined, then the value of [`contentType`](#encodingContentType) (implicit or explicit) SHALL be ignored. +allowReserved | `boolean` | When this is true, parameter values are serialized using reserved expansion, as defined by [RFC6570](https://datatracker.ietf.org/doc/html/rfc6570#autoid-20), which allows [RFC3986's reserved character set](https://datatracker.ietf.org/doc/html/rfc3986#autoid-13), as well as percent-encoded triples, to pass through unchanged, while still percent-encoding all other disallowed characters (including `%` outside of percent-encoded triples). Applications are still responsible for percent-encoding reserved characters that are [not allowed in the query string](https://datatracker.ietf.org/doc/html/rfc3986#autoid-24) (`[`, `]`, `#`), or have a special meaning in `application/x-www-form-urlencoded` (`-`, `&`, `+`); see Appendices [C](#usingRFC6570Implementations) and [E](#percentEncodingAndFormMediaTypes) for details. The default value is `false`. This property SHALL be ignored if the request body media type is not `application/x-www-form-urlencoded` or `multipart/form-data`. If a value is explicitly defined, then the value of [`contentType`](#encodingContentType) (implicit or explicit) SHALL be ignored. + +See also [Appendix C: Using RFC6570 Implementations](#usingRFC6570Implementations) for additional guidance, including on difficulties caused by the interaction between RFC6570's percent-encoding rules and the `multipart/form-data` media type. + +Note that the presence of at least one of `style`, `explode`, or `allowReserved` with an explicit value is equivalent to using `schema` with `in: query` Parameter Objects. +The absence of all three of those fields is the equivalent of using `content`, but with the media type specified in `contentType` rather than through a Media Type Object. + +See [Appendix E](#percentEncodingAndFormMediaTypes) for a detailed examination of percent-encoding concerns for form media types. To submit content using form url encoding via [RFC1866](https://tools.ietf.org/html/rfc1866), the following definition may be used: @@ -1722,9 +1763,28 @@ Here is the `id` parameter (without `address`) serialized as `application/json` id=%22f81d4fae-7dec-11d0-a765-00a0c91e6bf6%22 ``` -See [Appendix E](#percentEncodingAndFormMediaTypes) for a detailed examination of percent-encoding concerns for form media types. +`application/x-www-form-urlencoded` is a text format, which requires base64-encoding any binary data: -##### Special Considerations for `multipart` Content +```YAML +requestBody: + content: + application/x-www-form-urlencoded: + schema: + type: object + properties: + name: + type: string + icon: + # default for type string is text/plain, need to declare + # the appropriate contentType in the Encoding Object + type: string + contentEncoding: base64url + encoding: + icon: + contentType: image/png, image/jpeg +``` + +###### Encoding `multipart` Media Types It is common to use `multipart/form-data` as a `Content-Type` when transferring request bodies to operations. In contrast to 2.0, a `schema` is REQUIRED to define the input parameters to the operation when using `multipart` content. This supports complex structures as well as supporting mechanisms for multiple file uploads. @@ -1740,6 +1800,23 @@ Per the JSON Schema specification, `contentMediaType` without `contentEncoding` Note that only `multipart/*` media types with named parts can be described as shown here. Note also that while `multipart/form-data` originally defined a per-part `Content-Transfer-Encoding` header that could indicate base64 encoding (`contentEncoding: base64`), it has been deprecated for use with HTTP as of [RFC7578](https://www.rfc-editor.org/rfc/rfc7578#section-4.7). +The `form-data` disposition and its `name` parameter are mandatory for `multipart/form-data` ([RFC7578 §4.2](https://www.rfc-editor.org/rfc/rfc7578.html#section-4.2)). +Array properties are handled by applying the same `name` to multiple parts, as is recommended by [RFC7578 §4.3](https://www.rfc-editor.org/rfc/rfc7578.html#section-4.3) for supplying multiple values per form field. +See [RFC7578 §5](https://www.rfc-editor.org/rfc/rfc7578.html#section-5) for guidance regarding non-ASCII part names. + +Various other `multipart` types, most notable `multipart/mixed` ([RFC2046 §5.1.3](https://www.rfc-editor.org/rfc/rfc2046.html#section-5.1.3)) neither require nor forbid specific `Content-Disposition` values, which means care must be taken to ensure that any values used are supported by all relevant software. +It is not currently possible to correlate schema properties with unnamed, ordered parts in media types such as `multipart/mixed`, but implementations MAY choose to support such types when `Content-Disposition: form-data` is used with a `name` parameter. + +Note that there are significant restrictions on what headers can be used with `multipart` media types in general ([RFC2046 §5.1](https://www.rfc-editor.org/rfc/rfc2046.html#section-5.1)) and `multi-part/form-data` in particular ([RFC7578 §4.8](https://www.rfc-editor.org/rfc/rfc7578.html#section-4.8)). + +Note also that `Content-Transfer-Encoding` is deprecated for `multipart/form-data` ([RFC7578 §4.7](https://www.rfc-editor.org/rfc/rfc7578.html#section-4.7)) where binary data is supported, as it is in HTTP. +Using `contentEncoding` is equivalent to setting `Content-Transfer-Encoding` to the same value. +If `contentEncoding` is used along with setting a different `Content-Transfer-Encoding` value with the `headers` field, the result is undefined. + +See [Appendix E](#percentEncodingAndFormMediaTypes) for a detailed examination of percent-encoding concerns for form media types. + +##### Encoding Object Example + Examples: ```yaml @@ -1777,74 +1854,6 @@ requestBody: $ref: '#/components/schemas/Address' ``` -An `encoding` attribute is introduced to give you control over the serialization of parts of `multipart` request bodies. This attribute is _only_ applicable to request bodies, and _only_ for `multipart` and `application/x-www-form-urlencoded` media types. - -#### Encoding Object - -A single encoding definition applied to a single schema property. -See [Appendix B](#dataTypeConversion) for a discussion of converting values of various types to string representations. - -Properties are correlated with `multipart` parts using the `name` parameter to `Content-Disposition: form-data`, and with `application/x-www-form-urlencoded` using the query string parameter names. -In both cases, their order is implementation-defined. - -See [Appendix E](#percentEncodingAndFormMediaTypes) for a detailed examination of percent-encoding concerns for form media types. - -###### Common Fixed Fields - -These fields MAY be used either with or without the RFC6570-style serialization fields defined in the next section below. - -Field Name | Type | Description ----|:---:|--- -contentType | `string` | The `Content-Type` for encoding a specific property. The value is a comma-separated list, each element of which is either a specific media type (e.g. `image/png`) or a wildcard media type (e.g. `image/*`). Default value depends on the property type as shown in the table below. -headers | Map[`string`, [Header Object](#headerObject) \| [Reference Object](#referenceObject)] | A map allowing additional information to be provided as headers. `Content-Type` is described separately and SHALL be ignored in this section. This property SHALL be ignored if the request body media type is not a `multipart`. - -This object MAY be extended with [Specification Extensions](#specificationExtensions). - -The default values for `contentType` are as follows, where an _n/a_ in the `contentEncoding` column means that the presence or value of `contentEncoding` is irrelevant: - -Property `type` | Property `contentEncoding` | Default `contentType` ---------------- | -------------------------- | --------------------- -_absent_ | _n/a_ | `application/octet-stream` -`string` | _present_ | `application/octet-stream` -`string` | _absent_ | `text/plain` -`number`, `integer`, or `boolean` | _n/a_ | `text/plain` -`object` | _n/a_ | `application/json` -`array` | _n/a_ | according to the `type` of the `items` schema - -Determining how to handle a `type` value of `null` depends on how `null` values are being serialized. -If `null` values are entirely omitted, then the `contentType` is irrelevant. -See [Appendix B](#dataTypeConversion) for a discussion of data type conversion options. - -##### Fixed Fields for RFC6570-style Serialization - -Field Name | Type | Description ----|:---:|--- -style | `string` | Describes how a specific property value will be serialized depending on its type. See [Parameter Object](#parameterObject) for details on the [`style`](#parameterStyle) property. The behavior follows the same values as `query` parameters, including default values. Note that the initial `?` used in query strings is not used in `application/x-www-form-urlencoded` message bodies, and MUST be removed (if using an RFC6570 implementation) or simply not added (if constructing the string manually). This property SHALL be ignored if the request body media type is not `application/x-www-form-urlencoded` or `multipart/form-data`. If a value is explicitly defined, then the value of [`contentType`](#encodingContentType) (implicit or explicit) SHALL be ignored. -explode | `boolean` | When this is true, property values of type `array` or `object` generate separate parameters for each value of the array, or key-value-pair of the map. For other types of properties this property has no effect. When [`style`](#encodingStyle) is `form`, the default value is `true`. For all other styles, the default value is `false`. Note that despite `false` being the default for `deepObject`, the combination of `false` with `deepObject` is undefined. This property SHALL be ignored if the request body media type is not `application/x-www-form-urlencoded` or `multipart/form-data`. If a value is explicitly defined, then the value of [`contentType`](#encodingContentType) (implicit or explicit) SHALL be ignored. -allowReserved | `boolean` | When this is true, parameter values are serialized using reserved expansion, as defined by [RFC6570](https://datatracker.ietf.org/doc/html/rfc6570#autoid-20), which allows [RFC3986's reserved character set](https://datatracker.ietf.org/doc/html/rfc3986#autoid-13), as well as percent-encoded triples, to pass through unchanged, while still percent-encoding all other disallowed characters (including `%` outside of percent-encoded triples). Applications are still responsible for percent-encoding reserved characters that are [not allowed in the query string](https://datatracker.ietf.org/doc/html/rfc3986#autoid-24) (`[`, `]`, `#`), or have a special meaning in `application/x-www-form-urlencoded` (`-`, `&`, `+`); see Appendices [C](#usingRFC6570Implementations) and [E](#percentEncodingAndFormMediaTypes) for details. The default value is `false`. This property SHALL be ignored if the request body media type is not `application/x-www-form-urlencoded` or `multipart/form-data`. If a value is explicitly defined, then the value of [`contentType`](#encodingContentType) (implicit or explicit) SHALL be ignored. - -See also [Appendix C: Using RFC6570 Implementations](#usingRFC6570Implementations) for additional guidance, including on difficulties caused by the interaction between RFC6570's percent-encoding rules and the `multipart/form-data` media type. - -Note that the presence of at least one of `style`, `explode`, or `allowReserved` with an explicit value is equivalent to using `schema` with `in: query` Parameter Objects. -The absence of all three of those fields is the equivalent of using `content`, but with the media type specified in `contentType` rather than through a Media Type Object. - -###### Encoding `multipart` Media Types - -The `form-data` disposition and its `name` parameter are mandatory for `multipart/form-data` ([RFC7578 §4.2](https://www.rfc-editor.org/rfc/rfc7578.html#section-4.2)). -Array properties are handled by applying the same `name` to multiple parts, as is recommended by [RFC7578 §4.3](https://www.rfc-editor.org/rfc/rfc7578.html#section-4.3) for supplying multiple values per form field. -See [RFC7578 §5](https://www.rfc-editor.org/rfc/rfc7578.html#section-5) for guidance regarding non-ASCII part names. - -Various other `multipart` types, most notable `multipart/mixed` ([RFC2046 §5.1.3](https://www.rfc-editor.org/rfc/rfc2046.html#section-5.1.3)) neither require nor forbid specific `Content-Disposition` values, which means care must be taken to ensure that any values used are supported by all relevant software. -It is not currently possible to correlate schema properties with unnamed, ordered parts in media types such as `multipart/mixed`, but implementations MAY choose to support such types when `Content-Disposition: form-data` is used with a `name` parameter. - -Note that there are significant restrictions on what headers can be used with `multipart` media types in general ([RFC2046 §5.1](https://www.rfc-editor.org/rfc/rfc2046.html#section-5.1)) and `multi-part/form-data` in particular ([RFC7578 §4.8](https://www.rfc-editor.org/rfc/rfc7578.html#section-4.8)). - -Note also that `Content-Transfer-Encoding` is deprecated for `multipart/form-data` ([RFC7578 §4.7](https://www.rfc-editor.org/rfc/rfc7578.html#section-4.7)) where binary data is supported, as it is in HTTP. -Using `contentEncoding` is equivalent to setting `Content-Transfer-Encoding` to the same value. -If `contentEncoding` is used along with setting a different `Content-Transfer-Encoding` value with the `headers` field, the result is undefined. - -##### Encoding Object Example - `multipart/form-data` allows for binary parts: ```yaml @@ -1882,27 +1891,22 @@ requestBody: type: integer ``` -`application/x-www-form-urlencoded` is a text format, which requires base64-encoding any binary data: +To upload multiple files, a `multipart` media type MUST be used: -```YAML +```yaml requestBody: content: - application/x-www-form-urlencoded: + multipart/form-data: schema: - type: object properties: - name: - type: string - icon: - # default for type string is text/plain, need to declare - # the appropriate contentType in the Encoding Object - type: string - contentEncoding: base64url - encoding: - icon: - contentType: image/png, image/jpeg + # The property name 'file' will be used for all files. + file: + type: array + items: {} ``` +As seen in the section on `multipart/form-data` below, the empty schema for `items` indicates a media type of `application/octet-stream`. + #### Responses Object A container for the expected responses of an operation. From 9e07940785eb9d2358ae559cfcbbaeb596028809 Mon Sep 17 00:00:00 2001 From: "Henry H. Andrews" Date: Wed, 19 Jun 2024 16:39:45 -0700 Subject: [PATCH 2/7] Add section titles, fix levels (3.1.1 port of 3923 2/6) Make the Parameter, Encoding, and Header Object fixed fields section organization the same in all three places, with the same levels of indentation. Add more headings under the Encoding Object for guidance on each form media type, and sub-headings for each example in each of those sections. This will make the diff for the next commit much more legible. --- versions/3.1.1.md | 26 ++++++++++++++++++++------ 1 file changed, 20 insertions(+), 6 deletions(-) diff --git a/versions/3.1.1.md b/versions/3.1.1.md index a16418c5b6..624e69962a 100644 --- a/versions/3.1.1.md +++ b/versions/3.1.1.md @@ -1673,6 +1673,8 @@ In both cases, their order is implementation-defined. See [Appendix E](#percentEncodingAndFormMediaTypes) for a detailed examination of percent-encoding concerns for form media types. +##### Fixed Fields + ###### Common Fixed Fields These fields MAY be used either with or without the RFC6570-style serialization fields defined in the next section below. @@ -1699,7 +1701,7 @@ Determining how to handle a `type` value of `null` depends on how `null` values If `null` values are entirely omitted, then the `contentType` is irrelevant. See [Appendix B](#dataTypeConversion) for a discussion of data type conversion options. -##### Fixed Fields for RFC6570-style Serialization +###### Fixed Fields for RFC6570-style Serialization Field Name | Type | Description ---|:---:|--- @@ -1712,11 +1714,15 @@ See also [Appendix C: Using RFC6570 Implementations](#usingRFC6570Implementation Note that the presence of at least one of `style`, `explode`, or `allowReserved` with an explicit value is equivalent to using `schema` with `in: query` Parameter Objects. The absence of all three of those fields is the equivalent of using `content`, but with the media type specified in `contentType` rather than through a Media Type Object. +##### Encoding the `x-www-form-urlencoded` Media Type + See [Appendix E](#percentEncodingAndFormMediaTypes) for a detailed examination of percent-encoding concerns for form media types. To submit content using form url encoding via [RFC1866](https://tools.ietf.org/html/rfc1866), the following definition may be used: +###### Example: URL Encoded Form with JSON Values + ```yaml requestBody: content: @@ -1763,6 +1769,8 @@ Here is the `id` parameter (without `address`) serialized as `application/json` id=%22f81d4fae-7dec-11d0-a765-00a0c91e6bf6%22 ``` +###### Example: URL Encoded Form with Binary Values + `application/x-www-form-urlencoded` is a text format, which requires base64-encoding any binary data: ```YAML @@ -1784,7 +1792,7 @@ requestBody: contentType: image/png, image/jpeg ``` -###### Encoding `multipart` Media Types +##### Encoding `multipart` Media Types It is common to use `multipart/form-data` as a `Content-Type` when transferring request bodies to operations. In contrast to 2.0, a `schema` is REQUIRED to define the input parameters to the operation when using `multipart` content. This supports complex structures as well as supporting mechanisms for multiple file uploads. @@ -1815,7 +1823,7 @@ If `contentEncoding` is used along with setting a different `Content-Transfer-En See [Appendix E](#percentEncodingAndFormMediaTypes) for a detailed examination of percent-encoding concerns for form media types. -##### Encoding Object Example +###### Example: Basic Multipart Form Examples: @@ -1854,6 +1862,8 @@ requestBody: $ref: '#/components/schemas/Address' ``` +###### Example: Multipart Form with Encoding Objects + `multipart/form-data` allows for binary parts: ```yaml @@ -1891,6 +1901,8 @@ requestBody: type: integer ``` +###### Example: Multipart Form with Multiple Files + To upload multiple files, a `multipart` media type MUST be used: ```yaml @@ -2566,7 +2578,9 @@ The Header Object follows the structure of the [Parameter Object](#parameterObje 1. `in` MUST NOT be specified, it is implicitly in `header`. 1. All traits that are affected by the location MUST be applicable to a location of `header` (for example, [`style`](#parameterStyle)). This means that `allowEmptyValue` and `allowReserved` MUST NOT be used, and `style`, if used, MUST be limited to `simple`. -##### Common Fixed Fields +##### Fixed Fields + +###### Common Fixed Fields These fields MAY be used with either `content` or `schema`. @@ -2578,7 +2592,7 @@ Field Name | Type | Description This object MAY be extended with [Specification Extensions](#specificationExtensions). -##### Fixed Fields for use with `schema` +###### Fixed Fields for use with `schema` For simpler scenarios, a [`schema`](#headerSchema) and [`style`](#headerStyle) can describe the structure and syntax of the header. When `example` or `examples` are provided in conjunction with the `schema` object, the example MUST follow the prescribed serialization strategy for the header. @@ -2598,7 +2612,7 @@ Field Name | Type | Description See also [Appendix C: Using RFC6570 Implementations](#usingRFC6570Implementations) for additional guidance. -##### Fixed Fields for use with `content` +###### Fixed Fields for use with `content` For more complex scenarios, the [`content`](#headerContent) property can define the media type and schema of the header, as well as give examples of its use. Using `content` with a `text/plain` media type is RECOMMENDED for headers where the `schema` strategy is not appropriate. From 1371a9310226475daf7186c85c2a039b75bef3bb Mon Sep 17 00:00:00 2001 From: "Henry H. Andrews" Date: Wed, 19 Jun 2024 16:46:41 -0700 Subject: [PATCH 3/7] Consolidating form guidance: Media Type Object (3.1.1 port of 3923 3/6) This puts the useful part of the "An encoding attribute..." text into the fixed fields table, and removes the duplication. It also links the remaining stub or truncated sections to the information's new location under the Encoding Object. --- versions/3.1.1.md | 12 +++++++----- 1 file changed, 7 insertions(+), 5 deletions(-) diff --git a/versions/3.1.1.md b/versions/3.1.1.md index 624e69962a..475137eda8 100644 --- a/versions/3.1.1.md +++ b/versions/3.1.1.md @@ -1543,15 +1543,13 @@ See [Working With Examples](#working-with-examples) for further guidance regardi ##### Fixed Fields Field Name | Type | Description ---|:---:|--- -schema | [Schema Object](#schemaObject) | The schema defining the content of the request, response, or parameter. +schema | [Schema Object](#schemaObject) | The schema defining the content of the request, response, parameter, or header. example | Any | Example of the media type; see [Working With Examples](#working-with-examples). examples | Map[ `string`, [Example Object](#exampleObject) \| [Reference Object](#referenceObject)] | Examples of the media type; see [Working With Examples](#working-with-examples). -encoding | Map[`string`, [Encoding Object](#encodingObject)] | A map between a property name and its encoding information. The key, being the property name, MUST exist in the schema as a property. The encoding attribute SHALL only apply to [Request Body Objects](#requestBodyObject), and only when the media type is `multipart` or `application/x-www-form-urlencoded`. If no Encoding Object is provided for a property, the behavior is determined by the default values documented for the Encoding Object. +encoding | Map[`string`, [Encoding Object](#encodingObject)] | A map between a property name and information providing more control over the serialization of the value. The key, being the property name, MUST exist in the schema as a property. The encoding attribute SHALL only apply to [Request Body Objects](#requestBodyObject), and only when the media type is `multipart` or `application/x-www-form-urlencoded`. If no Encoding Object is provided for a property, the behavior is determined by the default values documented for the Encoding Object. This object MAY be extended with [Specification Extensions](#specificationExtensions). -An `encoding` attribute is introduced to give you control over the serialization of parts of `multipart` request bodies. This attribute is _only_ applicable to request bodies, and _only_ for `multipart` and `application/x-www-form-urlencoded` media types. - ##### Media Type Examples ```json @@ -1657,12 +1655,16 @@ requestBody: image/png: {} ``` -To upload multiple files, a `multipart` media type MUST be used: +To upload multiple files, a `multipart` media type MUST be used as shown under [Example: Multipart Form with Multiple Files](#example-multipart-form-with-multiple-files). ##### Support for x-www-form-urlencoded Request Bodies +See [Encoding the `x-www-form-urlencoded` Media Type](#encoding-the-x-www-form-urlencoded-media-type) for guidance and examples, both with and without the `encoding` attribute. + ##### Special Considerations for `multipart` Content +See [Encoding `multipart` Media Types](#encoding-multipart-media-types) for further guidance and examples, both with and without the `encoding` attribute. + #### Encoding Object A single encoding definition applied to a single schema property. From 4c988a2aaa0a0e8f82804facd4f4465346ec7304 Mon Sep 17 00:00:00 2001 From: "Henry H. Andrews" Date: Wed, 19 Jun 2024 17:24:52 -0700 Subject: [PATCH 4/7] Re-organize form-urlencoded guidance (3.1.1 port of 3923 4/6) This re-organizes and streamlines the form-urlencoded guidance that was consolidated from the Media Type Object. It also adds an example of a base64-encoded URL query parameter. --- versions/3.1.1.md | 27 ++++++++++++++++----------- 1 file changed, 16 insertions(+), 11 deletions(-) diff --git a/versions/3.1.1.md b/versions/3.1.1.md index 475137eda8..11c929fc90 100644 --- a/versions/3.1.1.md +++ b/versions/3.1.1.md @@ -1718,13 +1718,15 @@ The absence of all three of those fields is the equivalent of using `content`, b ##### Encoding the `x-www-form-urlencoded` Media Type -See [Appendix E](#percentEncodingAndFormMediaTypes) for a detailed examination of percent-encoding concerns for form media types. +To submit content using form url encoding via [RFC1866](https://tools.ietf.org/html/rfc1866), use the `application/x-www-form-urlencoded` media type in the [Media Type Object](#mediaTypeObject) under the [Request Body Object](#requestBodyObject). +This configuration means that the request body MUST be encoded per [RFC1866](https://tools.ietf.org/html/rfc1866) when passed to the server, after any complex objects have been serialized to a string representation. -To submit content using form url encoding via [RFC1866](https://tools.ietf.org/html/rfc1866), the following -definition may be used: +See [Appendix E](#percentEncodingAndFormMediaTypes) for a detailed examination of percent-encoding concerns for form media types. ###### Example: URL Encoded Form with JSON Values +When there is no [`encoding` field](#mediaTypeEncoding), the serialization strategy is based on the Encoding Object's default values: + ```yaml requestBody: content: @@ -1741,11 +1743,7 @@ requestBody: properties: {} ``` -In this example, the contents in the `requestBody` MUST be encoded per [RFC1866](https://tools.ietf.org/html/rfc1866) when passed to the server. In addition, the `address` field complex object will be serialized to a string representation prior to encoding. - -When passing complex objects in the `application/x-www-form-urlencoded` content type, the default serialization strategy of such properties is described in the [Encoding Object](#encodingObject)'s [`style`](#encodingStyle) property as `form`. - -With this example, given an `id` of `f81d4fae-7dec-11d0-a765-00a0c91e6bf6` and a US-style address (with ZIP+4) as follows: +With this example, consider an `id` of `f81d4fae-7dec-11d0-a765-00a0c91e6bf6` and a US-style address (with ZIP+4) as follows: ```json { @@ -1773,7 +1771,7 @@ id=%22f81d4fae-7dec-11d0-a765-00a0c91e6bf6%22 ###### Example: URL Encoded Form with Binary Values -`application/x-www-form-urlencoded` is a text format, which requires base64-encoding any binary data: +Note that `application/x-www-form-urlencoded` is a text format, which requires base64-encoding any binary data: ```YAML requestBody: @@ -1785,8 +1783,8 @@ requestBody: name: type: string icon: - # default for type string is text/plain, need to declare - # the appropriate contentType in the Encoding Object + # The default with "contentEncoding" is application/octet-stream, + # so we need to set image media type(s) in the Encoding Object. type: string contentEncoding: base64url encoding: @@ -1794,6 +1792,13 @@ requestBody: contentType: image/png, image/jpeg ``` +Given a name of `example` and a solid red 2x2-pixel PNG for `icon`, this +would produce a request body of: + +```urlencoded +name=example&icon=iVBORw0KGgoAAAANSUhEUgAAAAIAAAACCAYAAABytg0kAAAAEklEQVQIW2P8z8AARAwMjDAGACwBA/+8RVWvAAAAAElFTk +``` + ##### Encoding `multipart` Media Types It is common to use `multipart/form-data` as a `Content-Type` when transferring request bodies to operations. In contrast to 2.0, a `schema` is REQUIRED to define the input parameters to the operation when using `multipart` content. This supports complex structures as well as supporting mechanisms for multiple file uploads. From f6c2164c9a9d3cb6fba908f51ce69c68a26ba858 Mon Sep 17 00:00:00 2001 From: "Henry H. Andrews" Date: Thu, 20 Jun 2024 12:31:07 -0700 Subject: [PATCH 5/7] Fix base64 encoding example for URL quoting (3.1.1 port of 2923 5/6) I forgot to run the example through URL quoting, which is necessary. --- versions/3.1.1.md | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/versions/3.1.1.md b/versions/3.1.1.md index 11c929fc90..8dabe8e941 100644 --- a/versions/3.1.1.md +++ b/versions/3.1.1.md @@ -1796,9 +1796,13 @@ Given a name of `example` and a solid red 2x2-pixel PNG for `icon`, this would produce a request body of: ```urlencoded -name=example&icon=iVBORw0KGgoAAAANSUhEUgAAAAIAAAACCAYAAABytg0kAAAAEklEQVQIW2P8z8AARAwMjDAGACwBA/+8RVWvAAAAAElFTk +name=example&icon=iVBORw0KGgoAAAANSUhEUgAAAAIAAAACCAIAAAD91JpzAAAABGdBTUEAALGPC_xhBQAAADhlWElmTU0AKgAAAAgAAYdpAAQAAAABAAAAGgAAAAAAAqACAAQAAAABAAAAAqADAAQAAAABAAAAAgAAAADO0J6QAAAAEElEQVQIHWP8zwACTGCSAQANHQEDqtPptQAAAABJRU5ErkJggg%3D%3D ``` +Note that the `=` padding characters at the end need to be percent-encoded, even with the "URL safe" `contentEncoding: base64url`. +Some base64-decoding implementations may be able to use the string without the padding per [RFC4648 §3.2](https://datatracker.ietf.org/doc/html/rfc4648#section-3.2). +However, this is not guaranteed, so it may be more interoperable to keep the padding and rely on percent-decoding. + ##### Encoding `multipart` Media Types It is common to use `multipart/form-data` as a `Content-Type` when transferring request bodies to operations. In contrast to 2.0, a `schema` is REQUIRED to define the input parameters to the operation when using `multipart` content. This supports complex structures as well as supporting mechanisms for multiple file uploads. From f913074938402faf768ae741cf1325af57dc4c8a Mon Sep 17 00:00:00 2001 From: "Henry H. Andrews" Date: Wed, 19 Jun 2024 17:25:44 -0700 Subject: [PATCH 6/7] Reorganize multipart/form-data guidance (3.1.1 port of 3923 6/6, 3929) This organizes and streamlines the guidance on multipart that was incorporated from the Media Type Object. Lots of duplication has been removed, and the examples reworked to show distinct use cases. --- versions/3.1.1.md | 81 ++++++++++++++++++++--------------------------- 1 file changed, 34 insertions(+), 47 deletions(-) diff --git a/versions/3.1.1.md b/versions/3.1.1.md index 8dabe8e941..19db812edb 100644 --- a/versions/3.1.1.md +++ b/versions/3.1.1.md @@ -1805,19 +1805,7 @@ However, this is not guaranteed, so it may be more interoperable to keep the pad ##### Encoding `multipart` Media Types -It is common to use `multipart/form-data` as a `Content-Type` when transferring request bodies to operations. In contrast to 2.0, a `schema` is REQUIRED to define the input parameters to the operation when using `multipart` content. This supports complex structures as well as supporting mechanisms for multiple file uploads. - -In a `multipart/form-data` request body, each schema property, or each element of a schema array property, takes a section in the payload with an internal header as defined by [RFC7578](https://tools.ietf.org/html/rfc7578). The serialization strategy for each property of a `multipart/form-data` request body can be specified in an associated [`Encoding Object`](#encodingObject). - -When passing in `multipart` types, boundaries MAY be used to separate sections of the content being transferred – thus, the following default `Content-Type`s are defined for `multipart`: - -* If the property is a primitive, or an array of primitive values, the default Content-Type is `text/plain` -* If the property is complex, or an array of complex values, the default Content-Type is `application/json` -* If the property is a `type: string` with a `contentEncoding`, the default Content-Type is `application/octet-stream` - -Per the JSON Schema specification, `contentMediaType` without `contentEncoding` present is treated as if `contentEncoding: identity` were present. While useful for embedding text documents such as `text/html` into JSON strings, it is not useful for a `multipart/form-data` part, as it just causes the document to be treated as `text/plain` instead of its actual media type. Use the Encoding Object without `contentMediaType` if no `contentEncoding` is required. - -Note that only `multipart/*` media types with named parts can be described as shown here. Note also that while `multipart/form-data` originally defined a per-part `Content-Transfer-Encoding` header that could indicate base64 encoding (`contentEncoding: base64`), it has been deprecated for use with HTTP as of [RFC7578](https://www.rfc-editor.org/rfc/rfc7578#section-4.7). +It is common to use `multipart/form-data` as a `Content-Type` when transferring forms as request bodies. In contrast to 2.0, a `schema` is REQUIRED to define the input parameters to the operation when using `multipart` content. This supports complex structures as well as supporting mechanisms for multiple file uploads. The `form-data` disposition and its `name` parameter are mandatory for `multipart/form-data` ([RFC7578 §4.2](https://www.rfc-editor.org/rfc/rfc7578.html#section-4.2)). Array properties are handled by applying the same `name` to multiple parts, as is recommended by [RFC7578 §4.3](https://www.rfc-editor.org/rfc/rfc7578.html#section-4.3) for supplying multiple values per form field. @@ -1829,14 +1817,18 @@ It is not currently possible to correlate schema properties with unnamed, ordere Note that there are significant restrictions on what headers can be used with `multipart` media types in general ([RFC2046 §5.1](https://www.rfc-editor.org/rfc/rfc2046.html#section-5.1)) and `multi-part/form-data` in particular ([RFC7578 §4.8](https://www.rfc-editor.org/rfc/rfc7578.html#section-4.8)). Note also that `Content-Transfer-Encoding` is deprecated for `multipart/form-data` ([RFC7578 §4.7](https://www.rfc-editor.org/rfc/rfc7578.html#section-4.7)) where binary data is supported, as it is in HTTP. -Using `contentEncoding` is equivalent to setting `Content-Transfer-Encoding` to the same value. -If `contentEncoding` is used along with setting a different `Content-Transfer-Encoding` value with the `headers` field, the result is undefined. + ++Using `contentEncoding` for a multipart field is equivalent to specifying an [Encoding Object](#encodingObject) with a `headers` field containing `Content-Transfer-Encoding` with a schema that requires the value used in `contentEncoding`. ++If `contentEncoding` is used for a multipart field that has an Encoding Object with a `headers` field containing `Content-Transfer-Encoding` with a schema that disallows the value from `contentEncoding`, the result is undefined for serialization and parsing. + +Note that as stated in [Working with Binary Data](#binaryData), if the Encoding Object's `contentType`, whether set explicitly or implicitly through its default value rules, disagrees with the `contentMediaType` in a Schema Object, the `contentMediaType` SHALL be ignored. +Because of this, and because the Encoding Object's `contentType` defaulting rules do not take the Schema Object's` contentMediaType` into account, the use of `contentMediaType` with an Encoding Object is NOT RECOMMENDED. See [Appendix E](#percentEncodingAndFormMediaTypes) for a detailed examination of percent-encoding concerns for form media types. ###### Example: Basic Multipart Form -Examples: +When the `encoding` attribute is _not_ used, the encoding is determined by the Encoding Object's defaults: ```yaml requestBody: @@ -1846,27 +1838,16 @@ requestBody: type: object properties: id: + # default for primitives without a special format is text/plain type: string format: uuid - address: - # default Content-Type for objects is `application/json` - type: object - properties: {} profileImage: - # default Content-Type for properties with type string and a contentEncoding - # is `application/octet-stream`, so `image/png` must be set using contentMediaType + # default for string with binary format is `application/octet-stream` type: string - contentMediaType: image/png - contentEncoding: base64 - children: - # default Content-Type for arrays is based on the items subschema type, which - # is a string, producing a default of `text/plain` - type: array - items: - type: string + format: binary addresses: - # default Content-Type for arrays is based on the items subschema type, which - # is an object, producing a default of `application/json` + # default for arrays is based on the type in the `items` + # subschema, which is an object, so `application/json` type: array items: type: object @@ -1875,7 +1856,8 @@ requestBody: ###### Example: Multipart Form with Encoding Objects -`multipart/form-data` allows for binary parts: +Using `encoding`, we can set more specific types for binary data, or non-JSON formats for complex values. +We can also describe headers for each part: ```yaml requestBody: @@ -1885,25 +1867,30 @@ requestBody: type: object properties: id: - # default is text/plain + # default is `text/plain` type: string format: uuid - address: - # default is application/json - type: object - properties: {} - historyMetadata: - # need to declare XML format! - description: metadata in XML format - type: object - properties: {} - profileImage: {} + addresses: + # default based on the `items` subschema would be + # `application/json`, but we want these address objects + # serialized as `application/xml` instead + description: addresses in XML format + type: array + items: + $ref: '#/components/schemas/Address' + profileImage: + # default is application/octet-stream, but we can declare + # a more specific image type or types + type: string + format: binary encoding: - historyMetadata: + addresses: # require XML Content-Type in utf-8 encoding + # This is applied to each address part corresponding + # to each address in he array contentType: application/xml; charset=utf-8 profileImage: - # only accept png/jpeg + # only accept png or jpeg contentType: image/png, image/jpeg headers: X-Rate-Limit-Limit: @@ -1914,7 +1901,7 @@ requestBody: ###### Example: Multipart Form with Multiple Files -To upload multiple files, a `multipart` media type MUST be used: +In accordance with [RFC7578 §4.3](https://www.rfc-editor.org/rfc/rfc7578.html#section-4.3), multiple files for a single form field are uploaded using the same name (`file` in this example) for each file's part: ```yaml requestBody: From 75abe34f52d00f4732d68e4c847a5bf09d827a08 Mon Sep 17 00:00:00 2001 From: "Henry H. Andrews" Date: Tue, 9 Jul 2024 15:05:10 -0700 Subject: [PATCH 7/7] Review feedback clarifications- binary encoding --- versions/3.1.1.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/versions/3.1.1.md b/versions/3.1.1.md index 19db812edb..1d20a42596 100644 --- a/versions/3.1.1.md +++ b/versions/3.1.1.md @@ -1692,7 +1692,7 @@ The default values for `contentType` are as follows, where an _n/a_ in the `cont Property `type` | Property `contentEncoding` | Default `contentType` --------------- | -------------------------- | --------------------- -_absent_ | _n/a_ | `application/octet-stream` +[_absent_](#binaryData) | _n/a_ | `application/octet-stream` `string` | _present_ | `application/octet-stream` `string` | _absent_ | `text/plain` `number`, `integer`, or `boolean` | _n/a_ | `text/plain` @@ -1915,7 +1915,7 @@ requestBody: items: {} ``` -As seen in the section on `multipart/form-data` below, the empty schema for `items` indicates a media type of `application/octet-stream`. +As seen in the [Encoding Object's `contentType` field documentation](#encodingContentType), the empty schema for `items` indicates a media type of `application/octet-stream`. #### Responses Object