From 78e210a8238cecc8fa10854f0b3c533fa912fe73 Mon Sep 17 00:00:00 2001 From: Vladimir Gorej Date: Tue, 5 Jul 2022 10:02:47 +0200 Subject: [PATCH 01/41] feat: strip custom referencing mechanism from Channel Item (#777) --- spec/asyncapi.md | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/spec/asyncapi.md b/spec/asyncapi.md index 56fdd0687..0a67aed8d 100644 --- a/spec/asyncapi.md +++ b/spec/asyncapi.md @@ -540,7 +540,7 @@ Channels are also known as "topics", "routing keys", "event types" or "paths". Field Pattern | Type | Description ---|:---:|--- -{channel} | [Channel Item Object](#channelItemObject) | A relative path to an individual channel. The field name MUST be in the form of a [RFC 6570 URI template](https://tools.ietf.org/html/rfc6570). Query parameters and fragments SHALL NOT be used, instead use [bindings](#channelBindingsObject) to define them. +{channel} | [Channel Item Object](#channelItemObject) \| [Reference Object](#referenceObject) | A relative path to an individual channel. The field name MUST be in the form of a [RFC 6570 URI template](https://tools.ietf.org/html/rfc6570). Query parameters and fragments SHALL NOT be used, instead use [bindings](#channelBindingsObject) to define them. ##### Channels Object Example @@ -574,7 +574,6 @@ Describes the operations available on a single channel. Field Name | Type | Description ---|:---:|--- -$ref | `string` | Allows for a referenced definition of this channel item. The referenced structure MUST be in the form of a [Channel Item Object](#channelItemObject). In case a Channel Item Object field appears both in the defined object and the referenced object, the behavior is *undefined*. Resolution is done as defined by the [JSON Reference](https://tools.ietf.org/html/draft-pbryan-zyp-json-ref-03).

**Deprecated:** Usage of the `$ref` property has been deprecated. description | `string` | An optional description of this channel item. [CommonMark syntax](https://spec.commonmark.org/) can be used for rich text representation. servers | [`string`] | The servers on which this channel is available, specified as an optional unordered list of names (string keys) of [Server Objects](#serverObject) defined in the [Servers Object](#serversObject) (a map). If `servers` is absent or empty then this channel must be available on all servers defined in the [Servers Object](#serversObject). subscribe | [Operation Object](#operationObject) | A definition of the SUBSCRIBE operation, which defines the messages produced by the application and sent to the channel. @@ -1468,8 +1467,8 @@ Field Name | Type | Description ---|:---|--- schemas | Map[`string`, [Schema Object](#schemaObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Schema Objects](#schemaObject). servers | Map[`string`, [Server Object](#serverObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Server Objects](#serverObject). + channels | Map[`string`, [Channel Item Object](#channelItemObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Channel Item Objects](#channelItemObject). serverVariables | Map[`string`, [Server Variable Object](#serverVariableObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Server Variable Objects](#serverVariableObject). - channels | Map[`string`, [Channel Item Object](#channelItemObject)] | An object to hold reusable [Channel Item Objects](#channelItemObject). messages | Map[`string`, [Message Object](#messageObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Message Objects](#messageObject). securitySchemes| Map[`string`, [Security Scheme Object](#securitySchemeObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Security Scheme Objects](#securitySchemeObject). parameters | Map[`string`, [Parameter Object](#parameterObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Parameter Objects](#parameterObject). From 3c59fa687d9d3a92e43249ff3ca2d4b1f65c0041 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Fran=20M=C3=A9ndez?= Date: Mon, 25 Jul 2022 18:02:18 +0200 Subject: [PATCH 02/41] docs: clarify the meaning of components (#803) --- spec/asyncapi.md | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/spec/asyncapi.md b/spec/asyncapi.md index 0a67aed8d..4a5962906 100644 --- a/spec/asyncapi.md +++ b/spec/asyncapi.md @@ -143,6 +143,8 @@ In order to preserve the ability to round-trip between YAML and JSON formats, YA An AsyncAPI document MAY be made up of a single document or be divided into multiple, connected parts at the discretion of the author. In the latter case, [Reference Objects](#referenceObject) are used. +It is important to note that everything that is defined in an AsyncAPI document MUST be used by the implemented [Application](#definitionsApplication), with the exception of the [Components Object](#componentsObject). Everything that is defined inside the Components Object represents a resource that MAY or MAY NOT be used by the implemented [Application](#definitionsApplication). + By convention, the AsyncAPI Specification (A2S) file is named `asyncapi.json` or `asyncapi.yaml`. ### Absolute URLs @@ -165,8 +167,8 @@ Field Name | Type | Description info | [Info Object](#infoObject) | **REQUIRED.** Provides metadata about the API. The metadata can be used by the clients if needed. servers | [Servers Object](#serversObject) | Provides connection details of servers. defaultContentType | [Default Content Type](#defaultContentTypeString) | Default content type to use when encoding/decoding a message's payload. -channels | [Channels Object](#channelsObject) | **REQUIRED** The available channels and messages for the API. -components | [Components Object](#componentsObject) | An element to hold various schemas for the specification. +channels | [Channels Object](#channelsObject) | **Required** The available channels and messages for the API. +components | [Components Object](#componentsObject) | An element to hold various reusable objects for the specification. Everything that is defined inside this object represents a resource that MAY or MAY NOT be used in the rest of the document and MAY or MAY NOT be used by the implemented [Application](#definitionsApplication). tags | [Tags Object](#tagsObject) | A list of tags used by the specification with additional metadata. Each tag name in the list MUST be unique. externalDocs | [External Documentation Object](#externalDocumentationObject) | Additional external documentation. From 624ad527110c58ee78d8b73199a5049cfa04a980 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Fran=20M=C3=A9ndez?= Date: Wed, 21 Sep 2022 14:43:44 +0200 Subject: [PATCH 03/41] feat: add new channels object (#827) --- spec/asyncapi.md | 194 ++++++++++++++++++++++++----------------------- 1 file changed, 99 insertions(+), 95 deletions(-) diff --git a/spec/asyncapi.md b/spec/asyncapi.md index 4a5962906..c6ee26101 100644 --- a/spec/asyncapi.md +++ b/spec/asyncapi.md @@ -57,7 +57,7 @@ It means that the [application](#definitionsApplication) allows [consumers](#def - [Server Variable Object](#serverVariableObject) - [Default Content Type](#defaultContentTypeString) - [Channels Object](#channelsObject) - - [Channel Item Object](#channelItemObject) + - [Channel Object](#channelObject) - [Operation Object](#operationObject) - [Operation Trait Object](#operationTraitObject) - [Message Object](#messageObject) @@ -167,7 +167,7 @@ Field Name | Type | Description info | [Info Object](#infoObject) | **REQUIRED.** Provides metadata about the API. The metadata can be used by the clients if needed. servers | [Servers Object](#serversObject) | Provides connection details of servers. defaultContentType | [Default Content Type](#defaultContentTypeString) | Default content type to use when encoding/decoding a message's payload. -channels | [Channels Object](#channelsObject) | **Required** The available channels and messages for the API. +channels | [Channels Object](#channelsObject) | The channels used by this [application](#definitionsApplication). components | [Components Object](#componentsObject) | An element to hold various reusable objects for the specification. Everything that is defined inside this object represents a resource that MAY or MAY NOT be used in the rest of the document and MAY or MAY NOT be used by the implemented [Application](#definitionsApplication). tags | [Tags Object](#tagsObject) | A list of tags used by the specification with additional metadata. Each tag name in the list MUST be unique. externalDocs | [External Documentation Object](#externalDocumentationObject) | Additional external documentation. @@ -534,23 +534,22 @@ defaultContentType: application/json #### Channels Object -Holds the relative paths to the individual channel and their operations. Channel paths are relative to servers. - -Channels are also known as "topics", "routing keys", "event types" or "paths". +An object containing all the [Channel Object](#channelObject) definitions the [Application](#definitionsApplication) MUST use during runtime. ##### Patterned Fields Field Pattern | Type | Description ---|:---:|--- -{channel} | [Channel Item Object](#channelItemObject) \| [Reference Object](#referenceObject) | A relative path to an individual channel. The field name MUST be in the form of a [RFC 6570 URI template](https://tools.ietf.org/html/rfc6570). Query parameters and fragments SHALL NOT be used, instead use [bindings](#channelBindingsObject) to define them. +{channelId} | [Channel Object](#channelObject) \| [Reference Object](#referenceObject) | An identifier for the described channel. The `channelId` value is **case-sensitive**. Tools and libraries MAY use the `channelId` to uniquely identify a channel, therefore, it is RECOMMENDED to follow common programming naming conventions. ##### Channels Object Example ```json { - "user/signedup": { - "subscribe": { - "message": { + "userSignedUp": { + "address": "user.signedup", + "messages": { + "userSignedUp": { "$ref": "#/components/messages/userSignedUp" } } @@ -559,54 +558,59 @@ Field Pattern | Type | Description ``` ```yaml -user/signedup: - subscribe: - message: - $ref: "#/components/messages/userSignedUp" +userSignedUp: + address: 'user.signedup' + messages: + userSignedUp: + $ref: '#/components/messages/userSignedUp' ``` -#### Channel Item Object +#### Channel Object -Describes the operations available on a single channel. +Describes a shared communication channel. ##### Fixed Fields Field Name | Type | Description ---|:---:|--- -description | `string` | An optional description of this channel item. [CommonMark syntax](https://spec.commonmark.org/) can be used for rich text representation. -servers | [`string`] | The servers on which this channel is available, specified as an optional unordered list of names (string keys) of [Server Objects](#serverObject) defined in the [Servers Object](#serversObject) (a map). If `servers` is absent or empty then this channel must be available on all servers defined in the [Servers Object](#serversObject). -subscribe | [Operation Object](#operationObject) | A definition of the SUBSCRIBE operation, which defines the messages produced by the application and sent to the channel. -publish | [Operation Object](#operationObject) | A definition of the PUBLISH operation, which defines the messages consumed by the application from the channel. -parameters | [Parameters Object](#parametersObject) | A map of the parameters included in the channel name. It SHOULD be present only when using channels with expressions (as defined by [RFC 6570 section 2.2](https://tools.ietf.org/html/rfc6570#section-2.2)). -bindings | [Channel Bindings Object](#channelBindingsObject) \| [Reference Object](#referenceObject) | A map where the keys describe the name of the protocol and the values describe protocol-specific definitions for the channel. +address | `string` \| `null` | An optional string representation of this channel's address. The address is typically the "topic name", "routing key", "event type", or "path". When `null` or absent, it MUST be interpreted as unknown. This is useful when the address is generated dynamically at runtime or can't be known upfront. It MAY contain [Channel Address Expressions](#channelAddressExpressions). +messages | [Messages Object](#messagesObject) | A map of the messages that will be sent to this channel by any application at any time. **Every message sent to this channel MUST be valid against one, and only one, of the [message objects](#messageObject) defined in this map.** +description | `string` | An optional description of this channel. [CommonMark syntax](https://spec.commonmark.org/) can be used for rich text representation. +servers | [[Reference Object](#referenceObject)] | An array of `$ref` pointers to the definition of the servers in which this channel is available. If `servers` is absent or empty, this channel MUST be available on all the servers defined in the [Servers Object](#serversObject). Please note the `servers` property value MUST be an array of [Reference Objects](#referenceObject) and, therefore, MUST NOT contain an array of [Server Objects](#serverObject). However, it is RECOMMENDED that parsers (or other software) dereference this property for a better development experience. +parameters | [Parameters Object](#parametersObject) | A map of the parameters included in the channel address. It MUST be present only when the address contains [Channel Address Expressions](#channelAddressExpressions). +bindings | [Channel Bindings Object](#channelBindingsObject) \| [Reference Object](#referenceObject) | A map where the keys describe the name of the protocol and the values describe protocol-specific definitions for the channel. +tags | [Tags Object](#tagsObject) | A list of tags for logical grouping of channels. +externalDocs | [External Documentation Object](#externalDocumentationObject) | Additional external documentation for this channel. + This object MAY be extended with [Specification Extensions](#specificationExtensions). -##### Channel Item Object Example +##### Channel Object Example ```json { - "description": "This channel is used to exchange messages about users signing up", - "subscribe": { - "summary": "A user signed up.", - "message": { - "description": "A longer description of the message", - "payload": { - "type": "object", - "properties": { - "user": { - "$ref": "#/components/schemas/user" - }, - "signup": { - "$ref": "#/components/schemas/signup" - } - } - } + "address": "users.{userId}", + "description": "This channel is used to exchange messages about user events.", + "messages": { + "userSignedUp": { + "$ref": "#/components/messages/userSignedUp" + }, + "userCompletedOrder": { + "$ref": "#/components/messages/userCompletedOrder" + } + }, + "parameters": { + "userId": { + "$ref": "#/components/parameters/userId" } }, + "servers": [ + { "$ref": "#/servers/rabbitmqInProd" }, + { "$ref": "#/servers/rabbitmqInStaging" } + ], "bindings": { "amqp": { "is": "queue", @@ -614,87 +618,87 @@ This object MAY be extended with [Specification Extensions](#specificationExtens "exclusive": true } } + }, + "tags": [{ + "name": "user", + "description": "User-related messages" + }], + "externalDocs": { + "description": "Find more info here", + "url": "https://example.com" } } ``` ```yaml -description: This channel is used to exchange messages about users signing up -subscribe: - summary: A user signed up. - message: - description: A longer description of the message - payload: - type: object - properties: - user: - $ref: "#/components/schemas/user" - signup: - $ref: "#/components/schemas/signup" +address: 'users.{userId}' +description: This channel is used to exchange messages about user events. +messages: + userSignedUp: + $ref: '#/components/messages/userSignedUp' + userCompletedOrder: + $ref: '#/components/messages/userCompletedOrder' +parameters: + userId: + $ref: '#/components/parameters/userId' +servers: + - $ref: '#/servers/rabbitmqInProd' + - $ref: '#/servers/rabbitmqInStaging' bindings: amqp: is: queue queue: exclusive: true +tags: + - name: user + description: User-related messages +externalDocs: + description: 'Find more info here' + url: 'https://example.com' ``` -Using `oneOf` to specify multiple messages per operation: -```json -{ - "subscribe": { - "message": { - "oneOf": [ - { "$ref": "#/components/messages/signup" }, - { "$ref": "#/components/messages/login" } - ] - } - } -} -``` -```yaml -subscribe: - message: - oneOf: - - $ref: '#/components/messages/signup' - - $ref: '#/components/messages/login' -``` -Using explicit by-name references to the servers on which the channel is available: +#### Channel Address Expressions + +Channel addresses MAY contain expressions that can be used to define dynamic values. + +Expressions MUST be composed by a name enclosed in curly braces (`{` and `}`). E.g., `{userId}`. + + + + + +#### Messages Object + +Describes a map of messages included in a channel. + +##### Patterned Fields + +Field Pattern | Type | Description +---|:---:|--- +`{messageId}` | [Message Object](#messageObject) \| [Reference Object](#referenceObject) | The key represents the message identifier. The `messageId` value is **case-sensitive**. Tools and libraries MAY use the `messageId` value to uniquely identify a message, therefore, it is RECOMMENDED to follow common programming naming conventions. + +##### Messages Object Example ```json { - "description": "This application publishes WebUICommand messages to an AMQP queue on RabbitMQ brokers in the Staging and Production environments.", - "servers": [ - "rabbitmqBrokerInProd", - "rabbitmqBrokerInStaging", - ], - "subscribe": { - "message": { - "$ref": "#/components/messages/WebUICommand" - } + "userSignedUp": { + "$ref": "#/components/messages/userSignedUp" }, - "bindings": { - "amqp": { - "is": "queue" - } + "userCompletedOrder": { + "$ref": "#/components/messages/userCompletedOrder" } } ``` ```yaml -description: This application publishes WebUICommand messages to an AMQP queue on RabbitMQ brokers in the Staging and Production environments. -servers: - - rabbitmqBrokerInProd - - rabbitmqBrokerInStaging -subscribe: - message: - $ref: "#/components/messages/WebUICommand" -bindings: - amqp: - is: queue +userSignedUp: + $ref: '#/components/messages/userSignedUp' +userCompletedOrder: + $ref: '#/components/messages/userCompletedOrder' ``` @@ -1469,7 +1473,7 @@ Field Name | Type | Description ---|:---|--- schemas | Map[`string`, [Schema Object](#schemaObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Schema Objects](#schemaObject). servers | Map[`string`, [Server Object](#serverObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Server Objects](#serverObject). - channels | Map[`string`, [Channel Item Object](#channelItemObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Channel Item Objects](#channelItemObject). + channels | Map[`string`, [Channel Object](#channelObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Channel Objects](#channelObject). serverVariables | Map[`string`, [Server Variable Object](#serverVariableObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Server Variable Objects](#serverVariableObject). messages | Map[`string`, [Message Object](#messageObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Message Objects](#messageObject). securitySchemes| Map[`string`, [Security Scheme Object](#securitySchemeObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Security Scheme Objects](#securitySchemeObject). From 1d50ccb7c4fbaac2c6cab4010accfe124858c902 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Fran=20M=C3=A9ndez?= Date: Mon, 26 Sep 2022 16:46:27 +0200 Subject: [PATCH 04/41] feat!: move operations to its own root object (#806) --- spec/asyncapi.md | 126 ++++++++++++++++++++++++++++++----------------- 1 file changed, 80 insertions(+), 46 deletions(-) diff --git a/spec/asyncapi.md b/spec/asyncapi.md index c6ee26101..2e44f296c 100644 --- a/spec/asyncapi.md +++ b/spec/asyncapi.md @@ -1,3 +1,7 @@ +# ATTENTION: Work in progress + +This version is not yet ready to be used. We're currently working on it. If you want to join the effort and participate in the development of the next major version of AsyncAPI, head over to [GitHub Issue that we use for tracking 3.0 development progress](https://github.com/asyncapi/spec/issues/691). + # AsyncAPI Specification #### Disclaimer @@ -58,6 +62,7 @@ It means that the [application](#definitionsApplication) allows [consumers](#def - [Default Content Type](#defaultContentTypeString) - [Channels Object](#channelsObject) - [Channel Object](#channelObject) + - [Operations Object](#operationsObject) - [Operation Object](#operationObject) - [Operation Trait Object](#operationTraitObject) - [Message Object](#messageObject) @@ -168,6 +173,7 @@ Field Name | Type | Description servers | [Servers Object](#serversObject) | Provides connection details of servers. defaultContentType | [Default Content Type](#defaultContentTypeString) | Default content type to use when encoding/decoding a message's payload. channels | [Channels Object](#channelsObject) | The channels used by this [application](#definitionsApplication). +operations | [Operations Object](#operationsObject) | The operations this [application](#definitionsApplication) MUST implement. components | [Components Object](#componentsObject) | An element to hold various reusable objects for the specification. Everything that is defined inside this object represents a resource that MAY or MAY NOT be used in the rest of the document and MAY or MAY NOT be used by the implemented [Application](#definitionsApplication). tags | [Tags Object](#tagsObject) | A list of tags used by the specification with additional metadata. Each tag name in the list MUST be unique. externalDocs | [External Documentation Object](#externalDocumentationObject) | Additional external documentation. @@ -703,19 +709,77 @@ userCompletedOrder: +#### Operations Object + +Holds a dictionary with all the [operations](#operationObject) this application MUST implement. + +> If you're looking for a place to define operations that MAY or MAY NOT be implemented by the application, consider defining them in [`components/operations`](#componentsOperations). + +##### Patterned Fields + +Field Pattern | Type | Description +---|:---:|--- +{operationId} | [Operation Object](#channelObject) \| [Reference Object](#referenceObject) | The operation this application MUST implement. The field name (`operationId`) MUST be a string used to identify the operation in the document where it is defined, and its value is **case-sensitive**. Tools and libraries MAY use the `operationId` to uniquely identify an operation, therefore, it is RECOMMENDED to follow common programming naming conventions. + +##### Operations Object Example + +```json +{ + "onUserSignUp": { + "summary": "Action to sign a user up.", + "description": "A longer description", + "channel": { + "$ref": "#/channels/userSignup" + }, + "action": "send", + "tags": [ + { "name": "user" }, + { "name": "signup" }, + { "name": "register" } + ], + "bindings": { + "amqp": { + "ack": false + } + }, + "traits": [ + { "$ref": "#/components/operationTraits/kafka" } + ] + } +} +``` + +```yaml +onUserSignUp: + summary: Action to sign a user up. + description: A longer description + channel: + $ref: '#/channels/userSignup' + action: send + tags: + - name: user + - name: signup + - name: register + bindings: + amqp: + ack: false + traits: + - $ref: '#/components/operationTraits/kafka' +``` + -#### Operation Object -Describes a publish or a subscribe operation. This provides a place to document how and why messages are sent and received. +#### Operation Object -For example, an operation might describe a chat application use case where a user sends a text message to a group. A publish operation describes messages that are received by the chat application, whereas a subscribe operation describes messages that are sent by the chat application. +Describes a specific operation. ##### Fixed Fields Field Name | Type | Description ---|:---:|--- -operationId | `string` | Unique string used to identify the operation. The id MUST be unique among all operations described in the API. The operationId value is **case-sensitive**. Tools and libraries MAY use the operationId to uniquely identify an operation, therefore, it is RECOMMENDED to follow common programming naming conventions. +action | `string` | **Required**. Allowed values are `send` and `receive`. Use `send` when it's expected that the application will send a message to the given [`channel`](#operationObjectChannel), and `receive` when the application should expect receiving messages from the given [`channel`](#operationObjectChannel). +channel | [Reference Object](#referenceObject) | **Required**. A `$ref` pointer to the definition of the channel in which this operation is performed. Please note the `channel` property value MUST be a [Reference Object](#referenceObject) and, therefore, MUST NOT contain a [Channel Object](#channelObject). However, it is RECOMMENDED that parsers (or other software) dereference this property for a better development experience. summary | `string` | A short summary of what the operation is about. description | `string` | A verbose explanation of the operation. [CommonMark syntax](http://spec.commonmark.org/) can be used for rich text representation. security | [[Security Requirement Object](#securityRequirementObject)]| A declaration of which security mechanisms are associated with this operation. Only one of the security requirement objects MUST be satisfied to authorize an operation. In cases where Server Security also applies, it MUST also be satisfied. @@ -723,7 +787,6 @@ Field Name | Type | Description externalDocs | [External Documentation Object](#externalDocumentationObject) | Additional external documentation for this operation. bindings | [Operation Bindings Object](#operationBindingsObject) \| [Reference Object](#referenceObject) | A map where the keys describe the name of the protocol and the values describe protocol-specific definitions for the operation. traits | [[Operation Trait Object](#operationTraitObject) | [Reference Object](#referenceObject) ] | A list of traits to apply to the operation object. Traits MUST be merged into the operation object using the [JSON Merge Patch](https://tools.ietf.org/html/rfc7386) algorithm in the same order they are defined here. -message | [Message Object](#messageObject) | [Reference Object](#referenceObject) | Map["oneOf", [[Message Object](#messageObject) | [Reference Object](#referenceObject)]] | A definition of the message that will be published or received by this operation. Map containing a single `oneOf` key is allowed here to specify multiple messages. However, **a message MUST be valid only against one of the message objects.** This object MAY be extended with [Specification Extensions](#specificationExtensions). @@ -731,9 +794,12 @@ This object MAY be extended with [Specification Extensions](#specificationExtens ```json { - "operationId": "registerUser", "summary": "Action to sign a user up.", "description": "A longer description", + "channel": { + "$ref": "#/channels/userSignup" + }, + "action": "send", "security": [ { "petstore_auth": [ @@ -747,28 +813,6 @@ This object MAY be extended with [Specification Extensions](#specificationExtens { "name": "signup" }, { "name": "register" } ], - "message": { - "headers": { - "type": "object", - "properties": { - "applicationInstanceId": { - "description": "Unique identifier for a given instance of the publishing application", - "type": "string" - } - } - }, - "payload": { - "type": "object", - "properties": { - "user": { - "$ref": "#/components/schemas/userCreate" - }, - "signup": { - "$ref": "#/components/schemas/signup" - } - } - } - }, "bindings": { "amqp": { "ack": false @@ -781,9 +825,11 @@ This object MAY be extended with [Specification Extensions](#specificationExtens ``` ```yaml -operationId: registerUser summary: Action to sign a user up. description: A longer description +channel: + $ref: '#/channels/userSignup' +action: send security: - petstore_auth: - write:pets @@ -792,20 +838,6 @@ tags: - name: user - name: signup - name: register -message: - headers: - type: object - properties: - applicationInstanceId: - description: Unique identifier for a given instance of the publishing application - type: string - payload: - type: object - properties: - user: - $ref: "#/components/schemas/userCreate" - signup: - $ref: "#/components/schemas/signup" bindings: amqp: ack: false @@ -818,7 +850,7 @@ traits: #### Operation Trait Object -Describes a trait that MAY be applied to an [Operation Object](#operationObject). This object MAY contain any property from the [Operation Object](#operationObject), except `message` and `traits`. +Describes a trait that MAY be applied to an [Operation Object](#operationObject). This object MAY contain any property from the [Operation Object](#operationObject), except the `message` and `traits` ones. If you're looking to apply traits to a message, see the [Message Trait Object](#messageTraitObject). @@ -826,7 +858,8 @@ If you're looking to apply traits to a message, see the [Message Trait Object](# Field Name | Type | Description ---|:---:|--- -operationId | `string` | Unique string used to identify the operation. The id MUST be unique among all operations described in the API. The operationId value is **case-sensitive**. Tools and libraries MAY use the operationId to uniquely identify an operation, therefore, it is RECOMMENDED to follow common programming naming conventions. +action | `string` | Allowed values are `send` and `receive`. Use `send` when it's expected that the application will send a message to the given [`channel`](#operationObjectChannel), and `receive` when the application should expect receiving messages from the given [`channel`](#operationObjectChannel). +channel | [Reference Object](#referenceObject) | A `$ref` pointer to the definition of the channel in which this operation is performed. Please note the `channel` property value MUST be a [Reference Object](#referenceObject) and, therefore, MUST NOT contain a [Channel Object](#channelObject). However, it is RECOMMENDED that parsers (or other software) dereference this property for a better development experience. summary | `string` | A short summary of what the operation is about. description | `string` | A verbose explanation of the operation. [CommonMark syntax](https://spec.commonmark.org/) can be used for rich text representation. security | [[Security Requirement Object](#securityRequirementObject)]| A declaration of which security mechanisms are associated with this operation. Only one of the security requirement objects MUST be satisfied to authorize an operation. In cases where Server Security also applies, it MUST also be satisfied. @@ -1473,8 +1506,9 @@ Field Name | Type | Description ---|:---|--- schemas | Map[`string`, [Schema Object](#schemaObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Schema Objects](#schemaObject). servers | Map[`string`, [Server Object](#serverObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Server Objects](#serverObject). + serverVariables | Map[`string`, [Server Variable Object](#serverVariableObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Server Variable Objects](#serverVariableObject). channels | Map[`string`, [Channel Object](#channelObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Channel Objects](#channelObject). - serverVariables | Map[`string`, [Server Variable Object](#serverVariableObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Server Variable Objects](#serverVariableObject). + operations | Map[`string`, [Operation Item Object](#operationObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Operation Item Objects](#operationObject). messages | Map[`string`, [Message Object](#messageObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Message Objects](#messageObject). securitySchemes| Map[`string`, [Security Scheme Object](#securitySchemeObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Security Scheme Objects](#securitySchemeObject). parameters | Map[`string`, [Parameter Object](#parameterObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Parameter Objects](#parameterObject). From a1783a2e083d90d23036408f4b370674530d1a0d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Maciej=20Urba=C5=84czyk?= Date: Tue, 11 Oct 2022 13:22:22 +0200 Subject: [PATCH 05/41] feat: add more reusable objects to the components object (#792) Co-authored-by: Jonas Lagoni --- spec/asyncapi.md | 22 ++++++++++++---------- 1 file changed, 12 insertions(+), 10 deletions(-) diff --git a/spec/asyncapi.md b/spec/asyncapi.md index 04c57edd2..231570e6a 100644 --- a/spec/asyncapi.md +++ b/spec/asyncapi.md @@ -176,7 +176,7 @@ Field Name | Type | Description operations | [Operations Object](#operationsObject) | The operations this [application](#definitionsApplication) MUST implement. components | [Components Object](#componentsObject) | An element to hold various reusable objects for the specification. Everything that is defined inside this object represents a resource that MAY or MAY NOT be used in the rest of the document and MAY or MAY NOT be used by the implemented [Application](#definitionsApplication). tags | [Tags Object](#tagsObject) | A list of tags used by the specification with additional metadata. Each tag name in the list MUST be unique. -externalDocs | [External Documentation Object](#externalDocumentationObject) | Additional external documentation. +externalDocs | [External Documentation Object](#externalDocumentationObject) \| [Reference Object](#referenceObject) | Additional external documentation. This object MAY be extended with [Specification Extensions](#specificationExtensions). @@ -617,7 +617,7 @@ Field Name | Type | Description parameters | [Parameters Object](#parametersObject) | A map of the parameters included in the channel address. It MUST be present only when the address contains [Channel Address Expressions](#channelAddressExpressions). bindings | [Channel Bindings Object](#channelBindingsObject) \| [Reference Object](#referenceObject) | A map where the keys describe the name of the protocol and the values describe protocol-specific definitions for the channel. tags | [Tags Object](#tagsObject) | A list of tags for logical grouping of channels. -externalDocs | [External Documentation Object](#externalDocumentationObject) | Additional external documentation for this channel. +externalDocs | [External Documentation Object](#externalDocumentationObject) \| [Reference Object](#referenceObject) | Additional external documentation for this channel. This object MAY be extended with [Specification Extensions](#specificationExtensions). @@ -812,7 +812,7 @@ Field Name | Type | Description description | `string` | A verbose explanation of the operation. [CommonMark syntax](http://spec.commonmark.org/) can be used for rich text representation. security | [[Security Requirement Object](#securityRequirementObject)]| A declaration of which security mechanisms are associated with this operation. Only one of the security requirement objects MUST be satisfied to authorize an operation. In cases where Server Security also applies, it MUST also be satisfied. tags | [Tags Object](#tagsObject) | A list of tags for logical grouping and categorization of operations. -externalDocs | [External Documentation Object](#externalDocumentationObject) | Additional external documentation for this operation. +externalDocs | [External Documentation Object](#externalDocumentationObject) \| [Reference Object](#referenceObject) | Additional external documentation for this operation. bindings | [Operation Bindings Object](#operationBindingsObject) \| [Reference Object](#referenceObject) | A map where the keys describe the name of the protocol and the values describe protocol-specific definitions for the operation. traits | [[Operation Trait Object](#operationTraitObject) | [Reference Object](#referenceObject) ] | A list of traits to apply to the operation object. Traits MUST be merged into the operation object using the [JSON Merge Patch](https://tools.ietf.org/html/rfc7386) algorithm in the same order they are defined here. @@ -892,7 +892,7 @@ Field Name | Type | Description description | `string` | A verbose explanation of the operation. [CommonMark syntax](https://spec.commonmark.org/) can be used for rich text representation. security | [[Security Requirement Object](#securityRequirementObject)]| A declaration of which security mechanisms are associated with this operation. Only one of the security requirement objects MUST be satisfied to authorize an operation. In cases where Server Security also applies, it MUST also be satisfied. tags | [Tags Object](#tagsObject) | A list of tags for logical grouping and categorization of operations. -externalDocs | [External Documentation Object](#externalDocumentationObject) | Additional external documentation for this operation. +externalDocs | [External Documentation Object](#externalDocumentationObject) \| [Reference Object](#referenceObject) | Additional external documentation for this operation. bindings | [Operation Bindings Object](#operationBindingsObject) \| [Reference Object](#referenceObject) | A map where the keys describe the name of the protocol and the values describe protocol-specific definitions for the operation. This object MAY be extended with [Specification Extensions](#specificationExtensions). @@ -1169,7 +1169,7 @@ Field Name | Type | Description summary | `string` | A short summary of what the message is about. description | `string` | A verbose explanation of the message. [CommonMark syntax](https://spec.commonmark.org/) can be used for rich text representation. tags | [Tags Object](#tagsObject) | A list of tags for logical grouping and categorization of messages. -externalDocs | [External Documentation Object](#externalDocumentationObject) | Additional external documentation for this message. +externalDocs | [External Documentation Object](#externalDocumentationObject) \| [Reference Object](#referenceObject) | Additional external documentation for this message. bindings | [Message Bindings Object](#messageBindingsObject) \| [Reference Object](#referenceObject) | A map where the keys describe the name of the protocol and the values describe protocol-specific definitions for the message. examples | [[Message Example Object](#messageExampleObject)] | List of examples. traits | [[Message Trait Object](#messageTraitObject) | [Reference Object](#referenceObject)] | A list of traits to apply to the message object. Traits MUST be merged into the message object using the [JSON Merge Patch](https://tools.ietf.org/html/rfc7386) algorithm in the same order they are defined here. The resulting object MUST be a valid [Message Object](#messageObject). @@ -1368,7 +1368,7 @@ Field Name | Type | Description summary | `string` | A short summary of what the message is about. description | `string` | A verbose explanation of the message. [CommonMark syntax](https://spec.commonmark.org/) can be used for rich text representation. tags | [Tags Object](#tagsObject) | A list of tags for logical grouping and categorization of messages. -externalDocs | [External Documentation Object](#externalDocumentationObject) | Additional external documentation for this message. +externalDocs | [External Documentation Object](#externalDocumentationObject) \| [Reference Object](#referenceObject) | Additional external documentation for this message. bindings | [Message Bindings Object](#messageBindingsObject) \| [Reference Object](#referenceObject) | A map where the keys describe the name of the protocol and the values describe protocol-specific definitions for the message. examples | [[Message Example Object](#messageExampleObject)] | List of examples. @@ -1439,7 +1439,7 @@ payload: #### Tags Object -A Tags object is a list of Tag Objects. +A Tags object is a list of [Tag Objects](#tagObject). An [Tag Object](#tagObject) in a list can be referenced by [Reference Object](#referenceObject). #### Tag Object @@ -1450,7 +1450,7 @@ Field Name | Type | Description ---|:---:|--- name | `string` | **REQUIRED.** The name of the tag. description | `string` | A short description for the tag. [CommonMark syntax](https://spec.commonmark.org/) can be used for rich text representation. -externalDocs | [External Documentation Object](#externalDocumentationObject) | Additional external documentation for this tag. +externalDocs | [External Documentation Object](#externalDocumentationObject) \| [Reference Object](#referenceObject) | Additional external documentation for this tag. This object MAY be extended with [Specification Extensions](#specificationExtensions). @@ -1539,13 +1539,15 @@ Field Name | Type | Description ---|:---|--- schemas | Map[`string`, [Schema Object](#schemaObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Schema Objects](#schemaObject). servers | Map[`string`, [Server Object](#serverObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Server Objects](#serverObject). - serverVariables | Map[`string`, [Server Variable Object](#serverVariableObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Server Variable Objects](#serverVariableObject). channels | Map[`string`, [Channel Object](#channelObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Channel Objects](#channelObject). operations | Map[`string`, [Operation Item Object](#operationObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Operation Item Objects](#operationObject). messages | Map[`string`, [Message Object](#messageObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Message Objects](#messageObject). securitySchemes| Map[`string`, [Security Scheme Object](#securitySchemeObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Security Scheme Objects](#securitySchemeObject). + serverVariables | Map[`string`, [Server Variable Object](#serverVariableObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Server Variable Objects](#serverVariableObject). parameters | Map[`string`, [Parameter Object](#parameterObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Parameter Objects](#parameterObject). correlationIds | Map[`string`, [Correlation ID Object](#correlationIdObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Correlation ID Objects](#correlationIdObject). + externalDocs | Map[`string`, [External Documentation Object](#externalDocumentationObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [External Documentation Objects](#externalDocumentationObject). + tags | Map[`string`, [Tag Object](#tagObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Tag Objects](#tagObject). operationTraits | Map[`string`, [Operation Trait Object](#operationTraitObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Operation Trait Objects](#operationTraitObject). messageTraits | Map[`string`, [Message Trait Object](#messageTraitObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Message Trait Objects](#messageTraitObject). serverBindings | Map[`string`, [Server Bindings Object](#serverBindingsObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Server Bindings Objects](#serverBindingsObject). @@ -1843,7 +1845,7 @@ In addition to the JSON Schema fields, the following AsyncAPI vocabulary fields Field Name | Type | Description ---|:---:|--- discriminator | `string` | Adds support for polymorphism. The discriminator is the schema property name that is used to differentiate between other schema that inherit this schema. The property name used MUST be defined at this schema and it MUST be in the `required` property list. When used, the value MUST be the name of this schema or any schema that inherits it. See [Composition and Inheritance](#schemaComposition) for more details. -externalDocs | [External Documentation Object](#externalDocumentationObject) | Additional external documentation for this schema. +externalDocs | [External Documentation Object](#externalDocumentationObject) \| [Reference Object](#referenceObject) | Additional external documentation for this schema. deprecated | `boolean` | Specifies that a schema is deprecated and SHOULD be transitioned out of usage. Default value is `false`. This object MAY be extended with [Specification Extensions](#specificationExtensions). From f3a8468b700c7072ac32cb238af8f1f6d91f0a27 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Maciej=20Urba=C5=84czyk?= Date: Wed, 26 Oct 2022 20:26:43 +0200 Subject: [PATCH 06/41] feat: move root tags and externalDocs to the info object (#794) Co-authored-by: Jonas Lagoni --- spec/asyncapi.md | 27 ++++++++++++++++++++------- 1 file changed, 20 insertions(+), 7 deletions(-) diff --git a/spec/asyncapi.md b/spec/asyncapi.md index 231570e6a..0bd9fbd83 100644 --- a/spec/asyncapi.md +++ b/spec/asyncapi.md @@ -175,9 +175,6 @@ Field Name | Type | Description channels | [Channels Object](#channelsObject) | The channels used by this [application](#definitionsApplication). operations | [Operations Object](#operationsObject) | The operations this [application](#definitionsApplication) MUST implement. components | [Components Object](#componentsObject) | An element to hold various reusable objects for the specification. Everything that is defined inside this object represents a resource that MAY or MAY NOT be used in the rest of the document and MAY or MAY NOT be used by the implemented [Application](#definitionsApplication). -tags | [Tags Object](#tagsObject) | A list of tags used by the specification with additional metadata. Each tag name in the list MUST be unique. -externalDocs | [External Documentation Object](#externalDocumentationObject) \| [Reference Object](#referenceObject) | Additional external documentation. - This object MAY be extended with [Specification Extensions](#specificationExtensions). @@ -234,6 +231,8 @@ Field Name | Type | Description termsOfService | `string` | A URL to the Terms of Service for the API. This MUST be in the form of an absolute URL. contact | [Contact Object](#contactObject) | The contact information for the exposed API. license | [License Object](#licenseObject) | The license information for the exposed API. +tags | [Tags Object](#tagsObject) | A list of tags for application API documentation control. Tags can be used for logical grouping of applications. +externalDocs | [External Documentation Object](#externalDocumentationObject) \| [Reference Object](#referenceObject) | Additional external documentation of the exposed API. This object MAY be extended with [Specification Extensions](#specificationExtensions). @@ -242,7 +241,8 @@ This object MAY be extended with [Specification Extensions](#specificationExtens ```json { "title": "AsyncAPI Sample App", - "description": "This is a sample server.", + "version": "1.0.1", + "description": "This is a sample app.", "termsOfService": "https://asyncapi.org/terms/", "contact": { "name": "API Support", @@ -253,13 +253,22 @@ This object MAY be extended with [Specification Extensions](#specificationExtens "name": "Apache 2.0", "url": "https://www.apache.org/licenses/LICENSE-2.0.html" }, - "version": "1.0.1" + "externalDocs": { + "description": "Find more info here", + "url": "https://www.asyncapi.org" + }, + "tags": [ + { + "name": "e-commerce" + } + ] } ``` ```yaml title: AsyncAPI Sample App -description: This is a sample server. +version: 1.0.1 +description: This is a sample app. termsOfService: https://asyncapi.org/terms/ contact: name: API Support @@ -268,7 +277,11 @@ contact: license: name: Apache 2.0 url: https://www.apache.org/licenses/LICENSE-2.0.html -version: 1.0.1 +externalDocs: + description: Find more info here + url: https://www.asyncapi.org +tags: + - name: e-commerce ``` #### Contact Object From f3773c5dea83a125865c72bdc7a8173035348910 Mon Sep 17 00:00:00 2001 From: Jonas Lagoni Date: Mon, 31 Oct 2022 10:37:27 +0100 Subject: [PATCH 07/41] chore: fix inconsistent title level (#865) --- spec/asyncapi.md | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/spec/asyncapi.md b/spec/asyncapi.md index 0bd9fbd83..418b2b826 100644 --- a/spec/asyncapi.md +++ b/spec/asyncapi.md @@ -91,28 +91,28 @@ It means that the [application](#definitionsApplication) allows [consumers](#def ## Definitions -#### Server +### Server A server MAY be a message broker that is capable of sending and/or receiving between a [producer](#definitionsProducer) and [consumer](#definitionsConsumer). A server MAY be a service with WebSocket API that enables message-driven communication between browser-to-server or server-to-server. -#### Application +### Application An application is any kind of computer program or a group of them. It MUST be a [producer](#definitionsProducer), a [consumer](#definitionsConsumer) or both. An application MAY be a microservice, IoT device (sensor), mainframe process, etc. An application MAY be written in any number of different programming languages as long as they support the selected [protocol](#definitionsProtocol). An application MUST also use a protocol supported by the [server](#definitionsServer) in order to connect and exchange [messages](#definitionsMessage). -#### Producer +### Producer A producer is a type of application, connected to a [server](#definitionsServer), that is creating [messages](#definitionsMessage) and addressing them to [channels](#definitionsChannel). A producer MAY be publishing to multiple channels depending on the [server](#definitionsServer), protocol, and use-case pattern. -#### Consumer +### Consumer A consumer is a type of application, connected to a [server](#definitionsServer) via a supported [protocol](#definitionsProtocol), that is consuming [messages](#definitionsMessage) from [channels](#definitionsChannel). A consumer MAY be consuming from multiple channels depending on the [server](#definitionsServer), protocol, and the use-case pattern. -#### Message +### Message A message is the mechanism by which information is exchanged via a channel between [servers](#definitionsServer) and applications. A message MUST contain a payload and MAY also contain headers. The headers MAY be subdivided into [protocol](#definitionsProtocol)-defined headers and header properties defined by the application which can act as supporting metadata. The payload contains the data, defined by the application, which MUST be serialized into a format (JSON, XML, Avro, binary, etc.). Since a message is a generic mechanism, it can support multiple interaction patterns such as event, command, request, or response. -#### Channel +### Channel A channel is an addressable component, made available by the [server](#definitionsServer), for the organization of [messages](#definitionsMessage). [Producer](#definitionsProducer) applications send messages to channels and [consumer](#definitionsConsumer) applications consume messages from channels. [Servers](#definitionsServer) MAY support many channel instances, allowing messages with different content to be addressed to different channels. Depending on the [server](#definitionsServer) implementation, the channel MAY be included in the message via protocol-defined headers. -#### Protocol +### Protocol A protocol is the mechanism (wireline protocol or API) by which [messages](#definitionsMessage) are exchanged between the application and the [channel](#definitionsChannel). Example protocols include, but are not limited to, AMQP, HTTP, JMS, Kafka, Anypoint MQ, MQTT, Solace, STOMP, Mercure, WebSocket. -#### Bindings +### Bindings A "binding" (or "protocol binding") is a mechanism to define protocol-specific information. Therefore, a protocol binding MUST define protocol-specific information only. ## Specification From 623fbc84f74d1e14c116d80904fd7b428a01f5d7 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Maciej=20Urba=C5=84czyk?= Date: Wed, 9 Nov 2022 16:08:16 +0100 Subject: [PATCH 08/41] fix: remove action and channel fields from Operation Trait Object (#860) --- spec/asyncapi.md | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/spec/asyncapi.md b/spec/asyncapi.md index 418b2b826..bc4a0d01f 100644 --- a/spec/asyncapi.md +++ b/spec/asyncapi.md @@ -891,7 +891,7 @@ traits: #### Operation Trait Object -Describes a trait that MAY be applied to an [Operation Object](#operationObject). This object MAY contain any property from the [Operation Object](#operationObject), except the `message` and `traits` ones. +Describes a trait that MAY be applied to an [Operation Object](#operationObject). This object MAY contain any property from the [Operation Object](#operationObject), except the `action`, `channel` and `traits` ones. If you're looking to apply traits to a message, see the [Message Trait Object](#messageTraitObject). @@ -899,8 +899,6 @@ If you're looking to apply traits to a message, see the [Message Trait Object](# Field Name | Type | Description ---|:---:|--- -action | `string` | Allowed values are `send` and `receive`. Use `send` when it's expected that the application will send a message to the given [`channel`](#operationObjectChannel), and `receive` when the application should expect receiving messages from the given [`channel`](#operationObjectChannel). -channel | [Reference Object](#referenceObject) | A `$ref` pointer to the definition of the channel in which this operation is performed. Please note the `channel` property value MUST be a [Reference Object](#referenceObject) and, therefore, MUST NOT contain a [Channel Object](#channelObject). However, it is RECOMMENDED that parsers (or other software) dereference this property for a better development experience. summary | `string` | A short summary of what the operation is about. description | `string` | A verbose explanation of the operation. [CommonMark syntax](https://spec.commonmark.org/) can be used for rich text representation. security | [[Security Requirement Object](#securityRequirementObject)]| A declaration of which security mechanisms are associated with this operation. Only one of the security requirement objects MUST be satisfied to authorize an operation. In cases where Server Security also applies, it MUST also be satisfied. From 33a997186ac2434c76a9e617822dcc37bf079b05 Mon Sep 17 00:00:00 2001 From: Jonas Lagoni Date: Mon, 21 Nov 2022 21:02:37 +0100 Subject: [PATCH 09/41] chore: update AsyncAPI version to 3.0.0 (#864) --- spec/asyncapi.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/spec/asyncapi.md b/spec/asyncapi.md index bc4a0d01f..fa30270b4 100644 --- a/spec/asyncapi.md +++ b/spec/asyncapi.md @@ -8,7 +8,7 @@ This version is not yet ready to be used. We're currently working on it. If you Part of this content has been taken from the great work done by the folks at the [OpenAPI Initiative](https://openapis.org). Mainly because **it's a great work** and we want to keep as much compatibility as possible with the [OpenAPI Specification](https://github.com/OAI/OpenAPI-Specification). -#### Version 2.5.0 +#### Version 3.0.0 The key words "MUST", "MUST NOT", "REQUIRED", "SHALL", "SHALL NOT", "SHOULD", "SHOULD NOT", "RECOMMENDED", "MAY", and "OPTIONAL" in this document are to be interpreted as described in [RFC 2119](https://www.ietf.org/rfc/rfc2119.txt). @@ -1193,7 +1193,7 @@ The following table contains a set of values that every implementation MUST supp Name | Allowed values | Notes ---|:---:|--- -[AsyncAPI 2.5.0 Schema Object](#schemaObject) | `application/vnd.aai.asyncapi;version=2.5.0`, `application/vnd.aai.asyncapi+json;version=2.5.0`, `application/vnd.aai.asyncapi+yaml;version=2.5.0` | This is the default when a `schemaFormat` is not provided. +[AsyncAPI 3.0.0 Schema Object](#schemaObject) | `application/vnd.aai.asyncapi;version=3.0.0`, `application/vnd.aai.asyncapi+json;version=3.0.0`, `application/vnd.aai.asyncapi+yaml;version=3.0.0` | This is the default when a `schemaFormat` is not provided. [JSON Schema Draft 07](https://json-schema.org/specification-links.html#draft-7) | `application/schema+json;version=draft-07`, `application/schema+yaml;version=draft-07` | The following table contains a set of values that every implementation is RECOMMENDED to support. From c46448f6097e0392fbea9a1b8d21526de36b0c35 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Maciej=20Urba=C5=84czyk?= Date: Mon, 19 Dec 2022 12:01:40 +0100 Subject: [PATCH 10/41] feat: add missed "metadata" fields in the Server/Channel/Operation Objects (#796) Co-authored-by: Jonas Lagoni --- spec/asyncapi.md | 100 ++++++++++++++++++++++++++++++++++------------- 1 file changed, 73 insertions(+), 27 deletions(-) diff --git a/spec/asyncapi.md b/spec/asyncapi.md index fa30270b4..f75cd7848 100644 --- a/spec/asyncapi.md +++ b/spec/asyncapi.md @@ -57,9 +57,9 @@ It means that the [application](#definitionsApplication) allows [consumers](#def - [Contact Object](#contactObject) - [License Object](#licenseObject) - [Servers Object](#serversObject) - - [Server Object](#serverObject) + - [Server Object](#serverObject) - [Server Variable Object](#serverVariableObject) - - [Default Content Type](#defaultContentTypeString) + - [Default Content Type](#defaultContentTypeString) - [Channels Object](#channelsObject) - [Channel Object](#channelObject) - [Operations Object](#operationsObject) @@ -355,21 +355,39 @@ Field Pattern | Type | Description ```json { - "production": { + "development": { "url": "development.gigantic-server.com", - "description": "Development server", "protocol": "kafka", - "protocolVersion": "1.0.0" + "protocolVersion": "1.0.0", + "title": "Development server", + "summary": "A development server", + "description": "A longer description", + "tags": [ + { + "name": "env:development" + } + ], + "externalDocs": { + "description": "Find more info here", + "url": "https://kafka.apache.org/" + } } } ``` ```yaml -production: +development: url: development.gigantic-server.com - description: Development server protocol: kafka - protocolVersion: '1.0.0' + protocolVersion: 1.0.0 + title: Development server + summary: A development server + description: A longer description + tags: + - name: "env:development" + externalDocs: + description: Find more info here + url: https://kafka.apache.org/ ``` @@ -384,14 +402,15 @@ Field Name | Type | Description url | `string` | **REQUIRED**. A URL to the target host. This URL supports Server Variables and MAY be relative, to indicate that the host location is relative to the location where the AsyncAPI document is being served. Variable substitutions will be made when a variable is named in `{`braces`}`. protocol | `string` | **REQUIRED**. The protocol this URL supports for connection. Supported protocol include, but are not limited to: `amqp`, `amqps`, `http`, `https`, `ibmmq`, `jms`, `kafka`, `kafka-secure`, `anypointmq`, `mqtt`, `secure-mqtt`, `solace`, `stomp`, `stomps`, `ws`, `wss`, `mercure`, `googlepubsub`. protocolVersion | `string` | The version of the protocol used for connection. For instance: AMQP `0.9.1`, HTTP `2.0`, Kafka `1.0.0`, etc. +title | `string` | A human-friendly title for the server. +summary | `string` | A short summary of the server. description | `string` | An optional string describing the host designated by the URL. [CommonMark syntax](https://spec.commonmark.org/) MAY be used for rich text representation. variables | Map[`string`, [Server Variable Object](#serverVariableObject) \| [Reference Object](#referenceObject)]] | A map between a variable name and its value. The value is used for substitution in the server's URL template. security | [[Security Requirement Object](#securityRequirementObject)] | A declaration of which security mechanisms can be used with this server. The list of values includes alternative security requirement objects that can be used. Only one of the security requirement objects need to be satisfied to authorize a connection or operation. tags | [Tags Object](#tagsObject) | A list of tags for logical grouping and categorization of servers. +externalDocs | [External Documentation Object](#externalDocumentationObject) \| [Reference Object](#referenceObject) | Additional external documentation for this server. bindings | [Server Bindings Object](#serverBindingsObject) \| [Reference Object](#referenceObject) | A map where the keys describe the name of the protocol and the values describe protocol-specific definitions for the server. -This object MAY be extended with [Specification Extensions](#specificationExtensions). - ##### Server Object Example A single server would be described as: @@ -399,17 +418,35 @@ A single server would be described as: ```json { "url": "development.gigantic-server.com", - "description": "Development server", "protocol": "kafka", - "protocolVersion": "1.0.0" + "protocolVersion": "1.0.0", + "title": "Development server", + "summary": "A development server", + "description": "A longer description", + "tags": [ + { + "name": "env:development" + } + ], + "externalDocs": { + "description": "Find more info here", + "url": "https://kafka.apache.org/" + } } ``` ```yaml url: development.gigantic-server.com -description: Development server protocol: kafka -protocolVersion: '1.0.0' +protocolVersion: 1.0.0 +title: Development server +summary: A development server +description: A longer description +tags: + - name: "env:development" +externalDocs: + description: Find more info here + url: https://kafka.apache.org/ ``` The following shows how multiple servers can be described, for example, at the AsyncAPI Object's [`servers`](#A2SServers): @@ -419,9 +456,9 @@ The following shows how multiple servers can be described, for example, at the A "servers": { "development": { "url": "development.gigantic-server.com", - "description": "Development server", "protocol": "amqp", "protocolVersion": "0.9.1", + "title": "Development server", "tags": [ { "name": "env:development", @@ -431,9 +468,9 @@ The following shows how multiple servers can be described, for example, at the A }, "staging": { "url": "staging.gigantic-server.com", - "description": "Staging server", "protocol": "amqp", "protocolVersion": "0.9.1", + "title": "Staging server", "tags": [ { "name": "env:staging", @@ -443,9 +480,9 @@ The following shows how multiple servers can be described, for example, at the A }, "production": { "url": "api.gigantic-server.com", - "description": "Production server", "protocol": "amqp", "protocolVersion": "0.9.1", + "title": "Production server", "tags": [ { "name": "env:production", @@ -461,25 +498,25 @@ The following shows how multiple servers can be described, for example, at the A servers: development: url: development.gigantic-server.com - description: Development server protocol: amqp protocolVersion: 0.9.1 + title: Development server tags: - name: "env:development" description: "This environment is meant for developers to run their own tests" staging: url: staging.gigantic-server.com - description: Staging server protocol: amqp protocolVersion: 0.9.1 + title: Staging server tags: - name: "env:staging" description: "This environment is a replica of the production environment" production: url: api.gigantic-server.com - description: Production server protocol: amqp protocolVersion: 0.9.1 + title: Production server tags: - name: "env:production" description: "This environment is the live environment available for final users" @@ -492,8 +529,8 @@ The following shows how variables can be used for a server configuration: "servers": { "production": { "url": "{username}.gigantic-server.com:{port}/{basePath}", - "description": "The production API server", "protocol": "secure-mqtt", + "title": "Production server", "variables": { "username": { "default": "demo", @@ -519,8 +556,8 @@ The following shows how variables can be used for a server configuration: servers: production: url: '{username}.gigantic-server.com:{port}/{basePath}' - description: The production API server protocol: secure-mqtt + title: Production server variables: username: # note! no enum here means it is an open value @@ -625,12 +662,14 @@ Field Name | Type | Description ---|:---:|--- address | `string` \| `null` | An optional string representation of this channel's address. The address is typically the "topic name", "routing key", "event type", or "path". When `null` or absent, it MUST be interpreted as unknown. This is useful when the address is generated dynamically at runtime or can't be known upfront. It MAY contain [Channel Address Expressions](#channelAddressExpressions). messages | [Messages Object](#messagesObject) | A map of the messages that will be sent to this channel by any application at any time. **Every message sent to this channel MUST be valid against one, and only one, of the [message objects](#messageObject) defined in this map.** +title | `string` | A human-friendly title for the channel. +summary | `string` | A short summary of the channel. description | `string` | An optional description of this channel. [CommonMark syntax](https://spec.commonmark.org/) can be used for rich text representation. servers | [[Reference Object](#referenceObject)] | An array of `$ref` pointers to the definition of the servers in which this channel is available. If `servers` is absent or empty, this channel MUST be available on all the servers defined in the [Servers Object](#serversObject). Please note the `servers` property value MUST be an array of [Reference Objects](#referenceObject) and, therefore, MUST NOT contain an array of [Server Objects](#serverObject). However, it is RECOMMENDED that parsers (or other software) dereference this property for a better development experience. parameters | [Parameters Object](#parametersObject) | A map of the parameters included in the channel address. It MUST be present only when the address contains [Channel Address Expressions](#channelAddressExpressions). -bindings | [Channel Bindings Object](#channelBindingsObject) \| [Reference Object](#referenceObject) | A map where the keys describe the name of the protocol and the values describe protocol-specific definitions for the channel. tags | [Tags Object](#tagsObject) | A list of tags for logical grouping of channels. externalDocs | [External Documentation Object](#externalDocumentationObject) \| [Reference Object](#referenceObject) | Additional external documentation for this channel. +bindings | [Channel Bindings Object](#channelBindingsObject) \| [Reference Object](#referenceObject) | A map where the keys describe the name of the protocol and the values describe protocol-specific definitions for the channel. This object MAY be extended with [Specification Extensions](#specificationExtensions). @@ -640,6 +679,7 @@ This object MAY be extended with [Specification Extensions](#specificationExtens ```json { "address": "users.{userId}", + "title": "Users channel", "description": "This channel is used to exchange messages about user events.", "messages": { "userSignedUp": { @@ -679,6 +719,7 @@ This object MAY be extended with [Specification Extensions](#specificationExtens ```yaml address: 'users.{userId}' +title: Users channel description: This channel is used to exchange messages about user events. messages: userSignedUp: @@ -767,6 +808,7 @@ Field Pattern | Type | Description ```json { "onUserSignUp": { + "title": "User sign up", "summary": "Action to sign a user up.", "description": "A longer description", "channel": { @@ -792,6 +834,7 @@ Field Pattern | Type | Description ```yaml onUserSignUp: + title: User sign up summary: Action to sign a user up. description: A longer description channel: @@ -809,8 +852,6 @@ onUserSignUp: ``` - - #### Operation Object Describes a specific operation. @@ -821,8 +862,9 @@ Field Name | Type | Description ---|:---:|--- action | `string` | **Required**. Allowed values are `send` and `receive`. Use `send` when it's expected that the application will send a message to the given [`channel`](#operationObjectChannel), and `receive` when the application should expect receiving messages from the given [`channel`](#operationObjectChannel). channel | [Reference Object](#referenceObject) | **Required**. A `$ref` pointer to the definition of the channel in which this operation is performed. Please note the `channel` property value MUST be a [Reference Object](#referenceObject) and, therefore, MUST NOT contain a [Channel Object](#channelObject). However, it is RECOMMENDED that parsers (or other software) dereference this property for a better development experience. +title | `string` | A human-friendly title for the operation. summary | `string` | A short summary of what the operation is about. -description | `string` | A verbose explanation of the operation. [CommonMark syntax](http://spec.commonmark.org/) can be used for rich text representation. +description | `string` | A verbose explanation of the operation. [CommonMark syntax](https://spec.commonmark.org/) can be used for rich text representation. security | [[Security Requirement Object](#securityRequirementObject)]| A declaration of which security mechanisms are associated with this operation. Only one of the security requirement objects MUST be satisfied to authorize an operation. In cases where Server Security also applies, it MUST also be satisfied. tags | [Tags Object](#tagsObject) | A list of tags for logical grouping and categorization of operations. externalDocs | [External Documentation Object](#externalDocumentationObject) \| [Reference Object](#referenceObject) | Additional external documentation for this operation. @@ -835,6 +877,7 @@ This object MAY be extended with [Specification Extensions](#specificationExtens ```json { + "title": "User sign up", "summary": "Action to sign a user up.", "description": "A longer description", "channel": { @@ -866,6 +909,7 @@ This object MAY be extended with [Specification Extensions](#specificationExtens ``` ```yaml +title: User sign up summary: Action to sign a user up. description: A longer description channel: @@ -899,6 +943,7 @@ If you're looking to apply traits to a message, see the [Message Trait Object](# Field Name | Type | Description ---|:---:|--- +title | `string` | A human-friendly title for the operation. summary | `string` | A short summary of what the operation is about. description | `string` | A verbose explanation of the operation. [CommonMark syntax](https://spec.commonmark.org/) can be used for rich text representation. security | [[Security Requirement Object](#securityRequirementObject)]| A declaration of which security mechanisms are associated with this operation. Only one of the security requirement objects MUST be satisfied to authorize an operation. In cases where Server Security also applies, it MUST also be satisfied. @@ -1512,6 +1557,7 @@ description: Find more info here url: https://example.com ``` + #### Reference Object A simple object to allow referencing other components in the specification, internally and externally. @@ -2316,7 +2362,7 @@ type: userPassword ``` ```yaml -type: apiKey, +type: apiKey in: user ``` From 36061cdba277d525e19ec00e2faa896b9f189c6b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Fran=20M=C3=A9ndez?= Date: Tue, 17 Jan 2023 16:35:16 +0100 Subject: [PATCH 11/41] feat: unify all referencing mechanisms (#852) --- spec/asyncapi.md | 277 ++++++++++++++--------------------------------- 1 file changed, 81 insertions(+), 196 deletions(-) diff --git a/spec/asyncapi.md b/spec/asyncapi.md index f75cd7848..b3f0a35e6 100644 --- a/spec/asyncapi.md +++ b/spec/asyncapi.md @@ -75,7 +75,6 @@ It means that the [application](#definitionsApplication) allows [consumers](#def - [Reference Object](#referenceObject) - [Schema Object](#schemaObject) - [Security Scheme Object](#securitySchemeObject) - - [Security Requirement Object](#security-requirement-object) - [OAuth Flows Object](#oauth-flows-object) - [OAuth Flow Object](#oauth-flow-object) - [Server Bindings Object](#serverBindingsObject) @@ -406,7 +405,7 @@ Field Name | Type | Description summary | `string` | A short summary of the server. description | `string` | An optional string describing the host designated by the URL. [CommonMark syntax](https://spec.commonmark.org/) MAY be used for rich text representation. variables | Map[`string`, [Server Variable Object](#serverVariableObject) \| [Reference Object](#referenceObject)]] | A map between a variable name and its value. The value is used for substitution in the server's URL template. -security | [[Security Requirement Object](#securityRequirementObject)] | A declaration of which security mechanisms can be used with this server. The list of values includes alternative security requirement objects that can be used. Only one of the security requirement objects need to be satisfied to authorize a connection or operation. +security | [[Security Scheme Object](#securitySchemeObject) \| [Reference Object](#referenceObject)] | A declaration of which security schemes can be used with this server. The list of values includes alternative [security scheme objects](#securitySchemeObject) that can be used. Only one of the security scheme objects need to be satisfied to authorize a connection or operation. tags | [Tags Object](#tagsObject) | A list of tags for logical grouping and categorization of servers. externalDocs | [External Documentation Object](#externalDocumentationObject) \| [Reference Object](#referenceObject) | Additional external documentation for this server. bindings | [Server Bindings Object](#serverBindingsObject) \| [Reference Object](#referenceObject) | A map where the keys describe the name of the protocol and the values describe protocol-specific definitions for the server. @@ -449,128 +448,82 @@ externalDocs: url: https://kafka.apache.org/ ``` -The following shows how multiple servers can be described, for example, at the AsyncAPI Object's [`servers`](#A2SServers): +Using server variables for dynamic URLs: ```json { - "servers": { - "development": { - "url": "development.gigantic-server.com", - "protocol": "amqp", - "protocolVersion": "0.9.1", - "title": "Development server", - "tags": [ - { - "name": "env:development", - "description": "This environment is meant for developers to run their own tests" - } - ] + "url": "{username}.gigantic-server.com:{port}/{basePath}", + "description": "The production API server", + "protocol": "secure-mqtt", + "variables": { + "username": { + "default": "demo", + "description": "This value is assigned by the service provider, in this example `gigantic-server.com`" }, - "staging": { - "url": "staging.gigantic-server.com", - "protocol": "amqp", - "protocolVersion": "0.9.1", - "title": "Staging server", - "tags": [ - { - "name": "env:staging", - "description": "This environment is a replica of the production environment" - } - ] + "port": { + "enum": [ + "8883", + "8884" + ], + "default": "8883" }, - "production": { - "url": "api.gigantic-server.com", - "protocol": "amqp", - "protocolVersion": "0.9.1", - "title": "Production server", - "tags": [ - { - "name": "env:production", - "description": "This environment is the live environment available for final users" - } - ] + "basePath": { + "default": "v2" } } } ``` ```yaml -servers: - development: - url: development.gigantic-server.com - protocol: amqp - protocolVersion: 0.9.1 - title: Development server - tags: - - name: "env:development" - description: "This environment is meant for developers to run their own tests" - staging: - url: staging.gigantic-server.com - protocol: amqp - protocolVersion: 0.9.1 - title: Staging server - tags: - - name: "env:staging" - description: "This environment is a replica of the production environment" - production: - url: api.gigantic-server.com - protocol: amqp - protocolVersion: 0.9.1 - title: Production server - tags: - - name: "env:production" - description: "This environment is the live environment available for final users" -``` - -The following shows how variables can be used for a server configuration: +url: '{username}.gigantic-server.com:{port}/{basePath}' +description: The production API server +protocol: secure-mqtt +variables: + username: + # Note: no enum here means it is an open value. + default: demo + description: This value is assigned by the service provider, in this example `gigantic-server.com` + port: + enum: + - '8883' + - '8884' + default: '8883' + basePath: + # Note: open meaning. There is the opportunity to use special base paths as assigned by the provider, default is `v2`. + default: v2 +``` + +Using security mechanisms: ```json { - "servers": { - "production": { - "url": "{username}.gigantic-server.com:{port}/{basePath}", - "protocol": "secure-mqtt", - "title": "Production server", - "variables": { - "username": { - "default": "demo", - "description": "This value is assigned by the service provider, in this example `gigantic-server.com`" - }, - "port": { - "enum": [ - "8883", - "8884" - ], - "default": "8883" - }, - "basePath": { - "default": "v2" - } - } + "url": "broker.company.com", + "description": "Production MQTT broker", + "protocol": "secure-mqtt", + "protocolVersion": "5", + "security": [ + { + "type": "userPassword", + "description": "Connect to the MQTT broker using basic authentication." + }, + { + "type": "X509", + "description": "Connect to the MQTT broker using a X509 certificate." } - } + ] } ``` ```yaml -servers: - production: - url: '{username}.gigantic-server.com:{port}/{basePath}' - protocol: secure-mqtt - title: Production server - variables: - username: - # note! no enum here means it is an open value - default: demo - description: This value is assigned by the service provider, in this example `gigantic-server.com` - port: - enum: - - '8883' - - '8884' - default: '8883' - basePath: - # open meaning there is the opportunity to use special base paths as assigned by the provider, default is `v2` - default: v2 +url: broker.company.com +description: Production MQTT broker +protocol: secure-mqtt +protocolVersion: '5' +security: + - type: userPassword + description: Connect to the MQTT broker using basic authentication. + - type: X509 + description: Connect to the MQTT broker using a X509 certificate. ``` @@ -864,8 +817,8 @@ Field Name | Type | Description channel | [Reference Object](#referenceObject) | **Required**. A `$ref` pointer to the definition of the channel in which this operation is performed. Please note the `channel` property value MUST be a [Reference Object](#referenceObject) and, therefore, MUST NOT contain a [Channel Object](#channelObject). However, it is RECOMMENDED that parsers (or other software) dereference this property for a better development experience. title | `string` | A human-friendly title for the operation. summary | `string` | A short summary of what the operation is about. -description | `string` | A verbose explanation of the operation. [CommonMark syntax](https://spec.commonmark.org/) can be used for rich text representation. -security | [[Security Requirement Object](#securityRequirementObject)]| A declaration of which security mechanisms are associated with this operation. Only one of the security requirement objects MUST be satisfied to authorize an operation. In cases where Server Security also applies, it MUST also be satisfied. +description | `string` | A verbose explanation of the operation. [CommonMark syntax](http://spec.commonmark.org/) can be used for rich text representation. +security | [[Security Scheme Object](#securitySchemeObject) \| [Reference Object](#referenceObject)]| A declaration of which security schemes are associated with this operation. Only one of the [security scheme objects](#securitySchemeObject) MUST be satisfied to authorize an operation. In cases where [Server Security](#serverObjectSecurity) also applies, it MUST also be satisfied. tags | [Tags Object](#tagsObject) | A list of tags for logical grouping and categorization of operations. externalDocs | [External Documentation Object](#externalDocumentationObject) \| [Reference Object](#referenceObject) | Additional external documentation for this operation. bindings | [Operation Bindings Object](#operationBindingsObject) \| [Reference Object](#referenceObject) | A map where the keys describe the name of the protocol and the values describe protocol-specific definitions for the operation. @@ -946,7 +899,7 @@ Field Name | Type | Description title | `string` | A human-friendly title for the operation. summary | `string` | A short summary of what the operation is about. description | `string` | A verbose explanation of the operation. [CommonMark syntax](https://spec.commonmark.org/) can be used for rich text representation. -security | [[Security Requirement Object](#securityRequirementObject)]| A declaration of which security mechanisms are associated with this operation. Only one of the security requirement objects MUST be satisfied to authorize an operation. In cases where Server Security also applies, it MUST also be satisfied. +security | [[Security Scheme Object](#securitySchemeObject) \| [Reference Object](#referenceObject)]| A declaration of which security schemes are associated with this operation. Only one of the [security scheme objects](#securitySchemeObject) MUST be satisfied to authorize an operation. In cases where [Server Security](#serverObjectSecurity) also applies, it MUST also be satisfied. tags | [Tags Object](#tagsObject) | A list of tags for logical grouping and categorization of operations. externalDocs | [External Documentation Object](#externalDocumentationObject) \| [Reference Object](#referenceObject) | Additional external documentation for this operation. bindings | [Operation Bindings Object](#operationBindingsObject) \| [Reference Object](#referenceObject) | A map where the keys describe the name of the protocol and the values describe protocol-specific definitions for the operation. @@ -2335,6 +2288,7 @@ Field Name | Type | Applies To | Description bearerFormat | `string` | `http` (`"bearer"`) | A hint to the client to identify how the bearer token is formatted. Bearer tokens are usually generated by an authorization server, so this information is primarily for documentation purposes. flows | [OAuth Flows Object](#oauthFlowsObject) | `oauth2` | **REQUIRED**. An object containing configuration information for the flow types supported. openIdConnectUrl | `string` | `openIdConnect` | **REQUIRED**. OpenId Connect URL to discover OAuth2 configuration values. This MUST be in the form of an absolute URL. +scopes | [`string`] | `oauth2` \| `openIdConnect` | List of the needed scope names. An empty array means no scopes are needed. This object MAY be extended with [Specification Extensions](#specificationExtensions). @@ -2444,12 +2398,15 @@ bearerFormat: JWT "flows": { "implicit": { "authorizationUrl": "https://example.com/api/oauth/dialog", - "scopes": { + "availableScopes": { "write:pets": "modify pets in your account", "read:pets": "read your pets" } } - } + }, + "scopes": [ + "write:pets" + ] } ``` @@ -2458,9 +2415,11 @@ type: oauth2 flows: implicit: authorizationUrl: https://example.com/api/oauth/dialog - scopes: + availableScopes: write:pets: modify pets in your account read:pets: read your pets +scopes: + - 'write:pets' ``` ###### SASL Sample @@ -2499,7 +2458,7 @@ Field Name | Type | Applies To | Description authorizationUrl | `string` | `oauth2` (`"implicit"`, `"authorizationCode"`) | **REQUIRED**. The authorization URL to be used for this flow. This MUST be in the form of an absolute URL. tokenUrl | `string` | `oauth2` (`"password"`, `"clientCredentials"`, `"authorizationCode"`) | **REQUIRED**. The token URL to be used for this flow. This MUST be in the form of an absolute URL. refreshUrl | `string` | `oauth2` | The URL to be used for obtaining refresh tokens. This MUST be in the form of an absolute URL. -scopes | Map[`string`, `string`] | `oauth2` | **REQUIRED**. The available scopes for the OAuth2 security scheme. A map between the scope name and a short description for it. +availableScopes | Map[`string`, `string`] | `oauth2` | **REQUIRED**. The available scopes for the OAuth2 security scheme. A map between the scope name and a short description for it. This object MAY be extended with [Specification Extensions](#specificationExtensions). @@ -2507,98 +2466,24 @@ This object MAY be extended with [Specification Extensions](#specificationExtens ```JSON { - "type": "oauth2", - "flows": { - "implicit": { - "authorizationUrl": "https://example.com/api/oauth/dialog", - "scopes": { - "write:pets": "modify pets in your account", - "read:pets": "read your pets" - } - }, - "authorizationCode": { - "authorizationUrl": "https://example.com/api/oauth/dialog", - "tokenUrl": "https://example.com/api/oauth/token", - "scopes": { - "write:pets": "modify pets in your account", - "read:pets": "read your pets" - } - } + "authorizationUrl": "https://example.com/api/oauth/dialog", + "tokenUrl": "https://example.com/api/oauth/token", + "availableScopes": { + "write:pets": "modify pets in your account", + "read:pets": "read your pets" } } ``` ```YAML -type: oauth2 -flows: - implicit: - authorizationUrl: https://example.com/api/oauth/dialog - scopes: - write:pets: modify pets in your account - read:pets: read your pets - authorizationCode: - authorizationUrl: https://example.com/api/oauth/dialog - tokenUrl: https://example.com/api/oauth/token - scopes: - write:pets: modify pets in your account - read:pets: read your pets -``` - -#### Security Requirement Object - -Lists the required security schemes to execute this operation. -The name used for each property MUST correspond to a security scheme declared in the [Security Schemes](#componentsSecuritySchemes) under the [Components Object](#componentsObject). - -When a list of Security Requirement Objects is defined on a [Server object](#serverObject), only one of the Security Requirement Objects in the list needs to be satisfied to authorize the connection. - -##### Patterned Fields - -Field Pattern | Type | Description ----|:---:|--- -{name} | [`string`] | Each name MUST correspond to a security scheme which is declared in the [Security Schemes](#componentsSecuritySchemes) under the [Components Object](#componentsObject). If the security scheme is of type `"oauth2"` or `"openIdConnect"`, then the value is a list of scope names. Provide scopes that are required to establish successful connection with the server. If scopes are not needed, the list can be empty. For other security scheme types, the array MUST be empty. - -##### Security Requirement Object Examples - -###### User/Password Security Requirement - -```json -{ - "user_pass": [] -} +authorizationUrl: https://example.com/api/oauth/dialog +tokenUrl: https://example.com/api/oauth/token +availableScopes: + write:pets: modify pets in your account + read:pets: read your pets ``` -```yaml -user_pass: [] -``` - -###### API Key Security Requirement - -```json -{ - "api_key": [] -} -``` - -```yaml -api_key: [] -``` - -###### OAuth2 Security Requirement - -```json -{ - "petstore_auth": [ - "write:pets", - "read:pets" - ] -} -``` -```yaml -petstore_auth: -- write:pets -- read:pets -``` ### Correlation ID Object From df2bab7c833075a45ad31d310b3321da718d8a8e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Fran=20M=C3=A9ndez?= Date: Sun, 22 Jan 2023 19:37:07 +0100 Subject: [PATCH 12/41] chore: clarify introduction (#875) --- spec/asyncapi.md | 48 +++++++++++++++++++++++++++++++++++++++--------- 1 file changed, 39 insertions(+), 9 deletions(-) diff --git a/spec/asyncapi.md b/spec/asyncapi.md index b3f0a35e6..4c363e227 100644 --- a/spec/asyncapi.md +++ b/spec/asyncapi.md @@ -16,24 +16,54 @@ The AsyncAPI Specification is licensed under [The Apache License, Version 2.0](h ## Introduction -The AsyncAPI Specification is a project used to describe and document message-driven APIs in a machine-readable format. It’s protocol-agnostic, so you can use it for APIs that work over any protocol (e.g., AMQP, MQTT, WebSockets, Kafka, STOMP, HTTP, Mercure, etc). +The AsyncAPI Specification is a project used to describe message-driven APIs in a machine-readable format. It’s protocol-agnostic, so you can use it for APIs that work over any protocol (e.g., AMQP, MQTT, WebSockets, Kafka, STOMP, HTTP, Mercure, etc). -The AsyncAPI Specification defines a set of files required to describe such an API. -These files can then be used to create utilities, such as documentation, integration and/or testing tools. +The AsyncAPI Specification defines a set of files required to describe the API of an [application](#definitionsApplication). +These files can be used to create utilities, such as documentation, code, integration, or testing tools. -The file(s) MUST describe the operations an [application](#definitionsApplication) accepts. For instance, consider the following AsyncAPI definition snippet: +The file(s) MUST describe the operations an [application](#definitionsApplication) performs. For instance, consider the following AsyncAPI definition snippet: ```yaml -user/signedup: - subscribe: - message: - $ref: "#/components/messages/userSignUp" +channels: + userSignedUp: + # ...(redacted for brevity) +operations: + onUserSignedUp: + action: receive + channel: + $ref: "#/channels/userSignedUp" ``` -It means that the [application](#definitionsApplication) allows [consumers](#definitionsConsumer) to subscribe to the `user/signedup` [channel](#definitionsChannel) to receive userSignUp [messages](#definitionsMessage) produced by the application. +It means that the [application](#definitionsApplication) will subscribe to the `userSignedUp` [channel](#definitionsChannel) to receive messages. **The AsyncAPI specification does not assume any kind of software topology, architecture or pattern.** Therefore, a server MAY be a message broker, a web server or any other kind of computer program capable of sending and/or receiving data. However, AsyncAPI offers a mechanism called "bindings" that aims to help with more specific information about the protocol. +It's NOT RECOMMENDED to derive a [consumer](#definitionsConsumer) AsyncAPI document from a [producer](#definitionsProducer) one or vice versa. There are no guarantees that the channel used by an application to receive messages will be the same channel where another application is sending them. Also, certain fields in the document like `summary`, `description`, and the id of the operation might stop making sense. For instance, given the following consumer snippet: + +```yaml +operations: + onUserSignedUp: + summary: On user signed up. + description: Event received when a user signed up on the product. + action: receive + channel: + $ref: "#/channels/userSignedUp" +``` + +We can't automatically assume that an _opposite_ application exists by simply replacing `receive` with `send`: + +```yaml +operations: + onUserSignedUp: # <-- This doesn't make sense now. Should be something like sendUserSignedUp. + summary: On user signed up. # <-- This doesn't make sense now. Should say something like "Sends a user signed up event". + description: Event received when a user signed up on the product. # <-- This doesn't make sense now. Should speak about sending an event, not receiving it. + action: send + channel: + $ref: "#/channels/userSignedUp" +``` + +Aside from the issues mentioned above, there may also be infrastructure configuration that is not represented here. For instance, a system may use a read-only channel for receiving messages, a different one for sending them, and an intermediary process that will forward messages from one channel to the other. + ## Table of Contents From 190acedeb6b2ab2f7349ed2399e78323240758c4 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Maciej=20Urba=C5=84czyk?= Date: Tue, 7 Feb 2023 17:26:27 +0100 Subject: [PATCH 13/41] fix: use union for operation action (#905) --- spec/asyncapi.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/spec/asyncapi.md b/spec/asyncapi.md index 4c363e227..d3e85338b 100644 --- a/spec/asyncapi.md +++ b/spec/asyncapi.md @@ -843,7 +843,7 @@ Describes a specific operation. Field Name | Type | Description ---|:---:|--- -action | `string` | **Required**. Allowed values are `send` and `receive`. Use `send` when it's expected that the application will send a message to the given [`channel`](#operationObjectChannel), and `receive` when the application should expect receiving messages from the given [`channel`](#operationObjectChannel). +action | `"send"` | `"receive"` | **Required**. Use `send` when it's expected that the application will send a message to the given [`channel`](#operationObjectChannel), and `receive` when the application should expect receiving messages from the given [`channel`](#operationObjectChannel). channel | [Reference Object](#referenceObject) | **Required**. A `$ref` pointer to the definition of the channel in which this operation is performed. Please note the `channel` property value MUST be a [Reference Object](#referenceObject) and, therefore, MUST NOT contain a [Channel Object](#channelObject). However, it is RECOMMENDED that parsers (or other software) dereference this property for a better development experience. title | `string` | A human-friendly title for the operation. summary | `string` | A short summary of what the operation is about. From a2fdc03b5c3211532ea921e0e96ffa1bb0f08af3 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Fran=20M=C3=A9ndez?= Date: Mon, 13 Feb 2023 13:12:34 +0100 Subject: [PATCH 14/41] feat: replace server url with server host and pathname (#888) --- spec/asyncapi.md | 247 ++++++++++++++++++++++------------------------- 1 file changed, 115 insertions(+), 132 deletions(-) diff --git a/spec/asyncapi.md b/spec/asyncapi.md index d3e85338b..4454d3364 100644 --- a/spec/asyncapi.md +++ b/spec/asyncapi.md @@ -385,38 +385,69 @@ Field Pattern | Type | Description ```json { "development": { - "url": "development.gigantic-server.com", - "protocol": "kafka", - "protocolVersion": "1.0.0", - "title": "Development server", - "summary": "A development server", - "description": "A longer description", + "host": "localhost:5672", + "description": "Development AMQP broker.", + "protocol": "amqp", + "protocolVersion": "0-9-1", "tags": [ - { - "name": "env:development" + { + "name": "env:development", + "description": "This environment is meant for developers to run their own tests." } - ], - "externalDocs": { - "description": "Find more info here", - "url": "https://kafka.apache.org/" - } + ] + }, + "staging": { + "host": "rabbitmq-staging.in.mycompany.com:5672", + "description": "RabbitMQ broker for the staging environment.", + "protocol": "amqp", + "protocolVersion": "0-9-1", + "tags": [ + { + "name": "env:staging", + "description": "This environment is a replica of the production environment." + } + ] + }, + "production": { + "host": "rabbitmq.in.mycompany.com:5672", + "description": "RabbitMQ broker for the production environment.", + "protocol": "amqp", + "protocolVersion": "0-9-1", + "tags": [ + { + "name": "env:production", + "description": "This environment is the live environment available for final users." + } + ] } } ``` ```yaml development: - url: development.gigantic-server.com - protocol: kafka - protocolVersion: 1.0.0 - title: Development server - summary: A development server - description: A longer description + host: localhost:5672 + description: Development AMQP broker. + protocol: amqp + protocolVersion: 0-9-1 tags: - name: "env:development" - externalDocs: - description: Find more info here - url: https://kafka.apache.org/ + description: "This environment is meant for developers to run their own tests." +staging: + host: rabbitmq-staging.in.mycompany.com:5672 + description: RabbitMQ broker for the staging environment. + protocol: amqp + protocolVersion: 0-9-1 + tags: + - name: "env:staging" + description: "This environment is a replica of the production environment." +production: + host: rabbitmq.in.mycompany.com:5672 + description: RabbitMQ broker for the production environment. + protocol: amqp + protocolVersion: 0-9-1 + tags: + - name: "env:production" + description: "This environment is the live environment available for final users." ``` @@ -428,13 +459,14 @@ An object representing a message broker, a server or any other kind of computer Field Name | Type | Description ---|:---:|--- -url | `string` | **REQUIRED**. A URL to the target host. This URL supports Server Variables and MAY be relative, to indicate that the host location is relative to the location where the AsyncAPI document is being served. Variable substitutions will be made when a variable is named in `{`braces`}`. -protocol | `string` | **REQUIRED**. The protocol this URL supports for connection. Supported protocol include, but are not limited to: `amqp`, `amqps`, `http`, `https`, `ibmmq`, `jms`, `kafka`, `kafka-secure`, `anypointmq`, `mqtt`, `secure-mqtt`, `solace`, `stomp`, `stomps`, `ws`, `wss`, `mercure`, `googlepubsub`. +host | `string` | **REQUIRED**. The server host name. It MAY include the port. This field supports [Server Variables](#serverObjectVariables). Variable substitutions will be made when a variable is named in `{`braces`}`. +protocol | `string` | **REQUIRED**. The protocol this server supports for connection. protocolVersion | `string` | The version of the protocol used for connection. For instance: AMQP `0.9.1`, HTTP `2.0`, Kafka `1.0.0`, etc. +pathname | `string` | The path to a resource in the host. This field supports [Server Variables](#serverObjectVariables). Variable substitutions will be made when a variable is named in `{`braces`}`. +description | `string` | An optional string describing the server. [CommonMark syntax](https://spec.commonmark.org/) MAY be used for rich text representation. title | `string` | A human-friendly title for the server. summary | `string` | A short summary of the server. -description | `string` | An optional string describing the host designated by the URL. [CommonMark syntax](https://spec.commonmark.org/) MAY be used for rich text representation. -variables | Map[`string`, [Server Variable Object](#serverVariableObject) \| [Reference Object](#referenceObject)]] | A map between a variable name and its value. The value is used for substitution in the server's URL template. +variables | Map[`string`, [Server Variable Object](#serverVariableObject) \| [Reference Object](#referenceObject)]] | A map between a variable name and its value. The value is used for substitution in the server's `host` and `pathname` template. security | [[Security Scheme Object](#securitySchemeObject) \| [Reference Object](#referenceObject)] | A declaration of which security schemes can be used with this server. The list of values includes alternative [security scheme objects](#securitySchemeObject) that can be used. Only one of the security scheme objects need to be satisfied to authorize a connection or operation. tags | [Tags Object](#tagsObject) | A list of tags for logical grouping and categorization of servers. externalDocs | [External Documentation Object](#externalDocumentationObject) \| [Reference Object](#referenceObject) | Additional external documentation for this server. @@ -446,117 +478,38 @@ A single server would be described as: ```json { - "url": "development.gigantic-server.com", + "host": "kafka.in.mycompany.com:9092", + "description": "Production Kafka broker.", "protocol": "kafka", - "protocolVersion": "1.0.0", - "title": "Development server", - "summary": "A development server", - "description": "A longer description", - "tags": [ - { - "name": "env:development" - } - ], - "externalDocs": { - "description": "Find more info here", - "url": "https://kafka.apache.org/" - } + "protocolVersion": "3.2" } ``` ```yaml -url: development.gigantic-server.com +host: kafka.in.mycompany.com:9092 +description: Production Kafka broker. protocol: kafka -protocolVersion: 1.0.0 -title: Development server -summary: A development server -description: A longer description -tags: - - name: "env:development" -externalDocs: - description: Find more info here - url: https://kafka.apache.org/ -``` - -Using server variables for dynamic URLs: - -```json -{ - "url": "{username}.gigantic-server.com:{port}/{basePath}", - "description": "The production API server", - "protocol": "secure-mqtt", - "variables": { - "username": { - "default": "demo", - "description": "This value is assigned by the service provider, in this example `gigantic-server.com`" - }, - "port": { - "enum": [ - "8883", - "8884" - ], - "default": "8883" - }, - "basePath": { - "default": "v2" - } - } -} +protocolVersion: '3.2' ``` -```yaml -url: '{username}.gigantic-server.com:{port}/{basePath}' -description: The production API server -protocol: secure-mqtt -variables: - username: - # Note: no enum here means it is an open value. - default: demo - description: This value is assigned by the service provider, in this example `gigantic-server.com` - port: - enum: - - '8883' - - '8884' - default: '8883' - basePath: - # Note: open meaning. There is the opportunity to use special base paths as assigned by the provider, default is `v2`. - default: v2 -``` - -Using security mechanisms: +An example of a server that has a `pathname`: ```json { - "url": "broker.company.com", - "description": "Production MQTT broker", - "protocol": "secure-mqtt", - "protocolVersion": "5", - "security": [ - { - "type": "userPassword", - "description": "Connect to the MQTT broker using basic authentication." - }, - { - "type": "X509", - "description": "Connect to the MQTT broker using a X509 certificate." - } - ] + "host": "rabbitmq.in.mycompany.com:5672", + "pathname": "/production", + "protocol": "amqp", + "description": "Production RabbitMQ broker (uses the `production` vhost)." } ``` ```yaml -url: broker.company.com -description: Production MQTT broker -protocol: secure-mqtt -protocolVersion: '5' -security: - - type: userPassword - description: Connect to the MQTT broker using basic authentication. - - type: X509 - description: Connect to the MQTT broker using a X509 certificate. +host: rabbitmq.in.mycompany.com:5672 +pathname: /production +protocol: amqp +description: Production RabbitMQ broker (uses the `production` vhost). ``` - #### Server Variable Object An object representing a Server Variable for server URL template substitution. @@ -572,8 +525,38 @@ Field Name | Type | Description This object MAY be extended with [Specification Extensions](#specificationExtensions). +##### Server Variable Object Example +```json +{ + "host": "rabbitmq.in.mycompany.com:5672", + "pathname": "/{env}", + "protocol": "amqp", + "description": "RabbitMQ broker. Use the `env` variable to point to either `production` or `staging`.", + "variables": { + "env": { + "description": "Environment to connect to. It can be either `production` or `staging`.", + "enum": [ + "production", + "staging" + ] + } + } +} +``` +```yaml +host: 'rabbitmq.in.mycompany.com:5672' +pathname: '/{env}' +protocol: amqp +description: RabbitMQ broker. Use the `env` variable to point to either `production` or `staging`. +variables: + env: + description: Environment to connect to. It can be either `production` or `staging`. + enum: + - production + - staging +``` #### Default Content Type @@ -1642,10 +1625,10 @@ my.org.User }, "servers": { "development": { - "url": "{stage}.gigantic-server.com:{port}", - "description": "Development server", + "host": "{stage}.in.mycompany.com:{port}", + "description": "RabbitMQ broker", "protocol": "amqp", - "protocolVersion": "0.9.1", + "protocolVersion": "0-9-1", "variables": { "stage": { "$ref": "#/components/serverVariables/stage" @@ -1659,11 +1642,11 @@ my.org.User "serverVariables": { "stage": { "default": "demo", - "description": "This value is assigned by the service provider, in this example `gigantic-server.com`" + "description": "This value is assigned by the service provider, in this example `mycompany.com`" }, "port": { - "enum": ["8883", "8884"], - "default": "8883" + "enum": ["5671", "5672"], + "default": "5672" } }, "channels": { @@ -1762,10 +1745,10 @@ components: type: string servers: development: - url: "{stage}.gigantic-server.com:{port}" - description: Development server + url: "{stage}.in.mycompany.com:{port}" + description: RabbitMQ broker protocol: amqp - protocolVersion: 0.9.1 + protocolVersion: 0-9-1 variables: stage: $ref: "#/components/serverVariables/stage" @@ -1774,10 +1757,10 @@ components: serverVariables: stage: default: demo - description: This value is assigned by the service provider, in this example `gigantic-server.com` + description: This value is assigned by the service provider, in this example `mycompany.com` port: - enum: [8883, 8884] - default: 8883 + enum: [5671, 5672] + default: 5672 channels: user/signedup: subscribe: From d367c23c439ff66f1f637e179f4184869e4dca74 Mon Sep 17 00:00:00 2001 From: Heiko Henning Date: Fri, 10 Mar 2023 16:06:43 +0100 Subject: [PATCH 15/41] feat: request/response support (#847) Co-authored-by: ue85540 --- examples/adeo-kafka-request-reply.yml | 332 ++++++++++++++++ ...-request-reply-message-filter-in-reply.yml | 357 +++++++++++++++++ ...socket-request-reply-multiple-channels.yml | 372 ++++++++++++++++++ spec/asyncapi.md | 76 +++- 4 files changed, 1136 insertions(+), 1 deletion(-) create mode 100644 examples/adeo-kafka-request-reply.yml create mode 100644 examples/kraken-websocket-request-reply-message-filter-in-reply.yml create mode 100644 examples/kraken-websocket-request-reply-multiple-channels.yml diff --git a/examples/adeo-kafka-request-reply.yml b/examples/adeo-kafka-request-reply.yml new file mode 100644 index 000000000..76fca663b --- /dev/null +++ b/examples/adeo-kafka-request-reply.yml @@ -0,0 +1,332 @@ +asyncapi: 3.0.0 +info: + title: Adeo AsyncAPI Case Study + version: "%REPLACED_BY_MAVEN%" + description: > + This Adeo specification illustrates how ADEO uses AsyncAPI to document some of their exchanges + contact: + name: AsyncAPI team + email: info@asyncapi.io +servers: + production: + url: "prod.url:9092" + protocol: kafka-secure + description: Kafka PRODUCTION cluster + security: + - sasl-ssl: [] + bindings: + kafka: + schemaRegistryUrl: >- + https://schema-registry.prod.url/ + staging: + url: "staging.url:9092" + protocol: kafka-secure + description: Kafka STAGING cluster for `uat` and `preprod` environments + security: + - sasl-ssl: [] + bindings: + kafka: + schemaRegistryUrl: >- + https://schema-registry.staging.url/ + dev: + url: "dev.url:9092" + protocol: kafka-secure + description: Kafka DEV cluster for `dev` and `sit` environments + security: + - sasl-ssl: [] + bindings: + kafka: + schemaRegistryUrl: >- + https://schema-registry.dev.url/ +tags: + - name: costing + description: "Costing channels, used by Costing clients." +channels: + costingRequest: + address: "adeo-{env}-case-study-COSTING-REQUEST-{version}" + description: > + Use this topic to do a Costing Request to Costing product. + We use the + [**RecordNameStrategy**](https://docs.confluent.io/platform/current/schema-registry/serdes-develop/index.html#subject-name-strategy) + to infer the messages schema. + You have to define `x-value.subject.name.strategy` to + `io.confluent.kafka.serializers.subject.RecordNameStrategy` in your + producer to use the schema we manage. + The schema below illustrates how Costing Request messages are + handled. + ![](https://user-images.githubusercontent.com/5501911/188920831-689cec5f-8dc3-460b-8794-0b54ec8b0ac8.png) + parameters: + env: + $ref: "#/components/parameters/Env" + version: + $ref: "#/components/parameters/Version" + bindings: + kafka: + replicas: 3 + partitions: 3 + topicConfiguration + cleanup.policy: delete + retention.ms: 7 days + messages: + costingRequest: + $ref: "#/components/messages/costingRequestV1" + + + + + + costingResponse: + address: "adeo-{env}-case-study-COSTING-RESPONSE-{version}" + description: > + This topic is used to REPLY Costing Requests and is targeted by the + `REPLY_TOPIC` header. + **You must grant PUBLISH access to our `svc-ccr-app` service account.**. + We use the + [**RecordNameStrategy**](https://docs.confluent.io/platform/current/schema-registry/serdes-develop/index.html#subject-name-strategy) + to infer the messages schema. + You have to define `key.subject.name.strategy` and + `x-value.subject.name.strategy` to + `io.confluent.kafka.serializers.subject.RecordNameStrategy` in your + consumer. + The schema below illustrates how Costing Response messages are + handled. + ![](https://user-images.githubusercontent.com/5501911/188920831-689cec5f-8dc3-460b-8794-0b54ec8b0ac8.png) + parameters: + env: + $ref: "#/components/parameters/Env" + version: + $ref: "#/components/parameters/Version" + bindings: + kafka: + groupId: + type: string + description: > + The groupId must be prefixed by your `svc` account, deliver by the + Adeo Kafka team. + This `svc` must have the read access to the topic. + x-key.subject.name.strategy: + type: string + description: > + We use the RecordNameStrategy to infer the messages schema. + Use + `x-key.subject.name.strategy=io.confluent.kafka.serializers.subject.RecordNameStrategy` + in your consumer configuration. + x-value.subject.name.strategy: + type: string + description: > + We use the RecordNameStrategy to infer the messages schema. + Use + `x-value.subject.name.strategy=io.confluent.kafka.serializers.subject.RecordNameStrategy` + in your consumer configuration. + messages: + costingResponse: + $ref: "#/components/messages/costingResponse" + + + + + +operations: + requestCosting: + action: receive + channel: + $ref: '#/channels/costingRequest' + reply: + channel: + $ref: '#/channels/costingResponse' + address: + locaton: '$message.header#/REPLY_TOPIC' + summary: | + [COSTING] Request one or more Costing calculation for any product + description: > + You can try a costing request using our [Conduktor producer + template](https://conduktor.url) + tags: + - name: costing + bindings: + kafka: + groupId: + type: string + description: > + The groupId must be prefixed by your `svc` account, deliver by the + Adeo Kafka team. + This `svc` must have the write access to the topic. + x-value.subject.name.strategy: + type: string + description: > + We use the RecordNameStrategy to infer the messages schema. + Use + `x-value.subject.name.strategy=io.confluent.kafka.serializers.subject.RecordNameStrategy` + in your producer configuration. + getCostingResponse: + action: send + channel: + $ref: '#/channels/costingResponse' + summary: > + [COSTING] Get the costing responses matching an initial Costing + Request. + tags: + - name: costing + + + + + +components: + correlationIds: + costingCorrelationId: + description: > + This correlation ID is used for message tracing and messages + correlation. + This correlation ID is generated at runtime based on the `REQUEST_ID` + and sent to the RESPONSE message. + location: $message.header#/REQUEST_ID + messages: + costingRequestV1: + name: CostingRequestV1 + title: Costing Request V1 + summary: Costing Request V1 inputs. + tags: + - name: costing + schemaFormat: application/vnd.apache.avro;version=1.9.0 + correlationId: + $ref: "#/components/correlationIds/costingCorrelationId" + headers: + type: object + required: + - REQUESTER_ID + - REQUESTER_CODE + - REQUEST_ID + - REPLY_TOPIC + properties: + REQUEST_ID: + $ref: "#/components/schemas/RequestId" + REPLY_TOPIC: + $ref: "#/components/schemas/ReplyTopic" + REQUESTER_ID: + $ref: "#/components/schemas/RequesterId" + REQUESTER_CODE: + $ref: "#/components/schemas/RequesterCode" + payload: + $ref: "https://deploy-preview-921--asyncapi-website.netlify.app/resources/casestudies/adeo/CostingRequestPayload.avsc" + costingResponse: + name: CostingResponse + title: Costing Response + summary: Costing Response ouputs. + tags: + - name: costing + description: > + Please refer to the `CostingResponseKey.avsc` schema, available on [our + github + project](https://github.url/). + schemaFormat: application/vnd.apache.avro;version=1.9.0 + correlationId: + $ref: "#/components/correlationIds/costingCorrelationId" + headers: + type: object + properties: + CALCULATION_ID: + $ref: "#/components/schemas/MessageId" + CORRELATION_ID: + $ref: "#/components/schemas/CorrelationId" + REQUEST_TIMESTAMP: + type: string + format: date-time + description: Timestamp of the costing request + CALCULATION_TIMESTAMP: + type: string + format: date-time + description: Technical timestamp for the costing calculation + bindings: + kafka: + key: + $ref: "https://deploy-preview-921--asyncapi-website.netlify.app/resources/casestudies/adeo/CostingResponseKey.avsc" + payload: + $ref: "https://deploy-preview-921--asyncapi-website.netlify.app/resources/casestudies/adeo/CostingResponsePayload.avsc" + schemas: + RequesterId: + type: string + description: The Costing requester service account used to produce costing request. + example: svc-ecollect-app + RequesterCode: + type: string + description: >- + The Costing requester code (generally the BU Code). The requester code + is useful to get the dedicated context (tenant). + example: 1 + MessageId: + type: string + format: uuid + description: A unique Message ID. + example: 1fa6ef40-8f47-40a8-8cf6-f8607d0066ef + RequestId: + type: string + format: uuid + description: >- + A unique Request ID needed to define a `CORRELATION_ID` for exchanges, + which will be sent back in the Costing Responses. + example: 1fa6ef40-8f47-40a8-8cf6-f8607d0066ef + CorrelationId: + type: string + format: uuid + description: >- + A unique Correlation ID defined from the `REQUEST_ID` or the + `MESSAGE_ID` provided in the Costing Request. + example: 1fa6ef40-8f47-40a8-8cf6-f8607d0066ef + BuCode: + type: string + description: The Business Unit code for which data are applicable. + example: 1 + ReplyTopic: + type: string + description: > + The Kafka topic where to send the Costing Response. This is required for + the [Return Address EIP + pattern](https://www.enterpriseintegrationpatterns.com/patterns/messaging/ReturnAddress.html). + **You must grant WRITE access to our `svc-ccr-app` service account.** + example: adeo-case-study-COSTING-RESPONSE-V1 + ErrorStep: + type: string + description: | + The woker that has thrown the error. + example: EXPOSE_RESULT + ErrorMessage: + type: string + description: | + The error message describing the error. + example: Error message + ErrorCode: + type: string + description: | + The error code. + example: CURRENCY_NOT_FOUND + parameters: + Env: + description: Adeo Kafka Environement for messages publications. + schema: + type: string + enum: + - dev + - sit + - uat1 + - preprod + - prod + Version: + description: the topic version you want to use + schema: + type: string + example: V1 + default: V1 + securitySchemes: + sasl-ssl: + type: plain + x-sasl.jaas.config: >- + org.apache.kafka.common.security.plain.PlainLoginModule required + username="" password=""; + x-security.protocol: SASL_SSL + x-ssl.endpoint.identification.algorithm: https + x-sasl.mechanism: PLAIN + description: > + Use [SASL authentication with SSL + encryption](https://docs.confluent.io/platform/current/security/security_tutorial.html#configure-clients) + to connect to the ADEO Broker. \ No newline at end of file diff --git a/examples/kraken-websocket-request-reply-message-filter-in-reply.yml b/examples/kraken-websocket-request-reply-message-filter-in-reply.yml new file mode 100644 index 000000000..f82a7aa93 --- /dev/null +++ b/examples/kraken-websocket-request-reply-message-filter-in-reply.yml @@ -0,0 +1,357 @@ +asyncapi: 3.0.0 + +info: + title: Kraken Websockets API + version: '1.8.0' + description: | + WebSockets API offers real-time market data updates. WebSockets is a bidirectional protocol offering fastest real-time data, helping you build real-time applications. The public message types presented below do not require authentication. Private-data messages can be subscribed on a separate authenticated endpoint. + + ### General Considerations + + - TLS with SNI (Server Name Indication) is required in order to establish a Kraken WebSockets API connection. See Cloudflare's [What is SNI?](https://www.cloudflare.com/learning/ssl/what-is-sni/) guide for more details. + - All messages sent and received via WebSockets are encoded in JSON format + - All decimal fields (including timestamps) are quoted to preserve precision. + - Timestamps should not be considered unique and not be considered as aliases for transaction IDs. Also, the granularity of timestamps is not representative of transaction rates. + - At least one private message should be subscribed to keep the authenticated client connection open. + - Please use REST API endpoint [AssetPairs](https://www.kraken.com/features/api#get-tradable-pairs) to fetch the list of pairs which can be subscribed via WebSockets API. For example, field 'wsname' gives the supported pairs name which can be used to subscribe. + - Cloudflare imposes a connection/re-connection rate limit (per IP address) of approximately 150 attempts per rolling 10 minutes. If this is exceeded, the IP is banned for 10 minutes. + - Recommended reconnection behaviour is to (1) attempt reconnection instantly up to a handful of times if the websocket is dropped randomly during normal operation but (2) after maintenance or extended downtime, attempt to reconnect no more quickly than once every 5 seconds. There is no advantage to reconnecting more rapidly after maintenance during cancel_only mode. + + +channels: + currencyExchange: + address: / + messages: + ping: + $ref: '#/components/messages/ping' + pong: + $ref: '#/components/messages/pong' + heartbeat: + $ref: '#/components/messages/heartbeat' + systemStatus: + $ref: '#/components/messages/systemStatus' + subscriptionStatus: + $ref: '#/components/messages/subscriptionStatus' + subscribe: + $ref: '#/components/messages/subscribe' + unsubscribe: + $ref: '#/components/messages/unsubscribe' + + +operations: + pingPong: + action: send + channel: + $ref: '#/channels/currencyExchange' + reply: + channel: + $ref: '#/channels/currencyExchange' + messages: + $ref: '#/components/messages/ping' + heartbeat: + action: receive + channel: + $ref: '#/channels/currencyExchange' + systemStatus: + action: receive + channel: + $ref: '#/channels/currencyExchange' + subscribe: + action: send + channel: + $ref: '#/channels/currencyExchange' + reply: + channel: + $ref: '#/channels/currencyExchange' + messages: + $ref: '#/components/messages/subscriptionStatus' + unsubscribe: + action: send + channel: + $ref: '#/channels/currencyExchange' + reply: + channel: + $ref: '#/channels/currencyExchange' + messages: + $ref: '#/components/messages/subscriptionStatus' + + +components: + messages: + ping: + summary: Ping server to determine whether connection is alive + description: Client can ping server to determine whether connection is alive, server responds with pong. This is an application level ping as opposed to default ping in websockets standard which is server initiated + payload: + $ref: '#/components/schemas/ping' + correlationId: + location: $message.payload#/reqid + + pong: + summary: Pong is a response to ping message + description: Server pong response to a ping to determine whether connection is alive. This is an application level pong as opposed to default pong in websockets standard which is sent by client in response to a ping + payload: + $ref: '#/components/schemas/pong' + correlationId: + location: $message.payload#/reqid + + subscribe: + description: Subscribe to a topic on a single or multiple currency pairs. + payload: + $ref: '#/components/schemas/subscribe' + correlationId: + location: $message.payload#/reqid + unsubscribe: + description: Unsubscribe, can specify a channelID or multiple currency pairs. + payload: + $ref: '#/components/schemas/unsubscribe' + correlationId: + location: $message.payload#/reqid + subscriptionStatus: + description: Subscription status response to subscribe, unsubscribe or exchange initiated unsubscribe. + payload: + $ref: '#/components/schemas/subscriptionStatus' + examples: + - payload: + channelID: 10001 + channelName: ohlc-5 + event: subscriptionStatus + pair: XBT/EUR + reqid: 42 + status: unsubscribed + subscription: + interval: 5 + name: ohlc + - payload: + errorMessage: Subscription depth not supported + event: subscriptionStatus + pair: XBT/USD + status: error + subscription: + depth: 42 + name: book + + systemStatus: + description: Status sent on connection or system status changes. + payload: + $ref: '#/components/schemas/systemStatus' + + heartbeat: + description: Server heartbeat sent if no subscription traffic within 1 second (approximately) + payload: + $ref: '#/components/schemas/heartbeat' + + + schemas: + ping: + type: object + properties: + event: + type: string + const: ping + reqid: + $ref: '#/components/schemas/reqid' + required: + - event + heartbeat: + type: object + properties: + event: + type: string + const: heartbeat + pong: + type: object + properties: + event: + type: string + const: pong + reqid: + $ref: '#/components/schemas/reqid' + systemStatus: + type: object + properties: + event: + type: string + const: systemStatus + connectionID: + type: integer + description: The ID of the connection + status: + $ref: '#/components/schemas/status' + version: + type: string + status: + type: string + enum: + - online + - maintenance + - cancel_only + - limit_only + - post_only + subscribe: + type: object + properties: + event: + type: string + const: subscribe + reqid: + $ref: '#/components/schemas/reqid' + pair: + $ref: '#/components/schemas/pair' + subscription: + type: object + properties: + depth: + $ref: '#/components/schemas/depth' + interval: + $ref: '#/components/schemas/interval' + name: + $ref: '#/components/schemas/name' + ratecounter: + $ref: '#/components/schemas/ratecounter' + snapshot: + $ref: '#/components/schemas/snapshot' + token: + $ref: '#/components/schemas/token' + required: + - name + required: + - event + unsubscribe: + type: object + properties: + event: + type: string + const: unsubscribe + reqid: + $ref: '#/components/schemas/reqid' + pair: + $ref: '#/components/schemas/pair' + subscription: + type: object + properties: + depth: + $ref: '#/components/schemas/depth' + interval: + $ref: '#/components/schemas/interval' + name: + $ref: '#/components/schemas/name' + token: + $ref: '#/components/schemas/token' + required: + - name + required: + - event + subscriptionStatus: + type: object + oneOf: + - $ref: '#/components/schemas/subscriptionStatusError' + - $ref: '#/components/schemas/subscriptionStatusSuccess' + subscriptionStatusError: + allOf: + - properties: + errorMessage: + type: string + required: + - errorMessage + - $ref: '#/components/schemas/subscriptionStatusCommon' + subscriptionStatusSuccess: + allOf: + - properties: + channelID: + type: integer + description: ChannelID on successful subscription, applicable to public messages only. + channelName: + type: string + description: Channel Name on successful subscription. For payloads 'ohlc' and 'book', respective interval or depth will be added as suffix. + required: + - channelID + - channelName + - $ref: '#/components/schemas/subscriptionStatusCommon' + subscriptionStatusCommon: + type: object + required: + - event + properties: + event: + type: string + const: subscriptionStatus + reqid: + $ref: '#/components/schemas/reqid' + pair: + $ref: '#/components/schemas/pair' + status: + $ref: '#/components/schemas/status' + subscription: + required: + - name + type: object + properties: + depth: + $ref: '#/components/schemas/depth' + interval: + $ref: '#/components/schemas/interval' + maxratecount: + $ref: '#/components/schemas/maxratecount' + name: + $ref: '#/components/schemas/name' + token: + $ref: '#/components/schemas/token' + interval: + type: integer + description: Time interval associated with ohlc subscription in minutes. + default: 1 + enum: + - 1 + - 5 + - 15 + - 30 + - 60 + - 240 + - 1440 + - 10080 + - 21600 + name: + type: string + description: The name of the channel you subscribe too. + enum: + - book + - ohlc + - openOrders + - ownTrades + - spread + - ticker + - trade + token: + type: string + description: base64-encoded authentication token for private-data endpoints. + depth: + type: integer + default: 10 + enum: + - 10 + - 25 + - 100 + - 500 + - 1000 + description: Depth associated with book subscription in number of levels each side. + maxratecount: + type: integer + description: Max rate-limit budget. Compare to the ratecounter field in the openOrders updates to check whether you are approaching the rate limit. + ratecounter: + type: boolean + default: false + description: Whether to send rate-limit counter in updates (supported only for openOrders subscriptions) + snapshot: + type: boolean + default: true + description: Whether to send historical feed data snapshot upon subscription (supported only for ownTrades subscriptions) + reqid: + type: integer + description: client originated ID reflected in response message. + pair: + type: array + description: Array of currency pairs. + items: + type: string + description: Format of each pair is "A/B", where A and B are ISO 4217-A3 for standardized assets and popular unique symbol if not standardized. + pattern: '[A-Z\s]+\/[A-Z\s]+' \ No newline at end of file diff --git a/examples/kraken-websocket-request-reply-multiple-channels.yml b/examples/kraken-websocket-request-reply-multiple-channels.yml new file mode 100644 index 000000000..4bf3bf570 --- /dev/null +++ b/examples/kraken-websocket-request-reply-multiple-channels.yml @@ -0,0 +1,372 @@ +asyncapi: 3.0.0 + +info: + title: Kraken Websockets API + version: '1.8.0' + description: | + WebSockets API offers real-time market data updates. WebSockets is a bidirectional protocol offering fastest real-time data, helping you build real-time applications. The public message types presented below do not require authentication. Private-data messages can be subscribed on a separate authenticated endpoint. + + ### General Considerations + + - TLS with SNI (Server Name Indication) is required in order to establish a Kraken WebSockets API connection. See Cloudflare's [What is SNI?](https://www.cloudflare.com/learning/ssl/what-is-sni/) guide for more details. + - All messages sent and received via WebSockets are encoded in JSON format + - All decimal fields (including timestamps) are quoted to preserve precision. + - Timestamps should not be considered unique and not be considered as aliases for transaction IDs. Also, the granularity of timestamps is not representative of transaction rates. + - At least one private message should be subscribed to keep the authenticated client connection open. + - Please use REST API endpoint [AssetPairs](https://www.kraken.com/features/api#get-tradable-pairs) to fetch the list of pairs which can be subscribed via WebSockets API. For example, field 'wsname' gives the supported pairs name which can be used to subscribe. + - Cloudflare imposes a connection/re-connection rate limit (per IP address) of approximately 150 attempts per rolling 10 minutes. If this is exceeded, the IP is banned for 10 minutes. + - Recommended reconnection behaviour is to (1) attempt reconnection instantly up to a handful of times if the websocket is dropped randomly during normal operation but (2) after maintenance or extended downtime, attempt to reconnect no more quickly than once every 5 seconds. There is no advantage to reconnecting more rapidly after maintenance during cancel_only mode. + + +channels: + ping: + address: / + messages: + ping: + $ref: '#/components/messages/ping' + pong: + address: / + messages: + pong: + $ref: '#/components/messages/pong' + + heartbeat: + address: / + messages: + heartbeat: + $ref: '#/components/messages/heartbeat' + + systemStatus: + address: / + messages: + systemStatus: + $ref: '#/components/messages/systemStatus' + + subscriptionStatus: + address: / + messages: + subscriptionStatus: + $ref: '#/components/messages/subscriptionStatus' + subscribe: + address: / + messages: + subscribe: + $ref: '#/components/messages/subscribe' + unsubscribe: + address: / + messages: + unsubscribe: + $ref: '#/components/messages/unsubscribe' + + +operations: + pingPong: + action: send + channel: + $ref: '#/channels/ping' + reply: + channel: + $ref: '#/channels/pong' + heartbeat: + action: receive + channel: + $ref: '#/channels/heartbeat' + systemStatus: + action: receive + channel: + $ref: '#/channels/systemStatus' + subscribe: + action: send + channel: + $ref: '#/channels/subscribe' + reply: + channel: + $ref: '#/channels/subscriptionStatus' + unsubscribe: + action: send + channel: + $ref: '#/channels/unsubscribe' + reply: + channel: + $ref: '#/channels/subscriptionStatus' + + +components: + messages: + ping: + summary: Ping server to determine whether connection is alive + description: Client can ping server to determine whether connection is alive, server responds with pong. This is an application level ping as opposed to default ping in websockets standard which is server initiated + payload: + $ref: '#/components/schemas/ping' + correlationId: + location: $message.payload#/reqid + + pong: + summary: Pong is a response to ping message + description: Server pong response to a ping to determine whether connection is alive. This is an application level pong as opposed to default pong in websockets standard which is sent by client in response to a ping + payload: + $ref: '#/components/schemas/pong' + correlationId: + location: $message.payload#/reqid + + subscribe: + description: Subscribe to a topic on a single or multiple currency pairs. + payload: + $ref: '#/components/schemas/subscribe' + correlationId: + location: $message.payload#/reqid + unsubscribe: + description: Unsubscribe, can specify a channelID or multiple currency pairs. + payload: + $ref: '#/components/schemas/unsubscribe' + correlationId: + location: $message.payload#/reqid + subscriptionStatus: + description: Subscription status response to subscribe, unsubscribe or exchange initiated unsubscribe. + payload: + $ref: '#/components/schemas/subscriptionStatus' + examples: + - payload: + channelID: 10001 + channelName: ohlc-5 + event: subscriptionStatus + pair: XBT/EUR + reqid: 42 + status: unsubscribed + subscription: + interval: 5 + name: ohlc + - payload: + errorMessage: Subscription depth not supported + event: subscriptionStatus + pair: XBT/USD + status: error + subscription: + depth: 42 + name: book + + systemStatus: + description: Status sent on connection or system status changes. + payload: + $ref: '#/components/schemas/systemStatus' + + heartbeat: + description: Server heartbeat sent if no subscription traffic within 1 second (approximately) + payload: + $ref: '#/components/schemas/heartbeat' + + + schemas: + ping: + type: object + properties: + event: + type: string + const: ping + reqid: + $ref: '#/components/schemas/reqid' + required: + - event + heartbeat: + type: object + properties: + event: + type: string + const: heartbeat + pong: + type: object + properties: + event: + type: string + const: pong + reqid: + $ref: '#/components/schemas/reqid' + systemStatus: + type: object + properties: + event: + type: string + const: systemStatus + connectionID: + type: integer + description: The ID of the connection + status: + $ref: '#/components/schemas/status' + version: + type: string + status: + type: string + enum: + - online + - maintenance + - cancel_only + - limit_only + - post_only + subscribe: + type: object + properties: + event: + type: string + const: subscribe + reqid: + $ref: '#/components/schemas/reqid' + pair: + $ref: '#/components/schemas/pair' + subscription: + type: object + properties: + depth: + $ref: '#/components/schemas/depth' + interval: + $ref: '#/components/schemas/interval' + name: + $ref: '#/components/schemas/name' + ratecounter: + $ref: '#/components/schemas/ratecounter' + snapshot: + $ref: '#/components/schemas/snapshot' + token: + $ref: '#/components/schemas/token' + required: + - name + required: + - event + unsubscribe: + type: object + properties: + event: + type: string + const: unsubscribe + reqid: + $ref: '#/components/schemas/reqid' + pair: + $ref: '#/components/schemas/pair' + subscription: + type: object + properties: + depth: + $ref: '#/components/schemas/depth' + interval: + $ref: '#/components/schemas/interval' + name: + $ref: '#/components/schemas/name' + token: + $ref: '#/components/schemas/token' + required: + - name + required: + - event + subscriptionStatus: + type: object + oneOf: + - $ref: '#/components/schemas/subscriptionStatusError' + - $ref: '#/components/schemas/subscriptionStatusSuccess' + subscriptionStatusError: + allOf: + - properties: + errorMessage: + type: string + required: + - errorMessage + - $ref: '#/components/schemas/subscriptionStatusCommon' + subscriptionStatusSuccess: + allOf: + - properties: + channelID: + type: integer + description: ChannelID on successful subscription, applicable to public messages only. + channelName: + type: string + description: Channel Name on successful subscription. For payloads 'ohlc' and 'book', respective interval or depth will be added as suffix. + required: + - channelID + - channelName + - $ref: '#/components/schemas/subscriptionStatusCommon' + subscriptionStatusCommon: + type: object + required: + - event + properties: + event: + type: string + const: subscriptionStatus + reqid: + $ref: '#/components/schemas/reqid' + pair: + $ref: '#/components/schemas/pair' + status: + $ref: '#/components/schemas/status' + subscription: + required: + - name + type: object + properties: + depth: + $ref: '#/components/schemas/depth' + interval: + $ref: '#/components/schemas/interval' + maxratecount: + $ref: '#/components/schemas/maxratecount' + name: + $ref: '#/components/schemas/name' + token: + $ref: '#/components/schemas/token' + interval: + type: integer + description: Time interval associated with ohlc subscription in minutes. + default: 1 + enum: + - 1 + - 5 + - 15 + - 30 + - 60 + - 240 + - 1440 + - 10080 + - 21600 + name: + type: string + description: The name of the channel you subscribe too. + enum: + - book + - ohlc + - openOrders + - ownTrades + - spread + - ticker + - trade + token: + type: string + description: base64-encoded authentication token for private-data endpoints. + depth: + type: integer + default: 10 + enum: + - 10 + - 25 + - 100 + - 500 + - 1000 + description: Depth associated with book subscription in number of levels each side. + maxratecount: + type: integer + description: Max rate-limit budget. Compare to the ratecounter field in the openOrders updates to check whether you are approaching the rate limit. + ratecounter: + type: boolean + default: false + description: Whether to send rate-limit counter in updates (supported only for openOrders subscriptions) + snapshot: + type: boolean + default: true + description: Whether to send historical feed data snapshot upon subscription (supported only for ownTrades subscriptions) + reqid: + type: integer + description: client originated ID reflected in response message. + pair: + type: array + description: Array of currency pairs. + items: + type: string + description: Format of each pair is "A/B", where A and B are ISO 4217-A3 for standardized assets and popular unique symbol if not standardized. + pattern: '[A-Z\s]+\/[A-Z\s]+' \ No newline at end of file diff --git a/spec/asyncapi.md b/spec/asyncapi.md index 4454d3364..d3e603846 100644 --- a/spec/asyncapi.md +++ b/spec/asyncapi.md @@ -95,6 +95,8 @@ Aside from the issues mentioned above, there may also be infrastructure configur - [Operations Object](#operationsObject) - [Operation Object](#operationObject) - [Operation Trait Object](#operationTraitObject) + - [Operation Reply Object](#operationReplyObject) + - [Operation Reply Address Object](#operationReplyAddressObject) - [Message Object](#messageObject) - [Message Trait Object](#messageTraitObject) - [Message Example Object](#messageExampleObject) @@ -836,6 +838,8 @@ Field Name | Type | Description externalDocs | [External Documentation Object](#externalDocumentationObject) \| [Reference Object](#referenceObject) | Additional external documentation for this operation. bindings | [Operation Bindings Object](#operationBindingsObject) \| [Reference Object](#referenceObject) | A map where the keys describe the name of the protocol and the values describe protocol-specific definitions for the operation. traits | [[Operation Trait Object](#operationTraitObject) | [Reference Object](#referenceObject) ] | A list of traits to apply to the operation object. Traits MUST be merged into the operation object using the [JSON Merge Patch](https://tools.ietf.org/html/rfc7386) algorithm in the same order they are defined here. +messages | [[Reference Object](#referenceObject)] | A list of `$ref` pointers pointing to the supported [Message Objects](#messageObject) that can be processed by this operation. It MUST contain a subset of the messages defined in the [channel referenced in this operation](#operationObjectChannel). **Every message processed by this operation MUST be valid against one, and only one, of the [message objects](#messageObject) referenced in this list.** Please note the `messages` property value MUST be a list of [Reference Objects](#referenceObject) and, therefore, MUST NOT contain [Message Objects](#messageObject). However, it is RECOMMENDED that parsers (or other software) dereference this property for a better development experience. +reply | [Operation Reply Object](#operationReplyObject) | [Reference Object](#referenceObject) | The definition of the reply in a request-reply operation. This object MAY be extended with [Specification Extensions](#specificationExtensions). @@ -870,7 +874,21 @@ This object MAY be extended with [Specification Extensions](#specificationExtens }, "traits": [ { "$ref": "#/components/operationTraits/kafka" } - ] + ], + "messages": [ + { "$ref": "/components/messages/userSignedUp" } + ], + "reply": { + "address": { + "location": "$message.header#/replyTo" + }, + "channel": { + "$ref": "#/channels/userSignupReply" + }, + "messages": [ + { "$ref": "/components/messages/userSignedUpReply" } + ], + } } ``` @@ -894,6 +912,15 @@ bindings: ack: false traits: - $ref: "#/components/operationTraits/kafka" +messages: + - $ref: '#/components/messages/userSignedUp' +reply: + address: + location: '$message.header#/replyTo' + channel: + $ref: '#/channels/userSignupReply' + messages: + - $ref: '#/components/messages/userSignedUpReply' ``` @@ -940,6 +967,51 @@ bindings: +#### Operation Reply Object + +Describes the reply part that MAY be applied to an Operation Object. If an operation implements the request/reply pattern, the reply object represents the response message. + +##### Fixed Fields + +Field Name | Type | Description +---|:---:|--- +address | [Operation Reply Address Object](#operationReplyAddressObject) | [Reference Object](#referenceObject) | Definition of the address that implementations MUST use for the reply. +channel | [Reference Object](#referenceObject) | A `$ref` pointer to the definition of the channel in which this operation is performed. When [address](#operationReplyAddressObject) is specified, the [`address` property](#channelObjectAddress) of the channel referenced by this property MUST be either `null` or not defined. Please note the `channel` property value MUST be a [Reference Object](#referenceObject) and, therefore, MUST NOT contain a [Channel Object](#channelObject). However, it is RECOMMENDED that parsers (or other software) dereference this property for a better development experience. +messages | [[Reference Object](#referenceObject)] | A list of `$ref` pointers pointing to the supported [Message Objects](#messageObject) that can be processed by this operation as reply. It MUST contain a subset of the messages defined in the [channel referenced in this operation reply](#operationObjectChannel). **Every message processed by this operation MUST be valid against one, and only one, of the [message objects](#messageObject) referenced in this list.** Please note the `messages` property value MUST be a list of [Reference Objects](#referenceObject) and, therefore, MUST NOT contain [Message Objects](#messageObject). However, it is RECOMMENDED that parsers (or other software) dereference this property for a better development experience. + +This object MAY be extended with [Specification Extensions](#specificationExtensions). + +#### Operation Reply Address Object + +An object that specifies where an operation has to send the reply. + +For specifying and computing the location of a reply address, a [runtime expression](#runtimeExpression) is used. + + +##### Fixed Fields + +Field Name | Type | Description +---|:---|--- +description | `string` | An optional description of the address. [CommonMark syntax](https://spec.commonmark.org/) can be used for rich text representation. +location | `string` | **REQUIRED.** A [runtime expression](#runtimeExpression) that specifies the location of the reply address. + +This object MAY be extended with [Specification Extensions](#specificationExtensions). + +##### Examples + +```json +{ + "description": "Consumer inbox", + "location": "$message.header#/replyTo" +} +``` + +```yaml +description: Consumer Inbox +location: $message.header#/replyTo +``` + + #### Parameters Object Describes a map of parameters included in a channel name. @@ -1569,6 +1641,8 @@ Field Name | Type | Description serverVariables | Map[`string`, [Server Variable Object](#serverVariableObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Server Variable Objects](#serverVariableObject). parameters | Map[`string`, [Parameter Object](#parameterObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Parameter Objects](#parameterObject). correlationIds | Map[`string`, [Correlation ID Object](#correlationIdObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Correlation ID Objects](#correlationIdObject). +replies | Map[`string`, [Operation Reply Object](#operationReplyObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Operation Reply Objects](#operationReplyObject). + replyAddresses | Map[`string`, [Operation Reply Address Object](#operationReplyAddressObject) | [Reference Object](#referenceObject)] | An object to hold reusable [Operation Reply Address Objects](#operationReplyAddressObject). externalDocs | Map[`string`, [External Documentation Object](#externalDocumentationObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [External Documentation Objects](#externalDocumentationObject). tags | Map[`string`, [Tag Object](#tagObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Tag Objects](#tagObject). operationTraits | Map[`string`, [Operation Trait Object](#operationTraitObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Operation Trait Objects](#operationTraitObject). From 385d65158d53d261d41154be26f81921c301f8eb Mon Sep 17 00:00:00 2001 From: nickshoe <32668766+nickshoe@users.noreply.github.com> Date: Wed, 26 Apr 2023 16:05:43 +0200 Subject: [PATCH 16/41] docs: fixes Operation Object link pointing to Channel Object doc (#929) --- spec/asyncapi.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/spec/asyncapi.md b/spec/asyncapi.md index d3e603846..48da08dd9 100644 --- a/spec/asyncapi.md +++ b/spec/asyncapi.md @@ -769,7 +769,7 @@ Holds a dictionary with all the [operations](#operationObject) this application Field Pattern | Type | Description ---|:---:|--- -{operationId} | [Operation Object](#channelObject) \| [Reference Object](#referenceObject) | The operation this application MUST implement. The field name (`operationId`) MUST be a string used to identify the operation in the document where it is defined, and its value is **case-sensitive**. Tools and libraries MAY use the `operationId` to uniquely identify an operation, therefore, it is RECOMMENDED to follow common programming naming conventions. +{operationId} | [Operation Object](#operationObject) \| [Reference Object](#referenceObject) | The operation this application MUST implement. The field name (`operationId`) MUST be a string used to identify the operation in the document where it is defined, and its value is **case-sensitive**. Tools and libraries MAY use the `operationId` to uniquely identify an operation, therefore, it is RECOMMENDED to follow common programming naming conventions. ##### Operations Object Example From 242c0f691e3787edf1620022377eda89da47be6d Mon Sep 17 00:00:00 2001 From: Lukasz Gornicki Date: Tue, 23 May 2023 16:10:12 +0200 Subject: [PATCH 17/41] docs: remove info about compatibility with openapi (#933) --- spec/asyncapi.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/spec/asyncapi.md b/spec/asyncapi.md index 48da08dd9..d9c997171 100644 --- a/spec/asyncapi.md +++ b/spec/asyncapi.md @@ -4,9 +4,9 @@ This version is not yet ready to be used. We're currently working on it. If you # AsyncAPI Specification -#### Disclaimer +#### Attribution -Part of this content has been taken from the great work done by the folks at the [OpenAPI Initiative](https://openapis.org). Mainly because **it's a great work** and we want to keep as much compatibility as possible with the [OpenAPI Specification](https://github.com/OAI/OpenAPI-Specification). +Part of this content has been taken from the great work done by the folks at the [OpenAPI Initiative](https://openapis.org). #### Version 3.0.0 From 1987e69a0e44f5e9526edc0e9f2df3ed19e8565f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Fran=20M=C3=A9ndez?= Date: Mon, 29 May 2023 08:52:03 +0200 Subject: [PATCH 18/41] feat: simplify parameter object (#935) --- spec/asyncapi.md | 80 ++++++++++++++++-------------------------------- 1 file changed, 27 insertions(+), 53 deletions(-) diff --git a/spec/asyncapi.md b/spec/asyncapi.md index d9c997171..c7d3dc849 100644 --- a/spec/asyncapi.md +++ b/spec/asyncapi.md @@ -1014,48 +1014,34 @@ location: $message.header#/replyTo #### Parameters Object -Describes a map of parameters included in a channel name. +Describes a map of parameters included in a channel address. -This map MUST contain all the parameters used in the parent channel name. +This map MUST contain all the parameters used in the parent channel address. ##### Patterned Fields Field Pattern | Type | Description ---|:---:|--- -`^[A-Za-z0-9_\-]+$` | [Parameter Object](#parameterObject) | [Reference Object](#referenceObject) | The key represents the name of the parameter. It MUST match the parameter name used in the parent channel name. +`^[A-Za-z0-9_\-]+$` | [Parameter Object](#parameterObject) | [Reference Object](#referenceObject) | The key represents the name of the parameter. It MUST match the parameter name used in the parent channel address. ##### Parameters Object Example ```json { - "user/{userId}/signup": { - "parameters": { - "userId": { - "description": "Id of the user.", - "schema": { - "type": "string" - } - } - }, - "subscribe": { - "message": { - "$ref": "#/components/messages/userSignedUp" - } + "address": "user/{userId}/signedup", + "parameters": { + "userId": { + "description": "Id of the user." } } } ``` ```yaml -user/{userId}/signup: - parameters: - userId: - description: Id of the user. - schema: - type: string - subscribe: - message: - $ref: "#/components/messages/userSignedUp" +address: user/{userId}/signedup +parameters: + userId: + description: Id of the user. ``` @@ -1064,15 +1050,17 @@ user/{userId}/signup: #### Parameter Object -Describes a parameter included in a channel name. +Describes a parameter included in a channel address. ##### Fixed Fields Field Name | Type | Description ---|:---:|--- -description | `string` | A verbose explanation of the parameter. [CommonMark syntax](https://spec.commonmark.org/) can be used for rich text representation. -schema | [Schema Object](#schemaObject) \| [Reference Object](#referenceObject) | Definition of the parameter. -location | `string` | A [runtime expression](#runtimeExpression) that specifies the location of the parameter value. Even when a definition for the target field exists, it MUST NOT be used to validate this parameter but, instead, the `schema` property MUST be used. +enum | [`string`] | An enumeration of string values to be used if the substitution options are from a limited set. +default | `string` | The default value to use for substitution, and to send, if an alternate value is _not_ supplied. +description | `string` | An optional description for the parameter. [CommonMark syntax](https://spec.commonmark.org/) MAY be used for rich text representation. +examples | [`string`] | An array of examples of the parameter value. +location | `string` | A [runtime expression](#runtimeExpression) that specifies the location of the parameter value. This object MAY be extended with [Specification Extensions](#specificationExtensions). @@ -1080,36 +1068,22 @@ This object MAY be extended with [Specification Extensions](#specificationExtens ```json { - "user/{userId}/signup": { - "parameters": { - "userId": { - "description": "Id of the user.", - "schema": { - "type": "string" - }, - "location": "$message.payload#/user/id" - } - }, - "subscribe": { - "message": { - "$ref": "#/components/messages/userSignedUp" - } + "address": "user/{userId}/signedup", + "parameters": { + "userId": { + "description": "Id of the user.", + "location": "$message.payload#/user/id" } } } ``` ```yaml -user/{userId}/signup: - parameters: - userId: - description: Id of the user. - schema: - type: string - location: $message.payload#/user/id - subscribe: - message: - $ref: "#/components/messages/userSignedUp" +address: user/{userId}/signedup +parameters: + userId: + description: Id of the user. + location: $message.payload#/user/id ``` From 3c61f49118e3a200a104a5bfd2797eb7fad594aa Mon Sep 17 00:00:00 2001 From: Heiko Henning Date: Tue, 30 May 2023 09:46:24 +0200 Subject: [PATCH 19/41] feat: allow defining schema format other than default (#910) Co-authored-by: Lukasz Gornicki --- spec/asyncapi.md | 87 +++++++++++++++++++++++++++++++----------------- 1 file changed, 56 insertions(+), 31 deletions(-) diff --git a/spec/asyncapi.md b/spec/asyncapi.md index c7d3dc849..7de5b16a5 100644 --- a/spec/asyncapi.md +++ b/spec/asyncapi.md @@ -105,6 +105,7 @@ Aside from the issues mentioned above, there may also be infrastructure configur - [External Documentation Object](#externalDocumentationObject) - [Components Object](#componentsObject) - [Reference Object](#referenceObject) + - [Multi Format Schema Object](#multiFormatSchemaObject) - [Schema Object](#schemaObject) - [Security Scheme Object](#securitySchemeObject) - [OAuth Flows Object](#oauth-flows-object) @@ -1227,10 +1228,9 @@ Describes a message received on a given channel and operation. Field Name | Type | Description ---|:---:|--- messageId | `string` | Unique string used to identify the message. The id MUST be unique among all messages described in the API. The messageId value is **case-sensitive**. Tools and libraries MAY use the messageId to uniquely identify a message, therefore, it is RECOMMENDED to follow common programming naming conventions. -headers | [Schema Object](#schemaObject) | [Reference Object](#referenceObject) | Schema definition of the application headers. Schema MUST be of type "object". It **MUST NOT** define the protocol headers. -payload | `any` | Definition of the message payload. It can be of any type but defaults to [Schema object](#schemaObject). It must match the schema format, including encoding type - e.g Avro should be inlined as either a YAML or JSON object NOT a string to be parsed as YAML or JSON. +headers | [Multi Format Schema Object](#multiFormatSchemaObject) | [Schema Object](#schemaObject) | [Reference Object](#referenceObject) | Schema definition of the application headers. Schema MUST be of type "object". It **MUST NOT** define the protocol headers. If this is a [Schema Object](#schemaObject), then the `schemaFormat` will be assumed to be "application/vnd.aai.asyncapi+json;version=`asyncapi`" where the version is equal to the [AsyncAPI Version String](#A2SVersionString). +payload | [Multi Format Schema Object](#multiFormatSchemaObject) | [Schema Object](#schemaObject) | [Reference Object](#referenceObject) | Definition of the message payload. If this is a [Schema Object](#schemaObject), then the `schemaFormat` will be assumed to be "application/vnd.aai.asyncapi+json;version=`asyncapi`" where the version is equal to the [AsyncAPI Version String](#A2SVersionString). correlationId | [Correlation ID Object](#correlationIdObject) | [Reference Object](#referenceObject) | Definition of the correlation ID used for message tracing or matching. -schemaFormat | `string` | A string containing the name of the schema format used to define the message payload. If omitted, implementations should parse the payload as a [Schema object](#schemaObject). When the payload is defined using a `$ref` to a remote file, it is RECOMMENDED the schema format includes the file encoding type to allow implementations to parse the file correctly. E.g., adding `+yaml` if content type is `application/vnd.apache.avro` results in `application/vnd.apache.avro+yaml`.

Check out the [supported schema formats table](#messageObjectSchemaFormatTable) for more information. Custom values are allowed but their implementation is OPTIONAL. A custom value MUST NOT refer to one of the schema formats listed in the [table](#messageObjectSchemaFormatTable). contentType | `string` | The content type to use when encoding/decoding a message's payload. The value MUST be a specific media type (e.g. `application/json`). When omitted, the value MUST be the one specified on the [defaultContentType](#defaultContentTypeString) field. name | `string` | A machine-friendly name for the message. title | `string` | A human-friendly title for the message. @@ -1244,24 +1244,6 @@ Field Name | Type | Description This object MAY be extended with [Specification Extensions](#specificationExtensions). -##### Schema formats table - -The following table contains a set of values that every implementation MUST support. - -Name | Allowed values | Notes ----|:---:|--- -[AsyncAPI 3.0.0 Schema Object](#schemaObject) | `application/vnd.aai.asyncapi;version=3.0.0`, `application/vnd.aai.asyncapi+json;version=3.0.0`, `application/vnd.aai.asyncapi+yaml;version=3.0.0` | This is the default when a `schemaFormat` is not provided. -[JSON Schema Draft 07](https://json-schema.org/specification-links.html#draft-7) | `application/schema+json;version=draft-07`, `application/schema+yaml;version=draft-07` | - -The following table contains a set of values that every implementation is RECOMMENDED to support. - -Name | Allowed values | Notes ----|:---:|--- -[Avro 1.9.0 schema](https://avro.apache.org/docs/1.9.0/spec.html#schemas) | `application/vnd.apache.avro;version=1.9.0`, `application/vnd.apache.avro+json;version=1.9.0`, `application/vnd.apache.avro+yaml;version=1.9.0` | -[OpenAPI 3.0.0 Schema Object](https://github.com/OAI/OpenAPI-Specification/blob/master/versions/3.0.0.md#schemaObject) | `application/vnd.oai.openapi;version=3.0.0`, `application/vnd.oai.openapi+json;version=3.0.0`, `application/vnd.oai.openapi+yaml;version=3.0.0` | -[RAML 1.0 data type](https://github.com/raml-org/raml-spec/blob/master/versions/raml-10/raml-10.md/) | `application/raml+yaml;version=1.0` | - - ##### Message Object Example ```json @@ -1388,9 +1370,11 @@ Example using Avro to define the payload: { "name": "signup" }, { "name": "register" } ], - "schemaFormat": "application/vnd.apache.avro+json;version=1.9.0", "payload": { - "$ref": "path/to/user-create.avsc#/UserCreate" + "schemaFormat": "application/vnd.apache.avro+json;version=1.9.0", + "schema": { + "$ref": "path/to/user-create.avsc#/UserCreate" + } } } ``` @@ -1405,9 +1389,10 @@ tags: - name: user - name: signup - name: register -schemaFormat: 'application/vnd.apache.avro+yaml;version=1.9.0' payload: - $ref: 'path/to/user-create.avsc/#UserCreate' + schemaFormat: 'application/vnd.apache.avro+yaml;version=1.9.0' + schema: + $ref: 'path/to/user-create.avsc/#UserCreate' ``` @@ -1427,9 +1412,8 @@ If you're looking to apply traits to an operation, see the [Operation Trait Obje Field Name | Type | Description ---|:---:|--- messageId | `string` | Unique string used to identify the message. The id MUST be unique among all messages described in the API. The messageId value is **case-sensitive**. Tools and libraries MAY use the messageId to uniquely identify a message, therefore, it is RECOMMENDED to follow common programming naming conventions. -headers | [Schema Object](#schemaObject) | [Reference Object](#referenceObject) | Schema definition of the application headers. Schema MUST be of type "object". It **MUST NOT** define the protocol headers. +headers | [Multi Format Schema Object](#multiFormatSchemaObject) | [Schema Object](#schemaObject) | [Reference Object](#referenceObject) | Schema definition of the application headers. Schema MUST be of type "object". It **MUST NOT** define the protocol headers. If this is a [Schema Object](#schemaObject), then the `schemaFormat` will be assumed to be "application/vnd.aai.asyncapi+json;version=`asyncapi`" where the version is equal to the [AsyncAPI Version String](#A2SVersionString). correlationId | [Correlation ID Object](#correlationIdObject) | [Reference Object](#referenceObject) | Definition of the correlation ID used for message tracing or matching. -schemaFormat | `string` | A string containing the name of the schema format/language used to define the message payload. If omitted, implementations should parse the payload as a [Schema object](#schemaObject). contentType | `string` | The content type to use when encoding/decoding a message's payload. The value MUST be a specific media type (e.g. `application/json`). When omitted, the value MUST be the one specified on the [defaultContentType](#defaultContentTypeString) field. name | `string` | A machine-friendly name for the message. title | `string` | A human-friendly title for the message. @@ -1446,13 +1430,11 @@ This object MAY be extended with [Specification Extensions](#specificationExtens ```json { - "schemaFormat": "application/vnd.apache.avro+json;version=1.9.0", "contentType": "application/json" } ``` ```yaml -schemaFormat: 'application/vnd.apache.avro+yaml;version=1.9.0' contentType: application/json ``` @@ -1465,7 +1447,7 @@ Message Example Object represents an example of a [Message Object](#messageObjec Field Name | Type | Description ---|:---:|--- headers | `Map[string, any]` | The value of this field MUST validate against the [Message Object's headers](#messageObjectHeaders) field. -payload | `any` | The value of this field MUST validate against the [Message Object's payload](#messageObjectPayload) field. +payload | `Map[string, any]` | The value of this field MUST validate against the [Message Object's payload](#messageObjectPayload) field. name | `string` | A machine-friendly name. summary | `string` | A short summary of what the example is about. @@ -1606,7 +1588,7 @@ All objects defined within the components object will have no effect on the API Field Name | Type | Description ---|:---|--- - schemas | Map[`string`, [Schema Object](#schemaObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Schema Objects](#schemaObject). + schemas | Map[`string`, [Multi Format Schema Object](#multiFormatSchemaObject) \| [Schema Object](#schemaObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Schema Object](#schemaObject). If this is a [Schema Object](#schemaObject), then the `schemaFormat` will be assumed to be "application/vnd.aai.asyncapi+json;version=`asyncapi`" where the version is equal to the [AsyncAPI Version String](#A2SVersionString). servers | Map[`string`, [Server Object](#serverObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Server Objects](#serverObject). channels | Map[`string`, [Channel Object](#channelObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Channel Objects](#channelObject). operations | Map[`string`, [Operation Item Object](#operationObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Operation Item Objects](#operationObject). @@ -1669,6 +1651,12 @@ my.org.User "type": "string" } } + }, + "AvroExample": { + "schemaFormat": "application/vnd.apache.avro+json;version=1.9.0", + "schema": { + "$ref": "path/to/user-create.avsc#/UserCreate" + } } }, "servers": { @@ -1791,6 +1779,10 @@ components: format: int64 name: type: string + AvroExample: + schemaFormat: application/vnd.apache.avro+json;version=1.9.0 + schema: + $ref: 'path/to/user-create.avsc/#UserCreate' servers: development: url: "{stage}.in.mycompany.com:{port}" @@ -1856,6 +1848,39 @@ components: maximum: 100 ``` +#### Multi Format Schema Object + +The Multi Format Schema Object represents a schema definition. It differs from the [Schema Object](#schemaObject) in that it supports multiple schema formats or languages (e.g., JSON Schema, Avro, etc.). + +##### Fixed Fields + +Field Name | Type | Description +---|:---:|--- +schemaFormat | `string` | **Required**. A string containing the name of the schema format that is used to define the information. +If `schemaFormat` is missing, it MUST default to `application/vnd.aai.asyncapi+json;version={{asyncapi}}` where `{{version}}` matches the [AsyncAPI Version String](#A2SVersionString). In such a case, this would make the Multi Format Schema Object equivalent to the [Schema Object](#schemaObject). When using [Reference Object](#referenceObject) within the schema, the `schemaFormat` of the resource being referenced MUST match the `schemaFormat` of the schema that contains the initial reference. For example, if you reference Avro `schema`, then `schemaFormat` of referencing resource and the resource being reference MUST match.

Check out the [supported schema formats table](#multiFormatSchemaFormatTable) for more information. Custom values are allowed but their implementation is OPTIONAL. A custom value MUST NOT refer to one of the schema formats listed in the [table](#multiFormatSchemaFormatTable).

When using [Reference Objects](#referenceObject) within the schema, the `schemaFormat` of the referenced resource MUST match the `schemaFormat` of the schema containing the reference. +schema | `any` | **Required**. Definition of the message payload. It can be of any type but defaults to [Schema Object](#schemaObject). It MUST match the schema format defined in [`schemaFormat`](#multiFormatSchemaObjectSchemaFormat), including the encoding type. E.g., Avro should be inlined as either a YAML or JSON object instead of as a string to be parsed as YAML or JSON. Non-JSON-based schemas (e.g., Protobuf or XSD) MUST be inlined as a string. + +This object MAY be extended with [Specification Extensions](#specificationExtensions). + +##### Schema formats table + +The following table contains a set of values that every implementation MUST support. + +Name | Allowed values | Notes +---|:---:|--- +[AsyncAPI 3.0.0 Schema Object](#schemaObject) | `application/vnd.aai.asyncapi;version=3.0.0`, `application/vnd.aai.asyncapi+json;version=3.0.0`, `application/vnd.aai.asyncapi+yaml;version=3.0.0` | This is the default when a `schemaFormat` is not provided. +[JSON Schema Draft 07](https://json-schema.org/specification-links.html#draft-7) | `application/schema+json;version=draft-07`, `application/schema+yaml;version=draft-07` | + +The following table contains a set of values that every implementation is RECOMMENDED to support. + +Name | Allowed values | Notes +---|:---:|--- +[Avro 1.9.0 schema](https://avro.apache.org/docs/1.9.0/spec.html#schemas) | `application/vnd.apache.avro;version=1.9.0`, `application/vnd.apache.avro+json;version=1.9.0`, `application/vnd.apache.avro+yaml;version=1.9.0` | +[OpenAPI 3.0.0 Schema Object](https://github.com/OAI/OpenAPI-Specification/blob/master/versions/3.0.0.md#schemaObject) | `application/vnd.oai.openapi;version=3.0.0`, `application/vnd.oai.openapi+json;version=3.0.0`, `application/vnd.oai.openapi+yaml;version=3.0.0` | +[RAML 1.0 data type](https://github.com/raml-org/raml-spec/blob/master/versions/raml-10/raml-10.md/) | `application/raml+yaml;version=1.0` | +[Protocol Buffers](https://protobuf.dev/) | `application/vnd.google.protobuf;version=2`, `application/vnd.google.protobuf;version=3` | + + #### Schema Object The Schema Object allows the definition of input and output data types. From 83035abbe92abe82f5ce704266614ac453311233 Mon Sep 17 00:00:00 2001 From: Jonas Lagoni Date: Tue, 13 Jun 2023 18:53:16 +0200 Subject: [PATCH 20/41] chore: fix multiformat schema object table (#943) --- spec/asyncapi.md | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/spec/asyncapi.md b/spec/asyncapi.md index 7de5b16a5..10326e254 100644 --- a/spec/asyncapi.md +++ b/spec/asyncapi.md @@ -1856,8 +1856,7 @@ The Multi Format Schema Object represents a schema definition. It differs from t Field Name | Type | Description ---|:---:|--- -schemaFormat | `string` | **Required**. A string containing the name of the schema format that is used to define the information. -If `schemaFormat` is missing, it MUST default to `application/vnd.aai.asyncapi+json;version={{asyncapi}}` where `{{version}}` matches the [AsyncAPI Version String](#A2SVersionString). In such a case, this would make the Multi Format Schema Object equivalent to the [Schema Object](#schemaObject). When using [Reference Object](#referenceObject) within the schema, the `schemaFormat` of the resource being referenced MUST match the `schemaFormat` of the schema that contains the initial reference. For example, if you reference Avro `schema`, then `schemaFormat` of referencing resource and the resource being reference MUST match.

Check out the [supported schema formats table](#multiFormatSchemaFormatTable) for more information. Custom values are allowed but their implementation is OPTIONAL. A custom value MUST NOT refer to one of the schema formats listed in the [table](#multiFormatSchemaFormatTable).

When using [Reference Objects](#referenceObject) within the schema, the `schemaFormat` of the referenced resource MUST match the `schemaFormat` of the schema containing the reference. +schemaFormat | `string` | **Required**. A string containing the name of the schema format that is used to define the information. If `schemaFormat` is missing, it MUST default to `application/vnd.aai.asyncapi+json;version={{asyncapi}}` where `{{asyncapi}}` matches the [AsyncAPI Version String](#A2SVersionString). In such a case, this would make the Multi Format Schema Object equivalent to the [Schema Object](#schemaObject). When using [Reference Object](#referenceObject) within the schema, the `schemaFormat` of the resource being referenced MUST match the `schemaFormat` of the schema that contains the initial reference. For example, if you reference Avro `schema`, then `schemaFormat` of referencing resource and the resource being reference MUST match.

Check out the [supported schema formats table](#multiFormatSchemaFormatTable) for more information. Custom values are allowed but their implementation is OPTIONAL. A custom value MUST NOT refer to one of the schema formats listed in the [table](#multiFormatSchemaFormatTable).

When using [Reference Objects](#referenceObject) within the schema, the `schemaFormat` of the referenced resource MUST match the `schemaFormat` of the schema containing the reference. schema | `any` | **Required**. Definition of the message payload. It can be of any type but defaults to [Schema Object](#schemaObject). It MUST match the schema format defined in [`schemaFormat`](#multiFormatSchemaObjectSchemaFormat), including the encoding type. E.g., Avro should be inlined as either a YAML or JSON object instead of as a string to be parsed as YAML or JSON. Non-JSON-based schemas (e.g., Protobuf or XSD) MUST be inlined as a string. This object MAY be extended with [Specification Extensions](#specificationExtensions). From d89a1a6678e95949b6c020c8045e43dea16828f1 Mon Sep 17 00:00:00 2001 From: Lukasz Gornicki Date: Thu, 29 Jun 2023 10:49:00 +0300 Subject: [PATCH 21/41] docs: align text about send receive and publisher and subscriber (#934) --- spec/asyncapi.md | 26 +++++++++++++------------- 1 file changed, 13 insertions(+), 13 deletions(-) diff --git a/spec/asyncapi.md b/spec/asyncapi.md index 10326e254..21d49b613 100644 --- a/spec/asyncapi.md +++ b/spec/asyncapi.md @@ -21,7 +21,7 @@ The AsyncAPI Specification is a project used to describe message-driven APIs in The AsyncAPI Specification defines a set of files required to describe the API of an [application](#definitionsApplication). These files can be used to create utilities, such as documentation, code, integration, or testing tools. -The file(s) MUST describe the operations an [application](#definitionsApplication) performs. For instance, consider the following AsyncAPI definition snippet: +The file(s) SHOULD describe the operations an [application](#definitionsApplication) performs. For instance, consider the following AsyncAPI definition snippet: ```yaml channels: @@ -34,11 +34,11 @@ operations: $ref: "#/channels/userSignedUp" ``` -It means that the [application](#definitionsApplication) will subscribe to the `userSignedUp` [channel](#definitionsChannel) to receive messages. +It means that the [application](#definitionsApplication) will receive messages from the `userSignedUp` [channel](#definitionsChannel). **The AsyncAPI specification does not assume any kind of software topology, architecture or pattern.** Therefore, a server MAY be a message broker, a web server or any other kind of computer program capable of sending and/or receiving data. However, AsyncAPI offers a mechanism called "bindings" that aims to help with more specific information about the protocol. -It's NOT RECOMMENDED to derive a [consumer](#definitionsConsumer) AsyncAPI document from a [producer](#definitionsProducer) one or vice versa. There are no guarantees that the channel used by an application to receive messages will be the same channel where another application is sending them. Also, certain fields in the document like `summary`, `description`, and the id of the operation might stop making sense. For instance, given the following consumer snippet: +It's NOT RECOMMENDED to derive a [receiver](#definitionsReceiver) AsyncAPI document from a [sender](#definitionsSender) one or vice versa. There are no guarantees that the channel used by an application to receive messages will be the same channel where another application is sending them. Also, certain fields in the document like `summary`, `description`, and the id of the operation might stop making sense. For instance, given the following receiver snippet: ```yaml operations: @@ -70,8 +70,8 @@ Aside from the issues mentioned above, there may also be infrastructure configur - [Definitions](#definitions) - [Server](#definitionsServer) - [Application](#definitionsApplication) - - [Producer](#definitionsProducer) - - [Consumer](#definitionsConsumer) + - [Sender](#definitionsSender) + - [Receiver](#definitionsReceiver) - [Message](#definitionsMessage) - [Channel](#definitionsChannel) - [Protocol](#definitionsProtocol) @@ -124,22 +124,22 @@ Aside from the issues mentioned above, there may also be infrastructure configur ## Definitions ### Server -A server MAY be a message broker that is capable of sending and/or receiving between a [producer](#definitionsProducer) and [consumer](#definitionsConsumer). A server MAY be a service with WebSocket API that enables message-driven communication between browser-to-server or server-to-server. +A server MAY be a message broker that is capable of sending and/or receiving between a [sender](#definitionsSender) and [receiver](#definitionsReceiver). A server MAY be a service with WebSocket API that enables message-driven communication between browser-to-server or server-to-server. ### Application -An application is any kind of computer program or a group of them. It MUST be a [producer](#definitionsProducer), a [consumer](#definitionsConsumer) or both. An application MAY be a microservice, IoT device (sensor), mainframe process, etc. An application MAY be written in any number of different programming languages as long as they support the selected [protocol](#definitionsProtocol). An application MUST also use a protocol supported by the [server](#definitionsServer) in order to connect and exchange [messages](#definitionsMessage). +An application is any kind of computer program or a group of them. It MUST be a [sender](#definitionsSender), a [receiver](#definitionsReceiver), or both. An application MAY be a microservice, IoT device (sensor), mainframe process, message broker, etc. An application MAY be written in any number of different programming languages as long as they support the selected [protocol](#definitionsProtocol). An application MUST also use a protocol supported by the [server](#definitionsServer) in order to connect and exchange [messages](#definitionsMessage). -### Producer -A producer is a type of application, connected to a [server](#definitionsServer), that is creating [messages](#definitionsMessage) and addressing them to [channels](#definitionsChannel). A producer MAY be publishing to multiple channels depending on the [server](#definitionsServer), protocol, and use-case pattern. +### Sender +A sender is a type of application, that is sending [messages](#definitionsMessage) to [channels](#definitionsChannel). A sender MAY send to multiple channels depending on the [server](#definitionsServer), protocol, and use-case pattern. -### Consumer -A consumer is a type of application, connected to a [server](#definitionsServer) via a supported [protocol](#definitionsProtocol), that is consuming [messages](#definitionsMessage) from [channels](#definitionsChannel). A consumer MAY be consuming from multiple channels depending on the [server](#definitionsServer), protocol, and the use-case pattern. +### Receiver +A receiver is a type of application that is receiving [messages](#definitionsMessage) from [channels](#definitionsChannel). A receiver MAY receive from multiple channels depending on the [server](#definitionsServer), protocol, and the use-case pattern. A receiver MAY forward a received message further without changing it. A receiver MAY act as a consumer and react to the message. A receiver MAY act as a processor that, for example, aggregates multiple messages in one and forwards them. ### Message A message is the mechanism by which information is exchanged via a channel between [servers](#definitionsServer) and applications. A message MUST contain a payload and MAY also contain headers. The headers MAY be subdivided into [protocol](#definitionsProtocol)-defined headers and header properties defined by the application which can act as supporting metadata. The payload contains the data, defined by the application, which MUST be serialized into a format (JSON, XML, Avro, binary, etc.). Since a message is a generic mechanism, it can support multiple interaction patterns such as event, command, request, or response. ### Channel -A channel is an addressable component, made available by the [server](#definitionsServer), for the organization of [messages](#definitionsMessage). [Producer](#definitionsProducer) applications send messages to channels and [consumer](#definitionsConsumer) applications consume messages from channels. [Servers](#definitionsServer) MAY support many channel instances, allowing messages with different content to be addressed to different channels. Depending on the [server](#definitionsServer) implementation, the channel MAY be included in the message via protocol-defined headers. +A channel is an addressable component, made available by the [server](#definitionsServer), for the organization of [messages](#definitionsMessage). [Sender](#definitionsSender) applications send messages to channels and [receiver](#definitionsReceiver) applications receive messages from channels. [Servers](#definitionsServer) MAY support many channel instances, allowing messages with different content to be addressed to different channels. Depending on the [server](#definitionsServer) implementation, the channel MAY be included in the message via protocol-defined headers. ### Protocol A protocol is the mechanism (wireline protocol or API) by which [messages](#definitionsMessage) are exchanged between the application and the [channel](#definitionsChannel). Example protocols include, but are not limited to, AMQP, HTTP, JMS, Kafka, Anypoint MQ, MQTT, Solace, STOMP, Mercure, WebSocket. @@ -1930,7 +1930,7 @@ The following properties are taken from the JSON Schema definition but their def - description - [CommonMark syntax](https://spec.commonmark.org/) can be used for rich text representation. - format - See [Data Type Formats](#dataTypeFormat) for further details. While relying on JSON Schema's defined formats, the AsyncAPI Specification offers a few additional predefined formats. -- default - The default value represents what would be assumed by the consumer of the input as the value of the schema if one is not provided. Unlike JSON Schema, the value MUST conform to the defined type for the Schema Object defined at the same level. For example, of `type` is `string`, then `default` can be `"foo"` but cannot be `1`. +- default - Use it to specify that property has a predefined value if no other value is present. Unlike JSON Schema, the value MUST conform to the defined type for the Schema Object defined at the same level. For example, of `type` is `string`, then `default` can be `"foo"` but cannot be `1`. Alternatively, any time a Schema Object can be used, a [Reference Object](#referenceObject) can be used in its place. This allows referencing definitions in place of defining them inline. It is appropriate to clarify that the `$ref` keyword MUST follow the behavior described by [Reference Object](#referenceObject) instead of the one in [JSON Schema definition](https://json-schema.org/understanding-json-schema/structuring.html#ref). From e26b9a5bb5da5883b313805b1f431370fac77502 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Maciej=20Urba=C5=84czyk?= Date: Thu, 13 Jul 2023 23:10:34 +0200 Subject: [PATCH 22/41] feat: new traits merge mechanism (#907) Co-authored-by: Sergio Moya <1083296+smoya@users.noreply.github.com>%0ACo-authored-by: Jonas Lagoni %0ACo-authored-by: jonas-lt@live.dk --- spec/asyncapi.md | 30 ++++++++++++++++++++++++++++-- 1 file changed, 28 insertions(+), 2 deletions(-) diff --git a/spec/asyncapi.md b/spec/asyncapi.md index 21d49b613..7de215902 100644 --- a/spec/asyncapi.md +++ b/spec/asyncapi.md @@ -838,7 +838,7 @@ Field Name | Type | Description tags | [Tags Object](#tagsObject) | A list of tags for logical grouping and categorization of operations. externalDocs | [External Documentation Object](#externalDocumentationObject) \| [Reference Object](#referenceObject) | Additional external documentation for this operation. bindings | [Operation Bindings Object](#operationBindingsObject) \| [Reference Object](#referenceObject) | A map where the keys describe the name of the protocol and the values describe protocol-specific definitions for the operation. -traits | [[Operation Trait Object](#operationTraitObject) | [Reference Object](#referenceObject) ] | A list of traits to apply to the operation object. Traits MUST be merged into the operation object using the [JSON Merge Patch](https://tools.ietf.org/html/rfc7386) algorithm in the same order they are defined here. +traits | [[Operation Trait Object](#operationTraitObject) | [Reference Object](#referenceObject) ] | A list of traits to apply to the operation object. Traits MUST be merged using [traits merge mechanism](#traits-merge-mechanism). The resulting object MUST be a valid [Operation Object](#operationObject). messages | [[Reference Object](#referenceObject)] | A list of `$ref` pointers pointing to the supported [Message Objects](#messageObject) that can be processed by this operation. It MUST contain a subset of the messages defined in the [channel referenced in this operation](#operationObjectChannel). **Every message processed by this operation MUST be valid against one, and only one, of the [message objects](#messageObject) referenced in this list.** Please note the `messages` property value MUST be a list of [Reference Objects](#referenceObject) and, therefore, MUST NOT contain [Message Objects](#messageObject). However, it is RECOMMENDED that parsers (or other software) dereference this property for a better development experience. reply | [Operation Reply Object](#operationReplyObject) | [Reference Object](#referenceObject) | The definition of the reply in a request-reply operation. @@ -1240,7 +1240,7 @@ Field Name | Type | Description externalDocs | [External Documentation Object](#externalDocumentationObject) \| [Reference Object](#referenceObject) | Additional external documentation for this message. bindings | [Message Bindings Object](#messageBindingsObject) \| [Reference Object](#referenceObject) | A map where the keys describe the name of the protocol and the values describe protocol-specific definitions for the message. examples | [[Message Example Object](#messageExampleObject)] | List of examples. -traits | [[Message Trait Object](#messageTraitObject) | [Reference Object](#referenceObject)] | A list of traits to apply to the message object. Traits MUST be merged into the message object using the [JSON Merge Patch](https://tools.ietf.org/html/rfc7386) algorithm in the same order they are defined here. The resulting object MUST be a valid [Message Object](#messageObject). +traits | [[Message Trait Object](#messageTraitObject) | [Reference Object](#referenceObject)] | A list of traits to apply to the message object. Traits MUST be merged using [traits merge mechanism](#traits-merge-mechanism). The resulting object MUST be a valid [Message Object](#messageObject). This object MAY be extended with [Specification Extensions](#specificationExtensions). @@ -2625,6 +2625,32 @@ Message Payload Property | `$message.payload#/messageId` | Correlation ID is set Runtime expressions preserve the type of the referenced value. +### Traits Merge Mechanism + +Traits MUST be merged with the target object using the [JSON Merge Patch](https://tools.ietf.org/html/rfc7386) algorithm in the same order they are defined. A property on a trait MUST NOT override the same property on the target object. + +#### Example + +An object like the following: + +```yaml +description: A longer description. +traits: + - name: UserSignup + description: Description from trait. + - tags: + - name: user +``` + +Would look like the following after applying traits: + +```yaml +name: UserSignup +description: A longer description. +tags: + - name: user +``` + ### Specification Extensions While the AsyncAPI Specification tries to accommodate most use cases, additional data can be added to extend the specification at certain points. From f812cd7f99f1c63a0e6c7ef7d46a40a2babf963a Mon Sep 17 00:00:00 2001 From: Lukasz Gornicki Date: Thu, 20 Jul 2023 15:09:14 +0200 Subject: [PATCH 23/41] docs: add info that runtime expression is used by reply obj (#955) --- spec/asyncapi.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/spec/asyncapi.md b/spec/asyncapi.md index 7de215902..d973cb87e 100644 --- a/spec/asyncapi.md +++ b/spec/asyncapi.md @@ -2602,7 +2602,7 @@ location: $message.header#/correlationId ### Runtime Expression A runtime expression allows values to be defined based on information that will be available within the message. -This mechanism is used by [Correlation ID Object](#correlationIdObject). +This mechanism is used by [Correlation ID Object](#correlationIdObject) and [Operation Reply Address Object](#operationReplyAddressObject). The runtime expression is defined by the following [ABNF](https://tools.ietf.org/html/rfc5234) syntax: From 6ce7d35c1fc1fca3c92500c5d58870d6afbd4371 Mon Sep 17 00:00:00 2001 From: Rishi <52498617+kaushik-rishi@users.noreply.github.com> Date: Wed, 26 Jul 2023 21:10:21 +0530 Subject: [PATCH 24/41] ci: update release workflow on release branch (#956) --- .github/workflows/release.yml | 11 ++++++----- 1 file changed, 6 insertions(+), 5 deletions(-) diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml index 8252eadd8..6544ac8f5 100644 --- a/.github/workflows/release.yml +++ b/.github/workflows/release.yml @@ -11,13 +11,14 @@ jobs: release: name: 'Create GitHub release' runs-on: ubuntu-latest - steps: - name: Checkout repo - uses: actions/checkout@v2 + uses: actions/checkout@v3 - name: Setup Node.js - uses: actions/setup-node@v1 + uses: actions/setup-node@v3 + with: + node-version: 18 - name: Add plugin for conventional commits - run: npm install conventional-changelog-conventionalcommits + run: npm install --save-dev conventional-changelog-conventionalcommits@6.1.0 - name: Release to GitHub env: GITHUB_TOKEN: ${{ secrets.GH_TOKEN }} @@ -25,4 +26,4 @@ jobs: GIT_AUTHOR_EMAIL: info@asyncapi.io GIT_COMMITTER_NAME: asyncapi-bot GIT_COMMITTER_EMAIL: info@asyncapi.io - run: npx semantic-release@17.4.3 + run: npx semantic-release@21.0.7 From e2a3fa45e033e6e42b8f4b888c8777a8a94407cb Mon Sep 17 00:00:00 2001 From: Sergio Moya <1083296+smoya@users.noreply.github.com> Date: Fri, 28 Jul 2023 11:16:58 +0200 Subject: [PATCH 25/41] fix: clarify expected type for Message headers (#952) --- spec/asyncapi.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/spec/asyncapi.md b/spec/asyncapi.md index d973cb87e..f4be4969f 100644 --- a/spec/asyncapi.md +++ b/spec/asyncapi.md @@ -1228,7 +1228,7 @@ Describes a message received on a given channel and operation. Field Name | Type | Description ---|:---:|--- messageId | `string` | Unique string used to identify the message. The id MUST be unique among all messages described in the API. The messageId value is **case-sensitive**. Tools and libraries MAY use the messageId to uniquely identify a message, therefore, it is RECOMMENDED to follow common programming naming conventions. -headers | [Multi Format Schema Object](#multiFormatSchemaObject) | [Schema Object](#schemaObject) | [Reference Object](#referenceObject) | Schema definition of the application headers. Schema MUST be of type "object". It **MUST NOT** define the protocol headers. If this is a [Schema Object](#schemaObject), then the `schemaFormat` will be assumed to be "application/vnd.aai.asyncapi+json;version=`asyncapi`" where the version is equal to the [AsyncAPI Version String](#A2SVersionString). +headers | [Multi Format Schema Object](#multiFormatSchemaObject) | [Schema Object](#schemaObject) | [Reference Object](#referenceObject) | Schema definition of the application headers. Schema MUST be a map of key-value pairs. It **MUST NOT** define the protocol headers. If this is a [Schema Object](#schemaObject), then the `schemaFormat` will be assumed to be "application/vnd.aai.asyncapi+json;version=`asyncapi`" where the version is equal to the [AsyncAPI Version String](#A2SVersionString). payload | [Multi Format Schema Object](#multiFormatSchemaObject) | [Schema Object](#schemaObject) | [Reference Object](#referenceObject) | Definition of the message payload. If this is a [Schema Object](#schemaObject), then the `schemaFormat` will be assumed to be "application/vnd.aai.asyncapi+json;version=`asyncapi`" where the version is equal to the [AsyncAPI Version String](#A2SVersionString). correlationId | [Correlation ID Object](#correlationIdObject) | [Reference Object](#referenceObject) | Definition of the correlation ID used for message tracing or matching. contentType | `string` | The content type to use when encoding/decoding a message's payload. The value MUST be a specific media type (e.g. `application/json`). When omitted, the value MUST be the one specified on the [defaultContentType](#defaultContentTypeString) field. @@ -1412,7 +1412,7 @@ If you're looking to apply traits to an operation, see the [Operation Trait Obje Field Name | Type | Description ---|:---:|--- messageId | `string` | Unique string used to identify the message. The id MUST be unique among all messages described in the API. The messageId value is **case-sensitive**. Tools and libraries MAY use the messageId to uniquely identify a message, therefore, it is RECOMMENDED to follow common programming naming conventions. -headers | [Multi Format Schema Object](#multiFormatSchemaObject) | [Schema Object](#schemaObject) | [Reference Object](#referenceObject) | Schema definition of the application headers. Schema MUST be of type "object". It **MUST NOT** define the protocol headers. If this is a [Schema Object](#schemaObject), then the `schemaFormat` will be assumed to be "application/vnd.aai.asyncapi+json;version=`asyncapi`" where the version is equal to the [AsyncAPI Version String](#A2SVersionString). +headers | [Multi Format Schema Object](#multiFormatSchemaObject) | [Schema Object](#schemaObject) | [Reference Object](#referenceObject) | Schema definition of the application headers. Schema MUST be a map of key-value pairs. It **MUST NOT** define the protocol headers. If this is a [Schema Object](#schemaObject), then the `schemaFormat` will be assumed to be "application/vnd.aai.asyncapi+json;version=`asyncapi`" where the version is equal to the [AsyncAPI Version String](#A2SVersionString). correlationId | [Correlation ID Object](#correlationIdObject) | [Reference Object](#referenceObject) | Definition of the correlation ID used for message tracing or matching. contentType | `string` | The content type to use when encoding/decoding a message's payload. The value MUST be a specific media type (e.g. `application/json`). When omitted, the value MUST be the one specified on the [defaultContentType](#defaultContentTypeString) field. name | `string` | A machine-friendly name for the message. From c37d7450d2ae1a65fc9fddbad8c5225fe0772986 Mon Sep 17 00:00:00 2001 From: Jonas Lagoni Date: Thu, 3 Aug 2023 00:16:12 +0200 Subject: [PATCH 26/41] chore: update examples to v3 (#947) --- examples/adeo-kafka-request-reply.yml | 63 +- examples/anyof.yml | 25 +- examples/application-headers.yml | 54 +- examples/correlation-id.yml | 124 +- examples/gitter-streaming.yml | 248 +-- ...-request-reply-message-filter-in-reply.yml | 6 +- examples/mercure.yml | 48 +- examples/not.yml | 21 +- examples/oneof.yml | 53 +- examples/operation-security.yml | 57 +- examples/rpc-client.yml | 73 +- examples/rpc-server.yml | 67 +- examples/simple.yml | 14 +- examples/slack-rtm.yml | 316 ++-- examples/social-media/backend/asyncapi.yaml | 100 +- .../comments-service/asyncapi.yaml | 65 +- examples/social-media/common/servers.yaml | 3 +- examples/social-media/frontend/asyncapi.yaml | 34 +- .../notification-service/asyncapi.yaml | 39 +- .../social-media/public-api/asyncapi.yaml | 43 +- examples/streetlights-kafka.yml | 174 +- examples/streetlights-mqtt.yml | 201 +- examples/streetlights-operation-security.yml | 235 +-- examples/websocket-gemini.yml | 258 ++- scripts/converter/README.md | 1 + scripts/converter/index.js | 57 + scripts/converter/package-lock.json | 1618 +++++++++++++++++ scripts/converter/package.json | 12 + 28 files changed, 3079 insertions(+), 930 deletions(-) create mode 100644 scripts/converter/README.md create mode 100644 scripts/converter/index.js create mode 100644 scripts/converter/package-lock.json create mode 100644 scripts/converter/package.json diff --git a/examples/adeo-kafka-request-reply.yml b/examples/adeo-kafka-request-reply.yml index 76fca663b..b9a048957 100644 --- a/examples/adeo-kafka-request-reply.yml +++ b/examples/adeo-kafka-request-reply.yml @@ -7,40 +7,41 @@ info: contact: name: AsyncAPI team email: info@asyncapi.io + tags: + - name: costing + description: "Costing channels, used by Costing clients." servers: production: - url: "prod.url:9092" + host: "prod.url:9092" protocol: kafka-secure description: Kafka PRODUCTION cluster security: - - sasl-ssl: [] + - $ref: '#/components/securitySchemes/sasl-ssl' bindings: kafka: schemaRegistryUrl: >- https://schema-registry.prod.url/ staging: - url: "staging.url:9092" + host: "staging.url:9092" protocol: kafka-secure description: Kafka STAGING cluster for `uat` and `preprod` environments security: - - sasl-ssl: [] + - $ref: '#/components/securitySchemes/sasl-ssl' bindings: kafka: schemaRegistryUrl: >- https://schema-registry.staging.url/ dev: - url: "dev.url:9092" + host: "dev.url:9092" protocol: kafka-secure description: Kafka DEV cluster for `dev` and `sit` environments security: - - sasl-ssl: [] + - $ref: '#/components/securitySchemes/sasl-ssl' bindings: kafka: schemaRegistryUrl: >- https://schema-registry.dev.url/ -tags: - - name: costing - description: "Costing channels, used by Costing clients." + channels: costingRequest: address: "adeo-{env}-case-study-COSTING-REQUEST-{version}" @@ -64,9 +65,9 @@ channels: kafka: replicas: 3 partitions: 3 - topicConfiguration - cleanup.policy: delete - retention.ms: 7 days + topicConfiguration: + cleanup.policy: [ "delete" ] + retention.ms: 604800000 messages: costingRequest: $ref: "#/components/messages/costingRequestV1" @@ -98,12 +99,6 @@ channels: $ref: "#/components/parameters/Version" bindings: kafka: - groupId: - type: string - description: > - The groupId must be prefixed by your `svc` account, deliver by the - Adeo Kafka team. - This `svc` must have the read access to the topic. x-key.subject.name.strategy: type: string description: > @@ -125,7 +120,6 @@ channels: - operations: requestCosting: action: receive @@ -135,7 +129,7 @@ operations: channel: $ref: '#/channels/costingResponse' address: - locaton: '$message.header#/REPLY_TOPIC' + location: '$message.header#/REPLY_TOPIC' summary: | [COSTING] Request one or more Costing calculation for any product description: > @@ -165,6 +159,14 @@ operations: summary: > [COSTING] Get the costing responses matching an initial Costing Request. + bindings: + kafka: + groupId: + type: string + description: > + The groupId must be prefixed by your `svc` account, deliver by the + Adeo Kafka team. + This `svc` must have the read access to the topic. tags: - name: costing @@ -188,7 +190,6 @@ components: summary: Costing Request V1 inputs. tags: - name: costing - schemaFormat: application/vnd.apache.avro;version=1.9.0 correlationId: $ref: "#/components/correlationIds/costingCorrelationId" headers: @@ -208,7 +209,9 @@ components: REQUESTER_CODE: $ref: "#/components/schemas/RequesterCode" payload: - $ref: "https://deploy-preview-921--asyncapi-website.netlify.app/resources/casestudies/adeo/CostingRequestPayload.avsc" + schemaFormat: application/vnd.apache.avro;version=1.9.0 + schema: + $ref: "https://www.asyncapi.com/resources/casestudies/adeo/CostingRequestPayload.avsc" costingResponse: name: CostingResponse title: Costing Response @@ -219,7 +222,6 @@ components: Please refer to the `CostingResponseKey.avsc` schema, available on [our github project](https://github.url/). - schemaFormat: application/vnd.apache.avro;version=1.9.0 correlationId: $ref: "#/components/correlationIds/costingCorrelationId" headers: @@ -242,7 +244,9 @@ components: key: $ref: "https://deploy-preview-921--asyncapi-website.netlify.app/resources/casestudies/adeo/CostingResponseKey.avsc" payload: - $ref: "https://deploy-preview-921--asyncapi-website.netlify.app/resources/casestudies/adeo/CostingResponsePayload.avsc" + schemaFormat: application/vnd.apache.avro;version=1.9.0 + schema: + $ref: "https://deploy-preview-921--asyncapi-website.netlify.app/resources/casestudies/adeo/CostingResponsePayload.avsc" schemas: RequesterId: type: string @@ -303,9 +307,7 @@ components: parameters: Env: description: Adeo Kafka Environement for messages publications. - schema: - type: string - enum: + enum: - dev - sit - uat1 @@ -313,10 +315,9 @@ components: - prod Version: description: the topic version you want to use - schema: - type: string - example: V1 - default: V1 + examples: + - V1 + default: V1 securitySchemes: sasl-ssl: type: plain diff --git a/examples/anyof.yml b/examples/anyof.yml index a73ac4090..97492ed99 100644 --- a/examples/anyof.yml +++ b/examples/anyof.yml @@ -1,22 +1,27 @@ -asyncapi: '2.5.0' +asyncapi: 3.0.0 info: title: AnyOf example - version: '1.0.0' - + version: 1.0.0 channels: test: - publish: - message: + address: test + messages: + publish.message: $ref: '#/components/messages/testMessages' - +operations: + test.publish: + action: receive + channel: + $ref: '#/channels/test' + messages: + - $ref: '#/components/messages/testMessages' components: messages: testMessages: payload: - anyOf: # anyOf in payload schema - - $ref: "#/components/schemas/objectWithKey" - - $ref: "#/components/schemas/objectWithKey2" - + anyOf: + - $ref: '#/components/schemas/objectWithKey' + - $ref: '#/components/schemas/objectWithKey2' schemas: objectWithKey: type: object diff --git a/examples/application-headers.yml b/examples/application-headers.yml index 0ebe339d1..2c397f5ed 100644 --- a/examples/application-headers.yml +++ b/examples/application-headers.yml @@ -1,15 +1,15 @@ -asyncapi: '2.5.0' +asyncapi: 3.0.0 info: title: Application Headers example - version: '1.0.0' - description: A cut of the Streetlights API to test application header changes supporting #112 + version: 1.0.0 + description: A cut of the Streetlights API to test application header changes supporting license: name: Apache 2.0 - url: https://www.apache.org/licenses/LICENSE-2.0 - + url: 'https://www.apache.org/licenses/LICENSE-2.0' +defaultContentType: application/json servers: production: - url: test.mosquitto.org:{port} + host: 'test.mosquitto.org:{port}' protocol: mqtt description: Test broker variables: @@ -19,28 +19,36 @@ servers: enum: - '1883' - '8883' - -defaultContentType: application/json - channels: - smartylighting/streetlights/1/0/event/{streetlightId}/lighting/measured: + 'smartylighting/streetlights/1/0/event/{streetlightId}/lighting/measured': + address: 'smartylighting/streetlights/1/0/event/{streetlightId}/lighting/measured' + messages: + receiveLightMeasurement.message: + $ref: '#/components/messages/lightMeasured' parameters: streetlightId: $ref: '#/components/parameters/streetlightId' - publish: - summary: Inform about environmental lighting conditions of a particular streetlight. - operationId: receiveLightMeasurement - message: - $ref: '#/components/messages/lightMeasured' - +operations: + receiveLightMeasurement: + action: receive + channel: + $ref: >- + #/channels/smartylighting~1streetlights~11~10~1event~1{streetlightId}~1lighting~1measured + summary: >- + Inform about environmental lighting conditions of a particular + streetlight. + messages: + - $ref: '#/components/messages/lightMeasured' components: messages: lightMeasured: name: lightMeasured title: Light measured - summary: Inform about environmental lighting conditions of a particular streetlight. + summary: >- + Inform about environmental lighting conditions of a particular + streetlight. correlationId: - location: "$message.header#/MQMD/CorrelId" + location: $message.header#/MQMD/CorrelId contentType: application/json headers: type: object @@ -54,10 +62,9 @@ components: maxLength: 24 format: binary applicationInstanceId: - $ref: "#/components/schemas/applicationInstanceId" + $ref: '#/components/schemas/applicationInstanceId' payload: - $ref: "#/components/schemas/lightMeasuredPayload" - + $ref: '#/components/schemas/lightMeasuredPayload' schemas: lightMeasuredPayload: type: object @@ -67,7 +74,7 @@ components: minimum: 0 description: Light intensity measured in lumens. sentAt: - $ref: "#/components/schemas/sentAt" + $ref: '#/components/schemas/sentAt' sentAt: type: string format: date-time @@ -75,9 +82,6 @@ components: applicationInstanceId: description: Unique identifier for a given instance of the publishing application type: string - parameters: streetlightId: description: The ID of the streetlight. - schema: - type: string diff --git a/examples/correlation-id.yml b/examples/correlation-id.yml index 33bb2770e..41309194a 100644 --- a/examples/correlation-id.yml +++ b/examples/correlation-id.yml @@ -1,15 +1,15 @@ -asyncapi: '2.5.0' +asyncapi: 3.0.0 info: title: Correlation ID Example - version: '1.0.0' + version: 1.0.0 description: A cut of the Streetlights API to test Correlation ID license: name: Apache 2.0 - url: https://www.apache.org/licenses/LICENSE-2.0 - + url: 'https://www.apache.org/licenses/LICENSE-2.0' +defaultContentType: application/json servers: production: - url: test.mosquitto.org:{port} + host: 'test.mosquitto.org:{port}' protocol: mqtt description: Test broker variables: @@ -20,55 +20,97 @@ servers: - '1883' - '8883' security: - - apiKey: [] - - supportedOauthFlows: - - streetlights:on - - streetlights:off - - streetlights:dim - - openIdConnectWellKnown: [] - -defaultContentType: application/json - + - $ref: '#/components/securitySchemes/apiKey' + - type: oauth2 + description: Flows to support OAuth 2.0 + flows: + implicit: + authorizationUrl: 'https://authserver.example/auth' + availableScopes: + 'streetlights:on': Ability to switch lights on + 'streetlights:off': Ability to switch lights off + 'streetlights:dim': Ability to dim the lights + password: + tokenUrl: 'https://authserver.example/token' + availableScopes: + 'streetlights:on': Ability to switch lights on + 'streetlights:off': Ability to switch lights off + 'streetlights:dim': Ability to dim the lights + clientCredentials: + tokenUrl: 'https://authserver.example/token' + availableScopes: + 'streetlights:on': Ability to switch lights on + 'streetlights:off': Ability to switch lights off + 'streetlights:dim': Ability to dim the lights + authorizationCode: + authorizationUrl: 'https://authserver.example/auth' + tokenUrl: 'https://authserver.example/token' + refreshUrl: 'https://authserver.example/refresh' + availableScopes: + 'streetlights:on': Ability to switch lights on + 'streetlights:off': Ability to switch lights off + 'streetlights:dim': Ability to dim the lights + scopes: + - 'streetlights:on' + - 'streetlights:off' + - 'streetlights:dim' + - $ref: '#/components/securitySchemes/openIdConnectWellKnown' channels: - smartylighting/streetlights/1/0/event/{streetlightId}/lighting/measured: + 'smartylighting/streetlights/1/0/event/{streetlightId}/lighting/measured': + address: 'smartylighting/streetlights/1/0/event/{streetlightId}/lighting/measured' + messages: + receiveLightMeasurement.message: + $ref: '#/components/messages/lightMeasured' parameters: streetlightId: $ref: '#/components/parameters/streetlightId' - publish: - summary: Inform about environmental lighting conditions of a particular streetlight. - operationId: receiveLightMeasurement - message: - $ref: '#/components/messages/lightMeasured' - - smartylighting/streetlights/1/0/action/{streetlightId}/dim: + 'smartylighting/streetlights/1/0/action/{streetlightId}/dim': + address: 'smartylighting/streetlights/1/0/action/{streetlightId}/dim' + messages: + dimLight.message: + $ref: '#/components/messages/dimLight' parameters: streetlightId: $ref: '#/components/parameters/streetlightId' - subscribe: - operationId: dimLight - message: - $ref: '#/components/messages/dimLight' - +operations: + receiveLightMeasurement: + action: receive + channel: + $ref: >- + #/channels/smartylighting~1streetlights~11~10~1event~1{streetlightId}~1lighting~1measured + summary: >- + Inform about environmental lighting conditions of a particular + streetlight. + messages: + - $ref: '#/components/messages/lightMeasured' + dimLight: + action: send + channel: + $ref: >- + #/channels/smartylighting~1streetlights~11~10~1action~1{streetlightId}~1dim + messages: + - $ref: '#/components/messages/dimLight' components: messages: lightMeasured: name: lightMeasured title: Light measured - summary: Inform about environmental lighting conditions of a particular streetlight. + summary: >- + Inform about environmental lighting conditions of a particular + streetlight. correlationId: - location: "$message.header#/MQMD/CorrelId" + location: $message.header#/MQMD/CorrelId contentType: application/json payload: - $ref: "#/components/schemas/lightMeasuredPayload" + $ref: '#/components/schemas/lightMeasuredPayload' dimLight: name: dimLight title: Dim light summary: Command a particular streetlight to dim the lights. correlationId: - $ref: "#/components/correlationIds/sentAtCorrelator" + $ref: '#/components/correlationIds/sentAtCorrelator' payload: - $ref: "#/components/schemas/dimLightPayload" - + $ref: '#/components/schemas/dimLightPayload' schemas: lightMeasuredPayload: type: object @@ -78,7 +120,7 @@ components: minimum: 0 description: Light intensity measured in lumens. sentAt: - $ref: "#/components/schemas/sentAt" + $ref: '#/components/schemas/sentAt' dimLightPayload: type: object properties: @@ -88,18 +130,14 @@ components: minimum: 0 maximum: 100 sentAt: - $ref: "#/components/schemas/sentAt" + $ref: '#/components/schemas/sentAt' sentAt: type: string format: date-time description: Date and time when the message was sent. - parameters: streetlightId: description: The ID of the streetlight. - schema: - type: string - correlationIds: sentAtCorrelator: description: Data from message payload used as correlation ID @@ -115,19 +153,19 @@ components: flows: implicit: authorizationUrl: 'https://authserver.example/auth' - scopes: + availableScopes: 'streetlights:on': Ability to switch lights on 'streetlights:off': Ability to switch lights off 'streetlights:dim': Ability to dim the lights password: tokenUrl: 'https://authserver.example/token' - scopes: + availableScopes: 'streetlights:on': Ability to switch lights on 'streetlights:off': Ability to switch lights off 'streetlights:dim': Ability to dim the lights clientCredentials: tokenUrl: 'https://authserver.example/token' - scopes: + availableScopes: 'streetlights:on': Ability to switch lights on 'streetlights:off': Ability to switch lights off 'streetlights:dim': Ability to dim the lights @@ -135,7 +173,7 @@ components: authorizationUrl: 'https://authserver.example/auth' tokenUrl: 'https://authserver.example/token' refreshUrl: 'https://authserver.example/refresh' - scopes: + availableScopes: 'streetlights:on': Ability to switch lights on 'streetlights:off': Ability to switch lights off 'streetlights:dim': Ability to dim the lights diff --git a/examples/gitter-streaming.yml b/examples/gitter-streaming.yml index 1d53a01bb..cb987bbcb 100644 --- a/examples/gitter-streaming.yml +++ b/examples/gitter-streaming.yml @@ -1,42 +1,45 @@ -asyncapi: '2.5.0' +asyncapi: 3.0.0 id: 'tag:stream.gitter.im,2022:api' info: title: Gitter Streaming API - version: '1.0.0' - + version: 1.0.0 servers: production: - url: https://stream.gitter.im/v1 + host: stream.gitter.im + pathname: /v1 protocol: https protocolVersion: '1.1' security: - - httpBearerToken: [] - + - $ref: '#/components/securitySchemes/httpBearerToken' channels: - /rooms/{roomId}/{resource}: + '/rooms/{roomId}/{resource}': + address: '/rooms/{roomId}/{resource}' + messages: + subscribe.message.0: + $ref: '#/components/messages/chatMessage' + subscribe.message.1: + $ref: '#/components/messages/heartbeat' parameters: roomId: description: Id of the Gitter room. - schema: - type: string - examples: - - 53307860c3599d1de448e19d + examples: + - 53307860c3599d1de448e19d resource: + enum: + - chatMessages + - events description: The resource to consume. - schema: - type: string - enum: - - chatMessages - - events - subscribe: - bindings: - http: - type: response - message: - oneOf: - - $ref: '#/components/messages/chatMessage' - - $ref: '#/components/messages/heartbeat' - +operations: + '/rooms/{roomId}/{resource}.subscribe': + action: send + channel: + $ref: '#/channels/~1rooms~1{roomId}~1{resource}' + bindings: + http: + type: response + messages: + - $ref: '#/components/messages/chatMessage' + - $ref: '#/components/messages/heartbeat' components: securitySchemes: httpBearerToken: @@ -44,121 +47,122 @@ components: scheme: bearer messages: chatMessage: - schemaFormat: 'application/schema+yaml;version=draft-07' summary: >- - A message represents an individual chat message sent to a room. - They are a sub-resource of a room. + A message represents an individual chat message sent to a room. They are + a sub-resource of a room. payload: - type: object - properties: - id: - type: string - description: ID of the message. - text: - type: string - description: Original message in plain-text/markdown. - html: - type: string - description: HTML formatted message. - sent: - type: string - format: date-time - description: ISO formatted date of the message. - fromUser: - type: object - description: User that sent the message. - properties: - id: - type: string - description: Gitter User ID. - username: - type: string - description: Gitter/GitHub username. - displayName: - type: string - description: Gitter/GitHub user real name. - url: - type: string - description: Path to the user on Gitter. - avatarUrl: - type: string - format: uri - description: User avatar URI. - avatarUrlSmall: - type: string - format: uri - description: User avatar URI (small). - avatarUrlMedium: - type: string - format: uri - description: User avatar URI (medium). - v: - type: number - description: Version. - gv: - type: string - description: Stands for "Gravatar version" and is used for cache busting. - unread: - type: boolean - description: Boolean that indicates if the current user has read the message. - readBy: - type: number - description: Number of users that have read the message. - urls: - type: array - description: List of URLs present in the message. - items: + schemaFormat: application/schema+yaml;version=draft-07 + schema: + type: object + properties: + id: type: string - format: uri - mentions: - type: array - description: List of @Mentions in the message. - items: + description: ID of the message. + text: + type: string + description: Original message in plain-text/markdown. + html: + type: string + description: HTML formatted message. + sent: + type: string + format: date-time + description: ISO formatted date of the message. + fromUser: type: object + description: User that sent the message. properties: - screenName: + id: type: string - userId: + description: Gitter User ID. + username: type: string - userIds: - type: array - items: - type: string - issues: - type: array - description: 'List of #Issues referenced in the message.' - items: - type: object - properties: - number: + description: Gitter/GitHub username. + displayName: + type: string + description: Gitter/GitHub user real name. + url: + type: string + description: Path to the user on Gitter. + avatarUrl: + type: string + format: uri + description: User avatar URI. + avatarUrlSmall: + type: string + format: uri + description: User avatar URI (small). + avatarUrlMedium: type: string - meta: - type: array - description: Metadata. This is currently not used for anything. - items: {} - v: - type: number - description: Version. - gv: - type: string - description: Stands for "Gravatar version" and is used for cache busting. + format: uri + description: User avatar URI (medium). + v: + type: number + description: Version. + gv: + type: string + description: Stands for "Gravatar version" and is used for cache busting. + unread: + type: boolean + description: Boolean that indicates if the current user has read the message. + readBy: + type: number + description: Number of users that have read the message. + urls: + type: array + description: List of URLs present in the message. + items: + type: string + format: uri + mentions: + type: array + description: List of @Mentions in the message. + items: + type: object + properties: + screenName: + type: string + userId: + type: string + userIds: + type: array + items: + type: string + issues: + type: array + description: 'List of #Issues referenced in the message.' + items: + type: object + properties: + number: + type: string + meta: + type: array + description: Metadata. This is currently not used for anything. + items: {} + v: + type: number + description: Version. + gv: + type: string + description: Stands for "Gravatar version" and is used for cache busting. bindings: http: $ref: '#/components/messageBindings/streamingHeaders' - heartbeat: - schemaFormat: 'application/schema+yaml;version=draft-07' summary: Its purpose is to keep the connection alive. payload: - type: string - enum: ["\r\n"] + schemaFormat: application/schema+yaml;version=draft-07 + schema: + type: string + enum: + - "\r\n" bindings: http: $ref: '#/components/messageBindings/streamingHeaders' - messageBindings: streamingHeaders: http: headers: - 'Transfer-Encoding': 'chunked' - Trailer: '\r\n' + Transfer-Encoding: chunked + Trailer: \r\n diff --git a/examples/kraken-websocket-request-reply-message-filter-in-reply.yml b/examples/kraken-websocket-request-reply-message-filter-in-reply.yml index f82a7aa93..932f02274 100644 --- a/examples/kraken-websocket-request-reply-message-filter-in-reply.yml +++ b/examples/kraken-websocket-request-reply-message-filter-in-reply.yml @@ -47,7 +47,7 @@ operations: channel: $ref: '#/channels/currencyExchange' messages: - $ref: '#/components/messages/ping' + - $ref: '#/components/messages/ping' heartbeat: action: receive channel: @@ -64,7 +64,7 @@ operations: channel: $ref: '#/channels/currencyExchange' messages: - $ref: '#/components/messages/subscriptionStatus' + - $ref: '#/components/messages/subscriptionStatus' unsubscribe: action: send channel: @@ -73,7 +73,7 @@ operations: channel: $ref: '#/channels/currencyExchange' messages: - $ref: '#/components/messages/subscriptionStatus' + - $ref: '#/components/messages/subscriptionStatus' components: diff --git a/examples/mercure.yml b/examples/mercure.yml index 388f4dbc1..33ec12fd1 100644 --- a/examples/mercure.yml +++ b/examples/mercure.yml @@ -1,37 +1,47 @@ -asyncapi: '2.5.0' +asyncapi: 3.0.0 info: title: Mercure Hub Example - version: '1.0.0' + version: 1.0.0 description: This example demonstrates how to define a Mercure hub. - -# While not mandatory, it's a best practice to use formats with hypermedia capabilities such as JSON-LD, Atom or HTML with the Mercure protocol defaultContentType: application/ld+json - servers: production: - url: https://demo.mercure.rocks/.well-known/mercure + host: demo.mercure.rocks + pathname: /.well-known/mercure protocol: mercure - channels: 'https://example.com/books/{id}': - description: Every time a resource of type `http://schema.org/Book` is created or modified, a JSON-LD representation of the new version of this resource must be pushed in this Mercure topic. - parameters: - id: - schema: - type: integer - subscribe: - message: - $ref: '#/components/messages/book' - publish: - message: + address: 'https://example.com/books/{id}' + messages: + publish.message: + $ref: '#/components/messages/book' + subscribe.message: $ref: '#/components/messages/book' - + description: >- + Every time a resource of type `http://schema.org/Book` is created or + modified, a JSON-LD representation of the new version of this resource + must be pushed in this Mercure topic. + parameters: + id: {} +operations: + 'https://example.com/books/{id}.publish': + action: receive + channel: + $ref: '#/channels/https:~1~1example.com~1books~1{id}' + messages: + - $ref: '#/components/messages/book' + 'https://example.com/books/{id}.subscribe': + action: send + channel: + $ref: '#/channels/https:~1~1example.com~1books~1{id}' + messages: + - $ref: '#/components/messages/book' components: messages: book: summary: The content of a book resource. externalDocs: - url: https://schema.org/Book + url: 'https://schema.org/Book' payload: type: object properties: diff --git a/examples/not.yml b/examples/not.yml index 0b4e2e716..0dd2cad1d 100644 --- a/examples/not.yml +++ b/examples/not.yml @@ -1,20 +1,25 @@ -asyncapi: '2.5.0' +asyncapi: 3.0.0 info: title: Not example - version: '1.0.0' - + version: 1.0.0 channels: test: - publish: - message: + address: test + messages: + publish.message: $ref: '#/components/messages/testMessages' - +operations: + test.publish: + action: receive + channel: + $ref: '#/channels/test' + messages: + - $ref: '#/components/messages/testMessages' components: messages: testMessages: payload: - $ref: "#/components/schemas/testSchema" - + $ref: '#/components/schemas/testSchema' schemas: testSchema: type: object diff --git a/examples/oneof.yml b/examples/oneof.yml index 6bc4c92e3..2df5f6eea 100644 --- a/examples/oneof.yml +++ b/examples/oneof.yml @@ -1,38 +1,49 @@ -asyncapi: '2.5.0' +asyncapi: 3.0.0 info: title: OneOf example - version: '1.0.0' - + version: 1.0.0 channels: test: - publish: - message: + address: test + messages: + publish.message: $ref: '#/components/messages/testMessages' - test2: - subscribe: - message: - # Use oneOf here if different messages are published on test2 topic. - oneOf: - - payload: - $ref: "#/components/schemas/objectWithKey" - - payload: - $ref: "#/components/schemas/objectWithKey2" - + address: test2 + messages: + subscribe.message.0: + payload: + $ref: '#/components/schemas/objectWithKey' + subscribe.message.1: + payload: + $ref: '#/components/schemas/objectWithKey2' +operations: + test.publish: + action: receive + channel: + $ref: '#/channels/test' + messages: + - $ref: '#/components/messages/testMessages' + test2.subscribe: + action: send + channel: + $ref: '#/channels/test2' + messages: + - $ref: '#/channels/test2/messages/subscribe.message.0' + - $ref: '#/channels/test2/messages/subscribe.message.1' components: messages: testMessages: payload: - oneOf: # oneOf in payload schema - - $ref: "#/components/schemas/objectWithKey" - - $ref: "#/components/schemas/objectWithKey2" + oneOf: + - $ref: '#/components/schemas/objectWithKey' + - $ref: '#/components/schemas/objectWithKey2' testMessage1: payload: - $ref: "#/components/schemas/objectWithKey" + $ref: '#/components/schemas/objectWithKey' testMessage2: payload: - $ref: "#/components/schemas/objectWithKey2" - + $ref: '#/components/schemas/objectWithKey2' schemas: objectWithKey: type: object diff --git a/examples/operation-security.yml b/examples/operation-security.yml index f853072b2..99d959467 100644 --- a/examples/operation-security.yml +++ b/examples/operation-security.yml @@ -1,29 +1,44 @@ -asyncapi: 2.5.0 +asyncapi: 3.0.0 info: title: Notifications version: 1.0.0 description: >- - This contract defines HTTP Push notification for - application authorization revocation topic + This contract defines HTTP Push notification for application authorization + revocation topic channels: AUTHORIZATION_REVOCATION: - subscribe: - message: + address: AUTHORIZATION_REVOCATION + messages: + subscribe.message: $ref: '#/components/messages/message' - bindings: - http: - type: request - method: POST - headers: - type: object - properties: - Content-Type: - type: string - enum: - - application/json - security: - petstore_auth: - - subscribe:auth_revocations +operations: + AUTHORIZATION_REVOCATION.subscribe: + action: send + channel: + $ref: '#/channels/AUTHORIZATION_REVOCATION' + security: + - type: oauth2 + description: The oauth security descriptions + flows: + clientCredentials: + tokenUrl: 'https://example.com/api/oauth/dialog' + availableScopes: + 'subscribe:auth_revocations': Scope required for authorization revocation topic + scopes: + - 'subscribe:auth_revocations' + bindings: + http: + type: request + method: POST + headers: + type: object + properties: + Content-Type: + type: string + enum: + - application/json + messages: + - $ref: '#/components/messages/message' components: messages: message: @@ -102,5 +117,5 @@ components: flows: clientCredentials: tokenUrl: 'https://example.com/api/oauth/dialog' - scopes: - subscribe:auth_revocations: Scope required for authorization revocation topic + availableScopes: + 'subscribe:auth_revocations': Scope required for authorization revocation topic diff --git a/examples/rpc-client.yml b/examples/rpc-client.yml index 68f5d8014..dd35d2de5 100644 --- a/examples/rpc-client.yml +++ b/examples/rpc-client.yml @@ -1,35 +1,19 @@ -asyncapi: '2.5.0' +asyncapi: 3.0.0 id: 'urn:example:rpcclient' -defaultContentType: application/json - info: title: RPC Client Example + version: 1.0.0 description: This example demonstrates how to define an RPC client. - version: '1.0.0' - +defaultContentType: application/json servers: production: - url: rabbitmq.example.org + host: rabbitmq.example.org protocol: amqp - channels: '{queue}': - parameters: - queue: - schema: - type: string - pattern: '^amq\\.gen\\-.+$' - bindings: - amqp: - is: queue - queue: - exclusive: true - publish: - operationId: receiveSumResult - bindings: - amqp: - ack: false - message: + address: '{queue}' + messages: + receiveSumResult.message: correlationId: location: $message.header#/correlation_id payload: @@ -39,19 +23,17 @@ channels: type: number examples: - 7 - - rpc_queue: + parameters: + queue: {} bindings: amqp: is: queue queue: - durable: false - subscribe: - operationId: requestSum - bindings: - amqp: - ack: true - message: + exclusive: true + rpc_queue: + address: rpc_queue + messages: + requestSum.message: bindings: amqp: replyTo: @@ -66,4 +48,29 @@ channels: items: type: number examples: - - [4,3] + - - 4 + - 3 + bindings: + amqp: + is: queue + queue: + durable: false +operations: + receiveSumResult: + action: receive + channel: + $ref: '#/channels/{queue}' + bindings: + amqp: + ack: false + messages: + - $ref: '#/channels/{queue}/messages/receiveSumResult.message' + requestSum: + action: send + channel: + $ref: '#/channels/rpc_queue' + bindings: + amqp: + ack: true + messages: + - $ref: '#/channels/rpc_queue/messages/requestSum.message' diff --git a/examples/rpc-server.yml b/examples/rpc-server.yml index de4896eb6..de1f8ca43 100644 --- a/examples/rpc-server.yml +++ b/examples/rpc-server.yml @@ -1,35 +1,19 @@ -asyncapi: '2.5.0' +asyncapi: 3.0.0 id: 'urn:example:rpcserver' -defaultContentType: application/json - info: title: RPC Server Example + version: 1.0.0 description: This example demonstrates how to define an RPC server. - version: '1.0.0' - +defaultContentType: application/json servers: production: - url: rabbitmq.example.org + host: rabbitmq.example.org protocol: amqp - channels: '{queue}': - parameters: - queue: - schema: - type: string - pattern: '^amq\\.gen\\-.+$' - bindings: - amqp: - is: queue - queue: - exclusive: true - subscribe: - operationId: sendSumResult - bindings: - amqp: - ack: true - message: + address: '{queue}' + messages: + sendSumResult.message: correlationId: location: $message.header#/correlation_id payload: @@ -39,16 +23,17 @@ channels: type: number examples: - 7 - - rpc_queue: + parameters: + queue: {} bindings: amqp: is: queue queue: - durable: false - publish: - operationId: sum - message: + exclusive: true + rpc_queue: + address: rpc_queue + messages: + sum.message: bindings: amqp: replyTo: @@ -63,4 +48,26 @@ channels: items: type: number examples: - - [4,3] + - - 4 + - 3 + bindings: + amqp: + is: queue + queue: + durable: false +operations: + sendSumResult: + action: send + channel: + $ref: '#/channels/{queue}' + bindings: + amqp: + ack: true + messages: + - $ref: '#/channels/{queue}/messages/sendSumResult.message' + sum: + action: receive + channel: + $ref: '#/channels/rpc_queue' + messages: + - $ref: '#/channels/rpc_queue/messages/sum.message' diff --git a/examples/simple.yml b/examples/simple.yml index 329d5073b..f72ea6ece 100644 --- a/examples/simple.yml +++ b/examples/simple.yml @@ -1,13 +1,21 @@ -asyncapi: '2.5.0' +asyncapi: 3.0.0 info: title: Account Service version: 1.0.0 description: This service is in charge of processing user signups channels: user/signedup: - subscribe: - message: + address: user/signedup + messages: + subscribe.message: $ref: '#/components/messages/UserSignedUp' +operations: + user/signedup.subscribe: + action: send + channel: + $ref: '#/channels/user~1signedup' + messages: + - $ref: '#/components/messages/UserSignedUp' components: messages: UserSignedUp: diff --git a/examples/slack-rtm.yml b/examples/slack-rtm.yml index 20234a2bb..4de2a3c8f 100644 --- a/examples/slack-rtm.yml +++ b/examples/slack-rtm.yml @@ -1,79 +1,178 @@ -asyncapi: '2.5.0' +asyncapi: 3.0.0 id: 'wss://wss-primary.slack.com/websocket' info: title: Slack Real Time Messaging API - version: '1.0.0' - + version: 1.0.0 servers: production: - url: https://slack.com/api/rtm.connect + host: slack.com + pathname: /api/rtm.connect protocol: https protocolVersion: '1.1' security: - - token: [] - + - $ref: '#/components/securitySchemes/token' channels: /: - publish: - message: + address: / + messages: + publish.message: $ref: '#/components/messages/outgoingMessage' - subscribe: - message: - oneOf: - - $ref: '#/components/messages/hello' - - $ref: '#/components/messages/connectionError' - - $ref: '#/components/messages/accountsChanged' - - $ref: '#/components/messages/botAdded' - - $ref: '#/components/messages/botChanged' - - $ref: '#/components/messages/channelArchive' - - $ref: '#/components/messages/channelCreated' - - $ref: '#/components/messages/channelDeleted' - - $ref: '#/components/messages/channelHistoryChanged' - - $ref: '#/components/messages/channelJoined' - - $ref: '#/components/messages/channelLeft' - - $ref: '#/components/messages/channelMarked' - - $ref: '#/components/messages/channelRename' - - $ref: '#/components/messages/channelUnarchive' - - $ref: '#/components/messages/commandsChanged' - - $ref: '#/components/messages/dndUpdated' - - $ref: '#/components/messages/dndUpdatedUser' - - $ref: '#/components/messages/emailDomainChanged' - - $ref: '#/components/messages/emojiRemoved' - - $ref: '#/components/messages/emojiAdded' - - $ref: '#/components/messages/fileChange' - - $ref: '#/components/messages/fileCommentAdded' - - $ref: '#/components/messages/fileCommentDeleted' - - $ref: '#/components/messages/fileCommentEdited' - - $ref: '#/components/messages/fileCreated' - - $ref: '#/components/messages/fileDeleted' - - $ref: '#/components/messages/filePublic' - - $ref: '#/components/messages/fileShared' - - $ref: '#/components/messages/fileUnshared' - - $ref: '#/components/messages/goodbye' - - $ref: '#/components/messages/groupArchive' - - $ref: '#/components/messages/groupClose' - - $ref: '#/components/messages/groupHistoryChanged' - - $ref: '#/components/messages/groupJoined' - - $ref: '#/components/messages/groupLeft' - - $ref: '#/components/messages/groupMarked' - - $ref: '#/components/messages/groupOpen' - - $ref: '#/components/messages/groupRename' - - $ref: '#/components/messages/groupUnarchive' - - $ref: '#/components/messages/imClose' - - $ref: '#/components/messages/imCreated' - - $ref: '#/components/messages/imMarked' - - $ref: '#/components/messages/imOpen' - - $ref: '#/components/messages/manualPresenceChange' - - $ref: '#/components/messages/memberJoinedChannel' - - $ref: '#/components/messages/message' - + subscribe.message.0: + $ref: '#/components/messages/hello' + subscribe.message.1: + $ref: '#/components/messages/connectionError' + subscribe.message.2: + $ref: '#/components/messages/accountsChanged' + subscribe.message.3: + $ref: '#/components/messages/botAdded' + subscribe.message.4: + $ref: '#/components/messages/botChanged' + subscribe.message.5: + $ref: '#/components/messages/channelArchive' + subscribe.message.6: + $ref: '#/components/messages/channelCreated' + subscribe.message.7: + $ref: '#/components/messages/channelDeleted' + subscribe.message.8: + $ref: '#/components/messages/channelHistoryChanged' + subscribe.message.9: + $ref: '#/components/messages/channelJoined' + subscribe.message.10: + $ref: '#/components/messages/channelLeft' + subscribe.message.11: + $ref: '#/components/messages/channelMarked' + subscribe.message.12: + $ref: '#/components/messages/channelRename' + subscribe.message.13: + $ref: '#/components/messages/channelUnarchive' + subscribe.message.14: + $ref: '#/components/messages/commandsChanged' + subscribe.message.15: + $ref: '#/components/messages/dndUpdated' + subscribe.message.16: + $ref: '#/components/messages/dndUpdatedUser' + subscribe.message.17: + $ref: '#/components/messages/emailDomainChanged' + subscribe.message.18: + $ref: '#/components/messages/emojiRemoved' + subscribe.message.19: + $ref: '#/components/messages/emojiAdded' + subscribe.message.20: + $ref: '#/components/messages/fileChange' + subscribe.message.21: + $ref: '#/components/messages/fileCommentAdded' + subscribe.message.22: + $ref: '#/components/messages/fileCommentDeleted' + subscribe.message.23: + $ref: '#/components/messages/fileCommentEdited' + subscribe.message.24: + $ref: '#/components/messages/fileCreated' + subscribe.message.25: + $ref: '#/components/messages/fileDeleted' + subscribe.message.26: + $ref: '#/components/messages/filePublic' + subscribe.message.27: + $ref: '#/components/messages/fileShared' + subscribe.message.28: + $ref: '#/components/messages/fileUnshared' + subscribe.message.29: + $ref: '#/components/messages/goodbye' + subscribe.message.30: + $ref: '#/components/messages/groupArchive' + subscribe.message.31: + $ref: '#/components/messages/groupClose' + subscribe.message.32: + $ref: '#/components/messages/groupHistoryChanged' + subscribe.message.33: + $ref: '#/components/messages/groupJoined' + subscribe.message.34: + $ref: '#/components/messages/groupLeft' + subscribe.message.35: + $ref: '#/components/messages/groupMarked' + subscribe.message.36: + $ref: '#/components/messages/groupOpen' + subscribe.message.37: + $ref: '#/components/messages/groupRename' + subscribe.message.38: + $ref: '#/components/messages/groupUnarchive' + subscribe.message.39: + $ref: '#/components/messages/imClose' + subscribe.message.40: + $ref: '#/components/messages/imCreated' + subscribe.message.41: + $ref: '#/components/messages/imMarked' + subscribe.message.42: + $ref: '#/components/messages/imOpen' + subscribe.message.43: + $ref: '#/components/messages/manualPresenceChange' + subscribe.message.44: + $ref: '#/components/messages/memberJoinedChannel' + subscribe.message.45: + $ref: '#/components/messages/message' +operations: + /.publish: + action: receive + channel: + $ref: '#/channels/~1' + messages: + - $ref: '#/components/messages/outgoingMessage' + /.subscribe: + action: send + channel: + $ref: '#/channels/~1' + messages: + - $ref: '#/components/messages/hello' + - $ref: '#/components/messages/connectionError' + - $ref: '#/components/messages/accountsChanged' + - $ref: '#/components/messages/botAdded' + - $ref: '#/components/messages/botChanged' + - $ref: '#/components/messages/channelArchive' + - $ref: '#/components/messages/channelCreated' + - $ref: '#/components/messages/channelDeleted' + - $ref: '#/components/messages/channelHistoryChanged' + - $ref: '#/components/messages/channelJoined' + - $ref: '#/components/messages/channelLeft' + - $ref: '#/components/messages/channelMarked' + - $ref: '#/components/messages/channelRename' + - $ref: '#/components/messages/channelUnarchive' + - $ref: '#/components/messages/commandsChanged' + - $ref: '#/components/messages/dndUpdated' + - $ref: '#/components/messages/dndUpdatedUser' + - $ref: '#/components/messages/emailDomainChanged' + - $ref: '#/components/messages/emojiRemoved' + - $ref: '#/components/messages/emojiAdded' + - $ref: '#/components/messages/fileChange' + - $ref: '#/components/messages/fileCommentAdded' + - $ref: '#/components/messages/fileCommentDeleted' + - $ref: '#/components/messages/fileCommentEdited' + - $ref: '#/components/messages/fileCreated' + - $ref: '#/components/messages/fileDeleted' + - $ref: '#/components/messages/filePublic' + - $ref: '#/components/messages/fileShared' + - $ref: '#/components/messages/fileUnshared' + - $ref: '#/components/messages/goodbye' + - $ref: '#/components/messages/groupArchive' + - $ref: '#/components/messages/groupClose' + - $ref: '#/components/messages/groupHistoryChanged' + - $ref: '#/components/messages/groupJoined' + - $ref: '#/components/messages/groupLeft' + - $ref: '#/components/messages/groupMarked' + - $ref: '#/components/messages/groupOpen' + - $ref: '#/components/messages/groupRename' + - $ref: '#/components/messages/groupUnarchive' + - $ref: '#/components/messages/imClose' + - $ref: '#/components/messages/imCreated' + - $ref: '#/components/messages/imMarked' + - $ref: '#/components/messages/imOpen' + - $ref: '#/components/messages/manualPresenceChange' + - $ref: '#/components/messages/memberJoinedChannel' + - $ref: '#/components/messages/message' components: securitySchemes: token: type: httpApiKey name: token in: query - schemas: attachment: type: object @@ -123,10 +222,9 @@ components: format: uri ts: type: number - messages: hello: - summary: 'First event received upon connection.' + summary: First event received upon connection. payload: type: object properties: @@ -135,7 +233,7 @@ components: enum: - hello connectionError: - summary: 'Event received when a connection error happens.' + summary: Event received when a connection error happens. payload: type: object properties: @@ -151,7 +249,7 @@ components: msg: type: string accountsChanged: - summary: 'The list of accounts a user is signed into has changed.' + summary: The list of accounts a user is signed into has changed. payload: type: object properties: @@ -160,7 +258,7 @@ components: enum: - accounts_changed botAdded: - summary: 'A bot user was added.' + summary: A bot user was added. payload: type: object properties: @@ -182,7 +280,7 @@ components: additionalProperties: type: string botChanged: - summary: 'A bot user was changed.' + summary: A bot user was changed. payload: type: object properties: @@ -204,7 +302,7 @@ components: additionalProperties: type: string channelArchive: - summary: 'A channel was archived.' + summary: A channel was archived. payload: type: object properties: @@ -217,7 +315,7 @@ components: user: type: string channelCreated: - summary: 'A channel was created.' + summary: A channel was created. payload: type: object properties: @@ -237,7 +335,7 @@ components: creator: type: string channelDeleted: - summary: 'A channel was deleted.' + summary: A channel was deleted. payload: type: object properties: @@ -248,7 +346,7 @@ components: channel: type: string channelHistoryChanged: - summary: 'Bulk updates were made to a channel''s history.' + summary: Bulk updates were made to a channel's history. payload: type: object properties: @@ -263,7 +361,7 @@ components: event_ts: type: string channelJoined: - summary: 'You joined a channel.' + summary: You joined a channel. payload: type: object properties: @@ -283,7 +381,7 @@ components: creator: type: string channelLeft: - summary: 'You left a channel.' + summary: You left a channel. payload: type: object properties: @@ -294,7 +392,7 @@ components: channel: type: string channelMarked: - summary: 'Your channel read marker was updated.' + summary: Your channel read marker was updated. payload: type: object properties: @@ -307,7 +405,7 @@ components: ts: type: string channelRename: - summary: 'A channel was renamed.' + summary: A channel was renamed. payload: type: object properties: @@ -325,7 +423,7 @@ components: created: type: number channelUnarchive: - summary: 'A channel was unarchived.' + summary: A channel was unarchived. payload: type: object properties: @@ -338,7 +436,7 @@ components: user: type: string commandsChanged: - summary: 'A slash command has been added or changed.' + summary: A slash command has been added or changed. payload: type: object properties: @@ -349,7 +447,7 @@ components: event_ts: type: string dndUpdated: - summary: 'Do not Disturb settings changed for the current user.' + summary: Do not Disturb settings changed for the current user. payload: type: object properties: @@ -373,7 +471,7 @@ components: snooze_endtime: type: number dndUpdatedUser: - summary: 'Do not Disturb settings changed for a member.' + summary: Do not Disturb settings changed for a member. payload: type: object properties: @@ -393,7 +491,7 @@ components: next_dnd_end_ts: type: number emailDomainChanged: - summary: 'The workspace email domain has changed.' + summary: The workspace email domain has changed. payload: type: object properties: @@ -406,7 +504,7 @@ components: event_ts: type: string emojiRemoved: - summary: 'A custom emoji has been removed.' + summary: A custom emoji has been removed. payload: type: object properties: @@ -425,7 +523,7 @@ components: event_ts: type: string emojiAdded: - summary: 'A custom emoji has been added.' + summary: A custom emoji has been added. payload: type: object properties: @@ -445,7 +543,7 @@ components: event_ts: type: string fileChange: - summary: 'A file was changed.' + summary: A file was changed. payload: type: object properties: @@ -461,7 +559,7 @@ components: id: type: string fileCommentAdded: - summary: 'A file comment was added.' + summary: A file comment was added. payload: type: object properties: @@ -478,7 +576,7 @@ components: id: type: string fileCommentDeleted: - summary: 'A file comment was deleted.' + summary: A file comment was deleted. payload: type: object properties: @@ -496,7 +594,7 @@ components: id: type: string fileCommentEdited: - summary: 'A file comment was edited.' + summary: A file comment was edited. payload: type: object properties: @@ -513,7 +611,7 @@ components: id: type: string fileCreated: - summary: 'A file was created.' + summary: A file was created. payload: type: object properties: @@ -529,7 +627,7 @@ components: id: type: string fileDeleted: - summary: 'A file was deleted.' + summary: A file was deleted. payload: type: object properties: @@ -542,7 +640,7 @@ components: event_ts: type: string filePublic: - summary: 'A file was made public.' + summary: A file was made public. payload: type: object properties: @@ -558,7 +656,7 @@ components: id: type: string fileShared: - summary: 'A file was shared.' + summary: A file was shared. payload: type: object properties: @@ -574,7 +672,7 @@ components: id: type: string fileUnshared: - summary: 'A file was unshared.' + summary: A file was unshared. payload: type: object properties: @@ -590,7 +688,7 @@ components: id: type: string goodbye: - summary: 'The server intends to close the connection soon.' + summary: The server intends to close the connection soon. payload: type: object properties: @@ -599,7 +697,7 @@ components: enum: - goodbye groupArchive: - summary: 'A private channel was archived.' + summary: A private channel was archived. payload: type: object properties: @@ -610,7 +708,7 @@ components: channel: type: string groupClose: - summary: 'You closed a private channel.' + summary: You closed a private channel. payload: type: object properties: @@ -623,7 +721,7 @@ components: channel: type: string groupHistoryChanged: - summary: 'Bulk updates were made to a private channel''s history.' + summary: Bulk updates were made to a private channel's history. payload: type: object properties: @@ -638,7 +736,7 @@ components: event_ts: type: string groupJoined: - summary: 'You joined a private channel.' + summary: You joined a private channel. payload: type: object properties: @@ -658,7 +756,7 @@ components: creator: type: string groupLeft: - summary: 'You left a private channel.' + summary: You left a private channel. payload: type: object properties: @@ -669,7 +767,7 @@ components: channel: type: string groupMarked: - summary: 'A private channel read marker was updated.' + summary: A private channel read marker was updated. payload: type: object properties: @@ -682,7 +780,7 @@ components: ts: type: string groupOpen: - summary: 'You opened a private channel.' + summary: You opened a private channel. payload: type: object properties: @@ -695,7 +793,7 @@ components: channel: type: string groupRename: - summary: 'A private channel was renamed.' + summary: A private channel was renamed. payload: type: object properties: @@ -713,7 +811,7 @@ components: created: type: number groupUnarchive: - summary: 'A private channel was unarchived.' + summary: A private channel was unarchived. payload: type: object properties: @@ -726,7 +824,7 @@ components: user: type: string imClose: - summary: 'You closed a DM.' + summary: You closed a DM. payload: type: object properties: @@ -739,7 +837,7 @@ components: user: type: string imCreated: - summary: 'A DM was created.' + summary: A DM was created. payload: type: object properties: @@ -761,7 +859,7 @@ components: user: type: string imMarked: - summary: 'A direct message read marker was updated.' + summary: A direct message read marker was updated. payload: type: object properties: @@ -774,7 +872,7 @@ components: ts: type: string imOpen: - summary: 'You opened a DM.' + summary: You opened a DM. payload: type: object properties: @@ -787,7 +885,7 @@ components: user: type: string manualPresenceChange: - summary: 'You manually updated your presence.' + summary: You manually updated your presence. payload: type: object properties: @@ -798,7 +896,7 @@ components: presence: type: string memberJoinedChannel: - summary: 'A user joined a public or private channel.' + summary: A user joined a public or private channel. payload: type: object properties: @@ -820,7 +918,7 @@ components: inviter: type: string memberLeftChannel: - summary: 'A user left a public or private channel.' + summary: A user left a public or private channel. payload: type: object properties: @@ -840,7 +938,7 @@ components: team: type: string message: - summary: 'A message was sent to a channel.' + summary: A message was sent to a channel. payload: type: object properties: @@ -868,7 +966,7 @@ components: ts: type: string outgoingMessage: - summary: 'A message was sent to a channel.' + summary: A message was sent to a channel. payload: type: object properties: @@ -881,4 +979,4 @@ components: channel: type: string text: - type: string \ No newline at end of file + type: string diff --git a/examples/social-media/backend/asyncapi.yaml b/examples/social-media/backend/asyncapi.yaml index 5f7cb94e5..b93a16dc3 100644 --- a/examples/social-media/backend/asyncapi.yaml +++ b/examples/social-media/backend/asyncapi.yaml @@ -1,52 +1,82 @@ -asyncapi: 2.2.0 - +asyncapi: 3.0.0 info: title: Website Backend version: 1.0.0 - servers: websiteWebSocketServer: - $ref: '../common/servers.yaml#/websiteWebSocketServer' + $ref: ../common/servers.yaml#/websiteWebSocketServer mosquitto: - url: mqtt://test.mosquitto.org + host: test.mosquitto.org protocol: mqtt + tags: + - name: 'env:production' + description: This environment is meant for production use case + - name: 'kind:remote' + description: This server is a remote server. Not exposed by the application + - name: 'visibility:public' + description: This resource is public and available to everyone bindings: mqtt: clientId: websocketServer - tags: - - name: "env:production" - description: "This environment is meant for production use case" - - name: "kind:remote" - description: "This server is a remote server. Not exposed by the application" - - name: "visibility:public" - description: "This resource is public and available to everyone" - channels: comment/liked: + address: comment/liked + messages: + subscribe.message: + $ref: ../common/messages.yaml#/commentLiked description: Notify all the services that a comment has been liked. - servers: ['mosquitto'] - subscribe: - message: - $ref: '../common/messages.yaml#/commentLiked' + servers: + - $ref: '#/servers/mosquitto' like/comment: + address: like/comment + messages: + publish.message: + $ref: ../common/messages.yaml#/likeComment description: When a comment like is received from the frontend. - servers: ['websiteWebSocketServer'] - publish: - message: - $ref: '../common/messages.yaml#/likeComment' - comment/{commentId}/changed: - description: When an event from the broker arrives telling us to update the comment likes count on the frontend. - parameters: - commentId: - schema: - $ref: '../common/schemas.yaml#/commentId' - servers: ['mosquitto'] - publish: - message: - $ref: '../common/messages.yaml#/commentChanged' + servers: + - $ref: '#/servers/websiteWebSocketServer' + 'comment/{commentId}/changed': + address: 'comment/{commentId}/changed' + messages: + publish.message: + $ref: ../common/messages.yaml#/commentChanged + description: >- + When an event from the broker arrives telling us to update the comment + likes count on the frontend. + servers: + - $ref: '#/servers/mosquitto' + parameters: + commentId: {} update/comment/likes: + address: update/comment/likes + messages: + subscribe.message: + $ref: ../common/messages.yaml#/updateCommentLikes description: Update comment likes count in the frontend. - servers: ['websiteWebSocketServer'] - subscribe: - message: - $ref: '../common/messages.yaml#/updateCommentLikes' \ No newline at end of file + servers: + - $ref: '#/servers/websiteWebSocketServer' +operations: + comment/liked.subscribe: + action: send + channel: + $ref: '#/channels/comment~1liked' + messages: + - $ref: ../common/messages.yaml#/commentLiked + like/comment.publish: + action: receive + channel: + $ref: '#/channels/like~1comment' + messages: + - $ref: ../common/messages.yaml#/likeComment + 'comment/{commentId}/changed.publish': + action: receive + channel: + $ref: '#/channels/comment~1{commentId}~1changed' + messages: + - $ref: ../common/messages.yaml#/commentChanged + update/comment/likes.subscribe: + action: send + channel: + $ref: '#/channels/update~1comment~1likes' + messages: + - $ref: ../common/messages.yaml#/updateCommentLikes diff --git a/examples/social-media/comments-service/asyncapi.yaml b/examples/social-media/comments-service/asyncapi.yaml index ce8f93a9e..db4f3603f 100644 --- a/examples/social-media/comments-service/asyncapi.yaml +++ b/examples/social-media/comments-service/asyncapi.yaml @@ -1,38 +1,51 @@ -asyncapi: 2.2.0 - +asyncapi: 3.0.0 info: title: Comments Service version: 1.0.0 description: This service is in charge of processing all the events related to comments. - servers: mosquitto: - url: mqtt://test.mosquitto.org + host: test.mosquitto.org protocol: mqtt + tags: + - name: 'env:production' + description: This environment is meant for production use case + - name: 'kind:remote' + description: This server is a remote server. Not exposed by the application + - name: 'visibility:public' + description: This resource is public and available to everyone bindings: mqtt: clientId: comment-service - tags: - - name: "env:production" - description: "This environment is meant for production use case" - - name: "kind:remote" - description: "This server is a remote server. Not exposed by the application" - - name: "visibility:public" - description: "This resource is public and available to everyone" - channels: comment/liked: - description: Updates the likes count in the database and sends the new count to the broker. - publish: - message: - $ref: '../common/messages.yaml#/commentLiked' - comment/{commentId}/changed: - description: Sends the new count to the broker after it has been updated in the database. - parameters: - commentId: - schema: - $ref: '../common/schemas.yaml#/commentId' - subscribe: - message: - $ref: '../common/messages.yaml#/commentChanged' - + address: comment/liked + messages: + publish.message: + $ref: ../common/messages.yaml#/commentLiked + description: >- + Updates the likes count in the database and sends the new count to the + broker. + 'comment/{commentId}/changed': + address: 'comment/{commentId}/changed' + messages: + subscribe.message: + $ref: ../common/messages.yaml#/commentChanged + description: >- + Sends the new count to the broker after it has been updated in the + database. + parameters: + commentId: {} +operations: + comment/liked.publish: + action: receive + channel: + $ref: '#/channels/comment~1liked' + messages: + - $ref: ../common/messages.yaml#/commentLiked + 'comment/{commentId}/changed.subscribe': + action: send + channel: + $ref: '#/channels/comment~1{commentId}~1changed' + messages: + - $ref: ../common/messages.yaml#/commentChanged diff --git a/examples/social-media/common/servers.yaml b/examples/social-media/common/servers.yaml index bb32c3802..288b0cce7 100644 --- a/examples/social-media/common/servers.yaml +++ b/examples/social-media/common/servers.yaml @@ -1,3 +1,4 @@ websiteWebSocketServer: - url: ws://mycompany.com/ws + host: mycompany.com + pathname: /ws protocol: ws \ No newline at end of file diff --git a/examples/social-media/frontend/asyncapi.yaml b/examples/social-media/frontend/asyncapi.yaml index 2837fb6ff..0257336a6 100644 --- a/examples/social-media/frontend/asyncapi.yaml +++ b/examples/social-media/frontend/asyncapi.yaml @@ -1,21 +1,33 @@ -asyncapi: 2.2.0 - +asyncapi: 3.0.0 info: title: Website WebSocket Client version: 1.0.0 - servers: websiteWebSocketServer: - $ref: '../common/servers.yaml#/websiteWebSocketServer' - + $ref: ../common/servers.yaml#/websiteWebSocketServer channels: like/comment: + address: like/comment + messages: + subscribe.message: + $ref: ../common/messages.yaml#/likeComment description: Notify the backend that a comment has been liked. - subscribe: - message: - $ref: '../common/messages.yaml#/likeComment' update/comment/likes: + address: update/comment/likes + messages: + publish.message: + $ref: ../common/messages.yaml#/updateCommentLikes description: Update the UI when the comment likes count is updated. - publish: - message: - $ref: '../common/messages.yaml#/updateCommentLikes' \ No newline at end of file +operations: + like/comment.subscribe: + action: send + channel: + $ref: '#/channels/like~1comment' + messages: + - $ref: ../common/messages.yaml#/likeComment + update/comment/likes.publish: + action: receive + channel: + $ref: '#/channels/update~1comment~1likes' + messages: + - $ref: ../common/messages.yaml#/updateCommentLikes diff --git a/examples/social-media/notification-service/asyncapi.yaml b/examples/social-media/notification-service/asyncapi.yaml index be78362c9..858f3e2eb 100644 --- a/examples/social-media/notification-service/asyncapi.yaml +++ b/examples/social-media/notification-service/asyncapi.yaml @@ -1,27 +1,34 @@ -asyncapi: 2.2.0 - +asyncapi: 3.0.0 info: title: Notifications Service version: 1.0.0 - servers: mosquitto: - url: mqtt://test.mosquitto.org + host: test.mosquitto.org protocol: mqtt + tags: + - name: 'env:production' + description: This environment is meant for production use case + - name: 'kind:remote' + description: This server is a remote server. Not exposed by the application + - name: 'visibility:public' + description: This resource is public and available to everyone bindings: mqtt: clientId: notification-service - tags: - - name: "env:production" - description: "This environment is meant for production use case" - - name: "kind:remote" - description: "This server is a remote server. Not exposed by the application" - - name: "visibility:public" - description: "This resource is public and available to everyone" - channels: comment/liked: - description: When a "comment has been liked" message is received, it sends an SMS or push notification to the author. - publish: - message: - $ref: '../common/messages.yaml#/commentLiked' \ No newline at end of file + address: comment/liked + messages: + publish.message: + $ref: ../common/messages.yaml#/commentLiked + description: >- + When a "comment has been liked" message is received, it sends an SMS or + push notification to the author. +operations: + comment/liked.publish: + action: receive + channel: + $ref: '#/channels/comment~1liked' + messages: + - $ref: ../common/messages.yaml#/commentLiked diff --git a/examples/social-media/public-api/asyncapi.yaml b/examples/social-media/public-api/asyncapi.yaml index 0a7cdde79..9c6ec1b72 100644 --- a/examples/social-media/public-api/asyncapi.yaml +++ b/examples/social-media/public-api/asyncapi.yaml @@ -1,28 +1,35 @@ -asyncapi: 2.2.0 - +asyncapi: 3.0.0 info: - title: Public API - description: Public API for others to interact with the system + title: Public API version: 1.0.0 - + description: Public API for others to interact with the system servers: mosquitto: - url: mqtt://test.mosquitto.org + host: test.mosquitto.org protocol: mqtt + tags: + - name: 'env:production' + description: This environment is meant for production use case + - name: 'kind:remote' + description: This server is a remote server. Not exposed by the application + - name: 'visibility:public' + description: This resource is public and available to everyone bindings: mqtt: clientId: public-api - tags: - - name: "env:production" - description: "This environment is meant for production use case" - - name: "kind:remote" - description: "This server is a remote server. Not exposed by the application" - - name: "visibility:public" - description: "This resource is public and available to everyone" - channels: comment/liked: - description: Others are publishing to you, whenever a comment is liked, for you to do react to such an event. - publish: - message: - $ref: '../common/messages.yaml#/commentLiked' \ No newline at end of file + address: comment/liked + messages: + publish.message: + $ref: ../common/messages.yaml#/commentLiked + description: >- + Others are publishing to you, whenever a comment is liked, for you to do + react to such an event. +operations: + comment/liked.publish: + action: receive + channel: + $ref: '#/channels/comment~1liked' + messages: + - $ref: ../common/messages.yaml#/commentLiked diff --git a/examples/streetlights-kafka.yml b/examples/streetlights-kafka.yml index 916111154..0affab93b 100644 --- a/examples/streetlights-kafka.yml +++ b/examples/streetlights-kafka.yml @@ -1,107 +1,127 @@ -asyncapi: '2.5.0' +asyncapi: 3.0.0 info: title: Streetlights Kafka API - version: '1.0.0' - description: | - The Smartylighting Streetlights API allows you to remotely manage the city lights. - - ### Check out its awesome features: - - * Turn a specific streetlight on/off 🌃 - * Dim a specific streetlight 😎 - * Receive real-time information about environmental lighting conditions 📈 + version: 1.0.0 + description: "The Smartylighting Streetlights API allows you to remotely manage the city lights.\n\n### Check out its awesome features:\n\n* Turn a specific streetlight on/off \U0001F303\n* Dim a specific streetlight \U0001F60E\n* Receive real-time information about environmental lighting conditions \U0001F4C8\n" license: name: Apache 2.0 - url: https://www.apache.org/licenses/LICENSE-2.0 - + url: 'https://www.apache.org/licenses/LICENSE-2.0' +defaultContentType: application/json servers: scram-connections: - url: test.mykafkacluster.org:18092 + host: 'test.mykafkacluster.org:18092' protocol: kafka-secure description: Test broker secured with scramSha256 security: - - saslScram: [] + - $ref: '#/components/securitySchemes/saslScram' tags: - - name: "env:test-scram" - description: "This environment is meant for running internal tests through scramSha256" - - name: "kind:remote" - description: "This server is a remote server. Not exposed by the application" - - name: "visibility:private" - description: "This resource is private and only available to certain users" + - name: 'env:test-scram' + description: >- + This environment is meant for running internal tests through + scramSha256 + - name: 'kind:remote' + description: This server is a remote server. Not exposed by the application + - name: 'visibility:private' + description: This resource is private and only available to certain users mtls-connections: - url: test.mykafkacluster.org:28092 + host: 'test.mykafkacluster.org:28092' protocol: kafka-secure description: Test broker secured with X509 security: - - certs: [] + - $ref: '#/components/securitySchemes/certs' tags: - - name: "env:test-mtls" - description: "This environment is meant for running internal tests through mtls" - - name: "kind:remote" - description: "This server is a remote server. Not exposed by the application" - - name: "visibility:private" - description: "This resource is private and only available to certain users" - -defaultContentType: application/json - + - name: 'env:test-mtls' + description: This environment is meant for running internal tests through mtls + - name: 'kind:remote' + description: This server is a remote server. Not exposed by the application + - name: 'visibility:private' + description: This resource is private and only available to certain users channels: - smartylighting.streetlights.1.0.event.{streetlightId}.lighting.measured: + 'smartylighting.streetlights.1.0.event.{streetlightId}.lighting.measured': + address: 'smartylighting.streetlights.1.0.event.{streetlightId}.lighting.measured' + messages: + receiveLightMeasurement.message: + $ref: '#/components/messages/lightMeasured' description: The topic on which measured values may be produced and consumed. parameters: streetlightId: $ref: '#/components/parameters/streetlightId' - publish: - summary: Inform about environmental lighting conditions of a particular streetlight. - operationId: receiveLightMeasurement - traits: - - $ref: '#/components/operationTraits/kafka' - message: - $ref: '#/components/messages/lightMeasured' - - smartylighting.streetlights.1.0.action.{streetlightId}.turn.on: + 'smartylighting.streetlights.1.0.action.{streetlightId}.turn.on': + address: 'smartylighting.streetlights.1.0.action.{streetlightId}.turn.on' + messages: + turnOn.message: + $ref: '#/components/messages/turnOnOff' parameters: streetlightId: $ref: '#/components/parameters/streetlightId' - subscribe: - operationId: turnOn - traits: - - $ref: '#/components/operationTraits/kafka' - message: + 'smartylighting.streetlights.1.0.action.{streetlightId}.turn.off': + address: 'smartylighting.streetlights.1.0.action.{streetlightId}.turn.off' + messages: + turnOff.message: $ref: '#/components/messages/turnOnOff' - - smartylighting.streetlights.1.0.action.{streetlightId}.turn.off: parameters: streetlightId: $ref: '#/components/parameters/streetlightId' - subscribe: - operationId: turnOff - traits: - - $ref: '#/components/operationTraits/kafka' - message: - $ref: '#/components/messages/turnOnOff' - - smartylighting.streetlights.1.0.action.{streetlightId}.dim: + 'smartylighting.streetlights.1.0.action.{streetlightId}.dim': + address: 'smartylighting.streetlights.1.0.action.{streetlightId}.dim' + messages: + dimLight.message: + $ref: '#/components/messages/dimLight' parameters: streetlightId: $ref: '#/components/parameters/streetlightId' - subscribe: - operationId: dimLight - traits: - - $ref: '#/components/operationTraits/kafka' - message: - $ref: '#/components/messages/dimLight' - +operations: + receiveLightMeasurement: + action: receive + channel: + $ref: >- + #/channels/smartylighting.streetlights.1.0.event.{streetlightId}.lighting.measured + summary: >- + Inform about environmental lighting conditions of a particular + streetlight. + traits: + - $ref: '#/components/operationTraits/kafka' + messages: + - $ref: '#/components/messages/lightMeasured' + turnOn: + action: send + channel: + $ref: >- + #/channels/smartylighting.streetlights.1.0.action.{streetlightId}.turn.on + traits: + - $ref: '#/components/operationTraits/kafka' + messages: + - $ref: '#/components/messages/turnOnOff' + turnOff: + action: send + channel: + $ref: >- + #/channels/smartylighting.streetlights.1.0.action.{streetlightId}.turn.off + traits: + - $ref: '#/components/operationTraits/kafka' + messages: + - $ref: '#/components/messages/turnOnOff' + dimLight: + action: send + channel: + $ref: '#/channels/smartylighting.streetlights.1.0.action.{streetlightId}.dim' + traits: + - $ref: '#/components/operationTraits/kafka' + messages: + - $ref: '#/components/messages/dimLight' components: messages: lightMeasured: name: lightMeasured title: Light measured - summary: Inform about environmental lighting conditions of a particular streetlight. + summary: >- + Inform about environmental lighting conditions of a particular + streetlight. contentType: application/json traits: - $ref: '#/components/messageTraits/commonHeaders' payload: - $ref: "#/components/schemas/lightMeasuredPayload" + $ref: '#/components/schemas/lightMeasuredPayload' turnOnOff: name: turnOnOff title: Turn on/off @@ -109,7 +129,7 @@ components: traits: - $ref: '#/components/messageTraits/commonHeaders' payload: - $ref: "#/components/schemas/turnOnOffPayload" + $ref: '#/components/schemas/turnOnOffPayload' dimLight: name: dimLight title: Dim light @@ -117,8 +137,7 @@ components: traits: - $ref: '#/components/messageTraits/commonHeaders' payload: - $ref: "#/components/schemas/dimLightPayload" - + $ref: '#/components/schemas/dimLightPayload' schemas: lightMeasuredPayload: type: object @@ -128,18 +147,18 @@ components: minimum: 0 description: Light intensity measured in lumens. sentAt: - $ref: "#/components/schemas/sentAt" + $ref: '#/components/schemas/sentAt' turnOnOffPayload: type: object properties: command: type: string enum: - - on - - off + - 'on' + - 'off' description: Whether to turn on or off the light. sentAt: - $ref: "#/components/schemas/sentAt" + $ref: '#/components/schemas/sentAt' dimLightPayload: type: object properties: @@ -149,12 +168,11 @@ components: minimum: 0 maximum: 100 sentAt: - $ref: "#/components/schemas/sentAt" + $ref: '#/components/schemas/sentAt' sentAt: type: string format: date-time description: Date and time when the message was sent. - securitySchemes: saslScram: type: scramSha256 @@ -162,13 +180,9 @@ components: certs: type: X509 description: Download the certificate files from service provider - parameters: streetlightId: description: The ID of the streetlight. - schema: - type: string - messageTraits: commonHeaders: headers: @@ -178,11 +192,11 @@ components: type: integer minimum: 0 maximum: 100 - operationTraits: kafka: bindings: kafka: clientId: type: string - enum: ['my-app-id'] + enum: + - my-app-id diff --git a/examples/streetlights-mqtt.yml b/examples/streetlights-mqtt.yml index b3721d878..7a3fb23cb 100644 --- a/examples/streetlights-mqtt.yml +++ b/examples/streetlights-mqtt.yml @@ -1,22 +1,15 @@ -asyncapi: '2.5.0' +asyncapi: 3.0.0 info: title: Streetlights MQTT API - version: '1.0.0' - description: | - The Smartylighting Streetlights API allows you to remotely manage the city lights. - - ### Check out its awesome features: - - * Turn a specific streetlight on/off 🌃 - * Dim a specific streetlight 😎 - * Receive real-time information about environmental lighting conditions 📈 + version: 1.0.0 + description: "The Smartylighting Streetlights API allows you to remotely manage the city lights.\n\n### Check out its awesome features:\n\n* Turn a specific streetlight on/off \U0001F303\n* Dim a specific streetlight \U0001F60E\n* Receive real-time information about environmental lighting conditions \U0001F4C8\n" license: name: Apache 2.0 - url: https://www.apache.org/licenses/LICENSE-2.0 - + url: 'https://www.apache.org/licenses/LICENSE-2.0' +defaultContentType: application/json servers: production: - url: test.mosquitto.org:{port} + host: 'test.mosquitto.org:{port}' protocol: mqtt description: Test broker variables: @@ -27,80 +20,135 @@ servers: - '1883' - '8883' security: - - apiKey: [] - - supportedOauthFlows: - - streetlights:on - - streetlights:off - - streetlights:dim - - openIdConnectWellKnown: [] + - $ref: '#/components/securitySchemes/apiKey' + - type: oauth2 + description: Flows to support OAuth 2.0 + flows: + implicit: + authorizationUrl: 'https://authserver.example/auth' + availableScopes: + 'streetlights:on': Ability to switch lights on + 'streetlights:off': Ability to switch lights off + 'streetlights:dim': Ability to dim the lights + password: + tokenUrl: 'https://authserver.example/token' + availableScopes: + 'streetlights:on': Ability to switch lights on + 'streetlights:off': Ability to switch lights off + 'streetlights:dim': Ability to dim the lights + clientCredentials: + tokenUrl: 'https://authserver.example/token' + availableScopes: + 'streetlights:on': Ability to switch lights on + 'streetlights:off': Ability to switch lights off + 'streetlights:dim': Ability to dim the lights + authorizationCode: + authorizationUrl: 'https://authserver.example/auth' + tokenUrl: 'https://authserver.example/token' + refreshUrl: 'https://authserver.example/refresh' + availableScopes: + 'streetlights:on': Ability to switch lights on + 'streetlights:off': Ability to switch lights off + 'streetlights:dim': Ability to dim the lights + scopes: + - 'streetlights:on' + - 'streetlights:off' + - 'streetlights:dim' + - $ref: '#/components/securitySchemes/openIdConnectWellKnown' tags: - - name: "env:production" - description: "This environment is meant for production use case" - - name: "kind:remote" - description: "This server is a remote server. Not exposed by the application" - - name: "visibility:public" - description: "This resource is public and available to everyone" - -defaultContentType: application/json - + - name: 'env:production' + description: This environment is meant for production use case + - name: 'kind:remote' + description: This server is a remote server. Not exposed by the application + - name: 'visibility:public' + description: This resource is public and available to everyone channels: - smartylighting/streetlights/1/0/event/{streetlightId}/lighting/measured: + 'smartylighting/streetlights/1/0/event/{streetlightId}/lighting/measured': + address: 'smartylighting/streetlights/1/0/event/{streetlightId}/lighting/measured' + messages: + receiveLightMeasurement.message: + $ref: '#/components/messages/lightMeasured' description: The topic on which measured values may be produced and consumed. parameters: streetlightId: $ref: '#/components/parameters/streetlightId' - publish: - summary: Inform about environmental lighting conditions of a particular streetlight. - operationId: receiveLightMeasurement - traits: - - $ref: '#/components/operationTraits/mqtt' - message: - $ref: '#/components/messages/lightMeasured' - - smartylighting/streetlights/1/0/action/{streetlightId}/turn/on: + 'smartylighting/streetlights/1/0/action/{streetlightId}/turn/on': + address: 'smartylighting/streetlights/1/0/action/{streetlightId}/turn/on' + messages: + turnOn.message: + $ref: '#/components/messages/turnOnOff' parameters: streetlightId: $ref: '#/components/parameters/streetlightId' - subscribe: - operationId: turnOn - traits: - - $ref: '#/components/operationTraits/mqtt' - message: + 'smartylighting/streetlights/1/0/action/{streetlightId}/turn/off': + address: 'smartylighting/streetlights/1/0/action/{streetlightId}/turn/off' + messages: + turnOff.message: $ref: '#/components/messages/turnOnOff' - - smartylighting/streetlights/1/0/action/{streetlightId}/turn/off: parameters: streetlightId: $ref: '#/components/parameters/streetlightId' - subscribe: - operationId: turnOff - traits: - - $ref: '#/components/operationTraits/mqtt' - message: - $ref: '#/components/messages/turnOnOff' - - smartylighting/streetlights/1/0/action/{streetlightId}/dim: + 'smartylighting/streetlights/1/0/action/{streetlightId}/dim': + address: 'smartylighting/streetlights/1/0/action/{streetlightId}/dim' + messages: + dimLight.message: + $ref: '#/components/messages/dimLight' parameters: streetlightId: $ref: '#/components/parameters/streetlightId' - subscribe: - operationId: dimLight - traits: - - $ref: '#/components/operationTraits/mqtt' - message: - $ref: '#/components/messages/dimLight' - +operations: + receiveLightMeasurement: + action: receive + channel: + $ref: >- + #/channels/smartylighting~1streetlights~11~10~1event~1{streetlightId}~1lighting~1measured + summary: >- + Inform about environmental lighting conditions of a particular + streetlight. + traits: + - $ref: '#/components/operationTraits/mqtt' + messages: + - $ref: '#/components/messages/lightMeasured' + turnOn: + action: send + channel: + $ref: >- + #/channels/smartylighting~1streetlights~11~10~1action~1{streetlightId}~1turn~1on + traits: + - $ref: '#/components/operationTraits/mqtt' + messages: + - $ref: '#/components/messages/turnOnOff' + turnOff: + action: send + channel: + $ref: >- + #/channels/smartylighting~1streetlights~11~10~1action~1{streetlightId}~1turn~1off + traits: + - $ref: '#/components/operationTraits/mqtt' + messages: + - $ref: '#/components/messages/turnOnOff' + dimLight: + action: send + channel: + $ref: >- + #/channels/smartylighting~1streetlights~11~10~1action~1{streetlightId}~1dim + traits: + - $ref: '#/components/operationTraits/mqtt' + messages: + - $ref: '#/components/messages/dimLight' components: messages: lightMeasured: name: lightMeasured title: Light measured - summary: Inform about environmental lighting conditions of a particular streetlight. + summary: >- + Inform about environmental lighting conditions of a particular + streetlight. contentType: application/json traits: - $ref: '#/components/messageTraits/commonHeaders' payload: - $ref: "#/components/schemas/lightMeasuredPayload" + $ref: '#/components/schemas/lightMeasuredPayload' turnOnOff: name: turnOnOff title: Turn on/off @@ -108,7 +156,7 @@ components: traits: - $ref: '#/components/messageTraits/commonHeaders' payload: - $ref: "#/components/schemas/turnOnOffPayload" + $ref: '#/components/schemas/turnOnOffPayload' dimLight: name: dimLight title: Dim light @@ -116,8 +164,7 @@ components: traits: - $ref: '#/components/messageTraits/commonHeaders' payload: - $ref: "#/components/schemas/dimLightPayload" - + $ref: '#/components/schemas/dimLightPayload' schemas: lightMeasuredPayload: type: object @@ -127,18 +174,18 @@ components: minimum: 0 description: Light intensity measured in lumens. sentAt: - $ref: "#/components/schemas/sentAt" + $ref: '#/components/schemas/sentAt' turnOnOffPayload: type: object properties: command: type: string enum: - - on - - off + - 'on' + - 'off' description: Whether to turn on or off the light. sentAt: - $ref: "#/components/schemas/sentAt" + $ref: '#/components/schemas/sentAt' dimLightPayload: type: object properties: @@ -148,12 +195,11 @@ components: minimum: 0 maximum: 100 sentAt: - $ref: "#/components/schemas/sentAt" + $ref: '#/components/schemas/sentAt' sentAt: type: string format: date-time description: Date and time when the message was sent. - securitySchemes: apiKey: type: apiKey @@ -165,19 +211,19 @@ components: flows: implicit: authorizationUrl: 'https://authserver.example/auth' - scopes: + availableScopes: 'streetlights:on': Ability to switch lights on 'streetlights:off': Ability to switch lights off 'streetlights:dim': Ability to dim the lights password: tokenUrl: 'https://authserver.example/token' - scopes: + availableScopes: 'streetlights:on': Ability to switch lights on 'streetlights:off': Ability to switch lights off 'streetlights:dim': Ability to dim the lights clientCredentials: tokenUrl: 'https://authserver.example/token' - scopes: + availableScopes: 'streetlights:on': Ability to switch lights on 'streetlights:off': Ability to switch lights off 'streetlights:dim': Ability to dim the lights @@ -185,20 +231,16 @@ components: authorizationUrl: 'https://authserver.example/auth' tokenUrl: 'https://authserver.example/token' refreshUrl: 'https://authserver.example/refresh' - scopes: + availableScopes: 'streetlights:on': Ability to switch lights on 'streetlights:off': Ability to switch lights off 'streetlights:dim': Ability to dim the lights openIdConnectWellKnown: type: openIdConnect openIdConnectUrl: 'https://authserver.example/.well-known' - parameters: streetlightId: description: The ID of the streetlight. - schema: - type: string - messageTraits: commonHeaders: headers: @@ -208,7 +250,6 @@ components: type: integer minimum: 0 maximum: 100 - operationTraits: mqtt: bindings: diff --git a/examples/streetlights-operation-security.yml b/examples/streetlights-operation-security.yml index faf122763..a29723e9c 100644 --- a/examples/streetlights-operation-security.yml +++ b/examples/streetlights-operation-security.yml @@ -1,125 +1,162 @@ -asyncapi: '2.5.0' +asyncapi: 3.0.0 info: title: Streetlights Kafka API - version: '1.0.0' - description: | - The Smartylighting Streetlights API allows you to remotely manage the city lights. - - ### Check out its awesome features: - - * Turn a specific streetlight on/off 🌃 - * Dim a specific streetlight 😎 - * Receive real-time information about environmental lighting conditions 📈 + version: 1.0.0 + description: "The Smartylighting Streetlights API allows you to remotely manage the city lights.\n\n### Check out its awesome features:\n\n* Turn a specific streetlight on/off \U0001F303\n* Dim a specific streetlight \U0001F60E\n* Receive real-time information about environmental lighting conditions \U0001F4C8\n" license: name: Apache 2.0 - url: https://www.apache.org/licenses/LICENSE-2.0 - + url: 'https://www.apache.org/licenses/LICENSE-2.0' +defaultContentType: application/json servers: test: - url: test.mykafkacluster.org:8092 + host: 'test.mykafkacluster.org:8092' protocol: kafka-secure description: Test broker security: - - saslScram: [] + - $ref: '#/components/securitySchemes/saslScram' test_oauth: - url: test.mykafkacluster.org:8093 + host: 'test.mykafkacluster.org:8093' protocol: kafka-secure - description: Test port for oauth + description: Test port for oauth security: - - streetlights_auth: - - streetlights:write - - streetlights:read - - -defaultContentType: application/json - + - type: oauth2 + description: The oauth security descriptions + flows: + clientCredentials: + tokenUrl: 'https://example.com/api/oauth/dialog' + availableScopes: + 'streetlights:read': Scope required for subscribing to channel + 'streetlights:write': Scope required for publishing to channel + scopes: + - 'streetlights:write' + - 'streetlights:read' channels: - smartylighting.streetlights.1.0.event.{streetlightId}.lighting.measured: + 'smartylighting.streetlights.1.0.event.{streetlightId}.lighting.measured': + address: 'smartylighting.streetlights.1.0.event.{streetlightId}.lighting.measured' + messages: + receiveLightMeasurement.message: + $ref: '#/components/messages/lightMeasured' description: The topic on which measured values may be produced and consumed. servers: - - test + - $ref: '#/servers/test' parameters: streetlightId: $ref: '#/components/parameters/streetlightId' - publish: - summary: Inform about environmental lighting conditions of a particular streetlight. - operationId: receiveLightMeasurement - traits: - - $ref: '#/components/operationTraits/kafka' - message: - $ref: '#/components/messages/lightMeasured' - - smartylighting.streetlights.1.0.action.{streetlightId}.turn.on: + 'smartylighting.streetlights.1.0.action.{streetlightId}.turn.on': + address: 'smartylighting.streetlights.1.0.action.{streetlightId}.turn.on' + messages: + turnOn.message: + $ref: '#/components/messages/turnOnOff' servers: - - test_oauth + - $ref: '#/servers/test_oauth' parameters: streetlightId: $ref: '#/components/parameters/streetlightId' - subscribe: - operationId: turnOn - traits: - - $ref: '#/components/operationTraits/kafka' - message: + 'smartylighting.streetlights.1.0.action.{streetlightId}.turn.off': + address: 'smartylighting.streetlights.1.0.action.{streetlightId}.turn.off' + messages: + turnOff.message: $ref: '#/components/messages/turnOnOff' - security: - # This operation level security implies the ability to subscribe to messages from - # `smartylighting.streetlights.1.0.action.{streetlightId}.turn.on` channel with Authorization headers - # that have `streetlights:read` scope. Note that an operation level security must still satisfy - # security requirements specified at the server level. - - streetlights_auth: - - streetlights:read - - smartylighting.streetlights.1.0.action.{streetlightId}.turn.off: servers: - - test_oauth + - $ref: '#/servers/test_oauth' parameters: streetlightId: $ref: '#/components/parameters/streetlightId' - subscribe: - operationId: turnOff - traits: - - $ref: '#/components/operationTraits/kafka' - message: - $ref: '#/components/messages/turnOnOff' - security: - # This operation level security implies the ability to subscribe to messages from - # `smartylighting.streetlights.1.0.action.{streetlightId}.turn.off` channel with Authorization headers - # that have `streetlights:read` scope. Note that an operation level security must still satisfy - # security options specified at the server level. - - streetlights_auth: - - streetlights:read - smartylighting.streetlights.1.0.action.{streetlightId}.dim: + 'smartylighting.streetlights.1.0.action.{streetlightId}.dim': + address: 'smartylighting.streetlights.1.0.action.{streetlightId}.dim' + messages: + dimLight.message: + $ref: '#/components/messages/dimLight' servers: - - test_oauth + - $ref: '#/servers/test_oauth' parameters: streetlightId: $ref: '#/components/parameters/streetlightId' - subscribe: - operationId: dimLight - traits: - - $ref: '#/components/operationTraits/kafka' - message: - $ref: '#/components/messages/dimLight' - security: - # This operation level security implies the ability to subscribe to messages from - # `smartylighting.streetlights.1.0.action.{streetlightId}.dim` channel with Authorization headers - # that have `streetlights:read` scope. Note that an operation level security must still satisfy - # security options specified at the server level. - - streetlights_auth: - - streetlights:read - - +operations: + receiveLightMeasurement: + action: receive + channel: + $ref: >- + #/channels/smartylighting.streetlights.1.0.event.{streetlightId}.lighting.measured + summary: >- + Inform about environmental lighting conditions of a particular + streetlight. + traits: + - $ref: '#/components/operationTraits/kafka' + messages: + - $ref: '#/components/messages/lightMeasured' + turnOn: + action: send + channel: + $ref: >- + #/channels/smartylighting.streetlights.1.0.action.{streetlightId}.turn.on + security: + - type: oauth2 + description: The oauth security descriptions + flows: + clientCredentials: + tokenUrl: 'https://example.com/api/oauth/dialog' + availableScopes: + 'streetlights:read': Scope required for subscribing to channel + 'streetlights:write': Scope required for publishing to channel + scopes: + - 'streetlights:read' + traits: + - $ref: '#/components/operationTraits/kafka' + messages: + - $ref: '#/components/messages/turnOnOff' + turnOff: + action: send + channel: + $ref: >- + #/channels/smartylighting.streetlights.1.0.action.{streetlightId}.turn.off + security: + - type: oauth2 + description: The oauth security descriptions + flows: + clientCredentials: + tokenUrl: 'https://example.com/api/oauth/dialog' + availableScopes: + 'streetlights:read': Scope required for subscribing to channel + 'streetlights:write': Scope required for publishing to channel + scopes: + - 'streetlights:read' + traits: + - $ref: '#/components/operationTraits/kafka' + messages: + - $ref: '#/components/messages/turnOnOff' + dimLight: + action: send + channel: + $ref: '#/channels/smartylighting.streetlights.1.0.action.{streetlightId}.dim' + security: + - type: oauth2 + description: The oauth security descriptions + flows: + clientCredentials: + tokenUrl: 'https://example.com/api/oauth/dialog' + availableScopes: + 'streetlights:read': Scope required for subscribing to channel + 'streetlights:write': Scope required for publishing to channel + scopes: + - 'streetlights:read' + traits: + - $ref: '#/components/operationTraits/kafka' + messages: + - $ref: '#/components/messages/dimLight' components: messages: lightMeasured: name: lightMeasured title: Light measured - summary: Inform about environmental lighting conditions of a particular streetlight. + summary: >- + Inform about environmental lighting conditions of a particular + streetlight. contentType: application/json traits: - $ref: '#/components/messageTraits/commonHeaders' payload: - $ref: "#/components/schemas/lightMeasuredPayload" + $ref: '#/components/schemas/lightMeasuredPayload' turnOnOff: name: turnOnOff title: Turn on/off @@ -127,7 +164,7 @@ components: traits: - $ref: '#/components/messageTraits/commonHeaders' payload: - $ref: "#/components/schemas/turnOnOffPayload" + $ref: '#/components/schemas/turnOnOffPayload' dimLight: name: dimLight title: Dim light @@ -135,8 +172,7 @@ components: traits: - $ref: '#/components/messageTraits/commonHeaders' payload: - $ref: "#/components/schemas/dimLightPayload" - + $ref: '#/components/schemas/dimLightPayload' schemas: lightMeasuredPayload: type: object @@ -146,18 +182,18 @@ components: minimum: 0 description: Light intensity measured in lumens. sentAt: - $ref: "#/components/schemas/sentAt" + $ref: '#/components/schemas/sentAt' turnOnOffPayload: type: object properties: command: type: string enum: - - on - - off + - 'on' + - 'off' description: Whether to turn on or off the light. sentAt: - $ref: "#/components/schemas/sentAt" + $ref: '#/components/schemas/sentAt' dimLightPayload: type: object properties: @@ -167,12 +203,11 @@ components: minimum: 0 maximum: 100 sentAt: - $ref: "#/components/schemas/sentAt" + $ref: '#/components/schemas/sentAt' sentAt: type: string format: date-time description: Date and time when the message was sent. - securitySchemes: saslScram: type: scramSha256 @@ -181,18 +216,14 @@ components: type: oauth2 description: The oauth security descriptions flows: - clientCredentials: - tokenUrl: 'https://example.com/api/oauth/dialog' - scopes: - streetlights:read: Scope required for subscribing to channel - streetlights:write: Scope required for publishing to channel - + clientCredentials: + tokenUrl: 'https://example.com/api/oauth/dialog' + availableScopes: + 'streetlights:read': Scope required for subscribing to channel + 'streetlights:write': Scope required for publishing to channel parameters: streetlightId: description: The ID of the streetlight. - schema: - type: string - messageTraits: commonHeaders: headers: @@ -202,11 +233,11 @@ components: type: integer minimum: 0 maximum: 100 - operationTraits: kafka: bindings: kafka: clientId: type: string - enum: ['my-app-id'] + enum: + - my-app-id diff --git a/examples/websocket-gemini.yml b/examples/websocket-gemini.yml index 75af8d4d6..cc1cd9193 100644 --- a/examples/websocket-gemini.yml +++ b/examples/websocket-gemini.yml @@ -1,83 +1,137 @@ -# -# -# -# This example showcases usage of AsyncAPI for the purpose of describing a WebSocket API. It is based on a real public service maintained by company called Gemini that provides cryptocurency trading products. It uses AsyncAPI bindings. -# -# This AsyncAPI document describes their v1 of the API. The v2 is also available and changes in the way that it provides a multimessage channel, where you subscribe for messages by sending a subscription message instead of using query parameters. For example with multimessage channel check out this article https://www.asyncapi.com/blog/websocket-part2 about another real public API called Kraken -# -# All available learning materials about AsyncAPI and WebSocket are: -# - WebSocket, Shrek, and AsyncAPI - An Opinionated Intro article: https://www.asyncapi.com/blog/websocket-part1 -# - Creating AsyncAPI for WebSocket API - Step by Step article: https://www.asyncapi.com/blog/websocket-part2 -# - From API-First to Code Generation - A WebSocket Use Case article: https://www.asyncapi.com/blog/websocket-part3 -# - Live stream about topics mentioned in part 1 and 2 articles: https://www.youtube.com/watch?v=8tFBcf31e_c -# - -asyncapi: '2.5.0' - -# -# Overal information for users of the application -# +asyncapi: 3.0.0 info: title: Gemini Market Data Websocket API - version: '1.0.0' - contact: - name: Gemini - url: https://www.gemini.com/ - description: | - Market data is a public API that streams all the market data on a given symbol. - - You can quickly play with the API using [websocat](https://github.com/vi/websocat#installation) like this: + version: 1.0.0 + description: > + Market data is a public API that streams all the market data on a given + symbol. + + + You can quickly play with the API using + [websocat](https://github.com/vi/websocat#installation) like this: + ```bash + websocat wss://api.gemini.com/v1/marketdata/btcusd?heartbeat=true -S + ``` - -# -# Link to external docs -# -externalDocs: - url: https://docs.sandbox.gemini.com/websocket-api/#market-data - -# -# Details on how to connect to the application -# + contact: + name: Gemini + url: 'https://www.gemini.com/' + externalDocs: + url: 'https://docs.sandbox.gemini.com/websocket-api/#market-data' servers: public: - url: wss://api.gemini.com + host: api.gemini.com protocol: wss - -# -# Details about all the channels that you can listen to or send to messages -# channels: - /v1/marketdata/{symbol}: + '/v1/marketdata/{symbol}': + address: '/v1/marketdata/{symbol}' + messages: + subscribe.message: + $ref: '#/components/messages/marketData' parameters: symbol: - description: | - Symbols are formatted as CCY1CCY2 where prices are in CCY2 and quantities are in CCY1. To read more click [here](https://docs.sandbox.gemini.com/websocket-api/#symbols-and-minimums). - schema: - type: string - enum: ['btcusd', 'ethbtc', 'ethusd', 'zecusd', 'zecbtc', 'zeceth', 'zecbch', 'zecltc', 'bchusd', 'bchbtc', 'bcheth', 'ltcusd', 'ltcbtc', 'ltceth', 'ltcbch', 'batusd', 'daiusd', 'linkusd', 'oxtusd', 'batbtc', 'linkbtc', 'oxtbtc', 'bateth', 'linketh', 'oxteth', 'ampusd', 'compusd', 'paxgusd', 'mkrusd', 'zrxusd', 'kncusd', 'manausd', 'storjusd', 'snxusd', 'crvusd', 'balusd', 'uniusd', 'renusd', 'umausd', 'yfiusd', 'btcdai', 'ethdai', 'aaveusd', 'filusd', 'btceur', 'btcgbp', 'etheur', 'ethgbp', 'btcsgd', 'ethsgd', 'sklusd', 'grtusd', 'bntusd', '1inchusd', 'enjusd', 'lrcusd', 'sandusd', 'cubeusd', 'lptusd', 'bondusd', 'maticusd', 'injusd', 'sushiusd'] + enum: + - btcusd + - ethbtc + - ethusd + - zecusd + - zecbtc + - zeceth + - zecbch + - zecltc + - bchusd + - bchbtc + - bcheth + - ltcusd + - ltcbtc + - ltceth + - ltcbch + - batusd + - daiusd + - linkusd + - oxtusd + - batbtc + - linkbtc + - oxtbtc + - bateth + - linketh + - oxteth + - ampusd + - compusd + - paxgusd + - mkrusd + - zrxusd + - kncusd + - manausd + - storjusd + - snxusd + - crvusd + - balusd + - uniusd + - renusd + - umausd + - yfiusd + - btcdai + - ethdai + - aaveusd + - filusd + - btceur + - btcgbp + - etheur + - ethgbp + - btcsgd + - ethsgd + - sklusd + - grtusd + - bntusd + - 1inchusd + - enjusd + - lrcusd + - sandusd + - cubeusd + - lptusd + - bondusd + - maticusd + - injusd + - sushiusd + description: > + Symbols are formatted as CCY1CCY2 where prices are in CCY2 and + quantities are in CCY1. To read more click + [here](https://docs.sandbox.gemini.com/websocket-api/#symbols-and-minimums). bindings: ws: bindingVersion: 0.1.0 query: type: object - description: | + description: > The semantics of entry type filtering is: - If any entry type is specified as true or false, all of them must be explicitly flagged true to show up in the response - If no entry types filtering parameters are included in the url, then all entry types will appear in the response - NOTE: top_of_book has no meaning and initial book events are empty when only trades is specified + If any entry type is specified as true or false, all of them must be + explicitly flagged true to show up in the response + + If no entry types filtering parameters are included in the url, then + all entry types will appear in the response + + + NOTE: top_of_book has no meaning and initial book events are empty + when only trades is specified properties: heartbeat: type: boolean default: false - description: Optionally add this parameter and set to true to receive a heartbeat every 5 seconds + description: >- + Optionally add this parameter and set to true to receive a + heartbeat every 5 seconds top_of_book: type: boolean default: false - description: If absent or false, receive full order book depth; if present and true, receive top of book only. Only applies to bids and offers. + description: >- + If absent or false, receive full order book depth; if present + and true, receive top of book only. Only applies to bids and + offers. bids: type: boolean default: true @@ -94,25 +148,29 @@ channels: type: boolean default: true description: Include auction events - subscribe: - summary: Receive market updates on a given symbol - message: - $ref: '#/components/messages/marketData' - -# -# All reusable parts for readability and staying DRY -# +operations: + '/v1/marketdata/{symbol}.subscribe': + action: send + channel: + $ref: '#/channels/~1v1~1marketdata~1{symbol}' + summary: Receive market updates on a given symbol + messages: + - $ref: '#/components/messages/marketData' components: messages: marketData: summary: Message with marked data information. - description: | - The initial response message will show the existing state of the order book. Subsequent messages will show all executed trades, as well as all other changes to the order book from orders placed or canceled. + description: > + The initial response message will show the existing state of the order + book. Subsequent messages will show all executed trades, as well as all + other changes to the order book from orders placed or canceled. payload: $ref: '#/components/schemas/market' examples: - name: updateMessage - summary: Example of an update message that contains a change in price information. + summary: >- + Example of an update message that contains a change in price + information. payload: type: update eventId: 36902233362 @@ -127,7 +185,7 @@ components: delta: '0.002' reason: place - name: heartbeatMessage - summary: Example of additional heartbeat message when you enable them. + summary: Example of additional heartbeat message when you enable them. payload: type: heartbeat socket_sequence: 1656 @@ -154,13 +212,19 @@ components: const: update eventId: type: integer - description: A monotonically increasing sequence number indicating when this change occurred. These numbers are persistent and consistent between market data connections. + description: >- + A monotonically increasing sequence number indicating when this + change occurred. These numbers are persistent and consistent + between market data connections. events: $ref: '#/components/schemas/events' timestamp: type: string format: date-time - description: The timestamp in seconds for this group of events (included for compatibility reasons). We recommend using the timestampms field instead. + description: >- + The timestamp in seconds for this group of events (included for + compatibility reasons). We recommend using the timestampms field + instead. timestampms: type: string format: time @@ -174,40 +238,68 @@ components: - $ref: '#/components/schemas/default' default: type: object - description: This object is always part of the payload. In case of type=heartbeat, these are the only fields. + description: >- + This object is always part of the payload. In case of type=heartbeat, + these are the only fields. required: - - type - - socket_sequence + - type + - socket_sequence properties: socket_sequence: type: integer - description: zero-indexed monotonic increasing sequence number attached to each message sent - if there is a gap in this sequence, you have missed a message. If you choose to enable heartbeats, then heartbeat and update messages will share a single increasing sequence. See [Sequence Numbers](https://docs.sandbox.gemini.com/websocket-api/#sequence-numbers) for more information. + description: >- + zero-indexed monotonic increasing sequence number attached to each + message sent - if there is a gap in this sequence, you have missed a + message. If you choose to enable heartbeats, then heartbeat and + update messages will share a single increasing sequence. See + [Sequence + Numbers](https://docs.sandbox.gemini.com/websocket-api/#sequence-numbers) + for more information. events: type: array - description: Either a change to the order book, or the indication that a trade has occurred. + description: >- + Either a change to the order book, or the indication that a trade has + occurred. items: type: object additionalProperties: false properties: type: type: string - enum: ['trade', 'change', 'auction, block_trade'] + enum: + - trade + - change + - 'auction, block_trade' price: type: number - multipleOf: 1.000 + multipleOf: 1 description: The price of this order book entry. side: type: string - enum: ['bid', 'side'] + enum: + - bid + - side reason: type: string - enum: ['place', 'trade', 'cancel', 'initial'] - description: Indicates why the change has occurred. initial is for the initial response message, which will show the entire existing state of the order book. - remaining: + enum: + - place + - trade + - cancel + - initial + description: >- + Indicates why the change has occurred. initial is for the initial + response message, which will show the entire existing state of the + order book. + remaining: type: number - multipleOf: 1.000 - description: The quantity remaining at that price level after this change occurred. May be zero if all orders at this price level have been filled or canceled. + multipleOf: 1 + description: >- + The quantity remaining at that price level after this change + occurred. May be zero if all orders at this price level have been + filled or canceled. delta: type: number - multipleOf: 1.000 - description: The quantity changed. May be negative, if an order is filled or canceled. For initial messages, delta will equal remaining. \ No newline at end of file + multipleOf: 1 + description: >- + The quantity changed. May be negative, if an order is filled or + canceled. For initial messages, delta will equal remaining. diff --git a/scripts/converter/README.md b/scripts/converter/README.md new file mode 100644 index 000000000..4f5eb5599 --- /dev/null +++ b/scripts/converter/README.md @@ -0,0 +1 @@ +This script converts the official examples to newer versions once released. \ No newline at end of file diff --git a/scripts/converter/index.js b/scripts/converter/index.js new file mode 100644 index 000000000..02866b535 --- /dev/null +++ b/scripts/converter/index.js @@ -0,0 +1,57 @@ +const path = require('path'); +const fs = require('fs'); +const { convert } = require('@asyncapi/converter'); +const jsYaml = require('js-yaml'); +const examplesDirectory = path.resolve(__dirname, '../../examples'); +const toVersion = '3.0.0'; + +/** + * This function converts a single example file into a newer version and overwrite the old one. + * + * @param {*} exampleFile full path to file + */ +function convertExample(exampleFile) { + console.warn(`Converting: ${exampleFile}`); + const document = fs.readFileSync(exampleFile, 'utf-8'); + const loadedDocument = jsYaml.load(document); + if(loadedDocument.asyncapi === undefined) { + //Probably encountered a common file (used in other files), ignore + console.error(`___________________________________________________________________________________ + !!!Manual change required!!! + + ${exampleFile} is a shared resource among other AsyncAPI documents, make sure to manually inspect this! + +___________________________________________________________________________________`); + return; + } else if(loadedDocument.asyncapi === toVersion) { + console.warn(`${exampleFile} is already version ${toVersion}`); + return; + } + const convertedDocument = convert(document, toVersion, { }); + fs.writeFileSync(exampleFile, convertedDocument); +} + +/** + * Convert all examples within a single directory and nested directories. + * + * @param {*} directoryPath full path to a directory to convert examples from. + */ +async function convertExampleDir(directoryPath) { + let examplesFiles = await fs.promises.readdir(directoryPath); + examplesFiles = examplesFiles.map((file) => path.resolve(directoryPath, file)); + const nestedDirectory = examplesFiles.filter((file) => fs.lstatSync(file).isDirectory()); + for (const dir of nestedDirectory) { + await convertExampleDir(dir); + } + + // only convert .yml files + examplesFiles = examplesFiles.filter((file) => path.extname(file) === '.yml' || path.extname(file) === '.yaml'); + examplesFiles.forEach(convertExample); +} + +/** + * + */ +(async () => { + await convertExampleDir(examplesDirectory); +})() \ No newline at end of file diff --git a/scripts/converter/package-lock.json b/scripts/converter/package-lock.json new file mode 100644 index 000000000..2654cba02 --- /dev/null +++ b/scripts/converter/package-lock.json @@ -0,0 +1,1618 @@ +{ + "name": "converter", + "lockfileVersion": 3, + "requires": true, + "packages": { + "": { + "name": "converter", + "dependencies": { + "@asyncapi/converter": "1.3.1", + "js-yaml": "^4.1.0" + } + }, + "node_modules/@asyncapi/converter": { + "version": "1.3.1", + "resolved": "https://registry.npmjs.org/@asyncapi/converter/-/converter-1.3.1.tgz", + "integrity": "sha512-aLbJTGaaqP6IHc+ggi/feQ8oynP/2iEd4S0JuSyWZFSYSR2uAXsDH9FrAEFGPrhD9inbc+p0fTshnhKLNGdJQw==", + "dependencies": { + "@asyncapi/parser": "^2.0.0-next-major.11", + "js-yaml": "^3.14.1" + } + }, + "node_modules/@asyncapi/converter/node_modules/argparse": { + "version": "1.0.10", + "resolved": "https://registry.npmjs.org/argparse/-/argparse-1.0.10.tgz", + "integrity": "sha512-o5Roy6tNG4SL/FOkCAN6RzjiakZS25RLYFrcMttJqbdd8BWrnA+fGz57iN5Pb06pvBGvl5gQ0B48dJlslXvoTg==", + "dependencies": { + "sprintf-js": "~1.0.2" + } + }, + "node_modules/@asyncapi/converter/node_modules/js-yaml": { + "version": "3.14.1", + "resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-3.14.1.tgz", + "integrity": "sha512-okMH7OXXJ7YrN9Ok3/SXrnu4iX9yOk+25nqX4imS2npuvTYDmo/QEZoqwZkYaIDk3jVvBOTOIEgEhaLOynBS9g==", + "dependencies": { + "argparse": "^1.0.7", + "esprima": "^4.0.0" + }, + "bin": { + "js-yaml": "bin/js-yaml.js" + } + }, + "node_modules/@asyncapi/parser": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/@asyncapi/parser/-/parser-2.0.3.tgz", + "integrity": "sha512-2gtIQOaCz8sR70JFREpg6UwgUBboC/26JcAGySkXY/f1ayjcfDoNLi4LsDvmu6G21qLrGN2lI83i8iLG1AzTAw==", + "dependencies": { + "@asyncapi/specs": "^5.1.0", + "@openapi-contrib/openapi-schema-to-json-schema": "~3.2.0", + "@stoplight/json-ref-resolver": "^3.1.5", + "@stoplight/spectral-core": "^1.16.1", + "@stoplight/spectral-functions": "^1.7.2", + "@stoplight/spectral-parsers": "^1.0.2", + "@types/json-schema": "^7.0.11", + "@types/urijs": "^1.19.19", + "ajv": "^8.11.0", + "ajv-errors": "^3.0.0", + "ajv-formats": "^2.1.1", + "avsc": "^5.7.5", + "js-yaml": "^4.1.0", + "jsonpath-plus": "^7.2.0", + "node-fetch": "2.6.7", + "ramldt2jsonschema": "^1.2.3", + "webapi-parser": "^0.5.0" + } + }, + "node_modules/@asyncapi/specs": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/@asyncapi/specs/-/specs-5.1.0.tgz", + "integrity": "sha512-yffhETqehkim43luMnPKOwzY0D0YtU4bKpORIXIaid6p5Y5kDLrMGJaEPkNieQp03HMjhjFrnUPtT8kvqe0+aQ==", + "dependencies": { + "@types/json-schema": "^7.0.11" + } + }, + "node_modules/@jsep-plugin/regex": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/@jsep-plugin/regex/-/regex-1.0.3.tgz", + "integrity": "sha512-XfZgry4DwEZvSFtS/6Y+R48D7qJYJK6R9/yJFyUFHCIUMEEHuJ4X95TDgJp5QkmzfLYvapMPzskV5HpIDrREug==", + "engines": { + "node": ">= 10.16.0" + }, + "peerDependencies": { + "jsep": "^0.4.0||^1.0.0" + } + }, + "node_modules/@jsep-plugin/ternary": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/@jsep-plugin/ternary/-/ternary-1.1.3.tgz", + "integrity": "sha512-qtLGzCNzPVJ3kdH6/zoLWDPjauHIKiLSBAR71Wa0+PWvGA8wODUQvRgxtpUA5YqAYL3CQ8S4qXhd/9WuWTZirg==", + "engines": { + "node": ">= 10.16.0" + }, + "peerDependencies": { + "jsep": "^0.4.0||^1.0.0" + } + }, + "node_modules/@openapi-contrib/openapi-schema-to-json-schema": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/@openapi-contrib/openapi-schema-to-json-schema/-/openapi-schema-to-json-schema-3.2.0.tgz", + "integrity": "sha512-Gj6C0JwCr8arj0sYuslWXUBSP/KnUlEGnPW4qxlXvAl543oaNQgMgIgkQUA6vs5BCCvwTEiL8m/wdWzfl4UvSw==", + "dependencies": { + "fast-deep-equal": "^3.1.3" + } + }, + "node_modules/@stoplight/better-ajv-errors": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/@stoplight/better-ajv-errors/-/better-ajv-errors-1.0.3.tgz", + "integrity": "sha512-0p9uXkuB22qGdNfy3VeEhxkU5uwvp/KrBTAbrLBURv6ilxIVwanKwjMc41lQfIVgPGcOkmLbTolfFrSsueu7zA==", + "dependencies": { + "jsonpointer": "^5.0.0", + "leven": "^3.1.0" + }, + "engines": { + "node": "^12.20 || >= 14.13" + }, + "peerDependencies": { + "ajv": ">=8" + } + }, + "node_modules/@stoplight/json": { + "version": "3.21.0", + "resolved": "https://registry.npmjs.org/@stoplight/json/-/json-3.21.0.tgz", + "integrity": "sha512-5O0apqJ/t4sIevXCO3SBN9AHCEKKR/Zb4gaj7wYe5863jme9g02Q0n/GhM7ZCALkL+vGPTe4ZzTETP8TFtsw3g==", + "dependencies": { + "@stoplight/ordered-object-literal": "^1.0.3", + "@stoplight/path": "^1.3.2", + "@stoplight/types": "^13.6.0", + "jsonc-parser": "~2.2.1", + "lodash": "^4.17.21", + "safe-stable-stringify": "^1.1" + }, + "engines": { + "node": ">=8.3.0" + } + }, + "node_modules/@stoplight/json-ref-readers": { + "version": "1.2.2", + "resolved": "https://registry.npmjs.org/@stoplight/json-ref-readers/-/json-ref-readers-1.2.2.tgz", + "integrity": "sha512-nty0tHUq2f1IKuFYsLM4CXLZGHdMn+X/IwEUIpeSOXt0QjMUbL0Em57iJUDzz+2MkWG83smIigNZ3fauGjqgdQ==", + "dependencies": { + "node-fetch": "^2.6.0", + "tslib": "^1.14.1" + }, + "engines": { + "node": ">=8.3.0" + } + }, + "node_modules/@stoplight/json-ref-readers/node_modules/tslib": { + "version": "1.14.1", + "resolved": "https://registry.npmjs.org/tslib/-/tslib-1.14.1.tgz", + "integrity": "sha512-Xni35NKzjgMrwevysHTCArtLDpPvye8zV/0E4EyYn43P7/7qvQwPh9BGkHewbMulVntbigmcT7rdX3BNo9wRJg==" + }, + "node_modules/@stoplight/json-ref-resolver": { + "version": "3.1.6", + "resolved": "https://registry.npmjs.org/@stoplight/json-ref-resolver/-/json-ref-resolver-3.1.6.tgz", + "integrity": "sha512-YNcWv3R3n3U6iQYBsFOiWSuRGE5su1tJSiX6pAPRVk7dP0L7lqCteXGzuVRQ0gMZqUl8v1P0+fAKxF6PLo9B5A==", + "dependencies": { + "@stoplight/json": "^3.21.0", + "@stoplight/path": "^1.3.2", + "@stoplight/types": "^12.3.0 || ^13.0.0", + "@types/urijs": "^1.19.19", + "dependency-graph": "~0.11.0", + "fast-memoize": "^2.5.2", + "immer": "^9.0.6", + "lodash": "^4.17.21", + "tslib": "^2.6.0", + "urijs": "^1.19.11" + }, + "engines": { + "node": ">=8.3.0" + } + }, + "node_modules/@stoplight/ordered-object-literal": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/@stoplight/ordered-object-literal/-/ordered-object-literal-1.0.4.tgz", + "integrity": "sha512-OF8uib1jjDs5/cCU+iOVy+GJjU3X7vk/qJIkIJFqwmlJKrrtijFmqwbu8XToXrwTYLQTP+Hebws5gtZEmk9jag==", + "engines": { + "node": ">=8" + } + }, + "node_modules/@stoplight/path": { + "version": "1.3.2", + "resolved": "https://registry.npmjs.org/@stoplight/path/-/path-1.3.2.tgz", + "integrity": "sha512-lyIc6JUlUA8Ve5ELywPC8I2Sdnh1zc1zmbYgVarhXIp9YeAB0ReeqmGEOWNtlHkbP2DAA1AL65Wfn2ncjK/jtQ==", + "engines": { + "node": ">=8" + } + }, + "node_modules/@stoplight/spectral-core": { + "version": "1.18.3", + "resolved": "https://registry.npmjs.org/@stoplight/spectral-core/-/spectral-core-1.18.3.tgz", + "integrity": "sha512-YY8x7X2SWJIhGTLPol+eFiQpWPz0D0mJdkK2i4A0QJG68KkNhypP6+JBC7/Kz3XWjqr0L/RqAd+N5cQLPOKZGQ==", + "dependencies": { + "@stoplight/better-ajv-errors": "1.0.3", + "@stoplight/json": "~3.21.0", + "@stoplight/path": "1.3.2", + "@stoplight/spectral-parsers": "^1.0.0", + "@stoplight/spectral-ref-resolver": "^1.0.0", + "@stoplight/spectral-runtime": "^1.0.0", + "@stoplight/types": "~13.6.0", + "@types/es-aggregate-error": "^1.0.2", + "@types/json-schema": "^7.0.11", + "ajv": "^8.6.0", + "ajv-errors": "~3.0.0", + "ajv-formats": "~2.1.0", + "es-aggregate-error": "^1.0.7", + "jsonpath-plus": "7.1.0", + "lodash": "~4.17.21", + "lodash.topath": "^4.5.2", + "minimatch": "3.1.2", + "nimma": "0.2.2", + "pony-cause": "^1.0.0", + "simple-eval": "1.0.0", + "tslib": "^2.3.0" + }, + "engines": { + "node": "^12.20 || >= 14.13" + } + }, + "node_modules/@stoplight/spectral-core/node_modules/@stoplight/types": { + "version": "13.6.0", + "resolved": "https://registry.npmjs.org/@stoplight/types/-/types-13.6.0.tgz", + "integrity": "sha512-dzyuzvUjv3m1wmhPfq82lCVYGcXG0xUYgqnWfCq3PCVR4BKFhjdkHrnJ+jIDoMKvXb05AZP/ObQF6+NpDo29IQ==", + "dependencies": { + "@types/json-schema": "^7.0.4", + "utility-types": "^3.10.0" + }, + "engines": { + "node": "^12.20 || >=14.13" + } + }, + "node_modules/@stoplight/spectral-core/node_modules/jsonpath-plus": { + "version": "7.1.0", + "resolved": "https://registry.npmjs.org/jsonpath-plus/-/jsonpath-plus-7.1.0.tgz", + "integrity": "sha512-gTaNRsPWO/K2KY6MrqaUFClF9kmuM6MFH5Dhg1VYDODgFbByw1yb7xu3hrViE/sz+dGOeMWgCzwUwQtAnCTE9g==", + "engines": { + "node": ">=12.0.0" + } + }, + "node_modules/@stoplight/spectral-formats": { + "version": "1.5.0", + "resolved": "https://registry.npmjs.org/@stoplight/spectral-formats/-/spectral-formats-1.5.0.tgz", + "integrity": "sha512-VskkdU3qBSvI1dfJ79ysjvTssfNlbA6wrf/XkXK6iTyjfIVqOAWVtjypTb2U95tN/X8IjIBBhNWtZ4tNVZilrA==", + "dependencies": { + "@stoplight/json": "^3.17.0", + "@stoplight/spectral-core": "^1.8.0", + "@types/json-schema": "^7.0.7", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/@stoplight/spectral-functions": { + "version": "1.7.2", + "resolved": "https://registry.npmjs.org/@stoplight/spectral-functions/-/spectral-functions-1.7.2.tgz", + "integrity": "sha512-f+61/FtIkQeIo+a269CeaeqjpyRsgDyIk6DGr7iS4hyuk1PPk7Uf6MNRDs9FEIBh7CpdEJ+HSHbMLwgpymWTIw==", + "dependencies": { + "@stoplight/better-ajv-errors": "1.0.3", + "@stoplight/json": "^3.17.1", + "@stoplight/spectral-core": "^1.7.0", + "@stoplight/spectral-formats": "^1.0.0", + "@stoplight/spectral-runtime": "^1.1.0", + "ajv": "^8.6.3", + "ajv-draft-04": "~1.0.0", + "ajv-errors": "~3.0.0", + "ajv-formats": "~2.1.0", + "lodash": "~4.17.21", + "tslib": "^2.3.0" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/@stoplight/spectral-parsers": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/@stoplight/spectral-parsers/-/spectral-parsers-1.0.3.tgz", + "integrity": "sha512-J0KW5Rh5cHWnJQ3yN+cr/ijNFVirPSR0pkQbdrNX30VboEl083UEDrQ3yov9kjLVIWEk9t9kKE7Eo3QT/k4JLA==", + "dependencies": { + "@stoplight/json": "~3.21.0", + "@stoplight/types": "^13.6.0", + "@stoplight/yaml": "~4.2.3", + "tslib": "^2.3.1" + }, + "engines": { + "node": "^12.20 || >=14.13" + } + }, + "node_modules/@stoplight/spectral-ref-resolver": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/@stoplight/spectral-ref-resolver/-/spectral-ref-resolver-1.0.4.tgz", + "integrity": "sha512-5baQIYL0NJTSVy8v6RxOR4U51xOUYM8wJri1YvlAT6bPN8m0EIxMwfVYi0xUZEMVeHcWx869nIkoqyWmOutF2A==", + "dependencies": { + "@stoplight/json-ref-readers": "1.2.2", + "@stoplight/json-ref-resolver": "~3.1.6", + "@stoplight/spectral-runtime": "^1.1.2", + "dependency-graph": "0.11.0", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/@stoplight/spectral-runtime": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/@stoplight/spectral-runtime/-/spectral-runtime-1.1.2.tgz", + "integrity": "sha512-fr5zRceXI+hrl82yAVoME+4GvJie8v3wmOe9tU+ZLRRNonizthy8qDi0Z/z4olE+vGreSDcuDOZ7JjRxFW5kTw==", + "dependencies": { + "@stoplight/json": "^3.17.0", + "@stoplight/path": "^1.3.2", + "@stoplight/types": "^12.3.0", + "abort-controller": "^3.0.0", + "lodash": "^4.17.21", + "node-fetch": "^2.6.7", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/@stoplight/spectral-runtime/node_modules/@stoplight/types": { + "version": "12.5.0", + "resolved": "https://registry.npmjs.org/@stoplight/types/-/types-12.5.0.tgz", + "integrity": "sha512-dwqYcDrGmEyUv5TWrDam5TGOxU72ufyQ7hnOIIDdmW5ezOwZaBFoR5XQ9AsH49w7wgvOqB2Bmo799pJPWnpCbg==", + "dependencies": { + "@types/json-schema": "^7.0.4", + "utility-types": "^3.10.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/@stoplight/types": { + "version": "13.17.0", + "resolved": "https://registry.npmjs.org/@stoplight/types/-/types-13.17.0.tgz", + "integrity": "sha512-9wzSi8MZQXjO+GSYehwMWFSUHO5qtDr282RxrDDsxO9ZHn0a4nWE+kTWDWSdtbiZrIEantTSkycmQJxKxnnRTQ==", + "dependencies": { + "@types/json-schema": "^7.0.4", + "utility-types": "^3.10.0" + }, + "engines": { + "node": "^12.20 || >=14.13" + } + }, + "node_modules/@stoplight/yaml": { + "version": "4.2.3", + "resolved": "https://registry.npmjs.org/@stoplight/yaml/-/yaml-4.2.3.tgz", + "integrity": "sha512-Mx01wjRAR9C7yLMUyYFTfbUf5DimEpHMkRDQ1PKLe9dfNILbgdxyrncsOXM3vCpsQ1Hfj4bPiGl+u4u6e9Akqw==", + "dependencies": { + "@stoplight/ordered-object-literal": "^1.0.1", + "@stoplight/types": "^13.0.0", + "@stoplight/yaml-ast-parser": "0.0.48", + "tslib": "^2.2.0" + }, + "engines": { + "node": ">=10.8" + } + }, + "node_modules/@stoplight/yaml-ast-parser": { + "version": "0.0.48", + "resolved": "https://registry.npmjs.org/@stoplight/yaml-ast-parser/-/yaml-ast-parser-0.0.48.tgz", + "integrity": "sha512-sV+51I7WYnLJnKPn2EMWgS4EUfoP4iWEbrWwbXsj0MZCB/xOK8j6+C9fntIdOM50kpx45ZLC3s6kwKivWuqvyg==" + }, + "node_modules/@types/es-aggregate-error": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/@types/es-aggregate-error/-/es-aggregate-error-1.0.2.tgz", + "integrity": "sha512-erqUpFXksaeR2kejKnhnjZjbFxUpGZx4Z7ydNL9ie8tEhXPiZTsLeUDJ6aR1F8j5wWUAtOAQWUqkc7givBJbBA==", + "dependencies": { + "@types/node": "*" + } + }, + "node_modules/@types/json-schema": { + "version": "7.0.12", + "resolved": "https://registry.npmjs.org/@types/json-schema/-/json-schema-7.0.12.tgz", + "integrity": "sha512-Hr5Jfhc9eYOQNPYO5WLDq/n4jqijdHNlDXjuAQkkt+mWdQR+XJToOHrsD4cPaMXpn6KO7y2+wM8AZEs8VpBLVA==" + }, + "node_modules/@types/node": { + "version": "20.4.4", + "resolved": "https://registry.npmjs.org/@types/node/-/node-20.4.4.tgz", + "integrity": "sha512-CukZhumInROvLq3+b5gLev+vgpsIqC2D0deQr/yS1WnxvmYLlJXZpaQrQiseMY+6xusl79E04UjWoqyr+t1/Ew==" + }, + "node_modules/@types/urijs": { + "version": "1.19.19", + "resolved": "https://registry.npmjs.org/@types/urijs/-/urijs-1.19.19.tgz", + "integrity": "sha512-FDJNkyhmKLw7uEvTxx5tSXfPeQpO0iy73Ry+PmYZJvQy0QIWX8a7kJ4kLWRf+EbTPJEPDSgPXHaM7pzr5lmvCg==" + }, + "node_modules/abort-controller": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/abort-controller/-/abort-controller-3.0.0.tgz", + "integrity": "sha512-h8lQ8tacZYnR3vNQTgibj+tODHI5/+l06Au2Pcriv/Gmet0eaj4TwWH41sO9wnHDiQsEj19q0drzdWdeAHtweg==", + "dependencies": { + "event-target-shim": "^5.0.0" + }, + "engines": { + "node": ">=6.5" + } + }, + "node_modules/ajv": { + "version": "8.12.0", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-8.12.0.tgz", + "integrity": "sha512-sRu1kpcO9yLtYxBKvqfTeh9KzZEwO3STyX1HT+4CaDzC6HpTGYhIhPIzj9XuKU7KYDwnaeh5hcOwjy1QuJzBPA==", + "dependencies": { + "fast-deep-equal": "^3.1.1", + "json-schema-traverse": "^1.0.0", + "require-from-string": "^2.0.2", + "uri-js": "^4.2.2" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/epoberezkin" + } + }, + "node_modules/ajv-draft-04": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/ajv-draft-04/-/ajv-draft-04-1.0.0.tgz", + "integrity": "sha512-mv00Te6nmYbRp5DCwclxtt7yV/joXJPGS7nM+97GdxvuttCOfgI3K4U25zboyeX0O+myI8ERluxQe5wljMmVIw==", + "peerDependencies": { + "ajv": "^8.5.0" + }, + "peerDependenciesMeta": { + "ajv": { + "optional": true + } + } + }, + "node_modules/ajv-errors": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/ajv-errors/-/ajv-errors-3.0.0.tgz", + "integrity": "sha512-V3wD15YHfHz6y0KdhYFjyy9vWtEVALT9UrxfN3zqlI6dMioHnJrqOYfyPKol3oqrnCM9uwkcdCwkJ0WUcbLMTQ==", + "peerDependencies": { + "ajv": "^8.0.1" + } + }, + "node_modules/ajv-formats": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/ajv-formats/-/ajv-formats-2.1.1.tgz", + "integrity": "sha512-Wx0Kx52hxE7C18hkMEggYlEifqWZtYaRgouJor+WMdPnQyEK13vgEWyVNup7SoeeoLMsr4kf5h6dOW11I15MUA==", + "dependencies": { + "ajv": "^8.0.0" + }, + "peerDependencies": { + "ajv": "^8.0.0" + }, + "peerDependenciesMeta": { + "ajv": { + "optional": true + } + } + }, + "node_modules/argparse": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/argparse/-/argparse-2.0.1.tgz", + "integrity": "sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q==" + }, + "node_modules/array-buffer-byte-length": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/array-buffer-byte-length/-/array-buffer-byte-length-1.0.0.tgz", + "integrity": "sha512-LPuwb2P+NrQw3XhxGc36+XSvuBPopovXYTR9Ew++Du9Yb/bx5AzBfrIsBoj0EZUifjQU+sHL21sseZ3jerWO/A==", + "dependencies": { + "call-bind": "^1.0.2", + "is-array-buffer": "^3.0.1" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/arraybuffer.prototype.slice": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/arraybuffer.prototype.slice/-/arraybuffer.prototype.slice-1.0.1.tgz", + "integrity": "sha512-09x0ZWFEjj4WD8PDbykUwo3t9arLn8NIzmmYEJFpYekOAQjpkGSyrQhNoRTcwwcFRu+ycWF78QZ63oWTqSjBcw==", + "dependencies": { + "array-buffer-byte-length": "^1.0.0", + "call-bind": "^1.0.2", + "define-properties": "^1.2.0", + "get-intrinsic": "^1.2.1", + "is-array-buffer": "^3.0.2", + "is-shared-array-buffer": "^1.0.2" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/astring": { + "version": "1.8.6", + "resolved": "https://registry.npmjs.org/astring/-/astring-1.8.6.tgz", + "integrity": "sha512-ISvCdHdlTDlH5IpxQJIex7BWBywFWgjJSVdwst+/iQCoEYnyOaQ95+X1JGshuBjGp6nxKUy1jMgE3zPqN7fQdg==", + "bin": { + "astring": "bin/astring" + } + }, + "node_modules/available-typed-arrays": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/available-typed-arrays/-/available-typed-arrays-1.0.5.tgz", + "integrity": "sha512-DMD0KiN46eipeziST1LPP/STfDU0sufISXmjSgvVsoU2tqxctQeASejWcfNtxYKqETM1UxQ8sp2OrSBWpHY6sw==", + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/avsc": { + "version": "5.7.7", + "resolved": "https://registry.npmjs.org/avsc/-/avsc-5.7.7.tgz", + "integrity": "sha512-9cYNccliXZDByFsFliVwk5GvTq058Fj513CiR4E60ndDwmuXzTJEp/Bp8FyuRmGyYupLjHLs+JA9/CBoVS4/NQ==", + "engines": { + "node": ">=0.11" + } + }, + "node_modules/balanced-match": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.2.tgz", + "integrity": "sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==" + }, + "node_modules/brace-expansion": { + "version": "1.1.11", + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", + "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", + "dependencies": { + "balanced-match": "^1.0.0", + "concat-map": "0.0.1" + } + }, + "node_modules/call-bind": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/call-bind/-/call-bind-1.0.2.tgz", + "integrity": "sha512-7O+FbCihrB5WGbFYesctwmTKae6rOiIzmz1icreWJ+0aA7LJfuqhEso2T9ncpcFtzMQtzXf2QGGueWJGTYsqrA==", + "dependencies": { + "function-bind": "^1.1.1", + "get-intrinsic": "^1.0.2" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/co": { + "version": "4.6.0", + "resolved": "https://registry.npmjs.org/co/-/co-4.6.0.tgz", + "integrity": "sha512-QVb0dM5HvG+uaxitm8wONl7jltx8dqhfU33DcqtOZcLSVIKSDDLDi7+0LbAKiyI8hD9u42m2YxXSkMGWThaecQ==", + "engines": { + "iojs": ">= 1.0.0", + "node": ">= 0.12.0" + } + }, + "node_modules/commander": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/commander/-/commander-5.1.0.tgz", + "integrity": "sha512-P0CysNDQ7rtVw4QIQtm+MRxV66vKFSvlsQvGYXZWR3qFU0jlMKHZZZgw8e+8DSah4UDKMqnknRDQz+xuQXQ/Zg==", + "engines": { + "node": ">= 6" + } + }, + "node_modules/concat-map": { + "version": "0.0.1", + "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", + "integrity": "sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg==" + }, + "node_modules/define-properties": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/define-properties/-/define-properties-1.2.0.tgz", + "integrity": "sha512-xvqAVKGfT1+UAvPwKTVw/njhdQ8ZhXK4lI0bCIuCMrp2up9nPnaDftrLtmpTazqd1o+UY4zgzU+avtMbDP+ldA==", + "dependencies": { + "has-property-descriptors": "^1.0.0", + "object-keys": "^1.1.1" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/dependency-graph": { + "version": "0.11.0", + "resolved": "https://registry.npmjs.org/dependency-graph/-/dependency-graph-0.11.0.tgz", + "integrity": "sha512-JeMq7fEshyepOWDfcfHK06N3MhyPhz++vtqWhMT5O9A3K42rdsEDpfdVqjaqaAhsw6a+ZqeDvQVtD0hFHQWrzg==", + "engines": { + "node": ">= 0.6.0" + } + }, + "node_modules/es-abstract": { + "version": "1.22.1", + "resolved": "https://registry.npmjs.org/es-abstract/-/es-abstract-1.22.1.tgz", + "integrity": "sha512-ioRRcXMO6OFyRpyzV3kE1IIBd4WG5/kltnzdxSCqoP8CMGs/Li+M1uF5o7lOkZVFjDs+NLesthnF66Pg/0q0Lw==", + "dependencies": { + "array-buffer-byte-length": "^1.0.0", + "arraybuffer.prototype.slice": "^1.0.1", + "available-typed-arrays": "^1.0.5", + "call-bind": "^1.0.2", + "es-set-tostringtag": "^2.0.1", + "es-to-primitive": "^1.2.1", + "function.prototype.name": "^1.1.5", + "get-intrinsic": "^1.2.1", + "get-symbol-description": "^1.0.0", + "globalthis": "^1.0.3", + "gopd": "^1.0.1", + "has": "^1.0.3", + "has-property-descriptors": "^1.0.0", + "has-proto": "^1.0.1", + "has-symbols": "^1.0.3", + "internal-slot": "^1.0.5", + "is-array-buffer": "^3.0.2", + "is-callable": "^1.2.7", + "is-negative-zero": "^2.0.2", + "is-regex": "^1.1.4", + "is-shared-array-buffer": "^1.0.2", + "is-string": "^1.0.7", + "is-typed-array": "^1.1.10", + "is-weakref": "^1.0.2", + "object-inspect": "^1.12.3", + "object-keys": "^1.1.1", + "object.assign": "^4.1.4", + "regexp.prototype.flags": "^1.5.0", + "safe-array-concat": "^1.0.0", + "safe-regex-test": "^1.0.0", + "string.prototype.trim": "^1.2.7", + "string.prototype.trimend": "^1.0.6", + "string.prototype.trimstart": "^1.0.6", + "typed-array-buffer": "^1.0.0", + "typed-array-byte-length": "^1.0.0", + "typed-array-byte-offset": "^1.0.0", + "typed-array-length": "^1.0.4", + "unbox-primitive": "^1.0.2", + "which-typed-array": "^1.1.10" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/es-aggregate-error": { + "version": "1.0.9", + "resolved": "https://registry.npmjs.org/es-aggregate-error/-/es-aggregate-error-1.0.9.tgz", + "integrity": "sha512-fvnX40sb538wdU6r4s35cq4EY6Lr09Upj40BEVem4LEsuW8XgQep9yD5Q1U2KftokNp1rWODFJ2qwZSsAjFpbg==", + "dependencies": { + "define-properties": "^1.1.4", + "es-abstract": "^1.20.4", + "function-bind": "^1.1.1", + "functions-have-names": "^1.2.3", + "get-intrinsic": "^1.1.3", + "globalthis": "^1.0.3", + "has-property-descriptors": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/es-set-tostringtag": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/es-set-tostringtag/-/es-set-tostringtag-2.0.1.tgz", + "integrity": "sha512-g3OMbtlwY3QewlqAiMLI47KywjWZoEytKr8pf6iTC8uJq5bIAH52Z9pnQ8pVL6whrCto53JZDuUIsifGeLorTg==", + "dependencies": { + "get-intrinsic": "^1.1.3", + "has": "^1.0.3", + "has-tostringtag": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/es-to-primitive": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/es-to-primitive/-/es-to-primitive-1.2.1.tgz", + "integrity": "sha512-QCOllgZJtaUo9miYBcLChTUaHNjJF3PYs1VidD7AwiEj1kYxKeQTctLAezAOH5ZKRH0g2IgPn6KwB4IT8iRpvA==", + "dependencies": { + "is-callable": "^1.1.4", + "is-date-object": "^1.0.1", + "is-symbol": "^1.0.2" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/esprima": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/esprima/-/esprima-4.0.1.tgz", + "integrity": "sha512-eGuFFw7Upda+g4p+QHvnW0RyTX/SVeJBDM/gCtMARO0cLuT2HcEKnTPvhjV6aGeqrCB/sbNop0Kszm0jsaWU4A==", + "bin": { + "esparse": "bin/esparse.js", + "esvalidate": "bin/esvalidate.js" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/event-target-shim": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/event-target-shim/-/event-target-shim-5.0.1.tgz", + "integrity": "sha512-i/2XbnSz/uxRCU6+NdVJgKWDTM427+MqYbkQzD321DuCQJUqOuJKIA0IM2+W2xtYHdKOmZ4dR6fExsd4SXL+WQ==", + "engines": { + "node": ">=6" + } + }, + "node_modules/fast-deep-equal": { + "version": "3.1.3", + "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-3.1.3.tgz", + "integrity": "sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q==" + }, + "node_modules/fast-json-stable-stringify": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/fast-json-stable-stringify/-/fast-json-stable-stringify-2.1.0.tgz", + "integrity": "sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw==" + }, + "node_modules/fast-memoize": { + "version": "2.5.2", + "resolved": "https://registry.npmjs.org/fast-memoize/-/fast-memoize-2.5.2.tgz", + "integrity": "sha512-Ue0LwpDYErFbmNnZSF0UH6eImUwDmogUO1jyE+JbN2gsQz/jICm1Ve7t9QT0rNSsfJt+Hs4/S3GnsDVjL4HVrw==" + }, + "node_modules/for-each": { + "version": "0.3.3", + "resolved": "https://registry.npmjs.org/for-each/-/for-each-0.3.3.tgz", + "integrity": "sha512-jqYfLp7mo9vIyQf8ykW2v7A+2N4QjeCeI5+Dz9XraiO1ign81wjiH7Fb9vSOWvQfNtmSa4H2RoQTrrXivdUZmw==", + "dependencies": { + "is-callable": "^1.1.3" + } + }, + "node_modules/function-bind": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.1.tgz", + "integrity": "sha512-yIovAzMX49sF8Yl58fSCWJ5svSLuaibPxXQJFLmBObTuCr0Mf1KiPopGM9NiFjiYBCbfaa2Fh6breQ6ANVTI0A==" + }, + "node_modules/function.prototype.name": { + "version": "1.1.5", + "resolved": "https://registry.npmjs.org/function.prototype.name/-/function.prototype.name-1.1.5.tgz", + "integrity": "sha512-uN7m/BzVKQnCUF/iW8jYea67v++2u7m5UgENbHRtdDVclOUP+FMPlCNdmk0h/ysGyo2tavMJEDqJAkJdRa1vMA==", + "dependencies": { + "call-bind": "^1.0.2", + "define-properties": "^1.1.3", + "es-abstract": "^1.19.0", + "functions-have-names": "^1.2.2" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/functions-have-names": { + "version": "1.2.3", + "resolved": "https://registry.npmjs.org/functions-have-names/-/functions-have-names-1.2.3.tgz", + "integrity": "sha512-xckBUXyTIqT97tq2x2AMb+g163b5JFysYk0x4qxNFwbfQkmNZoiRHb6sPzI9/QV33WeuvVYBUIiD4NzNIyqaRQ==", + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/get-intrinsic": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/get-intrinsic/-/get-intrinsic-1.2.1.tgz", + "integrity": "sha512-2DcsyfABl+gVHEfCOaTrWgyt+tb6MSEGmKq+kI5HwLbIYgjgmMcV8KQ41uaKz1xxUcn9tJtgFbQUEVcEbd0FYw==", + "dependencies": { + "function-bind": "^1.1.1", + "has": "^1.0.3", + "has-proto": "^1.0.1", + "has-symbols": "^1.0.3" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/get-symbol-description": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/get-symbol-description/-/get-symbol-description-1.0.0.tgz", + "integrity": "sha512-2EmdH1YvIQiZpltCNgkuiUnyukzxM/R6NDJX31Ke3BG1Nq5b0S2PhX59UKi9vZpPDQVdqn+1IcaAwnzTT5vCjw==", + "dependencies": { + "call-bind": "^1.0.2", + "get-intrinsic": "^1.1.1" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/globalthis": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/globalthis/-/globalthis-1.0.3.tgz", + "integrity": "sha512-sFdI5LyBiNTHjRd7cGPWapiHWMOXKyuBNX/cWJ3NfzrZQVa8GI/8cofCl74AOVqq9W5kNmguTIzJ/1s2gyI9wA==", + "dependencies": { + "define-properties": "^1.1.3" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/gopd": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/gopd/-/gopd-1.0.1.tgz", + "integrity": "sha512-d65bNlIadxvpb/A2abVdlqKqV563juRnZ1Wtk6s1sIR8uNsXR70xqIzVqxVf1eTqDunwT2MkczEeaezCKTZhwA==", + "dependencies": { + "get-intrinsic": "^1.1.3" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/has": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/has/-/has-1.0.3.tgz", + "integrity": "sha512-f2dvO0VU6Oej7RkWJGrehjbzMAjFp5/VKPp5tTpWIV4JHHZK1/BxbFRtf/siA2SWTe09caDmVtYYzWEIbBS4zw==", + "dependencies": { + "function-bind": "^1.1.1" + }, + "engines": { + "node": ">= 0.4.0" + } + }, + "node_modules/has-bigints": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/has-bigints/-/has-bigints-1.0.2.tgz", + "integrity": "sha512-tSvCKtBr9lkF0Ex0aQiP9N+OpV4zi2r/Nee5VkRDbaqv35RLYMzbwQfFSZZH0kR+Rd6302UJZ2p/bJCEoR3VoQ==", + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/has-property-descriptors": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/has-property-descriptors/-/has-property-descriptors-1.0.0.tgz", + "integrity": "sha512-62DVLZGoiEBDHQyqG4w9xCuZ7eJEwNmJRWw2VY84Oedb7WFcA27fiEVe8oUQx9hAUJ4ekurquucTGwsyO1XGdQ==", + "dependencies": { + "get-intrinsic": "^1.1.1" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/has-proto": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/has-proto/-/has-proto-1.0.1.tgz", + "integrity": "sha512-7qE+iP+O+bgF9clE5+UoBFzE65mlBiVj3tKCrlNQ0Ogwm0BjpT/gK4SlLYDMybDh5I3TCTKnPPa0oMG7JDYrhg==", + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/has-symbols": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/has-symbols/-/has-symbols-1.0.3.tgz", + "integrity": "sha512-l3LCuF6MgDNwTDKkdYGEihYjt5pRPbEg46rtlmnSPlUbgmB8LOIrKJbYYFBSbnPaJexMKtiPO8hmeRjRz2Td+A==", + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/has-tostringtag": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/has-tostringtag/-/has-tostringtag-1.0.0.tgz", + "integrity": "sha512-kFjcSNhnlGV1kyoGk7OXKSawH5JOb/LzUc5w9B02hOTO0dfFRjbHQKvg1d6cf3HbeUmtU9VbbV3qzZ2Teh97WQ==", + "dependencies": { + "has-symbols": "^1.0.2" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/immer": { + "version": "9.0.21", + "resolved": "https://registry.npmjs.org/immer/-/immer-9.0.21.tgz", + "integrity": "sha512-bc4NBHqOqSfRW7POMkHd51LvClaeMXpm8dx0e8oE2GORbq5aRK7Bxl4FyzVLdGtLmvLKL7BTDBG5ACQm4HWjTA==", + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/immer" + } + }, + "node_modules/internal-slot": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/internal-slot/-/internal-slot-1.0.5.tgz", + "integrity": "sha512-Y+R5hJrzs52QCG2laLn4udYVnxsfny9CpOhNhUvk/SSSVyF6T27FzRbF0sroPidSu3X8oEAkOn2K804mjpt6UQ==", + "dependencies": { + "get-intrinsic": "^1.2.0", + "has": "^1.0.3", + "side-channel": "^1.0.4" + }, + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/is-array-buffer": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/is-array-buffer/-/is-array-buffer-3.0.2.tgz", + "integrity": "sha512-y+FyyR/w8vfIRq4eQcM1EYgSTnmHXPqaF+IgzgraytCFq5Xh8lllDVmAZolPJiZttZLeFSINPYMaEJ7/vWUa1w==", + "dependencies": { + "call-bind": "^1.0.2", + "get-intrinsic": "^1.2.0", + "is-typed-array": "^1.1.10" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-bigint": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/is-bigint/-/is-bigint-1.0.4.tgz", + "integrity": "sha512-zB9CruMamjym81i2JZ3UMn54PKGsQzsJeo6xvN3HJJ4CAsQNB6iRutp2To77OfCNuoxspsIhzaPoO1zyCEhFOg==", + "dependencies": { + "has-bigints": "^1.0.1" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-boolean-object": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/is-boolean-object/-/is-boolean-object-1.1.2.tgz", + "integrity": "sha512-gDYaKHJmnj4aWxyj6YHyXVpdQawtVLHU5cb+eztPGczf6cjuTdwve5ZIEfgXqH4e57An1D1AKf8CZ3kYrQRqYA==", + "dependencies": { + "call-bind": "^1.0.2", + "has-tostringtag": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-callable": { + "version": "1.2.7", + "resolved": "https://registry.npmjs.org/is-callable/-/is-callable-1.2.7.tgz", + "integrity": "sha512-1BC0BVFhS/p0qtw6enp8e+8OD0UrK0oFLztSjNzhcKA3WDuJxxAPXzPuPtKkjEY9UUoEWlX/8fgKeu2S8i9JTA==", + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-date-object": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/is-date-object/-/is-date-object-1.0.5.tgz", + "integrity": "sha512-9YQaSxsAiSwcvS33MBk3wTCVnWK+HhF8VZR2jRxehM16QcVOdHqPn4VPHmRK4lSr38n9JriurInLcP90xsYNfQ==", + "dependencies": { + "has-tostringtag": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-negative-zero": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/is-negative-zero/-/is-negative-zero-2.0.2.tgz", + "integrity": "sha512-dqJvarLawXsFbNDeJW7zAz8ItJ9cd28YufuuFzh0G8pNHjJMnY08Dv7sYX2uF5UpQOwieAeOExEYAWWfu7ZZUA==", + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-number-object": { + "version": "1.0.7", + "resolved": "https://registry.npmjs.org/is-number-object/-/is-number-object-1.0.7.tgz", + "integrity": "sha512-k1U0IRzLMo7ZlYIfzRu23Oh6MiIFasgpb9X76eqfFZAqwH44UI4KTBvBYIZ1dSL9ZzChTB9ShHfLkR4pdW5krQ==", + "dependencies": { + "has-tostringtag": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-regex": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/is-regex/-/is-regex-1.1.4.tgz", + "integrity": "sha512-kvRdxDsxZjhzUX07ZnLydzS1TU/TJlTUHHY4YLL87e37oUA49DfkLqgy+VjFocowy29cKvcSiu+kIv728jTTVg==", + "dependencies": { + "call-bind": "^1.0.2", + "has-tostringtag": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-shared-array-buffer": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/is-shared-array-buffer/-/is-shared-array-buffer-1.0.2.tgz", + "integrity": "sha512-sqN2UDu1/0y6uvXyStCOzyhAjCSlHceFoMKJW8W9EU9cvic/QdsZ0kEU93HEy3IUEFZIiH/3w+AH/UQbPHNdhA==", + "dependencies": { + "call-bind": "^1.0.2" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-string": { + "version": "1.0.7", + "resolved": "https://registry.npmjs.org/is-string/-/is-string-1.0.7.tgz", + "integrity": "sha512-tE2UXzivje6ofPW7l23cjDOMa09gb7xlAqG6jG5ej6uPV32TlWP3NKPigtaGeHNu9fohccRYvIiZMfOOnOYUtg==", + "dependencies": { + "has-tostringtag": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-symbol": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/is-symbol/-/is-symbol-1.0.4.tgz", + "integrity": "sha512-C/CPBqKWnvdcxqIARxyOh4v1UUEOCHpgDa0WYgpKDFMszcrPcffg5uhwSgPCLD2WWxmq6isisz87tzT01tuGhg==", + "dependencies": { + "has-symbols": "^1.0.2" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-typed-array": { + "version": "1.1.12", + "resolved": "https://registry.npmjs.org/is-typed-array/-/is-typed-array-1.1.12.tgz", + "integrity": "sha512-Z14TF2JNG8Lss5/HMqt0//T9JeHXttXy5pH/DBU4vi98ozO2btxzq9MwYDZYnKwU8nRsz/+GVFVRDq3DkVuSPg==", + "dependencies": { + "which-typed-array": "^1.1.11" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-weakref": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/is-weakref/-/is-weakref-1.0.2.tgz", + "integrity": "sha512-qctsuLZmIQ0+vSSMfoVvyFe2+GSEvnmZ2ezTup1SBse9+twCCeial6EEi3Nc2KFcf6+qz2FBPnjXsk8xhKSaPQ==", + "dependencies": { + "call-bind": "^1.0.2" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/isarray": { + "version": "2.0.5", + "resolved": "https://registry.npmjs.org/isarray/-/isarray-2.0.5.tgz", + "integrity": "sha512-xHjhDr3cNBK0BzdUJSPXZntQUx/mwMS5Rw4A7lPJ90XGAO6ISP/ePDNuo0vhqOZU+UD5JoodwCAAoZQd3FeAKw==" + }, + "node_modules/js-yaml": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-4.1.0.tgz", + "integrity": "sha512-wpxZs9NoxZaJESJGIZTyDEaYpl0FKSA+FB9aJiyemKhMwkxQg63h4T1KJgUGHpTqPDNRcmmYLugrRjJlBtWvRA==", + "dependencies": { + "argparse": "^2.0.1" + }, + "bin": { + "js-yaml": "bin/js-yaml.js" + } + }, + "node_modules/jsep": { + "version": "1.3.8", + "resolved": "https://registry.npmjs.org/jsep/-/jsep-1.3.8.tgz", + "integrity": "sha512-qofGylTGgYj9gZFsHuyWAN4jr35eJ66qJCK4eKDnldohuUoQFbU3iZn2zjvEbd9wOAhP9Wx5DsAAduTyE1PSWQ==", + "engines": { + "node": ">= 10.16.0" + } + }, + "node_modules/json-schema-migrate": { + "version": "0.2.0", + "resolved": "https://registry.npmjs.org/json-schema-migrate/-/json-schema-migrate-0.2.0.tgz", + "integrity": "sha512-dq4/oHWmtw/+0ytnXsDqVn+VsVweTEmzm5jLgguPn9BjSzn6/q58ZiZx3BHiQyJs612f0T5Z+MrUEUUY5DHsRg==", + "dependencies": { + "ajv": "^5.0.0" + } + }, + "node_modules/json-schema-migrate/node_modules/ajv": { + "version": "5.5.2", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-5.5.2.tgz", + "integrity": "sha512-Ajr4IcMXq/2QmMkEmSvxqfLN5zGmJ92gHXAeOXq1OekoH2rfDNsgdDoL2f7QaRCy7G/E6TpxBVdRuNraMztGHw==", + "dependencies": { + "co": "^4.6.0", + "fast-deep-equal": "^1.0.0", + "fast-json-stable-stringify": "^2.0.0", + "json-schema-traverse": "^0.3.0" + } + }, + "node_modules/json-schema-migrate/node_modules/fast-deep-equal": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-1.1.0.tgz", + "integrity": "sha512-fueX787WZKCV0Is4/T2cyAdM4+x1S3MXXOAhavE1ys/W42SHAPacLTQhucja22QBYrfGw50M2sRiXPtTGv9Ymw==" + }, + "node_modules/json-schema-migrate/node_modules/json-schema-traverse": { + "version": "0.3.1", + "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.3.1.tgz", + "integrity": "sha512-4JD/Ivzg7PoW8NzdrBSr3UFwC9mHgvI7Z6z3QGBsSHgKaRTUDmyZAAKJo2UbG1kUVfS9WS8bi36N49U1xw43DA==" + }, + "node_modules/json-schema-traverse": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-1.0.0.tgz", + "integrity": "sha512-NM8/P9n3XjXhIZn1lLhkFaACTOURQXjWhV4BA/RnOv8xvgqtqpAX9IO4mRQxSx1Rlo4tqzeqb0sOlruaOy3dug==" + }, + "node_modules/jsonc-parser": { + "version": "2.2.1", + "resolved": "https://registry.npmjs.org/jsonc-parser/-/jsonc-parser-2.2.1.tgz", + "integrity": "sha512-o6/yDBYccGvTz1+QFevz6l6OBZ2+fMVu2JZ9CIhzsYRX4mjaK5IyX9eldUdCmga16zlgQxyrj5pt9kzuj2C02w==" + }, + "node_modules/jsonpath-plus": { + "version": "7.2.0", + "resolved": "https://registry.npmjs.org/jsonpath-plus/-/jsonpath-plus-7.2.0.tgz", + "integrity": "sha512-zBfiUPM5nD0YZSBT/o/fbCUlCcepMIdP0CJZxM1+KgA4f2T206f6VAg9e7mX35+KlMaIc5qXW34f3BnwJ3w+RA==", + "engines": { + "node": ">=12.0.0" + } + }, + "node_modules/jsonpointer": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/jsonpointer/-/jsonpointer-5.0.1.tgz", + "integrity": "sha512-p/nXbhSEcu3pZRdkW1OfJhpsVtW1gd4Wa1fnQc9YLiTfAjn0312eMKimbdIQzuZl9aa9xUGaRlP9T/CJE/ditQ==", + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/leven": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/leven/-/leven-3.1.0.tgz", + "integrity": "sha512-qsda+H8jTaUaN/x5vzW2rzc+8Rw4TAQ/4KjB46IwK5VH+IlVeeeje/EoZRpiXvIqjFgK84QffqPztGI3VBLG1A==", + "engines": { + "node": ">=6" + } + }, + "node_modules/lodash": { + "version": "4.17.21", + "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.21.tgz", + "integrity": "sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg==" + }, + "node_modules/lodash.topath": { + "version": "4.5.2", + "resolved": "https://registry.npmjs.org/lodash.topath/-/lodash.topath-4.5.2.tgz", + "integrity": "sha512-1/W4dM+35DwvE/iEd1M9ekewOSTlpFekhw9mhAtrwjVqUr83/ilQiyAvmg4tVX7Unkcfl1KC+i9WdaT4B6aQcg==" + }, + "node_modules/minimatch": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.1.2.tgz", + "integrity": "sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==", + "dependencies": { + "brace-expansion": "^1.1.7" + }, + "engines": { + "node": "*" + } + }, + "node_modules/nimma": { + "version": "0.2.2", + "resolved": "https://registry.npmjs.org/nimma/-/nimma-0.2.2.tgz", + "integrity": "sha512-V52MLl7BU+tH2Np9tDrIXK8bql3MVUadnMIl/0/oZSGC9keuro0O9UUv9QKp0aMvtN8HRew4G7byY7H4eWsxaQ==", + "dependencies": { + "@jsep-plugin/regex": "^1.0.1", + "@jsep-plugin/ternary": "^1.0.2", + "astring": "^1.8.1", + "jsep": "^1.2.0" + }, + "engines": { + "node": "^12.20 || >=14.13" + }, + "optionalDependencies": { + "jsonpath-plus": "^6.0.1", + "lodash.topath": "^4.5.2" + } + }, + "node_modules/nimma/node_modules/jsonpath-plus": { + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/jsonpath-plus/-/jsonpath-plus-6.0.1.tgz", + "integrity": "sha512-EvGovdvau6FyLexFH2OeXfIITlgIbgZoAZe3usiySeaIDm5QS+A10DKNpaPBBqqRSZr2HN6HVNXxtwUAr2apEw==", + "optional": true, + "engines": { + "node": ">=10.0.0" + } + }, + "node_modules/node-fetch": { + "version": "2.6.7", + "resolved": "https://registry.npmjs.org/node-fetch/-/node-fetch-2.6.7.tgz", + "integrity": "sha512-ZjMPFEfVx5j+y2yF35Kzx5sF7kDzxuDj6ziH4FFbOp87zKDZNx8yExJIb05OGF4Nlt9IHFIMBkRl41VdvcNdbQ==", + "dependencies": { + "whatwg-url": "^5.0.0" + }, + "engines": { + "node": "4.x || >=6.0.0" + }, + "peerDependencies": { + "encoding": "^0.1.0" + }, + "peerDependenciesMeta": { + "encoding": { + "optional": true + } + } + }, + "node_modules/object-inspect": { + "version": "1.12.3", + "resolved": "https://registry.npmjs.org/object-inspect/-/object-inspect-1.12.3.tgz", + "integrity": "sha512-geUvdk7c+eizMNUDkRpW1wJwgfOiOeHbxBR/hLXK1aT6zmVSO0jsQcs7fj6MGw89jC/cjGfLcNOrtMYtGqm81g==", + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/object-keys": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/object-keys/-/object-keys-1.1.1.tgz", + "integrity": "sha512-NuAESUOUMrlIXOfHKzD6bpPu3tYt3xvjNdRIQ+FeT0lNb4K8WR70CaDxhuNguS2XG+GjkyMwOzsN5ZktImfhLA==", + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/object.assign": { + "version": "4.1.4", + "resolved": "https://registry.npmjs.org/object.assign/-/object.assign-4.1.4.tgz", + "integrity": "sha512-1mxKf0e58bvyjSCtKYY4sRe9itRk3PJpquJOjeIkz885CczcI4IvJJDLPS72oowuSh+pBxUFROpX+TU++hxhZQ==", + "dependencies": { + "call-bind": "^1.0.2", + "define-properties": "^1.1.4", + "has-symbols": "^1.0.3", + "object-keys": "^1.1.1" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/pony-cause": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/pony-cause/-/pony-cause-1.1.1.tgz", + "integrity": "sha512-PxkIc/2ZpLiEzQXu5YRDOUgBlfGYBY8156HY5ZcRAwwonMk5W/MrJP2LLkG/hF7GEQzaHo2aS7ho6ZLCOvf+6g==", + "engines": { + "node": ">=12.0.0" + } + }, + "node_modules/punycode": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.3.0.tgz", + "integrity": "sha512-rRV+zQD8tVFys26lAGR9WUuS4iUAngJScM+ZRSKtvl5tKeZ2t5bvdNFdNHBW9FWR4guGHlgmsZ1G7BSm2wTbuA==", + "engines": { + "node": ">=6" + } + }, + "node_modules/ramldt2jsonschema": { + "version": "1.2.3", + "resolved": "https://registry.npmjs.org/ramldt2jsonschema/-/ramldt2jsonschema-1.2.3.tgz", + "integrity": "sha512-+wLDAV2NNv9NkfEUOYStaDu/6RYgYXeC1zLtXE+dMU/jDfjpN4iJnBGycDwFTFaIQGosOQhxph7fEX6Mpwxdug==", + "dependencies": { + "commander": "^5.0.0", + "js-yaml": "^3.14.0", + "json-schema-migrate": "^0.2.0", + "webapi-parser": "^0.5.0" + }, + "bin": { + "dt2js": "bin/dt2js.js", + "js2dt": "bin/js2dt.js" + } + }, + "node_modules/ramldt2jsonschema/node_modules/argparse": { + "version": "1.0.10", + "resolved": "https://registry.npmjs.org/argparse/-/argparse-1.0.10.tgz", + "integrity": "sha512-o5Roy6tNG4SL/FOkCAN6RzjiakZS25RLYFrcMttJqbdd8BWrnA+fGz57iN5Pb06pvBGvl5gQ0B48dJlslXvoTg==", + "dependencies": { + "sprintf-js": "~1.0.2" + } + }, + "node_modules/ramldt2jsonschema/node_modules/js-yaml": { + "version": "3.14.1", + "resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-3.14.1.tgz", + "integrity": "sha512-okMH7OXXJ7YrN9Ok3/SXrnu4iX9yOk+25nqX4imS2npuvTYDmo/QEZoqwZkYaIDk3jVvBOTOIEgEhaLOynBS9g==", + "dependencies": { + "argparse": "^1.0.7", + "esprima": "^4.0.0" + }, + "bin": { + "js-yaml": "bin/js-yaml.js" + } + }, + "node_modules/regexp.prototype.flags": { + "version": "1.5.0", + "resolved": "https://registry.npmjs.org/regexp.prototype.flags/-/regexp.prototype.flags-1.5.0.tgz", + "integrity": "sha512-0SutC3pNudRKgquxGoRGIz946MZVHqbNfPjBdxeOhBrdgDKlRoXmYLQN9xRbrR09ZXWeGAdPuif7egofn6v5LA==", + "dependencies": { + "call-bind": "^1.0.2", + "define-properties": "^1.2.0", + "functions-have-names": "^1.2.3" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/require-from-string": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/require-from-string/-/require-from-string-2.0.2.tgz", + "integrity": "sha512-Xf0nWe6RseziFMu+Ap9biiUbmplq6S9/p+7w7YXP/JBHhrUDDUhwa+vANyubuqfZWTveU//DYVGsDG7RKL/vEw==", + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/safe-array-concat": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/safe-array-concat/-/safe-array-concat-1.0.0.tgz", + "integrity": "sha512-9dVEFruWIsnie89yym+xWTAYASdpw3CJV7Li/6zBewGf9z2i1j31rP6jnY0pHEO4QZh6N0K11bFjWmdR8UGdPQ==", + "dependencies": { + "call-bind": "^1.0.2", + "get-intrinsic": "^1.2.0", + "has-symbols": "^1.0.3", + "isarray": "^2.0.5" + }, + "engines": { + "node": ">=0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/safe-regex-test": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/safe-regex-test/-/safe-regex-test-1.0.0.tgz", + "integrity": "sha512-JBUUzyOgEwXQY1NuPtvcj/qcBDbDmEvWufhlnXZIm75DEHp+afM1r1ujJpJsV/gSM4t59tpDyPi1sd6ZaPFfsA==", + "dependencies": { + "call-bind": "^1.0.2", + "get-intrinsic": "^1.1.3", + "is-regex": "^1.1.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/safe-stable-stringify": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/safe-stable-stringify/-/safe-stable-stringify-1.1.1.tgz", + "integrity": "sha512-ERq4hUjKDbJfE4+XtZLFPCDi8Vb1JqaxAPTxWFLBx8XcAlf9Bda/ZJdVezs/NAfsMQScyIlUMx+Yeu7P7rx5jw==" + }, + "node_modules/side-channel": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/side-channel/-/side-channel-1.0.4.tgz", + "integrity": "sha512-q5XPytqFEIKHkGdiMIrY10mvLRvnQh42/+GoBlFW3b2LXLE2xxJpZFdm94we0BaoV3RwJyGqg5wS7epxTv0Zvw==", + "dependencies": { + "call-bind": "^1.0.0", + "get-intrinsic": "^1.0.2", + "object-inspect": "^1.9.0" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/simple-eval": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/simple-eval/-/simple-eval-1.0.0.tgz", + "integrity": "sha512-kpKJR+bqTscgC0xuAl2xHN6bB12lHjC2DCUfqjAx19bQyO3R2EVLOurm3H9AUltv/uFVcSCVNc6faegR+8NYLw==", + "dependencies": { + "jsep": "^1.1.2" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/sprintf-js": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/sprintf-js/-/sprintf-js-1.0.3.tgz", + "integrity": "sha512-D9cPgkvLlV3t3IzL0D0YLvGA9Ahk4PcvVwUbN0dSGr1aP0Nrt4AEnTUbuGvquEC0mA64Gqt1fzirlRs5ibXx8g==" + }, + "node_modules/string.prototype.trim": { + "version": "1.2.7", + "resolved": "https://registry.npmjs.org/string.prototype.trim/-/string.prototype.trim-1.2.7.tgz", + "integrity": "sha512-p6TmeT1T3411M8Cgg9wBTMRtY2q9+PNy9EV1i2lIXUN/btt763oIfxwN3RR8VU6wHX8j/1CFy0L+YuThm6bgOg==", + "dependencies": { + "call-bind": "^1.0.2", + "define-properties": "^1.1.4", + "es-abstract": "^1.20.4" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/string.prototype.trimend": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/string.prototype.trimend/-/string.prototype.trimend-1.0.6.tgz", + "integrity": "sha512-JySq+4mrPf9EsDBEDYMOb/lM7XQLulwg5R/m1r0PXEFqrV0qHvl58sdTilSXtKOflCsK2E8jxf+GKC0T07RWwQ==", + "dependencies": { + "call-bind": "^1.0.2", + "define-properties": "^1.1.4", + "es-abstract": "^1.20.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/string.prototype.trimstart": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/string.prototype.trimstart/-/string.prototype.trimstart-1.0.6.tgz", + "integrity": "sha512-omqjMDaY92pbn5HOX7f9IccLA+U1tA9GvtU4JrodiXFfYB7jPzzHpRzpglLAjtUV6bB557zwClJezTqnAiYnQA==", + "dependencies": { + "call-bind": "^1.0.2", + "define-properties": "^1.1.4", + "es-abstract": "^1.20.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/tr46": { + "version": "0.0.3", + "resolved": "https://registry.npmjs.org/tr46/-/tr46-0.0.3.tgz", + "integrity": "sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw==" + }, + "node_modules/tslib": { + "version": "2.6.1", + "resolved": "https://registry.npmjs.org/tslib/-/tslib-2.6.1.tgz", + "integrity": "sha512-t0hLfiEKfMUoqhG+U1oid7Pva4bbDPHYfJNiB7BiIjRkj1pyC++4N3huJfqY6aRH6VTB0rvtzQwjM4K6qpfOig==" + }, + "node_modules/typed-array-buffer": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/typed-array-buffer/-/typed-array-buffer-1.0.0.tgz", + "integrity": "sha512-Y8KTSIglk9OZEr8zywiIHG/kmQ7KWyjseXs1CbSo8vC42w7hg2HgYTxSWwP0+is7bWDc1H+Fo026CpHFwm8tkw==", + "dependencies": { + "call-bind": "^1.0.2", + "get-intrinsic": "^1.2.1", + "is-typed-array": "^1.1.10" + }, + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/typed-array-byte-length": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/typed-array-byte-length/-/typed-array-byte-length-1.0.0.tgz", + "integrity": "sha512-Or/+kvLxNpeQ9DtSydonMxCx+9ZXOswtwJn17SNLvhptaXYDJvkFFP5zbfU/uLmvnBJlI4yrnXRxpdWH/M5tNA==", + "dependencies": { + "call-bind": "^1.0.2", + "for-each": "^0.3.3", + "has-proto": "^1.0.1", + "is-typed-array": "^1.1.10" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/typed-array-byte-offset": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/typed-array-byte-offset/-/typed-array-byte-offset-1.0.0.tgz", + "integrity": "sha512-RD97prjEt9EL8YgAgpOkf3O4IF9lhJFr9g0htQkm0rchFp/Vx7LW5Q8fSXXub7BXAODyUQohRMyOc3faCPd0hg==", + "dependencies": { + "available-typed-arrays": "^1.0.5", + "call-bind": "^1.0.2", + "for-each": "^0.3.3", + "has-proto": "^1.0.1", + "is-typed-array": "^1.1.10" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/typed-array-length": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/typed-array-length/-/typed-array-length-1.0.4.tgz", + "integrity": "sha512-KjZypGq+I/H7HI5HlOoGHkWUUGq+Q0TPhQurLbyrVrvnKTBgzLhIJ7j6J/XTQOi0d1RjyZ0wdas8bKs2p0x3Ng==", + "dependencies": { + "call-bind": "^1.0.2", + "for-each": "^0.3.3", + "is-typed-array": "^1.1.9" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/unbox-primitive": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/unbox-primitive/-/unbox-primitive-1.0.2.tgz", + "integrity": "sha512-61pPlCD9h51VoreyJ0BReideM3MDKMKnh6+V9L08331ipq6Q8OFXZYiqP6n/tbHx4s5I9uRhcye6BrbkizkBDw==", + "dependencies": { + "call-bind": "^1.0.2", + "has-bigints": "^1.0.2", + "has-symbols": "^1.0.3", + "which-boxed-primitive": "^1.0.2" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/uri-js": { + "version": "4.4.1", + "resolved": "https://registry.npmjs.org/uri-js/-/uri-js-4.4.1.tgz", + "integrity": "sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg==", + "dependencies": { + "punycode": "^2.1.0" + } + }, + "node_modules/urijs": { + "version": "1.19.11", + "resolved": "https://registry.npmjs.org/urijs/-/urijs-1.19.11.tgz", + "integrity": "sha512-HXgFDgDommxn5/bIv0cnQZsPhHDA90NPHD6+c/v21U5+Sx5hoP8+dP9IZXBU1gIfvdRfhG8cel9QNPeionfcCQ==" + }, + "node_modules/utility-types": { + "version": "3.10.0", + "resolved": "https://registry.npmjs.org/utility-types/-/utility-types-3.10.0.tgz", + "integrity": "sha512-O11mqxmi7wMKCo6HKFt5AhO4BwY3VV68YU07tgxfz8zJTIxr4BpsezN49Ffwy9j3ZpwwJp4fkRwjRzq3uWE6Rg==", + "engines": { + "node": ">= 4" + } + }, + "node_modules/webapi-parser": { + "version": "0.5.0", + "resolved": "https://registry.npmjs.org/webapi-parser/-/webapi-parser-0.5.0.tgz", + "integrity": "sha512-fPt6XuMqLSvBz8exwX4QE1UT+pROLHa00EMDCdO0ybICduwQ1V4f7AWX4pNOpCp+x+0FjczEsOxtQU0d8L3QKw==", + "dependencies": { + "ajv": "6.5.2" + } + }, + "node_modules/webapi-parser/node_modules/ajv": { + "version": "6.5.2", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.5.2.tgz", + "integrity": "sha512-hOs7GfvI6tUI1LfZddH82ky6mOMyTuY0mk7kE2pWpmhhUSkumzaTO5vbVwij39MdwPQWCV4Zv57Eo06NtL/GVA==", + "dependencies": { + "fast-deep-equal": "^2.0.1", + "fast-json-stable-stringify": "^2.0.0", + "json-schema-traverse": "^0.4.1", + "uri-js": "^4.2.1" + } + }, + "node_modules/webapi-parser/node_modules/fast-deep-equal": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-2.0.1.tgz", + "integrity": "sha512-bCK/2Z4zLidyB4ReuIsvALH6w31YfAQDmXMqMx6FyfHqvBxtjC0eRumeSu4Bs3XtXwpyIywtSTrVT99BxY1f9w==" + }, + "node_modules/webapi-parser/node_modules/json-schema-traverse": { + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", + "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==" + }, + "node_modules/webidl-conversions": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/webidl-conversions/-/webidl-conversions-3.0.1.tgz", + "integrity": "sha512-2JAn3z8AR6rjK8Sm8orRC0h/bcl/DqL7tRPdGZ4I1CjdF+EaMLmYxBHyXuKL849eucPFhvBoxMsflfOb8kxaeQ==" + }, + "node_modules/whatwg-url": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/whatwg-url/-/whatwg-url-5.0.0.tgz", + "integrity": "sha512-saE57nupxk6v3HY35+jzBwYa0rKSy0XR8JSxZPwgLr7ys0IBzhGviA1/TUGJLmSVqs8pb9AnvICXEuOHLprYTw==", + "dependencies": { + "tr46": "~0.0.3", + "webidl-conversions": "^3.0.0" + } + }, + "node_modules/which-boxed-primitive": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/which-boxed-primitive/-/which-boxed-primitive-1.0.2.tgz", + "integrity": "sha512-bwZdv0AKLpplFY2KZRX6TvyuN7ojjr7lwkg6ml0roIy9YeuSr7JS372qlNW18UQYzgYK9ziGcerWqZOmEn9VNg==", + "dependencies": { + "is-bigint": "^1.0.1", + "is-boolean-object": "^1.1.0", + "is-number-object": "^1.0.4", + "is-string": "^1.0.5", + "is-symbol": "^1.0.3" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/which-typed-array": { + "version": "1.1.11", + "resolved": "https://registry.npmjs.org/which-typed-array/-/which-typed-array-1.1.11.tgz", + "integrity": "sha512-qe9UWWpkeG5yzZ0tNYxDmd7vo58HDBc39mZ0xWWpolAGADdFOzkfamWLDxkOWcvHQKVmdTyQdLD4NOfjLWTKew==", + "dependencies": { + "available-typed-arrays": "^1.0.5", + "call-bind": "^1.0.2", + "for-each": "^0.3.3", + "gopd": "^1.0.1", + "has-tostringtag": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + } + } +} diff --git a/scripts/converter/package.json b/scripts/converter/package.json new file mode 100644 index 000000000..68739aca8 --- /dev/null +++ b/scripts/converter/package.json @@ -0,0 +1,12 @@ +{ + "name": "converter", + "description": "This script converts the official examples to newer versions once released.", + "dependencies": { + "@asyncapi/converter": "1.3.1", + "js-yaml": "^4.1.0" + }, + "main": "index.js", + "scripts": { + "convert": "node index.js" + } +} From 05e7b7150de636ed502f8e83ab98b24c3b01d2a4 Mon Sep 17 00:00:00 2001 From: Lukasz Gornicki Date: Tue, 12 Sep 2023 09:34:12 +0200 Subject: [PATCH 27/41] fix: trigger release with fixed release workflow (#968) --- .github/workflows/release.yml | 1 + 1 file changed, 1 insertion(+) diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml index 6544ac8f5..5bb2cf9bd 100644 --- a/.github/workflows/release.yml +++ b/.github/workflows/release.yml @@ -11,6 +11,7 @@ jobs: release: name: 'Create GitHub release' runs-on: ubuntu-latest + steps: - name: Checkout repo uses: actions/checkout@v3 - name: Setup Node.js From abfae495b0fbb88fccd56f8099e466a83f4b76ab Mon Sep 17 00:00:00 2001 From: Sergio Moya <1083296+smoya@users.noreply.github.com> Date: Mon, 18 Sep 2023 00:05:57 +0200 Subject: [PATCH 28/41] fix: update some examples according to v3 (#971) --- spec/asyncapi.md | 13 ++++--------- 1 file changed, 4 insertions(+), 9 deletions(-) diff --git a/spec/asyncapi.md b/spec/asyncapi.md index f4be4969f..ebdfda4ce 100644 --- a/spec/asyncapi.md +++ b/spec/asyncapi.md @@ -1730,10 +1730,7 @@ my.org.User }, "parameters": { "userId": { - "description": "Id of the user.", - "schema": { - "type": "string" - } + "description": "Id of the user." } }, "correlationIds": { @@ -1785,7 +1782,7 @@ components: $ref: 'path/to/user-create.avsc/#UserCreate' servers: development: - url: "{stage}.in.mycompany.com:{port}" + host: "{stage}.in.mycompany.com:{port}" description: RabbitMQ broker protocol: amqp protocolVersion: 0-9-1 @@ -1799,8 +1796,8 @@ components: default: demo description: This value is assigned by the service provider, in this example `mycompany.com` port: - enum: [5671, 5672] - default: 5672 + enum: ["5671", "5672"] + default: "5672" channels: user/signedup: subscribe: @@ -1831,8 +1828,6 @@ components: parameters: userId: description: Id of the user. - schema: - type: string correlationIds: default: description: Default Correlation ID From cc109febc432fde3c6b6a56d125111bcc2c9032f Mon Sep 17 00:00:00 2001 From: Lukasz Gornicki Date: Mon, 30 Oct 2023 12:38:43 +0100 Subject: [PATCH 29/41] docs: update examples to be written by human not converter (#977) --- examples/README.md | 12 +- ... => adeo-kafka-request-reply-asyncapi.yml} | 0 examples/{anyof.yml => anyof-asyncapi.yml} | 2 +- ...s.yml => application-headers-asyncapi.yml} | 9 +- ...ion-id.yml => correlation-id-asyncapi.yml} | 16 ++- ...ming.yml => gitter-streaming-asyncapi.yml} | 36 +++--- ...eply-message-filter-in-reply-asyncapi.yml} | 63 ++++++++--- ...uest-reply-multiple-channels-asyncapi.yml} | 42 +++++-- .../{mercure.yml => mercure-asyncapi.yml} | 17 ++- examples/{not.yml => not-asyncapi.yml} | 0 examples/{oneof.yml => oneof-asyncapi.yml} | 0 ...ty.yml => operation-security-asyncapi.yml} | 13 +-- ...rpc-client.yml => rpc-client-asyncapi.yml} | 16 +-- ...rpc-server.yml => rpc-server-asyncapi.yml} | 16 +-- examples/{simple.yml => simple-asyncapi.yml} | 10 +- .../{slack-rtm.yml => slack-rtm-asyncapi.yml} | 104 +++++++++--------- examples/social-media/backend/asyncapi.yaml | 45 ++++---- .../comments-service/asyncapi.yaml | 27 ++--- examples/social-media/common/parameters.yaml | 2 + examples/social-media/frontend/asyncapi.yaml | 26 ++--- .../notification-service/asyncapi.yaml | 12 +- .../social-media/public-api/asyncapi.yaml | 12 +- ...ka.yml => streetlights-kafka-asyncapi.yml} | 27 ++--- ...qtt.yml => streetlights-mqtt-asyncapi.yml} | 28 ++--- ...eetlights-operation-security-asyncapi.yml} | 27 ++--- ...mini.yml => websocket-gemini-asyncapi.yml} | 10 +- 26 files changed, 312 insertions(+), 260 deletions(-) rename examples/{adeo-kafka-request-reply.yml => adeo-kafka-request-reply-asyncapi.yml} (100%) rename examples/{anyof.yml => anyof-asyncapi.yml} (96%) rename examples/{application-headers.yml => application-headers-asyncapi.yml} (89%) rename examples/{correlation-id.yml => correlation-id-asyncapi.yml} (93%) rename examples/{gitter-streaming.yml => gitter-streaming-asyncapi.yml} (89%) rename examples/{kraken-websocket-request-reply-message-filter-in-reply.yml => kraken-websocket-request-reply-message-filter-in-reply-asyncapi.yml} (88%) rename examples/{kraken-websocket-request-reply-multiple-channels.yml => kraken-websocket-request-reply-multiple-channels-asyncapi.yml} (92%) rename examples/{mercure.yml => mercure-asyncapi.yml} (78%) rename examples/{not.yml => not-asyncapi.yml} (100%) rename examples/{oneof.yml => oneof-asyncapi.yml} (100%) rename examples/{operation-security.yml => operation-security-asyncapi.yml} (96%) rename examples/{rpc-client.yml => rpc-client-asyncapi.yml} (80%) rename examples/{rpc-server.yml => rpc-server-asyncapi.yml} (81%) rename examples/{simple.yml => simple-asyncapi.yml} (79%) rename examples/{slack-rtm.yml => slack-rtm-asyncapi.yml} (94%) create mode 100644 examples/social-media/common/parameters.yaml rename examples/{streetlights-kafka.yml => streetlights-kafka-asyncapi.yml} (88%) rename examples/{streetlights-mqtt.yml => streetlights-mqtt-asyncapi.yml} (91%) rename examples/{streetlights-operation-security.yml => streetlights-operation-security-asyncapi.yml} (90%) rename examples/{websocket-gemini.yml => websocket-gemini-asyncapi.yml} (98%) diff --git a/examples/README.md b/examples/README.md index b706d2482..a13a22ee5 100644 --- a/examples/README.md +++ b/examples/README.md @@ -2,4 +2,14 @@ In this directory, you can find some examples of AsyncAPI documents. -**Do you have an example that could be valuable?** Open a pull request to contribute it. \ No newline at end of file +**Do you have an example that could be valuable?** Open a pull request to contribute it. + +## File naming + +You may notice `asyncapi` in the the name of each example. We recommend doing the same with your AsyncAPI document. This way you enable features like documentation display on node hover, auto completion and validation of your AsyncAPI documents in IDEs like VSCode or IntelliJ IDEA. IDEs integrate with [SchemaStore](https://www.schemastore.org/json/) where AsyncAPI specification JSON Schema files are referenced. Some IDEs do it by default, some, like VSCode require you to install additional extensions, like `YAML` extension. + +## Editors + +To edit your AsyncAPI documents, you can use [AsyncAPI Studio](https://studio.asyncapi.com/). + +If you prefer to use your favourite IDE, there are official extensions for [VSCode](https://marketplace.visualstudio.com/items?itemName=asyncapi.asyncapi-preview) and [IntelliJ IDEA](https://plugins.jetbrains.com/plugin/15673-asyncapi) \ No newline at end of file diff --git a/examples/adeo-kafka-request-reply.yml b/examples/adeo-kafka-request-reply-asyncapi.yml similarity index 100% rename from examples/adeo-kafka-request-reply.yml rename to examples/adeo-kafka-request-reply-asyncapi.yml diff --git a/examples/anyof.yml b/examples/anyof-asyncapi.yml similarity index 96% rename from examples/anyof.yml rename to examples/anyof-asyncapi.yml index 97492ed99..519a03ab2 100644 --- a/examples/anyof.yml +++ b/examples/anyof-asyncapi.yml @@ -33,4 +33,4 @@ components: type: object properties: key2: - type: string + type: string \ No newline at end of file diff --git a/examples/application-headers.yml b/examples/application-headers-asyncapi.yml similarity index 89% rename from examples/application-headers.yml rename to examples/application-headers-asyncapi.yml index 2c397f5ed..1c6b10269 100644 --- a/examples/application-headers.yml +++ b/examples/application-headers-asyncapi.yml @@ -20,10 +20,10 @@ servers: - '1883' - '8883' channels: - 'smartylighting/streetlights/1/0/event/{streetlightId}/lighting/measured': + lightingMeasured: address: 'smartylighting/streetlights/1/0/event/{streetlightId}/lighting/measured' messages: - receiveLightMeasurement.message: + lightMeasured: $ref: '#/components/messages/lightMeasured' parameters: streetlightId: @@ -32,8 +32,7 @@ operations: receiveLightMeasurement: action: receive channel: - $ref: >- - #/channels/smartylighting~1streetlights~11~10~1event~1{streetlightId}~1lighting~1measured + $ref: '#/channels/lightingMeasured' summary: >- Inform about environmental lighting conditions of a particular streetlight. @@ -84,4 +83,4 @@ components: type: string parameters: streetlightId: - description: The ID of the streetlight. + description: The ID of the streetlight. \ No newline at end of file diff --git a/examples/correlation-id.yml b/examples/correlation-id-asyncapi.yml similarity index 93% rename from examples/correlation-id.yml rename to examples/correlation-id-asyncapi.yml index 41309194a..5836509b5 100644 --- a/examples/correlation-id.yml +++ b/examples/correlation-id-asyncapi.yml @@ -56,18 +56,18 @@ servers: - 'streetlights:dim' - $ref: '#/components/securitySchemes/openIdConnectWellKnown' channels: - 'smartylighting/streetlights/1/0/event/{streetlightId}/lighting/measured': + lightingMeasured: address: 'smartylighting/streetlights/1/0/event/{streetlightId}/lighting/measured' messages: - receiveLightMeasurement.message: + lightMeasured: $ref: '#/components/messages/lightMeasured' parameters: streetlightId: $ref: '#/components/parameters/streetlightId' - 'smartylighting/streetlights/1/0/action/{streetlightId}/dim': + lightsDim: address: 'smartylighting/streetlights/1/0/action/{streetlightId}/dim' messages: - dimLight.message: + dimLight: $ref: '#/components/messages/dimLight' parameters: streetlightId: @@ -76,8 +76,7 @@ operations: receiveLightMeasurement: action: receive channel: - $ref: >- - #/channels/smartylighting~1streetlights~11~10~1event~1{streetlightId}~1lighting~1measured + $ref: '#/channels/lightingMeasured' summary: >- Inform about environmental lighting conditions of a particular streetlight. @@ -86,8 +85,7 @@ operations: dimLight: action: send channel: - $ref: >- - #/channels/smartylighting~1streetlights~11~10~1action~1{streetlightId}~1dim + $ref: '#/channels/lightsDim' messages: - $ref: '#/components/messages/dimLight' components: @@ -179,4 +177,4 @@ components: 'streetlights:dim': Ability to dim the lights openIdConnectWellKnown: type: openIdConnect - openIdConnectUrl: 'https://authserver.example/.well-known' + openIdConnectUrl: 'https://authserver.example/.well-known' \ No newline at end of file diff --git a/examples/gitter-streaming.yml b/examples/gitter-streaming-asyncapi.yml similarity index 89% rename from examples/gitter-streaming.yml rename to examples/gitter-streaming-asyncapi.yml index cb987bbcb..5a8704f2d 100644 --- a/examples/gitter-streaming.yml +++ b/examples/gitter-streaming-asyncapi.yml @@ -12,12 +12,12 @@ servers: security: - $ref: '#/components/securitySchemes/httpBearerToken' channels: - '/rooms/{roomId}/{resource}': + rooms: address: '/rooms/{roomId}/{resource}' messages: - subscribe.message.0: + chatMessage: $ref: '#/components/messages/chatMessage' - subscribe.message.1: + heartbeat: $ref: '#/components/messages/heartbeat' parameters: roomId: @@ -30,10 +30,10 @@ channels: - events description: The resource to consume. operations: - '/rooms/{roomId}/{resource}.subscribe': + sendRoomInfo: action: send channel: - $ref: '#/channels/~1rooms~1{roomId}~1{resource}' + $ref: '#/channels/rooms' bindings: http: type: response @@ -148,7 +148,15 @@ components: description: Stands for "Gravatar version" and is used for cache busting. bindings: http: - $ref: '#/components/messageBindings/streamingHeaders' + headers: + type: object + properties: + Transfer-Encoding: + type: string + const: chunked + Trailer: + type: string + const: \r\n heartbeat: summary: Its purpose is to keep the connection alive. payload: @@ -159,10 +167,12 @@ components: - "\r\n" bindings: http: - $ref: '#/components/messageBindings/streamingHeaders' - messageBindings: - streamingHeaders: - http: - headers: - Transfer-Encoding: chunked - Trailer: \r\n + headers: + type: object + properties: + Transfer-Encoding: + type: string + const: chunked + Trailer: + type: string + const: \r\n \ No newline at end of file diff --git a/examples/kraken-websocket-request-reply-message-filter-in-reply.yml b/examples/kraken-websocket-request-reply-message-filter-in-reply-asyncapi.yml similarity index 88% rename from examples/kraken-websocket-request-reply-message-filter-in-reply.yml rename to examples/kraken-websocket-request-reply-message-filter-in-reply-asyncapi.yml index 932f02274..7ca161506 100644 --- a/examples/kraken-websocket-request-reply-message-filter-in-reply.yml +++ b/examples/kraken-websocket-request-reply-message-filter-in-reply-asyncapi.yml @@ -36,28 +36,36 @@ channels: $ref: '#/components/messages/subscribe' unsubscribe: $ref: '#/components/messages/unsubscribe' + dummyCurrencyInfo: + $ref: '#/components/messages/dummyCurrencyInfo' operations: - pingPong: - action: send + receivePing: + action: receive channel: $ref: '#/channels/currencyExchange' reply: channel: $ref: '#/channels/currencyExchange' messages: - - $ref: '#/components/messages/ping' - heartbeat: - action: receive + - $ref: '#/components/messages/pong' + messages: + - $ref: '#/components/messages/ping' + sendHeartbeat: + action: send channel: - $ref: '#/channels/currencyExchange' + $ref: '#/channels/currencyExchange' + messages: + - $ref: '#/components/messages/heartbeat' systemStatus: - action: receive - channel: - $ref: '#/channels/currencyExchange' - subscribe: action: send + channel: + $ref: '#/channels/currencyExchange' + messages: + - $ref: '#/components/messages/systemStatus' + receiveSubscribeRequest: + action: receive channel: $ref: '#/channels/currencyExchange' reply: @@ -65,8 +73,11 @@ operations: $ref: '#/channels/currencyExchange' messages: - $ref: '#/components/messages/subscriptionStatus' - unsubscribe: - action: send + - $ref: '#/components/messages/dummyCurrencyInfo' + messages: + - $ref: '#/components/messages/subscribe' + receiveUnsubscribeRequest: + action: receive channel: $ref: '#/channels/currencyExchange' reply: @@ -74,17 +85,37 @@ operations: $ref: '#/channels/currencyExchange' messages: - $ref: '#/components/messages/subscriptionStatus' + messages: + - $ref: '#/components/messages/unsubscribe' components: messages: + dummyCurrencyInfo: + summary: Dummy message with no real life details + description: It is here in this example to showcase that there is an additional message that normally is of a complex structure. It represents actually currency exchange value to show a reply to operation receiveSubscribeRequest with more than one possible message. + payload: + type: object + properties: + event: + type: string + const: currencyInfo + reqid: + $ref: '#/components/schemas/reqid' + data: + type: object + required: + - event + correlationId: + location: '$message.payload#/reqid' + ping: summary: Ping server to determine whether connection is alive description: Client can ping server to determine whether connection is alive, server responds with pong. This is an application level ping as opposed to default ping in websockets standard which is server initiated payload: $ref: '#/components/schemas/ping' correlationId: - location: $message.payload#/reqid + location: '$message.payload#/reqid' pong: summary: Pong is a response to ping message @@ -92,20 +123,20 @@ components: payload: $ref: '#/components/schemas/pong' correlationId: - location: $message.payload#/reqid + location: '$message.payload#/reqid' subscribe: description: Subscribe to a topic on a single or multiple currency pairs. payload: $ref: '#/components/schemas/subscribe' correlationId: - location: $message.payload#/reqid + location: '$message.payload#/reqid' unsubscribe: description: Unsubscribe, can specify a channelID or multiple currency pairs. payload: $ref: '#/components/schemas/unsubscribe' correlationId: - location: $message.payload#/reqid + location: '$message.payload#/reqid' subscriptionStatus: description: Subscription status response to subscribe, unsubscribe or exchange initiated unsubscribe. payload: diff --git a/examples/kraken-websocket-request-reply-multiple-channels.yml b/examples/kraken-websocket-request-reply-multiple-channels-asyncapi.yml similarity index 92% rename from examples/kraken-websocket-request-reply-multiple-channels.yml rename to examples/kraken-websocket-request-reply-multiple-channels-asyncapi.yml index 4bf3bf570..879df21fd 100644 --- a/examples/kraken-websocket-request-reply-multiple-channels.yml +++ b/examples/kraken-websocket-request-reply-multiple-channels-asyncapi.yml @@ -42,57 +42,79 @@ channels: systemStatus: $ref: '#/components/messages/systemStatus' - subscriptionStatus: + currencyInfo: address: / messages: subscriptionStatus: $ref: '#/components/messages/subscriptionStatus' + dummyCurrencyInfo: + $ref: '#/components/messages/dummyCurrencyInfo' + subscribe: address: / messages: subscribe: $ref: '#/components/messages/subscribe' + unsubscribe: address: / messages: unsubscribe: $ref: '#/components/messages/unsubscribe' - operations: - pingPong: - action: send + receivePing: + action: receive channel: $ref: '#/channels/ping' reply: channel: $ref: '#/channels/pong' heartbeat: - action: receive + action: send channel: $ref: '#/channels/heartbeat' systemStatus: - action: receive + action: send channel: $ref: '#/channels/systemStatus' subscribe: - action: send + action: receive channel: $ref: '#/channels/subscribe' reply: channel: - $ref: '#/channels/subscriptionStatus' + $ref: '#/channels/currencyInfo' unsubscribe: - action: send + action: receive channel: $ref: '#/channels/unsubscribe' reply: channel: - $ref: '#/channels/subscriptionStatus' + $ref: '#/channels/currencyInfo' + messages: + - $ref: '#/components/messages/subscriptionStatus' components: messages: + dummyCurrencyInfo: + summary: Dummy message with no real life details + description: It is here in this example to showcase that there is an additional message that normally is of a complex structure. It represents actually currency exchange value to show a reply to operation receiveSubscribeRequest with more than one possible message. + payload: + type: object + properties: + event: + type: string + const: currencyInfo + reqid: + $ref: '#/components/schemas/reqid' + data: + type: object + required: + - event + correlationId: + location: '$message.payload#/reqid' ping: summary: Ping server to determine whether connection is alive description: Client can ping server to determine whether connection is alive, server responds with pong. This is an application level ping as opposed to default ping in websockets standard which is server initiated diff --git a/examples/mercure.yml b/examples/mercure-asyncapi.yml similarity index 78% rename from examples/mercure.yml rename to examples/mercure-asyncapi.yml index 33ec12fd1..a2ff832e8 100644 --- a/examples/mercure.yml +++ b/examples/mercure-asyncapi.yml @@ -10,30 +10,29 @@ servers: pathname: /.well-known/mercure protocol: mercure channels: - 'https://example.com/books/{id}': + books: address: 'https://example.com/books/{id}' messages: - publish.message: - $ref: '#/components/messages/book' - subscribe.message: + book: $ref: '#/components/messages/book' description: >- Every time a resource of type `http://schema.org/Book` is created or modified, a JSON-LD representation of the new version of this resource must be pushed in this Mercure topic. parameters: - id: {} + id: + description: ID of the book operations: - 'https://example.com/books/{id}.publish': + ReceiveBooksInfo: action: receive channel: - $ref: '#/channels/https:~1~1example.com~1books~1{id}' + $ref: '#/channels/books' messages: - $ref: '#/components/messages/book' - 'https://example.com/books/{id}.subscribe': + SendBooksInfo: action: send channel: - $ref: '#/channels/https:~1~1example.com~1books~1{id}' + $ref: '#/channels/books' messages: - $ref: '#/components/messages/book' components: diff --git a/examples/not.yml b/examples/not-asyncapi.yml similarity index 100% rename from examples/not.yml rename to examples/not-asyncapi.yml diff --git a/examples/oneof.yml b/examples/oneof-asyncapi.yml similarity index 100% rename from examples/oneof.yml rename to examples/oneof-asyncapi.yml diff --git a/examples/operation-security.yml b/examples/operation-security-asyncapi.yml similarity index 96% rename from examples/operation-security.yml rename to examples/operation-security-asyncapi.yml index 99d959467..d3d90c054 100644 --- a/examples/operation-security.yml +++ b/examples/operation-security-asyncapi.yml @@ -28,15 +28,8 @@ operations: - 'subscribe:auth_revocations' bindings: http: - type: request method: POST - headers: - type: object - properties: - Content-Type: - type: string - enum: - - application/json + messages: - $ref: '#/components/messages/message' components: @@ -48,6 +41,10 @@ components: X-SIGNATURE: description: ECC message signature type: string + Content-Type: + type: string + enum: + - application/json payload: type: object properties: diff --git a/examples/rpc-client.yml b/examples/rpc-client-asyncapi.yml similarity index 80% rename from examples/rpc-client.yml rename to examples/rpc-client-asyncapi.yml index dd35d2de5..58602be3a 100644 --- a/examples/rpc-client.yml +++ b/examples/rpc-client-asyncapi.yml @@ -10,10 +10,10 @@ servers: host: rabbitmq.example.org protocol: amqp channels: - '{queue}': + queue: address: '{queue}' messages: - receiveSumResult.message: + receiveSumResult: correlationId: location: $message.header#/correlation_id payload: @@ -33,11 +33,7 @@ channels: rpc_queue: address: rpc_queue messages: - requestSum.message: - bindings: - amqp: - replyTo: - type: string + requestSum: correlationId: location: $message.header#/correlation_id payload: @@ -59,12 +55,12 @@ operations: receiveSumResult: action: receive channel: - $ref: '#/channels/{queue}' + $ref: '#/channels/queue' bindings: amqp: ack: false messages: - - $ref: '#/channels/{queue}/messages/receiveSumResult.message' + - $ref: '#/channels/queue/messages/receiveSumResult' requestSum: action: send channel: @@ -73,4 +69,4 @@ operations: amqp: ack: true messages: - - $ref: '#/channels/rpc_queue/messages/requestSum.message' + - $ref: '#/channels/rpc_queue/messages/requestSum' diff --git a/examples/rpc-server.yml b/examples/rpc-server-asyncapi.yml similarity index 81% rename from examples/rpc-server.yml rename to examples/rpc-server-asyncapi.yml index de1f8ca43..3d93776c8 100644 --- a/examples/rpc-server.yml +++ b/examples/rpc-server-asyncapi.yml @@ -10,10 +10,10 @@ servers: host: rabbitmq.example.org protocol: amqp channels: - '{queue}': + queue: address: '{queue}' messages: - sendSumResult.message: + sendSumResult: correlationId: location: $message.header#/correlation_id payload: @@ -33,11 +33,7 @@ channels: rpc_queue: address: rpc_queue messages: - sum.message: - bindings: - amqp: - replyTo: - type: string + sum: correlationId: location: $message.header#/correlation_id payload: @@ -59,15 +55,15 @@ operations: sendSumResult: action: send channel: - $ref: '#/channels/{queue}' + $ref: '#/channels/queue' bindings: amqp: ack: true messages: - - $ref: '#/channels/{queue}/messages/sendSumResult.message' + - $ref: '#/channels/queue/messages/sendSumResult' sum: action: receive channel: $ref: '#/channels/rpc_queue' messages: - - $ref: '#/channels/rpc_queue/messages/sum.message' + - $ref: '#/channels/rpc_queue/messages/sum' diff --git a/examples/simple.yml b/examples/simple-asyncapi.yml similarity index 79% rename from examples/simple.yml rename to examples/simple-asyncapi.yml index f72ea6ece..f724c8b08 100644 --- a/examples/simple.yml +++ b/examples/simple-asyncapi.yml @@ -4,16 +4,16 @@ info: version: 1.0.0 description: This service is in charge of processing user signups channels: - user/signedup: + userSignedup: address: user/signedup messages: - subscribe.message: + UserSignedUp: $ref: '#/components/messages/UserSignedUp' operations: - user/signedup.subscribe: + sendUserSignedup: action: send channel: - $ref: '#/channels/user~1signedup' + $ref: '#/channels/userSignedup' messages: - $ref: '#/components/messages/UserSignedUp' components: @@ -28,4 +28,4 @@ components: email: type: string format: email - description: Email of the user + description: Email of the user \ No newline at end of file diff --git a/examples/slack-rtm.yml b/examples/slack-rtm-asyncapi.yml similarity index 94% rename from examples/slack-rtm.yml rename to examples/slack-rtm-asyncapi.yml index 4de2a3c8f..883f5ea26 100644 --- a/examples/slack-rtm.yml +++ b/examples/slack-rtm-asyncapi.yml @@ -12,114 +12,114 @@ servers: security: - $ref: '#/components/securitySchemes/token' channels: - /: + root: address: / messages: - publish.message: + outgoingMessage: $ref: '#/components/messages/outgoingMessage' - subscribe.message.0: + hello: $ref: '#/components/messages/hello' - subscribe.message.1: + connectionError: $ref: '#/components/messages/connectionError' - subscribe.message.2: + accountsChanged: $ref: '#/components/messages/accountsChanged' - subscribe.message.3: + botAdded: $ref: '#/components/messages/botAdded' - subscribe.message.4: + botChanged: $ref: '#/components/messages/botChanged' - subscribe.message.5: + channelArchive: $ref: '#/components/messages/channelArchive' - subscribe.message.6: + channelCreated: $ref: '#/components/messages/channelCreated' - subscribe.message.7: + channelDeleted: $ref: '#/components/messages/channelDeleted' - subscribe.message.8: + channelHistoryChanged: $ref: '#/components/messages/channelHistoryChanged' - subscribe.message.9: + channelJoined: $ref: '#/components/messages/channelJoined' - subscribe.message.10: + channelLeft: $ref: '#/components/messages/channelLeft' - subscribe.message.11: + channelMarked: $ref: '#/components/messages/channelMarked' - subscribe.message.12: + channelRename: $ref: '#/components/messages/channelRename' - subscribe.message.13: + channelUnarchive: $ref: '#/components/messages/channelUnarchive' - subscribe.message.14: + commandsChanged: $ref: '#/components/messages/commandsChanged' - subscribe.message.15: + dndUpdated: $ref: '#/components/messages/dndUpdated' - subscribe.message.16: + dndUpdatedUser: $ref: '#/components/messages/dndUpdatedUser' - subscribe.message.17: + emailDomainChanged: $ref: '#/components/messages/emailDomainChanged' - subscribe.message.18: + emojiRemoved: $ref: '#/components/messages/emojiRemoved' - subscribe.message.19: + emojiAdded: $ref: '#/components/messages/emojiAdded' - subscribe.message.20: + fileChange: $ref: '#/components/messages/fileChange' - subscribe.message.21: + fileCommentAdded: $ref: '#/components/messages/fileCommentAdded' - subscribe.message.22: + fileCommentDeleted: $ref: '#/components/messages/fileCommentDeleted' - subscribe.message.23: + fileCommentEdited: $ref: '#/components/messages/fileCommentEdited' - subscribe.message.24: + fileCreated: $ref: '#/components/messages/fileCreated' - subscribe.message.25: + fileDeleted: $ref: '#/components/messages/fileDeleted' - subscribe.message.26: + filePublic: $ref: '#/components/messages/filePublic' - subscribe.message.27: + fileShared: $ref: '#/components/messages/fileShared' - subscribe.message.28: + fileUnshared: $ref: '#/components/messages/fileUnshared' - subscribe.message.29: + goodbye: $ref: '#/components/messages/goodbye' - subscribe.message.30: + groupArchive: $ref: '#/components/messages/groupArchive' - subscribe.message.31: + groupClose: $ref: '#/components/messages/groupClose' - subscribe.message.32: + groupHistoryChanged: $ref: '#/components/messages/groupHistoryChanged' - subscribe.message.33: + groupJoined: $ref: '#/components/messages/groupJoined' - subscribe.message.34: + groupLeft: $ref: '#/components/messages/groupLeft' - subscribe.message.35: + groupMarked: $ref: '#/components/messages/groupMarked' - subscribe.message.36: + groupOpen: $ref: '#/components/messages/groupOpen' - subscribe.message.37: + groupRename: $ref: '#/components/messages/groupRename' - subscribe.message.38: + groupUnarchive: $ref: '#/components/messages/groupUnarchive' - subscribe.message.39: + imClose: $ref: '#/components/messages/imClose' - subscribe.message.40: + imCreated: $ref: '#/components/messages/imCreated' - subscribe.message.41: + imMarked: $ref: '#/components/messages/imMarked' - subscribe.message.42: + imOpen: $ref: '#/components/messages/imOpen' - subscribe.message.43: + manualPresenceChange: $ref: '#/components/messages/manualPresenceChange' - subscribe.message.44: + memberJoinedChannel: $ref: '#/components/messages/memberJoinedChannel' - subscribe.message.45: + message: $ref: '#/components/messages/message' operations: - /.publish: + receiveOutgoingMessage: action: receive channel: - $ref: '#/channels/~1' + $ref: '#/channels/root' messages: - $ref: '#/components/messages/outgoingMessage' - /.subscribe: + sendMessages: action: send channel: - $ref: '#/channels/~1' + $ref: '#/channels/root' messages: - $ref: '#/components/messages/hello' - $ref: '#/components/messages/connectionError' diff --git a/examples/social-media/backend/asyncapi.yaml b/examples/social-media/backend/asyncapi.yaml index b93a16dc3..0ff462f50 100644 --- a/examples/social-media/backend/asyncapi.yaml +++ b/examples/social-media/backend/asyncapi.yaml @@ -4,7 +4,7 @@ info: version: 1.0.0 servers: websiteWebSocketServer: - $ref: ../common/servers.yaml#/websiteWebSocketServer + $ref: '../common/servers.yaml#/websiteWebSocketServer' mosquitto: host: test.mosquitto.org protocol: mqtt @@ -19,64 +19,65 @@ servers: mqtt: clientId: websocketServer channels: - comment/liked: + notifyAllCommentLiked: address: comment/liked messages: subscribe.message: - $ref: ../common/messages.yaml#/commentLiked + $ref: '../common/messages.yaml#/commentLiked' description: Notify all the services that a comment has been liked. servers: - $ref: '#/servers/mosquitto' - like/comment: + newLikeComment: address: like/comment messages: publish.message: - $ref: ../common/messages.yaml#/likeComment + $ref: '../common/messages.yaml#/likeComment' description: When a comment like is received from the frontend. servers: - $ref: '#/servers/websiteWebSocketServer' - 'comment/{commentId}/changed': + commentsCountChange: address: 'comment/{commentId}/changed' messages: publish.message: - $ref: ../common/messages.yaml#/commentChanged + $ref: '../common/messages.yaml#/commentChanged' description: >- When an event from the broker arrives telling us to update the comment likes count on the frontend. servers: - $ref: '#/servers/mosquitto' parameters: - commentId: {} - update/comment/likes: + commentId: + $ref: '../common/parameters.yaml#/commentId' + updateCommentsCount: address: update/comment/likes messages: subscribe.message: - $ref: ../common/messages.yaml#/updateCommentLikes + $ref: '../common/messages.yaml#/updateCommentLikes' description: Update comment likes count in the frontend. servers: - $ref: '#/servers/websiteWebSocketServer' operations: - comment/liked.subscribe: + sendCommentLiked: action: send channel: - $ref: '#/channels/comment~1liked' + $ref: '#/channels/notifyAllCommentLiked' messages: - - $ref: ../common/messages.yaml#/commentLiked - like/comment.publish: + - $ref: '../common/messages.yaml#/commentLiked' + receiveCommentLike: action: receive channel: - $ref: '#/channels/like~1comment' + $ref: '#/channels/newLikeComment' messages: - - $ref: ../common/messages.yaml#/likeComment - 'comment/{commentId}/changed.publish': + - $ref: '../common/messages.yaml#/likeComment' + receiveCommentChange: action: receive channel: - $ref: '#/channels/comment~1{commentId}~1changed' + $ref: '#/channels/commentsCountChange' messages: - - $ref: ../common/messages.yaml#/commentChanged - update/comment/likes.subscribe: + - $ref: '../common/messages.yaml#/commentChanged' + sendCommentLikeUpdate: action: send channel: - $ref: '#/channels/update~1comment~1likes' + $ref: '#/channels/updateCommentsCount' messages: - - $ref: ../common/messages.yaml#/updateCommentLikes + - $ref: '../common/messages.yaml#/updateCommentLikes' diff --git a/examples/social-media/comments-service/asyncapi.yaml b/examples/social-media/comments-service/asyncapi.yaml index db4f3603f..74085de8d 100644 --- a/examples/social-media/comments-service/asyncapi.yaml +++ b/examples/social-media/comments-service/asyncapi.yaml @@ -18,34 +18,35 @@ servers: mqtt: clientId: comment-service channels: - comment/liked: + commentLiked: address: comment/liked messages: - publish.message: - $ref: ../common/messages.yaml#/commentLiked + commentLiked: + $ref: '../common/messages.yaml#/commentLiked' description: >- Updates the likes count in the database and sends the new count to the broker. - 'comment/{commentId}/changed': + commentCountChange: address: 'comment/{commentId}/changed' messages: - subscribe.message: - $ref: ../common/messages.yaml#/commentChanged + commentChanged: + $ref: '../common/messages.yaml#/commentChanged' description: >- Sends the new count to the broker after it has been updated in the database. parameters: - commentId: {} + commentId: + $ref: '../common/parameters.yaml#/commentId' operations: - comment/liked.publish: + receiveCommentLiked: action: receive channel: - $ref: '#/channels/comment~1liked' + $ref: '#/channels/commentLiked' messages: - - $ref: ../common/messages.yaml#/commentLiked - 'comment/{commentId}/changed.subscribe': + - $ref: '../common/messages.yaml#/commentLiked' + sendCommentChange: action: send channel: - $ref: '#/channels/comment~1{commentId}~1changed' + $ref: '#/channels/commentCountChange' messages: - - $ref: ../common/messages.yaml#/commentChanged + - $ref: '../common/messages.yaml#/commentChanged' diff --git a/examples/social-media/common/parameters.yaml b/examples/social-media/common/parameters.yaml new file mode 100644 index 000000000..91948c25e --- /dev/null +++ b/examples/social-media/common/parameters.yaml @@ -0,0 +1,2 @@ +commentId: + description: ID of the comment \ No newline at end of file diff --git a/examples/social-media/frontend/asyncapi.yaml b/examples/social-media/frontend/asyncapi.yaml index 0257336a6..c1d5355ea 100644 --- a/examples/social-media/frontend/asyncapi.yaml +++ b/examples/social-media/frontend/asyncapi.yaml @@ -4,30 +4,30 @@ info: version: 1.0.0 servers: websiteWebSocketServer: - $ref: ../common/servers.yaml#/websiteWebSocketServer + $ref: '../common/servers.yaml#/websiteWebSocketServer' channels: - like/comment: + likeComment: address: like/comment messages: - subscribe.message: - $ref: ../common/messages.yaml#/likeComment + likeComment: + $ref: '../common/messages.yaml#/likeComment' description: Notify the backend that a comment has been liked. - update/comment/likes: + updateCommentLike: address: update/comment/likes messages: - publish.message: - $ref: ../common/messages.yaml#/updateCommentLikes + updateCommentLikes: + $ref: '../common/messages.yaml#/updateCommentLikes' description: Update the UI when the comment likes count is updated. operations: - like/comment.subscribe: + sendLikeComment: action: send channel: - $ref: '#/channels/like~1comment' + $ref: '#/channels/likeComment' messages: - - $ref: ../common/messages.yaml#/likeComment - update/comment/likes.publish: + - $ref: '../common/messages.yaml#/likeComment' + receiveUpdateCommentLiked: action: receive channel: - $ref: '#/channels/update~1comment~1likes' + $ref: '#/channels/updateCommentLike' messages: - - $ref: ../common/messages.yaml#/updateCommentLikes + - $ref: '../common/messages.yaml#/updateCommentLikes' \ No newline at end of file diff --git a/examples/social-media/notification-service/asyncapi.yaml b/examples/social-media/notification-service/asyncapi.yaml index 858f3e2eb..fc4b5bb17 100644 --- a/examples/social-media/notification-service/asyncapi.yaml +++ b/examples/social-media/notification-service/asyncapi.yaml @@ -17,18 +17,18 @@ servers: mqtt: clientId: notification-service channels: - comment/liked: + commentLiked: address: comment/liked messages: - publish.message: - $ref: ../common/messages.yaml#/commentLiked + commentLiked: + $ref: '../common/messages.yaml#/commentLiked' description: >- When a "comment has been liked" message is received, it sends an SMS or push notification to the author. operations: - comment/liked.publish: + receiveCommentLiked: action: receive channel: - $ref: '#/channels/comment~1liked' + $ref: '#/channels/commentLiked' messages: - - $ref: ../common/messages.yaml#/commentLiked + - $ref: '../common/messages.yaml#/commentLiked' \ No newline at end of file diff --git a/examples/social-media/public-api/asyncapi.yaml b/examples/social-media/public-api/asyncapi.yaml index 9c6ec1b72..01c7b462c 100644 --- a/examples/social-media/public-api/asyncapi.yaml +++ b/examples/social-media/public-api/asyncapi.yaml @@ -18,18 +18,18 @@ servers: mqtt: clientId: public-api channels: - comment/liked: + commentLiked: address: comment/liked messages: - publish.message: - $ref: ../common/messages.yaml#/commentLiked + commentLiked: + $ref: '../common/messages.yaml#/commentLiked' description: >- Others are publishing to you, whenever a comment is liked, for you to do react to such an event. operations: - comment/liked.publish: + receiveCommentLiked: action: receive channel: - $ref: '#/channels/comment~1liked' + $ref: '#/channels/commentLiked' messages: - - $ref: ../common/messages.yaml#/commentLiked + - $ref: '../common/messages.yaml#/commentLiked' \ No newline at end of file diff --git a/examples/streetlights-kafka.yml b/examples/streetlights-kafka-asyncapi.yml similarity index 88% rename from examples/streetlights-kafka.yml rename to examples/streetlights-kafka-asyncapi.yml index 0affab93b..957198a54 100644 --- a/examples/streetlights-kafka.yml +++ b/examples/streetlights-kafka-asyncapi.yml @@ -37,35 +37,35 @@ servers: - name: 'visibility:private' description: This resource is private and only available to certain users channels: - 'smartylighting.streetlights.1.0.event.{streetlightId}.lighting.measured': + lightingMeasured: address: 'smartylighting.streetlights.1.0.event.{streetlightId}.lighting.measured' messages: - receiveLightMeasurement.message: + lightMeasured: $ref: '#/components/messages/lightMeasured' description: The topic on which measured values may be produced and consumed. parameters: streetlightId: $ref: '#/components/parameters/streetlightId' - 'smartylighting.streetlights.1.0.action.{streetlightId}.turn.on': + lightTurnOn: address: 'smartylighting.streetlights.1.0.action.{streetlightId}.turn.on' messages: - turnOn.message: + turnOn: $ref: '#/components/messages/turnOnOff' parameters: streetlightId: $ref: '#/components/parameters/streetlightId' - 'smartylighting.streetlights.1.0.action.{streetlightId}.turn.off': + lightTurnOff: address: 'smartylighting.streetlights.1.0.action.{streetlightId}.turn.off' messages: - turnOff.message: + turnOff: $ref: '#/components/messages/turnOnOff' parameters: streetlightId: $ref: '#/components/parameters/streetlightId' - 'smartylighting.streetlights.1.0.action.{streetlightId}.dim': + lightsDim: address: 'smartylighting.streetlights.1.0.action.{streetlightId}.dim' messages: - dimLight.message: + dimLight: $ref: '#/components/messages/dimLight' parameters: streetlightId: @@ -74,8 +74,7 @@ operations: receiveLightMeasurement: action: receive channel: - $ref: >- - #/channels/smartylighting.streetlights.1.0.event.{streetlightId}.lighting.measured + $ref: '#/channels/lightingMeasured' summary: >- Inform about environmental lighting conditions of a particular streetlight. @@ -86,8 +85,7 @@ operations: turnOn: action: send channel: - $ref: >- - #/channels/smartylighting.streetlights.1.0.action.{streetlightId}.turn.on + $ref: '#/channels/lightTurnOn' traits: - $ref: '#/components/operationTraits/kafka' messages: @@ -95,8 +93,7 @@ operations: turnOff: action: send channel: - $ref: >- - #/channels/smartylighting.streetlights.1.0.action.{streetlightId}.turn.off + $ref: '#/channels/lightTurnOff' traits: - $ref: '#/components/operationTraits/kafka' messages: @@ -104,7 +101,7 @@ operations: dimLight: action: send channel: - $ref: '#/channels/smartylighting.streetlights.1.0.action.{streetlightId}.dim' + $ref: '#/channels/lightsDim' traits: - $ref: '#/components/operationTraits/kafka' messages: diff --git a/examples/streetlights-mqtt.yml b/examples/streetlights-mqtt-asyncapi.yml similarity index 91% rename from examples/streetlights-mqtt.yml rename to examples/streetlights-mqtt-asyncapi.yml index 7a3fb23cb..5e67c9ca8 100644 --- a/examples/streetlights-mqtt.yml +++ b/examples/streetlights-mqtt-asyncapi.yml @@ -63,35 +63,35 @@ servers: - name: 'visibility:public' description: This resource is public and available to everyone channels: - 'smartylighting/streetlights/1/0/event/{streetlightId}/lighting/measured': + lightingMeasured: address: 'smartylighting/streetlights/1/0/event/{streetlightId}/lighting/measured' messages: - receiveLightMeasurement.message: + lightMeasured: $ref: '#/components/messages/lightMeasured' description: The topic on which measured values may be produced and consumed. parameters: streetlightId: $ref: '#/components/parameters/streetlightId' - 'smartylighting/streetlights/1/0/action/{streetlightId}/turn/on': + lightTurnOn: address: 'smartylighting/streetlights/1/0/action/{streetlightId}/turn/on' messages: - turnOn.message: + turnOn: $ref: '#/components/messages/turnOnOff' parameters: streetlightId: $ref: '#/components/parameters/streetlightId' - 'smartylighting/streetlights/1/0/action/{streetlightId}/turn/off': + lightTurnOff: address: 'smartylighting/streetlights/1/0/action/{streetlightId}/turn/off' messages: - turnOff.message: + turnOff: $ref: '#/components/messages/turnOnOff' parameters: streetlightId: $ref: '#/components/parameters/streetlightId' - 'smartylighting/streetlights/1/0/action/{streetlightId}/dim': + lightsDim: address: 'smartylighting/streetlights/1/0/action/{streetlightId}/dim' messages: - dimLight.message: + dimLight: $ref: '#/components/messages/dimLight' parameters: streetlightId: @@ -100,8 +100,7 @@ operations: receiveLightMeasurement: action: receive channel: - $ref: >- - #/channels/smartylighting~1streetlights~11~10~1event~1{streetlightId}~1lighting~1measured + $ref: '#/channels/lightingMeasured' summary: >- Inform about environmental lighting conditions of a particular streetlight. @@ -112,8 +111,7 @@ operations: turnOn: action: send channel: - $ref: >- - #/channels/smartylighting~1streetlights~11~10~1action~1{streetlightId}~1turn~1on + $ref: '#/channels/lightTurnOn' traits: - $ref: '#/components/operationTraits/mqtt' messages: @@ -121,8 +119,7 @@ operations: turnOff: action: send channel: - $ref: >- - #/channels/smartylighting~1streetlights~11~10~1action~1{streetlightId}~1turn~1off + $ref: '#/channels/lightTurnOff' traits: - $ref: '#/components/operationTraits/mqtt' messages: @@ -130,8 +127,7 @@ operations: dimLight: action: send channel: - $ref: >- - #/channels/smartylighting~1streetlights~11~10~1action~1{streetlightId}~1dim + $ref: '#/channels/lightsDim' traits: - $ref: '#/components/operationTraits/mqtt' messages: diff --git a/examples/streetlights-operation-security.yml b/examples/streetlights-operation-security-asyncapi.yml similarity index 90% rename from examples/streetlights-operation-security.yml rename to examples/streetlights-operation-security-asyncapi.yml index a29723e9c..a159f9b32 100644 --- a/examples/streetlights-operation-security.yml +++ b/examples/streetlights-operation-security-asyncapi.yml @@ -31,10 +31,10 @@ servers: - 'streetlights:write' - 'streetlights:read' channels: - 'smartylighting.streetlights.1.0.event.{streetlightId}.lighting.measured': + lightingMeasured: address: 'smartylighting.streetlights.1.0.event.{streetlightId}.lighting.measured' messages: - receiveLightMeasurement.message: + lightMeasured: $ref: '#/components/messages/lightMeasured' description: The topic on which measured values may be produced and consumed. servers: @@ -42,30 +42,30 @@ channels: parameters: streetlightId: $ref: '#/components/parameters/streetlightId' - 'smartylighting.streetlights.1.0.action.{streetlightId}.turn.on': + lightTurnOn: address: 'smartylighting.streetlights.1.0.action.{streetlightId}.turn.on' messages: - turnOn.message: + turnOn: $ref: '#/components/messages/turnOnOff' servers: - $ref: '#/servers/test_oauth' parameters: streetlightId: $ref: '#/components/parameters/streetlightId' - 'smartylighting.streetlights.1.0.action.{streetlightId}.turn.off': + lightTurnOff: address: 'smartylighting.streetlights.1.0.action.{streetlightId}.turn.off' messages: - turnOff.message: + turnOff: $ref: '#/components/messages/turnOnOff' servers: - $ref: '#/servers/test_oauth' parameters: streetlightId: $ref: '#/components/parameters/streetlightId' - 'smartylighting.streetlights.1.0.action.{streetlightId}.dim': + lightsDim: address: 'smartylighting.streetlights.1.0.action.{streetlightId}.dim' messages: - dimLight.message: + dimLight: $ref: '#/components/messages/dimLight' servers: - $ref: '#/servers/test_oauth' @@ -76,8 +76,7 @@ operations: receiveLightMeasurement: action: receive channel: - $ref: >- - #/channels/smartylighting.streetlights.1.0.event.{streetlightId}.lighting.measured + $ref: '#/channels/lightingMeasured' summary: >- Inform about environmental lighting conditions of a particular streetlight. @@ -88,8 +87,7 @@ operations: turnOn: action: send channel: - $ref: >- - #/channels/smartylighting.streetlights.1.0.action.{streetlightId}.turn.on + $ref: '#/channels/lightTurnOn' security: - type: oauth2 description: The oauth security descriptions @@ -108,8 +106,7 @@ operations: turnOff: action: send channel: - $ref: >- - #/channels/smartylighting.streetlights.1.0.action.{streetlightId}.turn.off + $ref: '#/channels/lightTurnOff' security: - type: oauth2 description: The oauth security descriptions @@ -128,7 +125,7 @@ operations: dimLight: action: send channel: - $ref: '#/channels/smartylighting.streetlights.1.0.action.{streetlightId}.dim' + $ref: '#/channels/lightsDim' security: - type: oauth2 description: The oauth security descriptions diff --git a/examples/websocket-gemini.yml b/examples/websocket-gemini-asyncapi.yml similarity index 98% rename from examples/websocket-gemini.yml rename to examples/websocket-gemini-asyncapi.yml index cc1cd9193..2a72fa272 100644 --- a/examples/websocket-gemini.yml +++ b/examples/websocket-gemini-asyncapi.yml @@ -25,10 +25,10 @@ servers: host: api.gemini.com protocol: wss channels: - '/v1/marketdata/{symbol}': + marketDataV1: address: '/v1/marketdata/{symbol}' messages: - subscribe.message: + marketData: $ref: '#/components/messages/marketData' parameters: symbol: @@ -149,10 +149,10 @@ channels: default: true description: Include auction events operations: - '/v1/marketdata/{symbol}.subscribe': + sendMarketData: action: send channel: - $ref: '#/channels/~1v1~1marketdata~1{symbol}' + $ref: '#/channels/marketDataV1' summary: Receive market updates on a given symbol messages: - $ref: '#/components/messages/marketData' @@ -302,4 +302,4 @@ components: multipleOf: 1 description: >- The quantity changed. May be negative, if an order is filled or - canceled. For initial messages, delta will equal remaining. + canceled. For initial messages, delta will equal remaining. \ No newline at end of file From 768ac3f5381d253fa95e3cc1a31ebfd61b76b0c9 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Fran=20M=C3=A9ndez?= Date: Mon, 6 Nov 2023 13:04:45 +0100 Subject: [PATCH 30/41] feat!: remove messageId from Message and MessageTraits objects (#984) --- spec/asyncapi.md | 6 ------ 1 file changed, 6 deletions(-) diff --git a/spec/asyncapi.md b/spec/asyncapi.md index ebdfda4ce..adea6a21c 100644 --- a/spec/asyncapi.md +++ b/spec/asyncapi.md @@ -1227,7 +1227,6 @@ Describes a message received on a given channel and operation. Field Name | Type | Description ---|:---:|--- -messageId | `string` | Unique string used to identify the message. The id MUST be unique among all messages described in the API. The messageId value is **case-sensitive**. Tools and libraries MAY use the messageId to uniquely identify a message, therefore, it is RECOMMENDED to follow common programming naming conventions. headers | [Multi Format Schema Object](#multiFormatSchemaObject) | [Schema Object](#schemaObject) | [Reference Object](#referenceObject) | Schema definition of the application headers. Schema MUST be a map of key-value pairs. It **MUST NOT** define the protocol headers. If this is a [Schema Object](#schemaObject), then the `schemaFormat` will be assumed to be "application/vnd.aai.asyncapi+json;version=`asyncapi`" where the version is equal to the [AsyncAPI Version String](#A2SVersionString). payload | [Multi Format Schema Object](#multiFormatSchemaObject) | [Schema Object](#schemaObject) | [Reference Object](#referenceObject) | Definition of the message payload. If this is a [Schema Object](#schemaObject), then the `schemaFormat` will be assumed to be "application/vnd.aai.asyncapi+json;version=`asyncapi`" where the version is equal to the [AsyncAPI Version String](#A2SVersionString). correlationId | [Correlation ID Object](#correlationIdObject) | [Reference Object](#referenceObject) | Definition of the correlation ID used for message tracing or matching. @@ -1248,7 +1247,6 @@ This object MAY be extended with [Specification Extensions](#specificationExtens ```json { - "messageId": "userSignup", "name": "UserSignup", "title": "User signup", "summary": "Action to sign a user up.", @@ -1312,7 +1310,6 @@ This object MAY be extended with [Specification Extensions](#specificationExtens ``` ```yaml -messageId: userSignup name: UserSignup title: User signup summary: Action to sign a user up. @@ -1360,7 +1357,6 @@ Example using Avro to define the payload: ```json { - "messageId": "userSignup", "name": "UserSignup", "title": "User signup", "summary": "Action to sign a user up.", @@ -1380,7 +1376,6 @@ Example using Avro to define the payload: ``` ```yaml -messageId: userSignup name: UserSignup title: User signup summary: Action to sign a user up. @@ -1411,7 +1406,6 @@ If you're looking to apply traits to an operation, see the [Operation Trait Obje Field Name | Type | Description ---|:---:|--- -messageId | `string` | Unique string used to identify the message. The id MUST be unique among all messages described in the API. The messageId value is **case-sensitive**. Tools and libraries MAY use the messageId to uniquely identify a message, therefore, it is RECOMMENDED to follow common programming naming conventions. headers | [Multi Format Schema Object](#multiFormatSchemaObject) | [Schema Object](#schemaObject) | [Reference Object](#referenceObject) | Schema definition of the application headers. Schema MUST be a map of key-value pairs. It **MUST NOT** define the protocol headers. If this is a [Schema Object](#schemaObject), then the `schemaFormat` will be assumed to be "application/vnd.aai.asyncapi+json;version=`asyncapi`" where the version is equal to the [AsyncAPI Version String](#A2SVersionString). correlationId | [Correlation ID Object](#correlationIdObject) | [Reference Object](#referenceObject) | Definition of the correlation ID used for message tracing or matching. contentType | `string` | The content type to use when encoding/decoding a message's payload. The value MUST be a specific media type (e.g. `application/json`). When omitted, the value MUST be the one specified on the [defaultContentType](#defaultContentTypeString) field. From e7e66dbbf1f0b3ac3d4cc3a65441cfa4b8fbaa2d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Vladim=C3=ADr=20Gorej?= Date: Mon, 13 Nov 2023 11:52:29 +0100 Subject: [PATCH 31/41] fix: remove mentions of Operation Item Object (#988) --- spec/asyncapi.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/spec/asyncapi.md b/spec/asyncapi.md index adea6a21c..594a710f7 100644 --- a/spec/asyncapi.md +++ b/spec/asyncapi.md @@ -1585,7 +1585,7 @@ Field Name | Type | Description schemas | Map[`string`, [Multi Format Schema Object](#multiFormatSchemaObject) \| [Schema Object](#schemaObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Schema Object](#schemaObject). If this is a [Schema Object](#schemaObject), then the `schemaFormat` will be assumed to be "application/vnd.aai.asyncapi+json;version=`asyncapi`" where the version is equal to the [AsyncAPI Version String](#A2SVersionString). servers | Map[`string`, [Server Object](#serverObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Server Objects](#serverObject). channels | Map[`string`, [Channel Object](#channelObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Channel Objects](#channelObject). - operations | Map[`string`, [Operation Item Object](#operationObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Operation Item Objects](#operationObject). + operations | Map[`string`, [Operation Object](#operationObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Operation Objects](#operationObject). messages | Map[`string`, [Message Object](#messageObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Message Objects](#messageObject). securitySchemes| Map[`string`, [Security Scheme Object](#securitySchemeObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Security Scheme Objects](#securitySchemeObject). serverVariables | Map[`string`, [Server Variable Object](#serverVariableObject) \| [Reference Object](#referenceObject)] | An object to hold reusable [Server Variable Objects](#serverVariableObject). From e76206a5632591d8a9a19f1f758054612be37185 Mon Sep 17 00:00:00 2001 From: Lukasz Gornicki Date: Mon, 13 Nov 2023 12:19:28 +0100 Subject: [PATCH 32/41] =?UTF-8?q?docs:=20add=20constraint=20about=20channe?= =?UTF-8?q?l=20address=20to=20not=20use=20query=20params=20and=E2=80=A6=20?= =?UTF-8?q?(#986)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- spec/asyncapi.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/spec/asyncapi.md b/spec/asyncapi.md index 594a710f7..1f96a3a0d 100644 --- a/spec/asyncapi.md +++ b/spec/asyncapi.md @@ -629,7 +629,7 @@ Describes a shared communication channel. Field Name | Type | Description ---|:---:|--- -address | `string` \| `null` | An optional string representation of this channel's address. The address is typically the "topic name", "routing key", "event type", or "path". When `null` or absent, it MUST be interpreted as unknown. This is useful when the address is generated dynamically at runtime or can't be known upfront. It MAY contain [Channel Address Expressions](#channelAddressExpressions). +address | `string` \| `null` | An optional string representation of this channel's address. The address is typically the "topic name", "routing key", "event type", or "path". When `null` or absent, it MUST be interpreted as unknown. This is useful when the address is generated dynamically at runtime or can't be known upfront. It MAY contain [Channel Address Expressions](#channelAddressExpressions). Query parameters and fragments SHALL NOT be used, instead use [bindings](#channelBindingsObject) to define them. messages | [Messages Object](#messagesObject) | A map of the messages that will be sent to this channel by any application at any time. **Every message sent to this channel MUST be valid against one, and only one, of the [message objects](#messageObject) defined in this map.** title | `string` | A human-friendly title for the channel. summary | `string` | A short summary of the channel. From 5e3044ad4babb64ae0167a3d8a902d6b2712e3c7 Mon Sep 17 00:00:00 2001 From: Semen Date: Fri, 17 Nov 2023 01:25:40 +0200 Subject: [PATCH 33/41] docs provide definition for the reply --- spec/asyncapi.md | 11 +++++++---- 1 file changed, 7 insertions(+), 4 deletions(-) diff --git a/spec/asyncapi.md b/spec/asyncapi.md index 1f96a3a0d..6fa409745 100644 --- a/spec/asyncapi.md +++ b/spec/asyncapi.md @@ -136,7 +136,10 @@ A sender is a type of application, that is sending [messages](#definitionsMessag A receiver is a type of application that is receiving [messages](#definitionsMessage) from [channels](#definitionsChannel). A receiver MAY receive from multiple channels depending on the [server](#definitionsServer), protocol, and the use-case pattern. A receiver MAY forward a received message further without changing it. A receiver MAY act as a consumer and react to the message. A receiver MAY act as a processor that, for example, aggregates multiple messages in one and forwards them. ### Message -A message is the mechanism by which information is exchanged via a channel between [servers](#definitionsServer) and applications. A message MUST contain a payload and MAY also contain headers. The headers MAY be subdivided into [protocol](#definitionsProtocol)-defined headers and header properties defined by the application which can act as supporting metadata. The payload contains the data, defined by the application, which MUST be serialized into a format (JSON, XML, Avro, binary, etc.). Since a message is a generic mechanism, it can support multiple interaction patterns such as event, command, request, or response. +A message is the mechanism by which information is exchanged via a channel between [servers](#definitionsServer) and applications. A message MUST contain a payload and MAY also contain headers. The headers MAY be subdivided into [protocol](#definitionsProtocol)-defined headers and header properties defined by the application which can act as supporting metadata. The payload contains the data, defined by the application, which MUST be serialized into a format (JSON, XML, Avro, binary, etc.). Since a message is a generic mechanism, it can support multiple interaction patterns such as event, command, request, or reply. + +#### Reply message +A reply is a special type of message used in the request-reply interaction pattern and can only be used in combination with a request message. In the request-reply interaction pattern, messages are defined as follows: [Sender](#definitionsSender) sends a request message and waits for a reply message, while [Receiver](#definitionsReceiver) receives the request message and responds with a reply message. ### Channel A channel is an addressable component, made available by the [server](#definitionsServer), for the organization of [messages](#definitionsMessage). [Sender](#definitionsSender) applications send messages to channels and [receiver](#definitionsReceiver) applications receive messages from channels. [Servers](#definitionsServer) MAY support many channel instances, allowing messages with different content to be addressed to different channels. Depending on the [server](#definitionsServer) implementation, the channel MAY be included in the message via protocol-defined headers. @@ -840,7 +843,7 @@ Field Name | Type | Description bindings | [Operation Bindings Object](#operationBindingsObject) \| [Reference Object](#referenceObject) | A map where the keys describe the name of the protocol and the values describe protocol-specific definitions for the operation. traits | [[Operation Trait Object](#operationTraitObject) | [Reference Object](#referenceObject) ] | A list of traits to apply to the operation object. Traits MUST be merged using [traits merge mechanism](#traits-merge-mechanism). The resulting object MUST be a valid [Operation Object](#operationObject). messages | [[Reference Object](#referenceObject)] | A list of `$ref` pointers pointing to the supported [Message Objects](#messageObject) that can be processed by this operation. It MUST contain a subset of the messages defined in the [channel referenced in this operation](#operationObjectChannel). **Every message processed by this operation MUST be valid against one, and only one, of the [message objects](#messageObject) referenced in this list.** Please note the `messages` property value MUST be a list of [Reference Objects](#referenceObject) and, therefore, MUST NOT contain [Message Objects](#messageObject). However, it is RECOMMENDED that parsers (or other software) dereference this property for a better development experience. -reply | [Operation Reply Object](#operationReplyObject) | [Reference Object](#referenceObject) | The definition of the reply in a request-reply operation. +reply | [Operation Reply Object](#operationReplyObject) | [Reference Object](#referenceObject) | The definition of the reply part in a request-reply interaction. When this property is defined, the [messages](#operationObjectMessages) represent request messages in a request-reply interaction. This object MAY be extended with [Specification Extensions](#specificationExtensions). @@ -970,7 +973,7 @@ bindings: #### Operation Reply Object -Describes the reply part that MAY be applied to an Operation Object. If an operation implements the request/reply pattern, the reply object represents the response message. +Describes the reply part that MAY be applied to an Operation Object. If an operation implements the request-reply interaction pattern, this object represents the reply address/channel and the reply message. ##### Fixed Fields @@ -1192,7 +1195,7 @@ Map describing protocol-specific definitions for a message. Field Name | Type | Description ---|:---:|--- -`http` | [HTTP Message Binding](https://github.com/asyncapi/bindings/blob/master/http/README.md#message) | Protocol-specific information for an HTTP message, i.e., a request or a response. +`http` | [HTTP Message Binding](https://github.com/asyncapi/bindings/blob/master/http/README.md#message) | Protocol-specific information for an HTTP message, i.e., a request or a reply. `ws` | [WebSockets Message Binding](https://github.com/asyncapi/bindings/blob/master/websockets/README.md#message) | Protocol-specific information for a WebSockets message. `kafka` | [Kafka Message Binding](https://github.com/asyncapi/bindings/blob/master/kafka/README.md#message) | Protocol-specific information for a Kafka message. `anypointmq` | [Anypoint MQ Message Binding](https://github.com/asyncapi/bindings/blob/master/anypointmq/README.md#message) | Protocol-specific information for an Anypoint MQ message. From f8a6bb014aa417b9056ae380a7edd25d4713ab13 Mon Sep 17 00:00:00 2001 From: samz Date: Tue, 28 Nov 2023 21:30:18 +0100 Subject: [PATCH 34/41] chore: fix gitter binding example (#995) --- examples/gitter-streaming-asyncapi.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/examples/gitter-streaming-asyncapi.yml b/examples/gitter-streaming-asyncapi.yml index 5a8704f2d..726a04943 100644 --- a/examples/gitter-streaming-asyncapi.yml +++ b/examples/gitter-streaming-asyncapi.yml @@ -36,7 +36,7 @@ operations: $ref: '#/channels/rooms' bindings: http: - type: response + method: POST messages: - $ref: '#/components/messages/chatMessage' - $ref: '#/components/messages/heartbeat' From 5fb88a0191590beb4e3d13765dc65bd5734f09a8 Mon Sep 17 00:00:00 2001 From: Sergio Moya <1083296+smoya@users.noreply.github.com> Date: Wed, 29 Nov 2023 19:01:39 +0100 Subject: [PATCH 35/41] fix: clarify pointers for channel.servers and operation.channel fields (#996) --- spec/asyncapi.md | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/spec/asyncapi.md b/spec/asyncapi.md index 1f96a3a0d..57a003320 100644 --- a/spec/asyncapi.md +++ b/spec/asyncapi.md @@ -634,7 +634,7 @@ Field Name | Type | Description title | `string` | A human-friendly title for the channel. summary | `string` | A short summary of the channel. description | `string` | An optional description of this channel. [CommonMark syntax](https://spec.commonmark.org/) can be used for rich text representation. -servers | [[Reference Object](#referenceObject)] | An array of `$ref` pointers to the definition of the servers in which this channel is available. If `servers` is absent or empty, this channel MUST be available on all the servers defined in the [Servers Object](#serversObject). Please note the `servers` property value MUST be an array of [Reference Objects](#referenceObject) and, therefore, MUST NOT contain an array of [Server Objects](#serverObject). However, it is RECOMMENDED that parsers (or other software) dereference this property for a better development experience. +servers | [[Reference Object](#referenceObject)] | An array of `$ref` pointers to the definition of the servers in which this channel is available. If the channel is located in the [root Channels Object](#channelsObject), it MUST point to a subset of server definitions located in the [root Servers Object](#serversObject), and MUST NOT point to a subset of server definitions located in the [Components Object](#componentsObject) or anywhere else. If the channel is located in the [Components Object](#componentsObject), it MAY point to a [Server Objects](#serverObject) in any location. If `servers` is absent or empty, this channel MUST be available on all the servers defined in the [Servers Object](#serversObject). Please note the `servers` property value MUST be an array of [Reference Objects](#referenceObject) and, therefore, MUST NOT contain an array of [Server Objects](#serverObject). However, it is RECOMMENDED that parsers (or other software) dereference this property for a better development experience. parameters | [Parameters Object](#parametersObject) | A map of the parameters included in the channel address. It MUST be present only when the address contains [Channel Address Expressions](#channelAddressExpressions). tags | [Tags Object](#tagsObject) | A list of tags for logical grouping of channels. externalDocs | [External Documentation Object](#externalDocumentationObject) \| [Reference Object](#referenceObject) | Additional external documentation for this channel. @@ -830,7 +830,7 @@ Describes a specific operation. Field Name | Type | Description ---|:---:|--- action | `"send"` | `"receive"` | **Required**. Use `send` when it's expected that the application will send a message to the given [`channel`](#operationObjectChannel), and `receive` when the application should expect receiving messages from the given [`channel`](#operationObjectChannel). -channel | [Reference Object](#referenceObject) | **Required**. A `$ref` pointer to the definition of the channel in which this operation is performed. Please note the `channel` property value MUST be a [Reference Object](#referenceObject) and, therefore, MUST NOT contain a [Channel Object](#channelObject). However, it is RECOMMENDED that parsers (or other software) dereference this property for a better development experience. +channel | [Reference Object](#referenceObject) | **Required**. A `$ref` pointer to the definition of the channel in which this operation is performed. If the operation is located in the [root Operations Object](#operationsObject), it MUST point to a channel definition located in the [root Channels Object](#channelsObject), and MUST NOT point to a channel definition located in the [Components Object](#componentsObject) or anywhere else. If the operation is located in the [Components Object](#componentsObject), it MAY point to a [Channel Object](#channelObject) in any location. Please note the `channel` property value MUST be a [Reference Object](#referenceObject) and, therefore, MUST NOT contain a [Channel Object](#channelObject). However, it is RECOMMENDED that parsers (or other software) dereference this property for a better development experience. title | `string` | A human-friendly title for the operation. summary | `string` | A short summary of what the operation is about. description | `string` | A verbose explanation of the operation. [CommonMark syntax](http://spec.commonmark.org/) can be used for rich text representation. @@ -839,7 +839,7 @@ Field Name | Type | Description externalDocs | [External Documentation Object](#externalDocumentationObject) \| [Reference Object](#referenceObject) | Additional external documentation for this operation. bindings | [Operation Bindings Object](#operationBindingsObject) \| [Reference Object](#referenceObject) | A map where the keys describe the name of the protocol and the values describe protocol-specific definitions for the operation. traits | [[Operation Trait Object](#operationTraitObject) | [Reference Object](#referenceObject) ] | A list of traits to apply to the operation object. Traits MUST be merged using [traits merge mechanism](#traits-merge-mechanism). The resulting object MUST be a valid [Operation Object](#operationObject). -messages | [[Reference Object](#referenceObject)] | A list of `$ref` pointers pointing to the supported [Message Objects](#messageObject) that can be processed by this operation. It MUST contain a subset of the messages defined in the [channel referenced in this operation](#operationObjectChannel). **Every message processed by this operation MUST be valid against one, and only one, of the [message objects](#messageObject) referenced in this list.** Please note the `messages` property value MUST be a list of [Reference Objects](#referenceObject) and, therefore, MUST NOT contain [Message Objects](#messageObject). However, it is RECOMMENDED that parsers (or other software) dereference this property for a better development experience. +messages | [[Reference Object](#referenceObject)] | A list of `$ref` pointers pointing to the supported [Message Objects](#messageObject) that can be processed by this operation. It MUST contain a subset of the messages defined in the [channel referenced in this operation](#operationObjectChannel), and MUST NOT point to a subset of message definitions located in the [Messages Object](#componentsMessages) in the [Components Object](#componentsObject) or anywhere else. **Every message processed by this operation MUST be valid against one, and only one, of the [message objects](#messageObject) referenced in this list.** Please note the `messages` property value MUST be a list of [Reference Objects](#referenceObject) and, therefore, MUST NOT contain [Message Objects](#messageObject). However, it is RECOMMENDED that parsers (or other software) dereference this property for a better development experience. reply | [Operation Reply Object](#operationReplyObject) | [Reference Object](#referenceObject) | The definition of the reply in a request-reply operation. This object MAY be extended with [Specification Extensions](#specificationExtensions). @@ -977,8 +977,8 @@ Describes the reply part that MAY be applied to an Operation Object. If an opera Field Name | Type | Description ---|:---:|--- address | [Operation Reply Address Object](#operationReplyAddressObject) | [Reference Object](#referenceObject) | Definition of the address that implementations MUST use for the reply. -channel | [Reference Object](#referenceObject) | A `$ref` pointer to the definition of the channel in which this operation is performed. When [address](#operationReplyAddressObject) is specified, the [`address` property](#channelObjectAddress) of the channel referenced by this property MUST be either `null` or not defined. Please note the `channel` property value MUST be a [Reference Object](#referenceObject) and, therefore, MUST NOT contain a [Channel Object](#channelObject). However, it is RECOMMENDED that parsers (or other software) dereference this property for a better development experience. -messages | [[Reference Object](#referenceObject)] | A list of `$ref` pointers pointing to the supported [Message Objects](#messageObject) that can be processed by this operation as reply. It MUST contain a subset of the messages defined in the [channel referenced in this operation reply](#operationObjectChannel). **Every message processed by this operation MUST be valid against one, and only one, of the [message objects](#messageObject) referenced in this list.** Please note the `messages` property value MUST be a list of [Reference Objects](#referenceObject) and, therefore, MUST NOT contain [Message Objects](#messageObject). However, it is RECOMMENDED that parsers (or other software) dereference this property for a better development experience. +channel | [Reference Object](#referenceObject) | A `$ref` pointer to the definition of the channel in which this operation is performed. When [address](#operationReplyAddressObject) is specified, the [`address` property](#channelObjectAddress) of the channel referenced by this property MUST be either `null` or not defined. If the operation reply is located inside a [root Operation Object](#operationObject), it MUST point to a channel definition located in the [root Channels Object](#channelsObject), and MUST NOT point to a channel definition located in the [Components Object](#componentsObject) or anywhere else. If the operation reply is located inside an [Operation Object] in the [Components Object](#componentsObject) or in the [Replies Object](#componentsReplies) in the [Components Object](#componentsObject), it MAY point to a [Channel Object](#channelObject) in any location. Please note the `channel` property value MUST be a [Reference Object](#referenceObject) and, therefore, MUST NOT contain a [Channel Object](#channelObject). However, it is RECOMMENDED that parsers (or other software) dereference this property for a better development experience. +messages | [[Reference Object](#referenceObject)] | A list of `$ref` pointers pointing to the supported [Message Objects](#messageObject) that can be processed by this operation as reply. It MUST contain a subset of the messages defined in the [channel referenced in this operation reply](#operationObjectChannel), and MUST NOT point to a subset of message definitions located in the [Components Object](#componentsObject) or anywhere else. **Every message processed by this operation MUST be valid against one, and only one, of the [message objects](#messageObject) referenced in this list.** Please note the `messages` property value MUST be a list of [Reference Objects](#referenceObject) and, therefore, MUST NOT contain [Message Objects](#messageObject). However, it is RECOMMENDED that parsers (or other software) dereference this property for a better development experience. This object MAY be extended with [Specification Extensions](#specificationExtensions). From 1a8c669a0c4afe6fb2b8ca5c6e28a1bd40f89945 Mon Sep 17 00:00:00 2001 From: Lukasz Gornicki Date: Wed, 29 Nov 2023 23:40:19 +0100 Subject: [PATCH 36/41] chore: update examples so messages reference channel messages (#997) --- examples/anyof-asyncapi.yml | 6 +- examples/application-headers-asyncapi.yml | 2 +- examples/correlation-id-asyncapi.yml | 4 +- examples/gitter-streaming-asyncapi.yml | 4 +- ...reply-message-filter-in-reply-asyncapi.yml | 18 ++-- ...quest-reply-multiple-channels-asyncapi.yml | 2 +- examples/mercure-asyncapi.yml | 4 +- examples/not-asyncapi.yml | 6 +- examples/oneof-asyncapi.yml | 16 ++-- examples/operation-security-asyncapi.yml | 10 +- examples/simple-asyncapi.yml | 2 +- examples/slack-rtm-asyncapi.yml | 94 +++++++++---------- examples/social-media/backend/asyncapi.yaml | 16 ++-- .../comments-service/asyncapi.yaml | 4 +- examples/social-media/frontend/asyncapi.yaml | 4 +- .../notification-service/asyncapi.yaml | 2 +- .../social-media/public-api/asyncapi.yaml | 2 +- examples/streetlights-kafka-asyncapi.yml | 8 +- examples/streetlights-mqtt-asyncapi.yml | 8 +- ...reetlights-operation-security-asyncapi.yml | 8 +- examples/websocket-gemini-asyncapi.yml | 2 +- 21 files changed, 111 insertions(+), 111 deletions(-) diff --git a/examples/anyof-asyncapi.yml b/examples/anyof-asyncapi.yml index 519a03ab2..6492902f8 100644 --- a/examples/anyof-asyncapi.yml +++ b/examples/anyof-asyncapi.yml @@ -6,15 +6,15 @@ channels: test: address: test messages: - publish.message: + testMessages: $ref: '#/components/messages/testMessages' operations: - test.publish: + test: action: receive channel: $ref: '#/channels/test' messages: - - $ref: '#/components/messages/testMessages' + - $ref: '#/channels/test/messages/testMessages' components: messages: testMessages: diff --git a/examples/application-headers-asyncapi.yml b/examples/application-headers-asyncapi.yml index 1c6b10269..6edd83ae3 100644 --- a/examples/application-headers-asyncapi.yml +++ b/examples/application-headers-asyncapi.yml @@ -37,7 +37,7 @@ operations: Inform about environmental lighting conditions of a particular streetlight. messages: - - $ref: '#/components/messages/lightMeasured' + - $ref: '#/channels/lightingMeasured/messages/lightMeasured' components: messages: lightMeasured: diff --git a/examples/correlation-id-asyncapi.yml b/examples/correlation-id-asyncapi.yml index 5836509b5..e25a6a70e 100644 --- a/examples/correlation-id-asyncapi.yml +++ b/examples/correlation-id-asyncapi.yml @@ -81,13 +81,13 @@ operations: Inform about environmental lighting conditions of a particular streetlight. messages: - - $ref: '#/components/messages/lightMeasured' + - $ref: '#/channels/lightingMeasured/messages/lightMeasured' dimLight: action: send channel: $ref: '#/channels/lightsDim' messages: - - $ref: '#/components/messages/dimLight' + - $ref: '#/channels/lightsDim/messages/dimLight' components: messages: lightMeasured: diff --git a/examples/gitter-streaming-asyncapi.yml b/examples/gitter-streaming-asyncapi.yml index 726a04943..640bb4366 100644 --- a/examples/gitter-streaming-asyncapi.yml +++ b/examples/gitter-streaming-asyncapi.yml @@ -38,8 +38,8 @@ operations: http: method: POST messages: - - $ref: '#/components/messages/chatMessage' - - $ref: '#/components/messages/heartbeat' + - $ref: '#/channels/rooms/messages/chatMessage' + - $ref: '#/channels/rooms/messages/heartbeat' components: securitySchemes: httpBearerToken: diff --git a/examples/kraken-websocket-request-reply-message-filter-in-reply-asyncapi.yml b/examples/kraken-websocket-request-reply-message-filter-in-reply-asyncapi.yml index 7ca161506..9abb79398 100644 --- a/examples/kraken-websocket-request-reply-message-filter-in-reply-asyncapi.yml +++ b/examples/kraken-websocket-request-reply-message-filter-in-reply-asyncapi.yml @@ -49,21 +49,21 @@ operations: channel: $ref: '#/channels/currencyExchange' messages: - - $ref: '#/components/messages/pong' + - $ref: '#/channels/currencyExchange/messages/pong' messages: - - $ref: '#/components/messages/ping' + - $ref: '#/channels/currencyExchange/messages/ping' sendHeartbeat: action: send channel: $ref: '#/channels/currencyExchange' messages: - - $ref: '#/components/messages/heartbeat' + - $ref: '#/channels/currencyExchange/messages/heartbeat' systemStatus: action: send channel: $ref: '#/channels/currencyExchange' messages: - - $ref: '#/components/messages/systemStatus' + - $ref: '#/channels/currencyExchange/messages/systemStatus' receiveSubscribeRequest: action: receive channel: @@ -72,10 +72,10 @@ operations: channel: $ref: '#/channels/currencyExchange' messages: - - $ref: '#/components/messages/subscriptionStatus' - - $ref: '#/components/messages/dummyCurrencyInfo' + - $ref: '#/channels/currencyExchange/messages/subscriptionStatus' + - $ref: '#/channels/currencyExchange/messages/dummyCurrencyInfo' messages: - - $ref: '#/components/messages/subscribe' + - $ref: '#/channels/currencyExchange/messages/subscribe' receiveUnsubscribeRequest: action: receive channel: @@ -84,9 +84,9 @@ operations: channel: $ref: '#/channels/currencyExchange' messages: - - $ref: '#/components/messages/subscriptionStatus' + - $ref: '#/channels/currencyExchange/messages/subscriptionStatus' messages: - - $ref: '#/components/messages/unsubscribe' + - $ref: '#/channels/currencyExchange/messages/unsubscribe' components: diff --git a/examples/kraken-websocket-request-reply-multiple-channels-asyncapi.yml b/examples/kraken-websocket-request-reply-multiple-channels-asyncapi.yml index 879df21fd..6b09cab7f 100644 --- a/examples/kraken-websocket-request-reply-multiple-channels-asyncapi.yml +++ b/examples/kraken-websocket-request-reply-multiple-channels-asyncapi.yml @@ -93,7 +93,7 @@ operations: channel: $ref: '#/channels/currencyInfo' messages: - - $ref: '#/components/messages/subscriptionStatus' + - $ref: '#/channels/currencyInfo/messages/subscriptionStatus' components: diff --git a/examples/mercure-asyncapi.yml b/examples/mercure-asyncapi.yml index a2ff832e8..2fc1238cc 100644 --- a/examples/mercure-asyncapi.yml +++ b/examples/mercure-asyncapi.yml @@ -28,13 +28,13 @@ operations: channel: $ref: '#/channels/books' messages: - - $ref: '#/components/messages/book' + - $ref: '#/channels/books/messages/book' SendBooksInfo: action: send channel: $ref: '#/channels/books' messages: - - $ref: '#/components/messages/book' + - $ref: '#/channels/books/messages/book' components: messages: book: diff --git a/examples/not-asyncapi.yml b/examples/not-asyncapi.yml index 0dd2cad1d..ecd465044 100644 --- a/examples/not-asyncapi.yml +++ b/examples/not-asyncapi.yml @@ -6,15 +6,15 @@ channels: test: address: test messages: - publish.message: + testMessages: $ref: '#/components/messages/testMessages' operations: - test.publish: + onTestMsg: action: receive channel: $ref: '#/channels/test' messages: - - $ref: '#/components/messages/testMessages' + - $ref: '#/channels/test/messages/testMessages' components: messages: testMessages: diff --git a/examples/oneof-asyncapi.yml b/examples/oneof-asyncapi.yml index 2df5f6eea..8e9879c6e 100644 --- a/examples/oneof-asyncapi.yml +++ b/examples/oneof-asyncapi.yml @@ -6,31 +6,31 @@ channels: test: address: test messages: - publish.message: + testMessages: $ref: '#/components/messages/testMessages' test2: address: test2 messages: - subscribe.message.0: + objectWithKey: payload: $ref: '#/components/schemas/objectWithKey' - subscribe.message.1: + objectWithKey2: payload: $ref: '#/components/schemas/objectWithKey2' operations: - test.publish: + onTestMsg: action: receive channel: $ref: '#/channels/test' messages: - - $ref: '#/components/messages/testMessages' - test2.subscribe: + - $ref: '#/channels/test/messages/testMessages' + sendTest: action: send channel: $ref: '#/channels/test2' messages: - - $ref: '#/channels/test2/messages/subscribe.message.0' - - $ref: '#/channels/test2/messages/subscribe.message.1' + - $ref: '#/channels/test2/messages/objectWithKey' + - $ref: '#/channels/test2/messages/objectWithKey2' components: messages: testMessages: diff --git a/examples/operation-security-asyncapi.yml b/examples/operation-security-asyncapi.yml index d3d90c054..fb89977c4 100644 --- a/examples/operation-security-asyncapi.yml +++ b/examples/operation-security-asyncapi.yml @@ -6,16 +6,16 @@ info: This contract defines HTTP Push notification for application authorization revocation topic channels: - AUTHORIZATION_REVOCATION: + authRevoke: address: AUTHORIZATION_REVOCATION messages: - subscribe.message: + message: $ref: '#/components/messages/message' operations: - AUTHORIZATION_REVOCATION.subscribe: + sendAuthRevoke: action: send channel: - $ref: '#/channels/AUTHORIZATION_REVOCATION' + $ref: '#/channels/authRevoke' security: - type: oauth2 description: The oauth security descriptions @@ -31,7 +31,7 @@ operations: method: POST messages: - - $ref: '#/components/messages/message' + - $ref: '#/channels/authRevoke/messages/message' components: messages: message: diff --git a/examples/simple-asyncapi.yml b/examples/simple-asyncapi.yml index f724c8b08..75572baf4 100644 --- a/examples/simple-asyncapi.yml +++ b/examples/simple-asyncapi.yml @@ -15,7 +15,7 @@ operations: channel: $ref: '#/channels/userSignedup' messages: - - $ref: '#/components/messages/UserSignedUp' + - $ref: '#/channels/userSignedup/messages/UserSignedUp' components: messages: UserSignedUp: diff --git a/examples/slack-rtm-asyncapi.yml b/examples/slack-rtm-asyncapi.yml index 883f5ea26..9f50acd6d 100644 --- a/examples/slack-rtm-asyncapi.yml +++ b/examples/slack-rtm-asyncapi.yml @@ -115,58 +115,58 @@ operations: channel: $ref: '#/channels/root' messages: - - $ref: '#/components/messages/outgoingMessage' + - $ref: '#/channels/root/messages/outgoingMessage' sendMessages: action: send channel: $ref: '#/channels/root' messages: - - $ref: '#/components/messages/hello' - - $ref: '#/components/messages/connectionError' - - $ref: '#/components/messages/accountsChanged' - - $ref: '#/components/messages/botAdded' - - $ref: '#/components/messages/botChanged' - - $ref: '#/components/messages/channelArchive' - - $ref: '#/components/messages/channelCreated' - - $ref: '#/components/messages/channelDeleted' - - $ref: '#/components/messages/channelHistoryChanged' - - $ref: '#/components/messages/channelJoined' - - $ref: '#/components/messages/channelLeft' - - $ref: '#/components/messages/channelMarked' - - $ref: '#/components/messages/channelRename' - - $ref: '#/components/messages/channelUnarchive' - - $ref: '#/components/messages/commandsChanged' - - $ref: '#/components/messages/dndUpdated' - - $ref: '#/components/messages/dndUpdatedUser' - - $ref: '#/components/messages/emailDomainChanged' - - $ref: '#/components/messages/emojiRemoved' - - $ref: '#/components/messages/emojiAdded' - - $ref: '#/components/messages/fileChange' - - $ref: '#/components/messages/fileCommentAdded' - - $ref: '#/components/messages/fileCommentDeleted' - - $ref: '#/components/messages/fileCommentEdited' - - $ref: '#/components/messages/fileCreated' - - $ref: '#/components/messages/fileDeleted' - - $ref: '#/components/messages/filePublic' - - $ref: '#/components/messages/fileShared' - - $ref: '#/components/messages/fileUnshared' - - $ref: '#/components/messages/goodbye' - - $ref: '#/components/messages/groupArchive' - - $ref: '#/components/messages/groupClose' - - $ref: '#/components/messages/groupHistoryChanged' - - $ref: '#/components/messages/groupJoined' - - $ref: '#/components/messages/groupLeft' - - $ref: '#/components/messages/groupMarked' - - $ref: '#/components/messages/groupOpen' - - $ref: '#/components/messages/groupRename' - - $ref: '#/components/messages/groupUnarchive' - - $ref: '#/components/messages/imClose' - - $ref: '#/components/messages/imCreated' - - $ref: '#/components/messages/imMarked' - - $ref: '#/components/messages/imOpen' - - $ref: '#/components/messages/manualPresenceChange' - - $ref: '#/components/messages/memberJoinedChannel' - - $ref: '#/components/messages/message' + - $ref: '#/channels/root/messages/hello' + - $ref: '#/channels/root/messages/connectionError' + - $ref: '#/channels/root/messages/accountsChanged' + - $ref: '#/channels/root/messages/botAdded' + - $ref: '#/channels/root/messages/botChanged' + - $ref: '#/channels/root/messages/channelArchive' + - $ref: '#/channels/root/messages/channelCreated' + - $ref: '#/channels/root/messages/channelDeleted' + - $ref: '#/channels/root/messages/channelHistoryChanged' + - $ref: '#/channels/root/messages/channelJoined' + - $ref: '#/channels/root/messages/channelLeft' + - $ref: '#/channels/root/messages/channelMarked' + - $ref: '#/channels/root/messages/channelRename' + - $ref: '#/channels/root/messages/channelUnarchive' + - $ref: '#/channels/root/messages/commandsChanged' + - $ref: '#/channels/root/messages/dndUpdated' + - $ref: '#/channels/root/messages/dndUpdatedUser' + - $ref: '#/channels/root/messages/emailDomainChanged' + - $ref: '#/channels/root/messages/emojiRemoved' + - $ref: '#/channels/root/messages/emojiAdded' + - $ref: '#/channels/root/messages/fileChange' + - $ref: '#/channels/root/messages/fileCommentAdded' + - $ref: '#/channels/root/messages/fileCommentDeleted' + - $ref: '#/channels/root/messages/fileCommentEdited' + - $ref: '#/channels/root/messages/fileCreated' + - $ref: '#/channels/root/messages/fileDeleted' + - $ref: '#/channels/root/messages/filePublic' + - $ref: '#/channels/root/messages/fileShared' + - $ref: '#/channels/root/messages/fileUnshared' + - $ref: '#/channels/root/messages/goodbye' + - $ref: '#/channels/root/messages/groupArchive' + - $ref: '#/channels/root/messages/groupClose' + - $ref: '#/channels/root/messages/groupHistoryChanged' + - $ref: '#/channels/root/messages/groupJoined' + - $ref: '#/channels/root/messages/groupLeft' + - $ref: '#/channels/root/messages/groupMarked' + - $ref: '#/channels/root/messages/groupOpen' + - $ref: '#/channels/root/messages/groupRename' + - $ref: '#/channels/root/messages/groupUnarchive' + - $ref: '#/channels/root/messages/imClose' + - $ref: '#/channels/root/messages/imCreated' + - $ref: '#/channels/root/messages/imMarked' + - $ref: '#/channels/root/messages/imOpen' + - $ref: '#/channels/root/messages/manualPresenceChange' + - $ref: '#/channels/root/messages/memberJoinedChannel' + - $ref: '#/channels/root/messages/message' components: securitySchemes: token: diff --git a/examples/social-media/backend/asyncapi.yaml b/examples/social-media/backend/asyncapi.yaml index 0ff462f50..14e45cbe6 100644 --- a/examples/social-media/backend/asyncapi.yaml +++ b/examples/social-media/backend/asyncapi.yaml @@ -22,7 +22,7 @@ channels: notifyAllCommentLiked: address: comment/liked messages: - subscribe.message: + commentLiked: $ref: '../common/messages.yaml#/commentLiked' description: Notify all the services that a comment has been liked. servers: @@ -30,7 +30,7 @@ channels: newLikeComment: address: like/comment messages: - publish.message: + likeComment: $ref: '../common/messages.yaml#/likeComment' description: When a comment like is received from the frontend. servers: @@ -38,7 +38,7 @@ channels: commentsCountChange: address: 'comment/{commentId}/changed' messages: - publish.message: + commentChanged: $ref: '../common/messages.yaml#/commentChanged' description: >- When an event from the broker arrives telling us to update the comment @@ -51,7 +51,7 @@ channels: updateCommentsCount: address: update/comment/likes messages: - subscribe.message: + updateCommentLikes: $ref: '../common/messages.yaml#/updateCommentLikes' description: Update comment likes count in the frontend. servers: @@ -62,22 +62,22 @@ operations: channel: $ref: '#/channels/notifyAllCommentLiked' messages: - - $ref: '../common/messages.yaml#/commentLiked' + - $ref: '#/channels/notifyAllCommentLiked/messages/commentLiked' receiveCommentLike: action: receive channel: $ref: '#/channels/newLikeComment' messages: - - $ref: '../common/messages.yaml#/likeComment' + - $ref: '#/channels/newLikeComment/messages/likeComment' receiveCommentChange: action: receive channel: $ref: '#/channels/commentsCountChange' messages: - - $ref: '../common/messages.yaml#/commentChanged' + - $ref: '#/channels/commentsCountChange/messages/commentChanged' sendCommentLikeUpdate: action: send channel: $ref: '#/channels/updateCommentsCount' messages: - - $ref: '../common/messages.yaml#/updateCommentLikes' + - $ref: '#/channels/updateCommentsCount/messages/updateCommentLikes' \ No newline at end of file diff --git a/examples/social-media/comments-service/asyncapi.yaml b/examples/social-media/comments-service/asyncapi.yaml index 74085de8d..2fcee6889 100644 --- a/examples/social-media/comments-service/asyncapi.yaml +++ b/examples/social-media/comments-service/asyncapi.yaml @@ -43,10 +43,10 @@ operations: channel: $ref: '#/channels/commentLiked' messages: - - $ref: '../common/messages.yaml#/commentLiked' + - $ref: '#/channels/commentLiked/messages/commentLiked' sendCommentChange: action: send channel: $ref: '#/channels/commentCountChange' messages: - - $ref: '../common/messages.yaml#/commentChanged' + - $ref: '#/channels/commentCountChange/messages/commentChanged' diff --git a/examples/social-media/frontend/asyncapi.yaml b/examples/social-media/frontend/asyncapi.yaml index c1d5355ea..b0e50b5a7 100644 --- a/examples/social-media/frontend/asyncapi.yaml +++ b/examples/social-media/frontend/asyncapi.yaml @@ -24,10 +24,10 @@ operations: channel: $ref: '#/channels/likeComment' messages: - - $ref: '../common/messages.yaml#/likeComment' + - $ref: '#/channels/likeComment/messages/likeComment' receiveUpdateCommentLiked: action: receive channel: $ref: '#/channels/updateCommentLike' messages: - - $ref: '../common/messages.yaml#/updateCommentLikes' \ No newline at end of file + - $ref: '#/channels/updateCommentLike/messages/updateCommentLikes' \ No newline at end of file diff --git a/examples/social-media/notification-service/asyncapi.yaml b/examples/social-media/notification-service/asyncapi.yaml index fc4b5bb17..8d2e36efb 100644 --- a/examples/social-media/notification-service/asyncapi.yaml +++ b/examples/social-media/notification-service/asyncapi.yaml @@ -31,4 +31,4 @@ operations: channel: $ref: '#/channels/commentLiked' messages: - - $ref: '../common/messages.yaml#/commentLiked' \ No newline at end of file + - $ref: '#/channels/commentLiked/messages/commentLiked' \ No newline at end of file diff --git a/examples/social-media/public-api/asyncapi.yaml b/examples/social-media/public-api/asyncapi.yaml index 01c7b462c..8a62eba96 100644 --- a/examples/social-media/public-api/asyncapi.yaml +++ b/examples/social-media/public-api/asyncapi.yaml @@ -32,4 +32,4 @@ operations: channel: $ref: '#/channels/commentLiked' messages: - - $ref: '../common/messages.yaml#/commentLiked' \ No newline at end of file + - $ref: '#/channels/commentLiked/messages/commentLiked' \ No newline at end of file diff --git a/examples/streetlights-kafka-asyncapi.yml b/examples/streetlights-kafka-asyncapi.yml index 957198a54..45eecd653 100644 --- a/examples/streetlights-kafka-asyncapi.yml +++ b/examples/streetlights-kafka-asyncapi.yml @@ -81,7 +81,7 @@ operations: traits: - $ref: '#/components/operationTraits/kafka' messages: - - $ref: '#/components/messages/lightMeasured' + - $ref: '#/channels/lightingMeasured/messages/lightMeasured' turnOn: action: send channel: @@ -89,7 +89,7 @@ operations: traits: - $ref: '#/components/operationTraits/kafka' messages: - - $ref: '#/components/messages/turnOnOff' + - $ref: '#/channels/lightTurnOn/messages/turnOn' turnOff: action: send channel: @@ -97,7 +97,7 @@ operations: traits: - $ref: '#/components/operationTraits/kafka' messages: - - $ref: '#/components/messages/turnOnOff' + - $ref: '#/channels/lightTurnOff/messages/turnOff' dimLight: action: send channel: @@ -105,7 +105,7 @@ operations: traits: - $ref: '#/components/operationTraits/kafka' messages: - - $ref: '#/components/messages/dimLight' + - $ref: '#/channels/lightsDim/messages/dimLight' components: messages: lightMeasured: diff --git a/examples/streetlights-mqtt-asyncapi.yml b/examples/streetlights-mqtt-asyncapi.yml index 5e67c9ca8..ce6550907 100644 --- a/examples/streetlights-mqtt-asyncapi.yml +++ b/examples/streetlights-mqtt-asyncapi.yml @@ -107,7 +107,7 @@ operations: traits: - $ref: '#/components/operationTraits/mqtt' messages: - - $ref: '#/components/messages/lightMeasured' + - $ref: '#/channels/lightingMeasured/messages/lightMeasured' turnOn: action: send channel: @@ -115,7 +115,7 @@ operations: traits: - $ref: '#/components/operationTraits/mqtt' messages: - - $ref: '#/components/messages/turnOnOff' + - $ref: '#/channels/lightTurnOn/messages/turnOn' turnOff: action: send channel: @@ -123,7 +123,7 @@ operations: traits: - $ref: '#/components/operationTraits/mqtt' messages: - - $ref: '#/components/messages/turnOnOff' + - $ref: '#/channels/lightTurnOff/messages/turnOff' dimLight: action: send channel: @@ -131,7 +131,7 @@ operations: traits: - $ref: '#/components/operationTraits/mqtt' messages: - - $ref: '#/components/messages/dimLight' + - $ref: '#/channels/lightsDim/messages/dimLight' components: messages: lightMeasured: diff --git a/examples/streetlights-operation-security-asyncapi.yml b/examples/streetlights-operation-security-asyncapi.yml index a159f9b32..31a115fe7 100644 --- a/examples/streetlights-operation-security-asyncapi.yml +++ b/examples/streetlights-operation-security-asyncapi.yml @@ -83,7 +83,7 @@ operations: traits: - $ref: '#/components/operationTraits/kafka' messages: - - $ref: '#/components/messages/lightMeasured' + - $ref: '#/channels/lightingMeasured/messages/lightMeasured' turnOn: action: send channel: @@ -102,7 +102,7 @@ operations: traits: - $ref: '#/components/operationTraits/kafka' messages: - - $ref: '#/components/messages/turnOnOff' + - $ref: '#/channels/lightTurnOn/messages/turnOn' turnOff: action: send channel: @@ -121,7 +121,7 @@ operations: traits: - $ref: '#/components/operationTraits/kafka' messages: - - $ref: '#/components/messages/turnOnOff' + - $ref: '#/channels/lightTurnOff/messages/turnOff' dimLight: action: send channel: @@ -140,7 +140,7 @@ operations: traits: - $ref: '#/components/operationTraits/kafka' messages: - - $ref: '#/components/messages/dimLight' + - $ref: '#/channels/lightsDim/messages/dimLight' components: messages: lightMeasured: diff --git a/examples/websocket-gemini-asyncapi.yml b/examples/websocket-gemini-asyncapi.yml index 2a72fa272..675640f34 100644 --- a/examples/websocket-gemini-asyncapi.yml +++ b/examples/websocket-gemini-asyncapi.yml @@ -155,7 +155,7 @@ operations: $ref: '#/channels/marketDataV1' summary: Receive market updates on a given symbol messages: - - $ref: '#/components/messages/marketData' + - $ref: '#/channels/marketDataV1/messages/marketData' components: messages: marketData: From ba8ea9dbbf7850740feb995ad6ab8f1d2797bdc2 Mon Sep 17 00:00:00 2001 From: Jonas Lagoni Date: Mon, 4 Dec 2023 11:49:16 -1000 Subject: [PATCH 37/41] chore: apply #853 --- spec/asyncapi.md | 84 ++++++++++++++++++++++++------------------------ 1 file changed, 42 insertions(+), 42 deletions(-) diff --git a/spec/asyncapi.md b/spec/asyncapi.md index 7533fd494..71e864291 100644 --- a/spec/asyncapi.md +++ b/spec/asyncapi.md @@ -72,48 +72,48 @@ Aside from the issues mentioned above, there may also be infrastructure configur - [Channel](#definitionsChannel) - [Protocol](#definitionsProtocol) - [Specification](#specification) - - [Format](#format) - - [File Structure](#file-structure) - - [Absolute URLs](#absolute-urls) - - [Schema](#schema) - - [AsyncAPI Object](#A2SObject) - - [AsyncAPI Version String](#A2SVersionString) - - [Identifier](#A2SIdString) - - [Info Object](#infoObject) - - [Contact Object](#contactObject) - - [License Object](#licenseObject) - - [Servers Object](#serversObject) - - [Server Object](#serverObject) - - [Server Variable Object](#serverVariableObject) - - [Default Content Type](#defaultContentTypeString) - - [Channels Object](#channelsObject) - - [Channel Object](#channelObject) - - [Operations Object](#operationsObject) - - [Operation Object](#operationObject) - - [Operation Trait Object](#operationTraitObject) - - [Operation Reply Object](#operationReplyObject) - - [Operation Reply Address Object](#operationReplyAddressObject) - - [Message Object](#messageObject) - - [Message Trait Object](#messageTraitObject) - - [Message Example Object](#messageExampleObject) - - [Tags Object](#tagsObject) - - [Tag Object](#tag-object) - - [External Documentation Object](#externalDocumentationObject) - - [Components Object](#componentsObject) - - [Reference Object](#referenceObject) - - [Multi Format Schema Object](#multiFormatSchemaObject) - - [Schema Object](#schemaObject) - - [Security Scheme Object](#securitySchemeObject) - - [OAuth Flows Object](#oauth-flows-object) - - [OAuth Flow Object](#oauth-flow-object) - - [Server Bindings Object](#serverBindingsObject) - - [Parameters Object](#parametersObject) - - [Parameter Object](#parameterObject) - - [Channel Bindings Object](#channelBindingsObject) - - [Operation Bindings Object](#operationBindingsObject) - - [Message Bindings Object](#messageBindingsObject) - - [Correlation ID Object](#correlationIdObject) - - [Specification Extensions](#specificationExtensions) + - [Format](#format) + - [File Structure](#file-structure) + - [Absolute URLs](#absolute-urls) + - [Schema](#schema) + - [AsyncAPI Object](#A2SObject) + - [AsyncAPI Version String](#A2SVersionString) + - [Identifier](#A2SIdString) + - [Info Object](#infoObject) + - [Contact Object](#contactObject) + - [License Object](#licenseObject) + - [Servers Object](#serversObject) + - [Server Object](#serverObject) + - [Server Variable Object](#serverVariableObject) + - [Default Content Type](#defaultContentTypeString) + - [Channels Object](#channelsObject) + - [Channel Object](#channelObject) + - [Operations Object](#operationsObject) + - [Operation Object](#operationObject) + - [Operation Trait Object](#operationTraitObject) + - [Operation Reply Object](#operationReplyObject) + - [Operation Reply Address Object](#operationReplyAddressObject) + - [Message Object](#messageObject) + - [Message Trait Object](#messageTraitObject) + - [Message Example Object](#messageExampleObject) + - [Tags Object](#tagsObject) + - [Tag Object](#tag-object) + - [External Documentation Object](#externalDocumentationObject) + - [Components Object](#componentsObject) + - [Reference Object](#referenceObject) + - [Multi Format Schema Object](#multiFormatSchemaObject) + - [Schema Object](#schemaObject) + - [Security Scheme Object](#securitySchemeObject) + - [OAuth Flows Object](#oauth-flows-object) + - [OAuth Flow Object](#oauth-flow-object) + - [Server Bindings Object](#serverBindingsObject) + - [Parameters Object](#parametersObject) + - [Parameter Object](#parameterObject) + - [Channel Bindings Object](#channelBindingsObject) + - [Operation Bindings Object](#operationBindingsObject) + - [Message Bindings Object](#messageBindingsObject) + - [Correlation ID Object](#correlationIdObject) + - [Specification Extensions](#specificationExtensions) From 297b33618776210d605972943d3055b0b29f3fa0 Mon Sep 17 00:00:00 2001 From: Jonas Lagoni Date: Mon, 4 Dec 2023 11:49:31 -1000 Subject: [PATCH 38/41] chore: apply #884 --- examples/websocket-gemini-asyncapi.yml | 16 ++++++---------- 1 file changed, 6 insertions(+), 10 deletions(-) diff --git a/examples/websocket-gemini-asyncapi.yml b/examples/websocket-gemini-asyncapi.yml index 675640f34..7abcba981 100644 --- a/examples/websocket-gemini-asyncapi.yml +++ b/examples/websocket-gemini-asyncapi.yml @@ -180,9 +180,9 @@ components: events: - type: change side: bid - price: '54350.40' - remaining: '0.002' - delta: '0.002' + price: 54350.40 + remaining: 0.002 + delta: 0.002 reason: place - name: heartbeatMessage summary: Example of additional heartbeat message when you enable them. @@ -219,15 +219,13 @@ components: events: $ref: '#/components/schemas/events' timestamp: - type: string - format: date-time + type: number description: >- The timestamp in seconds for this group of events (included for compatibility reasons). We recommend using the timestampms field instead. timestampms: - type: string - format: time + type: number description: The timestamp in milliseconds for this group of events. required: - type @@ -272,7 +270,7 @@ components: - 'auction, block_trade' price: type: number - multipleOf: 1 + multipleOf: 0.01 description: The price of this order book entry. side: type: string @@ -292,14 +290,12 @@ components: order book. remaining: type: number - multipleOf: 1 description: >- The quantity remaining at that price level after this change occurred. May be zero if all orders at this price level have been filled or canceled. delta: type: number - multipleOf: 1 description: >- The quantity changed. May be negative, if an order is filled or canceled. For initial messages, delta will equal remaining. \ No newline at end of file From 3cb55502f1ee9bf1708c0e02464bd41363353de7 Mon Sep 17 00:00:00 2001 From: Jonas Lagoni Date: Mon, 4 Dec 2023 11:53:03 -1000 Subject: [PATCH 39/41] chore: apply #902 --- spec/asyncapi.md | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/spec/asyncapi.md b/spec/asyncapi.md index 71e864291..1513bfe0f 100644 --- a/spec/asyncapi.md +++ b/spec/asyncapi.md @@ -138,7 +138,7 @@ A message is the mechanism by which information is exchanged via a channel betwe A channel is an addressable component, made available by the [server](#definitionsServer), for the organization of [messages](#definitionsMessage). [Sender](#definitionsSender) applications send messages to channels and [receiver](#definitionsReceiver) applications receive messages from channels. [Servers](#definitionsServer) MAY support many channel instances, allowing messages with different content to be addressed to different channels. Depending on the [server](#definitionsServer) implementation, the channel MAY be included in the message via protocol-defined headers. ### Protocol -A protocol is the mechanism (wireline protocol or API) by which [messages](#definitionsMessage) are exchanged between the application and the [channel](#definitionsChannel). Example protocols include, but are not limited to, AMQP, HTTP, JMS, Kafka, Anypoint MQ, MQTT, Solace, STOMP, Mercure, WebSocket. +A protocol is the mechanism (wireline protocol or API) by which [messages](#definitionsMessage) are exchanged between the application and the [channel](#definitionsChannel). Example protocols include, but are not limited to, AMQP, HTTP, JMS, Kafka, Anypoint MQ, MQTT, Solace, STOMP, Mercure, WebSocket, Google Pub/Sub, Pulsar. ### Bindings A "binding" (or "protocol binding") is a mechanism to define protocol-specific information. Therefore, a protocol binding MUST define protocol-specific information only. @@ -1112,6 +1112,7 @@ Field Name | Type | Description `mercure` | [Mercure Server Binding](https://github.com/asyncapi/bindings/blob/master/mercure#server) | Protocol-specific information for a Mercure server. `ibmmq` | [IBM MQ Server Binding](https://github.com/asyncapi/bindings/blob/master/ibmmq#server-binding-object) | Protocol-specific information for an IBM MQ server. `googlepubsub` | [Google Cloud Pub/Sub Server Binding](https://github.com/asyncapi/bindings/blob/master/googlepubsub#server) | Protocol-specific information for a Google Cloud Pub/Sub server. +`pulsar` | [Pulsar Server Binding](https://github.com/asyncapi/bindings/tree/master/pulsar#server-binding-object) | Protocol-specific information for a Pulsar server. This object MAY be extended with [Specification Extensions](#specificationExtensions). @@ -1143,6 +1144,7 @@ Field Name | Type | Description `mercure` | [Mercure Channel Binding](https://github.com/asyncapi/bindings/blob/master/mercure#channel) | Protocol-specific information for a Mercure channel. `ibmmq` | [IBM MQ Channel Binding](https://github.com/asyncapi/bindings/tree/master/ibmmq#channel-binding-object) | Protocol-specific information for an IBM MQ channel. `googlepubsub` | [Google Cloud Pub/Sub Channel Binding](https://github.com/asyncapi/bindings/tree/master/googlepubsub#channel) | Protocol-specific information for a Google Cloud Pub/Sub channel. +`pulsar` | [Pulsar Channel Binding](https://github.com/asyncapi/bindings/tree/master/pulsar#channel-binding-object) | Protocol-specific information for a Pulsar channel. This object MAY be extended with [Specification Extensions](#specificationExtensions). @@ -1174,6 +1176,7 @@ Field Name | Type | Description `mercure` | [Mercure Operation Binding](https://github.com/asyncapi/bindings/blob/master/mercure#operation) | Protocol-specific information for a Mercure operation. `googlepubsub` | [Google Cloud Pub/Sub Operation Binding](https://github.com/asyncapi/bindings/blob/master/googlepubsub#operation) | Protocol-specific information for a Google Cloud Pub/Sub operation. `ibmmq` | [IBM MQ Operation Binding](https://github.com/asyncapi/bindings/blob/master/ibmmq#operation-binding-object) | Protocol-specific information for an IBM MQ operation. +`pulsar` | [Pulsar Operation Binding](https://github.com/asyncapi/bindings/tree/master/pulsar#operation-binding-fields) | Protocol-specific information for a Pulsar operation. This object MAY be extended with [Specification Extensions](#specificationExtensions). @@ -1206,6 +1209,7 @@ Field Name | Type | Description `mercure` | [Mercure Message Binding](https://github.com/asyncapi/bindings/blob/master/mercure#message) | Protocol-specific information for a Mercure message. `ibmmq` | [IBM MQ Message Binding](https://github.com/asyncapi/bindings/tree/master/ibmmq#message-binding-object) | Protocol-specific information for an IBM MQ message. `googlepubsub` | [Google Cloud Pub/Sub Message Binding](https://github.com/asyncapi/bindings/tree/master/googlepubsub#message) | Protocol-specific information for a Google Cloud Pub/Sub message. +`pulsar` | [Pulsar Message Binding](https://github.com/asyncapi/bindings/tree/master/pulsar#message-binding-fields) | Protocol-specific information for a Pulsar message. This object MAY be extended with [Specification Extensions](#specificationExtensions). From 736b5e1c372dc80bc18aa7ddad8947a04387ac40 Mon Sep 17 00:00:00 2001 From: Jonas Lagoni Date: Mon, 4 Dec 2023 11:53:33 -1000 Subject: [PATCH 40/41] chore: apply #909 --- spec/asyncapi.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/spec/asyncapi.md b/spec/asyncapi.md index 1513bfe0f..7450d3df6 100644 --- a/spec/asyncapi.md +++ b/spec/asyncapi.md @@ -1943,7 +1943,7 @@ While composition offers model extensibility, it does not imply a hierarchy betw To support polymorphism, AsyncAPI Specification adds the support of the `discriminator` field. When used, the `discriminator` will be the name of the property used to decide which schema definition is used to validate the structure of the model. As such, the `discriminator` field MUST be a required field. -There are are two ways to define the value of a discriminator for an inheriting instance. +There are two ways to define the value of a discriminator for an inheriting instance. - Use the schema's name. - Override the schema's name by overriding the property with a new value. If exists, this takes precedence over the schema's name. From 41686ae9b6da349b4aee93ce925f8eb8a7f1ad4a Mon Sep 17 00:00:00 2001 From: Jonas Lagoni Date: Mon, 4 Dec 2023 11:56:49 -1000 Subject: [PATCH 41/41] chore: apply #983 --- spec/asyncapi.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/spec/asyncapi.md b/spec/asyncapi.md index 7450d3df6..15d51f22a 100644 --- a/spec/asyncapi.md +++ b/spec/asyncapi.md @@ -132,7 +132,7 @@ A sender is a type of application, that is sending [messages](#definitionsMessag A receiver is a type of application that is receiving [messages](#definitionsMessage) from [channels](#definitionsChannel). A receiver MAY receive from multiple channels depending on the [server](#definitionsServer), protocol, and the use-case pattern. A receiver MAY forward a received message further without changing it. A receiver MAY act as a consumer and react to the message. A receiver MAY act as a processor that, for example, aggregates multiple messages in one and forwards them. ### Message -A message is the mechanism by which information is exchanged via a channel between [servers](#definitionsServer) and applications. A message MUST contain a payload and MAY also contain headers. The headers MAY be subdivided into [protocol](#definitionsProtocol)-defined headers and header properties defined by the application which can act as supporting metadata. The payload contains the data, defined by the application, which MUST be serialized into a format (JSON, XML, Avro, binary, etc.). Since a message is a generic mechanism, it can support multiple interaction patterns such as event, command, request, or response. +A message is the mechanism by which information is exchanged via a channel between [servers](#definitionsServer) and applications. A message MAY contain a payload and MAY also contain headers. The headers MAY be subdivided into [protocol](#definitionsProtocol)-defined headers and header properties defined by the application which can act as supporting metadata. The payload contains the data, defined by the application, which MUST be serialized into a format (JSON, XML, Avro, binary, etc.). Since a message is a generic mechanism, it can support multiple interaction patterns such as event, command, request, or response. ### Channel A channel is an addressable component, made available by the [server](#definitionsServer), for the organization of [messages](#definitionsMessage). [Sender](#definitionsSender) applications send messages to channels and [receiver](#definitionsReceiver) applications receive messages from channels. [Servers](#definitionsServer) MAY support many channel instances, allowing messages with different content to be addressed to different channels. Depending on the [server](#definitionsServer) implementation, the channel MAY be included in the message via protocol-defined headers.