From 313d0825fda891d8ae8e7209100da7e98121a2ee Mon Sep 17 00:00:00 2001 From: David Goffredo Date: Wed, 14 Dec 2022 10:25:50 -0500 Subject: [PATCH 01/11] fix typo in circleci readme --- .circleci/README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.circleci/README.md b/.circleci/README.md index cc703ab9..85c7e797 100644 --- a/.circleci/README.md +++ b/.circleci/README.md @@ -13,7 +13,7 @@ The following jobs are defined: - Based on the `toolchain` parameter, the build will use either g++ or clang++. - Based on the `sanitize` parameter, the build might use [AddressSanitizer and - MemorySanitizer][3]. + UndefinedBehaviorSanitizer][3]. [1]: https://bazel.build/ [2]: https://cmake.org/ From 39a6dd07bf193d301ba00b15e178f3429b593a2e Mon Sep 17 00:00:00 2001 From: David Goffredo Date: Wed, 14 Dec 2022 11:45:12 -0500 Subject: [PATCH 02/11] support the "b3multi" and "none" propagation styles --- src/datadog/propagation_styles.cpp | 3 +++ src/datadog/propagation_styles.h | 6 ++++++ src/datadog/trace_segment.cpp | 8 ++++++- src/datadog/tracer.cpp | 29 +++++++++++++++++++++++-- src/datadog/tracer_config.cpp | 10 ++++++--- test/span.cpp | 22 +++++++++++++++++++ test/tracer.cpp | 25 ++++++++++++++++++++++ test/tracer_config.cpp | 34 +++++++++++++++++++----------- 8 files changed, 119 insertions(+), 18 deletions(-) diff --git a/src/datadog/propagation_styles.cpp b/src/datadog/propagation_styles.cpp index 55ce6b50..eb3094d9 100644 --- a/src/datadog/propagation_styles.cpp +++ b/src/datadog/propagation_styles.cpp @@ -16,6 +16,9 @@ nlohmann::json to_json(const PropagationStyles& styles) { if (styles.b3) { selected_names.emplace_back("B3"); } + if (styles.none) { + selected_names.emplace_back("none"); + } return selected_names; } diff --git a/src/datadog/propagation_styles.h b/src/datadog/propagation_styles.h index ce0e4fb1..78e6378f 100644 --- a/src/datadog/propagation_styles.h +++ b/src/datadog/propagation_styles.h @@ -11,8 +11,14 @@ namespace datadog { namespace tracing { struct PropagationStyles { + // Datadog headers, e.g. X-Datadog-Trace-ID bool datadog = true; + // B3 multi-header style, e.g. X-B3-TraceID bool b3 = false; + // The absence of propagation. If this is the only style set, then + // propagation is disabled in the relevant direction (extraction or + // injection). + bool none = false; }; nlohmann::json to_json(const PropagationStyles&); diff --git a/src/datadog/trace_segment.cpp b/src/datadog/trace_segment.cpp index 9253ae19..5f57c8af 100644 --- a/src/datadog/trace_segment.cpp +++ b/src/datadog/trace_segment.cpp @@ -221,8 +221,14 @@ void TraceSegment::inject(DictWriter& writer, const SpanData& span) { encoded_trace_tags = encode_tags(trace_tags_); } - // Origin and trace tag headers are always propagated. + // Origin and trace tag headers are always propagated, unless the only + // injection style is "none". // Other headers depend on the injection styles. + if (injection_styles_.none && !injection_styles_.datadog && + !injection_styles_.b3) { + return; + } + if (origin_) { writer.set("x-datadog-origin", *origin_); } diff --git a/src/datadog/tracer.cpp b/src/datadog/tracer.cpp index 79f43672..eaec1e6d 100644 --- a/src/datadog/tracer.cpp +++ b/src/datadog/tracer.cpp @@ -174,6 +174,21 @@ bool operator!=(const ExtractedData& left, const ExtractedData& right) { left.sampling_priority != right.sampling_priority; } +nlohmann::json to_json(const ExtractedData& data) { + auto result = nlohmann::json::object({}); +#define ADD_FIELD(FIELD) \ + if (data.FIELD) { \ + result[#FIELD] = *data.FIELD; \ + } + ADD_FIELD(trace_id) + ADD_FIELD(parent_id) + ADD_FIELD(origin) + ADD_FIELD(trace_tags) + ADD_FIELD(sampling_priority) +#undef ADD_FIELD + return result; +} + Expected extract_data(ExtractionPolicy& extract, const DictReader& reader) { ExtractedData extracted_data; @@ -325,13 +340,24 @@ Expected Tracer::extract_span(const DictReader& reader, std::string message; message += "B3 extracted different data than did "; message += extracted_by; - // TODO: diagnose difference + message += ". B3 extracted "; + message += to_json(*data).dump(); + message += " while previously "; + message += extracted_by; + message += " extracted "; + message += to_json(*extracted_data).dump(); + message += '.'; return Error{Error::INCONSISTENT_EXTRACTION_STYLES, std::move(message)}; } extracted_data = *data; extracted_by = "B3"; } + if (extraction_styles_.none && !extracted_data) { + extracted_data.emplace(); + extracted_by = "none"; + } + assert(extracted_data); auto& [trace_id, parent_id, origin, trace_tags, sampling_priority] = *extracted_data; @@ -349,7 +375,6 @@ Expected Tracer::extract_span(const DictReader& reader, // producing a root span // - if origin is _not_ set, then it's an error // - trace ID and parent ID means we're extracting a child span - // - parent ID without trace ID is an error if (!trace_id && !parent_id) { return Error{Error::NO_SPAN_TO_EXTRACT, diff --git a/src/datadog/tracer_config.cpp b/src/datadog/tracer_config.cpp index 32656166..2bf7ae84 100644 --- a/src/datadog/tracer_config.cpp +++ b/src/datadog/tracer_config.cpp @@ -76,8 +76,10 @@ Expected parse_propagation_styles(StringView input) { to_lower(token); if (token == "datadog") { styles.datadog = true; - } else if (token == "b3") { + } else if (token == "b3" || token == "b3multi") { styles.b3 = true; + } else if (token == "none") { + styles.none = true; } else { std::string message; message += "Unsupported propagation style \""; @@ -219,10 +221,12 @@ Expected finalize_config(const TracerConfig &config) { result.injection_styles = *styles; } - if (!result.extraction_styles.datadog && !result.extraction_styles.b3) { + if (!result.extraction_styles.datadog && !result.extraction_styles.b3 && + !result.extraction_styles.none) { return Error{Error::MISSING_SPAN_EXTRACTION_STYLE, "At least one extraction style must be specified."}; - } else if (!result.injection_styles.datadog && !result.injection_styles.b3) { + } else if (!result.injection_styles.datadog && !result.injection_styles.b3 && + !result.injection_styles.none) { return Error{Error::MISSING_SPAN_INJECTION_STYLE, "At least one injection style must be specified."}; } diff --git a/test/span.cpp b/test/span.cpp index df491a52..a671ed72 100644 --- a/test/span.cpp +++ b/test/span.cpp @@ -377,6 +377,7 @@ TEST_CASE("injection") { config.logger = std::make_shared(); config.injection_styles.datadog = true; config.injection_styles.b3 = true; + config.injection_styles.none = false; auto finalized_config = finalize_config(config); REQUIRE(finalized_config); @@ -447,3 +448,24 @@ TEST_CASE("injection") { } } } + +TEST_CASE("injection can be disabled using the \"none\" style") { + TracerConfig config; + config.defaults.service = "testsvc"; + config.defaults.name = "spanny"; + config.collector = std::make_shared(); + config.logger = std::make_shared(); + config.injection_styles.datadog = false; + config.injection_styles.b3 = false; + config.injection_styles.none = true; // this one + + const auto finalized_config = finalize_config(config); + REQUIRE(finalized_config); + Tracer tracer{*finalized_config}; + + const auto span = tracer.create_span(); + MockDictWriter writer; + span.inject(writer); + const std::unordered_map empty; + REQUIRE(writer.items == empty); +} diff --git a/test/tracer.cpp b/test/tracer.cpp index 97e37bc5..63135ae0 100644 --- a/test/tracer.cpp +++ b/test/tracer.cpp @@ -552,6 +552,31 @@ TEST_CASE("span extraction") { checks(test_case, *span); } + SECTION("extraction can be disabled using the \"none\" style") { + config.extraction_styles.datadog = false; + config.extraction_styles.b3 = false; + config.extraction_styles.none = true; // this one + + const auto finalized_config = finalize_config(config); + REQUIRE(finalized_config); + Tracer tracer{*finalized_config}; + const std::unordered_map headers{ + // It doesn't matter which headers are present. + // The "none" extraction style will not inspect them, and will return + // the "no span to extract" error. + {"X-Datadog-Trace-ID", "foo"}, + {"X-Datadog-Parent-ID", "bar"}, + {"X-Datadog-Sampling-Priority", "baz"}, + {"X-B3-TraceID", "foo"}, + {"X-B3-SpanID", "bar"}, + {"X-B3-Sampled", "baz"}, + }; + MockDictReader reader{headers}; + const auto result = tracer.extract_span(reader); + REQUIRE(!result); + REQUIRE(result.error().code == Error::NO_SPAN_TO_EXTRACT); + } + SECTION("x-datadog-tags") { auto finalized_config = finalize_config(config); REQUIRE(finalized_config); diff --git a/test/tracer_config.cpp b/test/tracer_config.cpp index bbf9a44f..be3b4e7b 100644 --- a/test/tracer_config.cpp +++ b/test/tracer_config.cpp @@ -1008,6 +1008,7 @@ TEST_CASE("TracerConfig propagation styles") { REQUIRE(finalized); REQUIRE(!finalized->injection_styles.datadog); REQUIRE(finalized->injection_styles.b3); + REQUIRE(!finalized->injection_styles.none); } SECTION("parsing") { @@ -1020,20 +1021,24 @@ TEST_CASE("TracerConfig propagation styles") { // clang-format off auto test_case = GENERATE(values({ - {__LINE__, "Datadog", x, {true, false}}, - {__LINE__, "DaTaDoG", x, {true, false}}, - {__LINE__, "B3", x, {false, true}}, - {__LINE__, "b3", x, {false, true}}, - {__LINE__, "Datadog B3", x, {true, true}}, - {__LINE__, "B3 Datadog", x, {true, true}}, - {__LINE__, "b3 datadog", x, {true, true}}, - {__LINE__, "b3, datadog", x, {true, true}}, - {__LINE__, "b3,datadog", x, {true, true}}, - {__LINE__, "b3, datadog", x, {true, true}}, + {__LINE__, "Datadog", x, {true, false, false}}, + {__LINE__, "DaTaDoG", x, {true, false, false}}, + {__LINE__, "B3", x, {false, true, false}}, + {__LINE__, "b3", x, {false, true, false}}, + {__LINE__, "b3MULTI", x, {false, true, false}}, + {__LINE__, "b3, b3multi", x, {false, true, false}}, + {__LINE__, "Datadog B3", x, {true, true, false}}, + {__LINE__, "Datadog B3 none", x, {true, true, true}}, + {__LINE__, "NONE", x, {false, false, true}}, + {__LINE__, "B3 Datadog", x, {true, true, false}}, + {__LINE__, "b3 datadog", x, {true, true, false}}, + {__LINE__, "b3, datadog", x, {true, true, false}}, + {__LINE__, "b3,datadog", x, {true, true, false}}, + {__LINE__, "b3, datadog", x, {true, true, false}}, {__LINE__, "b3,,datadog", Error::UNKNOWN_PROPAGATION_STYLE}, {__LINE__, "b3,datadog,w3c", Error::UNKNOWN_PROPAGATION_STYLE}, - {__LINE__, "b3,datadog,datadog", x, {true, true}}, - {__LINE__, " b3 b3 b3, b3 , b3, b3, b3 , b3 b3 b3 ", x, {false, true}}, + {__LINE__, "b3,datadog,datadog", x, {true, true, false}}, + {__LINE__, " b3 b3 b3, b3 , b3, b3, b3 , b3 b3 b3 ", x, {false, true, false}}, })); // clang-format on @@ -1052,6 +1057,8 @@ TEST_CASE("TracerConfig propagation styles") { test_case.expected_styles.datadog); REQUIRE(finalized->injection_styles.b3 == test_case.expected_styles.b3); + REQUIRE(finalized->injection_styles.none == + test_case.expected_styles.none); } } } @@ -1064,11 +1071,13 @@ TEST_CASE("TracerConfig propagation styles") { REQUIRE(finalized); REQUIRE(finalized->extraction_styles.datadog); REQUIRE(!finalized->extraction_styles.b3); + REQUIRE(!finalized->extraction_styles.none); } SECTION("need at least one") { config.extraction_styles.datadog = false; config.extraction_styles.b3 = false; + config.extraction_styles.none = false; auto finalized = finalize_config(config); REQUIRE(!finalized); REQUIRE(finalized.error().code == Error::MISSING_SPAN_EXTRACTION_STYLE); @@ -1081,6 +1090,7 @@ TEST_CASE("TracerConfig propagation styles") { REQUIRE(finalized); REQUIRE(!finalized->extraction_styles.datadog); REQUIRE(finalized->extraction_styles.b3); + REQUIRE(!finalized->extraction_styles.none); } // It's the same as for injection styles, so let's omit most of the From accbb7e04d662d8305a74803b4fce6706e8331f6 Mon Sep 17 00:00:00 2001 From: David Goffredo Date: Wed, 14 Dec 2022 12:07:49 -0500 Subject: [PATCH 03/11] add new env vars (without using them), and refactor propagation style parsing --- src/datadog/environment.h | 3 ++ src/datadog/tracer_config.cpp | 78 ++++++++++++++++++++--------------- src/datadog/tracer_config.h | 9 ++-- 3 files changed, 52 insertions(+), 38 deletions(-) diff --git a/src/datadog/environment.h b/src/datadog/environment.h index 9e878af9..fbcd78c3 100644 --- a/src/datadog/environment.h +++ b/src/datadog/environment.h @@ -29,6 +29,9 @@ namespace environment { MACRO(DD_ENV) \ MACRO(DD_PROPAGATION_STYLE_EXTRACT) \ MACRO(DD_PROPAGATION_STYLE_INJECT) \ + MACRO(DD_TRACE_PROPAGATION_STYLE_EXTRACT) \ + MACRO(DD_TRACE_PROPAGATION_STYLE_INJECT) \ + MACRO(DD_TRACE_PROPAGATION_STYLE) \ MACRO(DD_SERVICE) \ MACRO(DD_SPAN_SAMPLING_RULES) \ MACRO(DD_SPAN_SAMPLING_RULES_FILE) \ diff --git a/src/datadog/tracer_config.cpp b/src/datadog/tracer_config.cpp index 2bf7ae84..1a12371f 100644 --- a/src/datadog/tracer_config.cpp +++ b/src/datadog/tracer_config.cpp @@ -121,6 +121,47 @@ Expected> parse_tags( return tags; } +Expected finalize_propagation_styles(FinalizedTracerConfig &result, + const TracerConfig &config) { + result.extraction_styles = config.extraction_styles; + if (auto styles_env = lookup(environment::DD_PROPAGATION_STYLE_EXTRACT)) { + auto styles = parse_propagation_styles(*styles_env); + if (auto *error = styles.if_error()) { + std::string prefix; + prefix += "Unable to parse "; + append(prefix, name(environment::DD_PROPAGATION_STYLE_EXTRACT)); + prefix += " environment variable: "; + return error->with_prefix(prefix); + } + result.extraction_styles = *styles; + } + + result.injection_styles = config.injection_styles; + if (auto styles_env = lookup(environment::DD_PROPAGATION_STYLE_INJECT)) { + auto styles = parse_propagation_styles(*styles_env); + if (auto *error = styles.if_error()) { + std::string prefix; + prefix += "Unable to parse "; + append(prefix, name(environment::DD_PROPAGATION_STYLE_INJECT)); + prefix += " environment variable: "; + return error->with_prefix(prefix); + } + result.injection_styles = *styles; + } + + if (!result.extraction_styles.datadog && !result.extraction_styles.b3 && + !result.extraction_styles.none) { + return Error{Error::MISSING_SPAN_EXTRACTION_STYLE, + "At least one extraction style must be specified."}; + } else if (!result.injection_styles.datadog && !result.injection_styles.b3 && + !result.injection_styles.none) { + return Error{Error::MISSING_SPAN_INJECTION_STYLE, + "At least one injection style must be specified."}; + } + + return {}; +} + } // namespace Expected finalize_config(const TracerConfig &config) { @@ -195,40 +236,9 @@ Expected finalize_config(const TracerConfig &config) { return std::move(span_sampler_config.error()); } - result.extraction_styles = config.extraction_styles; - if (auto styles_env = lookup(environment::DD_PROPAGATION_STYLE_EXTRACT)) { - auto styles = parse_propagation_styles(*styles_env); - if (auto *error = styles.if_error()) { - std::string prefix; - prefix += "Unable to parse "; - append(prefix, name(environment::DD_PROPAGATION_STYLE_EXTRACT)); - prefix += " environment variable: "; - return error->with_prefix(prefix); - } - result.extraction_styles = *styles; - } - - result.injection_styles = config.injection_styles; - if (auto styles_env = lookup(environment::DD_PROPAGATION_STYLE_INJECT)) { - auto styles = parse_propagation_styles(*styles_env); - if (auto *error = styles.if_error()) { - std::string prefix; - prefix += "Unable to parse "; - append(prefix, name(environment::DD_PROPAGATION_STYLE_INJECT)); - prefix += " environment variable: "; - return error->with_prefix(prefix); - } - result.injection_styles = *styles; - } - - if (!result.extraction_styles.datadog && !result.extraction_styles.b3 && - !result.extraction_styles.none) { - return Error{Error::MISSING_SPAN_EXTRACTION_STYLE, - "At least one extraction style must be specified."}; - } else if (!result.injection_styles.datadog && !result.injection_styles.b3 && - !result.injection_styles.none) { - return Error{Error::MISSING_SPAN_INJECTION_STYLE, - "At least one injection style must be specified."}; + auto maybe_error = finalize_propagation_styles(result, config); + if (!maybe_error) { + return maybe_error.error(); } result.report_hostname = config.report_hostname; diff --git a/src/datadog/tracer_config.h b/src/datadog/tracer_config.h index f49fb672..80f41617 100644 --- a/src/datadog/tracer_config.h +++ b/src/datadog/tracer_config.h @@ -59,14 +59,15 @@ struct TracerConfig { // `injection_styles` indicates with which tracing systems trace propagation // will be compatible when injecting (sending) trace context. - // `injection_styles` is overridden by the `DD_PROPAGATION_STYLE_INJECT` - // environment variable. + // `injection_styles` is overridden by the `DD_TRACE_PROPAGATION_STYLE_INJECT` + // and `DD_TRACE_PROPAGATION_STYLE` environment variables. PropagationStyles injection_styles; // `extraction_styles` indicates with which tracing systems trace propagation // will be compatible when extracting (receiving) trace context. - // `extraction_styles` is overridden by the `DD_PROPAGATION_STYLE_EXTRACT` - // environment variable. + // `extraction_styles` is overridden by the + // `DD_TRACE_PROPAGATION_STYLE_EXTRACT` and `DD_TRACE_PROPAGATION_STYLE` + // environment variables. PropagationStyles extraction_styles; // `report_hostname` indicates whether the tracer will include the result of From c31eef60f4ab345f01d1a2260eca4ee64795bf86 Mon Sep 17 00:00:00 2001 From: David Goffredo Date: Wed, 14 Dec 2022 16:11:03 -0500 Subject: [PATCH 04/11] New env vars: - DD_TRACE_PROPAGATION_STYLE - DD_TRACE_PROPAGATION_STYLE_INJECT - DD_TRACE_PROPAGATION_STYLE_EXTRACT --- src/datadog/error.h | 1 + src/datadog/optional.h | 14 ++++ src/datadog/tracer_config.cpp | 139 ++++++++++++++++++++++++++++------ test/tracer_config.cpp | 118 +++++++++++++++++++++++++++-- 4 files changed, 242 insertions(+), 30 deletions(-) diff --git a/src/datadog/error.h b/src/datadog/error.h index f19eae01..2857de15 100644 --- a/src/datadog/error.h +++ b/src/datadog/error.h @@ -67,6 +67,7 @@ struct Error { INVALID_DOUBLE = 42, MISSING_TRACE_ID = 43, ENVOY_HTTP_CLIENT_FAILURE = 44, + MULTIPLE_PROPAGATION_STYLE_ENVIRONMENT_VARIABLES = 45, }; Code code; diff --git a/src/datadog/optional.h b/src/datadog/optional.h index 8ce7be2b..f78221dc 100644 --- a/src/datadog/optional.h +++ b/src/datadog/optional.h @@ -33,6 +33,8 @@ #include #endif // defined DD_USE_ABSEIL_FOR_ENVOY +#include // std::forward + namespace datadog { namespace tracing { @@ -46,5 +48,17 @@ using Optional = std::optional; inline constexpr auto nullopt = std::nullopt; #endif // defined DD_USE_ABSEIL_FOR_ENVOY +// Return the first non-null argument value. The last argument must not be +// `Optional`. +template +auto value_or(Value&& value) { + return std::forward(value); +} + +template +auto value_or(Optional maybe, Rest&&... rest) { + return maybe.value_or(value_or(rest...)); +} + } // namespace tracing } // namespace datadog diff --git a/src/datadog/tracer_config.cpp b/src/datadog/tracer_config.cpp index 1a12371f..f3c04b1b 100644 --- a/src/datadog/tracer_config.cpp +++ b/src/datadog/tracer_config.cpp @@ -10,6 +10,7 @@ #include "cerr_logger.h" #include "datadog_agent.h" #include "environment.h" +#include "json.hpp" #include "null_collector.h" #include "parse_util.h" #include "string_view.h" @@ -121,40 +122,127 @@ Expected> parse_tags( return tags; } +// Return a `PropagationStyles` parsed from the specified `env_var`. +// If `env_var` is not in the environment, return `nullopt`. +// If an error occurs, throw an `Error`. +Optional styles_from_env(environment::Variable env_var) { + const auto styles_env = lookup(env_var); + if (!styles_env) { + return {}; + } + + auto styles = parse_propagation_styles(*styles_env); + if (auto *error = styles.if_error()) { + std::string prefix; + prefix += "Unable to parse "; + append(prefix, name(env_var)); + prefix += " environment variable: "; + throw error->with_prefix(prefix); + } + return *styles; +} + +std::string json_quoted(StringView text) { + std::string unquoted; + assign(unquoted, text); + return nlohmann::json(unquoted).dump(); +} + Expected finalize_propagation_styles(FinalizedTracerConfig &result, - const TracerConfig &config) { - result.extraction_styles = config.extraction_styles; - if (auto styles_env = lookup(environment::DD_PROPAGATION_STYLE_EXTRACT)) { - auto styles = parse_propagation_styles(*styles_env); - if (auto *error = styles.if_error()) { - std::string prefix; - prefix += "Unable to parse "; - append(prefix, name(environment::DD_PROPAGATION_STYLE_EXTRACT)); - prefix += " environment variable: "; - return error->with_prefix(prefix); + const TracerConfig &config, + Logger &logger) { + namespace env = environment; + // Print a warning if a questionable combination of environment variables is + // defined. + const auto ts = env::DD_TRACE_PROPAGATION_STYLE; + const auto tse = env::DD_TRACE_PROPAGATION_STYLE_EXTRACT; + const auto se = env::DD_PROPAGATION_STYLE_EXTRACT; + const auto tsi = env::DD_TRACE_PROPAGATION_STYLE_INJECT; + const auto si = env::DD_PROPAGATION_STYLE_INJECT; + // clang-format off + /* + ts tse se tsi si + --- --- --- --- --- + ts | x warn warn warn warn + | + tse | x x warn ok ok + | + se | x x x ok ok + | + tsi | x x x x warn + | + si | x x x x x + */ + // In each pair, the first would be overridden by the second. + const std::pair questionable_combinations[] = { + {ts, tse}, {ts, se}, {ts, tsi}, {ts, si}, + + {se, tse}, /* ok */ /* ok */ + + /* ok */ /* ok */ + + {si, tsi}, + }; + // clang-format on + + const auto warn_message = [](StringView name, StringView value, + StringView name_override, + StringView value_override) { + std::string message; + message += "Both the environment variables "; + append(message, name); + message += "="; + message += json_quoted(value); + message += " and "; + append(message, name_override); + message += "="; + message += json_quoted(value_override); + message += " are defined. "; + append(message, name_override); + message += " will take precedence."; + return message; + }; + + for (const auto &[var, var_override] : questionable_combinations) { + const auto value = lookup(var); + if (!value) { + continue; + } + const auto value_override = lookup(var_override); + if (!value_override) { + continue; } - result.extraction_styles = *styles; + const auto var_name = name(var); + const auto var_name_override = name(var_override); + logger.log_error(Error{ + Error::MULTIPLE_PROPAGATION_STYLE_ENVIRONMENT_VARIABLES, + warn_message(var_name, *value, var_name_override, *value_override)}); } - result.injection_styles = config.injection_styles; - if (auto styles_env = lookup(environment::DD_PROPAGATION_STYLE_INJECT)) { - auto styles = parse_propagation_styles(*styles_env); - if (auto *error = styles.if_error()) { - std::string prefix; - prefix += "Unable to parse "; - append(prefix, name(environment::DD_PROPAGATION_STYLE_INJECT)); - prefix += " environment variable: "; - return error->with_prefix(prefix); - } - result.injection_styles = *styles; + // Parse the propagation styles from the configuration and/or from the + // environment. + // Exceptions make this section simpler. + try { + const auto global_styles = styles_from_env(env::DD_TRACE_PROPAGATION_STYLE); + result.extraction_styles = + value_or(styles_from_env(env::DD_TRACE_PROPAGATION_STYLE_EXTRACT), + styles_from_env(env::DD_PROPAGATION_STYLE_EXTRACT), + global_styles, config.extraction_styles); + result.injection_styles = + value_or(styles_from_env(env::DD_TRACE_PROPAGATION_STYLE_INJECT), + styles_from_env(env::DD_PROPAGATION_STYLE_INJECT), + global_styles, config.injection_styles); + } catch (Error &error) { + return std::move(error); } if (!result.extraction_styles.datadog && !result.extraction_styles.b3 && !result.extraction_styles.none) { return Error{Error::MISSING_SPAN_EXTRACTION_STYLE, "At least one extraction style must be specified."}; - } else if (!result.injection_styles.datadog && !result.injection_styles.b3 && - !result.injection_styles.none) { + } + if (!result.injection_styles.datadog && !result.injection_styles.b3 && + !result.injection_styles.none) { return Error{Error::MISSING_SPAN_INJECTION_STYLE, "At least one injection style must be specified."}; } @@ -236,7 +324,8 @@ Expected finalize_config(const TracerConfig &config) { return std::move(span_sampler_config.error()); } - auto maybe_error = finalize_propagation_styles(result, config); + auto maybe_error = + finalize_propagation_styles(result, config, *result.logger); if (!maybe_error) { return maybe_error.error(); } diff --git a/test/tracer_config.cpp b/test/tracer_config.cpp index be3b4e7b..ba4d3bda 100644 --- a/test/tracer_config.cpp +++ b/test/tracer_config.cpp @@ -6,6 +6,7 @@ #include #include +#include #include #include #include @@ -985,6 +986,20 @@ TEST_CASE("TracerConfig propagation styles") { TracerConfig config; config.defaults.service = "testsvc"; + SECTION("DD_TRACE_PROPAGATION_STYLE overrides defaults") { + const EnvGuard guard{"DD_TRACE_PROPAGATION_STYLE", "B3"}; + auto finalized = finalize_config(config); + REQUIRE(finalized); + + REQUIRE(!finalized->injection_styles.datadog); + REQUIRE(finalized->injection_styles.b3); + REQUIRE(!finalized->injection_styles.none); + + REQUIRE(!finalized->extraction_styles.datadog); + REQUIRE(finalized->extraction_styles.b3); + REQUIRE(!finalized->extraction_styles.none); + } + SECTION("injection_styles") { SECTION("defaults to just Datadog") { auto finalized = finalize_config(config); @@ -1001,9 +1016,31 @@ TEST_CASE("TracerConfig propagation styles") { REQUIRE(finalized.error().code == Error::MISSING_SPAN_INJECTION_STYLE); } - SECTION("DD_PROPAGATION_STYLE_INJECT") { + SECTION("DD_TRACE_PROPAGATION_STYLE_INJECT") { SECTION("overrides injection_styles") { - const EnvGuard guard{"DD_PROPAGATION_STYLE_INJECT", "B3"}; + const EnvGuard guard{"DD_TRACE_PROPAGATION_STYLE_INJECT", "B3"}; + auto finalized = finalize_config(config); + REQUIRE(finalized); + REQUIRE(!finalized->injection_styles.datadog); + REQUIRE(finalized->injection_styles.b3); + REQUIRE(!finalized->injection_styles.none); + } + + SECTION("overrides DD_PROPAGATION_STYLE_INJECT") { + const EnvGuard guard1{"DD_TRACE_PROPAGATION_STYLE_INJECT", "B3"}; + const EnvGuard guard2{"DD_PROPAGATION_STYLE_INJECT", "Datadog"}; + config.logger = std::make_shared(); // suppress warning + auto finalized = finalize_config(config); + REQUIRE(finalized); + REQUIRE(!finalized->injection_styles.datadog); + REQUIRE(finalized->injection_styles.b3); + REQUIRE(!finalized->injection_styles.none); + } + + SECTION("overrides DD_TRACE_PROPAGATION_STYLE") { + const EnvGuard guard1{"DD_TRACE_PROPAGATION_STYLE_INJECT", "B3"}; + const EnvGuard guard2{"DD_TRACE_PROPAGATION_STYLE", "Datadog"}; + config.logger = std::make_shared(); // suppress warning auto finalized = finalize_config(config); REQUIRE(finalized); REQUIRE(!finalized->injection_styles.datadog); @@ -1045,7 +1082,7 @@ TEST_CASE("TracerConfig propagation styles") { CAPTURE(test_case.line); CAPTURE(test_case.env_value); - const EnvGuard guard{"DD_PROPAGATION_STYLE_INJECT", + const EnvGuard guard{"DD_TRACE_PROPAGATION_STYLE_INJECT", test_case.env_value}; auto finalized = finalize_config(config); if (test_case.expected_error) { @@ -1083,9 +1120,31 @@ TEST_CASE("TracerConfig propagation styles") { REQUIRE(finalized.error().code == Error::MISSING_SPAN_EXTRACTION_STYLE); } - SECTION("DD_PROPAGATION_STYLE_EXTRACT") { + SECTION("DD_TRACE_PROPAGATION_STYLE_EXTRACT") { SECTION("overrides extraction_styles") { - const EnvGuard guard{"DD_PROPAGATION_STYLE_EXTRACT", "B3"}; + const EnvGuard guard{"DD_TRACE_PROPAGATION_STYLE_EXTRACT", "B3"}; + auto finalized = finalize_config(config); + REQUIRE(finalized); + REQUIRE(!finalized->extraction_styles.datadog); + REQUIRE(finalized->extraction_styles.b3); + REQUIRE(!finalized->extraction_styles.none); + } + + SECTION("overrides DD_PROPAGATION_STYLE_EXTRACT") { + const EnvGuard guard1{"DD_TRACE_PROPAGATION_STYLE_EXTRACT", "B3"}; + const EnvGuard guard2{"DD_PROPAGATION_STYLE_EXTRACT", "Datadog"}; + config.logger = std::make_shared(); // suppress warning + auto finalized = finalize_config(config); + REQUIRE(finalized); + REQUIRE(!finalized->extraction_styles.datadog); + REQUIRE(finalized->extraction_styles.b3); + REQUIRE(!finalized->extraction_styles.none); + } + + SECTION("overrides DD_TRACE_PROPAGATION_STYLE") { + const EnvGuard guard1{"DD_TRACE_PROPAGATION_STYLE_EXTRACT", "B3"}; + const EnvGuard guard2{"DD_TRACE_PROPAGATION_STYLE", "Datadog"}; + config.logger = std::make_shared(); // suppress warning auto finalized = finalize_config(config); REQUIRE(finalized); REQUIRE(!finalized->extraction_styles.datadog); @@ -1104,4 +1163,53 @@ TEST_CASE("TracerConfig propagation styles") { } } } + + SECTION("warn if one env var overrides another") { + const auto logger = std::make_shared(); + config.logger = logger; + const auto ts = "DD_TRACE_PROPAGATION_STYLE"; + const auto tse = "DD_TRACE_PROPAGATION_STYLE_EXTRACT"; + const auto se = "DD_PROPAGATION_STYLE_EXTRACT"; + const auto tsi = "DD_TRACE_PROPAGATION_STYLE_INJECT"; + const auto si = "DD_PROPAGATION_STYLE_INJECT"; + const char* const vars[] = {ts, tse, se, tsi, si}; + constexpr auto n = sizeof(vars) / sizeof(vars[0]); + // clang-format off + const bool x = false; // ignored values + const bool expect_warning[n][n] = { + // ts tse se tsi si + // --- --- --- --- --- + /* ts */{ x, true, true, true, true }, + + /* tse */{ x, x, true, false, false }, + + /* se */{ x, x, x, false, false }, + + /* tsi */{ x, x, x, x, true }, + + /* si */{ x, x, x, x, x }, + }; + // clang-format on + for (std::size_t i = 0; i < n; ++i) { + for (std::size_t j = i + 1; j < n; ++j) { + CAPTURE(i); + CAPTURE(vars[i]); + CAPTURE(j); + CAPTURE(vars[j]); + CAPTURE(expect_warning[i][j]); + const EnvGuard guard1{vars[i], "B3"}; + const EnvGuard guard2{vars[j], "B3"}; + const auto finalized_config = finalize_config(config); + REQUIRE(finalized_config); + if (expect_warning[i][j]) { + REQUIRE(logger->error_count() == 1); + REQUIRE(logger->first_error().code == + Error::MULTIPLE_PROPAGATION_STYLE_ENVIRONMENT_VARIABLES); + } else { + REQUIRE(logger->error_count() == 0); + } + logger->entries.clear(); + } + } + } } From 67b2f96cc0dbfb810f63ea31db4cde7df60a3dd6 Mon Sep 17 00:00:00 2001 From: David Goffredo Date: Fri, 16 Dec 2022 12:57:30 -0500 Subject: [PATCH 05/11] nits --- src/datadog/optional.h | 2 +- src/datadog/tracer_config.cpp | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/src/datadog/optional.h b/src/datadog/optional.h index f78221dc..ae1deb7c 100644 --- a/src/datadog/optional.h +++ b/src/datadog/optional.h @@ -57,7 +57,7 @@ auto value_or(Value&& value) { template auto value_or(Optional maybe, Rest&&... rest) { - return maybe.value_or(value_or(rest...)); + return maybe.value_or(value_or(std::forward(rest)...)); } } // namespace tracing diff --git a/src/datadog/tracer_config.cpp b/src/datadog/tracer_config.cpp index f3c04b1b..2ba0a57d 100644 --- a/src/datadog/tracer_config.cpp +++ b/src/datadog/tracer_config.cpp @@ -145,7 +145,7 @@ Optional styles_from_env(environment::Variable env_var) { std::string json_quoted(StringView text) { std::string unquoted; assign(unquoted, text); - return nlohmann::json(unquoted).dump(); + return nlohmann::json(std::move(unquoted)).dump(); } Expected finalize_propagation_styles(FinalizedTracerConfig &result, From 1d4a168edf2cb89697e07bbfb1e4c6de3bac8e8e Mon Sep 17 00:00:00 2001 From: David Goffredo Date: Fri, 16 Dec 2022 15:07:28 -0500 Subject: [PATCH 06/11] untested: propagation style order matters --- BUILD.bazel | 4 +- CMakeLists.txt | 6 ++- doc/includes.dot | 4 +- doc/includes.svg | 4 +- src/datadog/error.h | 1 + src/datadog/propagation_style.cpp | 31 +++++++++++ src/datadog/propagation_style.h | 30 +++++++++++ src/datadog/propagation_styles.cpp | 26 ---------- src/datadog/propagation_styles.h | 27 ---------- src/datadog/trace_segment.cpp | 33 +++++++----- src/datadog/trace_segment.h | 6 +-- src/datadog/tracer.cpp | 83 +++++++++--------------------- src/datadog/tracer.h | 4 +- src/datadog/tracer_config.cpp | 48 ++++++++++++----- src/datadog/tracer_config.h | 15 ++++-- test/tracer_config.cpp | 7 +-- 16 files changed, 169 insertions(+), 160 deletions(-) create mode 100644 src/datadog/propagation_style.cpp create mode 100644 src/datadog/propagation_style.h delete mode 100644 src/datadog/propagation_styles.cpp delete mode 100644 src/datadog/propagation_styles.h diff --git a/BUILD.bazel b/BUILD.bazel index 5573b39b..088228a5 100644 --- a/BUILD.bazel +++ b/BUILD.bazel @@ -26,7 +26,7 @@ cc_library( "src/datadog/null_collector.cpp", "src/datadog/optional.cpp", "src/datadog/parse_util.cpp", - "src/datadog/propagation_styles.cpp", + "src/datadog/propagation_style.cpp", "src/datadog/rate.cpp", "src/datadog/sampling_decision.cpp", "src/datadog/sampling_mechanism.cpp", @@ -77,7 +77,7 @@ cc_library( "src/datadog/null_collector.h", "src/datadog/optional.h", "src/datadog/parse_util.h", - "src/datadog/propagation_styles.h", + "src/datadog/propagation_style.h", "src/datadog/rate.h", "src/datadog/sampling_decision.h", "src/datadog/sampling_mechanism.h", diff --git a/CMakeLists.txt b/CMakeLists.txt index ffb0ce6b..07aaaab9 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -6,6 +6,8 @@ project(dd-trace-cpp) option(BUILD_COVERAGE "Build code with code coverage profiling instrumentation" OFF) option(BUILD_EXAMPLE "Build the example program (example/)" OFF) +option(BUILD_TESTING "Build the unit tests (test/)" OFF) +option(SANITIZE "Build with address sanitizer and undefined behavior sanitizer" OFF) set(CMAKE_BUILD_TYPE "RelWithDebInfo") set(CMAKE_POSITION_INDEPENDENT_CODE ON) @@ -78,7 +80,7 @@ target_sources(dd_trace_cpp PRIVATE src/datadog/null_collector.cpp src/datadog/optional.cpp src/datadog/parse_util.cpp - src/datadog/propagation_styles.cpp + src/datadog/propagation_style.cpp src/datadog/rate.cpp src/datadog/sampling_decision.cpp src/datadog/sampling_mechanism.cpp @@ -135,7 +137,7 @@ target_sources(dd_trace_cpp PUBLIC src/datadog/null_collector.h src/datadog/optional.h src/datadog/parse_util.h - src/datadog/propagation_styles.h + src/datadog/propagation_style.h src/datadog/rate.h src/datadog/sampling_decision.h src/datadog/sampling_mechanism.h diff --git a/doc/includes.dot b/doc/includes.dot index 2db29b94..c609a655 100644 --- a/doc/includes.dot +++ b/doc/includes.dot @@ -75,7 +75,7 @@ digraph G { node73 [label="version.cpp"]; node74 [label="span_matcher.h"]; node75 [label="span_sampler_config.h"]; - node76 [label="propagation_styles.cpp"]; + node76 [label="propagation_style.cpp"]; node77 [label="dict_reader.h"]; node78 [label="span_matcher.cpp"]; node79 [label="default_http_client_curl.cpp"]; @@ -84,7 +84,7 @@ digraph G { node82 [label="clock.cpp"]; node83 [label="collector_response.cpp"]; node84 [label="sampling_priority.h"]; - node85 [label="propagation_styles.h"]; + node85 [label="propagation_style.h"]; node86 [label="limiter.cpp"]; node87 [label="net_util.h"]; node88 [label="error.cpp"]; diff --git a/doc/includes.svg b/doc/includes.svg index ac674744..a3ca087e 100644 --- a/doc/includes.svg +++ b/doc/includes.svg @@ -187,7 +187,7 @@ node85 -propagation_styles.h +propagation_style.h @@ -1465,7 +1465,7 @@ node76 -propagation_styles.cpp +propagation_style.cpp diff --git a/src/datadog/error.h b/src/datadog/error.h index 2857de15..97799604 100644 --- a/src/datadog/error.h +++ b/src/datadog/error.h @@ -68,6 +68,7 @@ struct Error { MISSING_TRACE_ID = 43, ENVOY_HTTP_CLIENT_FAILURE = 44, MULTIPLE_PROPAGATION_STYLE_ENVIRONMENT_VARIABLES = 45, + DUPLICATE_PROPAGATION_STYLE = 46, }; Code code; diff --git a/src/datadog/propagation_style.cpp b/src/datadog/propagation_style.cpp new file mode 100644 index 00000000..146c6cd1 --- /dev/null +++ b/src/datadog/propagation_style.cpp @@ -0,0 +1,31 @@ +#include "propagation_style.h" + +#include + +#include "json.hpp" + +namespace datadog { +namespace tracing { + +nlohmann::json to_json(PropagationStyle style) { + switch (style) { + case PropagationStyle::DATADOG: + return "datadog"; + case PropagationStyle::B3: + return "B3"; + default: + assert(style == PropagationStyle::NONE); + return "none"; + } +} + +nlohmann::json to_json(const std::vector& styles) { + std::vector styles_json; + for (const auto style : styles) { + styles_json.push_back(to_json(style)); + } + return styles_json; +} + +} // namespace tracing +} // namespace datadog diff --git a/src/datadog/propagation_style.h b/src/datadog/propagation_style.h new file mode 100644 index 00000000..66d29786 --- /dev/null +++ b/src/datadog/propagation_style.h @@ -0,0 +1,30 @@ +#pragma once + +// This component provides an `enum class`, `PropagationStyle`, that indicates a +// trace context extraction or injection format to be used. `TracerConfig` has +// one `std::vector` for extraction and another for injection. +// See `tracer_config.h`. + +#include + +#include "json_fwd.hpp" + +namespace datadog { +namespace tracing { + +enum class PropagationStyle { + // Datadog headers, e.g. X-Datadog-Trace-ID + DATADOG, + // B3 multi-header style, e.g. X-B3-TraceID + B3, + // The absence of propagation. If this is the only style set, then + // propagation is disabled in the relevant direction (extraction or + // injection). + NONE, +}; + +nlohmann::json to_json(PropagationStyle style); +nlohmann::json to_json(const std::vector& styles); + +} // namespace tracing +} // namespace datadog diff --git a/src/datadog/propagation_styles.cpp b/src/datadog/propagation_styles.cpp deleted file mode 100644 index eb3094d9..00000000 --- a/src/datadog/propagation_styles.cpp +++ /dev/null @@ -1,26 +0,0 @@ -#include "propagation_styles.h" - -#include -#include - -#include "json.hpp" - -namespace datadog { -namespace tracing { - -nlohmann::json to_json(const PropagationStyles& styles) { - std::vector selected_names; - if (styles.datadog) { - selected_names.emplace_back("datadog"); - } - if (styles.b3) { - selected_names.emplace_back("B3"); - } - if (styles.none) { - selected_names.emplace_back("none"); - } - return selected_names; -} - -} // namespace tracing -} // namespace datadog diff --git a/src/datadog/propagation_styles.h b/src/datadog/propagation_styles.h deleted file mode 100644 index 78e6378f..00000000 --- a/src/datadog/propagation_styles.h +++ /dev/null @@ -1,27 +0,0 @@ -#pragma once - -// This component provides a `struct`, `PropagationStyles`, that specifies which -// trace context extraction or injection formats are to be used. `TracerConfig` -// has one `PropagationStyles` for extraction and another for injection. See -// `tracer_config.h`. - -#include "json_fwd.hpp" - -namespace datadog { -namespace tracing { - -struct PropagationStyles { - // Datadog headers, e.g. X-Datadog-Trace-ID - bool datadog = true; - // B3 multi-header style, e.g. X-B3-TraceID - bool b3 = false; - // The absence of propagation. If this is the only style set, then - // propagation is disabled in the relevant direction (extraction or - // injection). - bool none = false; -}; - -nlohmann::json to_json(const PropagationStyles&); - -} // namespace tracing -} // namespace datadog diff --git a/src/datadog/trace_segment.cpp b/src/datadog/trace_segment.cpp index 5f57c8af..ac70d96e 100644 --- a/src/datadog/trace_segment.cpp +++ b/src/datadog/trace_segment.cpp @@ -45,7 +45,7 @@ TraceSegment::TraceSegment( const std::shared_ptr& trace_sampler, const std::shared_ptr& span_sampler, const std::shared_ptr& defaults, - const PropagationStyles& injection_styles, + const std::vector& injection_styles, const Optional& hostname, Optional origin, std::size_t tags_header_max_size, std::unordered_map trace_tags, @@ -224,8 +224,8 @@ void TraceSegment::inject(DictWriter& writer, const SpanData& span) { // Origin and trace tag headers are always propagated, unless the only // injection style is "none". // Other headers depend on the injection styles. - if (injection_styles_.none && !injection_styles_.datadog && - !injection_styles_.b3) { + if (injection_styles_.size() == 1 && + injection_styles_[0] == PropagationStyle::NONE) { return; } @@ -248,17 +248,22 @@ void TraceSegment::inject(DictWriter& writer, const SpanData& span) { writer.set("x-datadog-tags", encoded_trace_tags); } - if (injection_styles_.datadog) { - writer.set("x-datadog-trace-id", std::to_string(span.trace_id)); - writer.set("x-datadog-parent-id", std::to_string(span.span_id)); - writer.set("x-datadog-sampling-priority", - std::to_string(sampling_priority)); - } - - if (injection_styles_.b3) { - writer.set("x-b3-traceid", hex(span.trace_id)); - writer.set("x-b3-spanid", hex(span.span_id)); - writer.set("x-b3-sampled", std::to_string(int(sampling_priority > 0))); + for (const auto style : injection_styles_) { + switch (style) { + case PropagationStyle::DATADOG: + writer.set("x-datadog-trace-id", std::to_string(span.trace_id)); + writer.set("x-datadog-parent-id", std::to_string(span.span_id)); + writer.set("x-datadog-sampling-priority", + std::to_string(sampling_priority)); + break; + case PropagationStyle::B3: + writer.set("x-b3-traceid", hex(span.trace_id)); + writer.set("x-b3-spanid", hex(span.span_id)); + writer.set("x-b3-sampled", std::to_string(int(sampling_priority > 0))); + break; + case PropagationStyle::NONE: + break; + } } } diff --git a/src/datadog/trace_segment.h b/src/datadog/trace_segment.h index 2e095b18..0256e405 100644 --- a/src/datadog/trace_segment.h +++ b/src/datadog/trace_segment.h @@ -34,7 +34,7 @@ #include "expected.h" #include "optional.h" -#include "propagation_styles.h" +#include "propagation_style.h" #include "sampling_decision.h" namespace datadog { @@ -58,7 +58,7 @@ class TraceSegment { std::shared_ptr span_sampler_; std::shared_ptr defaults_; - const PropagationStyles injection_styles_; + const std::vector injection_styles_; const Optional hostname_; const Optional origin_; const std::size_t tags_header_max_size_; @@ -75,7 +75,7 @@ class TraceSegment { const std::shared_ptr& trace_sampler, const std::shared_ptr& span_sampler, const std::shared_ptr& defaults, - const PropagationStyles& injection_styles, + const std::vector& injection_styles, const Optional& hostname, Optional origin, std::size_t tags_header_max_size, std::unordered_map trace_tags, diff --git a/src/datadog/tracer.cpp b/src/datadog/tracer.cpp index eaec1e6d..13ccf913 100644 --- a/src/datadog/tracer.cpp +++ b/src/datadog/tracer.cpp @@ -168,27 +168,6 @@ struct ExtractedData { Optional sampling_priority; }; -bool operator!=(const ExtractedData& left, const ExtractedData& right) { - return left.trace_id != right.trace_id || left.parent_id != right.parent_id || - left.origin != right.origin || left.trace_tags != right.trace_tags || - left.sampling_priority != right.sampling_priority; -} - -nlohmann::json to_json(const ExtractedData& data) { - auto result = nlohmann::json::object({}); -#define ADD_FIELD(FIELD) \ - if (data.FIELD) { \ - result[#FIELD] = *data.FIELD; \ - } - ADD_FIELD(trace_id) - ADD_FIELD(parent_id) - ADD_FIELD(origin) - ADD_FIELD(trace_tags) - ADD_FIELD(sampling_priority) -#undef ADD_FIELD - return result; -} - Expected extract_data(ExtractionPolicy& extract, const DictReader& reader) { ExtractedData extracted_data; @@ -226,8 +205,8 @@ void log_startup_message(Logger& logger, StringView tracer_version_string, const SpanDefaults& defaults, const TraceSampler& trace_sampler, const SpanSampler& span_sampler, - const PropagationStyles& injection_styles, - const PropagationStyles& extraction_styles, + const std::vector& injection_styles, + const std::vector& extraction_styles, const Optional& hostname, std::size_t tags_header_max_size) { // clang-format off @@ -315,52 +294,38 @@ Expected Tracer::extract_span(const DictReader& reader) { Expected Tracer::extract_span(const DictReader& reader, const SpanConfig& config) { - assert(extraction_styles_.datadog || extraction_styles_.b3); + assert(!extraction_styles_.empty()); - Optional extracted_data; - const char* extracted_by; + ExtractedData extracted_data; - if (extraction_styles_.datadog) { - DatadogExtractionPolicy extract; - auto data = extract_data(extract, reader); - if (auto* error = data.if_error()) { - return std::move(*error); + for (const auto style : extraction_styles_) { + DatadogExtractionPolicy extract_datadog; + B3ExtractionPolicy extract_b3; + ExtractionPolicy* extract; + switch (style) { + case PropagationStyle::DATADOG: + extract = &extract_datadog; + break; + case PropagationStyle::B3: + extract = &extract_b3; + break; + default: + assert(style == PropagationStyle::NONE); + extracted_data = ExtractedData{}; + continue; } - extracted_data = *data; - extracted_by = "Datadog"; - } - - if (extraction_styles_.b3) { - B3ExtractionPolicy extract; - auto data = extract_data(extract, reader); + auto data = extract_data(*extract, reader); if (auto* error = data.if_error()) { return std::move(*error); } - if (extracted_data && *data != *extracted_data) { - std::string message; - message += "B3 extracted different data than did "; - message += extracted_by; - message += ". B3 extracted "; - message += to_json(*data).dump(); - message += " while previously "; - message += extracted_by; - message += " extracted "; - message += to_json(*extracted_data).dump(); - message += '.'; - return Error{Error::INCONSISTENT_EXTRACTION_STYLES, std::move(message)}; - } extracted_data = *data; - extracted_by = "B3"; - } - - if (extraction_styles_.none && !extracted_data) { - extracted_data.emplace(); - extracted_by = "none"; + if (extracted_data.trace_id) { + break; + } } - assert(extracted_data); auto& [trace_id, parent_id, origin, trace_tags, sampling_priority] = - *extracted_data; + extracted_data; // Some information might be missing. // Here are the combinations considered: diff --git a/src/datadog/tracer.h b/src/datadog/tracer.h index d3a6f0ae..b894c791 100644 --- a/src/datadog/tracer.h +++ b/src/datadog/tracer.h @@ -34,8 +34,8 @@ class Tracer { IDGenerator generator_; Clock clock_; std::shared_ptr defaults_; - PropagationStyles injection_styles_; - PropagationStyles extraction_styles_; + std::vector injection_styles_; + std::vector extraction_styles_; Optional hostname_; std::size_t tags_header_max_size_; diff --git a/src/datadog/tracer_config.cpp b/src/datadog/tracer_config.cpp index 2ba0a57d..90617650 100644 --- a/src/datadog/tracer_config.cpp +++ b/src/datadog/tracer_config.cpp @@ -1,6 +1,7 @@ #include "tracer_config.h" #include +#include #include #include #include @@ -68,19 +69,37 @@ std::vector parse_list(StringView input) { return items; } -Expected parse_propagation_styles(StringView input) { - PropagationStyles styles{false, false}; +Expected> parse_propagation_styles( + StringView input) { + std::vector styles; + + const auto last_is_duplicate = [&]() -> Optional { + assert(!styles.empty()); + + const auto dupe = + std::find(styles.begin(), styles.end() - 1, styles.back()); + if (dupe == styles.end()) { + return nullopt; // no duplicate + } + + std::string message; + message += "The propagation style "; + message += to_json(styles.back()).dump(); + message += " is duplicated in: "; + append(message, input); + return Error{Error::DUPLICATE_PROPAGATION_STYLE, std::move(message)}; + }; // Style names are separated by spaces, or a comma, or some combination. for (const StringView &item : parse_list(input)) { auto token = std::string(item); to_lower(token); if (token == "datadog") { - styles.datadog = true; + styles.push_back(PropagationStyle::DATADOG); } else if (token == "b3" || token == "b3multi") { - styles.b3 = true; + styles.push_back(PropagationStyle::B3); } else if (token == "none") { - styles.none = true; + styles.push_back(PropagationStyle::NONE); } else { std::string message; message += "Unsupported propagation style \""; @@ -90,6 +109,10 @@ Expected parse_propagation_styles(StringView input) { message += "\". The following styles are supported: Datadog, B3."; return Error{Error::UNKNOWN_PROPAGATION_STYLE, std::move(message)}; } + + if (auto maybe_error = last_is_duplicate()) { + return *maybe_error; + } } return styles; @@ -122,10 +145,11 @@ Expected> parse_tags( return tags; } -// Return a `PropagationStyles` parsed from the specified `env_var`. -// If `env_var` is not in the environment, return `nullopt`. -// If an error occurs, throw an `Error`. -Optional styles_from_env(environment::Variable env_var) { +// Return a `std::vector` parsed from the specified `env_var`. +// If `env_var` is not in the environment, return `nullopt`. If an error occurs, +// throw an `Error`. +Optional> styles_from_env( + environment::Variable env_var) { const auto styles_env = lookup(env_var); if (!styles_env) { return {}; @@ -236,13 +260,11 @@ Expected finalize_propagation_styles(FinalizedTracerConfig &result, return std::move(error); } - if (!result.extraction_styles.datadog && !result.extraction_styles.b3 && - !result.extraction_styles.none) { + if (result.extraction_styles.empty()) { return Error{Error::MISSING_SPAN_EXTRACTION_STYLE, "At least one extraction style must be specified."}; } - if (!result.injection_styles.datadog && !result.injection_styles.b3 && - !result.injection_styles.none) { + if (result.injection_styles.empty()) { return Error{Error::MISSING_SPAN_INJECTION_STYLE, "At least one injection style must be specified."}; } diff --git a/src/datadog/tracer_config.h b/src/datadog/tracer_config.h index 80f41617..f89d38f6 100644 --- a/src/datadog/tracer_config.h +++ b/src/datadog/tracer_config.h @@ -7,11 +7,12 @@ #include #include #include +#include #include "datadog_agent_config.h" #include "error.h" #include "expected.h" -#include "propagation_styles.h" +#include "propagation_style.h" #include "span_defaults.h" #include "span_sampler_config.h" #include "trace_sampler_config.h" @@ -59,16 +60,20 @@ struct TracerConfig { // `injection_styles` indicates with which tracing systems trace propagation // will be compatible when injecting (sending) trace context. + // All styles indicated by `injection_styles` are used for injection. // `injection_styles` is overridden by the `DD_TRACE_PROPAGATION_STYLE_INJECT` // and `DD_TRACE_PROPAGATION_STYLE` environment variables. - PropagationStyles injection_styles; + std::vector injection_styles; // `extraction_styles` indicates with which tracing systems trace propagation // will be compatible when extracting (receiving) trace context. + // Extraction styles are applied in the order in which they appear in + // `extraction_styles`. The first style that produces trace context or + // produces an error determines the result of extraction. // `extraction_styles` is overridden by the // `DD_TRACE_PROPAGATION_STYLE_EXTRACT` and `DD_TRACE_PROPAGATION_STYLE` // environment variables. - PropagationStyles extraction_styles; + std::vector extraction_styles; // `report_hostname` indicates whether the tracer will include the result of // `gethostname` with traces sent to the collector. @@ -110,8 +115,8 @@ class FinalizedTracerConfig { FinalizedTraceSamplerConfig trace_sampler; FinalizedSpanSamplerConfig span_sampler; - PropagationStyles injection_styles; - PropagationStyles extraction_styles; + std::vector injection_styles; + std::vector extraction_styles; bool report_hostname; std::size_t tags_header_size; diff --git a/test/tracer_config.cpp b/test/tracer_config.cpp index ba4d3bda..76da8ec5 100644 --- a/test/tracer_config.cpp +++ b/test/tracer_config.cpp @@ -1,6 +1,6 @@ #include #include -#include +#include #include #include #include @@ -31,7 +31,7 @@ namespace datadog { namespace tracing { std::ostream& operator<<(std::ostream& stream, - const PropagationStyles& styles) { + const std::vector& styles) { stream << '{'; const char* separator = ""; if (styles.datadog) { @@ -1053,7 +1053,8 @@ TEST_CASE("TracerConfig propagation styles") { int line; std::string env_value; Optional expected_error; - PropagationStyles expected_styles = PropagationStyles{}; + std::vector expected_styles = + std::vector{}; }; // clang-format off From 77723e4d7797d05fe9de771a2e8198dbefd5c51f Mon Sep 17 00:00:00 2001 From: David Goffredo Date: Fri, 16 Dec 2022 16:14:12 -0500 Subject: [PATCH 07/11] existing tests now compiling and passing again --- src/datadog/tracer_config.cpp | 2 +- src/datadog/tracer_config.h | 4 +- test/span.cpp | 8 +- test/test.h | 19 +++++ test/tracer.cpp | 141 +++++++--------------------------- test/tracer_config.cpp | 124 +++++++++++++----------------- 6 files changed, 105 insertions(+), 193 deletions(-) diff --git a/src/datadog/tracer_config.cpp b/src/datadog/tracer_config.cpp index 90617650..814bbef3 100644 --- a/src/datadog/tracer_config.cpp +++ b/src/datadog/tracer_config.cpp @@ -78,7 +78,7 @@ Expected> parse_propagation_styles( const auto dupe = std::find(styles.begin(), styles.end() - 1, styles.back()); - if (dupe == styles.end()) { + if (dupe == styles.end() - 1) { return nullopt; // no duplicate } diff --git a/src/datadog/tracer_config.h b/src/datadog/tracer_config.h index f89d38f6..2916aec0 100644 --- a/src/datadog/tracer_config.h +++ b/src/datadog/tracer_config.h @@ -63,7 +63,7 @@ struct TracerConfig { // All styles indicated by `injection_styles` are used for injection. // `injection_styles` is overridden by the `DD_TRACE_PROPAGATION_STYLE_INJECT` // and `DD_TRACE_PROPAGATION_STYLE` environment variables. - std::vector injection_styles; + std::vector injection_styles = {PropagationStyle::DATADOG}; // `extraction_styles` indicates with which tracing systems trace propagation // will be compatible when extracting (receiving) trace context. @@ -73,7 +73,7 @@ struct TracerConfig { // `extraction_styles` is overridden by the // `DD_TRACE_PROPAGATION_STYLE_EXTRACT` and `DD_TRACE_PROPAGATION_STYLE` // environment variables. - std::vector extraction_styles; + std::vector extraction_styles = {PropagationStyle::DATADOG}; // `report_hostname` indicates whether the tracer will include the result of // `gethostname` with traces sent to the collector. diff --git a/test/span.cpp b/test/span.cpp index a671ed72..b976b2de 100644 --- a/test/span.cpp +++ b/test/span.cpp @@ -375,9 +375,7 @@ TEST_CASE("injection") { config.defaults.service = "testsvc"; config.collector = std::make_shared(); config.logger = std::make_shared(); - config.injection_styles.datadog = true; - config.injection_styles.b3 = true; - config.injection_styles.none = false; + config.injection_styles = {PropagationStyle::DATADOG, PropagationStyle::B3}; auto finalized_config = finalize_config(config); REQUIRE(finalized_config); @@ -455,9 +453,7 @@ TEST_CASE("injection can be disabled using the \"none\" style") { config.defaults.name = "spanny"; config.collector = std::make_shared(); config.logger = std::make_shared(); - config.injection_styles.datadog = false; - config.injection_styles.b3 = false; - config.injection_styles.none = true; // this one + config.injection_styles = {PropagationStyle::NONE}; const auto finalized_config = finalize_config(config); REQUIRE(finalized_config); diff --git a/test/test.h b/test/test.h index 70a7078d..0c389815 100644 --- a/test/test.h +++ b/test/test.h @@ -1,9 +1,13 @@ +#pragma once + #define CATCH_CONFIG_CPP17_UNCAUGHT_EXCEPTIONS #define CATCH_CONFIG_CPP17_STRING_VIEW #define CATCH_CONFIG_CPP17_VARIANT #define CATCH_CONFIG_CPP17_OPTIONAL #define CATCH_CONFIG_CPP17_BYTE +#include + #include #include #include @@ -16,3 +20,18 @@ std::ostream& operator<<(std::ostream& stream, const std::pair& item); } // namespace std + +namespace datadog { +namespace tracing { + +template +std::ostream& operator<<(std::ostream& stream, + const Expected& expected) { + if (expected) { + return stream << "?"; // don't know in general + } + return stream << expected.error(); +} + +} // namespace tracing +} // namespace datadog diff --git a/test/tracer.cpp b/test/tracer.cpp index 63135ae0..6f0d7649 100644 --- a/test/tracer.cpp +++ b/test/tracer.cpp @@ -259,155 +259,82 @@ TEST_CASE("span extraction") { SECTION("extraction failures") { struct TestCase { std::string name; - bool extract_datadog; - bool extract_b3; + std::vector extraction_styles; std::unordered_map headers; // Null means "don't expect an error." Optional expected_error; }; auto test_case = GENERATE(values({ - {"no span", true, false, {}, Error::NO_SPAN_TO_EXTRACT}, + {"no span", {PropagationStyle::DATADOG}, {}, Error::NO_SPAN_TO_EXTRACT}, {"missing trace ID", - true, - false, + {PropagationStyle::DATADOG}, {{"x-datadog-parent-id", "456"}}, Error::MISSING_TRACE_ID}, {"missing parent span ID", - true, - false, + {PropagationStyle::DATADOG}, {{"x-datadog-trace-id", "123"}}, Error::MISSING_PARENT_SPAN_ID}, {"missing parent span ID, but it's ok because origin", - true, - false, + {PropagationStyle::DATADOG}, {{"x-datadog-trace-id", "123"}, {"x-datadog-origin", "anything"}}, nullopt}, - {"datadog and B3 agree", - true, - true, - {{"x-datadog-trace-id", "15"}, - {"x-b3-traceid", "f"}, - {"x-datadog-parent-id", "14"}, - {"x-b3-spanid", "e"}}, - nullopt}, - {"datadog and B3 disagree on trace ID", - true, - true, - {{"x-datadog-trace-id", "15"}, - {"x-b3-traceid", "f0"}, - {"x-datadog-parent-id", "14"}, - {"x-b3-spanid", "e"}}, - Error::INCONSISTENT_EXTRACTION_STYLES}, - {"datadog and B3 disagree on trace ID (2)", - true, - true, - {{"x-datadog-trace-id", "15"}, - {"x-datadog-parent-id", "14"}, - {"x-b3-spanid", "e"}}, - Error::INCONSISTENT_EXTRACTION_STYLES}, - {"datadog and B3 disagree on parent ID", - true, - true, - {{"x-datadog-trace-id", "15"}, - {"x-b3-traceid", "f"}, - {"x-datadog-parent-id", "13"}, - {"x-b3-spanid", "e"}}, - Error::INCONSISTENT_EXTRACTION_STYLES}, - {"datadog and B3 disagree on parent ID (2)", - true, - true, - {{"x-datadog-trace-id", "15"}, - {"x-b3-traceid", "f"}, - {"x-datadog-parent-id", "13"}}, - Error::INCONSISTENT_EXTRACTION_STYLES}, - {"datadog and B3 disagree on sampling priority", - true, - true, - {{"x-datadog-trace-id", "15"}, - {"x-b3-traceid", "f"}, - {"x-datadog-parent-id", "14"}, - {"x-b3-spanid", "e"}, - {"x-datadog-sampling-priority", "2"}, - {"x-b3-sampled", "1"}}, - Error::INCONSISTENT_EXTRACTION_STYLES}, - {"datadog and B3 disagree on sampling priority (2)", - true, - true, - {{"x-datadog-trace-id", "15"}, - {"x-b3-traceid", "f"}, - {"x-datadog-parent-id", "14"}, - {"x-b3-spanid", "e"}, - {"x-datadog-sampling-priority", "2"}}, - Error::INCONSISTENT_EXTRACTION_STYLES}, {"bad x-datadog-trace-id", - true, - false, + {PropagationStyle::DATADOG}, {{"x-datadog-trace-id", "f"}, {"x-datadog-parent-id", "456"}}, Error::INVALID_INTEGER}, {"bad x-datadog-trace-id (2)", - true, - false, + {PropagationStyle::DATADOG}, {{"x-datadog-trace-id", "99999999999999999999999999"}, {"x-datadog-parent-id", "456"}}, Error::OUT_OF_RANGE_INTEGER}, {"bad x-datadog-parent-id", - true, - false, + {PropagationStyle::DATADOG}, {{"x-datadog-parent-id", "f"}, {"x-datadog-trace-id", "456"}}, Error::INVALID_INTEGER}, {"bad x-datadog-parent-id (2)", - true, - false, + {PropagationStyle::DATADOG}, {{"x-datadog-parent-id", "99999999999999999999999999"}, {"x-datadog-trace-id", "456"}}, Error::OUT_OF_RANGE_INTEGER}, {"bad x-datadog-sampling-priority", - true, - false, + {PropagationStyle::DATADOG}, {{"x-datadog-parent-id", "123"}, {"x-datadog-trace-id", "456"}, {"x-datadog-sampling-priority", "keep"}}, Error::INVALID_INTEGER}, {"bad x-datadog-sampling-priority (2)", - true, - false, + {PropagationStyle::DATADOG}, {{"x-datadog-parent-id", "123"}, {"x-datadog-trace-id", "456"}, {"x-datadog-sampling-priority", "99999999999999999999999999"}}, Error::OUT_OF_RANGE_INTEGER}, {"bad x-b3-traceid", - false, - true, + {PropagationStyle::B3}, {{"x-b3-traceid", "0xdeadbeef"}, {"x-b3-spanid", "def"}}, Error::INVALID_INTEGER}, {"bad x-b3-traceid (2)", - false, - true, + {PropagationStyle::B3}, {{"x-b3-traceid", "ffffffffffffffffffffffffffffff"}, {"x-b3-spanid", "def"}}, Error::OUT_OF_RANGE_INTEGER}, {"bad x-b3-spanid", - false, - true, + {PropagationStyle::B3}, {{"x-b3-spanid", "0xdeadbeef"}, {"x-b3-traceid", "def"}}, Error::INVALID_INTEGER}, {"bad x-b3-spanid (2)", - false, - true, + {PropagationStyle::B3}, {{"x-b3-spanid", "ffffffffffffffffffffffffffffff"}, {"x-b3-traceid", "def"}}, Error::OUT_OF_RANGE_INTEGER}, {"bad x-b3-sampled", - false, - true, + {PropagationStyle::B3}, {{"x-b3-traceid", "abc"}, {"x-b3-spanid", "def"}, {"x-b3-sampled", "true"}}, Error::INVALID_INTEGER}, {"bad x-b3-sampled (2)", - false, - true, + {PropagationStyle::B3}, {{"x-b3-traceid", "abc"}, {"x-b3-spanid", "def"}, {"x-b3-sampled", "99999999999999999999999999"}}, @@ -416,8 +343,7 @@ TEST_CASE("span extraction") { CAPTURE(test_case.name); - config.extraction_styles.datadog = test_case.extract_datadog; - config.extraction_styles.b3 = test_case.extract_b3; + config.extraction_styles = test_case.extraction_styles; auto finalized_config = finalize_config(config); REQUIRE(finalized_config); Tracer tracer{*finalized_config}; @@ -449,8 +375,7 @@ TEST_CASE("span extraction") { SECTION("extracted span has the expected properties") { struct TestCase { std::string name; - bool extract_datadog; - bool extract_b3; + std::vector extraction_styles; std::unordered_map headers; std::uint64_t expected_trace_id; Optional expected_parent_id; @@ -459,8 +384,7 @@ TEST_CASE("span extraction") { auto test_case = GENERATE(values({ {"datadog style", - true, - false, + {PropagationStyle::DATADOG}, {{"x-datadog-trace-id", "123"}, {"x-datadog-parent-id", "456"}, {"x-datadog-sampling-priority", "2"}}, @@ -468,22 +392,19 @@ TEST_CASE("span extraction") { 456, 2}, {"datadog style without sampling priority", - true, - false, + {PropagationStyle::DATADOG}, {{"x-datadog-trace-id", "123"}, {"x-datadog-parent-id", "456"}}, 123, 456, nullopt}, {"datadog style without sampling priority and without parent ID", - true, - false, + {PropagationStyle::DATADOG}, {{"x-datadog-trace-id", "123"}, {"x-datadog-origin", "whatever"}}, 123, nullopt, nullopt}, {"B3 style", - false, - true, + {PropagationStyle::B3}, {{"x-b3-traceid", "abc"}, {"x-b3-spanid", "def"}, {"x-b3-sampled", "0"}}, @@ -491,15 +412,13 @@ TEST_CASE("span extraction") { 0xdef, 0}, {"B3 style without sampling priority", - false, - true, + {PropagationStyle::B3}, {{"x-b3-traceid", "abc"}, {"x-b3-spanid", "def"}}, 0xabc, 0xdef, nullopt}, {"Datadog and B3 style together", - true, - true, + {PropagationStyle::DATADOG, PropagationStyle::B3}, {{"x-datadog-trace-id", "255"}, {"x-datadog-parent-id", "14"}, {"x-datadog-sampling-priority", "0"}, @@ -510,8 +429,7 @@ TEST_CASE("span extraction") { 14, 0}, {"Datadog and B3 style together without sampling priority", - true, - true, + {PropagationStyle::DATADOG, PropagationStyle::B3}, {{"x-datadog-trace-id", "255"}, {"x-datadog-parent-id", "14"}, {"x-b3-traceid", "ff"}, @@ -523,8 +441,7 @@ TEST_CASE("span extraction") { CAPTURE(test_case.name); - config.extraction_styles.datadog = test_case.extract_datadog; - config.extraction_styles.b3 = test_case.extract_b3; + config.extraction_styles = test_case.extraction_styles; auto finalized_config = finalize_config(config); REQUIRE(finalized_config); Tracer tracer{*finalized_config}; @@ -553,9 +470,7 @@ TEST_CASE("span extraction") { } SECTION("extraction can be disabled using the \"none\" style") { - config.extraction_styles.datadog = false; - config.extraction_styles.b3 = false; - config.extraction_styles.none = true; // this one + config.extraction_styles = {PropagationStyle::NONE}; const auto finalized_config = finalize_config(config); REQUIRE(finalized_config); diff --git a/test/tracer_config.cpp b/test/tracer_config.cpp index 76da8ec5..27e4bb85 100644 --- a/test/tracer_config.cpp +++ b/test/tracer_config.cpp @@ -30,19 +30,8 @@ namespace datadog { namespace tracing { -std::ostream& operator<<(std::ostream& stream, - const std::vector& styles) { - stream << '{'; - const char* separator = ""; - if (styles.datadog) { - stream << "Datadog"; - separator = ", "; - } - if (styles.b3) { - stream << separator << "B3"; - separator = ", "; - } - return stream << '}'; +std::ostream& operator<<(std::ostream& stream, PropagationStyle style) { + return stream << to_json(style).dump(); } } // namespace tracing @@ -991,26 +980,24 @@ TEST_CASE("TracerConfig propagation styles") { auto finalized = finalize_config(config); REQUIRE(finalized); - REQUIRE(!finalized->injection_styles.datadog); - REQUIRE(finalized->injection_styles.b3); - REQUIRE(!finalized->injection_styles.none); + const std::vector expected_styles = { + PropagationStyle::B3}; - REQUIRE(!finalized->extraction_styles.datadog); - REQUIRE(finalized->extraction_styles.b3); - REQUIRE(!finalized->extraction_styles.none); + REQUIRE(finalized->injection_styles == expected_styles); + REQUIRE(finalized->extraction_styles == expected_styles); } SECTION("injection_styles") { SECTION("defaults to just Datadog") { auto finalized = finalize_config(config); REQUIRE(finalized); - REQUIRE(finalized->injection_styles.datadog); - REQUIRE(!finalized->injection_styles.b3); + const std::vector expected_styles = { + PropagationStyle::DATADOG}; + REQUIRE(finalized->injection_styles == expected_styles); } SECTION("need at least one") { - config.injection_styles.datadog = false; - config.injection_styles.b3 = false; + config.injection_styles.clear(); auto finalized = finalize_config(config); REQUIRE(!finalized); REQUIRE(finalized.error().code == Error::MISSING_SPAN_INJECTION_STYLE); @@ -1021,9 +1008,9 @@ TEST_CASE("TracerConfig propagation styles") { const EnvGuard guard{"DD_TRACE_PROPAGATION_STYLE_INJECT", "B3"}; auto finalized = finalize_config(config); REQUIRE(finalized); - REQUIRE(!finalized->injection_styles.datadog); - REQUIRE(finalized->injection_styles.b3); - REQUIRE(!finalized->injection_styles.none); + const std::vector expected_styles = { + PropagationStyle::B3}; + REQUIRE(finalized->injection_styles == expected_styles); } SECTION("overrides DD_PROPAGATION_STYLE_INJECT") { @@ -1032,9 +1019,9 @@ TEST_CASE("TracerConfig propagation styles") { config.logger = std::make_shared(); // suppress warning auto finalized = finalize_config(config); REQUIRE(finalized); - REQUIRE(!finalized->injection_styles.datadog); - REQUIRE(finalized->injection_styles.b3); - REQUIRE(!finalized->injection_styles.none); + const std::vector expected_styles = { + PropagationStyle::B3}; + REQUIRE(finalized->injection_styles == expected_styles); } SECTION("overrides DD_TRACE_PROPAGATION_STYLE") { @@ -1043,9 +1030,9 @@ TEST_CASE("TracerConfig propagation styles") { config.logger = std::make_shared(); // suppress warning auto finalized = finalize_config(config); REQUIRE(finalized); - REQUIRE(!finalized->injection_styles.datadog); - REQUIRE(finalized->injection_styles.b3); - REQUIRE(!finalized->injection_styles.none); + const std::vector expected_styles = { + PropagationStyle::B3}; + REQUIRE(finalized->injection_styles == expected_styles); } SECTION("parsing") { @@ -1053,30 +1040,32 @@ TEST_CASE("TracerConfig propagation styles") { int line; std::string env_value; Optional expected_error; - std::vector expected_styles = - std::vector{}; + std::vector expected_styles = {}; }; + // brevity + const auto datadog = PropagationStyle::DATADOG, + b3 = PropagationStyle::B3, none = PropagationStyle::NONE; // clang-format off auto test_case = GENERATE(values({ - {__LINE__, "Datadog", x, {true, false, false}}, - {__LINE__, "DaTaDoG", x, {true, false, false}}, - {__LINE__, "B3", x, {false, true, false}}, - {__LINE__, "b3", x, {false, true, false}}, - {__LINE__, "b3MULTI", x, {false, true, false}}, - {__LINE__, "b3, b3multi", x, {false, true, false}}, - {__LINE__, "Datadog B3", x, {true, true, false}}, - {__LINE__, "Datadog B3 none", x, {true, true, true}}, - {__LINE__, "NONE", x, {false, false, true}}, - {__LINE__, "B3 Datadog", x, {true, true, false}}, - {__LINE__, "b3 datadog", x, {true, true, false}}, - {__LINE__, "b3, datadog", x, {true, true, false}}, - {__LINE__, "b3,datadog", x, {true, true, false}}, - {__LINE__, "b3, datadog", x, {true, true, false}}, + {__LINE__, "Datadog", x, {datadog}}, + {__LINE__, "DaTaDoG", x, {datadog}}, + {__LINE__, "B3", x, {b3}}, + {__LINE__, "b3", x, {b3}}, + {__LINE__, "b3MULTI", x, {b3}}, + {__LINE__, "b3, b3multi", Error::DUPLICATE_PROPAGATION_STYLE }, + {__LINE__, "Datadog B3", x, {datadog, b3}}, + {__LINE__, "Datadog B3 none", x, {datadog, b3, none}}, + {__LINE__, "NONE", x, {none}}, + {__LINE__, "B3 Datadog", x, {b3, datadog}}, + {__LINE__, "b3 datadog", x, {b3, datadog}}, + {__LINE__, "b3, datadog", x, {b3, datadog}}, + {__LINE__, "b3,datadog", x, {b3, datadog}}, + {__LINE__, "b3, datadog", x, {b3, datadog}}, {__LINE__, "b3,,datadog", Error::UNKNOWN_PROPAGATION_STYLE}, {__LINE__, "b3,datadog,w3c", Error::UNKNOWN_PROPAGATION_STYLE}, - {__LINE__, "b3,datadog,datadog", x, {true, true, false}}, - {__LINE__, " b3 b3 b3, b3 , b3, b3, b3 , b3 b3 b3 ", x, {false, true, false}}, + {__LINE__, "b3,datadog,datadog", Error::DUPLICATE_PROPAGATION_STYLE}, + {__LINE__, " b3 b3 b3, b3 , b3, b3, b3 , b3 b3 b3 ", Error::DUPLICATE_PROPAGATION_STYLE}, })); // clang-format on @@ -1091,12 +1080,7 @@ TEST_CASE("TracerConfig propagation styles") { REQUIRE(finalized.error().code == *test_case.expected_error); } else { REQUIRE(finalized); - REQUIRE(finalized->injection_styles.datadog == - test_case.expected_styles.datadog); - REQUIRE(finalized->injection_styles.b3 == - test_case.expected_styles.b3); - REQUIRE(finalized->injection_styles.none == - test_case.expected_styles.none); + REQUIRE(finalized->injection_styles == test_case.expected_styles); } } } @@ -1107,15 +1091,13 @@ TEST_CASE("TracerConfig propagation styles") { SECTION("defaults to just Datadog") { auto finalized = finalize_config(config); REQUIRE(finalized); - REQUIRE(finalized->extraction_styles.datadog); - REQUIRE(!finalized->extraction_styles.b3); - REQUIRE(!finalized->extraction_styles.none); + const std::vector expected_styles = { + PropagationStyle::DATADOG}; + REQUIRE(finalized->extraction_styles == expected_styles); } SECTION("need at least one") { - config.extraction_styles.datadog = false; - config.extraction_styles.b3 = false; - config.extraction_styles.none = false; + config.extraction_styles.clear(); auto finalized = finalize_config(config); REQUIRE(!finalized); REQUIRE(finalized.error().code == Error::MISSING_SPAN_EXTRACTION_STYLE); @@ -1126,9 +1108,9 @@ TEST_CASE("TracerConfig propagation styles") { const EnvGuard guard{"DD_TRACE_PROPAGATION_STYLE_EXTRACT", "B3"}; auto finalized = finalize_config(config); REQUIRE(finalized); - REQUIRE(!finalized->extraction_styles.datadog); - REQUIRE(finalized->extraction_styles.b3); - REQUIRE(!finalized->extraction_styles.none); + const std::vector expected_styles = { + PropagationStyle::B3}; + REQUIRE(finalized->extraction_styles == expected_styles); } SECTION("overrides DD_PROPAGATION_STYLE_EXTRACT") { @@ -1137,9 +1119,9 @@ TEST_CASE("TracerConfig propagation styles") { config.logger = std::make_shared(); // suppress warning auto finalized = finalize_config(config); REQUIRE(finalized); - REQUIRE(!finalized->extraction_styles.datadog); - REQUIRE(finalized->extraction_styles.b3); - REQUIRE(!finalized->extraction_styles.none); + const std::vector expected_styles = { + PropagationStyle::B3}; + REQUIRE(finalized->extraction_styles == expected_styles); } SECTION("overrides DD_TRACE_PROPAGATION_STYLE") { @@ -1148,9 +1130,9 @@ TEST_CASE("TracerConfig propagation styles") { config.logger = std::make_shared(); // suppress warning auto finalized = finalize_config(config); REQUIRE(finalized); - REQUIRE(!finalized->extraction_styles.datadog); - REQUIRE(finalized->extraction_styles.b3); - REQUIRE(!finalized->extraction_styles.none); + const std::vector expected_styles = { + PropagationStyle::B3}; + REQUIRE(finalized->extraction_styles == expected_styles); } // It's the same as for injection styles, so let's omit most of the From d501fbe67b46c4c31e6ec4363ec612db14ec531c Mon Sep 17 00:00:00 2001 From: David Goffredo Date: Fri, 16 Dec 2022 16:47:35 -0500 Subject: [PATCH 08/11] test extract style priority --- test/tracer.cpp | 24 ++++++++++++++++++------ 1 file changed, 18 insertions(+), 6 deletions(-) diff --git a/test/tracer.cpp b/test/tracer.cpp index 6f0d7649..9f0ebdc7 100644 --- a/test/tracer.cpp +++ b/test/tracer.cpp @@ -417,26 +417,38 @@ TEST_CASE("span extraction") { 0xabc, 0xdef, nullopt}, - {"Datadog and B3 style together", + {"Datadog overriding B3", {PropagationStyle::DATADOG, PropagationStyle::B3}, {{"x-datadog-trace-id", "255"}, {"x-datadog-parent-id", "14"}, {"x-datadog-sampling-priority", "0"}, - {"x-b3-traceid", "ff"}, - {"x-b3-spanid", "e"}, + {"x-b3-traceid", "fff"}, + {"x-b3-spanid", "ef"}, {"x-b3-sampled", "0"}}, 255, 14, 0}, - {"Datadog and B3 style together without sampling priority", + {"Datadog overriding B3, without sampling priority", {PropagationStyle::DATADOG, PropagationStyle::B3}, {{"x-datadog-trace-id", "255"}, {"x-datadog-parent-id", "14"}, - {"x-b3-traceid", "ff"}, - {"x-b3-spanid", "e"}}, + {"x-b3-traceid", "fff"}, + {"x-b3-spanid", "ef"}}, 255, 14, nullopt}, + {"B3 after Datadog found no context", + {PropagationStyle::DATADOG, PropagationStyle::B3}, + {{"x-b3-traceid", "ff"}, {"x-b3-spanid", "e"}}, + 0xff, + 0xe, + nullopt}, + {"Datadog after B3 found no context", + {PropagationStyle::B3, PropagationStyle::DATADOG}, + {{"x-b3-traceid", "fff"}, {"x-b3-spanid", "ef"}}, + 0xfff, + 0xef, + nullopt}, })); CAPTURE(test_case.name); From 6cd77b35e6242d800be5f5b5602ff4a6796021ab Mon Sep 17 00:00:00 2001 From: David Goffredo Date: Fri, 16 Dec 2022 16:49:09 -0500 Subject: [PATCH 09/11] update include graph --- doc/includes.dot | 657 +++++----- doc/includes.svg | 3254 +++++++++++++++++++++++++--------------------- 2 files changed, 2127 insertions(+), 1784 deletions(-) diff --git a/doc/includes.dot b/doc/includes.dot index c609a655..1725ee7f 100644 --- a/doc/includes.dot +++ b/doc/includes.dot @@ -1,318 +1,367 @@ digraph G { - node0 [label="threaded_event_scheduler.cpp"]; - node1 [label="rate.cpp"]; - node2 [label="span_data.cpp"]; + node0 [label="rate.cpp"]; + node1 [label="span_data.cpp"]; + node2 [label="threaded_event_scheduler.cpp"]; node3 [label="default_http_client_null.cpp"]; node4 [label="trace_segment.h"]; - node5 [label="dict_writer.h"]; - node6 [label="tag_propagation.cpp"]; + node5 [label="tag_propagation.cpp"]; + node6 [label="dict_writer.h"]; node7 [label="json.hpp"]; - node8 [label="span_sampler.h"]; - node9 [label="dict_reader.cpp"]; - node10 [label="tracer_config.h"]; + node8 [label="string_view.h"]; + node9 [label="span_sampler.h"]; + node10 [label="dict_reader.cpp"]; node11 [label="tags.h"]; - node12 [label="curl/curl.h"]; - node13 [label="expected.h"]; - node14 [label="limiter.h"]; - node15 [label="span.h"]; - node16 [label="sampling_mechanism.cpp"]; - node17 [label="logger.cpp"]; - node18 [label="rate.h"]; - node19 [label="sampling_util.h"]; - node20 [label="span_data.h"]; - node21 [label="datadog_agent_config.h"]; - node22 [label="sampling_decision.h"]; - node23 [label="sampling_mechanism.h"]; - node24 [label="msgpack.cpp"]; - node25 [label="default_http_client.h"]; - node26 [label="datadog_agent_config.cpp"]; - node27 [label="sampling_util.cpp"]; - node28 [label="event_scheduler.cpp"]; - node29 [label="span.cpp"]; - node30 [label="json_fwd.hpp"]; - node31 [label="datadog_agent.h"]; - node32 [label="error.h"]; - node33 [label="event_scheduler.h"]; - node34 [label="tag_propagation.h"]; - node35 [label="logger.h"]; - node36 [label="clock.h"]; - node37 [label="span_defaults.h"]; - node38 [label="curl.h"]; - node39 [label="span_defaults.cpp"]; - node40 [label="threaded_event_scheduler.h"]; - node41 [label="tracer.h"]; - node42 [label="parse_util.h"]; - node43 [label="expected.cpp"]; - node44 [label="collector.cpp"]; - node45 [label="id_generator.cpp"]; - node46 [label="trace_sampler.cpp"]; - node47 [label="sampling_decision.cpp"]; - node48 [label="sampling_priority.cpp"]; - node49 [label="span_sampler.cpp"]; - node50 [label="collector.h"]; - node51 [label="curl.cpp"]; - node52 [label="collector_response.h"]; - node53 [label="cerr_logger.cpp"]; - node54 [label="null_collector.cpp"]; - node55 [label="msgpack.h"]; - node56 [label="trace_sampler.h"]; - node57 [label="span_config.cpp"]; - node58 [label="dict_writer.cpp"]; - node59 [label="trace_sampler_config.cpp"]; - node60 [label="environment.h"]; - node61 [label="span_config.h"]; - node62 [label="datadog_agent.cpp"]; - node63 [label="winsock.h"]; - node64 [label="id_generator.h"]; - node65 [label="environment.cpp"]; - node66 [label="tracer_config.cpp"]; - node67 [label="net_util.cpp"]; - node68 [label="parse_util.cpp"]; - node69 [label="http_client.cpp"]; - node70 [label="charconv"]; - node71 [label="null_collector.h"]; - node72 [label="version.h"]; - node73 [label="version.cpp"]; - node74 [label="span_matcher.h"]; - node75 [label="span_sampler_config.h"]; - node76 [label="propagation_style.cpp"]; - node77 [label="dict_reader.h"]; - node78 [label="span_matcher.cpp"]; - node79 [label="default_http_client_curl.cpp"]; - node80 [label="tracer.cpp"]; - node81 [label="http_client.h"]; - node82 [label="clock.cpp"]; - node83 [label="collector_response.cpp"]; - node84 [label="sampling_priority.h"]; - node85 [label="propagation_style.h"]; - node86 [label="limiter.cpp"]; - node87 [label="net_util.h"]; - node88 [label="error.cpp"]; - node89 [label="trace_sampler_config.h"]; - node90 [label="cerr_logger.h"]; - node91 [label="tags.cpp"]; - node92 [label="trace_segment.cpp"]; - node93 [label="span_sampler_config.cpp"]; + node12 [label="tracer_config.h"]; + node13 [label="curl/curl.h"]; + node14 [label="expected.h"]; + node15 [label="limiter.h"]; + node16 [label="optional.cpp"]; + node17 [label="span.h"]; + node18 [label="sampling_mechanism.cpp"]; + node19 [label="logger.cpp"]; + node20 [label="rate.h"]; + node21 [label="sampling_util.h"]; + node22 [label="string_view.cpp"]; + node23 [label="sampling_decision.h"]; + node24 [label="span_data.h"]; + node25 [label="datadog_agent_config.h"]; + node26 [label="sampling_mechanism.h"]; + node27 [label="glob.h"]; + node28 [label="msgpack.cpp"]; + node29 [label="absl/types/optional.h"]; + node30 [label="default_http_client.h"]; + node31 [label="sampling_util.cpp"]; + node32 [label="datadog_agent_config.cpp"]; + node33 [label="span.cpp"]; + node34 [label="event_scheduler.cpp"]; + node35 [label="json_fwd.hpp"]; + node36 [label="datadog_agent.h"]; + node37 [label="propagation_style.cpp"]; + node38 [label="error.h"]; + node39 [label="event_scheduler.h"]; + node40 [label="tag_propagation.h"]; + node41 [label="clock.h"]; + node42 [label="logger.h"]; + node43 [label="span_defaults.h"]; + node44 [label="curl.h"]; + node45 [label="span_defaults.cpp"]; + node46 [label="threaded_event_scheduler.h"]; + node47 [label="tracer.h"]; + node48 [label="parse_util.h"]; + node49 [label="expected.cpp"]; + node50 [label="collector.cpp"]; + node51 [label="id_generator.cpp"]; + node52 [label="trace_sampler.cpp"]; + node53 [label="sampling_decision.cpp"]; + node54 [label="sampling_priority.cpp"]; + node55 [label="span_sampler.cpp"]; + node56 [label="collector.h"]; + node57 [label="curl.cpp"]; + node58 [label="null_collector.cpp"]; + node59 [label="cerr_logger.cpp"]; + node60 [label="collector_response.h"]; + node61 [label="msgpack.h"]; + node62 [label="trace_sampler.h"]; + node63 [label="span_config.cpp"]; + node64 [label="propagation_style.h"]; + node65 [label="dict_writer.cpp"]; + node66 [label="trace_sampler_config.cpp"]; + node67 [label="environment.h"]; + node68 [label="span_config.h"]; + node69 [label="datadog_agent.cpp"]; + node70 [label="winsock.h"]; + node71 [label="environment.cpp"]; + node72 [label="id_generator.h"]; + node73 [label="tracer_config.cpp"]; + node74 [label="net_util.cpp"]; + node75 [label="parse_util.cpp"]; + node76 [label="http_client.cpp"]; + node77 [label="optional.h"]; + node78 [label="null_collector.h"]; + node79 [label="charconv"]; + node80 [label="version.h"]; + node81 [label="span_sampler_config.h"]; + node82 [label="span_matcher.h"]; + node83 [label="version.cpp"]; + node84 [label="dict_reader.h"]; + node85 [label="span_matcher.cpp"]; + node86 [label="tracer.cpp"]; + node87 [label="default_http_client_curl.cpp"]; + node88 [label="http_client.h"]; + node89 [label="clock.cpp"]; + node90 [label="collector_response.cpp"]; + node91 [label="sampling_priority.h"]; + node92 [label="net_util.h"]; + node93 [label="limiter.cpp"]; + node94 [label="error.cpp"]; + node95 [label="absl/strings/string_view.h"]; + node96 [label="trace_sampler_config.h"]; + node97 [label="tags.cpp"]; + node98 [label="cerr_logger.h"]; + node99 [label="trace_segment.cpp"]; + node100 [label="span_sampler_config.cpp"]; subgraph U { edge [dir=none]; } subgraph D { - node0 -> node7 []; - node0 -> node40 []; - node1 -> node18 []; - node2 -> node37 []; - node2 -> node61 []; - node2 -> node20 []; - node2 -> node55 []; - node2 -> node11 []; - node2 -> node32 []; - node3 -> node25 []; - node4 -> node85 []; - node4 -> node22 []; - node4 -> node13 []; - node6 -> node34 []; - node6 -> node42 []; - node6 -> node32 []; - node8 -> node36 []; - node8 -> node75 []; - node8 -> node22 []; - node8 -> node14 []; - node8 -> node30 []; - node9 -> node77 []; - node10 -> node75 []; - node10 -> node21 []; - node10 -> node89 []; - node10 -> node13 []; - node10 -> node32 []; - node10 -> node85 []; - node10 -> node37 []; - node13 -> node32 []; - node14 -> node36 []; - node14 -> node18 []; - node15 -> node36 []; - node15 -> node64 []; - node15 -> node32 []; - node16 -> node23 []; - node17 -> node35 []; - node17 -> node32 []; - node18 -> node13 []; - node19 -> node18 []; - node20 -> node36 []; - node20 -> node13 []; - node21 -> node13 []; - node21 -> node81 []; - node22 -> node23 []; - node22 -> node18 []; - node24 -> node55 []; - node24 -> node32 []; - node26 -> node42 []; - node26 -> node21 []; - node26 -> node25 []; - node26 -> node60 []; - node26 -> node40 []; - node27 -> node19 []; - node28 -> node33 []; - node29 -> node4 []; - node29 -> node61 []; - node29 -> node5 []; - node29 -> node20 []; - node29 -> node15 []; - node29 -> node11 []; - node31 -> node36 []; - node31 -> node50 []; - node31 -> node81 []; - node31 -> node33 []; - node33 -> node30 []; - node33 -> node32 []; - node34 -> node13 []; - node37 -> node30 []; - node38 -> node81 []; - node38 -> node30 []; - node39 -> node37 []; - node39 -> node7 []; - node40 -> node33 []; - node41 -> node36 []; - node41 -> node64 []; - node41 -> node15 []; - node41 -> node32 []; - node41 -> node13 []; - node41 -> node10 []; - node42 -> node13 []; - node43 -> node13 []; - node44 -> node50 []; - node45 -> node64 []; - node46 -> node19 []; - node46 -> node56 []; - node46 -> node84 []; - node46 -> node52 []; - node46 -> node20 []; - node46 -> node22 []; - node46 -> node7 []; - node47 -> node22 []; - node48 -> node84 []; - node49 -> node23 []; - node49 -> node19 []; - node49 -> node84 []; - node49 -> node7 []; - node49 -> node8 []; - node49 -> node20 []; - node50 -> node13 []; - node50 -> node30 []; - node51 -> node35 []; - node51 -> node7 []; - node51 -> node38 []; - node51 -> node5 []; - node51 -> node42 []; - node51 -> node12 []; - node51 -> node81 []; - node51 -> node77 []; - node52 -> node18 []; - node53 -> node90 []; - node54 -> node7 []; - node54 -> node71 []; - node55 -> node13 []; - node56 -> node36 []; - node56 -> node89 []; - node56 -> node18 []; + node0 -> node20 []; + node1 -> node43 []; + node1 -> node68 []; + node1 -> node8 []; + node1 -> node24 []; + node1 -> node61 []; + node1 -> node11 []; + node1 -> node38 []; + node2 -> node7 []; + node2 -> node46 []; + node3 -> node30 []; + node4 -> node64 []; + node4 -> node23 []; + node4 -> node14 []; + node4 -> node77 []; + node5 -> node40 []; + node5 -> node48 []; + node5 -> node38 []; + node6 -> node8 []; + node8 -> node95 []; + node9 -> node41 []; + node9 -> node81 []; + node9 -> node23 []; + node9 -> node15 []; + node9 -> node35 []; + node10 -> node84 []; + node11 -> node8 []; + node12 -> node43 []; + node12 -> node64 []; + node12 -> node81 []; + node12 -> node25 []; + node12 -> node96 []; + node12 -> node14 []; + node12 -> node38 []; + node14 -> node77 []; + node14 -> node38 []; + node15 -> node41 []; + node15 -> node20 []; + node16 -> node77 []; + node17 -> node41 []; + node17 -> node72 []; + node17 -> node8 []; + node17 -> node77 []; + node17 -> node38 []; + node18 -> node26 []; + node19 -> node42 []; + node19 -> node38 []; + node20 -> node14 []; + node21 -> node20 []; + node22 -> node8 []; + node23 -> node26 []; + node23 -> node20 []; + node23 -> node77 []; + node24 -> node41 []; + node24 -> node14 []; + node24 -> node8 []; + node24 -> node77 []; + node25 -> node14 []; + node25 -> node88 []; + node25 -> node8 []; + node27 -> node8 []; + node28 -> node61 []; + node28 -> node38 []; + node31 -> node21 []; + node32 -> node48 []; + node32 -> node25 []; + node32 -> node30 []; + node32 -> node67 []; + node32 -> node46 []; + node33 -> node4 []; + node33 -> node68 []; + node33 -> node6 []; + node33 -> node24 []; + node33 -> node77 []; + node33 -> node11 []; + node33 -> node8 []; + node33 -> node17 []; + node34 -> node39 []; + node36 -> node41 []; + node36 -> node56 []; + node36 -> node88 []; + node36 -> node39 []; + node37 -> node64 []; + node37 -> node7 []; + node38 -> node8 []; + node39 -> node35 []; + node39 -> node38 []; + node40 -> node14 []; + node40 -> node8 []; + node42 -> node8 []; + node43 -> node35 []; + node44 -> node88 []; + node44 -> node35 []; + node45 -> node43 []; + node45 -> node7 []; + node46 -> node39 []; + node47 -> node41 []; + node47 -> node72 []; + node47 -> node17 []; + node47 -> node77 []; + node47 -> node38 []; + node47 -> node14 []; + node47 -> node12 []; + node48 -> node14 []; + node48 -> node8 []; + node49 -> node14 []; + node50 -> node56 []; + node51 -> node72 []; + node52 -> node21 []; + node52 -> node62 []; + node52 -> node91 []; + node52 -> node60 []; + node52 -> node24 []; + node52 -> node23 []; + node52 -> node7 []; + node53 -> node23 []; + node54 -> node91 []; + node55 -> node26 []; + node55 -> node21 []; + node55 -> node91 []; + node55 -> node7 []; + node55 -> node9 []; + node55 -> node24 []; node56 -> node14 []; - node56 -> node30 []; - node57 -> node61 []; - node58 -> node5 []; - node59 -> node42 []; - node59 -> node89 []; - node59 -> node7 []; - node59 -> node60 []; - node60 -> node30 []; - node61 -> node36 []; - node62 -> node35 []; - node62 -> node21 []; - node62 -> node52 []; - node62 -> node7 []; - node62 -> node72 []; - node62 -> node31 []; - node62 -> node56 []; - node62 -> node5 []; + node56 -> node77 []; + node56 -> node35 []; + node57 -> node42 []; + node57 -> node7 []; + node57 -> node8 []; + node57 -> node44 []; + node57 -> node6 []; + node57 -> node48 []; + node57 -> node13 []; + node57 -> node88 []; + node57 -> node84 []; + node58 -> node7 []; + node58 -> node78 []; + node59 -> node98 []; + node60 -> node20 []; + node60 -> node8 []; + node61 -> node14 []; + node61 -> node8 []; + node62 -> node41 []; + node62 -> node96 []; node62 -> node20 []; - node62 -> node55 []; - node65 -> node7 []; - node65 -> node60 []; - node66 -> node42 []; - node66 -> node90 []; - node66 -> node10 []; - node66 -> node60 []; - node66 -> node71 []; - node66 -> node31 []; - node67 -> node87 []; - node67 -> node63 []; - node68 -> node70 []; - node68 -> node42 []; - node68 -> node32 []; - node69 -> node81 []; - node71 -> node50 []; - node73 -> node72 []; - node74 -> node13 []; - node74 -> node30 []; - node75 -> node13 []; - node75 -> node18 []; - node75 -> node74 []; - node75 -> node30 []; - node76 -> node85 []; - node76 -> node7 []; - node78 -> node7 []; - node78 -> node20 []; - node78 -> node74 []; - node78 -> node32 []; - node79 -> node25 []; - node79 -> node38 []; - node80 -> node4 []; - node80 -> node61 []; - node80 -> node41 []; + node62 -> node15 []; + node62 -> node77 []; + node62 -> node35 []; + node63 -> node68 []; + node64 -> node35 []; + node65 -> node6 []; + node66 -> node48 []; + node66 -> node96 []; + node66 -> node7 []; + node66 -> node67 []; + node67 -> node8 []; + node67 -> node77 []; + node67 -> node35 []; + node68 -> node41 []; + node68 -> node77 []; + node69 -> node42 []; + node69 -> node25 []; + node69 -> node60 []; + node69 -> node7 []; + node69 -> node80 []; + node69 -> node36 []; + node69 -> node62 []; + node69 -> node6 []; + node69 -> node24 []; + node69 -> node61 []; + node71 -> node7 []; + node71 -> node67 []; + node73 -> node48 []; + node73 -> node98 []; + node73 -> node7 []; + node73 -> node12 []; + node73 -> node67 []; + node73 -> node8 []; + node73 -> node78 []; + node73 -> node36 []; + node74 -> node92 []; + node74 -> node70 []; + node75 -> node79 []; + node75 -> node48 []; + node75 -> node38 []; + node76 -> node88 []; + node77 -> node29 []; + node78 -> node56 []; node80 -> node8 []; - node80 -> node31 []; - node80 -> node11 []; - node80 -> node34 []; - node80 -> node35 []; - node80 -> node56 []; - node80 -> node42 []; - node80 -> node7 []; - node80 -> node87 []; - node80 -> node20 []; - node80 -> node77 []; - node80 -> node60 []; - node80 -> node15 []; - node80 -> node72 []; - node81 -> node13 []; - node81 -> node30 []; - node81 -> node32 []; - node82 -> node36 []; - node83 -> node52 []; - node84 -> node23 []; - node85 -> node30 []; - node86 -> node14 []; - node88 -> node32 []; - node89 -> node13 []; - node89 -> node18 []; - node89 -> node74 []; - node89 -> node30 []; - node90 -> node35 []; - node91 -> node42 []; - node91 -> node11 []; - node92 -> node50 []; - node92 -> node52 []; - node92 -> node8 []; - node92 -> node20 []; - node92 -> node34 []; - node92 -> node35 []; - node92 -> node4 []; - node92 -> node70 []; - node92 -> node56 []; - node92 -> node5 []; - node92 -> node11 []; - node92 -> node32 []; - node93 -> node35 []; - node93 -> node75 []; - node93 -> node7 []; - node93 -> node13 []; - node93 -> node60 []; + node81 -> node14 []; + node81 -> node20 []; + node81 -> node82 []; + node81 -> node77 []; + node81 -> node35 []; + node82 -> node14 []; + node82 -> node35 []; + node83 -> node80 []; + node84 -> node8 []; + node84 -> node77 []; + node85 -> node7 []; + node85 -> node24 []; + node85 -> node38 []; + node85 -> node82 []; + node85 -> node77 []; + node86 -> node4 []; + node86 -> node68 []; + node86 -> node47 []; + node86 -> node9 []; + node86 -> node36 []; + node86 -> node11 []; + node86 -> node40 []; + node86 -> node42 []; + node86 -> node62 []; + node86 -> node48 []; + node86 -> node7 []; + node86 -> node92 []; + node86 -> node24 []; + node86 -> node84 []; + node86 -> node67 []; + node86 -> node17 []; + node86 -> node80 []; + node87 -> node30 []; + node87 -> node44 []; + node88 -> node14 []; + node88 -> node38 []; + node88 -> node77 []; + node88 -> node35 []; + node89 -> node41 []; + node90 -> node60 []; + node91 -> node26 []; + node92 -> node77 []; + node93 -> node15 []; + node94 -> node38 []; + node96 -> node14 []; + node96 -> node20 []; + node96 -> node82 []; + node96 -> node77 []; + node96 -> node35 []; + node97 -> node48 []; + node97 -> node11 []; + node98 -> node42 []; + node99 -> node56 []; + node99 -> node60 []; + node99 -> node9 []; + node99 -> node24 []; + node99 -> node77 []; + node99 -> node40 []; + node99 -> node42 []; + node99 -> node4 []; + node99 -> node79 []; + node99 -> node62 []; + node99 -> node6 []; + node99 -> node11 []; + node99 -> node38 []; + node100 -> node42 []; + node100 -> node81 []; + node100 -> node7 []; + node100 -> node14 []; + node100 -> node67 []; } } diff --git a/doc/includes.svg b/doc/includes.svg index a3ca087e..5e55705b 100644 --- a/doc/includes.svg +++ b/doc/includes.svg @@ -4,1876 +4,2170 @@ - - + + G - + node0 - -threaded_event_scheduler.cpp + +rate.cpp - - -node7 - -json.hpp + + +node20 + +rate.h - + -node0->node7 - - - - - -node40 - -threaded_event_scheduler.h - - - -node0->node40 - - +node0->node20 + + node1 - -rate.cpp + +span_data.cpp - - -node18 - -rate.h - - - -node1->node18 - - + + +node8 + +string_view.h - - -node2 - -span_data.cpp + + +node1->node8 + + node11 - -tags.h - - - -node2->node11 - - + +tags.h - - -node20 - -span_data.h - - - -node2->node20 - - + + +node1->node11 + + - - -node32 - -error.h + + +node24 + +span_data.h - - -node2->node32 - - + + +node1->node24 + + - - -node37 - -span_defaults.h + + +node38 + +error.h - - -node2->node37 - - + + +node1->node38 + + - - -node55 - -msgpack.h + + +node43 + +span_defaults.h - - -node2->node55 - - + + +node1->node43 + + node61 - -span_config.h + +msgpack.h - - -node2->node61 - - + + +node1->node61 + + + + + +node68 + +span_config.h + + + +node1->node68 + + + + + +node2 + +threaded_event_scheduler.cpp + + + +node7 + +json.hpp + + + +node2->node7 + + + + + +node46 + +threaded_event_scheduler.h + + + +node2->node46 + + node3 - -default_http_client_null.cpp + +default_http_client_null.cpp - - -node25 - -default_http_client.h + + +node30 + +default_http_client.h - - -node3->node25 - - + + +node3->node30 + + node4 - -trace_segment.h + +trace_segment.h - - -node13 - -expected.h + + +node14 + +expected.h + + + +node4->node14 + + + + + +node23 + +sampling_decision.h - + -node4->node13 - - +node4->node23 + + - - -node22 - -sampling_decision.h + + +node64 + +propagation_style.h - + -node4->node22 - - +node4->node64 + + - - -node85 - -propagation_style.h + + +node77 + +optional.h - - -node4->node85 - - + + +node4->node77 + + node5 - -dict_writer.h + +tag_propagation.cpp - - -node6 - -tag_propagation.cpp + + +node5->node38 + + - - -node6->node32 - - + + +node40 + +tag_propagation.h - - -node34 - -tag_propagation.h + + +node5->node40 + + - - -node6->node34 - - + + +node48 + +parse_util.h - - -node42 - -parse_util.h + + +node5->node48 + + - - -node6->node42 - - + + +node6 + +dict_writer.h - - -node8 - -span_sampler.h + + +node6->node8 + + - - -node14 - -limiter.h + + +node95 + +absl/strings/string_view.h - + -node8->node14 - - +node8->node95 + + - - -node8->node22 - - + + +node9 + +span_sampler.h - - -node30 - -json_fwd.hpp + + +node15 + +limiter.h - - -node8->node30 - - + + +node9->node15 + + - - -node36 - -clock.h + + +node9->node23 + + - - -node8->node36 - - + + +node35 + +json_fwd.hpp - - -node75 - -span_sampler_config.h + + +node9->node35 + + - - -node8->node75 - - + + +node41 + +clock.h - - -node9 - -dict_reader.cpp + + +node9->node41 + + - - -node77 - -dict_reader.h + + +node81 + +span_sampler_config.h - + -node9->node77 - - +node9->node81 + + node10 - -tracer_config.h + +dict_reader.cpp - - -node10->node13 - - - - - -node21 - -datadog_agent_config.h + + +node84 + +dict_reader.h - - -node10->node21 - - + + +node10->node84 + + - + -node10->node32 - - +node11->node8 + + - - -node10->node37 - - + + +node12 + +tracer_config.h - - -node10->node75 - - + + +node12->node14 + + - - -node10->node85 - - + + +node25 + +datadog_agent_config.h - - -node89 - -trace_sampler_config.h + + +node12->node25 + + - - -node10->node89 - - + + +node12->node38 + + - - -node12 - -curl/curl.h + + +node12->node43 + + - + + +node12->node64 + + + + -node13->node32 - - +node12->node81 + + + + + +node96 + +trace_sampler_config.h - + -node14->node18 - - +node12->node96 + + - - -node14->node36 - - + + +node13 + +curl/curl.h - - -node15 - -span.h + + +node14->node38 + + - + -node15->node32 - - +node14->node77 + + - - -node15->node36 - - - - - -node64 - -id_generator.h + + +node15->node20 + + - - -node15->node64 - - + + +node15->node41 + + node16 - -sampling_mechanism.cpp + +optional.cpp - - -node23 - -sampling_mechanism.h - - - -node16->node23 - - + + +node16->node77 + + node17 - -logger.cpp - - - -node17->node32 - - - - - -node35 - -logger.h - - - -node17->node35 - - + +span.h - - -node18->node13 - - + + +node17->node8 + + - - -node19 - -sampling_util.h + + +node17->node38 + + - + -node19->node18 - - +node17->node41 + + - - -node20->node13 - - + + +node72 + +id_generator.h - + -node20->node36 - - +node17->node72 + + - + -node21->node13 - - - - - -node81 - -http_client.h +node17->node77 + + - - -node21->node81 - - + + +node18 + +sampling_mechanism.cpp - - -node22->node18 - - + + +node26 + +sampling_mechanism.h - + -node22->node23 - - +node18->node26 + + - - -node24 - -msgpack.cpp + + +node19 + +logger.cpp + + + +node19->node38 + + - + + +node42 + +logger.h + + + +node19->node42 + + + + -node24->node32 - - +node20->node14 + + - - -node24->node55 - - + + +node21 + +sampling_util.h - - -node26 - -datadog_agent_config.cpp + + +node21->node20 + + - + + +node22 + +string_view.cpp + + -node26->node21 - - +node22->node8 + + + + + +node23->node20 + + - + -node26->node25 - - +node23->node26 + + - + -node26->node40 - - +node23->node77 + + - - -node26->node42 - - + + +node24->node8 + + - - -node60 - -environment.h + + +node24->node14 + + - - -node26->node60 - - + + +node24->node41 + + + + + +node24->node77 + + + + + +node25->node8 + + + + + +node25->node14 + + + + + +node88 + +http_client.h + + + +node25->node88 + + node27 - -sampling_util.cpp + +glob.h - - -node27->node19 - - + + +node27->node8 + + node28 - -event_scheduler.cpp + +msgpack.cpp - - -node33 - -event_scheduler.h + + +node28->node38 + + - - -node28->node33 - - + + +node28->node61 + + node29 - -span.cpp - - - -node29->node4 - - + +absl/types/optional.h - - -node29->node5 - - + + +node31 + +sampling_util.cpp - - -node29->node11 - - + + +node31->node21 + + - - -node29->node15 - - + + +node32 + +datadog_agent_config.cpp - - -node29->node20 - - + + +node32->node25 + + - - -node29->node61 - - + + +node32->node30 + + - - -node31 - -datadog_agent.h + + +node32->node46 + + - + -node31->node33 - - +node32->node48 + + - - -node31->node36 - - + + +node67 + +environment.h - - -node50 - -collector.h + + +node32->node67 + + - - -node31->node50 - - + + +node33 + +span.cpp - - -node31->node81 - - + + +node33->node4 + + - - -node33->node30 - - + + +node33->node6 + + - - -node33->node32 - - + + +node33->node8 + + - - -node34->node13 - - + + +node33->node11 + + - - -node37->node30 - - + + +node33->node17 + + - - -node38 - -curl.h + + +node33->node24 + + - + -node38->node30 - - +node33->node68 + + - - -node38->node81 - - + + +node33->node77 + + + + + +node34 + +event_scheduler.cpp node39 - -span_defaults.cpp - - - -node39->node7 - - - - - -node39->node37 - - + +event_scheduler.h - - -node40->node33 - - + + +node34->node39 + + - - -node41 - -tracer.h + + +node36 + +datadog_agent.h - - -node41->node10 - - + + +node36->node39 + + - + -node41->node13 - - - - - -node41->node15 - - - - - -node41->node32 - - +node36->node41 + + - - -node41->node36 - - + + +node56 + +collector.h - - -node41->node64 - - + + +node36->node56 + + - + -node42->node13 - - - - - -node43 - -expected.cpp +node36->node88 + + - - -node43->node13 - - + + +node37 + +propagation_style.cpp - - -node44 - -collector.cpp + + +node37->node7 + + - + -node44->node50 - - - - - -node45 - -id_generator.cpp - - - -node45->node64 - - +node37->node64 + + - - -node46 - -trace_sampler.cpp + + +node38->node8 + + - - -node46->node7 - - + + +node39->node35 + + - - -node46->node19 - - + + +node39->node38 + + - + -node46->node20 - - +node40->node8 + + + + + +node40->node14 + + - + -node46->node22 - - +node42->node8 + + - - -node52 - -collector_response.h + + +node43->node35 + + - - -node46->node52 - - + + +node44 + +curl.h - - -node56 - -trace_sampler.h + + +node44->node35 + + - - -node46->node56 - - + + +node44->node88 + + - - -node84 - -sampling_priority.h + + +node45 + +span_defaults.cpp - - -node46->node84 - - + + +node45->node7 + + + + + +node45->node43 + + + + + +node46->node39 + + node47 - -sampling_decision.cpp + +tracer.h - - -node47->node22 - - + + +node47->node12 + + - - -node48 - -sampling_priority.cpp + + +node47->node14 + + - - -node48->node84 - - + + +node47->node17 + + - - -node49 - -span_sampler.cpp + + +node47->node38 + + - + -node49->node7 - - +node47->node41 + + - + -node49->node8 - - +node47->node72 + + - - -node49->node19 - - + + +node47->node77 + + - - -node49->node20 - - + + +node48->node8 + + - - -node49->node23 - - + + +node48->node14 + + - - -node49->node84 - - + + +node49 + +expected.cpp - - -node50->node13 - - + + +node49->node14 + + - - -node50->node30 - - + + +node50 + +collector.cpp + + + +node50->node56 + + node51 - -curl.cpp + +id_generator.cpp - - -node51->node5 - - + + +node51->node72 + + - - -node51->node7 - - + + +node52 + +trace_sampler.cpp - - -node51->node12 - - + + +node52->node7 + + - - -node51->node35 - - + + +node52->node21 + + - - -node51->node38 - - + + +node52->node23 + + - - -node51->node42 - - + + +node52->node24 + + - - -node51->node77 - - + + +node60 + +collector_response.h - - -node51->node81 - - + + +node52->node60 + + + + + +node62 + +trace_sampler.h - + -node52->node18 - - +node52->node62 + + + + + +node91 + +sampling_priority.h + + + +node52->node91 + + node53 - -cerr_logger.cpp - - - -node90 - -cerr_logger.h + +sampling_decision.cpp - - -node53->node90 - - + + +node53->node23 + + node54 - -null_collector.cpp - - - -node54->node7 - - - - - -node71 - -null_collector.h + +sampling_priority.cpp - - -node54->node71 - - + + +node54->node91 + + - - -node55->node13 - - + + +node55 + +span_sampler.cpp - - -node56->node14 - - + + +node55->node7 + + - - -node56->node18 - - + + +node55->node9 + + - + -node56->node30 - - - - - -node56->node36 - - +node55->node21 + + - - -node56->node89 - - + + +node55->node24 + + - - -node57 - -span_config.cpp + + +node55->node26 + + - + -node57->node61 - - - - - -node58 - -dict_writer.cpp - - - -node58->node5 - - - - - -node59 - -trace_sampler_config.cpp +node55->node91 + + - + -node59->node7 - - - - - -node59->node42 - - - - - -node59->node60 - - - - - -node59->node89 - - +node56->node14 + + - + -node60->node30 - - - - - -node61->node36 - - +node56->node35 + + - - -node62 - -datadog_agent.cpp + + +node56->node77 + + - - -node62->node5 - - + + +node57 + +curl.cpp - + -node62->node7 - - +node57->node6 + + - - -node62->node20 - - + + +node57->node7 + + - + -node62->node21 - - +node57->node8 + + - + -node62->node31 - - +node57->node13 + + - - -node62->node35 - - + + +node57->node42 + + - + -node62->node52 - - +node57->node44 + + - - -node62->node55 - - + + +node57->node48 + + + + + +node57->node84 + + - + -node62->node56 - - +node57->node88 + + - - -node72 - -version.h + + +node58 + +null_collector.cpp - - -node62->node72 - - + + +node58->node7 + + - - -node63 - -winsock.h + + +node78 + +null_collector.h - - -node65 - -environment.cpp + + +node58->node78 + + + + + +node59 + +cerr_logger.cpp + + + +node98 + +cerr_logger.h - + -node65->node7 - - +node59->node98 + + - - -node65->node60 - - + + +node60->node8 + + - - -node66 - -tracer_config.cpp + + +node60->node20 + + - + -node66->node10 - - - - - -node66->node31 - - +node61->node8 + + - - -node66->node42 - - + + +node61->node14 + + - - -node66->node60 - - + + +node62->node15 + + - - -node66->node71 - - + + +node62->node20 + + - - -node66->node90 - - + + +node62->node35 + + - - -node67 - -net_util.cpp + + +node62->node41 + + - + -node67->node63 - - +node62->node77 + + - - -node87 - -net_util.h + + +node62->node96 + + - - -node67->node87 - - + + +node63 + +span_config.cpp - - -node68 - -parse_util.cpp + + +node63->node68 + + - + -node68->node32 - - - - - -node68->node42 - - +node64->node35 + + - - -node70 - -charconv + + +node65 + +dict_writer.cpp - - -node68->node70 - - + + +node65->node6 + + - - -node69 - -http_client.cpp + + +node66 + +trace_sampler_config.cpp - - -node69->node81 - - + + +node66->node7 + + - + -node71->node50 - - +node66->node48 + + - - -node73 - -version.cpp + + +node66->node67 + + - + -node73->node72 - - - - - -node74 - -span_matcher.h +node66->node96 + + - - -node74->node13 - - - - - -node74->node30 - - - - + -node75->node13 - - +node67->node8 + + - + + +node67->node35 + + + + -node75->node18 - - +node67->node77 + + - + -node75->node30 - - +node68->node41 + + - - -node75->node74 - - + + +node68->node77 + + - - -node76 - -propagation_style.cpp + + +node69 + +datadog_agent.cpp - - -node76->node7 - - + + +node69->node6 + + - - -node76->node85 - - + + +node69->node7 + + - - -node78 - -span_matcher.cpp + + +node69->node24 + + - + -node78->node7 - - - - - -node78->node20 - - +node69->node25 + + - - -node78->node32 - - + + +node69->node36 + + - - -node78->node74 - - + + +node69->node42 + + - - -node79 - -default_http_client_curl.cpp + + +node69->node60 + + - - -node79->node25 - - + + +node69->node61 + + - + -node79->node38 - - +node69->node62 + + node80 - -tracer.cpp + +version.h - - -node80->node4 - - + + +node69->node80 + + - - -node80->node7 - - + + +node70 + +winsock.h - + + +node71 + +environment.cpp + + -node80->node8 - - +node71->node7 + + - - -node80->node11 - - + + +node71->node67 + + - - -node80->node15 - - + + +node73 + +tracer_config.cpp - - -node80->node20 - - + + +node73->node7 + + - - -node80->node31 - - + + +node73->node8 + + - - -node80->node34 - - + + +node73->node12 + + - - -node80->node35 - - + + +node73->node36 + + - - -node80->node41 - - + + +node73->node48 + + - + -node80->node42 - - +node73->node67 + + - - -node80->node56 - - + + +node73->node78 + + - - -node80->node60 - - + + +node73->node98 + + - - -node80->node61 - - + + +node74 + +net_util.cpp - - -node80->node72 - - + + +node74->node70 + + + + + +node92 + +net_util.h - + -node80->node77 - - +node74->node92 + + - - -node80->node87 - - + + +node75 + +parse_util.cpp - + -node81->node13 - - +node75->node38 + + + + + +node75->node48 + + + + + +node79 + +charconv - + + +node75->node79 + + + + + +node76 + +http_client.cpp + + -node81->node30 - - +node76->node88 + + - + -node81->node32 - - - - - -node82 - -clock.cpp +node77->node29 + + - + -node82->node36 - - - - - -node83 - -collector_response.cpp +node78->node56 + + - + -node83->node52 - - +node80->node8 + + - + -node84->node23 - - +node81->node14 + + - + -node85->node30 - - +node81->node20 + + - - -node86 - -limiter.cpp - - - -node86->node14 - - - - - -node88 - -error.cpp + + +node81->node35 + + - + -node88->node32 - - +node81->node77 + + - - -node89->node13 - - + + +node82 + +span_matcher.h - - -node89->node18 - - + + +node81->node82 + + - - -node89->node30 - - + + +node82->node14 + + - + -node89->node74 - - +node82->node35 + + - - -node90->node35 - - + + +node83 + +version.cpp - - -node91 - -tags.cpp + + +node83->node80 + + - - -node91->node11 - - + + +node84->node8 + + - + -node91->node42 - - - - - -node92 - -trace_segment.cpp +node84->node77 + + - - -node92->node4 - - + + +node85 + +span_matcher.cpp - - -node92->node5 - - + + +node85->node7 + + - - -node92->node8 - - + + +node85->node24 + + - - -node92->node11 - - + + +node85->node38 + + - + -node92->node20 - - +node85->node77 + + - - -node92->node32 - - + + +node85->node82 + + + + + +node86 + +tracer.cpp - + -node92->node34 - - +node86->node4 + + - - -node92->node35 - - + + +node86->node7 + + - - -node92->node50 - - + + +node86->node9 + + - - -node92->node52 - - + + +node86->node11 + + + + + +node86->node17 + + + + + +node86->node24 + + - + -node92->node56 - - +node86->node36 + + - - -node92->node70 - - + + +node86->node40 + + - - -node93 - -span_sampler_config.cpp + + +node86->node42 + + - - -node93->node7 - - + + +node86->node47 + + - - -node93->node13 - - + + +node86->node48 + + - + -node93->node35 - - +node86->node62 + + - - -node93->node60 - - + + +node86->node67 + + - - -node93->node75 - - + + +node86->node68 + + + + + +node86->node80 + + + + + +node86->node84 + + + + + +node86->node92 + + + + + +node87 + +default_http_client_curl.cpp + + + +node87->node30 + + + + + +node87->node44 + + + + + +node88->node14 + + + + + +node88->node35 + + + + + +node88->node38 + + + + + +node88->node77 + + + + + +node89 + +clock.cpp + + + +node89->node41 + + + + + +node90 + +collector_response.cpp + + + +node90->node60 + + + + + +node91->node26 + + + + + +node92->node77 + + + + + +node93 + +limiter.cpp + + + +node93->node15 + + + + + +node94 + +error.cpp + + + +node94->node38 + + + + + +node96->node14 + + + + + +node96->node20 + + + + + +node96->node35 + + + + + +node96->node77 + + + + + +node96->node82 + + + + + +node97 + +tags.cpp + + + +node97->node11 + + + + + +node97->node48 + + + + + +node98->node42 + + + + + +node99 + +trace_segment.cpp + + + +node99->node4 + + + + + +node99->node6 + + + + + +node99->node9 + + + + + +node99->node11 + + + + + +node99->node24 + + + + + +node99->node38 + + + + + +node99->node40 + + + + + +node99->node42 + + + + + +node99->node56 + + + + + +node99->node60 + + + + + +node99->node62 + + + + + +node99->node77 + + + + + +node99->node79 + + + + + +node100 + +span_sampler_config.cpp + + + +node100->node7 + + + + + +node100->node14 + + + + + +node100->node42 + + + + + +node100->node67 + + + + + +node100->node81 + + From b7d831d0857d65c70f080b6070643f070a427577 Mon Sep 17 00:00:00 2001 From: David Goffredo Date: Mon, 19 Dec 2022 13:54:01 -0500 Subject: [PATCH 10/11] remove ExtractionPolicy interface --- src/datadog/tracer.cpp | 230 ++++++++++++++++------------------------- 1 file changed, 90 insertions(+), 140 deletions(-) diff --git a/src/datadog/tracer.cpp b/src/datadog/tracer.cpp index 13ccf913..515048db 100644 --- a/src/datadog/tracer.cpp +++ b/src/datadog/tracer.cpp @@ -24,180 +24,128 @@ namespace datadog { namespace tracing { namespace { -class ExtractionPolicy { - public: - virtual Expected> trace_id( - const DictReader& headers) = 0; - virtual Expected> parent_id( - const DictReader& headers) = 0; - virtual Expected> sampling_priority( - const DictReader& headers) = 0; - virtual Optional origin(const DictReader& headers) = 0; - virtual Optional trace_tags(const DictReader&) = 0; +Expected> extract_id_header(const DictReader& headers, + StringView header, + StringView header_kind, + StringView style_name, + int base) { + auto found = headers.lookup(header); + if (!found) { + return nullopt; + } + auto result = parse_uint64(*found, base); + if (auto* error = result.if_error()) { + std::string prefix; + prefix += "Could not extract "; + append(prefix, style_name); + prefix += "-style "; + append(prefix, header_kind); + prefix += "ID from "; + append(prefix, header); + prefix += ": "; + append(prefix, *found); + prefix += ' '; + return error->with_prefix(prefix); + } + return *result; +} + +struct ExtractedData { + Optional trace_id; + Optional parent_id; + Optional origin; + Optional trace_tags; + Optional sampling_priority; }; -class DatadogExtractionPolicy : public ExtractionPolicy { - Expected> id(const DictReader& headers, - StringView header, StringView kind) { - auto found = headers.lookup(header); - if (!found) { - return nullopt; - } - auto result = parse_uint64(*found, 10); - if (auto* error = result.if_error()) { - std::string prefix; - prefix += "Could not extract Datadog-style "; - append(prefix, kind); - prefix += "ID from "; - append(prefix, header); - prefix += ": "; - append(prefix, *found); - prefix += ' '; - return error->with_prefix(prefix); - } - return *result; - } +Expected extract_datadog(const DictReader& headers) { + ExtractedData result; - public: - Expected> trace_id( - const DictReader& headers) override { - return id(headers, "x-datadog-trace-id", "trace"); + auto trace_id = + extract_id_header(headers, "x-datadog-trace-id", "trace", "Datadog", 10); + if (auto* error = trace_id.if_error()) { + return std::move(*error); } + result.trace_id = *trace_id; - Expected> parent_id( - const DictReader& headers) override { - return id(headers, "x-datadog-parent-id", "parent span"); + auto parent_id = extract_id_header(headers, "x-datadog-parent-id", + "parent span", "Datadog", 10); + if (auto* error = parent_id.if_error()) { + return std::move(*error); } + result.parent_id = *parent_id; - Expected> sampling_priority( - const DictReader& headers) override { - const StringView header = "x-datadog-sampling-priority"; - auto found = headers.lookup(header); - if (!found) { - return nullopt; - } - auto result = parse_int(*found, 10); - if (auto* error = result.if_error()) { + const StringView sampling_priority_header = "x-datadog-sampling-priority"; + if (auto found = headers.lookup(sampling_priority_header)) { + auto sampling_priority = parse_int(*found, 10); + if (auto* error = sampling_priority.if_error()) { std::string prefix; prefix += "Could not extract Datadog-style sampling priority from "; - append(prefix, header); + append(prefix, sampling_priority_header); prefix += ": "; append(prefix, *found); prefix += ' '; return error->with_prefix(prefix); } - return *result; + result.sampling_priority = *sampling_priority; } - Optional origin(const DictReader& headers) override { - auto found = headers.lookup("x-datadog-origin"); - if (found) { - return std::string(*found); - } - return nullopt; + auto origin = headers.lookup("x-datadog-origin"); + if (origin) { + result.origin = *origin; } - Optional trace_tags(const DictReader& headers) override { - auto found = headers.lookup("x-datadog-tags"); - if (found) { - return std::string(*found); - } - return nullopt; + auto trace_tags = headers.lookup("x-datadog-tags"); + if (trace_tags) { + result.trace_tags = *trace_tags; } -}; -class B3ExtractionPolicy : public DatadogExtractionPolicy { - Expected> id(const DictReader& headers, - StringView header, StringView kind) { - auto found = headers.lookup(header); - if (!found) { - return nullopt; - } - auto result = parse_uint64(*found, 16); - if (auto* error = result.if_error()) { - std::string prefix; - prefix += "Could not extract B3-style "; - append(prefix, kind); - prefix += "ID from "; - append(prefix, header); - prefix += ": "; - append(prefix, *found); - prefix += ' '; - return error->with_prefix(prefix); - } - return *result; - } + return result; +} + +Expected extract_b3(const DictReader& headers) { + ExtractedData result; - public: - Expected> trace_id( - const DictReader& headers) override { - return id(headers, "x-b3-traceid", "trace"); + auto trace_id = extract_id_header(headers, "x-b3-traceid", "trace", "B3", 16); + if (auto* error = trace_id.if_error()) { + return std::move(*error); } + result.trace_id = *trace_id; - Expected> parent_id( - const DictReader& headers) override { - return id(headers, "x-b3-spanid", "parent span"); + auto parent_id = + extract_id_header(headers, "x-b3-spanid", "parent span", "B3", 16); + if (auto* error = parent_id.if_error()) { + return std::move(*error); } + result.parent_id = *parent_id; - Expected> sampling_priority( - const DictReader& headers) override { - const StringView header = "x-b3-sampled"; - auto found = headers.lookup(header); - if (!found) { - return nullopt; - } - auto result = parse_int(*found, 10); - if (auto* error = result.if_error()) { + const StringView sampling_priority_header = "x-b3-sampled"; + if (auto found = headers.lookup(sampling_priority_header)) { + auto sampling_priority = parse_int(*found, 10); + if (auto* error = sampling_priority.if_error()) { std::string prefix; prefix += "Could not extract B3-style sampling priority from "; - append(prefix, header); + append(prefix, sampling_priority_header); prefix += ": "; append(prefix, *found); prefix += ' '; return error->with_prefix(prefix); } - return *result; + result.sampling_priority = *sampling_priority; } -}; -struct ExtractedData { - Optional trace_id; - Optional parent_id; - Optional origin; - Optional trace_tags; - Optional sampling_priority; -}; - -Expected extract_data(ExtractionPolicy& extract, - const DictReader& reader) { - ExtractedData extracted_data; - - auto& [trace_id, parent_id, origin, trace_tags, sampling_priority] = - extracted_data; - - auto maybe_trace_id = extract.trace_id(reader); - if (auto* error = maybe_trace_id.if_error()) { - return std::move(*error); + // Origin and trace tags are still extracted, but from the Datadog headers. + auto origin = headers.lookup("x-datadog-origin"); + if (origin) { + result.origin = *origin; } - trace_id = *maybe_trace_id; - origin = extract.origin(reader); - - auto maybe_parent_id = extract.parent_id(reader); - if (auto* error = maybe_parent_id.if_error()) { - return std::move(*error); - } - parent_id = *maybe_parent_id; - - auto maybe_sampling_priority = extract.sampling_priority(reader); - if (auto* error = maybe_sampling_priority.if_error()) { - return std::move(*error); + auto trace_tags = headers.lookup("x-datadog-tags"); + if (trace_tags) { + result.trace_tags = *trace_tags; } - sampling_priority = *maybe_sampling_priority; - - trace_tags = extract.trace_tags(reader); - return extracted_data; + return result; } void log_startup_message(Logger& logger, StringView tracer_version_string, @@ -299,9 +247,8 @@ Expected Tracer::extract_span(const DictReader& reader, ExtractedData extracted_data; for (const auto style : extraction_styles_) { - DatadogExtractionPolicy extract_datadog; - B3ExtractionPolicy extract_b3; - ExtractionPolicy* extract; + using Extractor = decltype(&extract_datadog); // function pointer + Extractor extract; switch (style) { case PropagationStyle::DATADOG: extract = &extract_datadog; @@ -314,11 +261,14 @@ Expected Tracer::extract_span(const DictReader& reader, extracted_data = ExtractedData{}; continue; } - auto data = extract_data(*extract, reader); + auto data = extract(reader); if (auto* error = data.if_error()) { return std::move(*error); } extracted_data = *data; + // If the extractor produced a non-null trace ID, then we consider this + // extraction style the one "chosen" for this trace. + // Otherwise, we loop around to the next configured extraction style. if (extracted_data.trace_id) { break; } From 9ad952f950823a0f3765dc06b7e5d8be375baa48 Mon Sep 17 00:00:00 2001 From: David Goffredo Date: Mon, 19 Dec 2022 14:15:37 -0500 Subject: [PATCH 11/11] satisfy Abseil build mode --- src/datadog/tracer.cpp | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/src/datadog/tracer.cpp b/src/datadog/tracer.cpp index 515048db..81f3bf25 100644 --- a/src/datadog/tracer.cpp +++ b/src/datadog/tracer.cpp @@ -92,12 +92,12 @@ Expected extract_datadog(const DictReader& headers) { auto origin = headers.lookup("x-datadog-origin"); if (origin) { - result.origin = *origin; + result.origin = std::string(*origin); } auto trace_tags = headers.lookup("x-datadog-tags"); if (trace_tags) { - result.trace_tags = *trace_tags; + result.trace_tags = std::string(*trace_tags); } return result; @@ -137,12 +137,12 @@ Expected extract_b3(const DictReader& headers) { // Origin and trace tags are still extracted, but from the Datadog headers. auto origin = headers.lookup("x-datadog-origin"); if (origin) { - result.origin = *origin; + result.origin = std::string(*origin); } auto trace_tags = headers.lookup("x-datadog-tags"); if (trace_tags) { - result.trace_tags = *trace_tags; + result.trace_tags = std::string(*trace_tags); } return result;