From 3b7b26cc669e899b9d9b0d5283e07ba5ddd96d70 Mon Sep 17 00:00:00 2001 From: Josh McKinney Date: Mon, 25 Nov 2024 19:05:33 -0800 Subject: [PATCH] feat: Implement conversion for level types Implement `From` for `LevelFilter` and `Option` for both `log` and `tracing` crates. This makes it possible to just directly set the log filter: E.g.: ```rust env_logger::Builder::new().filter_level(cli.verbosity.into()).init(); // or tracing_subscriber::fmt().with_max_level(cli.verbosity).init(); ``` --- examples/log.rs | 4 ++-- examples/tracing.rs | 4 ++-- src/log.rs | 56 ++++++++++++++++++++++++++++++++++++++++++++- src/tracing.rs | 56 ++++++++++++++++++++++++++++++++++++++++++++- 4 files changed, 114 insertions(+), 6 deletions(-) diff --git a/examples/log.rs b/examples/log.rs index 689e7ed..c39f55a 100644 --- a/examples/log.rs +++ b/examples/log.rs @@ -5,14 +5,14 @@ use clap_verbosity_flag::Verbosity; #[derive(Debug, Parser)] struct Cli { #[command(flatten)] - verbose: Verbosity, + verbosity: Verbosity, } fn main() { let cli = Cli::parse(); env_logger::Builder::new() - .filter_level(cli.verbose.log_level_filter()) + .filter_level(cli.verbosity.into()) .init(); log::error!("Engines exploded"); diff --git a/examples/tracing.rs b/examples/tracing.rs index a34246e..2033c9b 100644 --- a/examples/tracing.rs +++ b/examples/tracing.rs @@ -5,14 +5,14 @@ use clap_verbosity_flag::Verbosity; #[derive(Debug, Parser)] struct Cli { #[command(flatten)] - verbose: Verbosity, + verbosity: Verbosity, } fn main() { let cli = Cli::parse(); tracing_subscriber::fmt() - .with_max_level(cli.verbose.tracing_level_filter()) + .with_max_level(cli.verbosity) .init(); tracing::error!("Engines exploded"); diff --git a/src/log.rs b/src/log.rs index 94d87d2..b04f23c 100644 --- a/src/log.rs +++ b/src/log.rs @@ -3,7 +3,7 @@ // information. pub use log::{Level, LevelFilter}; -use crate::VerbosityFilter; +use crate::{LogLevel, Verbosity, VerbosityFilter}; impl From for LevelFilter { fn from(filter: VerbosityFilter) -> Self { @@ -57,6 +57,18 @@ impl From> for VerbosityFilter { } } +impl From> for LevelFilter { + fn from(v: Verbosity) -> Self { + v.log_level_filter() + } +} + +impl From> for Option { + fn from(v: Verbosity) -> Self { + v.log_level() + } +} + #[cfg(test)] mod tests { use super::*; @@ -88,4 +100,46 @@ mod tests { assert_eq!(v.log_level(), Some(Level::Trace)); assert_eq!(v.log_level_filter(), LevelFilter::Trace); } + + #[test] + fn into_opt_level() { + let v = Verbosity::::default(); + assert_eq!(Option::::from(v), None); + + let v = Verbosity::::default(); + assert_eq!(Option::::from(v), Some(Level::Error)); + + let v = Verbosity::::default(); + assert_eq!(Option::::from(v), Some(Level::Warn)); + + let v = Verbosity::::default(); + assert_eq!(Option::::from(v), Some(Level::Info)); + + let v = Verbosity::::default(); + assert_eq!(Option::::from(v), Some(Level::Debug)); + + let v = Verbosity::::default(); + assert_eq!(Option::::from(v), Some(Level::Trace)); + } + + #[test] + fn into_level_filter() { + let v = Verbosity::::default(); + assert_eq!(LevelFilter::from(v), LevelFilter::Off); + + let v = Verbosity::::default(); + assert_eq!(LevelFilter::from(v), LevelFilter::Error); + + let v = Verbosity::::default(); + assert_eq!(LevelFilter::from(v), LevelFilter::Warn); + + let v = Verbosity::::default(); + assert_eq!(LevelFilter::from(v), LevelFilter::Info); + + let v = Verbosity::::default(); + assert_eq!(LevelFilter::from(v), LevelFilter::Debug); + + let v = Verbosity::::default(); + assert_eq!(LevelFilter::from(v), LevelFilter::Trace); + } } diff --git a/src/tracing.rs b/src/tracing.rs index 3715f52..98c4156 100644 --- a/src/tracing.rs +++ b/src/tracing.rs @@ -3,7 +3,7 @@ // more information. pub use tracing_core::{Level, LevelFilter}; -use crate::VerbosityFilter; +use crate::{LogLevel, Verbosity, VerbosityFilter}; impl From for LevelFilter { fn from(filter: VerbosityFilter) -> Self { @@ -57,6 +57,18 @@ impl From> for VerbosityFilter { } } +impl From> for LevelFilter { + fn from(v: Verbosity) -> Self { + v.tracing_level_filter() + } +} + +impl From> for Option { + fn from(v: Verbosity) -> Self { + v.tracing_level() + } +} + #[cfg(test)] mod tests { use super::*; @@ -88,4 +100,46 @@ mod tests { assert_eq!(v.tracing_level(), Some(Level::TRACE)); assert_eq!(v.tracing_level_filter(), LevelFilter::TRACE); } + + #[test] + fn into_opt_level() { + let v = Verbosity::::default(); + assert_eq!(Option::::from(v), None); + + let v = Verbosity::::default(); + assert_eq!(Option::::from(v), Some(Level::ERROR)); + + let v = Verbosity::::default(); + assert_eq!(Option::::from(v), Some(Level::WARN)); + + let v = Verbosity::::default(); + assert_eq!(Option::::from(v), Some(Level::INFO)); + + let v = Verbosity::::default(); + assert_eq!(Option::::from(v), Some(Level::DEBUG)); + + let v = Verbosity::::default(); + assert_eq!(Option::::from(v), Some(Level::TRACE)); + } + + #[test] + fn into_level_filter() { + let v = Verbosity::::default(); + assert_eq!(LevelFilter::from(v), LevelFilter::OFF); + + let v = Verbosity::::default(); + assert_eq!(LevelFilter::from(v), LevelFilter::ERROR); + + let v = Verbosity::::default(); + assert_eq!(LevelFilter::from(v), LevelFilter::WARN); + + let v = Verbosity::::default(); + assert_eq!(LevelFilter::from(v), LevelFilter::INFO); + + let v = Verbosity::::default(); + assert_eq!(LevelFilter::from(v), LevelFilter::DEBUG); + + let v = Verbosity::::default(); + assert_eq!(LevelFilter::from(v), LevelFilter::TRACE); + } }