如何修改env_logger的时间戳格式为"%Y-%m-%d %H:%M:%S%.3f"?
Hey there! Let me walk you through exactly how to tweak env_logger's timestamp output to match your desired format. The key here is using env_logger's builder API, which lets you take full control over how log lines are structured.
Step 1: Update Your Dependencies
First, make sure your Cargo.toml has the right crates. We'll use env_logger for logging, log for the logging macros, and chrono to handle the precise timestamp formatting (it makes this way simpler than rolling your own):
[dependencies] env_logger = "0.10" log = "0.4" chrono = "0.4"
Step 2: Full Working Example
Instead of using the basic env_logger::init(), we'll build a custom logger instance with our timestamp format. Here's a complete, runnable snippet:
use env_logger::{Builder, Env}; use log::{info, warn}; use std::fmt::Write; fn main() { // Set up the logger with custom formatting Builder::from_env(Env::default().default_filter_or("info")) .format(|buf, record| { // Grab the current local time and format it to your spec let timestamp = chrono::Local::now().format("%Y-%m-%d %H:%M:%S%.3f"); // Build the final log line writeln!( buf, "[{}] {}: {}", timestamp, record.level(), record.args() ) }) .init(); // Test out the logger info!("This is an info message with your custom timestamp"); warn!("This warning uses the same timestamp format too!"); }
Quick Breakdown of the Key Bits
Builder::from_env(...): This keeps the standardRUST_LOGenvironment variable behavior (so you can still filter logs via the shell), with a default filter of "info" ifRUST_LOGisn't set.- The
formatclosure: This is where the magic happens. We usechrono::Local::now()to get the current time, thenformat()with your exact timestamp string to get that preciseYYYY-MM-DD HH:MM:SS.sssoutput. writeln!: Puts all the pieces together—timestamp, log level, and your message—into a clean log line.
Alternative: No Chrono Dependency (If You Prefer)
If you don't want to add chrono, you can use the time crate instead to handle formatting. Here's a quick version of that:
use env_logger::{Builder, Env}; use log::{info, warn}; use std::fmt::Write; use std::time::{SystemTime, UNIX_EPOCH}; fn main() { Builder::from_env(Env::default().default_filter_or("info")) .format(|buf, record| { let now = SystemTime::now().duration_since(UNIX_EPOCH).unwrap(); let secs = now.as_secs(); let millis = now.subsec_millis(); // Convert seconds to a human-readable datetime, then append millis let dt = time::OffsetDateTime::from_unix_timestamp(secs as i64).unwrap(); let timestamp = format!("{}:{:03}", dt.format("%Y-%m-%d %H:%M:%S"), millis); writeln!( buf, "[{}] {}: {}", timestamp, record.level(), record.args() ) }) .init(); info!("Manual timestamp formatting without chrono"); }
For this, swap chrono with time in your Cargo.toml:
[dependencies] time = "0.3"
Either approach will give you the timestamp format you're after—logs will look like [2024-05-20 15:42:18.765] INFO: Your log message here.
内容的提问来源于stack exchange,提问作者Tobias Hermann

