Skip to content

Commit

Permalink
BREAKING: remove messaging.destination.kind and messaging.source.kind…
Browse files Browse the repository at this point in the history
… values (#3214)

Fixes #3170, #3265, #3249

## Changes

~~We currently allow `topic` or `queue` on `messaging.destination.kind`.
While it's common in messaging world to have one or another, messaging
semantic conventions can be applied to AMPQ communication (which does
not have topic/queue terminology), [socket.io](https://socket.io/), and
potentially other less traditional messaging use-cases.~~

It's unclear how `messaging.destination.kind` and
`messaging.source.kind` could be used. The distinction between queue and
topic is significant for messaging and distributed systems, but not for
tracing.

In either case, tracing backends should expect to process traces from 0+
messaging and 0+ messaging consumers. In either case, message consumers
can be simultaneous or consequent and there could be many of them.

The only known case (Solace) where it could be useful is when messaging
system allows having queues and topic with the same name on the same
broker, and it could be used to distinguish one from another.

Based on messaging SIG discussion, the attributes are removed for the
time being until we understand if and how they are useful.

Depending on messaging system queues or topics behavior vary a lot and
in future it would makes more sense to represent actual behavior with
individual attributes such as:
- auto-settlement (at-most-once or at least once guarantees)
- settlement for individual messages or offsets
- broadcast or unicast
- etc
  • Loading branch information
lmolkova committed Mar 21, 2023
1 parent e7a555a commit 89a9601
Show file tree
Hide file tree
Showing 3 changed files with 20 additions and 74 deletions.
2 changes: 2 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,8 @@ release.
([#3272](https://github.com/open-telemetry/opentelemetry-specification/pull/3272))
- Metric requirement levels are now stable
([#3271](https://github.com/open-telemetry/opentelemetry-specification/pull/3271))
- BREAKING: remove `messaging.destination.kind` and `messaging.source.kind`.
([#3214](https://github.com/open-telemetry/opentelemetry-specification/pull/3214))

### Compatibility

Expand Down
31 changes: 0 additions & 31 deletions semantic_conventions/trace/messaging.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -39,17 +39,6 @@ groups:
Destination name SHOULD uniquely identify a specific queue, topic or other entity within the broker. If
the broker does not have such notion, the destination name SHOULD uniquely identify the broker.
examples: ['MyQueue', 'MyTopic']
- id: kind
type:
allow_custom_values: false
members:
- id: queue
value: "queue"
brief: "A message sent to a queue"
- id: topic
value: "topic"
brief: "A message sent to a topic"
brief: 'The kind of message destination'
- id: template
type: string
brief: Low cardinality representation of the messaging destination name
Expand Down Expand Up @@ -79,17 +68,6 @@ groups:
Source name SHOULD uniquely identify a specific queue, topic, or other entity within the broker. If
the broker does not have such notion, the source name SHOULD uniquely identify the broker.
examples: ['MyQueue', 'MyTopic']
- id: kind
type:
allow_custom_values: true
members:
- id: queue
value: "queue"
brief: "A message received from a queue"
- id: topic
value: "topic"
brief: "A message received from a topic"
brief: 'The kind of message source'
- id: template
type: string
brief: 'Low cardinality representation of the messaging source name'
Expand Down Expand Up @@ -187,9 +165,6 @@ groups:
- ref: messaging.destination.name
requirement_level:
conditionally_required: If one message is being published or if the value applies to all messages in the batch.
- ref: messaging.destination.kind
requirement_level:
conditionally_required: If the message destination is either a `queue` or a `topic`.
- ref: messaging.destination.template
requirement_level:
conditionally_required: >
Expand Down Expand Up @@ -229,9 +204,6 @@ groups:
- ref: messaging.source.name
requirement_level:
conditionally_required: If the value applies to all messages in the batch.
- ref: messaging.source.kind
requirement_level:
conditionally_required: If the message source is either a `queue` or `topic`.
- ref: messaging.source.template
requirement_level:
conditionally_required: >
Expand All @@ -246,9 +218,6 @@ groups:
- ref: messaging.destination.name
requirement_level:
recommended: If known on consumer
- ref: messaging.destination.kind
requirement_level:
recommended: If known on consumer
- ref: messaging.destination.temporary
requirement_level:
recommended: If known on consumer
Expand Down
61 changes: 18 additions & 43 deletions specification/trace/semantic_conventions/messaging.md
Original file line number Diff line number Diff line change
Expand Up @@ -78,21 +78,11 @@ might be another intermediary or a consumer.
### Destinations and sources

A destination is usually uniquely identified by name within the messaging system instance. Examples of a destination name would be a URL or a simple one-word identifier.
Traditional messaging, such as JMS, involves two kinds of destinations: *topic*s and *queue*s.

A message that is sent (the send-operation is often called "*publish*" in this context) to a *topic* is broadcasted to all consumers that have *subscribed* to the topic.

A message that is sent to a *queue* is processed by a message *consumer* (usually exactly once although some message systems support a more performant at-least-once mode for messages with [idempotent][] processing).
Sending messages to a destination is called "*publish*" in context of this specification.

A source represents an entity within messaging system messages are consumed from. Source and destination for specific message may be the same. However, if message is routed within one or multiple brokers, source and destination can be different.

In a messaging system such as Apache Kafka, all destinations are *topic*s.
Each record, or message, is sent to a single consumer per consumer group.
Consumer groups provide *deliver once* semantics for consumers of a topic within a group.
Whether a specific message is processed as if it was sent to a topic or queue entirely depends on the consumer groups and their composition.
For instance, there can be multiple consumer groups processing records from the same topic.

[idempotent]: https://en.wikipedia.org/wiki/Idempotence
Typical examples of destinations and sources include Kafka topics, RabbitMQ queues and topics.

### Message consumption

Expand Down Expand Up @@ -274,25 +264,22 @@ The following additional attributes describe message producer operations.
| Attribute | Type | Description | Examples | Requirement Level |
|---|---|---|---|---|
| `messaging.destination.anonymous` | boolean | A boolean that is true if the message destination is anonymous (could be unnamed or have auto-generated name). | | Conditionally Required: [1] |
| `messaging.destination.kind` | string | The kind of message destination | `queue` | Conditionally Required: [2] |
| `messaging.destination.name` | string | The message destination name [3] | `MyQueue`; `MyTopic` | Conditionally Required: [4] |
| `messaging.destination.template` | string | Low cardinality representation of the messaging destination name [5] | `/customers/{customerId}` | Conditionally Required: [6] |
| `messaging.destination.temporary` | boolean | A boolean that is true if the message destination is temporary and might not exist anymore after messages are processed. | | Conditionally Required: [7] |
| `messaging.destination.name` | string | The message destination name [2] | `MyQueue`; `MyTopic` | Conditionally Required: [3] |
| `messaging.destination.template` | string | Low cardinality representation of the messaging destination name [4] | `/customers/{customerId}` | Conditionally Required: [5] |
| `messaging.destination.temporary` | boolean | A boolean that is true if the message destination is temporary and might not exist anymore after messages are processed. | | Conditionally Required: [6] |

**[1]:** If value is `true`. When missing, the value is assumed to be `false`.

**[2]:** If the message destination is either a `queue` or a `topic`.

**[3]:** Destination name SHOULD uniquely identify a specific queue, topic or other entity within the broker. If
**[2]:** Destination name SHOULD uniquely identify a specific queue, topic or other entity within the broker. If
the broker does not have such notion, the destination name SHOULD uniquely identify the broker.

**[4]:** If one message is being published or if the value applies to all messages in the batch.
**[3]:** If one message is being published or if the value applies to all messages in the batch.

**[5]:** Destination names could be constructed from templates. An example would be a destination name involving a user name or product id. Although the destination name in this case is of high cardinality, the underlying template is of low cardinality and can be effectively used for grouping and aggregation.
**[4]:** Destination names could be constructed from templates. An example would be a destination name involving a user name or product id. Although the destination name in this case is of high cardinality, the underlying template is of low cardinality and can be effectively used for grouping and aggregation.

**[6]:** If available. Instrumentations MUST NOT use `messaging.destination.name` as template unless low-cardinality of destination name is guaranteed.
**[5]:** If available. Instrumentations MUST NOT use `messaging.destination.name` as template unless low-cardinality of destination name is guaranteed.

**[7]:** If value is `true`. When missing, the value is assumed to be `false`.
**[6]:** If value is `true`. When missing, the value is assumed to be `false`.
<!-- endsemconv -->

### Consumer attributes
Expand All @@ -306,32 +293,28 @@ The following additional attributes describe message consumer operations.
|---|---|---|---|---|
| `messaging.consumer.id` | string | The identifier for the consumer receiving a message. For Kafka, set it to `{messaging.kafka.consumer.group} - {messaging.kafka.client_id}`, if both are present, or only `messaging.kafka.consumer.group`. For brokers, such as RabbitMQ and Artemis, set it to the `client_id` of the client consuming the message. | `mygroup - client-6` | Recommended |
| `messaging.destination.anonymous` | boolean | A boolean that is true if the message destination is anonymous (could be unnamed or have auto-generated name). | | Recommended: If known on consumer |
| `messaging.destination.kind` | string | The kind of message destination | `queue` | Recommended: If known on consumer |
| `messaging.destination.name` | string | The message destination name [1] | `MyQueue`; `MyTopic` | Recommended: If known on consumer |
| `messaging.destination.temporary` | boolean | A boolean that is true if the message destination is temporary and might not exist anymore after messages are processed. | | Recommended: If known on consumer |
| `messaging.source.anonymous` | boolean | A boolean that is true if the message source is anonymous (could be unnamed or have auto-generated name). | | Recommended: [2] |
| `messaging.source.kind` | string | The kind of message source | `queue` | Conditionally Required: [3] |
| `messaging.source.name` | string | The message source name [4] | `MyQueue`; `MyTopic` | Conditionally Required: [5] |
| `messaging.source.template` | string | Low cardinality representation of the messaging source name [6] | `/customers/{customerId}` | Conditionally Required: [7] |
| `messaging.source.temporary` | boolean | A boolean that is true if the message source is temporary and might not exist anymore after messages are processed. | | Recommended: [8] |
| `messaging.source.name` | string | The message source name [3] | `MyQueue`; `MyTopic` | Conditionally Required: [4] |
| `messaging.source.template` | string | Low cardinality representation of the messaging source name [5] | `/customers/{customerId}` | Conditionally Required: [6] |
| `messaging.source.temporary` | boolean | A boolean that is true if the message source is temporary and might not exist anymore after messages are processed. | | Recommended: [7] |

**[1]:** Destination name SHOULD uniquely identify a specific queue, topic or other entity within the broker. If
the broker does not have such notion, the destination name SHOULD uniquely identify the broker.

**[2]:** When supported by messaging system and only if the source is anonymous. When missing, the value is assumed to be `false`.

**[3]:** If the message source is either a `queue` or `topic`.

**[4]:** Source name SHOULD uniquely identify a specific queue, topic, or other entity within the broker. If
**[3]:** Source name SHOULD uniquely identify a specific queue, topic, or other entity within the broker. If
the broker does not have such notion, the source name SHOULD uniquely identify the broker.

**[5]:** If the value applies to all messages in the batch.
**[4]:** If the value applies to all messages in the batch.

**[6]:** Source names could be constructed from templates. An example would be a source name involving a user name or product id. Although the source name in this case is of high cardinality, the underlying template is of low cardinality and can be effectively used for grouping and aggregation.
**[5]:** Source names could be constructed from templates. An example would be a source name involving a user name or product id. Although the source name in this case is of high cardinality, the underlying template is of low cardinality and can be effectively used for grouping and aggregation.

**[7]:** If available. Instrumentations MUST NOT use `messaging.source.name` as template unless low-cardinality of source name is guaranteed.
**[6]:** If available. Instrumentations MUST NOT use `messaging.source.name` as template unless low-cardinality of source name is guaranteed.

**[8]:** When supported by messaging system and only if the source is temporary. When missing, the value is assumed to be `false`.
**[7]:** When supported by messaging system and only if the source is temporary. When missing, the value is assumed to be `false`.
<!-- endsemconv -->

The *receive* span is be used to track the time used for receiving the message(s), whereas the *process* span(s) track the time for processing the message(s).
Expand Down Expand Up @@ -459,9 +442,7 @@ Process CB: | Span CB1 |
| `net.peer.port` | `1234` | `1234` | `1234` |
| `messaging.system` | `"rabbitmq"` | `"rabbitmq"` | `"rabbitmq"` |
| `messaging.destination.name` | `"T"` | | |
| `messaging.destination.kind` | `"topic"` | | |
| `messaging.source.name` | | `"T"` | `"T"` |
| `messaging.source.kind` | | `"topic"` | `"topic"` |
| `messaging.operation` | | `"process"` | `"process"` |
| `messaging.message.id` | `"a1"` | `"a1"`| `"a1"` |

Expand Down Expand Up @@ -496,9 +477,7 @@ Process CB: | Span Rcv2 |
| `service.name` | | `"myConsumer1"` | `"myConsumer1"` | | `"myConsumer2"` |
| `messaging.system` | `"kafka"` | `"kafka"` | `"kafka"` | `"kafka"` | `"kafka"` |
| `messaging.destination.name` | `"T1"` | | | | |
| `messaging.destination.kind` | `"topic"` | | | | |
| `messaging.source.name` | | `"T1"` | `"T1"` | `"T2"` | `"T2"` |
| `messaging.source.kind` | | `"topic"` | `"topic"` | `"topic"` | `"topic"` |
| `messaging.operation` | | | `"process"` | | `"receive"` |
| `messaging.kafka.message.key` | `"myKey"` | `"myKey"` | `"myKey"` | `"anotherKey"` | `"anotherKey"` |
| `messaging.kafka.consumer.group` | | `"my-group"` | `"my-group"` | | `"another-group"` |
Expand Down Expand Up @@ -531,9 +510,7 @@ Process C: | Span Recv1 |
| `net.peer.port` | `1234` | `1234` | `1234` | `1234` | `1234` |
| `messaging.system` | `"rabbitmq"` | `"rabbitmq"` | `"rabbitmq"` | `"rabbitmq"` | `"rabbitmq"` |
| `messaging.destination.name` | `"Q"` | `"Q"` | | | |
| `messaging.destination.kind` | `"queue"` | `"queue"` | | | |
| `messaging.source.name` | | | `"Q"` | `"Q"` | `"Q"` |
| `messaging.source.kind` | | | `"queue"` | `"queue"` | `"queue"` |
| `messaging.operation` | | | `"receive"` | `"process"` | `"process"` |
| `messaging.message.id` | `"a1"` | `"a2"` | | `"a1"` | `"a2"` |
| `messaging.batch.message_count` | | | 2 | | |
Expand Down Expand Up @@ -568,9 +545,7 @@ Process C: | Span Recv1 | Span Recv2 |
| `net.peer.port` | `1234` | `1234` | `1234` | `1234` | `1234` |
| `messaging.system` | `"rabbitmq"` | `"rabbitmq"` | `"rabbitmq"` | `"rabbitmq"` | `"rabbitmq"` |
| `messaging.destination.name` | `"Q"` | `"Q"` | | | |
| `messaging.destination.kind` | `"queue"` | `"queue"` | | | |
| `messaging.source.name` | | | `"Q"` | `"Q"` | `"Q"` |
| `messaging.source.kind` | | | `"queue"` | `"queue"` | `"queue"` |
| `messaging.operation` | | | `"receive"` | `"receive"` | `"process"` |
| `messaging.message.id` | `"a1"` | `"a2"` | `"a1"` | `"a2"` | |
| `messaging.batch.message_count` | | | 1 | 1 | 2 |

0 comments on commit 89a9601

Please sign in to comment.