Skip to content

Commit

Permalink
Added random trace id flag to traceresponse header (w3c#533)
Browse files Browse the repository at this point in the history
* Added random trace id flag to traceresponse header

* In traceresponse header, include references to trace-id and random-flag from traceparent header.

* Fixing the format of the links.

* Apply suggestions from code review

Co-authored-by: Bastian Krol <[email protected]>

* Added info on when random-trace-id flag can be useful in the response header.

---------

Co-authored-by: Bastian Krol <[email protected]>
  • Loading branch information
kalyanaj and basti1302 authored May 19, 2023
1 parent a4e20e7 commit 0b83a23
Show file tree
Hide file tree
Showing 2 changed files with 27 additions and 26 deletions.
2 changes: 1 addition & 1 deletion spec/20-http_request_header_format.md
Original file line number Diff line number Diff line change
Expand Up @@ -108,7 +108,7 @@ Implementers SHOULD use a `trace-id` generation method which randomly (or pseudo
If the right-most 7 bytes are randomly (or pseudo-randomly) generated, the corresponding [random trace id flag](#random-trace-id-flag) SHOULD be set.
For more details, see [considerations for trace-id field generation](#considerations-for-trace-id-field-generation).

If the `trace-id` value is invalid (for example if it contains non-allowed characters or all zeros), vendors MUST ignore the `traceparent`.
If the `trace-id` value is invalid (for example if it contains non-allowed characters or all zeros), vendors MUST ignore the entire header.

#### parent-id

Expand Down
51 changes: 26 additions & 25 deletions spec/21-http_response_header_format.md
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,6 @@ In order to increase interoperability across multiple protocols and encourage su

### traceresponse Header Field Values


This section uses the Augmented Backus-Naur Form (ABNF) notation of [[!RFC5234]], including the DIGIT rule from that document. The `DIGIT` rule defines a single number character `0`-`9`.

``` abnf
Expand All @@ -47,47 +46,37 @@ The following `version-format` definition is used for version `00`.
version-format = trace-id "-" child-id "-" trace-flags
trace-id = 32HEXDIGLC ; 16 bytes array identifier. All zeroes forbidden
child-id = 16HEXDIGLC ; 8 bytes array identifier. All zeroes forbidden
trace-flags = 2HEXDIGLC ; 8 bit flags. Currently, only one bit is used. See below for details
trace-flags = 2HEXDIGLC ; 8 bit flags. See below for details
```

#### trace-id

This is the ID of the whole trace forest and is used to uniquely identify a <a href="#dfn-distributed-traces">distributed trace</a> through a system. It is represented as a 16-byte array, for example, `4bf92f3577b34da6a3ce929d0e0e4736`. All bytes as zero (`00000000000000000000000000000000`) is considered an invalid value.

If the `trace-id` value is invalid (for example if it contains non-allowed characters or all zeros), tracing systems MUST ignore the `traceresponse`.
The format and requirements for this are the same as those of the trace-id field in the `traceparent` request header.

See [considerations for trace-id field generation](#considerations-for-trace-id-field-generation) for recommendations on how to operate with `trace-id`.
For details, see the trace-id section under [traceparent Header Field Values](#traceparent-Header-Field-Values).

#### child-id

This is the ID of the operation of the callee (in some systems known as the span id) and is used to uniquely identify an operation within a trace. It is represented as an 8-byte array, for example, `00f067aa0ba902b7`. All bytes as zero (`0000000000000000`) is considered an invalid value.
This is the ID of the operation of the callee (in some tracing systems, this is known as the `span-id`, where a `span` is the execution of a client request) and is used to uniquely identify an operation within a trace. It is represented as an 8-byte array, for example, `00f067aa0ba902b7`. All bytes as zero (`0000000000000000`) is considered an invalid value.

Vendors MUST ignore the `traceresponse` header when the `child-id` is invalid (for example, if it contains non-lowercase hex characters).

#### trace-flags

An <a data-cite='!BIT-FIELD#firstHeading'>8-bit field</a> that provides additional information about how the callee handled the trace such as sampling, trace level, etc. These flags are recommendations given by the callee rather than strict rules to follow for three reasons:
Similar to the `trace-flags` field in the `traceparent` request header, this is a hex-encoded <a data-cite='!BIT-FIELD#firstHeading'>8-bit field</a> that provides information about how a callee handled the trace. The same requirement to properly mask the bit field value when interpreting it applies here as well.

The current version of this specification (`00`) supports only two flags: `sampled` and `random-trace-id`.

These flags are recommendations given by a callee rather than strict rules to follow for three reasons:

1. An untrusted callee may be able to abuse a tracing system by setting these flags maliciously.
2. A callee may have a bug which causes the tracing system to have a problem.
3. Different load between calling and called services might force one or more participants to discard part or all of a trace.

You can find more in the section [Security considerations](#security-considerations) of this specification.

Like other fields, `trace-flags` is hex-encoded. For example, all `8` flags set would be `ff` and no flags set would be `00`.

As this is a bit field, you cannot interpret flags by decoding the hex value and looking at the resulting number. For example, a flag `00000001` could be encoded as `01` in hex, or `09` in hex if the flag `00001000` was also present (`00001001` is `09`). A common mistake in bit fields is forgetting to mask when interpreting flags.

Here is an example of properly handling trace flags:

``` java
static final byte FLAG_SAMPLED = 1; // 00000001
...
boolean sampled = (traceFlags & FLAG_SAMPLED) == FLAG_SAMPLED;
```

##### Sampled flag

The current version of this specification (`00`) only supports a single flag called `sampled`.

When set, the least significant bit (right-most), denotes that the callee may have recorded trace data. When unset, the callee did not record trace data out-of-band.

The `sampled` flag provides interoperability between tracing systems. It allows tracing systems to communicate recording decisions and enable a better experience for the customer. For example, when a SaaS load balancer service participates in a <a>distributed trace</a>, this service has no knowledge of the tracing system used by its callee. This service may produce records of incoming requests for monitoring or troubleshooting purposes. The `sampled` flag can be used to ensure that information about requests that were marked for recording by the callee will also be recorded by the SaaS load balancer service upstream so that the callee can troubleshoot the behavior of every recorded request.
Expand All @@ -96,8 +85,8 @@ The `sampled` flag has no restrictions.

The following are a set of suggestions that tracing systems SHOULD use to increase interoperability.

- If a component made definitive recording decision - this decision SHOULD be reflected in the `sampled` flag.
- If a component needs to make a recording decision - it SHOULD respect the `sampled` flag value.
- If a component made a definitive recording decision, this decision SHOULD be reflected in the `sampled` flag.
- If a component needs to make a recording decision, it SHOULD respect the `sampled` flag value.
[Security considerations](#security-considerations) SHOULD be applied to protect from abusive or malicious use of this flag.
- If a component deferred or delayed the decision and only a subset of telemetry will be recorded, the `sampled` flag from the incoming `traceparent` header should be used if it is available. It should be set to `0` as the default option when the trace is initiated by this component.
- If a component receives a `0` for the `sampled` flag on an incoming request, it may still decide to record a trace. In this case it SHOULD return a `sampled` flag `1` on the response so that the caller can update its sampling decision if required.
Expand All @@ -107,6 +96,18 @@ There are two additional options that tracing systems MAY follow:
- A component that makes a deferred or delayed recording decision may communicate the priority of a recording by setting `sampled` flag to `1` for a subset of requests.
- A component may also fall back to probability sampling and set the `sampled` flag to `1` for the subset of requests.

##### Random Trace ID Flag

The second least significant bit of the trace-flags field denotes the random-trace-id flag.

If a trace was started by a downstream participant and it responds with the `traceresponse` HTTP header, an upstream participant can use this flag to determine if the `trace-id` was generated as per
the specification for this flag.

The format and requirements for this are the same as those of the random-trace-id flag in the trace-flags field in the `traceparent` request header.

For details, see the trace-flags section under [traceparent Header Field Values](#traceparent-Header-Field-Values).


##### Other Flags

The behavior of other flags, such as (`00000100`) is not defined and is reserved for future use. tracing systems MUST set those to zero.
The behavior of other flags, such as (`00000100`) is not defined and is reserved for future use. Tracing systems MUST set those to zero.

0 comments on commit 0b83a23

Please sign in to comment.