Configure Logging

Enable log levels per module

log-badge env_logger-badge cat-debugging-badge

Creates two modules foo and nested foo::bar with logging directives controlled separately with RUST_LOG environmental variable.

mod foo { mod bar { pub fn run() { log::warn!("[bar] warn"); log::info!("[bar] info"); log::debug!("[bar] debug"); } } pub fn run() { log::warn!("[foo] warn"); log::info!("[foo] info"); log::debug!("[foo] debug"); bar::run(); } } fn main() { env_logger::init(); log::warn!("[root] warn"); log::info!("[root] info"); log::debug!("[root] debug"); foo::run(); }

RUST_LOG environment variable controls env_logger output. Module declarations take comma separated entries formatted like path::to::module=log_level. Run the test application as follows:

RUST_LOG="warn,test::foo=info,test::foo::bar=debug" ./test

Sets the default log::Level to warn, module foo and module foo::bar to info and debug.

WARN:test: [root] warn WARN:test::foo: [foo] warn INFO:test::foo: [foo] info WARN:test::foo::bar: [bar] warn INFO:test::foo::bar: [bar] info DEBUG:test::foo::bar: [bar] debug

Use a custom environment variable to set up logging

log-badge env_logger-badge cat-debugging-badge

Builder configures logging.

Builder::from_env parses MY_APP_LOG environment variable contents in the form of RUST_LOG syntax. Then, Builder::init initializes the logger.

use env_logger::Builder; fn main() { Builder::from_env("MY_APP_LOG").init(); log::info!("informational message"); log::warn!("warning message"); log::error!("this is an error {}", "message"); }

Include timestamp in log messages

log-badge env_logger-badge chrono-badge cat-debugging-badge

Creates a custom logger configuration with Builder. Each log entry calls Local::now to get the current DateTime in local timezone and uses DateTime::format with strftime::specifiers to format a timestamp used in the final log.

The example calls Builder::format to set a closure which formats each message text with timestamp, Record::level and body (Record::args).

use std::io::Write; use chrono::Local; use env_logger::Builder; use log::LevelFilter; fn main() { Builder::new() .format(|buf, record| { writeln!(buf, "{} [{}] - {}", Local::now().format("%Y-%m-%dT%H:%M:%S"), record.level(), record.args() ) }) .filter(None, LevelFilter::Info) .init(); log::warn!("warn"); log::info!("info"); log::debug!("debug"); }

stderr output will contain

2017-05-22T21:57:06 [WARN] - warn 2017-05-22T21:57:06 [INFO] - info

Log messages to a custom location

log-badge log4rs-badge cat-debugging-badge

log4rs configures log output to a custom location. log4rs can use either an external YAML file or a builder configuration.

Create the log configuration with log4rs::append::file::FileAppender. An appender defines the logging destination. The configuration continues with encoding using a custom pattern from log4rs::encode::pattern. Assigns the configuration to log4rs::config::Config and sets the default log::LevelFilter.

use error_chain::error_chain; use log::LevelFilter; use log4rs::append::file::FileAppender; use log4rs::encode::pattern::PatternEncoder; use log4rs::config::{Appender, Config, Root}; error_chain! { foreign_links { Io(std::io::Error); LogConfig(log4rs::config::Errors); SetLogger(log::SetLoggerError); } } fn main() -> Result<()> { let logfile = FileAppender::builder() .encoder(Box::new(PatternEncoder::new("{l} - {m}\n"))) .build("log/output.log")?; let config = Config::builder() .appender(Appender::builder().build("logfile", Box::new(logfile))) .build(Root::builder() .appender("logfile") .build(LevelFilter::Info))?; log4rs::init_config(config)?; log::info!("Hello, world!"); Ok(()) }