-
Notifications
You must be signed in to change notification settings - Fork 14
Add KVP Tracer and OpenTel #83
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Changes from all commits
7eeb728
ba4d5c0
5d8910e
0a83a36
bca37eb
7d05d59
9fae1c9
052fa5b
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,26 @@ | ||
[package] | ||
name = "azurekvp" | ||
version = "0.1.1" | ||
edition = "2021" | ||
repository = "https://github.com/Azure/azure-init/" | ||
homepage = "https://github.com/Azure/azure-init/" | ||
license = "MIT" | ||
description = "A binary library for implementing OpenTelemetry KVP for Linux VMs on Azure." | ||
|
||
|
||
[dependencies] | ||
once_cell = "1.12.0" | ||
opentelemetry = "0.18.0" | ||
opentelemetry_sdk = "0.22.0" | ||
opentelemetry-stdout = "0.2.0" | ||
tracing = "0.1" | ||
tracing-opentelemetry = "0.18.0" | ||
tracing-subscriber = "0.3.11" | ||
serde = { version = "1.0" } | ||
serde_json = "1.0.68" | ||
tokio = { version = "1", features = ["full"] } | ||
libc = "0.2" | ||
|
||
[lib] | ||
name = "azurekvp" | ||
path = "src/tracing.rs" |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,4 @@ | ||
// Copyright (c) Microsoft Corporation. | ||
// Licensed under the MIT License. | ||
|
||
pub mod main; |
Original file line number | Diff line number | Diff line change | ||||||||||||||||||||||||||||||
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
@@ -0,0 +1,50 @@ | ||||||||||||||||||||||||||||||||
// Copyright (c) Microsoft Corporation. | ||||||||||||||||||||||||||||||||
// Licensed under the MIT License. | ||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||
use opentelemetry::{ trace::{self, TracerProvider}, trace::Tracer as _}; | ||||||||||||||||||||||||||||||||
use opentelemetry::sdk::trace as sdktrace; | ||||||||||||||||||||||||||||||||
use opentelemetry::sdk::export::trace::stdout; | ||||||||||||||||||||||||||||||||
use opentelemetry::global; | ||||||||||||||||||||||||||||||||
use tracing_opentelemetry::OpenTelemetryLayer; | ||||||||||||||||||||||||||||||||
use once_cell::sync::Lazy; | ||||||||||||||||||||||||||||||||
use std::fs::File; | ||||||||||||||||||||||||||||||||
use std::os::unix::io::AsRawFd; | ||||||||||||||||||||||||||||||||
use libc::dup2; | ||||||||||||||||||||||||||||||||
use tracing_subscriber::{Registry, layer::SubscriberExt}; | ||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||
pub static TRACER: Lazy<()> = Lazy::new(|| { | ||||||||||||||||||||||||||||||||
// Redirect stdout to a file | ||||||||||||||||||||||||||||||||
let log_file_path = "spans.log"; | ||||||||||||||||||||||||||||||||
let file = File::create(log_file_path).expect("Failed to create log file"); | ||||||||||||||||||||||||||||||||
let stdout_fd = file.as_raw_fd(); | ||||||||||||||||||||||||||||||||
unsafe { | ||||||||||||||||||||||||||||||||
dup2(stdout_fd, libc::STDOUT_FILENO); | ||||||||||||||||||||||||||||||||
} | ||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||
// Set up the stdout exporter correctly | ||||||||||||||||||||||||||||||||
let exporter = stdout::Exporter::new(std::io::stdout(), true); | ||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||
// Set up the TracerProvider with the stdout exporter | ||||||||||||||||||||||||||||||||
let provider = sdktrace::TracerProvider::builder() | ||||||||||||||||||||||||||||||||
.with_simple_exporter(exporter) | ||||||||||||||||||||||||||||||||
.build(); | ||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||
global::set_tracer_provider(provider.clone()); | ||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||
let tracer = provider.tracer("azure-kvp"); | ||||||||||||||||||||||||||||||||
// Create the OpenTelemetry layer using the SDK tracer | ||||||||||||||||||||||||||||||||
let otel_layer = OpenTelemetryLayer::new(tracer); | ||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||
// Create a `tracing` subscriber | ||||||||||||||||||||||||||||||||
let subscriber = Registry::default() | ||||||||||||||||||||||||||||||||
.with(otel_layer); | ||||||||||||||||||||||||||||||||
Comment on lines
+38
to
+41
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. The tracing subscriber lets you register multiple layers, and each layer can be configured with its own filters and formatters and so on. It takes a little digging in the tracing_subscriber docs and I forever forget how to do it properly, but here's an example that would let us avoid needing to duplicate the file descriptor:
Suggested change
This adds a second layer which writes to If you run with this diff, you'll get logs written to stderr and "example.log" for that layer, and then separately to "spans.log". I don't think we want this literal suggestion, but I think this is the general approach we want to take when setting things up. We can also apply a global filter that applies to all layers instead (or in addition to) filters on each layer. |
||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||
// Set the subscriber as the global default | ||||||||||||||||||||||||||||||||
tracing::subscriber::set_global_default(subscriber) | ||||||||||||||||||||||||||||||||
.expect("Setting default subscriber failed"); | ||||||||||||||||||||||||||||||||
}); | ||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||
pub fn initialize_tracing() { | ||||||||||||||||||||||||||||||||
Lazy::force(&TRACER); | ||||||||||||||||||||||||||||||||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I would recommend that we move the code within this block into the binary in the
azure-init
crate. Each application tends to want to configure its logging in its own way - different file names, different environment variables for configuration, different filtering rules, etc.What would be good in a library is any custom Layers we end up making, if any. These can be consumed (and configured) by applications in their tracing-subscriber setup.