From bdbabd45f83125513fd4b3e5105886ee0e3b38b5 Mon Sep 17 00:00:00 2001 From: "Henry H. Andrews" Date: Thu, 2 May 2024 11:34:58 -0700 Subject: [PATCH 01/10] Clarify resolving implicit connections (3.0.4) This clarifies how to handle resolving implicit (non-URI-based) connections in multi-document OpenAPI Descriptions. While the behavior is implementation-defined overall, this RECOMMENDS a single approach based on how things behaved going back to the 2.0 referencing model. This allows Security Schemes and Tags to (like the top-level Server Objects) define a deployment-specific interface for referenced documents to access. This entry document interface approach makes less sense for the Discriminator Object, but it can use the URI syntax of `mapping` to keep things within the local document. This also aligns the search for matching `operationId`s with 3.1's full-document parsing requirements. Note that the term "complete OpenAPI document" has been defined in another change pending approval on the 3.0.4 branch. --- versions/3.0.4.md | 34 +++++++++++++++++++++++++++++++++- 1 file changed, 33 insertions(+), 1 deletion(-) diff --git a/versions/3.0.4.md b/versions/3.0.4.md index 8dda05e8ba..5a8e44aba3 100644 --- a/versions/3.0.4.md +++ b/versions/3.0.4.md @@ -166,7 +166,7 @@ It is RECOMMENDED that the entry OpenAPI document be named: `openapi.json` or `o When parsing an OAD, JSON or YAML objects are parsed into specific Objects (such as [Operation Objects](#operationObject), [Response Objects](#responseObject), [Reference Objects](#referenceObject), etc.) based on the parsing context. Depending on how references are arranged, a given JSON or YAML object can be parsed in multiple different contexts: -* As a full OpenAPI Description document (an [OpenAPI Object](#oasObject) taking up an entire document) +* As a complete OpenAPI Description document * As the Object type implied by its parent Object within the document * As a reference target, with the Object type matching the reference source's context @@ -174,6 +174,38 @@ If the same JSON/YAML object is parsed multiple times and the respective context #### Resolving Implicit Connections +Several features of this specification require resolving a non-URI-based connection to some other part of the OpenAPI Description (OAD). + +These connections are easily resolved in single-document OADs, but the resolution process in multi-document OADs has never been spelled out, and is therefore _implementation-defined_, within the constraints described in this section. +In some cases, an unambiguous URI-based alternative is available, and OAD authors are RECOMMENDED to always use the alternative: + +Source | Target | Alternative +------ | ------ | ----------- +[Security Requirement Object](#securityRequirementObject) `{name}` | [Security Scheme Object](#securitySchemeObject) name under the [Components Object](#componentsObject) | _n/a_ +[Discriminator Object](#discriminatorObject) `mapping` _(implicit, or explicit name syntax)_ | [Schema Object](#schemaObject) name under the Components Object | `mapping` _(explicit URI syntax)_ +[Operation Object](#operationObject) `tags` | [Tag Object](#tagObject) `name` (in the Components Object) | _n/a_ +[Link Object](#linkObject) `operationId` | [Path Item Object](#pathItemObject) `operationId` | `operationRef` + +A fifth implicit connection, which involves appending the templated URL paths of the [Paths Object](#pathsObject) to the appropriate [Server Object](#serverObject)'s `url` field, is unambiguous because only the entry document's Paths Object contributes URLs to the described API. + +It is RECOMMENDED to consider all Operation Objects from all parsed documents when resolving any Link Object `operationId`. +This requires ensuring that all referenced documents have been parsed prior to determining an `operationId` to be unresolvable. + +The implicit connections in the Security Requirement Object and Discriminator Object rely on the _component name_, which is the property name holding the component in the appropriate typed sub-object of the Components Object. +For example, the component name of the Schema Object at `#/components/schemas/Foo` is `Foo`. +The implicit connection of tags in the Operation Object use the `name` field of Tag Objects, which (like the Components Object) are found under the root OpenAPI Object. +This means that resolving component names and tag names both depend on starting from the correct OpenAPI Object. + +For resolving component and tag name connections from a referenced (non-entry) document, it is RECOMMENDED that tools resolve from the entry document, rather than the current document. +This allows Security Scheme Objects and Tag Objects to be defined with the API's deployment information (the top-level Server Objects), and treated as an interface for referenced documents to access. + +The interface approach can also work for Discriminator Objects and Schema Objects, but it is also possible to keep the Discriminator Object's behavior within a single document using the relative URI-reference syntax of `mapping`. + +There are not currently URI-based alternatives for the Security Requirement Object or for the Operation Object's `tags` field. +These limitations are expected to be addressed in a future release. + +Note that no aspect of implicit connection resolution changes how [URIs are resolved](#relativeReferencesURI), or restricts their possible targets. + ### Data Types Primitive data types in the OAS are based on the types supported by the [JSON Schema Specification Wright Draft 00](https://tools.ietf.org/html/draft-wright-json-schema-00#section-4.2). From 44f08ec4dc50990e0e1dd99c22f9ba4cad0df5be Mon Sep 17 00:00:00 2001 From: Henry Andrews Date: Tue, 28 May 2024 06:58:39 -0700 Subject: [PATCH 02/10] wording review feedback Co-authored-by: Ralf Handl --- versions/3.0.4.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/versions/3.0.4.md b/versions/3.0.4.md index 5a8e44aba3..ba9a24d3c2 100644 --- a/versions/3.0.4.md +++ b/versions/3.0.4.md @@ -201,7 +201,7 @@ This allows Security Scheme Objects and Tag Objects to be defined with the API's The interface approach can also work for Discriminator Objects and Schema Objects, but it is also possible to keep the Discriminator Object's behavior within a single document using the relative URI-reference syntax of `mapping`. -There are not currently URI-based alternatives for the Security Requirement Object or for the Operation Object's `tags` field. +There currently are no URI-based alternatives for the Security Requirement Object or for the Operation Object's `tags` field. These limitations are expected to be addressed in a future release. Note that no aspect of implicit connection resolution changes how [URIs are resolved](#relativeReferencesURI), or restricts their possible targets. From c302993e0597fcf9c601ec1e06eca7e1d9a42d97 Mon Sep 17 00:00:00 2001 From: Henry Andrews Date: Sat, 8 Jun 2024 13:22:08 -0700 Subject: [PATCH 03/10] Apply suggestions from code review Co-authored-by: Jeremy Fiel <32110157+jeremyfiel@users.noreply.github.com> --- versions/3.0.4.md | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/versions/3.0.4.md b/versions/3.0.4.md index ba9a24d3c2..a4c4a7317b 100644 --- a/versions/3.0.4.md +++ b/versions/3.0.4.md @@ -174,7 +174,8 @@ If the same JSON/YAML object is parsed multiple times and the respective context #### Resolving Implicit Connections -Several features of this specification require resolving a non-URI-based connection to some other part of the OpenAPI Description (OAD). +Several features of this specification require resolution of non-URI-based connections to some other part of the OpenAPI Description (OAD). +`` These connections are easily resolved in single-document OADs, but the resolution process in multi-document OADs has never been spelled out, and is therefore _implementation-defined_, within the constraints described in this section. In some cases, an unambiguous URI-based alternative is available, and OAD authors are RECOMMENDED to always use the alternative: @@ -191,10 +192,10 @@ A fifth implicit connection, which involves appending the templated URL paths of It is RECOMMENDED to consider all Operation Objects from all parsed documents when resolving any Link Object `operationId`. This requires ensuring that all referenced documents have been parsed prior to determining an `operationId` to be unresolvable. -The implicit connections in the Security Requirement Object and Discriminator Object rely on the _component name_, which is the property name holding the component in the appropriate typed sub-object of the Components Object. +The implicit connections in the Security Requirement Object and Discriminator Object rely on the _component name_, which is the property name holding the component in the appropriately typed sub-object of the Components Object. For example, the component name of the Schema Object at `#/components/schemas/Foo` is `Foo`. -The implicit connection of tags in the Operation Object use the `name` field of Tag Objects, which (like the Components Object) are found under the root OpenAPI Object. -This means that resolving component names and tag names both depend on starting from the correct OpenAPI Object. +The implicit connection of `tags` in the Operation Object use the `name` field of Tag Objects, which (like the Components Object) are found under the root OpenAPI Object. +This means resolving component names and tag names both depend on starting from the correct OpenAPI Object. For resolving component and tag name connections from a referenced (non-entry) document, it is RECOMMENDED that tools resolve from the entry document, rather than the current document. This allows Security Scheme Objects and Tag Objects to be defined with the API's deployment information (the top-level Server Objects), and treated as an interface for referenced documents to access. From 8de6836374c60090d12a5add8371b3660cc8043a Mon Sep 17 00:00:00 2001 From: "Henry H. Andrews" Date: Sat, 8 Jun 2024 13:27:01 -0700 Subject: [PATCH 04/10] More review feedback. --- versions/3.0.4.md | 11 ++++++----- 1 file changed, 6 insertions(+), 5 deletions(-) diff --git a/versions/3.0.4.md b/versions/3.0.4.md index a4c4a7317b..0bf24f0854 100644 --- a/versions/3.0.4.md +++ b/versions/3.0.4.md @@ -177,7 +177,7 @@ If the same JSON/YAML object is parsed multiple times and the respective context Several features of this specification require resolution of non-URI-based connections to some other part of the OpenAPI Description (OAD). `` -These connections are easily resolved in single-document OADs, but the resolution process in multi-document OADs has never been spelled out, and is therefore _implementation-defined_, within the constraints described in this section. +These connections are unambiguously resolved in single-document OADs, but the resolution process in multi-document OADs is _implementation-defined_, within the constraints described in this section. In some cases, an unambiguous URI-based alternative is available, and OAD authors are RECOMMENDED to always use the alternative: Source | Target | Alternative @@ -187,14 +187,15 @@ Source | Target | Alternative [Operation Object](#operationObject) `tags` | [Tag Object](#tagObject) `name` (in the Components Object) | _n/a_ [Link Object](#linkObject) `operationId` | [Path Item Object](#pathItemObject) `operationId` | `operationRef` -A fifth implicit connection, which involves appending the templated URL paths of the [Paths Object](#pathsObject) to the appropriate [Server Object](#serverObject)'s `url` field, is unambiguous because only the entry document's Paths Object contributes URLs to the described API. +A fifth implicit connection involves appending the templated URL paths of the [Paths Object](#pathsObject) to the appropriate [Server Object](#serverObject)'s `url` field. +This is unambiguous because only the entry document's Paths Object contributes URLs to the described API. It is RECOMMENDED to consider all Operation Objects from all parsed documents when resolving any Link Object `operationId`. -This requires ensuring that all referenced documents have been parsed prior to determining an `operationId` to be unresolvable. +This requires parsing all referenced documents prior to determining an `operationId` to be unresolvable. The implicit connections in the Security Requirement Object and Discriminator Object rely on the _component name_, which is the property name holding the component in the appropriately typed sub-object of the Components Object. For example, the component name of the Schema Object at `#/components/schemas/Foo` is `Foo`. -The implicit connection of `tags` in the Operation Object use the `name` field of Tag Objects, which (like the Components Object) are found under the root OpenAPI Object. +The implicit connection of `tags` in the Operation Object uses the `name` field of Tag Objects, which (like the Components Object) are found under the root OpenAPI Object. This means resolving component names and tag names both depend on starting from the correct OpenAPI Object. For resolving component and tag name connections from a referenced (non-entry) document, it is RECOMMENDED that tools resolve from the entry document, rather than the current document. @@ -202,7 +203,7 @@ This allows Security Scheme Objects and Tag Objects to be defined with the API's The interface approach can also work for Discriminator Objects and Schema Objects, but it is also possible to keep the Discriminator Object's behavior within a single document using the relative URI-reference syntax of `mapping`. -There currently are no URI-based alternatives for the Security Requirement Object or for the Operation Object's `tags` field. +There are no URI-based alternatives for the Security Requirement Object or for the Operation Object's `tags` field. These limitations are expected to be addressed in a future release. Note that no aspect of implicit connection resolution changes how [URIs are resolved](#relativeReferencesURI), or restricts their possible targets. From e11a7cc4dc9991d02994059a922040a66ece71dd Mon Sep 17 00:00:00 2001 From: "Henry H. Andrews" Date: Mon, 10 Jun 2024 17:01:29 -0700 Subject: [PATCH 05/10] Add example resolution of Security Requirement --- versions/3.0.4.md | 38 ++++++++++++++++++++++++++++++++++++++ 1 file changed, 38 insertions(+) diff --git a/versions/3.0.4.md b/versions/3.0.4.md index 0bf24f0854..876ff94100 100644 --- a/versions/3.0.4.md +++ b/versions/3.0.4.md @@ -206,6 +206,9 @@ The interface approach can also work for Discriminator Objects and Schema Object There are no URI-based alternatives for the Security Requirement Object or for the Operation Object's `tags` field. These limitations are expected to be addressed in a future release. +See [Security Requirement in a Referenced Document](#security-requirement-in-a-referenced-document) for an example of the possible resolutions, including which one is recommended by this section. +The behavior for Discrimator Object non-URI mappings and for the Operation Object's `tags` field operate on the same principles. + Note that no aspect of implicit connection resolution changes how [URIs are resolved](#relativeReferencesURI), or restricts their possible targets. ### Data Types @@ -3796,6 +3799,41 @@ security: - read:pets ``` +###### Security Requirement in a Referenced Document + +See [Resolving Implicit Connections](#resolvingImplicitConnections) for more information. + +Entry document `openapi.yaml`: + +```YAML +components: + securitySchemes: + MySecurity: + type: http + scheme: bearer + bearerFormat: JWT +paths: + /foo: + $ref: "other.yaml#/components/pathItems/Foo" +``` + +Referenced document `other.yaml`: + +```YAML +components: + securitySchemes: + MySecurity: + type: http + scheme: basic + pathItems: + Foo: + get: + security: + - MySecurity: [] +``` + +In this example, it is implementation-defined whether the Security Requirement for "MySecurity" in `other.yaml` resolves to `other.yaml#/components/securitySchemes/MySecurity` or the RECOMMENDED resolved location of `openapi.yaml#/components/securitySchemes/MySecurity`. + ### Specification Extensions While the OpenAPI Specification tries to accommodate most use cases, additional data can be added to extend the specification at certain points. From ae356913c0a85b1a4a5de124bbc6331ded71af16 Mon Sep 17 00:00:00 2001 From: Henry Andrews Date: Tue, 11 Jun 2024 07:59:07 -0700 Subject: [PATCH 06/10] Fix stray random characters (review feedback) Co-authored-by: Ralf Handl --- versions/3.0.4.md | 1 - 1 file changed, 1 deletion(-) diff --git a/versions/3.0.4.md b/versions/3.0.4.md index 876ff94100..154b6924f1 100644 --- a/versions/3.0.4.md +++ b/versions/3.0.4.md @@ -175,7 +175,6 @@ If the same JSON/YAML object is parsed multiple times and the respective context #### Resolving Implicit Connections Several features of this specification require resolution of non-URI-based connections to some other part of the OpenAPI Description (OAD). -`` These connections are unambiguously resolved in single-document OADs, but the resolution process in multi-document OADs is _implementation-defined_, within the constraints described in this section. In some cases, an unambiguous URI-based alternative is available, and OAD authors are RECOMMENDED to always use the alternative: From c8a154feff083493d7b97eea62a8ee2968473c75 Mon Sep 17 00:00:00 2001 From: "Henry H. Andrews" Date: Tue, 11 Jun 2024 09:33:42 -0700 Subject: [PATCH 07/10] example as YAML/JSON via HTTP negotiation --- versions/3.0.4.md | 73 +++++++++++++++++++++++++++++++++++++++++++---- 1 file changed, 67 insertions(+), 6 deletions(-) diff --git a/versions/3.0.4.md b/versions/3.0.4.md index 154b6924f1..00d7bb0b1a 100644 --- a/versions/3.0.4.md +++ b/versions/3.0.4.md @@ -3802,9 +3802,38 @@ security: See [Resolving Implicit Connections](#resolvingImplicitConnections) for more information. -Entry document `openapi.yaml`: +First, our entry document is where parsing begins. It defines the `MySecurity` security scheme to be JWT-based, and it defines on Path Item as a reference to a component in another document: -```YAML +```HTTP +GET /api/description/openapi HTTP/1.1 +Host: www.example.com +Accept: application/openapi+json +``` + +```json +"components": { + "securitySchemes": { + "MySecurity": { + "type": "http", + "scheme": "bearer", + "bearerFormat": "JWT" + } + } +}, +"paths": { + "/foo": { + "$ref": "other#/components/pathItems/Foo" + } +} +``` + +```HTTP +GET /api/description/openapi HTTP/1.1 +Host: www.example.com +Accept: application/openapi+yaml +``` + +```yaml components: securitySchemes: MySecurity: @@ -3813,12 +3842,44 @@ components: bearerFormat: JWT paths: /foo: - $ref: "other.yaml#/components/pathItems/Foo" + $ref: "other#/components/pathItems/Foo" ``` -Referenced document `other.yaml`: +Next, we have our referenced document, `other`, that we presumably request in the same format we requested for the entry document. But the fact that we don't use file extensions gives the client the flexibilty to choose on a resource-by-resource basis, assuming both representations are available: -```YAML +```HTTP +GET /api/description/other HTTP/1.1 +Host: www.example.com +Accept: application/openapi+json +``` + +```json +"components": { + "securitySchemes": { + "MySecurity": { + "type": "http", + "scheme": "basic" + } + }, + "pathItems": { + "Foo": { + "get": { + "security": [ + "MySecurity": [] + ] + } + } + } +} +``` + +```HTTP +GET /api/description/other HTTP/1.1 +Host: www.example.com +Accept: application/openapi+yaml +``` + +```yaml components: securitySchemes: MySecurity: @@ -3831,7 +3892,7 @@ components: - MySecurity: [] ``` -In this example, it is implementation-defined whether the Security Requirement for "MySecurity" in `other.yaml` resolves to `other.yaml#/components/securitySchemes/MySecurity` or the RECOMMENDED resolved location of `openapi.yaml#/components/securitySchemes/MySecurity`. +In this `other` document, the reference path item has a Security Requirement for the Security Scheme "MySecurity". But there is a Security Scheme by that name in the `other` document as well. As discussed in [Resolving Implicit Connections](#resolvingImplicitConnections), which "MySecurity" gets used is [implementation-defined](#undefinedAndImplementationDefinedBehavior). However, as also documented in that section, it is RECOMMENDED that tools resolve component names from the [entry document](#documentStructure). As with all implementation-defined behavior, it is important to check tool documentation to determine which behavior is supported. ### Specification Extensions From 80ec461b2747824e329e22ff6eebd0c40bb0836c Mon Sep 17 00:00:00 2001 From: Henry Andrews Date: Tue, 11 Jun 2024 11:19:26 -0700 Subject: [PATCH 08/10] Formatting fix (review feedback) Co-authored-by: Ralf Handl --- versions/3.0.4.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/versions/3.0.4.md b/versions/3.0.4.md index 00d7bb0b1a..54006e4bb2 100644 --- a/versions/3.0.4.md +++ b/versions/3.0.4.md @@ -3865,7 +3865,7 @@ Accept: application/openapi+json "Foo": { "get": { "security": [ - "MySecurity": [] + "MySecurity": [] ] } } From 1639c5d43792bebb9229d796e2901773974ed0ee Mon Sep 17 00:00:00 2001 From: Henry Andrews Date: Wed, 12 Jun 2024 10:03:00 -0700 Subject: [PATCH 09/10] Apply suggestions from code review Co-authored-by: Jeremy Fiel <32110157+jeremyfiel@users.noreply.github.com> --- versions/3.0.4.md | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/versions/3.0.4.md b/versions/3.0.4.md index 54006e4bb2..d0a9538f75 100644 --- a/versions/3.0.4.md +++ b/versions/3.0.4.md @@ -3802,7 +3802,7 @@ security: See [Resolving Implicit Connections](#resolvingImplicitConnections) for more information. -First, our entry document is where parsing begins. It defines the `MySecurity` security scheme to be JWT-based, and it defines on Path Item as a reference to a component in another document: +First, our entry document is where parsing begins. It defines the `MySecurity` security scheme to be JWT-based, and it defines a Path Item as a reference to a component in another document: ```HTTP GET /api/description/openapi HTTP/1.1 @@ -3845,7 +3845,7 @@ paths: $ref: "other#/components/pathItems/Foo" ``` -Next, we have our referenced document, `other`, that we presumably request in the same format we requested for the entry document. But the fact that we don't use file extensions gives the client the flexibilty to choose on a resource-by-resource basis, assuming both representations are available: +Next, we have our referenced document, `other`. The fact that we don't use file extensions gives the client the flexibility to choose an acceptable format on a resource-by-resource basis, assuming both representations are available: ```HTTP GET /api/description/other HTTP/1.1 @@ -3892,7 +3892,7 @@ components: - MySecurity: [] ``` -In this `other` document, the reference path item has a Security Requirement for the Security Scheme "MySecurity". But there is a Security Scheme by that name in the `other` document as well. As discussed in [Resolving Implicit Connections](#resolvingImplicitConnections), which "MySecurity" gets used is [implementation-defined](#undefinedAndImplementationDefinedBehavior). However, as also documented in that section, it is RECOMMENDED that tools resolve component names from the [entry document](#documentStructure). As with all implementation-defined behavior, it is important to check tool documentation to determine which behavior is supported. +In the `other` document, the referenced path item has a Security Requirement for a Security Scheme, `MySecurity`. The same Security Scheme exists in the original entry document. As outlined in [Resolving Implicit Connections](#resolvingImplicitConnections), `MySecurity` is resolved with an [implementation-defined behavior](#undefinedAndImplementationDefinedBehavior). However, documented in that section, it is RECOMMENDED that tools resolve component names from the [entry document](#documentStructure). As with all implementation-defined behavior, it is important to check tool documentation to determine which behavior is supported. ### Specification Extensions From 7dd77192ada6bfaefe371e27711eef033ab5f092 Mon Sep 17 00:00:00 2001 From: "Henry H. Andrews" Date: Thu, 13 Jun 2024 12:26:38 -0700 Subject: [PATCH 10/10] 3.0 uses URLs not URIs in refs --- versions/3.0.4.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/versions/3.0.4.md b/versions/3.0.4.md index d0a9538f75..d13d1ab904 100644 --- a/versions/3.0.4.md +++ b/versions/3.0.4.md @@ -208,7 +208,7 @@ These limitations are expected to be addressed in a future release. See [Security Requirement in a Referenced Document](#security-requirement-in-a-referenced-document) for an example of the possible resolutions, including which one is recommended by this section. The behavior for Discrimator Object non-URI mappings and for the Operation Object's `tags` field operate on the same principles. -Note that no aspect of implicit connection resolution changes how [URIs are resolved](#relativeReferencesURI), or restricts their possible targets. +Note that no aspect of implicit connection resolution changes how [URLs are resolved](#relativeReferences), or restricts their possible targets. ### Data Types