From 8805c881d68b6be9c6159273a0179a1545f8a157 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] feat: add new channels object (#827) --- spec/asyncapi.md | 198 ++++++++++++++++++++++++----------------------- 1 file changed, 101 insertions(+), 97 deletions(-) diff --git a/spec/asyncapi.md b/spec/asyncapi.md index 8a4c431de..d65fd6b9e 100644 --- a/spec/asyncapi.md +++ b/spec/asyncapi.md @@ -56,7 +56,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) @@ -162,7 +162,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. @@ -529,23 +529,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" } } @@ -554,54 +553,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 can 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", @@ -609,87 +613,87 @@ This object can 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' ``` @@ -1464,7 +1468,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). @@ -2554,6 +2558,6 @@ string | `string` | | | byte | `string` | `byte` | base64 encoded characters binary | `string` | `binary` | any sequence of octets boolean | `boolean` | | | -date | `string` | `date` | As defined by `full-date` - [RFC3339](https://xml2rfc.ietf.org/public/rfc/html/rfc3339.html#anchor14) -dateTime | `string` | `date-time` | As defined by `date-time` - [RFC3339](https://xml2rfc.ietf.org/public/rfc/html/rfc3339.html#anchor14) +date | `string` | `date` | As defined by `full-date` - [RFC3339](https://www.rfc-editor.org/rfc/rfc3339) +dateTime | `string` | `date-time` | As defined by `date-time` - [RFC3339](https://www.rfc-editor.org/rfc/rfc3339) password | `string` | `password` | Used to hint UIs the input needs to be obscured.