Skip to content

Commit 6869ddd

Browse files
committed
Add data vs serialized example fields
This adds two fields to the Example Object and partially deprecates the existing `value` field. `dataValue` applies to the data that would be passed to schema validation. `serializedValue` (which MUST be a string), like `externalValue`, applies to the serialized form. Guidance is provided that `value` (and the shorthand singluar `example`) are safe for JSON serialization targets and for strings serialized to targets that do not apply further escaping, but are otherwise deprecated due to ambiguous behavior.
1 parent 2c7432c commit 6869ddd

File tree

7 files changed

+116
-17
lines changed

7 files changed

+116
-17
lines changed

src/oas.md

Lines changed: 54 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -2101,42 +2101,84 @@ transactionCallback:
21012101
#### Example Object
21022102

21032103
An object grouping an internal or external example value with basic `summary` and `description` metadata.
2104+
The examples can show either data suitable for schema validation, or serialized data as required by the containing [Media Type Object](#media-type-object), [Parameter Object](#parameter-object), or [Header Object](#header-object).
21042105
This object is typically used in fields named `examples` (plural), and is a [referenceable](#reference-object) alternative to older `example` (singular) fields that do not support referencing or metadata.
2105-
2106-
Examples allow demonstration of the usage of properties, parameters and objects within OpenAPI.
2106+
The various fields and types of examples are explained in more detail under [Working With Examples](#working-with-examples).
21072107

21082108
##### Fixed Fields
21092109

21102110
| Field Name | Type | Description |
21112111
| ---- | :----: | ---- |
21122112
| <a name="example-summary"></a>summary | `string` | Short description for the example. |
21132113
| <a name="example-description"></a>description | `string` | Long description for the example. [CommonMark syntax](https://spec.commonmark.org/) MAY be used for rich text representation. |
2114-
| <a name="example-value"></a>value | Any | Embedded literal example. The `value` field and `externalValue` field are mutually exclusive. To represent examples of media types that cannot naturally represented in JSON or YAML, use a string value to contain the example, escaping where necessary. |
2115-
| <a name="example-external-value"></a>externalValue | `string` | A URI that identifies the literal example. This provides the capability to reference examples that cannot easily be included in JSON or YAML documents. The `value` field and `externalValue` field are mutually exclusive. See the rules for resolving [Relative References](#relative-references-in-api-description-uris). |
2114+
| <a name="example-data-value"></a>dataValue | Any | An example of the data structure that MUST be valid according to the relevant [Schema Object](#schema-object). If this field is present, `value` MUST be absent. |
2115+
| <a name="example-serialized-value"></a>serializedValue | `string` | An example of the serialized form of the value, including encoding and escaping as described under [Validating Examples](#validating-examples). If `dataValue` is present, then this field SHOULD contain the serialization of the given data. Otherwise, it SHOULD be the valid serialization of a data value that itself MUST be valid as described for `dataValue`. This field SHOULD NOT be used if the serialization format is JSON, as the data form is easier to work with. If this field is present, `value`, and `externalValue` MUST be absent. |
2116+
| <a name="example-external-value"></a>externalValue | `string` | A URI that identifies the serialized example in a separate document, allowing for values not easily or readably expressed as a Unicode string. If `dataValue` is present, then this field SHOULD identify a serialization of the given data. Otherwise, the value SHOULD the valid serialization of a data value that itself MUST be valid as described for `dataValue`. If this field is present, `serializedValue`, and `value` MUST be absent. See also the rules for resolving [Relative References](#relative-references-in-api-description-uris). |
2117+
| <a name="example-value"></a>value | Any | Embedded literal example. The `value` field and `externalValue` field are mutually exclusive. To represent examples of media types that cannot naturally be represented in JSON or YAML, use a string value to contain the example, escaping where necessary.<br /><br>**Deprecated for non-JSON serialization targets:** Use `dataValue` and/or `serializedValue`, which both have unambiguous syntax and semantics, instead. |
21162118

21172119
This object MAY be extended with [Specification Extensions](#specification-extensions).
21182120

21192121
In all cases, the example value SHOULD be compatible with the schema of its associated value.
21202122
Tooling implementations MAY choose to validate compatibility automatically, and reject the example value(s) if incompatible.
2123+
See [Validating Examples](#validating-examples) for the exact meaning of "compatible" for each field in this Object.
21212124

21222125
##### Working with Examples
21232126

21242127
Example Objects can be used in [Parameter Objects](#parameter-object), [Header Objects](#header-object), and [Media Type Objects](#media-type-object).
21252128
In all three Objects, this is done through the `examples` (plural) field.
21262129
However, there are several other ways to provide examples: The `example` (singular) field that is mutually exclusive with `examples` in all three Objects, and two keywords (the deprecated singular `example` and the current plural `examples`, which takes an array of examples) in the [Schema Object](#schema-object) that appears in the `schema` field of all three Objects.
2130+
We will refer to the singular `example` field in the Parameter, Header, or Media Type Object, which has the same behavior as a single Example Object with only the `value` field, as the "shorthand `example`" field.
21272131
Each of these fields has slightly different considerations.
21282132

2129-
The Schema Object's fields are used to show example values without regard to how they might be formatted as parameters or within media type representations.
2130-
The `examples` array is part of JSON Schema and is the preferred way to include examples in the Schema Object, while `example` is retained purely for compatibility with older versions of the OpenAPI Specification.
2133+
###### JSON-Compatible and `value`-Safe Examples
2134+
2135+
The `value` and the shorthand `example` field are intended to have the same _semantics_ as `serializedValue` (or `externalValue`), while allowing a more convenient _syntax_ when there is no difference between a JSON (or [JSON-compatible YAML](#format)) representation and the final serialized form.
2136+
When using this syntax for `application/json` or any `+json` media type, these fields effectively behave like `dataValue`, as the serialization is trivial, and they are safe to use.
2137+
2138+
For data that consists of a single string, and a serialization target such as `text/plain` where the string is guaranteed to be serialized without any further escaping, these fields are also safe to use.
2139+
2140+
For other serialization targets, the ambiguity of the phrase "naturally be represented in JSON or YAML," as well as past errors in the parameter style examples table, have resulted in inconsistencies in the support and usage of these fields.
2141+
In practice, this has resulted in the `value` and shorthand `example` fields having implementation-defined behavior for non-JSON targets; OAD authors SHOULD use other fields to ensure interoperability.
2142+
2143+
###### Choosing Which Field(s) to Use
2144+
2145+
Keeping in mind the caveats from the previous section, and that the shorthand `example` can be used in place of `value` if there is only one Example Object involved, use the following guidelines to determine which field to use.
2146+
2147+
To show an example as it would be validated by a Schema Object:
2148+
2149+
* Use the Schema Object's `examples` array (from JSON Schema draft 2020-12) if the intent is to keep the example with the validating schema.
2150+
* Use the Schema Object's `example` (singular) only if compatibility with OAS v3.0 or earlier is required.
2151+
* Use the Example Object's `dataValue` field if the intent is to associate the example with an example of its serialization, or if it is desirable to maintain it separately from the schema.
2152+
* Use the Example Object's `value` field only if compatibility with OAS v3.1 or earlier is needed and the value can be "naturally represented in JSON or YAML" without any changes (such as percent-encoding) between the validation-ready value and the serialized representation.
21312153

2132-
The mutually exclusive fields in the Parameter, Header, or Media Type Objects are used to show example values which SHOULD both match the schema and be formatted as they would appear as a serialized parameter, serialized header, or within a media type representation.
2133-
The exact serialization and encoding is determined by various fields in the Parameter Object, Header Object, or in the Media Type Object's [Encoding Object](#encoding-object).
2154+
To show an example as it would be serialized in order to construct an HTTP/1.1 message:
21342155

2135-
The singular `example` field in the Parameter, Header, or Media Type Object is concise and convenient for simple examples, but does not offer any other advantages over using Example Objects under `examples`.
2156+
* Use the Example Object's `serializedValue` if the serialization can be represented as a valid Unicode string, and there is no need to demonstrate the exact character encoding to be used.
2157+
* Use the string form of `value` only if compatibility with OAS v3.1 or earlier is needed.
2158+
* Use the Example Object's `externalValue` for all other values, or if it is desirable to maintain the example separately from the OpenAPI document.
2159+
2160+
The `serializedValue` and `externalValue` fields both MUST show the serialized form of the data.
2161+
For Media Type Objects, this is a document of the appropriate media type, with any Encoding Object effects applied.
2162+
For Parameter and Header Objects using `schema` and `style` rather than a Media Type Object, see [Style Examples](#style-examples) for what constitutes a serialized value.
2163+
2164+
###### Criteria for `serializedExample`
2165+
2166+
A serialization can be represented as a valid Unicode string in `serializedValue` if any of the following are true of the serialization:
2167+
2168+
* It is for a media type that supports a `charset` parameter that indicates a Unicode encoding such as UTF-8, or any valid subset of such an encoding, such as US-ASCII.
2169+
* It is for a format (such as URIs or HTTP fields) or character-based media type that requires or defaults to a Unicode encoding such as UTF-8, or any valid subset of such an encoding, such as US-ASCII, and this is not overridden by `charset`.
2170+
* It is for a compound format where all parts meet at least one of the above criteria, e.g. a `multipart/mixed` media type with parts that are `application/json` (a media type that defaults to UTF-8) and `application/xml; charset=utf-8` (a media type with an explicit `charset` parameter).
2171+
2172+
For `externalValue`, if the character set is neither explicitly stated nor determined by the format or media type specification, implementations SHOULD assume UTF-8.
2173+
2174+
###### Validating Examples
2175+
2176+
Tooling implementations MAY choose to validate compatibility automatically, and reject the example value(s) if incompatible.
2177+
For examples that are in schema-ready data form, this is straightforward.
21362178

2137-
Some examples cannot be represented directly in JSON or YAML.
2138-
For all three ways of providing examples, these can be shown as string values with any escaping necessary to make the string valid in the JSON or YAML format of documents that comprise the OpenAPI Description.
2139-
With the Example Object, such values can alternatively be handled through the `externalValue` field.
2179+
With serialized examples, some formats allow multiple possible valid representations of the same data, including in scenarios noted in [Appendix B](#appendix-b-data-type-conversion).
2180+
In some cases, parsing the serialized example and validating the resulting data can eliminate the ambiguity, but in a few cases parsing is also ambiguous.
2181+
Therefore, OAD authors are cautioned that validation of certain serialized examples is by necessity a best-effort feature.
21402182

21412183
##### Example Object Examples
21422184

src/schemas/validation/schema.yaml

Lines changed: 20 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -641,14 +641,30 @@ $defs:
641641
type: string
642642
description:
643643
type: string
644+
dataValue: true
645+
serializedValue:
646+
type: string
644647
value: true
645648
externalValue:
646649
type: string
647650
format: uri-reference
648-
not:
649-
required:
650-
- value
651-
- externalValue
651+
allOf:
652+
- not:
653+
required:
654+
- value
655+
- externalValue
656+
- not:
657+
required:
658+
- value
659+
- dataValue
660+
- not:
661+
required:
662+
- value
663+
- serializedValue
664+
- not:
665+
required:
666+
- serializedValue
667+
- externalValue
652668
$ref: '#/$defs/specification-extensions'
653669
unevaluatedProperties: false
654670

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
openapi: 3.2.0
2+
info:
3+
title: API
4+
version: 1.0.0
5+
6+
components:
7+
examples:
8+
CannotHaveBoth:
9+
value: foo
10+
externalValue: https://example.com/foo
Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
openapi: 3.2.0
2+
info:
3+
title: API
4+
version: 1.0.0
5+
6+
components:
7+
examples:
8+
NoValueWithDataValue:
9+
value: foo
10+
dataValue: foo
Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
openapi: 3.2.0
2+
info:
3+
title: API
4+
version: 1.0.0
5+
6+
components:
7+
examples:
8+
CannotHaveBoth:
9+
value: foo
10+
serializedValue: foo
Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
openapi: 3.2.0
2+
info:
3+
title: API
4+
version: 1.0.0
5+
6+
components:
7+
examples:
8+
CannotHaveBoth:
9+
serializedValue: foo
10+
externalValue: https://example.com/foo

tests/schema/pass/example-object-examples.yaml

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -60,4 +60,5 @@ components:
6060
examples:
6161
jsonFormValue:
6262
description: 'The JSON string "json" as a form value'
63-
value: jsonValue=%22json%22
63+
dataValue: json
64+
serializedValue: jsonValue=%22json%22

0 commit comments

Comments
 (0)