depura/timer/
scope.rs

1// depura::time::scope
2//
3//! scope timer
4//
5// First version based on `measure_time` v0.8.2, Unlicense
6// https://github.com/PSeitz/rust_measure_time
7//
8
9use human_repr::HumanDuration;
10
11/// A structure used to log its lifetime the moment it drops.
12#[derive(Debug)]
13#[cfg_attr(feature = "nightly", doc(cfg(feature = "std")))]
14pub struct ScopeTime {
15    name: String,
16    target: &'static str,
17    module_path: &'static str,
18    file: &'static str,
19    line: u32,
20    start: instant::Instant,
21    level: log::LevelFilter,
22}
23impl ScopeTime {
24    pub fn new<S: Into<String>>(
25        target: &'static str,
26        module_path: &'static str,
27        file: &'static str,
28        line: u32,
29        name: S,
30        level: log::LevelFilter,
31    ) -> Self {
32        Self {
33            target,
34            module_path,
35            file,
36            line,
37            name: name.into(),
38            start: instant::Instant::now(),
39            level,
40        }
41    }
42}
43
44impl Drop for ScopeTime {
45    fn drop(&mut self) {
46        let time = self.start.elapsed().human_duration();
47
48        if let Some(level) = self.level.to_level() {
49            log::logger().log(
50                &log::Record::builder()
51                    .args(format_args!("{} {}", self.name, time))
52                    .level(level)
53                    .target(self.target)
54                    .module_path(Some(self.module_path))
55                    .file(Some(self.file))
56                    .line(Some(self.line))
57                    .build(),
58            );
59        } else {
60            println!("{} took {}", self.name, time);
61        }
62    }
63}
64
65/// Logs the time with the [`print!`] macro.
66#[macro_export]
67#[cfg_attr(feature = "nightly", doc(cfg(feature = "std")))]
68macro_rules! print_time {
69    ($($arg:tt)+) => {
70        #[allow(unused_variables)]
71        let time = $crate::all::ScopeTime::new(
72            module_path!(),
73            module_path!(),
74            file!(),
75            line!(),
76            format!($($arg)+),
77            log::LevelFilter::Off
78        );
79    } ;
80}
81pub use print_time;
82
83/// Logs the time with the [`log!`][log::log] macro.
84#[macro_export]
85#[cfg_attr(feature = "nightly", doc(cfg(feature = "std")))]
86macro_rules! log_time {
87    (target: $target:expr, $lvl:expr, $lvl2:expr, $($arg:tt)+) => (
88        #[allow(unused_variables)]
89        let time = if log::log_enabled!($lvl) {
90            Some($crate::all::ScopeTime::new($target, module_path!(), file!(), line!(), format!($($arg)+), $lvl2) )
91        } else{
92            None
93        };
94    );
95}
96pub use log_time;
97
98/// Logs the time with the [`error!`][log::error] macro.
99#[macro_export]
100#[cfg_attr(feature = "nightly", doc(cfg(feature = "std")))]
101macro_rules! error_time {
102    (target: $target:expr, $($arg:tt)+) => (
103        $crate::log_time!(target: $target, log::Level::Error, log::LevelFilter::Error, $($arg)+)
104    );
105    ($($arg:tt)+) => ($crate::log_time!(target: module_path!(), log::Level::Error, log::LevelFilter::Error, $($arg)+) )
106}
107pub use error_time;
108
109/// Logs the time with the [`warn!`][log::warn] macro.
110#[macro_export]
111#[cfg_attr(feature = "nightly", doc(cfg(feature = "std")))]
112macro_rules! warn_time {
113    (target: $target:expr, $($arg:tt)+) => (
114        $crate::log_time!(target: $target, log::Level::Warn, log::LevelFilter::Warn, $($arg)+)
115    );
116    ($($arg:tt)+) => ($crate::log_time!(target: module_path!(), log::Level::Warn, log::LevelFilter::Warn, $($arg)+) )
117}
118pub use warn_time;
119
120/// Logs the time with the [`info!`][log::info] macro.
121#[macro_export]
122#[cfg_attr(feature = "nightly", doc(cfg(feature = "std")))]
123macro_rules! info_time {
124    (target: $target:expr, $($arg:tt)+) => (
125        $crate::log_time!(target: $target, log::Level::Info, log::LevelFilter::Info, $($arg)+)
126    );
127    ($($arg:tt)+) => ($crate::log_time!(target: module_path!(), log::Level::Info, log::LevelFilter::Info, $($arg)+) )
128}
129pub use info_time;
130
131/// Logs the time with the [`debug!`][log::debug] macro.
132#[macro_export]
133#[cfg_attr(feature = "nightly", doc(cfg(feature = "std")))]
134macro_rules! debug_time {
135    (target: $target:expr, $($arg:tt)+) => (
136        $crate::log_time!(target: $target, log::Level::Debug, log::LevelFilter::Debug, $($arg)+)
137    );
138    ($($arg:tt)+) => ($crate::log_time!(target: module_path!(), log::Level::Debug, log::LevelFilter::Debug, $($arg)+) )
139}
140pub use debug_time;
141
142/// Logs the time with the [`trace!`][log::trace] macro.
143#[macro_export]
144#[cfg_attr(feature = "nightly", doc(cfg(feature = "std")))]
145macro_rules! trace_time {
146    (target: $target:expr, $($arg:tt)+) => (
147        $crate::log_time!(target: $target, $crate::all::Level::Trace, log::LevelFilter::Trace, $($arg)+)
148    );
149    ($($arg:tt)+) => ($crate::log_time!(target: module_path!(), log::Level::Trace, log::LevelFilter::Trace, $($arg)+) )
150}
151pub use trace_time;