Instrumentation measures performance and exposes diagnostic telemetry from Rust applications. The tracing crate emits structured traces as logs or through OpenTelemetry, while Tokio integrations support live analysis of asynchronous programs. section 8.9
Apply instrumentation with a focused production workflow:
- Configure a subscriber to receive traces before expecting useful output. section 8.9
- Mark functions with #[tracing::instrument] at the points whose execution, latency, or task behavior matters. section 8.9
- Select useful levels and targets instead of enabling every message by default. section 9.5.2
- Use logs or OpenTelemetry for persistent observability; reserve tokio-console for interactive debugging. section 8.9
use tokio::time::{sleep, Duration};
#[tracing::instrument] #1
async fn sleep_1s() {
sleep(Duration::from_secs(1)).await;
}
#[tracing::instrument]
async fn sleep_2s() {
sleep(Duration::from_secs(2)).await;
}
#[tracing::instrument]
async fn sleep_3s() {
sleep(Duration::from_secs(3)).await;
}
#[tokio::main]
async fn main() {
console_subscriber::init(); #2
loop {
tokio::spawn(sleep_1s()); #3
tokio::spawn(sleep_2s());
sleep_3s().await; #4
}
}
This runnable pattern instruments three asynchronous sleep functions, initializes the console subscriber, and mixes spawned tasks with an awaited task for live inspection. section 8.9
Listing 9.3 API service init_tracing() function in src/main.rs
fn init_tracing() {
use tracing_subscriber::{
filter::LevelFilter, fmt, prelude::*, EnvFilter
};
let rust_log = std::env::var(EnvFilter::DEFAULT_ENV) #1
.unwrap_or_else(|_| "sqlx=info,tower_http=debug,info".to_string());
tracing_subscriber::registry() #2
.with(fmt::layer()) #3
.with(
EnvFilter::builder() #4
.with_default_directive(LevelFilter::INFO.into())
.parse_lossy(rust_log),
)
.init();
}
This initialization pattern reads RUST_LOG, supplies defaults, attaches formatted output, applies EnvFilter directives, and installs the subscriber. section 9.5.2
Avoid setting RUST_LOG=trace casually: unrestricted output can become noisy and is discouraged in production when unnecessary. Prefer explicit crate-level directives such as sqlx=info and tower_http=debug. section 9.5.2












