diff --git a/.markdown_link_check_config.json b/.markdown_link_check_config.json
index 96d7455c249..dac3ae97bb1 100644
--- a/.markdown_link_check_config.json
+++ b/.markdown_link_check_config.json
@@ -4,6 +4,12 @@
"pattern": "^https://github\\.com/open-telemetry/opentelemetry-specification/(issues|pull)"
}
],
+ "replacementPatterns": [
+ {
+ "pattern": "^/",
+ "replacement": "{{BASEURL}}/"
+ }
+ ],
"retryOn429": true,
"aliveStatusCodes": [
200,
diff --git a/CHANGELOG.md b/CHANGELOG.md
index 14ae7e081b9..cffd1de1651 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -15,36 +15,104 @@ release.
### Logs
+### Resource
+
+### Semantic Conventions
+
+- Move X-Ray Env Variable propagation to span link instead of parent for AWS Lambda.
+ ([#3166](https://github.com/open-telemetry/opentelemetry-specification/pull/3166))
+
+### Compatibility
+
+### OpenTelemetry Protocol
+
+### SDK Configuration
+
+### Telemetry Schemas
+
+### Common
+
+## v1.18.0 (2023-02-09)
+
+### Context
+
+- No changes.
+
+### Traces
+
+- Clarify guidance regarding excessive logging when attributes are dropped
+ or truncated.
+ ([#3151](https://github.com/open-telemetry/opentelemetry-specification/pull/3151))
+
+### Metrics
+
+- No changes.
+
+### Logs
+
- Define BatchLogRecordProcessor default configuration values.
([#3002](https://github.com/open-telemetry/opentelemetry-specification/pull/3002))
+- Clarify guidance regarding excessive logging when attributes are dropped
+ or truncated.
+ ([#3151](https://github.com/open-telemetry/opentelemetry-specification/pull/3151))
### Resource
+- No changes.
+
### Semantic Conventions
+- Add Cloud Spanner and Microsoft SQL Server Compact to db.system semantic conventions
+ ([#3105](https://github.com/open-telemetry/opentelemetry-specification/pull/3105)).
- Enable semantic convention tooling for metrics in spec
([#3119](https://github.com/open-telemetry/opentelemetry-specification/pull/3119))
- Rename google openshift platform attribute from `google_cloud_openshift` to `gcp_openshift`
to match the existing `cloud.provider` prefix.
- [#3095](https://github.com/open-telemetry/opentelemetry-specification/pull/3095)
+ ([#3095](https://github.com/open-telemetry/opentelemetry-specification/pull/3095))
+- Changes http server span names from `{http.route}` to `{http.method} {http.route}`
+ (when route is available), and from `HTTP {http.method}` to `{http.method}` (when
+ route is not available).
+ Changes http client span names from `HTTP {http.method}` to `{http.method}`.
+ ([#3165](https://github.com/open-telemetry/opentelemetry-specification/pull/3165))
+- Mark `http.server.duration` and `http.client.duration` metrics as required, and mark
+ all other HTTP metrics as optional.
+ [#3158](https://github.com/open-telemetry/opentelemetry-specification/pull/3158)
+- Add `net.host.port` to `http.server.active_requests` metrics attributes.
+ [#3158](https://github.com/open-telemetry/opentelemetry-specification/pull/3158)
+- `http.route` SHOULD contain the "application root" if there is one.
+ ([#3164](https://github.com/open-telemetry/opentelemetry-specification/pull/3164))
### Compatibility
+- Add condition with sum and count for Prometheus summaries
+ ([3059](https://github.com/open-telemetry/opentelemetry-specification/pull/3059)).
+- Clarify prometheus unit conversions
+ ([#3066](https://github.com/open-telemetry/opentelemetry-specification/pull/3066)).
+- Define conversion mapping from OTel Exponential Histograms to Prometheus Native
+ Histograms.
+ ([#3079](https://github.com/open-telemetry/opentelemetry-specification/pull/3079))
- Fix Prometheus histogram metric suffixes. Bucket series end in `_bucket`
([#3018](https://github.com/open-telemetry/opentelemetry-specification/pull/3018)).
### OpenTelemetry Protocol
+- No changes.
+
### SDK Configuration
+- Add log-specific attribute limit configuration and clarify that general
+ attribute limit configuration also apply to log records
+ ([#2861](https://github.com/open-telemetry/opentelemetry-specification/pull/2861)).
+
### Telemetry Schemas
+- No changes.
+
### Common
-## v1.17.0 (2023-01-17)
+- No changes.
-- Add Cloud Spanner and Microsoft SQL Server Compact to db.system semantic conventions.
- [#3105](https://github.com/open-telemetry/opentelemetry-specification/pull/3105)
+## v1.17.0 (2023-01-17)
### Context
@@ -119,8 +187,6 @@ release.
- Add OpenCensus migration guide and add BinaryPropagation as an option to gRPC
instrumentation for OpenCensus compatibility
([#3015](https://github.com/open-telemetry/opentelemetry-specification/pull/3015)).
-- Add condition with sum and count for Prometheus summaries
-([3059](https://github.com/open-telemetry/opentelemetry-specification/pull/3059))
### OpenTelemetry Protocol
@@ -215,9 +281,6 @@ release.
- Specify handling of invalid numeric environment variables
([#2963](https://github.com/open-telemetry/opentelemetry-specification/pull/2963))
-- Add log-specific attribute limit configuration and clarify that general
- attribute limit configuration also apply to log records.
- ([#2861](https://github.com/open-telemetry/opentelemetry-specification/pull/2861))
### Telemetry Schemas
diff --git a/schemas/1.18.0 b/schemas/1.18.0
new file mode 100644
index 00000000000..400bd0969e0
--- /dev/null
+++ b/schemas/1.18.0
@@ -0,0 +1,60 @@
+file_format: 1.1.0
+schema_url: https://opentelemetry.io/schemas/1.18.0
+versions:
+ 1.18.0:
+ 1.17.0:
+ spans:
+ changes:
+ # https://github.com/open-telemetry/opentelemetry-specification/pull/2957
+ - rename_attributes:
+ attribute_map:
+ messaging.consumer_id: messaging.consumer.id
+ messaging.protocol: net.app.protocol.name
+ messaging.protocol_version: net.app.protocol.version
+ messaging.destination: messaging.destination.name
+ messaging.temp_destination: messaging.destination.temporary
+ messaging.destination_kind: messaging.destination.kind
+ messaging.message_id: messaging.message.id
+ messaging.conversation_id: messaging.message.conversation_id
+ messaging.message_payload_size_bytes: messaging.message.payload_size_bytes
+ messaging.message_payload_compressed_size_bytes: messaging.message.payload_compressed_size_bytes
+ messaging.rabbitmq.routing_key: messaging.rabbitmq.destination.routing_key
+ messaging.kafka.message_key: messaging.kafka.message.key
+ messaging.kafka.partition: messaging.kafka.destination.partition
+ messaging.kafka.tombstone: messaging.kafka.message.tombstone
+ messaging.rocketmq.message_type: messaging.rocketmq.message.type
+ messaging.rocketmq.message_tag: messaging.rocketmq.message.tag
+ messaging.rocketmq.message_keys: messaging.rocketmq.message.keys
+ messaging.kafka.consumer_group: messaging.kafka.consumer.group
+ 1.16.0:
+ 1.15.0:
+ spans:
+ changes:
+ # https://github.com/open-telemetry/opentelemetry-specification/pull/2743
+ - rename_attributes:
+ attribute_map:
+ http.retry_count: http.resend_count
+ 1.14.0:
+ 1.13.0:
+ spans:
+ changes:
+ # https://github.com/open-telemetry/opentelemetry-specification/pull/2614
+ - rename_attributes:
+ attribute_map:
+ net.peer.ip: net.sock.peer.addr
+ net.host.ip: net.sock.host.addr
+ 1.12.0:
+ 1.11.0:
+ 1.10.0:
+ 1.9.0:
+ 1.8.0:
+ spans:
+ changes:
+ - rename_attributes:
+ attribute_map:
+ db.cassandra.keyspace: db.name
+ db.hbase.namespace: db.name
+ 1.7.0:
+ 1.6.1:
+ 1.5.0:
+ 1.4.0:
diff --git a/semantic_conventions/http-common.yaml b/semantic_conventions/http-common.yaml
new file mode 100644
index 00000000000..8d1bf194494
--- /dev/null
+++ b/semantic_conventions/http-common.yaml
@@ -0,0 +1,120 @@
+groups:
+ - id: attributes.http.common
+ type: attribute_group
+ brief: "Describes HTTP attributes."
+ prefix: http
+ attributes:
+ - id: method
+ type: string
+ requirement_level: required
+ brief: 'HTTP request method.'
+ examples: ["GET", "POST", "HEAD"]
+ - id: status_code
+ type: int
+ requirement_level:
+ conditionally_required: If and only if one was received/sent.
+ brief: '[HTTP response status code](https://tools.ietf.org/html/rfc7231#section-6).'
+ examples: [200]
+ - id: flavor
+ type:
+ # Default value: `true`. If false, it helps the code gen tool to
+ # encode checks that only accept the listed values.
+ allow_custom_values: true
+ members:
+ - id: http_1_0
+ value: '1.0'
+ brief: 'HTTP/1.0'
+ - id: http_1_1
+ value: '1.1'
+ brief: 'HTTP/1.1'
+ - id: http_2_0
+ value: '2.0'
+ brief: 'HTTP/2'
+ - id: http_3_0
+ value: '3.0'
+ brief: 'HTTP/3'
+ - id: spdy
+ value: 'SPDY'
+ brief: 'SPDY protocol.'
+ - id: quic
+ value: 'QUIC'
+ brief: 'QUIC protocol.'
+ brief: 'Kind of HTTP protocol used.'
+ note: >
+ If `net.transport` is not specified, it can be assumed to be `IP.TCP` except if `http.flavor`
+ is `QUIC`, in which case `IP.UDP` is assumed.
+
+ - id: attributes.http.client
+ prefix: http
+ type: attribute_group
+ brief: 'HTTP Client spans attributes'
+ attributes:
+ - ref: net.peer.name
+ requirement_level: required
+ brief: >
+ Host identifier of the ["URI origin"](https://www.rfc-editor.org/rfc/rfc9110.html#name-uri-origin) HTTP request is sent to.
+ note: |
+ Determined by using the first of the following that applies
+
+ - Host identifier of the [request target](https://www.rfc-editor.org/rfc/rfc9110.html#target.resource)
+ if it's sent in absolute-form
+ - Host identifier of the `Host` header
+
+ SHOULD NOT be set if capturing it would require an extra DNS lookup.
+ - ref: net.peer.port
+ requirement_level:
+ conditionally_required: If not default (`80` for `http` scheme, `443` for `https`).
+ brief: >
+ Port identifier of the ["URI origin"](https://www.rfc-editor.org/rfc/rfc9110.html#name-uri-origin) HTTP request is sent to.
+ note: >
+ When [request target](https://www.rfc-editor.org/rfc/rfc9110.html#target.resource) is absolute URI, `net.peer.name` MUST match
+ URI port identifier, otherwise it MUST match `Host` header port identifier.
+
+ - id: attributes.http.server
+ prefix: http
+ type: attribute_group
+ brief: 'HTTP Server spans attributes'
+ attributes:
+ - id: scheme
+ type: string
+ brief: 'The URI scheme identifying the used protocol.'
+ requirement_level: required
+ examples: ["http", "https"]
+ - id: route
+ type: string
+ requirement_level:
+ conditionally_required: If and only if it's available
+ brief: >
+ The matched route (path template in the format used by the respective server framework). See note below
+ examples: ['/users/:userID?', '{controller}/{action}/{id?}']
+ note: >
+ MUST NOT be populated when this is not supported by the HTTP server framework as the route attribute should have low-cardinality and the URI path can NOT substitute it.
+
+ SHOULD include the [application root](/specification/trace/semantic_conventions/http.md#http-server-definitions) if there is one.
+ - ref: net.host.name
+ requirement_level: required
+ brief: >
+ Name of the local HTTP server that received the request.
+ note: |
+ Determined by using the first of the following that applies
+
+ - The [primary server name](/specification/trace/semantic_conventions/http.md#http-server-definitions) of the matched virtual host. MUST only
+ include host identifier.
+ - Host identifier of the [request target](https://www.rfc-editor.org/rfc/rfc9110.html#target.resource)
+ if it's sent in absolute-form.
+ - Host identifier of the `Host` header
+
+ SHOULD NOT be set if only IP address is available and capturing name would require a reverse DNS lookup.
+
+ - ref: net.host.port
+ requirement_level:
+ conditionally_required: If not default (`80` for `http` scheme, `443` for `https`).
+ brief: >
+ Port of the local HTTP server that received the request.
+ note: |
+ Determined by using the first of the following that applies
+
+ - Port identifier of the [primary server host](/specification/trace/semantic_conventions/http.md#http-server-definitions) of the matched virtual host.
+ - Port identifier of the [request target](https://www.rfc-editor.org/rfc/rfc9110.html#target.resource)
+ if it's sent in absolute-form.
+ - Port identifier of the `Host` header
diff --git a/semantic_conventions/logs/events.yaml b/semantic_conventions/logs/events.yaml
index 7d7d80f88df..f3398c9ac12 100644
--- a/semantic_conventions/logs/events.yaml
+++ b/semantic_conventions/logs/events.yaml
@@ -1,6 +1,6 @@
groups:
- id: event
- type: span
+ type: attribute_group
prefix: event
brief: >
This document defines attributes for Events represented using Log Records.
diff --git a/semantic_conventions/logs/log-exception.yaml b/semantic_conventions/logs/log-exception.yaml
index 94c52ba80cd..d0b251552aa 100644
--- a/semantic_conventions/logs/log-exception.yaml
+++ b/semantic_conventions/logs/log-exception.yaml
@@ -1,6 +1,6 @@
groups:
- id: log-exception
- type: span
+ type: attribute_group
prefix: exception
brief: >
This document defines attributes for exceptions represented using Log
diff --git a/semantic_conventions/metrics/http.yaml b/semantic_conventions/metrics/http.yaml
new file mode 100644
index 00000000000..cb23f27e927
--- /dev/null
+++ b/semantic_conventions/metrics/http.yaml
@@ -0,0 +1,119 @@
+groups:
+ - id: metric.http.server.duration
+ type: metric
+ metric_name: http.server.duration
+ brief: "Measures the duration of inbound HTTP requests."
+ instrument: histogram
+ unit: "ms"
+ extends: attributes.http.server
+ attributes:
+ # todo (lmolkova) build tools don't populate grandparent attributes
+ - ref: http.method
+ - ref: http.status_code
+ - ref: http.flavor
+
+ - id: metric.http.server.active_requests
+ type: metric
+ metric_name: http.server.active_requests
+ brief: "Measures the number of concurrent HTTP requests that are currently in-flight."
+ instrument: updowncounter
+ unit: "{requests}"
+ attributes:
+ - ref: http.method
+ - ref: http.status_code
+ - ref: http.scheme
+ - ref: net.host.name
+ requirement_level: required
+ brief: >
+ Name of the local HTTP server that received the request.
+ note: |
+ Determined by using the first of the following that applies
+
+ - The [primary server name](/specification/trace/semantic_conventions/http.md#http-server-definitions) of the matched virtual host. MUST only
+ include host identifier.
+ - Host identifier of the [request target](https://www.rfc-editor.org/rfc/rfc9110.html#target.resource)
+ if it's sent in absolute-form.
+ - Host identifier of the `Host` header
+
+ SHOULD NOT be set if only IP address is available and capturing name would require a reverse DNS lookup.
+
+ - ref: net.host.port
+ requirement_level:
+ conditionally_required: If not default (`80` for `http` scheme, `443` for `https`).
+ brief: >
+ Port of the local HTTP server that received the request.
+ note: |
+ Determined by using the first of the following that applies
+
+ - Port identifier of the [primary server host](/specification/trace/semantic_conventions/http.md#http-server-definitions) of the matched virtual host.
+ - Port identifier of the [request target](https://www.rfc-editor.org/rfc/rfc9110.html#target.resource)
+ if it's sent in absolute-form.
+ - Port identifier of the `Host` header
+
+ - id: metric.http.server.request.size
+ type: metric
+ metric_name: http.server.request.size
+ brief: "Measures the size of HTTP request messages (compressed)."
+ instrument: histogram
+ unit: "By"
+ extends: attributes.http.server
+ # TODO (trask) below attributes are identical to above in metric.http.server.duration
+ attributes:
+ # todo (lmolkova) build tools don't populate grandparent attributes
+ - ref: http.method
+ - ref: http.status_code
+ - ref: http.flavor
+
+ - id: metric.http.server.response.size
+ type: metric
+ metric_name: http.server.response.size
+ brief: "Measures the size of HTTP response messages (compressed)."
+ instrument: histogram
+ unit: "By"
+ extends: attributes.http.server
+ # TODO (trask) below attributes are identical to above in metric.http.server.duration
+ attributes:
+ - ref: http.method
+ - ref: http.status_code
+ - ref: http.flavor
+
+ - id: metric.http.client.duration
+ type: metric
+ metric_name: http.client.duration
+ brief: "Measures the duration of outbound HTTP requests."
+ instrument: histogram
+ unit: "ms"
+ extends: attributes.http.client
+ attributes:
+ - ref: http.method
+ - ref: http.status_code
+ - ref: http.flavor
+ - ref: net.sock.peer.addr
+
+ - id: metric.http.client.request.size
+ type: metric
+ metric_name: http.client.request.size
+ brief: "Measures the size of HTTP request messages (compressed)."
+ instrument: histogram
+ unit: "By"
+ extends: attributes.http.client
+ # TODO (trask) below attributes are identical to above in metric.http.client.duration
+ attributes:
+ - ref: http.method
+ - ref: http.status_code
+ - ref: http.flavor
+ - ref: net.sock.peer.addr
+
+ - id: metric.http.client.response.size
+ type: metric
+ metric_name: http.client.response.size
+ brief: "Measures the size of HTTP response messages (compressed)."
+ instrument: histogram
+ unit: "By"
+ extends: attributes.http.client
+ # TODO (trask) below attributes are identical to above in metric.http.client.duration
+ attributes:
+ - ref: http.method
+ - ref: http.status_code
+ - ref: http.flavor
+ - ref: net.sock.peer.addr
diff --git a/semantic_conventions/trace/faas.yaml b/semantic_conventions/trace/faas.yaml
index fac000a7cef..ff4963b164d 100644
--- a/semantic_conventions/trace/faas.yaml
+++ b/semantic_conventions/trace/faas.yaml
@@ -95,7 +95,7 @@ groups:
Semantic Convention for FaaS triggered as a response to some data
source operation such as a database or filesystem read/write.
constraints:
- - include: http.server
+ - include: trace.http.server
- id: faas_span.pubsub
type: span
diff --git a/semantic_conventions/trace/general.yaml b/semantic_conventions/trace/general.yaml
index 4491cc10290..54403442946 100644
--- a/semantic_conventions/trace/general.yaml
+++ b/semantic_conventions/trace/general.yaml
@@ -1,7 +1,7 @@
groups:
- id: network
prefix: net
- type: span
+ type: attribute_group
brief: >
These attributes may be used for any network related operation.
attributes:
diff --git a/semantic_conventions/trace/http.yaml b/semantic_conventions/trace/http.yaml
index d29672e4d3f..6b2eefbeacb 100644
--- a/semantic_conventions/trace/http.yaml
+++ b/semantic_conventions/trace/http.yaml
@@ -1,52 +1,13 @@
groups:
- - id: http
+ - id: trace.http.common
prefix: http
- type: span
+ extends: attributes.http.common
+ type: attribute_group
brief: 'This document defines semantic conventions for HTTP client and server Spans.'
note: >
These conventions can be used for http and https schemes
and various HTTP versions like 1.1, 2 and SPDY.
attributes:
- - id: method
- type: string
- requirement_level: required
- brief: 'HTTP request method.'
- sampling_relevant: true
- examples: ["GET", "POST", "HEAD"]
- - id: status_code
- type: int
- requirement_level:
- conditionally_required: If and only if one was received/sent.
- brief: '[HTTP response status code](https://tools.ietf.org/html/rfc7231#section-6).'
- examples: [200]
- - id: flavor
- type:
- # Default value: `true`. If false, it helps the code gen tool to
- # encode checks that only accept the listed values.
- allow_custom_values: true
- members:
- - id: http_1_0
- value: '1.0'
- brief: 'HTTP/1.0'
- - id: http_1_1
- value: '1.1'
- brief: 'HTTP/1.1'
- - id: http_2_0
- value: '2.0'
- brief: 'HTTP/2'
- - id: http_3_0
- value: '3.0'
- brief: 'HTTP/3'
- - id: spdy
- value: 'SPDY'
- brief: 'SPDY protocol.'
- - id: quic
- value: 'QUIC'
- brief: 'QUIC protocol.'
- brief: 'Kind of HTTP protocol used.'
- note: >
- If `net.transport` is not specified, it can be assumed to be `IP.TCP` except if `http.flavor`
- is `QUIC`, in which case `IP.UDP` is assumed.
- id: user_agent
type: string
brief: 'Value of the [HTTP User-Agent](https://www.rfc-editor.org/rfc/rfc9110.html#field.user-agent) header sent by the client.'
@@ -65,18 +26,18 @@ groups:
is often, but not always, present as the [Content-Length](https://www.rfc-editor.org/rfc/rfc9110.html#field.content-length)
header. For requests using transport encoding, this should be the compressed size.
examples: 3495
+ - ref: http.method
+ sampling_relevant: true
- ref: net.sock.peer.addr
- ref: net.sock.peer.port
- ref: net.sock.peer.name
- ref: net.sock.family
examples: ['inet', 'inet6']
- constraints:
- - include: network
- - id: http.client
+ - id: trace.http.client
prefix: http
type: span
- extends: http
+ extends: attributes.http.client
span_kind: client
brief: 'Semantic Convention for HTTP Client'
attributes:
@@ -91,9 +52,20 @@ groups:
In such case the attribute's value should be `https://www.example.com/`.
sampling_relevant: true
examples: ['https://www.foo.bar/search?q=OpenTelemetry#SemConv']
+ - id: resend_count
+ type: int
+ brief: >
+ The ordinal number of request resending attempt (for any reason, including redirects).
+ note: >
+ The resend count SHOULD be updated each time an HTTP request gets resent by the client, regardless of what
+ was the cause of the resending (e.g. redirection, authorization failure, 503 Server Unavailable, network issues,
+ or any other).
+ requirement_level:
+ recommended: if and only if request was retried.
+ examples: 3
- ref: net.peer.name
- requirement_level: required
sampling_relevant: true
+ requirement_level: required
brief: >
Host identifier of the ["URI origin"](https://www.rfc-editor.org/rfc/rfc9110.html#name-uri-origin) HTTP request is sent to.
note: |
@@ -113,46 +85,20 @@ groups:
note: >
When [request target](https://www.rfc-editor.org/rfc/rfc9110.html#target.resource) is absolute URI, `net.peer.name` MUST match
URI port identifier, otherwise it MUST match `Host` header port identifier.
- - id: resend_count
- type: int
- brief: >
- The ordinal number of request resending attempt (for any reason, including redirects).
- note: >
- The resend count SHOULD be updated each time an HTTP request gets resent by the client, regardless of what
- was the cause of the resending (e.g. redirection, authorization failure, 503 Server Unavailable, network issues,
- or any other).
- requirement_level:
- recommended: if and only if request was retried.
- examples: 3
- - id: http.server
+ - id: trace.http.server
prefix: http
type: span
- extends: http
+ extends: attributes.http.server
span_kind: server
brief: 'Semantic Convention for HTTP Server'
attributes:
- - id: scheme
- type: string
- brief: 'The URI scheme identifying the used protocol.'
- requirement_level: required
- sampling_relevant: true
- examples: ["http", "https"]
- id: target
type: string
brief: 'The full request target as passed in a HTTP request line or equivalent.'
requirement_level: required
sampling_relevant: true
examples: ['/path/12314/?q=ddds']
- - id: route
- type: string
- requirement_level:
- conditionally_required: If and only if it's available
- brief: >
- The matched route (path template in the format used by the respective server framework). See note below
- examples: ['/users/:userID?', '{controller}/{action}/{id?}']
- note: >
- 'http.route' MUST NOT be populated when this is not supported by the HTTP server framework as the route attribute should have low-cardinality and the URI path can NOT substitute it.
- id: client_ip
type: string
brief: >
@@ -171,6 +117,8 @@ groups:
one is at least somewhat confident that the address is not that of
the closest proxy.
examples: '83.164.160.102'
+ - ref: http.scheme
+ sampling_relevant: true
- ref: net.host.name
requirement_level: required
sampling_relevant: true
@@ -179,7 +127,7 @@ groups:
note: |
Determined by using the first of the following that applies
- - The [primary server name](#http-server-definitions) of the matched virtual host. MUST only
+ - The [primary server name](/specification/trace/semantic_conventions/http.md#http-server-definitions) of the matched virtual host. MUST only
include host identifier.
- Host identifier of the [request target](https://www.rfc-editor.org/rfc/rfc9110.html#target.resource)
if it's sent in absolute-form.
@@ -196,11 +144,10 @@ groups:
note: |
Determined by using the first of the following that applies
- - Port identifier of the [primary server host](#http-server-definitions) of the matched virtual host.
+ - Port identifier of the [primary server host](/specification/trace/semantic_conventions/http.md#http-server-definitions) of the matched virtual host.
- Port identifier of the [request target](https://www.rfc-editor.org/rfc/rfc9110.html#target.resource)
if it's sent in absolute-form.
- Port identifier of the `Host` header
-
- ref: net.sock.host.addr
requirement_level: optional
- ref: net.sock.host.port
diff --git a/semantic_conventions/trace/messaging.yaml b/semantic_conventions/trace/messaging.yaml
index 83b049f4561..e89f6b6f944 100644
--- a/semantic_conventions/trace/messaging.yaml
+++ b/semantic_conventions/trace/messaging.yaml
@@ -1,8 +1,7 @@
groups:
- id: messaging.message
prefix: messaging
- # todo (https://github.com/open-telemetry/build-tools/issues/123)
- type: span
+ type: attribute_group
brief: 'Semantic convention describing per-message attributes populated on messaging spans or links.'
attributes:
- ref: messaging.destination.name
@@ -30,8 +29,7 @@ groups:
- id: messaging.destination
prefix: messaging.destination
- # todo (https://github.com/open-telemetry/build-tools/issues/123)
- type: span
+ type: attribute_group
brief: 'Semantic convention for attributes that describe messaging destination on broker'
attributes:
- id: name
@@ -71,8 +69,7 @@ groups:
- id: messaging.source
prefix: messaging.source
- # todo (https://github.com/open-telemetry/build-tools/issues/123)
- type: span
+ type: attribute_group
brief: 'Semantic convention for attributes that describe messaging source on broker'
attributes:
- id: name
@@ -270,7 +267,7 @@ groups:
- id: messaging.rabbitmq
prefix: messaging.rabbitmq
- type: span
+ type: attribute_group
extends: messaging
brief: >
Attributes for RabbitMQ
@@ -285,7 +282,7 @@ groups:
- id: messaging.kafka
prefix: messaging.kafka
- type: span
+ type: attribute_group
extends: messaging
brief: >
Attributes for Apache Kafka
@@ -334,7 +331,7 @@ groups:
- id: messaging.rocketmq
prefix: messaging.rocketmq
- type: span
+ type: attribute_group
extends: messaging
brief: >
Attributes for Apache RocketMQ
diff --git a/spec-compliance-matrix.md b/spec-compliance-matrix.md
index c3ff23a5570..a19b9b16e80 100644
--- a/spec-compliance-matrix.md
+++ b/spec-compliance-matrix.md
@@ -28,7 +28,7 @@ formats is required. Implementing more than one format is optional.
| [Trace / Context interaction](specification/trace/api.md#context-interaction) | | | | | | | | | | | | |
| Get active Span | | N/A | + | + | + | + | + | + | + | + | + | + |
| Set active Span | | N/A | + | + | + | + | + | + | + | + | + | + |
-| [Tracer](specification/trace/api.md#tracer-operations) | | | | | | | | | | | | |
+| [Tracer](specification/trace/api.md#tracer-operations) | Optional | Go | Java | JS | Python | Ruby | Erlang | PHP | Rust | C++ | .NET | Swift |
| Create a new Span | | + | + | + | + | + | + | + | + | + | + | + |
| Documentation defines adding attributes at span creation as preferred | | | | | + | + | | + | | | + | |
| Get active Span | | N/A | + | + | + | + | + | + | + | + | + | + |
@@ -38,7 +38,7 @@ formats is required. Implementing more than one format is optional.
| IsValid | | + | + | + | + | + | + | + | + | + | + | + |
| IsRemote | | + | + | + | + | + | + | + | + | + | + | + |
| Conforms to the W3C TraceContext spec | | + | + | + | + | + | + | + | + | + | + | + |
-| [Span](specification/trace/api.md#span) | | | | | | | | | | | | |
+| [Span](specification/trace/api.md#span) | Optional | Go | Java | JS | Python | Ruby | Erlang | PHP | Rust | C++ | .NET | Swift |
| Create root span | | + | + | + | + | + | + | + | + | + | + | + |
| Create with default parent (active span) | | N/A | + | + | + | + | + | + | + | + | + | + |
| Create with parent from Context | | + | + | + | + | + | + | + | + | + | + | + |
@@ -55,7 +55,7 @@ formats is required. Implementing more than one format is optional.
| events collection size limit | | + | + | + | + | + | + | + | + | - | - | + |
| attribute collection size limit | | + | + | + | + | + | + | + | + | - | - | + |
| links collection size limit | | + | + | + | + | + | + | + | + | - | - | + |
-| [Span attributes](specification/trace/api.md#set-attributes) | | | | | | | | | | | | |
+| [Span attributes](specification/trace/api.md#set-attributes) | Optional | Go | Java | JS | Python | Ruby | Erlang | PHP | Rust | C++ | .NET | Swift |
| SetAttribute | | + | + | + | + | + | + | + | + | + | + | + |
| Set order preserved | X | + | - | + | + | + | + | + | + | + | + | + |
| String type | | + | + | + | + | + | + | + | + | + | + | + |
@@ -65,7 +65,7 @@ formats is required. Implementing more than one format is optional.
| Array of primitives (homogeneous) | | + | + | + | + | + | + | + | + | + | + | + |
| `null` values documented as invalid/undefined | | + | + | + | + | + | N/A | + | | + | | N/A |
| Unicode support for keys and string values | | + | + | + | + | + | + | + | + | + | + | + |
-| [Span linking](specification/trace/api.md#specifying-links) | | | | | | | | | | | | |
+| [Span linking](specification/trace/api.md#specifying-links) | Optional | Go | Java | JS | Python | Ruby | Erlang | PHP | Rust | C++ | .NET | Swift |
| Links can be recorded on span creation | | + | + | | + | + | + | + | + | + | + | |
| Links order is preserved | | + | + | | + | + | + | + | + | + | + | |
| [Span events](specification/trace/api.md#add-events) | | | | | | | | | | | | |
@@ -75,9 +75,10 @@ formats is required. Implementing more than one format is optional.
| [Span exceptions](specification/trace/api.md#record-exception) | | | | | | | | | | | | |
| RecordException | | - | + | + | + | + | + | + | + | - | + | - |
| RecordException with extra parameters | | - | + | + | + | + | + | + | + | - | + | - |
-| [Sampling](specification/trace/sdk.md#sampling) | | | | | | | | | | | | |
+| [Sampling](specification/trace/sdk.md#sampling) | Optional | Go | Java | JS | Python | Ruby | Erlang | PHP | Rust | C++ | .NET | Swift |
| Allow samplers to modify tracestate | | + | + | | + | + | + | + | + | + | - | + |
| ShouldSample gets full parent Context | | + | + | + | + | + | + | + | + | + | - | + |
+| Sampler: JaegerRemoteSampler | | + | + | | | | | | + | | | |
| [New Span ID created also for non-recording Spans](specification/trace/sdk.md#sdk-span-creation) | | + | + | | + | + | + | + | + | + | - | + |
| [IdGenerators](specification/trace/sdk.md#id-generators) | | + | + | | + | + | + | + | + | + | | + |
| [SpanLimits](specification/trace/sdk.md#span-limits) | X | + | + | | + | + | + | + | | - | | + |
diff --git a/specification/compatibility/prometheus_and_openmetrics.md b/specification/compatibility/prometheus_and_openmetrics.md
index 5314b1bb2f5..6db6993b0f8 100644
--- a/specification/compatibility/prometheus_and_openmetrics.md
+++ b/specification/compatibility/prometheus_and_openmetrics.md
@@ -27,8 +27,8 @@
* [Gauges](#gauges-1)
* [Sums](#sums)
* [Histograms](#histograms-1)
+ * [Exponential Histograms](#exponential-histograms)
* [Summaries](#summaries-1)
- * [Dropped Data Points](#dropped-data-points)
* [Metric Attributes](#metric-attributes)
* [Exemplars](#exemplars-1)
* [Resource Attributes](#resource-attributes-1)
@@ -293,6 +293,41 @@ An [OpenTelemetry Histogram](../metrics/data-model.md#histogram) with a cumulati
OpenTelemetry Histograms with Delta aggregation temporality SHOULD be aggregated into a Cumulative aggregation temporality and follow the logic above, or MUST be dropped.
+### Exponential Histograms
+
+An [OpenTelemetry Exponential Histogram](../metrics/data-model.md#exponentialhistogram) with
+a cumulative aggregation temporality MUST be converted to a Prometheus Native
+Histogram as follows:
+
+- `Scale` is converted to the Native Histogram `Schema`. Currently,
+ [valid values](https://github.com/prometheus/prometheus/commit/d9d51c565c622cdc7d626d3e7569652bc28abe15#diff-bdaf80ebc5fa26365f45db53435b960ce623ea6f86747fb8870ad1abc355f64fR76-R83)
+ for `schema` are -4 <= n <= 8.
+ If `Scale` is > 8 then Exponential Histogram data points SHOULD be downscaled
+ to a scale accepted by Prometheus (in range [-4,8]). Any data point unable to
+ be rescaled to an acceptable range MUST be dropped.
+- `Count` is converted to Native Histogram `Count` if the `NoRecordedValue`
+ flag is set to `false`, otherwise, Native Histogram `Count` is set to the
+ Stale NaN value.
+- `Sum` is converted to the Native Histogram `Sum` if `Sum` is set and the
+ `NoRecordedValue` flag is set to `false`, otherwise, Native Histogram `Sum` is
+ set to the Stale NaN value.
+- `TimeUnixNano` is converted to the Native Histogram `Timestamp` after
+ converting nanoseconds to milliseconds.
+- `ZeroCount` is converted directly to the Native Histogram `ZeroCount`.
+- `ZeroThreshold`, if set, is converted to the Native Histogram `ZeroThreshold`.
+ Otherwise, it is set to the default value `1e-128`.
+- The dense bucket layout represented by `Positive` bucket counts and `Offset` is
+ converted to the Native Histogram sparse layout represented by `PositiveSpans`
+ and `PositiveDeltas`. The same holds for the `Negative` bucket counts
+ and `Offset`. Note that Prometheus Native Histograms buckets are indexed by
+ upper boundary while Exponential Histograms are indexed by lower boundary, the
+ result being that the Offset fields are different-by-one.
+- `Min` and `Max` are not used.
+- `StartTimeUnixNano` is not used.
+
+[OpenTelemetry Exponential Histogram](../metrics/data-model.md#exponentialhistogram)
+metrics with the delta aggregation temporality are dropped.
+
### Summaries
An [OpenTelemetry Summary](../metrics/data-model.md#summary-legacy) MUST be converted to a Prometheus metric family with the following metrics:
@@ -310,12 +345,6 @@ An [OpenTelemetry Summary](../metrics/data-model.md#summary-legacy) MUST be conv
each point is the computed value of the quantile point.
- Summaries with `StartTimeUnixNano` set should export the `{name}_created` metric as well.
-### Dropped Data Points
-
-The following OTLP data points MUST be dropped:
-
-* [ExponentialHistogram](../metrics/data-model.md#exponentialhistogram)
-
### Metric Attributes
OpenTelemetry Metric Attributes MUST be converted to
diff --git a/specification/logs/data-model.md b/specification/logs/data-model.md
index 8d7221b094a..58faec0e78c 100644
--- a/specification/logs/data-model.md
+++ b/specification/logs/data-model.md
@@ -549,7 +549,7 @@ Can include data that describes particular occurrence of the event.
Can be meta-information, e.g. quality of timestamp value.
SDID origin.swVersion map to Resource["service.version"]
-SDID origin.ip map to attribute[net.host.ip"]
+SDID origin.ip map to attribute["net.sock.host.addr"]
Rest of SDIDs -> Attributes["syslog.*"] |
@@ -846,19 +846,19 @@ When mapping from the unified model to HEC, we apply this additional mapping:
%a |
string |
- Client IP |
- Attributes["net.peer.ip"] |
+ Client address |
+ Attributes["net.sock.peer.addr"] |
%A |
string |
- Server IP |
- Attributes["net.host.ip"] |
+ Server address |
+ Attributes["net.sock.host.addr"] |
%h |
string |
- Remote hostname. |
+ Client hostname. |
Attributes["net.peer.name"] |
@@ -918,7 +918,7 @@ When mapping from the unified model to HEC, we apply this additional mapping:
sourceIPAddress |
string |
The IP address that the request was made from. |
- Resource["net.peer.ip"] or Resource["net.host.ip"]? TBD |
+ Attributes["net.sock.peer.addr"] or Attributes["net.sock.host.addr"] |
errorCode |
@@ -1036,7 +1036,7 @@ All other fields | |
source.ip, client.ip |
string |
The IP address that the request was made from. |
- Attributes["net.peer.ip"] or Attributes["net.host.ip"] |
+ Attributes["net.sock.peer.addr"] or Attributes["net.sock.host.addr"] |
cloud.account.id |
diff --git a/specification/logs/sdk.md b/specification/logs/sdk.md
index 77853fcfe56..425c4121efd 100644
--- a/specification/logs/sdk.md
+++ b/specification/logs/sdk.md
@@ -153,8 +153,8 @@ public interface LogRecordLimits {
There SHOULD be a message printed in the SDK's log to indicate to the user
that an attribute was discarded due to such a limit.
-To prevent excessive logging, the message should not be printed once per
-`LogRecord` or per discarded attribute.
+To prevent excessive logging, the message MUST be printed at most once per
+`LogRecord` (i.e., not per discarded attribute).
## LogRecordProcessor
diff --git a/specification/metrics/api.md b/specification/metrics/api.md
index 663e4d46a17..5bac1968ec0 100644
--- a/specification/metrics/api.md
+++ b/specification/metrics/api.md
@@ -19,9 +19,7 @@ linkTitle: API
* [Meter operations](#meter-operations)
- [Instrument](#instrument)
* [General characteristics](#general-characteristics)
- + [Instrument type conflict detection](#instrument-type-conflict-detection)
- + [Instrument namespace](#instrument-namespace)
- + [Instrument naming rule](#instrument-naming-rule)
+ + [Instrument name syntax](#instrument-name-syntax)
+ [Instrument unit](#instrument-unit)
+ [Instrument description](#instrument-description)
+ [Synchronous and Asynchronous instruments](#synchronous-and-asynchronous-instruments)
@@ -115,30 +113,16 @@ The `MeterProvider` MUST provide the following functions:
This API MUST accept the following parameters:
-* `name`: This name SHOULD uniquely identify the [instrumentation
+* `name`: This name uniquely identifies the [instrumentation
scope](../glossary.md#instrumentation-scope), such as the
[instrumentation library](../glossary.md#instrumentation-library) (e.g.
`io.opentelemetry.contrib.mongodb`), package,
module or class name. If an application or library has built-in OpenTelemetry
instrumentation, both [Instrumented
library](../glossary.md#instrumented-library) and [Instrumentation
- library](../glossary.md#instrumentation-library) may refer to the same
+ library](../glossary.md#instrumentation-library) can refer to the same
library. In that scenario, the `name` denotes a module name or component name
- within that library or application. In case an invalid name (null or empty
- string) is specified, a working Meter implementation MUST be returned as a
- fallback rather than returning null or throwing an exception, its `name`
- property SHOULD keep the original invalid value, and a message reporting that
- the specified value is invalid SHOULD be logged. A library, implementing the
- OpenTelemetry API *may* also ignore this name and return a default instance
- for all calls, if it does not support "named" functionality (e.g. an
- implementation which is not even observability-related). A MeterProvider could
- also return a no-op Meter here if application owners configure the SDK to
- suppress telemetry produced by this library.
-
- The `name` needs to be provided by a user. If possible, the API SHOULD be
- structured so a user is obligated to provide this parameter. If it is not
- possible to structurally enforce this obligation, the API MUST be documented
- in a way to communicate to users that this parameter is needed.
+ within that library or application.
* `version`: Specifies the version of the instrumentation scope if the scope
has a version (e.g. a library version). Example value: `1.0.0`.
@@ -168,23 +152,6 @@ The term *identical* applied to Meters describes instances where all identifying
fields are equal. The term *distinct* applied to Meters describes instances where
at least one identifying field has a different value.
-Implementations MUST NOT require users to repeatedly obtain a `Meter` with
-the same identity to pick up configuration changes. This can be
-achieved either by allowing to work with an outdated configuration or by
-ensuring that new configuration applies also to previously returned `Meter`s.
-
-Note: This could, for example, be implemented by storing any mutable
-configuration in the `MeterProvider` and having `Meter` implementation objects
-have a reference to the `MeterProvider` from which they were obtained. If
-configuration must be stored per-meter (such as disabling a certain meter), the
-meter could, for example, do a look-up with its identity in a map
-in the `MeterProvider`, or the `MeterProvider` could maintain a registry of all
-returned `Meter`s and actively update their configuration if it changes.
-
-The effect of associating a Schema URL with a `Meter` MUST be that the telemetry
-emitted using the `Meter` will be associated with the Schema URL, provided that
-the emitted data format is capable of representing such association.
-
## Meter
The meter is responsible for creating [Instruments](#instrument).
@@ -224,42 +191,10 @@ floating point numbers SHOULD be considered as identifying.
### General characteristics
-#### Instrument type conflict detection
-
-When more than one Instrument of the same `name` is created for
-identical Meters, denoted *duplicate instrument registration*, the
-implementation MUST create a valid Instrument in every case. Here,
-"valid" means an instrument that is functional and can be expected to
-export data, despite potentially creating a [semantic error in the
-data
-model](data-model.md#opentelemetry-protocol-data-model-producer-recommendations).
+#### Instrument name syntax
-It is unspecified whether or under which conditions the same or
-different Instrument instance will be returned as a result of
-duplicate instrument registration. The term *identical* applied to
-Instruments describes instances where all identifying fields are
-equal. The term *distinct* applied to Instruments describes instances
-where at least one field value is different.
-
-When more than one distinct Instrument is registered with the same
-`name` for identical Meters, the implementation SHOULD emit a warning
-to the user informing them of duplicate registration conflict(s).
-The warning helps to avoid the semantic error state described in the
-[OpenTelemetry Metrics data
-model](data-model.md#opentelemetry-protocol-data-model-producer-recommendations)
-when more than one `Metric` is written for a given instrument `name`
-and Meter identity by the same MeterProvider.
-
-#### Instrument namespace
-
-Distinct Meters MUST be treated as separate namespaces for the
-purposes of detecting [duplicate instrument registration
-conflicts](#instrument-type-conflict-detection).
-
-#### Instrument naming rule
-
-Instrument names MUST conform to the following syntax (described using the
-[Augmented Backus-Naur Form](https://tools.ietf.org/html/rfc5234)):
+The instrument name syntax is defined below using the [Augmented Backus-Naur
+Form](https://tools.ietf.org/html/rfc5234):
```abnf
instrument-name = ALPHA 0*62 ("_" / "." / "-" / ALPHA / DIGIT)
@@ -277,12 +212,9 @@ DIGIT = %x30-39 ; 0-9
#### Instrument unit
-The `unit` is an optional string provided by the author of the Instrument. It
-SHOULD be treated as an opaque string from the API and SDK (e.g. the SDK is not
-expected to validate the unit of measurement, or perform the unit conversion).
+The `unit` is an optional string provided by the author of the Instrument. The
+API SHOULD treat it as an opaque string.
-* If the `unit` is not provided or the `unit` is null, the API and SDK MUST make
- sure that the behavior is the same as an empty `unit` string.
* It MUST be case-sensitive (e.g. `kb` and `kB` are different units), ASCII
string.
* It can have a maximum length of 63 characters. The number 63 is chosen to
@@ -293,11 +225,8 @@ expected to validate the unit of measurement, or perform the unit conversion).
#### Instrument description
The `description` is an optional free-form text provided by the author of the
-instrument. It MUST be treated as an opaque string from the API and SDK.
+instrument. The API MUST treat it as an opaque string.
-* If the `description` is not provided or the `description` is null, the API and
- SDK MUST make sure that the behavior is the same as an empty `description`
- string.
* It MUST support [BMP (Unicode Plane
0)](https://en.wikipedia.org/wiki/Plane_(Unicode)#Basic_Multilingual_Plane),
which is basically only the first three bytes of UTF-8 (or `utf8mb3`).
@@ -340,11 +269,10 @@ The API to construct synchronous instruments MUST accept the following parameter
possible to structurally enforce this obligation, the API MUST be documented
in a way to communicate to users that this parameter is needed.
- The `name` needs to follow the [instrument naming
- rule](#instrument-naming-rule). The API SHOULD be documented in a way to
- communicate to users that this parameter needs to conform to the linked
- syntax. The API SHOULD NOT validate the `name`, that is left to
- implementations of the API.
+ The API SHOULD be documented in a way to communicate to users that the `name`
+ parameter needs to conform to the [instrument name
+ syntax](#instrument-name-syntax). The API SHOULD NOT validate the `name`;
+ that is left to implementations of the API.
* A `unit` of measure.
Users can provide a `unit`, but it is up to their discretion. Therefore, this
@@ -383,11 +311,10 @@ The API to construct asynchronous instruments MUST accept the following paramete
possible to structurally enforce this obligation, the API MUST be documented
in a way to communicate to users that this parameter is needed.
- The `name` needs to follow the [instrument naming
- rule](#instrument-naming-rule). The API SHOULD be documented in a way to
- communicate to users that this parameter needs to conform to the linked
- syntax. The API SHOULD NOT validate the `name`, that is left to
- implementations of the API.
+ The API SHOULD be documented in a way to communicate to users that the `name`
+ parameter needs to conform to the [instrument name
+ syntax](#instrument-name-syntax). The API SHOULD NOT validate the `name`,
+ that is left to implementations of the API.
* A `unit` of measure.
Users can provide a `unit`, but it is up to their discretion. Therefore, this
diff --git a/specification/metrics/noop.md b/specification/metrics/noop.md
new file mode 100644
index 00000000000..94e72b70325
--- /dev/null
+++ b/specification/metrics/noop.md
@@ -0,0 +1,289 @@
+
+
+# Metrics No-Op API Implementation
+
+**Status**: [Experimental](../document-status.md)
+
+
+ Table of Contents
+
+
+
+- [MeterProvider](#meterprovider)
+ * [Meter Creation](#meter-creation)
+- [Meter](#meter)
+ * [Counter Creation](#counter-creation)
+ * [UpDownCounter Creation](#updowncounter-creation)
+ * [Histogram Creation](#histogram-creation)
+ * [Asynchronous Counter Creation](#asynchronous-counter-creation)
+ * [Asynchronous UpDownCounter Creation](#asynchronous-updowncounter-creation)
+ * [Asynchronous Gauge Creation](#asynchronous-gauge-creation)
+- [Instruments](#instruments)
+ * [Counter](#counter)
+ + [Counter Add](#counter-add)
+ * [UpDownCounter](#updowncounter)
+ + [UpDownCounter Add](#updowncounter-add)
+ * [Histogram](#histogram)
+ + [Histogram Record](#histogram-record)
+ * [Asynchronous Counter](#asynchronous-counter)
+ * [Asynchronous Counter Observations](#asynchronous-counter-observations)
+ * [Asynchronous UpDownCounter](#asynchronous-updowncounter)
+ * [Asynchronous UpDownCounter Observations](#asynchronous-updowncounter-observations)
+ * [Asynchronous Gauge](#asynchronous-gauge)
+ * [Asynchronous Gauge Observations](#asynchronous-gauge-observations)
+
+
+
+
+
+Users of OpenTelemetry need a way to disable the API from actually
+performing any operations. The No-Op OpenTelemetry API implementation
+(henceforth referred to as the No-Op) provides users with this
+functionally. It implements the OpenTelemetry API so that no telemetry
+is produced and computation resources are minimized.
+
+All language implementations of OpenTelemetry MUST provide a No-Op.
+
+## MeterProvider
+
+The No-Op MUST allow the creation of multiple MeterProviders.
+
+The MeterProviders created by the No-Op needs to hold as small a memory
+footprint as possible. Therefore, all MeterProviders created MUST NOT
+hold configuration or operational state.
+
+Since all MeterProviders hold the same empty state, a No-Op MAY
+provide the same MeterProvider instances to all creation requests.
+
+The No-Op is used by OpenTelemetry users to disable OpenTelemetry
+computation overhead and eliminate OpenTelemetry related output. For
+this reason, the MeterProvider MUST NOT return a non-empty error or log
+any message for any operations it performs.
+
+All operations a MeterProvider provides MUST be safe to be run
+concurrently.
+
+### Meter Creation
+
+[New Meter instances are always created with a
+MeterProvider](./api.md#meterprovider). Therefore, MeterProviders MUST
+allow for the creation of Meters. All Meters created MUST be an instance of the
+[No-Op Meter](#meter).
+
+Since all Meters will hold the same empty state, a MeterProvider MAY
+return the same Meter instances to all creation requests.
+
+[The API specifies multiple parameters](./api.md#meterprovider) that
+need to be accepted by the creation operation. The MeterProvider MUST
+accept these parameters. However, the MeterProvider MUST NOT validate
+any argument it receives.
+
+## Meter
+
+A Meter is always created by a MeterProvider. The No-Op MUST NOT provide
+a way for a user to create a Meter other than by a No-Op MeterProvider.
+
+The Meters created by the No-Op need to hold as small a memory
+footprint as possible. Therefore, all Meters created MUST NOT hold
+configuration or operational state.
+
+The Meter MUST NOT return a non-empty error or log any message for any
+operations it performs.
+
+All operations a Meter provides MUST be safe to be run concurrently.
+
+### Counter Creation
+
+The No-Op Meter MUST allow for the creation of a [Counter
+instrument](#counter).
+
+Since all Counters hold the same empty state, a Meter MAY return the
+same Counter instance to all creation requests.
+
+[The API specifies multiple
+parameters](./api.md#synchronous-instrument-api) that need to be
+accepted by the creation operation. The Meter MUST accept these
+parameters. However, the Meter MUST NOT validate any argument it
+receives.
+
+### UpDownCounter Creation
+
+The No-Op Meter MUST allow for the creation of a [UpDownCounter
+instrument](#updowncounter).
+
+Since all UpDownCounters hold the same empty state, a Meter MAY return
+the same UpDownCounter instance to all creation requests.
+
+[The API specifies multiple
+parameters](./api.md#synchronous-instrument-api) that need to be
+accepted by the creation operation. The Meter MUST accept these
+parameters. However, the Meter MUST NOT validate any argument it
+receives.
+
+### Histogram Creation
+
+The No-Op Meter MUST allow for the creation of a [Histogram
+instrument](#histogram).
+
+Since all Histograms hold the same empty state, a Meter MAY return the
+same Histogram instance to all creation requests.
+
+[The API specifies multiple
+parameters](./api.md#synchronous-instrument-api) that need to be
+accepted by the creation operation. The Meter MUST accept these
+parameters. However, the Meter MUST NOT validate any argument it
+receives.
+
+### Asynchronous Counter Creation
+
+The No-Op Meter MUST allow for the creation of an [Asynchronous Counter
+instrument](#asynchronous-counter).
+
+Since all Asynchronous Counters hold the same empty state, a Meter MAY
+return the same Asynchronous Counter instance to all creation requests.
+
+[The API specifies multiple
+parameters](./api.md#asynchronous-instrument-api) that need to be
+accepted by the creation operation. The Meter MUST accept these
+parameters. However, the Meter MUST NOT validate any argument it
+receives and it MUST NOT hold any reference to the passed callbacks.
+
+### Asynchronous UpDownCounter Creation
+
+The No-Op Meter MUST allow for the creation of an [Asynchronous
+UpDownCounter instrument](#asynchronous-updowncounter).
+
+Since all Asynchronous UpDownCounters hold the same empty state, a Meter
+MAY return the same Asynchronous UpDownCounter instance to all creation
+requests.
+
+[The API specifies multiple
+parameters](./api.md#asynchronous-instrument-api) that need to be
+accepted by the creation operation. The Meter MUST accept these
+parameters. However, the Meter MUST NOT validate any argument it
+receives and it MUST NOT hold any reference to the passed callbacks.
+
+### Asynchronous Gauge Creation
+
+The No-Op Meter MUST allow for the creation of an [Asynchronous Gauge
+instrument](#asynchronous-gauge).
+
+Since all Asynchronous Gauges hold the same empty state, a Meter MAY
+return the same Asynchronous UpDownCounter instance to all creation
+requests.
+
+[The API specifies multiple
+parameters](./api.md#asynchronous-instrument-api) that need to be
+accepted by the creation operation. The Meter MUST accept these
+parameters. However, the Meter MUST NOT validate any argument it
+receives and it MUST NOT hold any reference to the passed callbacks.
+
+## Instruments
+
+Instruments are used to make measurements and report telemetry for a
+system. However, the No-Op is used to disable this production of
+telemetry. Because of this, all instruments the No-Op provides MUST NOT
+hold any configuration or operational state including the aggregation of
+telemetry.
+
+### Counter
+
+Counters are always created by a Meter, the No-Op MUST NOT provide a way
+for a user to create a Counter other than by a No-Op Meter.
+
+Counters MUST NOT return a non-empty error or log any message for any
+operations they perform.
+
+All operations a Counter provides MUST be safe to be run concurrently.
+
+#### Counter Add
+
+The No-Op Counter MUST provide the user an interface to Add that
+implements the [API](./api.md#add). It MUST NOT validate or retain any
+state about the arguments it receives.
+
+### UpDownCounter
+
+UpDownCounters are always created by a Meter, the No-Op MUST NOT provide
+a way for a user to create a UpDownCounter other than by a No-Op Meter.
+
+UpDownCounters MUST NOT return a non-empty error or log any message for
+any operations they perform.
+
+All operations an UpDownCounter provides MUST be safe to be run
+concurrently.
+
+#### UpDownCounter Add
+
+The No-Op UpDownCounter MUST provide the user an interface to Add that
+implements the [API](./api.md#add-1). It MUST NOT validate or retain any
+state about the arguments it receives.
+
+### Histogram
+
+Histograms are always created by a Meter, the No-Op MUST NOT provide a
+way for a user to create a Histogram other than by a No-Op Meter.
+
+Histograms MUST NOT return a non-empty error or log any message for any
+operations they perform.
+
+All operations a Histogram provides MUST be safe to be run concurrently.
+
+#### Histogram Record
+
+The No-Op Histogram MUST provide the user an interface to Record that
+implements the [API](./api.md#record). It MUST NOT validate or retain
+any state about the arguments it receives.
+
+### Asynchronous Counter
+
+Asynchronous Counters are always created by a Meter, the No-Op MUST NOT
+provide a way for a user to create a Asynchronous Counter other than by
+a No-Op Meter.
+
+Asynchronous Counters MUST NOT return a non-empty error or log any
+message for any operations they perform.
+
+All operations an Asynchronous Counter provides MUST be safe to be run
+concurrently.
+
+### Asynchronous Counter Observations
+
+The No-Op Asynchronous Counter MUST NOT validate or retain any state
+about observations made for the instrument.
+
+### Asynchronous UpDownCounter
+
+Asynchronous UpDownCounters are always created by a Meter, the No-Op
+MUST NOT provide a way for a user to create a Asynchronous UpDownCounter
+other than by a No-Op Meter.
+
+Asynchronous UpDownCounters MUST NOT return a non-empty error or log any
+message for any operations they perform.
+
+All operations an Asynchronous UpDownCounter provides MUST be safe to be
+run concurrently.
+
+### Asynchronous UpDownCounter Observations
+
+The No-Op Asynchronous UpDownCounter MUST NOT validate or retain any
+state about observations made for the instrument.
+
+### Asynchronous Gauge
+
+Asynchronous Gauges are always created by a Meter, the No-Op MUST NOT
+provide a way for a user to create a Asynchronous Gauge other than by a
+No-Op Meter.
+
+Asynchronous Gauges MUST NOT return a non-empty error or log any message
+for any operations they perform.
+
+All operations an Asynchronous Gauge provides MUST be safe to be run
+concurrently.
+
+### Asynchronous Gauge Observations
+
+The No-Op Asynchronous Gauge MUST NOT validate or retain any state about
+observations made for the instrument.
diff --git a/specification/metrics/sdk.md b/specification/metrics/sdk.md
index f9e358e1542..092c17e1969 100644
--- a/specification/metrics/sdk.md
+++ b/specification/metrics/sdk.md
@@ -30,7 +30,11 @@ linkTitle: SDK
* [Use the maximum scale for single measurements](#use-the-maximum-scale-for-single-measurements)
* [Maintain the ideal scale](#maintain-the-ideal-scale)
* [Observations inside asynchronous callbacks](#observations-inside-asynchronous-callbacks)
- * [Resolving duplicate instrument registration conflicts](#resolving-duplicate-instrument-registration-conflicts)
+- [Meter](#meter)
+ * [Duplicate instrument registration](#duplicate-instrument-registration)
+ * [Instrument name](#instrument-name)
+ * [Instrument unit](#instrument-unit)
+ * [Instrument description](#instrument-description)
- [Attribute limits](#attribute-limits)
- [Exemplar](#exemplar)
* [ExemplarFilter](#exemplarfilter)
@@ -65,6 +69,13 @@ linkTitle: SDK
+Users of OpenTelemetry need a way for instrumentation interactions with the
+OpenTelemetry API to actually produce telemetry. The OpenTelemetry SDK
+(henceforth referred to as the SDK) is an implementation of the OpenTelemetry
+API that provides users with this functionally.
+
+All language implementations of OpenTelemetry MUST provide an SDK.
+
## MeterProvider
**Status**: [Stable](../document-status.md)
@@ -88,6 +99,15 @@ the `MeterProvider` MUST be used to create
an [`InstrumentationScope`](../glossary.md#instrumentation-scope) instance which
is stored on the created `Meter`.
+In the case where an invalid `name` (null or empty string) is specified, a
+working Meter MUST be returned as a fallback rather than returning null or
+throwing an exception, its `name` SHOULD keep the original invalid value, and a
+message reporting that the specified value is invalid SHOULD be logged.
+
+When a Schema URL is passed as an argument when creating a `Meter` the emitted
+telemetry for that `Meter` MUST be associated with the Schema URL, provided
+that the emitted data format is capable of representing such association.
+
Configuration (i.e., [MetricExporters](#metricexporter),
[MetricReaders](#metricreader) and [Views](#view)) MUST be managed solely by the
`MeterProvider` and the SDK MUST provide a way to configure all options that are
@@ -560,33 +580,67 @@ execution.
The implementation MUST complete the execution of all callbacks for a
given instrument before starting a subsequent round of collection.
-### Resolving duplicate instrument registration conflicts
+## Meter
+
+Distinct meters MUST be treated as separate namespaces for the purposes of detecting
+[duplicate instrument registrations](#duplicate-instrument-registration).
+
+### Duplicate instrument registration
+
+When more than one Instrument of the same `name` is created for identical
+Meters, denoted _duplicate instrument registration_, the Meter MUST create a
+valid Instrument in every case. Here, "valid" means an instrument that is
+functional and can be expected to export data, despite potentially creating a
+[semantic error in the data
+model](data-model.md#opentelemetry-protocol-data-model-producer-recommendations).
-As [stated in the API
-specification](api.md#instrument-type-conflict-detection),
-implementations are REQUIRED to create valid instruments in case of
-duplicate instrument registration, and the [data model includes
-RECOMMENDATIONS on how to treat the consequent duplicate
-conflicting](data-model.md#opentelemetry-protocol-data-model-producer-recommendations)
-`Metric` definitions.
+It is unspecified whether or under which conditions the same or
+different Instrument instance will be returned as a result of
+duplicate instrument registration. The term _identical_ applied to
+Instruments describes instances where all [identifying
+fields](./api.md#instrument) are equal. The term _distinct_ applied
+to Instruments describes instances where at least one field value is
+different.
-The implementation MUST aggregate data from identical Instruments
-together in its export pipeline.
+Based on [the recommendations from the data
+model](data-model.md#opentelemetry-protocol-data-model-producer-recommendations),
+the SDK MUST aggregate data from identical Instruments together in its export
+pipeline.
-The implementation SHOULD assist the user in managing conflicts by
-reporting each duplicate-conflicting instrument registration that was
-not corrected by a View as follows. When a potential conflict arises
-between two non-identical `Metric` instances having the same `name`:
+When a duplicate instrument registration occurs, and it is not corrected with a
+View, a warning SHOULD be emitted. The emitted warning SHOULD include
+information for the user on how to resolve the conflict, if possible.
1. If the potential conflict involves multiple `description`
properties, setting the `description` through a configured View
SHOULD avoid the warning.
2. If the potential conflict involves instruments that can be
distinguished by a supported View selector (e.g., instrument type)
- a View recipe SHOULD be printed advising the user how to avoid the
- warning by renaming one of the conflicting instruments.
-3. Otherwise (e.g., use of multiple units), the implementation SHOULD
- pass through the data by reporting both `Metric` objects.
+ a renaming View recipe SHOULD be included in the warning.
+3. Otherwise (e.g., use of multiple units), the SDK SHOULD pass through the
+ data by reporting both `Metric` objects and emit a generic warning
+ describing the duplicate instrument registration.
+
+### Instrument name
+
+When a Meter creates an instrument, it SHOULD validate the instrument name
+conforms to the [instrument name syntax](./api.md#instrument-name-syntax)
+
+If the instrument name does not conform to this syntax, the Meter SHOULD emit
+an error notifying the user about the invalid name. It is left unspecified if a
+valid instrument is also returned.
+
+### Instrument unit
+
+When a Meter creates an instrument, it SHOULD NOT validate the instrument unit.
+If a unit is not provided or the unit is null, the Meter MUST treat it the same
+as an empty unit string.
+
+### Instrument description
+
+When a Meter creates an instrument, it SHOULD NOT validate the instrument
+description. If a description is not provided or the description is null, the
+Meter MUST treat it the same as an empty description string.
## Attribute limits
diff --git a/specification/metrics/semantic_conventions/http-metrics.md b/specification/metrics/semantic_conventions/http-metrics.md
index 3a4244f80cd..be603a309fb 100644
--- a/specification/metrics/semantic_conventions/http-metrics.md
+++ b/specification/metrics/semantic_conventions/http-metrics.md
@@ -12,61 +12,354 @@ operations. By adding HTTP attributes to metric events it allows for finely tune
**Disclaimer:** These are initial HTTP metric instruments and attributes but more may be added in the future.
-## Metric Instruments
+## HTTP Server
-The following metric instruments MUST be used to describe HTTP operations. They MUST be of the specified
-type and units.
+### Metric: `http.server.duration`
-### HTTP Server
+This metric is required.
-Below is a table of HTTP server metric instruments.
+
+| Name | Instrument Type | Unit (UCUM) | Description |
+| -------- | --------------- | ----------- | -------------- |
+| `http.server.duration` | Histogram | `ms` | Measures the duration of inbound HTTP requests. |
+
-| Name | Instrument Type ([*](README.md#instrument-types)) | Unit | Unit ([UCUM](README.md#instrument-units)) | Description |
-|-------------------------------|---------------------------------------------------|--------------|-------------------------------------------|------------------------------------------------------------------------------|
-| `http.server.duration` | Histogram | milliseconds | `ms` | measures the duration inbound HTTP requests |
-| `http.server.request.size` | Histogram | bytes | `By` | measures the size of HTTP request messages (compressed) |
-| `http.server.response.size` | Histogram | bytes | `By` | measures the size of HTTP response messages (compressed) |
-| `http.server.active_requests` | UpDownCounter | requests | `{requests}` | measures the number of concurrent HTTP requests that are currently in-flight |
+
+| Attribute | Type | Description | Examples | Requirement Level |
+|---|---|---|---|---|
+| `http.scheme` | string | The URI scheme identifying the used protocol. | `http`; `https` | Required |
+| `http.route` | string | The matched route (path template in the format used by the respective server framework). See note below [1] | `/users/:userID?`; `{controller}/{action}/{id?}` | Conditionally Required: If and only if it's available |
+| `http.flavor` | string | Kind of HTTP protocol used. [2] | `1.0` | Recommended |
+| `http.method` | string | HTTP request method. | `GET`; `POST`; `HEAD` | Required |
+| `http.status_code` | int | [HTTP response status code](https://tools.ietf.org/html/rfc7231#section-6). | `200` | Conditionally Required: If and only if one was received/sent. |
+| [`net.host.name`](../../trace/semantic_conventions/span-general.md) | string | Name of the local HTTP server that received the request. [3] | `localhost` | Required |
+| [`net.host.port`](../../trace/semantic_conventions/span-general.md) | int | Port of the local HTTP server that received the request. [4] | `8080` | Conditionally Required: [5] |
-### HTTP Client
+**[1]:** MUST NOT be populated when this is not supported by the HTTP server framework as the route attribute should have low-cardinality and the URI path can NOT substitute it.
+SHOULD include the [application root](/specification/trace/semantic_conventions/http.md#http-server-definitions) if there is one.
-Below is a table of HTTP client metric instruments.
+**[2]:** If `net.transport` is not specified, it can be assumed to be `IP.TCP` except if `http.flavor` is `QUIC`, in which case `IP.UDP` is assumed.
-| Name | Instrument Type ([*](README.md#instrument-types)) | Unit | Unit ([UCUM](README.md#instrument-units)) | Description |
-|-----------------------------|---------------------------------------------------|--------------|-------------------------------------------|----------------------------------------------------------|
-| `http.client.duration` | Histogram | milliseconds | `ms` | measures the duration outbound HTTP requests |
-| `http.client.request.size` | Histogram | bytes | `By` | measures the size of HTTP request messages (compressed) |
-| `http.client.response.size` | Histogram | bytes | `By` | measures the size of HTTP response messages (compressed) |
+**[3]:** Determined by using the first of the following that applies
-## Attributes
+- The [primary server name](/specification/trace/semantic_conventions/http.md#http-server-definitions) of the matched virtual host. MUST only
+ include host identifier.
+- Host identifier of the [request target](https://www.rfc-editor.org/rfc/rfc9110.html#target.resource)
+ if it's sent in absolute-form.
+- Host identifier of the `Host` header
-Below is a table of the attributes that SHOULD be included on `duration` and `size` metric events
-and whether they should be on server, client, or both types of HTTP metric events:
+SHOULD NOT be set if only IP address is available and capturing name would require a reverse DNS lookup.
-| Name | Type | Requirement Level | Notes and examples |
-|----------------------|---------------------|------------------------------------------------------------------------------|-----------------------------------------------------------------------------------------------------------------------------------------|
-| `http.method` | `client` & `server` | Required | The HTTP request method. E.g. `"GET"` |
-| `http.scheme` | `server` | Required | The URI scheme identifying the used protocol in lowercase: `"http"` or `"https"` |
-| `http.route` | `server` | Conditionally Required: If and only if it's available | The matched route (path template in the format used by the respective server framework). See note below [1]. E.g. `"/path/{id}/?q={}"`. |
-| `http.status_code` | `client` & `server` | Conditionally Required: if and only if one was received/sent. | [HTTP response status code][]. E.g. `200` (int) |
-| `http.flavor` | `client` & `server` | Recommended | Kind of HTTP protocol used: `"1.0"`, `"1.1"`, `"2"`, `"SPDY"` or `"QUIC"`. |
-| `net.peer.name` | `client` | Required | Host identifier of the ["URI origin"](https://www.rfc-editor.org/rfc/rfc9110.html#name-uri-origin) HTTP request is sent to. |
-| `net.peer.port` | `client` | Conditionally Required: If not default (`80` for `http`, `443` for `https`). | Port identifier of the ["URI origin"](https://www.rfc-editor.org/rfc/rfc9110.html#name-uri-origin) HTTP request is sent to. |
-| `net.sock.peer.addr` | `client` | Recommended | See [general network connection attributes](../../trace/semantic_conventions/span-general.md#general-network-connection-attributes) |
-| `net.host.name` | `server` | Required | Host of the local HTTP server that received the request. |
-| `net.host.port` | `server` | Conditionally Required: If not default (`80` for `http`, `443` for `https`). | Port of the local HTTP server that received the request. |
+**[4]:** Determined by using the first of the following that applies
-**[1]:** 'http.route' MUST NOT be populated when this is not supported by the HTTP server framework as the route attribute should have low-cardinality and the URI path can NOT substitute it.
+- Port identifier of the [primary server host](/specification/trace/semantic_conventions/http.md#http-server-definitions) of the matched virtual host.
+- Port identifier of the [request target](https://www.rfc-editor.org/rfc/rfc9110.html#target.resource)
+ if it's sent in absolute-form.
+- Port identifier of the `Host` header
-The following attributes SHOULD be included in the `http.server.active_requests` observation:
+**[5]:** If not default (`80` for `http` scheme, `443` for `https`).
-| Name | Requirement Level | Notes and examples |
-|--------------------|-------------------|----------------------------------------------------------------------------------|
-| `http.method` | Required | The HTTP request method. E.g. `"GET"` |
-| `http.scheme` | Required | The URI scheme identifying the used protocol in lowercase: `"http"` or `"https"` |
-| `http.flavor` | Recommended | Kind of HTTP protocol used: `"1.0"`, `"1.1"`, `"2"`, `"SPDY"` or `"QUIC"` |
-| `net.host.name` | Required | Host component of the ["origin"](https://www.rfc-editor.org/rfc/rfc9110.html#section-3.6) server HTTP request is sent to. |
+`http.flavor` has the following list of well-known values. If one of them applies, then the respective value MUST be used, otherwise a custom value MAY be used.
-[HTTP host header]: https://www.rfc-editor.org/rfc/rfc9110.html#name-host-and-authority
-[HTTP response status code]: https://www.rfc-editor.org/rfc/rfc9110.html#name-status-codes
-[HTTP reason phrase]: https://www.rfc-editor.org/rfc/rfc9110.html#section-15.1
+| Value | Description |
+|---|---|
+| `1.0` | HTTP/1.0 |
+| `1.1` | HTTP/1.1 |
+| `2.0` | HTTP/2 |
+| `3.0` | HTTP/3 |
+| `SPDY` | SPDY protocol. |
+| `QUIC` | QUIC protocol. |
+
+
+### Metric: `http.server.active_requests`
+
+This metric is optional.
+
+
+| Name | Instrument Type | Unit (UCUM) | Description |
+| -------- | --------------- | ----------- | -------------- |
+| `http.server.active_requests` | UpDownCounter | `{requests}` | Measures the number of concurrent HTTP requests that are currently in-flight. |
+
+
+
+| Attribute | Type | Description | Examples | Requirement Level |
+|---|---|---|---|---|
+| `http.method` | string | HTTP request method. | `GET`; `POST`; `HEAD` | Required |
+| `http.scheme` | string | The URI scheme identifying the used protocol. | `http`; `https` | Required |
+| `http.status_code` | int | [HTTP response status code](https://tools.ietf.org/html/rfc7231#section-6). | `200` | Conditionally Required: If and only if one was received/sent. |
+| [`net.host.name`](../../trace/semantic_conventions/span-general.md) | string | Name of the local HTTP server that received the request. [1] | `localhost` | Required |
+| [`net.host.port`](../../trace/semantic_conventions/span-general.md) | int | Port of the local HTTP server that received the request. [2] | `8080` | Conditionally Required: [3] |
+
+**[1]:** Determined by using the first of the following that applies
+
+- The [primary server name](/specification/trace/semantic_conventions/http.md#http-server-definitions) of the matched virtual host. MUST only
+ include host identifier.
+- Host identifier of the [request target](https://www.rfc-editor.org/rfc/rfc9110.html#target.resource)
+ if it's sent in absolute-form.
+- Host identifier of the `Host` header
+
+SHOULD NOT be set if only IP address is available and capturing name would require a reverse DNS lookup.
+
+**[2]:** Determined by using the first of the following that applies
+
+- Port identifier of the [primary server host](/specification/trace/semantic_conventions/http.md#http-server-definitions) of the matched virtual host.
+- Port identifier of the [request target](https://www.rfc-editor.org/rfc/rfc9110.html#target.resource)
+ if it's sent in absolute-form.
+- Port identifier of the `Host` header
+
+**[3]:** If not default (`80` for `http` scheme, `443` for `https`).
+
+
+### Metric: `http.server.request.size`
+
+This metric is optional.
+
+
+| Name | Instrument Type | Unit (UCUM) | Description |
+| -------- | --------------- | ----------- | -------------- |
+| `http.server.request.size` | Histogram | `By` | Measures the size of HTTP request messages (compressed). |
+
+
+
+| Attribute | Type | Description | Examples | Requirement Level |
+|---|---|---|---|---|
+| `http.scheme` | string | The URI scheme identifying the used protocol. | `http`; `https` | Required |
+| `http.route` | string | The matched route (path template in the format used by the respective server framework). See note below [1] | `/users/:userID?`; `{controller}/{action}/{id?}` | Conditionally Required: If and only if it's available |
+| `http.flavor` | string | Kind of HTTP protocol used. [2] | `1.0` | Recommended |
+| `http.method` | string | HTTP request method. | `GET`; `POST`; `HEAD` | Required |
+| `http.status_code` | int | [HTTP response status code](https://tools.ietf.org/html/rfc7231#section-6). | `200` | Conditionally Required: If and only if one was received/sent. |
+| [`net.host.name`](../../trace/semantic_conventions/span-general.md) | string | Name of the local HTTP server that received the request. [3] | `localhost` | Required |
+| [`net.host.port`](../../trace/semantic_conventions/span-general.md) | int | Port of the local HTTP server that received the request. [4] | `8080` | Conditionally Required: [5] |
+
+**[1]:** MUST NOT be populated when this is not supported by the HTTP server framework as the route attribute should have low-cardinality and the URI path can NOT substitute it.
+SHOULD include the [application root](/specification/trace/semantic_conventions/http.md#http-server-definitions) if there is one.
+
+**[2]:** If `net.transport` is not specified, it can be assumed to be `IP.TCP` except if `http.flavor` is `QUIC`, in which case `IP.UDP` is assumed.
+
+**[3]:** Determined by using the first of the following that applies
+
+- The [primary server name](/specification/trace/semantic_conventions/http.md#http-server-definitions) of the matched virtual host. MUST only
+ include host identifier.
+- Host identifier of the [request target](https://www.rfc-editor.org/rfc/rfc9110.html#target.resource)
+ if it's sent in absolute-form.
+- Host identifier of the `Host` header
+
+SHOULD NOT be set if only IP address is available and capturing name would require a reverse DNS lookup.
+
+**[4]:** Determined by using the first of the following that applies
+
+- Port identifier of the [primary server host](/specification/trace/semantic_conventions/http.md#http-server-definitions) of the matched virtual host.
+- Port identifier of the [request target](https://www.rfc-editor.org/rfc/rfc9110.html#target.resource)
+ if it's sent in absolute-form.
+- Port identifier of the `Host` header
+
+**[5]:** If not default (`80` for `http` scheme, `443` for `https`).
+
+`http.flavor` has the following list of well-known values. If one of them applies, then the respective value MUST be used, otherwise a custom value MAY be used.
+
+| Value | Description |
+|---|---|
+| `1.0` | HTTP/1.0 |
+| `1.1` | HTTP/1.1 |
+| `2.0` | HTTP/2 |
+| `3.0` | HTTP/3 |
+| `SPDY` | SPDY protocol. |
+| `QUIC` | QUIC protocol. |
+
+
+### Metric: `http.server.response.size`
+
+This metric is optional.
+
+
+| Name | Instrument Type | Unit (UCUM) | Description |
+| -------- | --------------- | ----------- | -------------- |
+| `http.server.response.size` | Histogram | `By` | Measures the size of HTTP response messages (compressed). |
+
+
+
+| Attribute | Type | Description | Examples | Requirement Level |
+|---|---|---|---|---|
+| `http.scheme` | string | The URI scheme identifying the used protocol. | `http`; `https` | Required |
+| `http.route` | string | The matched route (path template in the format used by the respective server framework). See note below [1] | `/users/:userID?`; `{controller}/{action}/{id?}` | Conditionally Required: If and only if it's available |
+| `http.flavor` | string | Kind of HTTP protocol used. [2] | `1.0` | Recommended |
+| `http.method` | string | HTTP request method. | `GET`; `POST`; `HEAD` | Required |
+| `http.status_code` | int | [HTTP response status code](https://tools.ietf.org/html/rfc7231#section-6). | `200` | Conditionally Required: If and only if one was received/sent. |
+| [`net.host.name`](../../trace/semantic_conventions/span-general.md) | string | Name of the local HTTP server that received the request. [3] | `localhost` | Required |
+| [`net.host.port`](../../trace/semantic_conventions/span-general.md) | int | Port of the local HTTP server that received the request. [4] | `8080` | Conditionally Required: [5] |
+
+**[1]:** MUST NOT be populated when this is not supported by the HTTP server framework as the route attribute should have low-cardinality and the URI path can NOT substitute it.
+SHOULD include the [application root](/specification/trace/semantic_conventions/http.md#http-server-definitions) if there is one.
+
+**[2]:** If `net.transport` is not specified, it can be assumed to be `IP.TCP` except if `http.flavor` is `QUIC`, in which case `IP.UDP` is assumed.
+
+**[3]:** Determined by using the first of the following that applies
+
+- The [primary server name](/specification/trace/semantic_conventions/http.md#http-server-definitions) of the matched virtual host. MUST only
+ include host identifier.
+- Host identifier of the [request target](https://www.rfc-editor.org/rfc/rfc9110.html#target.resource)
+ if it's sent in absolute-form.
+- Host identifier of the `Host` header
+
+SHOULD NOT be set if only IP address is available and capturing name would require a reverse DNS lookup.
+
+**[4]:** Determined by using the first of the following that applies
+
+- Port identifier of the [primary server host](/specification/trace/semantic_conventions/http.md#http-server-definitions) of the matched virtual host.
+- Port identifier of the [request target](https://www.rfc-editor.org/rfc/rfc9110.html#target.resource)
+ if it's sent in absolute-form.
+- Port identifier of the `Host` header
+
+**[5]:** If not default (`80` for `http` scheme, `443` for `https`).
+
+`http.flavor` has the following list of well-known values. If one of them applies, then the respective value MUST be used, otherwise a custom value MAY be used.
+
+| Value | Description |
+|---|---|
+| `1.0` | HTTP/1.0 |
+| `1.1` | HTTP/1.1 |
+| `2.0` | HTTP/2 |
+| `3.0` | HTTP/3 |
+| `SPDY` | SPDY protocol. |
+| `QUIC` | QUIC protocol. |
+
+
+## HTTP Client
+
+### Metric: `http.client.duration`
+
+This metric is required.
+
+
+| Name | Instrument Type | Unit (UCUM) | Description |
+| -------- | --------------- | ----------- | -------------- |
+| `http.client.duration` | Histogram | `ms` | Measures the duration of outbound HTTP requests. |
+
+
+
+| Attribute | Type | Description | Examples | Requirement Level |
+|---|---|---|---|---|
+| `http.flavor` | string | Kind of HTTP protocol used. [1] | `1.0` | Recommended |
+| `http.method` | string | HTTP request method. | `GET`; `POST`; `HEAD` | Required |
+| `http.status_code` | int | [HTTP response status code](https://tools.ietf.org/html/rfc7231#section-6). | `200` | Conditionally Required: If and only if one was received/sent. |
+| [`net.peer.name`](../../trace/semantic_conventions/span-general.md) | string | Host identifier of the ["URI origin"](https://www.rfc-editor.org/rfc/rfc9110.html#name-uri-origin) HTTP request is sent to. [2] | `example.com` | Required |
+| [`net.peer.port`](../../trace/semantic_conventions/span-general.md) | int | Port identifier of the ["URI origin"](https://www.rfc-editor.org/rfc/rfc9110.html#name-uri-origin) HTTP request is sent to. [3] | `80`; `8080`; `443` | Conditionally Required: [4] |
+| [`net.sock.peer.addr`](../../trace/semantic_conventions/span-general.md) | string | Remote socket peer address: IPv4 or IPv6 for internet protocols, path for local communication, [etc](https://man7.org/linux/man-pages/man7/address_families.7.html). | `127.0.0.1`; `/tmp/mysql.sock` | Recommended |
+
+**[1]:** If `net.transport` is not specified, it can be assumed to be `IP.TCP` except if `http.flavor` is `QUIC`, in which case `IP.UDP` is assumed.
+
+**[2]:** Determined by using the first of the following that applies
+
+- Host identifier of the [request target](https://www.rfc-editor.org/rfc/rfc9110.html#target.resource)
+ if it's sent in absolute-form
+- Host identifier of the `Host` header
+
+SHOULD NOT be set if capturing it would require an extra DNS lookup.
+
+**[3]:** When [request target](https://www.rfc-editor.org/rfc/rfc9110.html#target.resource) is absolute URI, `net.peer.name` MUST match URI port identifier, otherwise it MUST match `Host` header port identifier.
+
+**[4]:** If not default (`80` for `http` scheme, `443` for `https`).
+
+`http.flavor` has the following list of well-known values. If one of them applies, then the respective value MUST be used, otherwise a custom value MAY be used.
+
+| Value | Description |
+|---|---|
+| `1.0` | HTTP/1.0 |
+| `1.1` | HTTP/1.1 |
+| `2.0` | HTTP/2 |
+| `3.0` | HTTP/3 |
+| `SPDY` | SPDY protocol. |
+| `QUIC` | QUIC protocol. |
+
+
+### Metric: `http.client.request.size`
+
+This metric is optional.
+
+
+| Name | Instrument Type | Unit (UCUM) | Description |
+| -------- | --------------- | ----------- | -------------- |
+| `http.client.request.size` | Histogram | `By` | Measures the size of HTTP request messages (compressed). |
+
+
+
+| Attribute | Type | Description | Examples | Requirement Level |
+|---|---|---|---|---|
+| `http.flavor` | string | Kind of HTTP protocol used. [1] | `1.0` | Recommended |
+| `http.method` | string | HTTP request method. | `GET`; `POST`; `HEAD` | Required |
+| `http.status_code` | int | [HTTP response status code](https://tools.ietf.org/html/rfc7231#section-6). | `200` | Conditionally Required: If and only if one was received/sent. |
+| [`net.peer.name`](../../trace/semantic_conventions/span-general.md) | string | Host identifier of the ["URI origin"](https://www.rfc-editor.org/rfc/rfc9110.html#name-uri-origin) HTTP request is sent to. [2] | `example.com` | Required |
+| [`net.peer.port`](../../trace/semantic_conventions/span-general.md) | int | Port identifier of the ["URI origin"](https://www.rfc-editor.org/rfc/rfc9110.html#name-uri-origin) HTTP request is sent to. [3] | `80`; `8080`; `443` | Conditionally Required: [4] |
+| [`net.sock.peer.addr`](../../trace/semantic_conventions/span-general.md) | string | Remote socket peer address: IPv4 or IPv6 for internet protocols, path for local communication, [etc](https://man7.org/linux/man-pages/man7/address_families.7.html). | `127.0.0.1`; `/tmp/mysql.sock` | Recommended |
+
+**[1]:** If `net.transport` is not specified, it can be assumed to be `IP.TCP` except if `http.flavor` is `QUIC`, in which case `IP.UDP` is assumed.
+
+**[2]:** Determined by using the first of the following that applies
+
+- Host identifier of the [request target](https://www.rfc-editor.org/rfc/rfc9110.html#target.resource)
+ if it's sent in absolute-form
+- Host identifier of the `Host` header
+
+SHOULD NOT be set if capturing it would require an extra DNS lookup.
+
+**[3]:** When [request target](https://www.rfc-editor.org/rfc/rfc9110.html#target.resource) is absolute URI, `net.peer.name` MUST match URI port identifier, otherwise it MUST match `Host` header port identifier.
+
+**[4]:** If not default (`80` for `http` scheme, `443` for `https`).
+
+`http.flavor` has the following list of well-known values. If one of them applies, then the respective value MUST be used, otherwise a custom value MAY be used.
+
+| Value | Description |
+|---|---|
+| `1.0` | HTTP/1.0 |
+| `1.1` | HTTP/1.1 |
+| `2.0` | HTTP/2 |
+| `3.0` | HTTP/3 |
+| `SPDY` | SPDY protocol. |
+| `QUIC` | QUIC protocol. |
+
+
+### Metric: `http.client.response.size`
+
+This metric is optional.
+
+
+| Name | Instrument Type | Unit (UCUM) | Description |
+| -------- | --------------- | ----------- | -------------- |
+| `http.client.response.size` | Histogram | `By` | Measures the size of HTTP response messages (compressed). |
+
+
+
+| Attribute | Type | Description | Examples | Requirement Level |
+|---|---|---|---|---|
+| `http.flavor` | string | Kind of HTTP protocol used. [1] | `1.0` | Recommended |
+| `http.method` | string | HTTP request method. | `GET`; `POST`; `HEAD` | Required |
+| `http.status_code` | int | [HTTP response status code](https://tools.ietf.org/html/rfc7231#section-6). | `200` | Conditionally Required: If and only if one was received/sent. |
+| [`net.peer.name`](../../trace/semantic_conventions/span-general.md) | string | Host identifier of the ["URI origin"](https://www.rfc-editor.org/rfc/rfc9110.html#name-uri-origin) HTTP request is sent to. [2] | `example.com` | Required |
+| [`net.peer.port`](../../trace/semantic_conventions/span-general.md) | int | Port identifier of the ["URI origin"](https://www.rfc-editor.org/rfc/rfc9110.html#name-uri-origin) HTTP request is sent to. [3] | `80`; `8080`; `443` | Conditionally Required: [4] |
+| [`net.sock.peer.addr`](../../trace/semantic_conventions/span-general.md) | string | Remote socket peer address: IPv4 or IPv6 for internet protocols, path for local communication, [etc](https://man7.org/linux/man-pages/man7/address_families.7.html). | `127.0.0.1`; `/tmp/mysql.sock` | Recommended |
+
+**[1]:** If `net.transport` is not specified, it can be assumed to be `IP.TCP` except if `http.flavor` is `QUIC`, in which case `IP.UDP` is assumed.
+
+**[2]:** Determined by using the first of the following that applies
+
+- Host identifier of the [request target](https://www.rfc-editor.org/rfc/rfc9110.html#target.resource)
+ if it's sent in absolute-form
+- Host identifier of the `Host` header
+
+SHOULD NOT be set if capturing it would require an extra DNS lookup.
+
+**[3]:** When [request target](https://www.rfc-editor.org/rfc/rfc9110.html#target.resource) is absolute URI, `net.peer.name` MUST match URI port identifier, otherwise it MUST match `Host` header port identifier.
+
+**[4]:** If not default (`80` for `http` scheme, `443` for `https`).
+
+`http.flavor` has the following list of well-known values. If one of them applies, then the respective value MUST be used, otherwise a custom value MAY be used.
+
+| Value | Description |
+|---|---|
+| `1.0` | HTTP/1.0 |
+| `1.1` | HTTP/1.1 |
+| `2.0` | HTTP/2 |
+| `3.0` | HTTP/3 |
+| `SPDY` | SPDY protocol. |
+| `QUIC` | QUIC protocol. |
+
diff --git a/specification/protocol/file-exporter.md b/specification/protocol/file-exporter.md
index b300090d71b..6342967b0e0 100644
--- a/specification/protocol/file-exporter.md
+++ b/specification/protocol/file-exporter.md
@@ -53,26 +53,26 @@ Files must contain exactly one type of data: traces, metrics, or logs.
This is an example showing traces:
```json lines
-{"resourceSpans":[{"resource":{"attributes":[{"key":"resource-attr","value":{"stringValue":"resource-attr-val-1"}}]},"instrumentationLibrarySpans":[{"instrumentationLibrary":{},"spans":[{"traceId":"","spanId":"","parentSpanId":"","name":"operationA","startTimeUnixNano":"1581452772000000321","endTimeUnixNano":"1581452773000000789","droppedAttributesCount":1,"events":[{"timeUnixNano":"1581452773000000123","name":"event-with-attr","attributes":[{"key":"span-event-attr","value":{"stringValue":"span-event-attr-val"}}],"droppedAttributesCount":2},{"timeUnixNano":"1581452773000000123","name":"event","droppedAttributesCount":2}],"droppedEventsCount":1,"status":{"message":"status-cancelled","code":"2"}},{"traceId":"","spanId":"","parentSpanId":"","name":"operationB","startTimeUnixNano":"1581452772000000321","endTimeUnixNano":"1581452773000000789","links":[{"traceId":"","spanId":"","attributes":[{"key":"span-link-attr","value":{"stringValue":"span-link-attr-val"}}],"droppedAttributesCount":4},{"traceId":"","spanId":"","droppedAttributesCount":1}],"droppedLinksCount":3,"status":{}}]}]}]}
-{"resourceSpans":[{"resource":{"attributes":[{"key":"resource-attr","value":{"stringValue":"resource-attr-val-1"}}]},"instrumentationLibrarySpans":[{"instrumentationLibrary":{},"spans":[{"traceId":"","spanId":"","parentSpanId":"","name":"operationA","startTimeUnixNano":"1581452772000000321","endTimeUnixNano":"1581452773000000789","droppedAttributesCount":1,"events":[{"timeUnixNano":"1581452773000000424","name":"event-with-attr","attributes":[{"key":"span-event-attr","value":{"stringValue":"span-event-attr-val"}}],"droppedAttributesCount":2},{"timeUnixNano":"1581452773000000424","name":"event","droppedAttributesCount":2}],"droppedEventsCount":1,"status":{"message":"status-cancelled","code":"2"}},{"traceId":"","spanId":"","parentSpanId":"","name":"operationB","startTimeUnixNano":"1581452772000000343","endTimeUnixNano":"1581452773000001089","links":[{"traceId":"","spanId":"","attributes":[{"key":"span-link-attr","value":{"stringValue":"span-link-attr-val"}}],"droppedAttributesCount":3},{"traceId":"","spanId":"","droppedAttributesCount":4}],"droppedLinksCount":2,"status":{}}]}]}]}
-{"resourceSpans":[{"resource":{"attributes":[{"key":"resource-attr","value":{"stringValue":"resource-attr-val-1"}}]},"instrumentationLibrarySpans":[{"instrumentationLibrary":{},"spans":[{"traceId":"","spanId":"","parentSpanId":"","name":"operationA","startTimeUnixNano":"1581452772000000321","endTimeUnixNano":"1581452773000000789","droppedAttributesCount":1,"events":[{"timeUnixNano":"1581452773000000826","name":"event-with-attr","attributes":[{"key":"span-event-attr","value":{"stringValue":"span-event-attr-val"}}],"droppedAttributesCount":2},{"timeUnixNano":"1581452773000000826","name":"event","droppedAttributesCount":2}],"droppedEventsCount":1,"status":{"message":"status-cancelled","code":"2"}},{"traceId":"","spanId":"","parentSpanId":"","name":"operationB","startTimeUnixNano":"1581452772000200521","endTimeUnixNano":"1581452773000004789","links":[{"traceId":"","spanId":"","attributes":[{"key":"span-link-attr","value":{"stringValue":"span-link-attr-val"}}],"droppedAttributesCount":5},{"traceId":"","spanId":"","droppedAttributesCount":2}],"droppedLinksCount":3,"status":{}}]}]}]}
-{"resourceSpans":[{"resource":{"attributes":[{"key":"resource-attr","value":{"stringValue":"resource-attr-val-1"}}]},"instrumentationLibrarySpans":[{"instrumentationLibrary":{},"spans":[{"traceId":"","spanId":"","parentSpanId":"","name":"operationA","startTimeUnixNano":"1581452772000000321","endTimeUnixNano":"1581452773000000789","droppedAttributesCount":1,"events":[{"timeUnixNano":"1581452773000010925","name":"event-with-attr","attributes":[{"key":"span-event-attr","value":{"stringValue":"span-event-attr-val"}}],"droppedAttributesCount":2},{"timeUnixNano":"1581452773000010925","name":"event","droppedAttributesCount":2}],"droppedEventsCount":1,"status":{"message":"status-cancelled","code":"2"}},{"traceId":"","spanId":"","parentSpanId":"","name":"operationB","startTimeUnixNano":"1581452772000011821","endTimeUnixNano":"1581452772000012924","links":[{"traceId":"","spanId":"","attributes":[{"key":"span-link-attr","value":{"stringValue":"span-link-attr-val"}}],"droppedAttributesCount":2},{"traceId":"","spanId":"","droppedAttributesCount":2}],"droppedLinksCount":5,"status":{}}]}]}]}
+{"resourceSpans":[{"resource":{"attributes":[{"key":"resource-attr","value":{"stringValue":"resource-attr-val-1"}}]},"scopeSpans":[{"scope":{},"spans":[{"traceId":"","spanId":"","parentSpanId":"","name":"operationA","startTimeUnixNano":"1581452772000000321","endTimeUnixNano":"1581452773000000789","droppedAttributesCount":1,"events":[{"timeUnixNano":"1581452773000000123","name":"event-with-attr","attributes":[{"key":"span-event-attr","value":{"stringValue":"span-event-attr-val"}}],"droppedAttributesCount":2},{"timeUnixNano":"1581452773000000123","name":"event","droppedAttributesCount":2}],"droppedEventsCount":1,"status":{"message":"status-cancelled","code":2}},{"traceId":"","spanId":"","parentSpanId":"","name":"operationB","startTimeUnixNano":"1581452772000000321","endTimeUnixNano":"1581452773000000789","links":[{"traceId":"","spanId":"","attributes":[{"key":"span-link-attr","value":{"stringValue":"span-link-attr-val"}}],"droppedAttributesCount":4},{"traceId":"","spanId":"","droppedAttributesCount":1}],"droppedLinksCount":3,"status":{}}]}]}]}
+{"resourceSpans":[{"resource":{"attributes":[{"key":"resource-attr","value":{"stringValue":"resource-attr-val-1"}}]},"scopeSpans":[{"scope":{},"spans":[{"traceId":"","spanId":"","parentSpanId":"","name":"operationA","startTimeUnixNano":"1581452772000000321","endTimeUnixNano":"1581452773000000789","droppedAttributesCount":1,"events":[{"timeUnixNano":"1581452773000000424","name":"event-with-attr","attributes":[{"key":"span-event-attr","value":{"stringValue":"span-event-attr-val"}}],"droppedAttributesCount":2},{"timeUnixNano":"1581452773000000424","name":"event","droppedAttributesCount":2}],"droppedEventsCount":1,"status":{"message":"status-cancelled","code":2}},{"traceId":"","spanId":"","parentSpanId":"","name":"operationB","startTimeUnixNano":"1581452772000000343","endTimeUnixNano":"1581452773000001089","links":[{"traceId":"","spanId":"","attributes":[{"key":"span-link-attr","value":{"stringValue":"span-link-attr-val"}}],"droppedAttributesCount":3},{"traceId":"","spanId":"","droppedAttributesCount":4}],"droppedLinksCount":2,"status":{}}]}]}]}
+{"resourceSpans":[{"resource":{"attributes":[{"key":"resource-attr","value":{"stringValue":"resource-attr-val-1"}}]},"scopeSpans":[{"scope":{},"spans":[{"traceId":"","spanId":"","parentSpanId":"","name":"operationA","startTimeUnixNano":"1581452772000000321","endTimeUnixNano":"1581452773000000789","droppedAttributesCount":1,"events":[{"timeUnixNano":"1581452773000000826","name":"event-with-attr","attributes":[{"key":"span-event-attr","value":{"stringValue":"span-event-attr-val"}}],"droppedAttributesCount":2},{"timeUnixNano":"1581452773000000826","name":"event","droppedAttributesCount":2}],"droppedEventsCount":1,"status":{"message":"status-cancelled","code":2}},{"traceId":"","spanId":"","parentSpanId":"","name":"operationB","startTimeUnixNano":"1581452772000200521","endTimeUnixNano":"1581452773000004789","links":[{"traceId":"","spanId":"","attributes":[{"key":"span-link-attr","value":{"stringValue":"span-link-attr-val"}}],"droppedAttributesCount":5},{"traceId":"","spanId":"","droppedAttributesCount":2}],"droppedLinksCount":3,"status":{}}]}]}]}
+{"resourceSpans":[{"resource":{"attributes":[{"key":"resource-attr","value":{"stringValue":"resource-attr-val-1"}}]},"scopeSpans":[{"scope":{},"spans":[{"traceId":"","spanId":"","parentSpanId":"","name":"operationA","startTimeUnixNano":"1581452772000000321","endTimeUnixNano":"1581452773000000789","droppedAttributesCount":1,"events":[{"timeUnixNano":"1581452773000010925","name":"event-with-attr","attributes":[{"key":"span-event-attr","value":{"stringValue":"span-event-attr-val"}}],"droppedAttributesCount":2},{"timeUnixNano":"1581452773000010925","name":"event","droppedAttributesCount":2}],"droppedEventsCount":1,"status":{"message":"status-cancelled","code":2}},{"traceId":"","spanId":"","parentSpanId":"","name":"operationB","startTimeUnixNano":"1581452772000011821","endTimeUnixNano":"1581452772000012924","links":[{"traceId":"","spanId":"","attributes":[{"key":"span-link-attr","value":{"stringValue":"span-link-attr-val"}}],"droppedAttributesCount":2},{"traceId":"","spanId":"","droppedAttributesCount":2}],"droppedLinksCount":5,"status":{}}]}]}]}
```
This is an example showing metrics:
```json lines
-{"resourceMetrics":[{"resource":{"attributes":[{"key":"resource-attr","value":{"stringValue":"resource-attr-val-1"}}]},"instrumentationLibraryMetrics":[{"instrumentationLibrary":{},"metrics":[{"name":"counter-int","unit":"1","sum":{"dataPoints":[{"attributes":[{"key":"label-1","value":{"stringValue":"label-value-1"}}],"startTimeUnixNano":"1581452773000000789","timeUnixNano":"1581452773000000789","asInt":"123"},{"attributes":[{"key":"label-2","value":{"stringValue":"label-value-2"}}],"startTimeUnixNano":"1581452772000000321","timeUnixNano":"1581452773000000789","asInt":"456"}],"aggregationTemporality":"2","isMonotonic":true}},{"name":"counter-int","unit":"1","sum":{"dataPoints":[{"attributes":[{"key":"label-1","value":{"stringValue":"label-value-1"}}],"startTimeUnixNano":"1581452772000000321","timeUnixNano":"1581452773000000789","asInt":"123"},{"attributes":[{"key":"label-2","value":{"stringValue":"label-value-2"}}],"startTimeUnixNano":"1581452772000000321","timeUnixNano":"1581452773000000789","asInt":"456"}],"aggregationTemporality":"2","isMonotonic":true}}]}]}]}
-{"resourceMetrics":[{"resource":{"attributes":[{"key":"resource-attr","value":{"stringValue":"resource-attr-val-1"}}]},"instrumentationLibraryMetrics":[{"instrumentationLibrary":{},"metrics":[{"name":"counter-int","unit":"1","sum":{"dataPoints":[{"attributes":[{"key":"label-1","value":{"stringValue":"label-value-1"}}],"startTimeUnixNano":"1581452773000001459","timeUnixNano":"1581452773000001459","asInt":"120"},{"attributes":[{"key":"label-2","value":{"stringValue":"label-value-2"}}],"startTimeUnixNano":"1581452773000001459","timeUnixNano":"1581452773000001459","asInt":"456"}],"aggregationTemporality":"2","isMonotonic":true}},{"name":"counter-int","unit":"1","sum":{"dataPoints":[{"attributes":[{"key":"label-1","value":{"stringValue":"label-value-1"}}],"startTimeUnixNano":"1581452773000001459","timeUnixNano":"1581452773000001459","asInt":"123"},{"attributes":[{"key":"label-2","value":{"stringValue":"label-value-2"}}],"startTimeUnixNano":"1581452773000001459","timeUnixNano":"1581452773000001459","asInt":"456"}],"aggregationTemporality":"2","isMonotonic":true}}]}]}]}
-{"resourceMetrics":[{"resource":{"attributes":[{"key":"resource-attr","value":{"stringValue":"resource-attr-val-1"}}]},"instrumentationLibraryMetrics":[{"instrumentationLibrary":{},"metrics":[{"name":"counter-int","unit":"1","sum":{"dataPoints":[{"attributes":[{"key":"label-1","value":{"stringValue":"label-value-1"}}],"startTimeUnixNano":"1581452773000002346","timeUnixNano":"1581452773000002346","asInt":"121"},{"attributes":[{"key":"label-2","value":{"stringValue":"label-value-2"}}],"startTimeUnixNano":"1581452773000002346","timeUnixNano":"1581452773000002346","asInt":"456"}],"aggregationTemporality":"2","isMonotonic":true}},{"name":"counter-int","unit":"1","sum":{"dataPoints":[{"attributes":[{"key":"label-1","value":{"stringValue":"label-value-1"}}],"startTimeUnixNano":"1581452773000002346","timeUnixNano":"1581452773000002346","asInt":"123"},{"attributes":[{"key":"label-2","value":{"stringValue":"label-value-2"}}],"startTimeUnixNano":"1581452772000000321","timeUnixNano":"1581452773000000789","asInt":"456"}],"aggregationTemporality":"2","isMonotonic":true}}]}]}]}
-{"resourceMetrics":[{"resource":{"attributes":[{"key":"resource-attr","value":{"stringValue":"resource-attr-val-1"}}]},"instrumentationLibraryMetrics":[{"instrumentationLibrary":{},"metrics":[{"name":"counter-int","unit":"1","sum":{"dataPoints":[{"attributes":[{"key":"label-1","value":{"stringValue":"label-value-1"}}],"startTimeUnixNano":"1581452773000007891","timeUnixNano":"1581452773000007891","asInt":"125"},{"attributes":[{"key":"label-2","value":{"stringValue":"label-value-2"}}],"startTimeUnixNano":"1581452772000000321","timeUnixNano":"1581452773000007891","asInt":"456"}],"aggregationTemporality":"2","isMonotonic":true}},{"name":"counter-int","unit":"1","sum":{"dataPoints":[{"attributes":[{"key":"label-1","value":{"stringValue":"label-value-1"}}],"startTimeUnixNano":"1581452773000007891","timeUnixNano":"1581452773000007891","asInt":"123"},{"attributes":[{"key":"label-2","value":{"stringValue":"label-value-2"}}],"startTimeUnixNano":"1581452772000000321","timeUnixNano":"1581452773000007891","asInt":"456"}],"aggregationTemporality":"2","isMonotonic":true}}]}]}]}
+{"resourceMetrics":[{"resource":{"attributes":[{"key":"resource-attr","value":{"stringValue":"resource-attr-val-1"}}]},"scopeMetrics":[{"scope":{},"metrics":[{"name":"counter-int","unit":"1","sum":{"dataPoints":[{"attributes":[{"key":"label-1","value":{"stringValue":"label-value-1"}}],"startTimeUnixNano":"1581452773000000789","timeUnixNano":"1581452773000000789","asInt":"123"},{"attributes":[{"key":"label-2","value":{"stringValue":"label-value-2"}}],"startTimeUnixNano":"1581452772000000321","timeUnixNano":"1581452773000000789","asInt":"456"}],"aggregationTemporality":2,"isMonotonic":true}},{"name":"counter-int","unit":"1","sum":{"dataPoints":[{"attributes":[{"key":"label-1","value":{"stringValue":"label-value-1"}}],"startTimeUnixNano":"1581452772000000321","timeUnixNano":"1581452773000000789","asInt":"123"},{"attributes":[{"key":"label-2","value":{"stringValue":"label-value-2"}}],"startTimeUnixNano":"1581452772000000321","timeUnixNano":"1581452773000000789","asInt":"456"}],"aggregationTemporality":2,"isMonotonic":true}}]}]}]}
+{"resourceMetrics":[{"resource":{"attributes":[{"key":"resource-attr","value":{"stringValue":"resource-attr-val-1"}}]},"scopeMetrics":[{"scope":{},"metrics":[{"name":"counter-int","unit":"1","sum":{"dataPoints":[{"attributes":[{"key":"label-1","value":{"stringValue":"label-value-1"}}],"startTimeUnixNano":"1581452773000001459","timeUnixNano":"1581452773000001459","asInt":"120"},{"attributes":[{"key":"label-2","value":{"stringValue":"label-value-2"}}],"startTimeUnixNano":"1581452773000001459","timeUnixNano":"1581452773000001459","asInt":"456"}],"aggregationTemporality":2,"isMonotonic":true}},{"name":"counter-int","unit":"1","sum":{"dataPoints":[{"attributes":[{"key":"label-1","value":{"stringValue":"label-value-1"}}],"startTimeUnixNano":"1581452773000001459","timeUnixNano":"1581452773000001459","asInt":"123"},{"attributes":[{"key":"label-2","value":{"stringValue":"label-value-2"}}],"startTimeUnixNano":"1581452773000001459","timeUnixNano":"1581452773000001459","asInt":"456"}],"aggregationTemporality":2,"isMonotonic":true}}]}]}]}
+{"resourceMetrics":[{"resource":{"attributes":[{"key":"resource-attr","value":{"stringValue":"resource-attr-val-1"}}]},"scopeMetrics":[{"scope":{},"metrics":[{"name":"counter-int","unit":"1","sum":{"dataPoints":[{"attributes":[{"key":"label-1","value":{"stringValue":"label-value-1"}}],"startTimeUnixNano":"1581452773000002346","timeUnixNano":"1581452773000002346","asInt":"121"},{"attributes":[{"key":"label-2","value":{"stringValue":"label-value-2"}}],"startTimeUnixNano":"1581452773000002346","timeUnixNano":"1581452773000002346","asInt":"456"}],"aggregationTemporality":2,"isMonotonic":true}},{"name":"counter-int","unit":"1","sum":{"dataPoints":[{"attributes":[{"key":"label-1","value":{"stringValue":"label-value-1"}}],"startTimeUnixNano":"1581452773000002346","timeUnixNano":"1581452773000002346","asInt":"123"},{"attributes":[{"key":"label-2","value":{"stringValue":"label-value-2"}}],"startTimeUnixNano":"1581452772000000321","timeUnixNano":"1581452773000000789","asInt":"456"}],"aggregationTemporality":2,"isMonotonic":true}}]}]}]}
+{"resourceMetrics":[{"resource":{"attributes":[{"key":"resource-attr","value":{"stringValue":"resource-attr-val-1"}}]},"scopeMetrics":[{"scope":{},"metrics":[{"name":"counter-int","unit":"1","sum":{"dataPoints":[{"attributes":[{"key":"label-1","value":{"stringValue":"label-value-1"}}],"startTimeUnixNano":"1581452773000007891","timeUnixNano":"1581452773000007891","asInt":"125"},{"attributes":[{"key":"label-2","value":{"stringValue":"label-value-2"}}],"startTimeUnixNano":"1581452772000000321","timeUnixNano":"1581452773000007891","asInt":"456"}],"aggregationTemporality":2,"isMonotonic":true}},{"name":"counter-int","unit":"1","sum":{"dataPoints":[{"attributes":[{"key":"label-1","value":{"stringValue":"label-value-1"}}],"startTimeUnixNano":"1581452773000007891","timeUnixNano":"1581452773000007891","asInt":"123"},{"attributes":[{"key":"label-2","value":{"stringValue":"label-value-2"}}],"startTimeUnixNano":"1581452772000000321","timeUnixNano":"1581452773000007891","asInt":"456"}],"aggregationTemporality":2,"isMonotonic":true}}]}]}]}
```
This is an example showing logs:
```json lines
-{"resourceLogs":[{"resource":{"attributes":[{"key":"resource-attr","value":{"stringValue":"resource-attr-val-1"}}]},"instrumentationLibraryLogs":[{"instrumentationLibrary":{},"logs":[{"timeUnixNano":"1581452773000000789","severityNumber":9,"severityText":"Info","name":"logA","body":{"stringValue":"This is a log message"},"attributes":[{"key":"app","value":{"stringValue":"server"}},{"key":"instance_num","value":{"intValue":"1"}}],"droppedAttributesCount":1,"traceId":"08040201000000000000000000000000","spanId":"0102040800000000"},{"timeUnixNano":"1581452773000000789","severityNumber":9,"severityText":"Info","name":"logB","body":{"stringValue":"something happened"},"attributes":[{"key":"customer","value":{"stringValue":"acme"}},{"key":"env","value":{"stringValue":"dev"}}],"droppedAttributesCount":1,"traceId":"","spanId":""}]}]}]}
-{"resourceLogs":[{"resource":{"attributes":[{"key":"resource-attr","value":{"stringValue":"resource-attr-val-1"}}]},"instrumentationLibraryLogs":[{"instrumentationLibrary":{},"logs":[{"timeUnixNano":"1581452773000001233","severityNumber":9,"severityText":"Info","name":"logA","body":{"stringValue":"This is a log message"},"attributes":[{"key":"app","value":{"stringValue":"server"}},{"key":"instance_num","value":{"intValue":"1"}}],"droppedAttributesCount":1,"traceId":"08040201000000000000000000000000","spanId":"0102040800000000"},{"timeUnixNano":"1581452773000000789","severityNumber":9,"severityText":"Info","name":"logB","body":{"stringValue":"something happened"},"attributes":[{"key":"customer","value":{"stringValue":"acme"}},{"key":"env","value":{"stringValue":"dev"}}],"droppedAttributesCount":1,"traceId":"","spanId":""}]}]}]}
-{"resourceLogs":[{"resource":{"attributes":[{"key":"resource-attr","value":{"stringValue":"resource-attr-val-1"}}]},"instrumentationLibraryLogs":[{"instrumentationLibrary":{},"logs":[{"timeUnixNano":"1581452773000005443","severityNumber":9,"severityText":"Info","name":"logA","body":{"stringValue":"This is a log message"},"attributes":[{"key":"app","value":{"stringValue":"server"}},{"key":"instance_num","value":{"intValue":"1"}}],"droppedAttributesCount":1,"traceId":"08040201000000000000000000000000","spanId":"0102040800000000"},{"timeUnixNano":"1581452773000000789","severityNumber":9,"severityText":"Info","name":"logB","body":{"stringValue":"something happened"},"attributes":[{"key":"customer","value":{"stringValue":"acme"}},{"key":"env","value":{"stringValue":"dev"}}],"droppedAttributesCount":1,"traceId":"","spanId":""}]}]}]}
-{"resourceLogs":[{"resource":{"attributes":[{"key":"resource-attr","value":{"stringValue":"resource-attr-val-1"}}]},"instrumentationLibraryLogs":[{"instrumentationLibrary":{},"logs":[{"timeUnixNano":"1581452773000009875","severityNumber":9,"severityText":"Info","name":"logA","body":{"stringValue":"This is a log message"},"attributes":[{"key":"app","value":{"stringValue":"server"}},{"key":"instance_num","value":{"intValue":"1"}}],"droppedAttributesCount":1,"traceId":"08040201000000000000000000000000","spanId":"0102040800000000"},{"timeUnixNano":"1581452773000000789","severityNumber":9,"severityText":"Info","name":"logB","body":{"stringValue":"something happened"},"attributes":[{"key":"customer","value":{"stringValue":"acme"}},{"key":"env","value":{"stringValue":"dev"}}],"droppedAttributesCount":1,"traceId":"","spanId":""}]}]}]}
+{"resourceLogs":[{"resource":{"attributes":[{"key":"resource-attr","value":{"stringValue":"resource-attr-val-1"}}]},"scopeLogs":[{"scope":{},"logRecords":[{"timeUnixNano":"1581452773000000789","severityNumber":9,"severityText":"Info","name":"logA","body":{"stringValue":"This is a log message"},"attributes":[{"key":"app","value":{"stringValue":"server"}},{"key":"instance_num","value":{"intValue":"1"}}],"droppedAttributesCount":1,"traceId":"08040201000000000000000000000000","spanId":"0102040800000000"},{"timeUnixNano":"1581452773000000789","severityNumber":9,"severityText":"Info","name":"logB","body":{"stringValue":"something happened"},"attributes":[{"key":"customer","value":{"stringValue":"acme"}},{"key":"env","value":{"stringValue":"dev"}}],"droppedAttributesCount":1,"traceId":"","spanId":""}]}]}]}
+{"resourceLogs":[{"resource":{"attributes":[{"key":"resource-attr","value":{"stringValue":"resource-attr-val-1"}}]},"scopeLogs":[{"scope":{},"logRecords":[{"timeUnixNano":"1581452773000001233","severityNumber":9,"severityText":"Info","name":"logA","body":{"stringValue":"This is a log message"},"attributes":[{"key":"app","value":{"stringValue":"server"}},{"key":"instance_num","value":{"intValue":"1"}}],"droppedAttributesCount":1,"traceId":"08040201000000000000000000000000","spanId":"0102040800000000"},{"timeUnixNano":"1581452773000000789","severityNumber":9,"severityText":"Info","name":"logB","body":{"stringValue":"something happened"},"attributes":[{"key":"customer","value":{"stringValue":"acme"}},{"key":"env","value":{"stringValue":"dev"}}],"droppedAttributesCount":1,"traceId":"","spanId":""}]}]}]}
+{"resourceLogs":[{"resource":{"attributes":[{"key":"resource-attr","value":{"stringValue":"resource-attr-val-1"}}]},"scopeLogs":[{"scope":{},"logRecords":[{"timeUnixNano":"1581452773000005443","severityNumber":9,"severityText":"Info","name":"logA","body":{"stringValue":"This is a log message"},"attributes":[{"key":"app","value":{"stringValue":"server"}},{"key":"instance_num","value":{"intValue":"1"}}],"droppedAttributesCount":1,"traceId":"08040201000000000000000000000000","spanId":"0102040800000000"},{"timeUnixNano":"1581452773000000789","severityNumber":9,"severityText":"Info","name":"logB","body":{"stringValue":"something happened"},"attributes":[{"key":"customer","value":{"stringValue":"acme"}},{"key":"env","value":{"stringValue":"dev"}}],"droppedAttributesCount":1,"traceId":"","spanId":""}]}]}]}
+{"resourceLogs":[{"resource":{"attributes":[{"key":"resource-attr","value":{"stringValue":"resource-attr-val-1"}}]},"scopeLogs":[{"scope":{},"logRecords":[{"timeUnixNano":"1581452773000009875","severityNumber":9,"severityText":"Info","name":"logA","body":{"stringValue":"This is a log message"},"attributes":[{"key":"app","value":{"stringValue":"server"}},{"key":"instance_num","value":{"intValue":"1"}}],"droppedAttributesCount":1,"traceId":"08040201000000000000000000000000","spanId":"0102040800000000"},{"timeUnixNano":"1581452773000000789","severityNumber":9,"severityText":"Info","name":"logB","body":{"stringValue":"something happened"},"attributes":[{"key":"customer","value":{"stringValue":"acme"}},{"key":"env","value":{"stringValue":"dev"}}],"droppedAttributesCount":1,"traceId":"","spanId":""}]}]}]}
```
diff --git a/specification/protocol/otlp.md b/specification/protocol/otlp.md
index 4d222c4c16b..5eb25f9f8c2 100644
--- a/specification/protocol/otlp.md
+++ b/specification/protocol/otlp.md
@@ -395,7 +395,7 @@ response headers when sending binary Protobuf encoded payload.
#### JSON Protobuf Encoding
-**Status**: [Experimental](../document-status.md)
+**Status**: [Stable](../document-status.md)
JSON Protobuf encoded payloads use proto3 standard defined
[JSON Mapping](https://developers.google.com/protocol-buffers/docs/proto3#json)
diff --git a/specification/trace/sdk.md b/specification/trace/sdk.md
index 458491015bc..2e5b0dd46dc 100644
--- a/specification/trace/sdk.md
+++ b/specification/trace/sdk.md
@@ -361,18 +361,22 @@ Optional parameters:
#### JaegerRemoteSampler
-[Jaeger remote sampler](https://www.jaegertracing.io/docs/1.29/sampling/#collector-sampling-configuration) allows remotely controlling the sampling configuration for the SDKs. The sampling is typically configured at the collector and the SDKs actively poll for changes. The sampler uses `TraceIdRatioBased` or rate-limited sampler under the hood. These samplers can be configured per whole service (a.k.a default), or per span name in a given service (a.k.a per operation).
+[Jaeger remote sampler][jaeger-remote-sampling] allows remotely controlling the sampling configuration for the SDKs. The sampling configuration is periodically loaded from the backend (see [Remote Sampling API][jaeger-remote-sampling-api]), where it can be managed by operators via configuration files or even automatically calculated (see [Adaptive Sampling][jaeger-adaptive-sampling]). The sampling configuration retrieved by the remote sampler can instruct it to use either a single sampling method for the whole service (e.g., `TraceIdRatioBased`), or different methods for different endpoints (span names), for example, sample `/product` endpoint at 10%, `/admin` endpoint at 100%, and never sample `/metrics` endpoint.
The full Protobuf definition can be found at [jaegertracing/jaeger-idl/api_v2/sampling.proto](https://github.com/jaegertracing/jaeger-idl/blob/main/proto/api_v2/sampling.proto).
##### Configuration
-Following configuration properties should be available when creating the sampler:
+The following configuration properties should be available when creating the sampler:
-* endpoint - collector address with running service with sampling manager
+* endpoint - address of a service that implements the [Remote Sampling API][jaeger-remote-sampling-api], such as Jaeger Collector or OpenTelemetry Collector.
* polling interval - polling interval for getting configuration from remote
* initial sampler - initial sampler that is used before the first configuration is fetched
+[jaeger-remote-sampling]: https://www.jaegertracing.io/docs/1.41/sampling/#remote-sampling
+[jaeger-remote-sampling-api]: https://www.jaegertracing.io/docs/1.41/apis/#remote-sampling-configuration-stable
+[jaeger-adaptive-sampling]: https://www.jaegertracing.io/docs/1.41/sampling/#adaptive-sampling
+
## Span Limits
Span attributes MUST adhere to the [common rules of attribute limits](../common/README.md#attribute-limits).
@@ -412,9 +416,10 @@ public final class SpanLimits {
* `AttributePerEventCountLimit` (Default=128) - Maximum allowed attribute per span event count;
* `AttributePerLinkCountLimit` (Default=128) - Maximum allowed attribute per span link count;
-There SHOULD be a log emitted to indicate to the user that an attribute, event,
-or link was discarded due to such a limit. To prevent excessive logging, the log
-should not be emitted once per span, or per discarded attribute, event, or links.
+There SHOULD be a message printed in the SDK's log to indicate to the user
+that an attribute was discarded due to such a limit.
+To prevent excessive logging, the message MUST be printed at most once per
+span (i.e., not per discarded attribute, event, or link).
## Id Generators
diff --git a/specification/trace/sdk_exporters/zipkin.md b/specification/trace/sdk_exporters/zipkin.md
index b398c1efa31..f88688732fb 100644
--- a/specification/trace/sdk_exporters/zipkin.md
+++ b/specification/trace/sdk_exporters/zipkin.md
@@ -95,16 +95,16 @@ always available. The following table lists the possible attributes for
|---|---|---|
|1|peer.service|[OpenTelemetry adopted attribute for remote service.](../semantic_conventions/span-general.md#general-remote-service-attributes)|
|2|net.peer.name|[OpenTelemetry adopted attribute for remote hostname, or similar.](../semantic_conventions/span-general.md#general-network-connection-attributes)|
-|3|net.peer.ip & net.peer.port|[OpenTelemetry adopted attribute for remote address of the peer.](../semantic_conventions/span-general.md#general-network-connection-attributes)|
-|4|peer.hostname|Remote hostname defined in OpenTracing specification.|
-|5|peer.address|Remote address defined in OpenTracing specification.|
-|6|http.host|Commonly used HTTP host header attribute for Http Spans.|
+|3|net.sock.peer.name|[OpenTelemetry adopted attribute for remote socket hostname of the peer.](../semantic_conventions/span-general.md#general-network-connection-attributes)|
+|4|net.sock.peer.addr & net.sock.peer.port|[OpenTelemetry adopted attribute for remote socket address of the peer.](../semantic_conventions/span-general.md#general-network-connection-attributes)|
+|5|peer.hostname|Remote hostname defined in OpenTracing specification.|
+|6|peer.address|Remote address defined in OpenTracing specification.|
|7|db.name|Commonly used database name attribute for DB Spans.|
* Ranking should control the selection order. For example, `net.peer.name` (Rank
- 2) should be selected before `http.host` (Rank 6).
-* `net.peer.ip` can be used by itself as `remoteEndpoint` but should be combined
- with `net.peer.port` if it is also present.
+ 2) should be selected before `peer.address` (Rank 6).
+* `net.sock.peer.name` and `net.sock.peer.addr` can be used by themselves as `remoteEndpoint` but should be combined
+ with `net.sock.peer.port` if it is also present.
#### Zipkin -> OTLP
diff --git a/specification/trace/semantic_conventions/http.md b/specification/trace/semantic_conventions/http.md
index eaa2e5ec40f..8bfc9bbfb1d 100644
--- a/specification/trace/semantic_conventions/http.md
+++ b/specification/trace/semantic_conventions/http.md
@@ -30,16 +30,14 @@ and various HTTP versions like 1.1, 2 and SPDY.
## Name
HTTP spans MUST follow the overall [guidelines for span names](../api.md#span).
-Many REST APIs encode parameters into URI path, e.g. `/api/users/123` where `123`
-is a user id, which creates high cardinality value space not suitable for span
-names. In case of HTTP servers, these endpoints are often mapped by the server
-frameworks to more concise *HTTP routes*, e.g. `/api/users/{user_id}`, which are
-recommended as the low cardinality span names. However, the same approach usually
-does not work for HTTP client spans, especially when instrumentation is provided
-by a lower-level middleware that is not aware of the specifics of how the URIs
-are formed. Therefore, HTTP client spans SHOULD be using conservative, low
-cardinality names formed from the available parameters of an HTTP request,
-such as `"HTTP {METHOD_NAME}"`. Instrumentation MUST NOT default to using URI
+HTTP server span names SHOULD be `{http.method} {http.route}` if there is a
+(low-cardinality) `http.route` available.
+HTTP server span names SHOULD be `{http.method}` if there is no (low-cardinality)
+`http.route` available.
+HTTP client spans have no `http.route` attribute since client-side instrumentation
+is not generally aware of the "route", and therefore HTTP client spans SHOULD use
+`{http.method}`.
+Instrumentation MUST NOT default to using URI
path as span name, but MAY provide hooks to allow custom logic to override the
default span name.
@@ -64,15 +62,15 @@ The common attributes listed in this section apply to both HTTP clients and serv
the specific attributes listed in the [HTTP client](#http-client) and [HTTP server](#http-server)
sections below.
-
+
| Attribute | Type | Description | Examples | Requirement Level |
|---|---|---|---|---|
-| `http.method` | string | HTTP request method. | `GET`; `POST`; `HEAD` | Required |
| `http.status_code` | int | [HTTP response status code](https://tools.ietf.org/html/rfc7231#section-6). | `200` | Conditionally Required: If and only if one was received/sent. |
| `http.flavor` | string | Kind of HTTP protocol used. [1] | `1.0` | Recommended |
| `http.user_agent` | string | Value of the [HTTP User-Agent](https://www.rfc-editor.org/rfc/rfc9110.html#field.user-agent) header sent by the client. | `CERN-LineMode/2.15 libwww/2.17b3` | Recommended |
| `http.request_content_length` | int | The size of the request payload body in bytes. This is the number of bytes transferred excluding headers and is often, but not always, present as the [Content-Length](https://www.rfc-editor.org/rfc/rfc9110.html#field.content-length) header. For requests using transport encoding, this should be the compressed size. | `3495` | Recommended |
| `http.response_content_length` | int | The size of the response payload body in bytes. This is the number of bytes transferred excluding headers and is often, but not always, present as the [Content-Length](https://www.rfc-editor.org/rfc/rfc9110.html#field.content-length) header. For requests using transport encoding, this should be the compressed size. | `3495` | Recommended |
+| `http.method` | string | HTTP request method. | `GET`; `POST`; `HEAD` | Required |
| [`net.sock.family`](span-general.md) | string | Protocol [address family](https://man7.org/linux/man-pages/man7/address_families.7.html) which is used for communication. | `inet`; `inet6` | Conditionally Required: [2] |
| [`net.sock.peer.addr`](span-general.md) | string | Remote socket peer address: IPv4 or IPv6 for internet protocols, path for local communication, [etc](https://man7.org/linux/man-pages/man7/address_families.7.html). | `127.0.0.1`; `/tmp/mysql.sock` | Recommended |
| [`net.sock.peer.name`](span-general.md) | string | Remote socket peer name. | `proxy.example.com` | Recommended: [3] |
@@ -100,6 +98,14 @@ Following attributes MUST be provided **at span creation time** (when provided a
| `3.0` | HTTP/3 |
| `SPDY` | SPDY protocol. |
| `QUIC` | QUIC protocol. |
+
+`net.sock.family` has the following list of well-known values. If one of them applies, then the respective value MUST be used, otherwise a custom value MAY be used.
+
+| Value | Description |
+|---|---|
+| `inet` | IPv4 address |
+| `inet6` | IPv6 address |
+| `unix` | Unix domain socket path |
It is recommended to also use the general [socket-level attributes][] - `net.sock.peer.addr` when available, `net.sock.peer.name` and `net.sock.peer.port` when don't match `net.peer.name` and `net.peer.port` (if [intermediary](https://www.rfc-editor.org/rfc/rfc9110.html#section-3.7) is detected).
@@ -130,7 +136,7 @@ For an HTTP client span, `SpanKind` MUST be `Client`.
If set, `http.url` must be the originally requested URL,
before any HTTP-redirects that may happen when executing the request.
-
+
| Attribute | Type | Description | Examples | Requirement Level |
|---|---|---|---|---|
| `http.url` | string | Full HTTP request URL in the form `scheme://host[:port]/path?query[#fragment]`. Usually the fragment is not transmitted over HTTP, but if it is known, it should be included nevertheless. [1] | `https://www.foo.bar/search?q=OpenTelemetry#SemConv` | Required |
@@ -202,8 +208,8 @@ Within a single virtual host, some servers support the concepts of an **HTTP app
in a deployment of a Python application to Apache, the application would be the [PEP 3333][] conformant callable that is configured using the
[`WSGIScriptAlias` directive][modwsgisetup] of `mod_wsgi`).
-An application can be "mounted" under some **application root**
-(also know as *[context root][]* *[context prefix][]*, or *[document base][]*)
+An application can be "mounted" under an **application root**
+(also known as a *[context root][]*, *[context prefix][]*, or *[document base][]*)
which is a fixed path prefix of the URL that determines to which application a request is routed
(e.g., the server could be configured to route all requests that go to an URL path starting with `/webshop/`
at a particular virtual host
@@ -232,23 +238,23 @@ This span type represents an inbound HTTP request.
For an HTTP server span, `SpanKind` MUST be `Server`.
Given an inbound request for a route (e.g. `"/users/:userID?"`) the `name` attribute of the span SHOULD be set to this route.
-If the route does not include the application root, it SHOULD be prepended to the span name.
If the route cannot be determined, the `name` attribute MUST be set as defined in the general semantic conventions for HTTP.
-
+
| Attribute | Type | Description | Examples | Requirement Level |
|---|---|---|---|---|
-| `http.scheme` | string | The URI scheme identifying the used protocol. | `http`; `https` | Required |
-| `http.target` | string | The full request target as passed in a HTTP request line or equivalent. | `/path/12314/?q=ddds` | Required |
| `http.route` | string | The matched route (path template in the format used by the respective server framework). See note below [1] | `/users/:userID?`; `{controller}/{action}/{id?}` | Conditionally Required: If and only if it's available |
+| `http.target` | string | The full request target as passed in a HTTP request line or equivalent. | `/path/12314/?q=ddds` | Required |
| `http.client_ip` | string | The IP address of the original client behind all proxies, if known (e.g. from [X-Forwarded-For](https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/X-Forwarded-For)). [2] | `83.164.160.102` | Recommended |
+| `http.scheme` | string | The URI scheme identifying the used protocol. | `http`; `https` | Required |
| [`net.host.name`](span-general.md) | string | Name of the local HTTP server that received the request. [3] | `localhost` | Required |
| [`net.host.port`](span-general.md) | int | Port of the local HTTP server that received the request. [4] | `8080` | Conditionally Required: [5] |
| [`net.sock.host.addr`](span-general.md) | string | Local socket address. Useful in case of a multi-IP host. | `192.168.0.1` | Optional |
| [`net.sock.host.port`](span-general.md) | int | Local socket port number. | `35555` | Recommended: [6] |
-**[1]:** 'http.route' MUST NOT be populated when this is not supported by the HTTP server framework as the route attribute should have low-cardinality and the URI path can NOT substitute it.
+**[1]:** MUST NOT be populated when this is not supported by the HTTP server framework as the route attribute should have low-cardinality and the URI path can NOT substitute it.
+SHOULD include the [application root](/specification/trace/semantic_conventions/http.md#http-server-definitions) if there is one.
**[2]:** This is not necessarily the same as `net.sock.peer.addr`, which would
identify the network-level peer, which may be a proxy.
@@ -264,7 +270,7 @@ the closest proxy.
**[3]:** Determined by using the first of the following that applies
-- The [primary server name](#http-server-definitions) of the matched virtual host. MUST only
+- The [primary server name](/specification/trace/semantic_conventions/http.md#http-server-definitions) of the matched virtual host. MUST only
include host identifier.
- Host identifier of the [request target](https://www.rfc-editor.org/rfc/rfc9110.html#target.resource)
if it's sent in absolute-form.
@@ -274,7 +280,7 @@ SHOULD NOT be set if only IP address is available and capturing name would requi
**[4]:** Determined by using the first of the following that applies
-- Port identifier of the [primary server host](#http-server-definitions) of the matched virtual host.
+- Port identifier of the [primary server host](/specification/trace/semantic_conventions/http.md#http-server-definitions) of the matched virtual host.
- Port identifier of the [request target](https://www.rfc-editor.org/rfc/rfc9110.html#target.resource)
if it's sent in absolute-form.
- Port identifier of the `Host` header
@@ -285,8 +291,8 @@ SHOULD NOT be set if only IP address is available and capturing name would requi
Following attributes MUST be provided **at span creation time** (when provided at all), so they can be considered for sampling decisions:
-* `http.scheme`
* `http.target`
+* `http.scheme`
* [`net.host.name`](span-general.md)
* [`net.host.port`](span-general.md)
@@ -301,7 +307,7 @@ Note that in some cases host and port identifiers in the `Host` header might be
As an example, if a browser request for `https://example.com:8080/webshop/articles/4?s=1` is invoked from a host with IP 192.0.2.4, we may have the following Span on the client side:
-Span name: `HTTP GET`
+Span name: `GET`
| Attribute name | Value |
| :------------------- | :-------------------------------------------------------|
@@ -315,7 +321,7 @@ Span name: `HTTP GET`
The corresponding server Span may look like this:
-Span name: `/webshop/articles/:article_id`.
+Span name: `GET /webshop/articles/:article_id`.
| Attribute name | Value |
| :------------------- | :---------------------------------------------- |
diff --git a/specification/trace/semantic_conventions/instrumentation/aws-lambda.md b/specification/trace/semantic_conventions/instrumentation/aws-lambda.md
index ac2726cfebe..cad57ad0eca 100644
--- a/specification/trace/semantic_conventions/instrumentation/aws-lambda.md
+++ b/specification/trace/semantic_conventions/instrumentation/aws-lambda.md
@@ -14,7 +14,7 @@ use cases.
- [All triggers](#all-triggers)
- * [Determining the parent of a span](#determining-the-parent-of-a-span)
+ * [AWS X-Ray Environment Span Link](#aws-x-ray-environment-span-link)
- [API Gateway](#api-gateway)
- [SQS](#sqs)
* [SQS Event](#sqs-event)
@@ -61,22 +61,19 @@ and the [cloud resource conventions][cloud]. The following AWS Lambda-specific a
[faasres]: ../../../resource/semantic_conventions/faas.md (FaaS resource conventions)
[cloud]: ../../../resource/semantic_conventions/cloud.md (Cloud resource conventions)
-### Determining the parent of a span
+### AWS X-Ray Environment Span Link
-The parent of the span MUST be determined by considering both the environment and any headers or attributes
-available from the event.
-
-If the `_X_AMZN_TRACE_ID` environment variable is set, instrumentations SHOULD first try to parse an
+If the `_X_AMZN_TRACE_ID` environment variable is set, instrumentation SHOULD try to parse an
OpenTelemetry `Context` out of it using the [AWS X-Ray Propagator](../../../context/api-propagators.md). If the
-resulting `Context` is [valid](../../api.md#isvalid) and sampled, then this `Context` is the parent of the
-function span. We check if it is valid because sometimes the `_X_AMZN_TRACE_ID` environment variable contains
-an incomplete trace context which indicates X-Ray isn’t enabled. The environment variable will be set and the
+resulting `Context` is [valid](../../api.md#isvalid) then a [Span Link][] SHOULD be added to the new Span's
+[start options](../../api.md#specifying-links) with an associated attribute of `source=x-ray-env` to
+indicate the source of the linked span.
+Instrumentation MUST check if the context is valid before using it because the `_X_AMZN_TRACE_ID` environment variable can
+contain an incomplete trace context which indicates X-Ray isn’t enabled. The environment variable will be set and the
`Context` will be valid and sampled only if AWS X-Ray has been enabled for the Lambda function. A user can
-disable AWS X-Ray for the function if X-Ray propagation is not desired.
+disable AWS X-Ray for the function if the X-Ray Span Link is not desired.
-Otherwise, when X-Ray propagation fails, the user's configured propagators SHOULD be applied to the HTTP
-headers of the request to extract a `Context`. For example, API Gateway proxy requests can be configured to
-send HTTP headers to a Lambda function using [a body mapping template](https://docs.aws.amazon.com/apigateway/latest/developerguide/apigateway-override-request-response-parameters.html).
+[Span Link]: https://opentelemetry.io/docs/concepts/signals/traces/#span-links
## API Gateway