NVIDIA DeepStream SDK API Reference

9.2 Release
includes/opentelemetry/trace/propagation/http_trace_context.h
Go to the documentation of this file.
1 // Copyright The OpenTelemetry Authors
2 // SPDX-License-Identifier: Apache-2.0
3 
4 #pragma once
5 
6 #include <array>
7 
8 #include "detail/hex.h"
9 #include "detail/string.h"
10 #include "opentelemetry/context/propagation/text_map_propagator.h"
11 #include "opentelemetry/nostd/function_ref.h"
12 #include "opentelemetry/nostd/shared_ptr.h"
13 #include "opentelemetry/nostd/span.h"
14 #include "opentelemetry/nostd/string_view.h"
15 #include "opentelemetry/trace/context.h"
16 #include "opentelemetry/trace/default_span.h"
17 #include "opentelemetry/version.h"
18 
20 namespace trace
21 {
22 namespace propagation
23 {
24 static const nostd::string_view kTraceParent = "traceparent";
25 static const nostd::string_view kTraceState = "tracestate";
26 static const size_t kVersionSize = 2;
27 static const size_t kTraceIdSize = 32;
28 static const size_t kSpanIdSize = 16;
29 static const size_t kTraceFlagsSize = 2;
30 static const size_t kTraceParentSize = 55;
31 
32 // The HttpTraceContext provides methods to extract and inject
33 // context into headers of HTTP requests with traces.
34 // Example:
35 // HttpTraceContext().Inject(carrier, context);
36 // HttpTraceContext().Extract(carrier, context);
37 
39 {
40 public:
42  const context::Context &context) noexcept override
43  {
44  SpanContext span_context = trace::GetSpan(context)->GetContext();
45  if (!span_context.IsValid())
46  {
47  return;
48  }
49  InjectImpl(carrier, span_context);
50  }
51 
53  context::Context &context) noexcept override
54  {
55  SpanContext span_context = ExtractImpl(carrier);
56  nostd::shared_ptr<Span> sp{new DefaultSpan(span_context)};
57  if (span_context.IsValid())
58  {
59  return trace::SetSpan(context, sp);
60  }
61  else
62  {
63  return context;
64  }
65  }
66 
68  {
69  uint8_t buf[kTraceIdSize / 2];
70  detail::HexToBinary(trace_id, buf, sizeof(buf));
71  return TraceId(buf);
72  }
73 
75  {
76  uint8_t buf[kSpanIdSize / 2];
77  detail::HexToBinary(span_id, buf, sizeof(buf));
78  return SpanId(buf);
79  }
80 
82  {
83  uint8_t flags;
84  detail::HexToBinary(trace_flags, &flags, sizeof(flags));
85  return TraceFlags(flags);
86  }
87 
88 private:
89  static constexpr uint8_t kInvalidVersion = 0xFF;
90  static constexpr uint8_t kDefaultAssumedVersion = 0x00;
91 
92  static void InjectImpl(context::propagation::TextMapCarrier &carrier,
93  const SpanContext &span_context)
94  {
95  char trace_parent[kTraceParentSize];
96  trace_parent[0] = '0';
97  trace_parent[1] = '0';
98  trace_parent[2] = '-';
99  span_context.trace_id().ToLowerBase16(
101  trace_parent[kTraceIdSize + 3] = '-';
102  span_context.span_id().ToLowerBase16(
104  trace_parent[kTraceIdSize + kSpanIdSize + 4] = '-';
105  span_context.trace_flags().ToLowerBase16(
106  nostd::span<char, 2>{&trace_parent[kTraceIdSize + kSpanIdSize + 5], 2});
107 
108  carrier.Set(kTraceParent, nostd::string_view(trace_parent, sizeof(trace_parent)));
109  const auto trace_state = span_context.trace_state()->ToHeader();
110  if (!trace_state.empty())
111  {
112  carrier.Set(kTraceState, trace_state);
113  }
114  }
115 
116  static SpanContext ExtractContextFromTraceHeaders(nostd::string_view trace_parent,
117  nostd::string_view trace_state)
118  {
119  std::array<nostd::string_view, 4> fields{};
120  if (detail::SplitString(trace_parent, '-', fields.data(), 4) != 4)
121  {
122  return SpanContext::GetInvalid();
123  }
124 
125  nostd::string_view version_hex = fields[0];
126  nostd::string_view trace_id_hex = fields[1];
127  nostd::string_view span_id_hex = fields[2];
128  nostd::string_view trace_flags_hex = fields[3];
129 
130  if (version_hex.size() != kVersionSize || trace_id_hex.size() != kTraceIdSize ||
131  span_id_hex.size() != kSpanIdSize || trace_flags_hex.size() != kTraceFlagsSize)
132  {
133  return SpanContext::GetInvalid();
134  }
135 
136  if (!detail::IsValidHex(version_hex) || !detail::IsValidHex(trace_id_hex) ||
137  !detail::IsValidHex(span_id_hex) || !detail::IsValidHex(trace_flags_hex))
138  {
139  return SpanContext::GetInvalid();
140  }
141 
142  // hex is valid, convert it to binary
143  uint8_t version_binary;
144  detail::HexToBinary(version_hex, &version_binary, sizeof(version_binary));
145  if (version_binary == kInvalidVersion)
146  {
147  // invalid version encountered
148  return SpanContext::GetInvalid();
149  }
150 
151  // See https://www.w3.org/TR/trace-context/#versioning-of-traceparent
152  if (version_binary > kDefaultAssumedVersion)
153  {
154  // higher than default version detected
155  if (trace_parent.size() < kTraceParentSize)
156  {
157  return SpanContext::GetInvalid();
158  }
159  }
160  else
161  {
162  // version is either lower or same as the default version
163  if (trace_parent.size() != kTraceParentSize)
164  {
165  return SpanContext::GetInvalid();
166  }
167  }
168 
169  TraceId trace_id = TraceIdFromHex(trace_id_hex);
170  SpanId span_id = SpanIdFromHex(span_id_hex);
171 
172  if (!trace_id.IsValid() || !span_id.IsValid())
173  {
174  return SpanContext::GetInvalid();
175  }
176 
177  return SpanContext(trace_id, span_id, TraceFlagsFromHex(trace_flags_hex), true,
178  trace::TraceState::FromHeader(trace_state));
179  }
180 
181  static SpanContext ExtractImpl(const context::propagation::TextMapCarrier &carrier)
182  {
183  // Get trace_parent after trimming the leading and trailing whitespaces
185  nostd::string_view trace_state = carrier.Get(kTraceState);
186  if (trace_parent == "")
187  {
188  return SpanContext::GetInvalid();
189  }
190 
191  return ExtractContextFromTraceHeaders(trace_parent, trace_state);
192  }
193 
194  bool Fields(nostd::function_ref<bool(nostd::string_view)> callback) const noexcept override
195  {
196  return (callback(kTraceParent) && callback(kTraceState));
197  }
198 };
199 } // namespace propagation
200 } // namespace trace
trace::TraceId
Definition: includes/opentelemetry/trace/trace_id.h:19
trace::SetSpan
context::Context SetSpan(context::Context &context, const nostd::shared_ptr< Span > &span) noexcept
Definition: includes/opentelemetry/trace/context.h:37
trace::propagation::HttpTraceContext::TraceFlagsFromHex
static TraceFlags TraceFlagsFromHex(nostd::string_view trace_flags)
Definition: includes/opentelemetry/trace/propagation/http_trace_context.h:81
nostd::function_ref
Definition: includes/opentelemetry/nostd/function_ref.h:17
trace
Definition: includes/opentelemetry/context/context_value.h:18
trace::SpanContext::trace_id
const trace::TraceId & trace_id() const noexcept
Definition: includes/opentelemetry/trace/span_context.h:63
trace::propagation::HttpTraceContext::Inject
void Inject(context::propagation::TextMapCarrier &carrier, const context::Context &context) noexcept override
Definition: includes/opentelemetry/trace/propagation/http_trace_context.h:41
trace::SpanContext
Definition: includes/opentelemetry/trace/span_context.h:24
trace::TraceId::ToLowerBase16
void ToLowerBase16(nostd::span< char, 2 *kSize > buffer) const noexcept
Definition: includes/opentelemetry/trace/trace_id.h:35
trace::propagation::kTraceIdSize
static const size_t kTraceIdSize
Definition: includes/opentelemetry/trace/propagation/http_trace_context.h:27
trace::DefaultSpan
DefaultSpan provides a non-operational Span that propagates the tracer context by wrapping it inside ...
Definition: includes/opentelemetry/trace/default_span.h:21
nostd::shared_ptr
Provide a type-erased version of std::shared_ptr that has ABI stability.
Definition: includes/opentelemetry/nostd/shared_ptr.h:28
trace::propagation::HttpTraceContext::SpanIdFromHex
static SpanId SpanIdFromHex(nostd::string_view span_id)
Definition: includes/opentelemetry/trace/propagation/http_trace_context.h:74
OPENTELEMETRY_BEGIN_NAMESPACE
#define OPENTELEMETRY_BEGIN_NAMESPACE
Definition: includes/opentelemetry/version.h:21
trace::propagation::kSpanIdSize
static const size_t kSpanIdSize
Definition: includes/opentelemetry/trace/propagation/http_trace_context.h:28
nostd::span
Back port of std::span.
Definition: includes/opentelemetry/nostd/span.h:51
trace::propagation::detail::SplitString
size_t SplitString(nostd::string_view s, char separator, nostd::string_view *results, size_t count)
Splits a string by separator, up to given buffer count words.
Definition: includes/opentelemetry/trace/propagation/detail/string.h:23
trace::propagation::kTraceFlagsSize
static const size_t kTraceFlagsSize
Definition: includes/opentelemetry/trace/propagation/http_trace_context.h:29
context
Definition: includes/opentelemetry/context/context.h:16
context::propagation::TextMapPropagator
Definition: includes/opentelemetry/context/propagation/text_map_propagator.h:42
trace::propagation::HttpTraceContext::Extract
context::Context Extract(const context::propagation::TextMapCarrier &carrier, context::Context &context) noexcept override
Definition: includes/opentelemetry/trace/propagation/http_trace_context.h:52
trace::propagation::kTraceState
static const nostd::string_view kTraceState
Definition: includes/opentelemetry/trace/propagation/http_trace_context.h:25
trace::SpanContext::trace_state
const nostd::shared_ptr< trace::TraceState > & trace_state() const noexcept
Definition: includes/opentelemetry/trace/span_context.h:69
context::propagation::TextMapCarrier::Set
virtual void Set(nostd::string_view key, nostd::string_view value) noexcept=0
trace::GetSpan
nostd::shared_ptr< Span > GetSpan(const context::Context &context) noexcept
Definition: includes/opentelemetry/trace/context.h:16
OPENTELEMETRY_END_NAMESPACE
#define OPENTELEMETRY_END_NAMESPACE
Definition: includes/opentelemetry/version.h:24
nostd::string_view::size
size_type size() const noexcept
Definition: includes/opentelemetry/nostd/string_view.h:62
trace::SpanContext::trace_flags
const trace::TraceFlags & trace_flags() const noexcept
Definition: includes/opentelemetry/trace/span_context.h:60
trace::propagation::HttpTraceContext
Definition: includes/opentelemetry/trace/propagation/http_trace_context.h:38
trace::propagation::HttpTraceContext::TraceIdFromHex
static TraceId TraceIdFromHex(nostd::string_view trace_id)
Definition: includes/opentelemetry/trace/propagation/http_trace_context.h:67
trace::propagation::detail::IsValidHex
bool IsValidHex(nostd::string_view s)
Definition: includes/opentelemetry/trace/propagation/detail/hex.h:42
trace::TraceFlags::ToLowerBase16
void ToLowerBase16(nostd::span< char, 2 > buffer) const noexcept
Definition: includes/opentelemetry/trace/trace_flags.h:45
trace::TraceState::FromHeader
static nostd::shared_ptr< TraceState > FromHeader(nostd::string_view header) noexcept
Returns shared_ptr to a newly created TraceState parsed from the header provided.
Definition: includes/opentelemetry/trace/trace_state.h:55
trace::SpanId::ToLowerBase16
void ToLowerBase16(nostd::span< char, 2 *kSize > buffer) const noexcept
Definition: includes/opentelemetry/trace/span_id.h:29
trace::propagation::kTraceParent
static const nostd::string_view kTraceParent
Definition: includes/opentelemetry/trace/propagation/http_trace_context.h:24
trace::SpanContext::IsValid
bool IsValid() const noexcept
Definition: includes/opentelemetry/trace/span_context.h:57
trace::TraceState::ToHeader
std::string ToHeader() const noexcept
Creates a w3c tracestate header from TraceState object.
Definition: includes/opentelemetry/trace/trace_state.h:92
common::StringUtil::Trim
static nostd::string_view Trim(nostd::string_view str, size_t left, size_t right) noexcept
Definition: includes/opentelemetry/common/string_util.h:18
trace::propagation::kVersionSize
static const size_t kVersionSize
Definition: includes/opentelemetry/trace/propagation/http_trace_context.h:26
trace::SpanContext::span_id
const trace::SpanId & span_id() const noexcept
Definition: includes/opentelemetry/trace/span_context.h:66
context::Context
Definition: includes/opentelemetry/context/context.h:23
context::propagation::TextMapCarrier
Definition: includes/opentelemetry/context/propagation/text_map_propagator.h:18
context::propagation::TextMapCarrier::Get
virtual nostd::string_view Get(nostd::string_view key) const noexcept=0
trace::SpanId
Definition: includes/opentelemetry/trace/span_id.h:16
trace::propagation::detail::HexToBinary
bool HexToBinary(nostd::string_view hex, uint8_t *buffer, size_t buffer_size)
Converts a hexadecimal to binary format if the hex string will fit the buffer.
Definition: includes/opentelemetry/trace/propagation/detail/hex.h:51
trace::propagation::kTraceParentSize
static const size_t kTraceParentSize
Definition: includes/opentelemetry/trace/propagation/http_trace_context.h:30
trace::TraceFlags
Definition: includes/opentelemetry/trace/trace_flags.h:18
trace::SpanContext::GetInvalid
static SpanContext GetInvalid() noexcept
Definition: includes/opentelemetry/trace/span_context.h:86
nostd::string_view
Back port of std::string_view to work with pre-cpp-17 compilers.
Definition: includes/opentelemetry/nostd/string_view.h:37