Skip to content
Merged
Show file tree
Hide file tree
Changes from 12 commits
Commits
Show all changes
19 commits
Select commit Hold shift + click to select a range
c0cdf59
chore(stackable-telemetry): move tracing to a module directory
NickLarsenNZ Oct 25, 2024
e92dbdd
feat(stackable-telemetry): Add a settings builder and implement it fo…
NickLarsenNZ Oct 25, 2024
cdedab7
feat(stackable-telemetry): Add a settings builder for the otlp trace …
NickLarsenNZ Oct 25, 2024
2ca287c
feat(stackable-telemetry): Add a settings builder for the otlp log ex…
NickLarsenNZ Oct 25, 2024
a502da7
chore(stackable-telemetry): Make settings available to the Tracing::i…
NickLarsenNZ Oct 25, 2024
cd609aa
chore(stackable-telemetry): Introduce the CommonSettings trait for qu…
NickLarsenNZ Oct 25, 2024
98e7acd
refactor(stackable-telemetry): Rename env_var() for consistency, reor…
NickLarsenNZ Oct 26, 2024
51ae3ed
chore(stackable-telemetry): Add SettingsDouble and SettingsTriple tup…
NickLarsenNZ Oct 26, 2024
41157cc
chore(stackable-telemetry): Resolve clippy warnings
NickLarsenNZ Oct 28, 2024
dbe3719
refactor(stackable-telemetry): Prefix builder methods with `with_`.
NickLarsenNZ Oct 28, 2024
2e4f19f
refactor(stackable-telemetry): Revert SettingsDouble/SettingsTriple
NickLarsenNZ Nov 27, 2024
951f5cc
docs(stackable-telemetry): Partially add docs
NickLarsenNZ Nov 27, 2024
48ef413
refactor: Simplify From and Build trait usages
Techassi Nov 27, 2024
5de6ed4
refactor: Provide centralized default impls for CommonSettings trait
Techassi Nov 27, 2024
7137d50
docs: Fix doc tests
Techassi Nov 27, 2024
7a4fdd8
docs: Fix doc comment references
Techassi Nov 27, 2024
8f59b15
refactor: Use Deref instead of CommonSettings trait
Techassi Nov 27, 2024
afc2163
chore(stackable-telemetry): Apply suggestions from code review
NickLarsenNZ Nov 27, 2024
e6ff024
chore(stackable-telemetry): Update changelog
NickLarsenNZ Nov 27, 2024
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -14,12 +14,16 @@ use opentelemetry_sdk::{
trace, Resource,
};
use opentelemetry_semantic_conventions::resource;
use settings::{CommonSettings as _, ConsoleLogSettings, OtlpLogSettings, OtlpTraceSettings};
use snafu::{ResultExt as _, Snafu};
use tracing::{level_filters::LevelFilter, subscriber::SetGlobalDefaultError};
use tracing::subscriber::SetGlobalDefaultError;
use tracing_subscriber::{filter::Directive, layer::SubscriberExt, EnvFilter, Layer, Registry};

pub mod settings;

type Result<T, E = Error> = std::result::Result<T, E>;

#[allow(missing_docs)]
#[derive(Debug, Snafu)]
pub enum Error {
#[snafu(display("unable to install opentelemetry trace exporter"))]
Expand All @@ -40,7 +44,7 @@ pub enum Error {
///
/// # Usage:
/// ```
/// use stackable_telemetry::tracing::{Tracing, Error};
/// use stackable_telemetry::tracing::{Tracing, Error, settings::{Build as _, Settings}};
/// use tracing_subscriber::filter::LevelFilter;
///
/// #[tokio::main]
Expand All @@ -49,9 +53,15 @@ pub enum Error {
/// // `let _ =`, as that will drop immediately.
/// let _tracing_guard = Tracing::builder()
/// .service_name("test")
/// .with_console_output("TEST_CONSOLE", LevelFilter::INFO)
/// .with_otlp_log_exporter("TEST_OTLP_LOG", LevelFilter::DEBUG)
/// .with_otlp_trace_exporter("TEST_OTLP_TRACE", LevelFilter::TRACE)
/// .with_console_output(
/// Settings::builder()
/// .environment_variable("TEST_CONSOLE")
/// .default_level(LevelFilter::INFO)
/// .enabled(true)
/// .build()
/// )
/// .with_otlp_log_exporter(("TEST_OTLP_LOG", LevelFilter::DEBUG).into())
/// .with_otlp_trace_exporter(("TEST_OTLP_TRACE", LevelFilter::TRACE).into())
/// .build()
/// .init()?;
///
Expand Down Expand Up @@ -123,9 +133,9 @@ pub enum Error {
/// [5]: https://docs.rs/opentelemetry_sdk/latest/src/opentelemetry_sdk/logs/log_processor.rs.html
pub struct Tracing {
service_name: &'static str,
console_log_config: SubscriberConfig,
otlp_log_config: SubscriberConfig,
otlp_trace_config: SubscriberConfig,
console_log_settings: ConsoleLogSettings,
otlp_log_settings: OtlpLogSettings,
otlp_trace_settings: OtlpTraceSettings,
logger_provider: Option<LoggerProvider>,
}

Expand All @@ -142,20 +152,22 @@ impl Tracing {
pub fn init(mut self) -> Result<Tracing> {
let mut layers: Vec<Box<dyn Layer<Registry> + Sync + Send>> = Vec::new();

if self.console_log_config.enabled {
if self.console_log_settings.enabled() {
let env_filter_layer = env_filter_builder(
self.console_log_config.env_var,
self.console_log_config.default_level_filter,
self.console_log_settings
.common_settings
.environment_variable,
self.console_log_settings.default_level(),
);
let console_output_layer =
tracing_subscriber::fmt::layer().with_filter(env_filter_layer);
layers.push(console_output_layer.boxed());
}

if self.otlp_log_config.enabled {
if self.otlp_log_settings.enabled() {
let env_filter_layer = env_filter_builder(
self.otlp_log_config.env_var,
self.otlp_log_config.default_level_filter,
self.otlp_log_settings.environment_variable(),
self.otlp_log_settings.default_level(),
)
// TODO (@NickLarsenNZ): Remove this directive once https://github.com/open-telemetry/opentelemetry-rust/issues/761 is resolved
.add_directive("h2=off".parse().expect("invalid directive"));
Expand All @@ -180,10 +192,12 @@ impl Tracing {
self.logger_provider = Some(otel_log);
}

if self.otlp_trace_config.enabled {
if self.otlp_trace_settings.enabled() {
let env_filter_layer = env_filter_builder(
self.otlp_trace_config.env_var,
self.otlp_trace_config.default_level_filter,
self.otlp_trace_settings
.common_settings
.environment_variable,
self.otlp_trace_settings.default_level(),
)
// TODO (@NickLarsenNZ): Remove this directive once https://github.com/open-telemetry/opentelemetry-rust/issues/761 is resolved
.add_directive("h2=off".parse().expect("invalid directive"));
Expand Down Expand Up @@ -231,12 +245,12 @@ impl Tracing {
impl Drop for Tracing {
fn drop(&mut self) {
tracing::debug!(
opentelemetry.tracing.enabled = self.otlp_trace_config.enabled,
opentelemetry.logger.enabled = self.otlp_log_config.enabled,
opentelemetry.tracing.enabled = self.otlp_trace_settings.enabled(),
opentelemetry.logger.enabled = self.otlp_log_settings.enabled(),
"shutting down opentelemetry OTLP providers"
);

if self.otlp_trace_config.enabled {
if self.otlp_trace_settings.enabled() {
// NOTE (@NickLarsenNZ): This might eventually be replaced with something like SdkMeterProvider::shutdown(&self)
// as has been done with the LoggerProvider (further below)
// see: https://github.com/open-telemetry/opentelemetry-rust/pull/1412/files#r1409608679
Expand Down Expand Up @@ -315,31 +329,14 @@ impl BuilderState for builder_state::Config {}
#[derive(Default)]
pub struct TracingBuilder<S: BuilderState> {
service_name: Option<&'static str>,
console_log_config: SubscriberConfig,
otlp_log_config: SubscriberConfig,
otlp_trace_config: SubscriberConfig,
console_log_settings: ConsoleLogSettings,
otlp_log_settings: OtlpLogSettings,
otlp_trace_settings: OtlpTraceSettings,

/// Allow the generic to be used (needed for impls).
_marker: std::marker::PhantomData<S>,
}

#[derive(Clone, Debug, PartialEq)]
struct SubscriberConfig {
enabled: bool,
env_var: &'static str,
default_level_filter: LevelFilter,
}

impl Default for SubscriberConfig {
fn default() -> Self {
Self {
enabled: false,
env_var: EnvFilter::DEFAULT_ENV,
default_level_filter: LevelFilter::OFF,
}
}
}

impl TracingBuilder<builder_state::PreServiceName> {
/// Set the service name used in OTLP exports, and console output.
///
Expand All @@ -358,18 +355,13 @@ impl TracingBuilder<builder_state::Config> {
/// variable.
pub fn with_console_output(
self,
env_var: &'static str,
default_level_filter: LevelFilter,
console_log_settings: ConsoleLogSettings,
) -> TracingBuilder<builder_state::Config> {
TracingBuilder {
service_name: self.service_name,
console_log_config: SubscriberConfig {
enabled: true,
env_var,
default_level_filter,
},
otlp_log_config: self.otlp_log_config,
otlp_trace_config: self.otlp_trace_config,
console_log_settings,
otlp_log_settings: self.otlp_log_settings,
otlp_trace_settings: self.otlp_trace_settings,
_marker: self._marker,
}
}
Expand All @@ -381,18 +373,13 @@ impl TracingBuilder<builder_state::Config> {
/// in the opentelemetry crates. See [`Tracing`].
pub fn with_otlp_log_exporter(
self,
env_var: &'static str,
default_level_filter: LevelFilter,
otlp_log_settings: OtlpLogSettings,
) -> TracingBuilder<builder_state::Config> {
TracingBuilder {
service_name: self.service_name,
console_log_config: self.console_log_config,
otlp_log_config: SubscriberConfig {
enabled: true,
env_var,
default_level_filter,
},
otlp_trace_config: self.otlp_trace_config,
console_log_settings: self.console_log_settings,
otlp_log_settings,
otlp_trace_settings: self.otlp_trace_settings,
_marker: self._marker,
}
}
Expand All @@ -404,18 +391,13 @@ impl TracingBuilder<builder_state::Config> {
/// in the opentelemetry crates. See [`Tracing`].
pub fn with_otlp_trace_exporter(
self,
env_var: &'static str,
default_level_filter: LevelFilter,
otlp_trace_settings: OtlpTraceSettings,
) -> TracingBuilder<builder_state::Config> {
TracingBuilder {
service_name: self.service_name,
console_log_config: self.console_log_config,
otlp_log_config: self.otlp_log_config,
otlp_trace_config: SubscriberConfig {
enabled: true,
env_var,
default_level_filter,
},
console_log_settings: self.console_log_settings,
otlp_log_settings: self.otlp_log_settings,
otlp_trace_settings,
_marker: self._marker,
}
}
Expand All @@ -429,9 +411,9 @@ impl TracingBuilder<builder_state::Config> {
service_name: self
.service_name
.expect("service_name must be configured at this point"),
console_log_config: self.console_log_config,
otlp_log_config: self.otlp_log_config,
otlp_trace_config: self.otlp_trace_config,
console_log_settings: self.console_log_settings,
otlp_log_settings: self.otlp_log_settings,
otlp_trace_settings: self.otlp_trace_settings,
logger_provider: None,
}
}
Expand All @@ -447,6 +429,9 @@ fn env_filter_builder(env_var: &str, default_directive: impl Into<Directive>) ->

#[cfg(test)]
mod test {
use settings::{Build as _, Settings};
use tracing::level_filters::LevelFilter;

use super::*;

#[test]
Expand All @@ -460,53 +445,93 @@ mod test {
fn builder_with_console_output() {
let trace_guard = Tracing::builder()
.service_name("test")
.with_console_output("ABC_A", LevelFilter::TRACE)
.with_console_output("ABC_B", LevelFilter::DEBUG)
.with_console_output(
Settings::builder()
.with_environment_variable("ABC_A")
.with_default_level(LevelFilter::TRACE)
.enabled(true)
.build(),
)
.with_console_output(
Settings::builder()
.with_environment_variable("ABC_B")
.with_default_level(LevelFilter::DEBUG)
.enabled(true)
.build(),
)
.build();

assert_eq!(
trace_guard.console_log_config,
SubscriberConfig {
enabled: true,
env_var: "ABC_B",
default_level_filter: LevelFilter::DEBUG
trace_guard.console_log_settings,
ConsoleLogSettings {
common_settings: Settings {
enabled: true,
environment_variable: "ABC_B",
default_level: LevelFilter::DEBUG
},
log_format: Default::default()
}
);
assert!(!trace_guard.otlp_log_config.enabled);
assert!(!trace_guard.otlp_trace_config.enabled);
assert!(!trace_guard.otlp_log_settings.enabled());
assert!(!trace_guard.otlp_trace_settings.enabled());
}

#[test]
fn builder_with_all() {
let trace_guard = Tracing::builder()
.service_name("test")
.with_console_output("ABC_CONSOLE", LevelFilter::INFO)
.with_otlp_log_exporter("ABC_OTLP_LOG", LevelFilter::DEBUG)
.with_otlp_trace_exporter("ABC_OTLP_TRACE", LevelFilter::TRACE)
.with_console_output(
Settings::builder()
.with_environment_variable("ABC_CONSOLE")
.with_default_level(LevelFilter::INFO)
.enabled(true)
.build(),
)
.with_otlp_log_exporter(
Settings::builder()
.with_environment_variable("ABC_OTLP_LOG")
.with_default_level(LevelFilter::DEBUG)
.enabled(true)
.build(),
)
.with_otlp_trace_exporter(
Settings::builder()
.with_environment_variable("ABC_OTLP_TRACE")
.with_default_level(LevelFilter::TRACE)
.enabled(true)
.build(),
)
.build();

assert_eq!(
trace_guard.console_log_config,
SubscriberConfig {
enabled: true,
env_var: "ABC_CONSOLE",
default_level_filter: LevelFilter::INFO
trace_guard.console_log_settings,
ConsoleLogSettings {
common_settings: Settings {
enabled: true,
environment_variable: "ABC_CONSOLE",
default_level: LevelFilter::INFO
},
log_format: Default::default()
}
);
assert_eq!(
trace_guard.otlp_log_config,
SubscriberConfig {
enabled: true,
env_var: "ABC_OTLP_LOG",
default_level_filter: LevelFilter::DEBUG
trace_guard.otlp_log_settings,
OtlpLogSettings {
common_settings: Settings {
enabled: true,
environment_variable: "ABC_OTLP_LOG",
default_level: LevelFilter::DEBUG
},
}
);
assert_eq!(
trace_guard.otlp_trace_config,
SubscriberConfig {
enabled: true,
env_var: "ABC_OTLP_TRACE",
default_level_filter: LevelFilter::TRACE
trace_guard.otlp_trace_settings,
OtlpTraceSettings {
common_settings: Settings {
enabled: true,
environment_variable: "ABC_OTLP_TRACE",
default_level: LevelFilter::TRACE
}
}
);
}
Expand Down
Loading
Loading