opentelemetry/trace/tracer_provider.rs
1use crate::{trace::Tracer, InstrumentationLibrary, InstrumentationLibraryBuilder, KeyValue};
2use std::{borrow::Cow, sync::Arc};
3
4/// Types that can create instances of [`Tracer`].
5///
6/// See the [`global`] module for examples of storing and retrieving tracer
7/// provider instances.
8///
9/// [`global`]: crate::global
10pub trait TracerProvider {
11 /// The [`Tracer`] type that this provider will return.
12 type Tracer: Tracer;
13
14 /// Returns a new tracer with the given name.
15 ///
16 /// The `name` should be the application name or the name of the library
17 /// providing instrumentation. If the name is empty, then an
18 /// implementation-defined default name may be used instead.
19 ///
20 /// # Examples
21 ///
22 /// ```
23 /// use opentelemetry::{global, trace::TracerProvider};
24 /// use opentelemetry::KeyValue;
25 ///
26 /// let provider = global::tracer_provider();
27 ///
28 /// // tracer used in applications/binaries
29 /// let tracer = provider.tracer("my_app");
30 ///
31 /// // tracer used in libraries/crates that optionally includes version and schema url
32 /// let tracer = provider.tracer_builder("my_library").
33 /// with_version(env!("CARGO_PKG_VERSION")).
34 /// with_schema_url("https://opentelemetry.io/schema/1.0.0").
35 /// with_attributes(vec![KeyValue::new("key", "value")]).
36 /// build();
37 /// ```
38 fn tracer(&self, name: impl Into<Cow<'static, str>>) -> Self::Tracer {
39 self.tracer_builder(name).build()
40 }
41
42 /// Deprecated, use [`TracerProvider::tracer_builder()`]
43 ///
44 /// Returns a new versioned tracer with a given name.
45 ///
46 /// The `name` should be the application name or the name of the library
47 /// providing instrumentation. If the name is empty, then an
48 /// implementation-defined default name may be used instead.
49 ///
50 /// # Examples
51 ///
52 /// ```
53 /// use opentelemetry::{global, trace::TracerProvider};
54 ///
55 /// let provider = global::tracer_provider();
56 ///
57 /// // tracer used in applications/binaries
58 /// let tracer = provider.tracer("my_app");
59 ///
60 /// // tracer used in libraries/crates that optionally includes version and schema url
61 /// let tracer = provider.versioned_tracer(
62 /// "my_library",
63 /// Some(env!("CARGO_PKG_VERSION")),
64 /// Some("https://opentelemetry.io/schema/1.0.0"),
65 /// None,
66 /// );
67 /// ```
68 #[deprecated(since = "0.23.0", note = "Please use tracer_builder() instead")]
69 fn versioned_tracer(
70 &self,
71 name: impl Into<Cow<'static, str>>,
72 version: Option<impl Into<Cow<'static, str>>>,
73 schema_url: Option<impl Into<Cow<'static, str>>>,
74 attributes: Option<Vec<KeyValue>>,
75 ) -> Self::Tracer {
76 let mut builder = self.tracer_builder(name);
77 if let Some(v) = version {
78 builder = builder.with_version(v);
79 }
80 if let Some(s) = schema_url {
81 builder = builder.with_version(s);
82 }
83 if let Some(a) = attributes {
84 builder = builder.with_attributes(a);
85 }
86
87 builder.build()
88 }
89
90 /// Returns a new builder for creating a [`Tracer`] instance
91 ///
92 /// The `name` should be the application name or the name of the library
93 /// providing instrumentation. If the name is empty, then an
94 /// implementation-defined default name may be used instead.
95 ///
96 /// # Examples
97 ///
98 /// ```
99 /// use opentelemetry::{global, trace::TracerProvider};
100 ///
101 /// let provider = global::tracer_provider();
102 ///
103 /// // tracer used in applications/binaries
104 /// let tracer = provider.tracer_builder("my_app").build();
105 ///
106 /// // tracer used in libraries/crates that optionally includes version and schema url
107 /// let tracer = provider.tracer_builder("my_library")
108 /// .with_version(env!("CARGO_PKG_VERSION"))
109 /// .with_schema_url("https://opentelemetry.io/schema/1.0.0")
110 /// .build();
111 /// ```
112 fn tracer_builder(&self, name: impl Into<Cow<'static, str>>) -> TracerBuilder<'_, Self> {
113 TracerBuilder {
114 provider: self,
115 library_builder: InstrumentationLibrary::builder(name),
116 }
117 }
118
119 /// Returns a new versioned tracer with the given instrumentation library.
120 ///
121 /// # Examples
122 ///
123 /// ```
124 /// use opentelemetry::{global, InstrumentationLibrary, trace::TracerProvider};
125 ///
126 /// let provider = global::tracer_provider();
127 ///
128 /// // tracer used in applications/binaries
129 /// let tracer = provider.tracer("my_app");
130 ///
131 /// // tracer used in libraries/crates that optionally includes version and schema url
132 /// let library = std::sync::Arc::new(
133 /// InstrumentationLibrary::builder(env!("CARGO_PKG_NAME"))
134 /// .with_version(env!("CARGO_PKG_VERSION"))
135 /// .with_schema_url("https://opentelemetry.io/schema/1.0.0")
136 /// .build(),
137 /// );
138 ///
139 /// let tracer = provider.library_tracer(library);
140 /// ```
141 fn library_tracer(&self, library: Arc<InstrumentationLibrary>) -> Self::Tracer;
142}
143
144#[derive(Debug)]
145pub struct TracerBuilder<'a, T: TracerProvider + ?Sized> {
146 provider: &'a T,
147 library_builder: InstrumentationLibraryBuilder,
148}
149
150impl<'a, T: TracerProvider + ?Sized> TracerBuilder<'a, T> {
151 pub fn with_version(mut self, version: impl Into<Cow<'static, str>>) -> Self {
152 self.library_builder = self.library_builder.with_version(version);
153 self
154 }
155
156 pub fn with_schema_url(mut self, schema_url: impl Into<Cow<'static, str>>) -> Self {
157 self.library_builder = self.library_builder.with_schema_url(schema_url);
158 self
159 }
160
161 pub fn with_attributes<I>(mut self, attributes: I) -> Self
162 where
163 I: IntoIterator<Item = KeyValue>,
164 {
165 self.library_builder = self.library_builder.with_attributes(attributes);
166 self
167 }
168
169 pub fn build(self) -> T::Tracer {
170 self.provider
171 .library_tracer(Arc::new(self.library_builder.build()))
172 }
173}