lightning_signer/util/
log_utils.rs1use crate::prelude::*;
2use anyhow::{anyhow, Result};
3
4const LOG_LEVEL_FILTERS: [log::LevelFilter; 6] = [
5 log::LevelFilter::Off,
6 log::LevelFilter::Error,
7 log::LevelFilter::Warn,
8 log::LevelFilter::Info,
9 log::LevelFilter::Debug,
10 log::LevelFilter::Trace,
11];
12
13pub const LOG_LEVEL_FILTER_NAMES: [&'static str; 6] =
15 ["OFF", "ERROR", "WARN", "INFO", "DEBUG", "TRACE"];
16
17pub fn parse_log_level_filter(lvlstr: String) -> Result<log::LevelFilter> {
19 Ok(*LOG_LEVEL_FILTERS
20 .iter()
21 .find(|ll| lvlstr == ll.as_str())
22 .ok_or_else(|| anyhow!("invalid log level: {}", lvlstr))?)
23}
24
25#[macro_export]
30macro_rules! catch_panic {
31 ($e:expr, $fmt:expr) => {{
32 catch_panic!($fmt,)
33 }};
34 ($e:expr, $fmt:expr, $($arg:tt)*) => {{
35 #[cfg(feature = "std")]
36 match std::panic::catch_unwind(|| $e) {
37 Ok(res) => res,
38 Err(err) => {
39 let details = if let Some(s) = err.downcast_ref::<String>() {
40 s.clone()
41 } else if let Some(s) = err.downcast_ref::<&str>() {
42 s.to_string()
43 } else {
44 "Unknown panic message".to_string()
45 };
46 ::log::error!($fmt, details, $($arg)*);
47 return Err(crate::util::status::Status::internal(format!($fmt, details, $($arg)*)))
48 }
49 }
50 #[cfg(not(feature = "std"))]
51 $e
52 }};
53}
54
55#[cfg(test)]
56mod tests {
57 use super::parse_log_level_filter;
58 use log::LevelFilter;
59
60 use crate::util::status::{Code, Status};
61
62 #[test]
63 fn catch_test() {
64 fn fut_panic() -> Result<u8, Status> {
65 catch_panic!(panic!("test"), "panic: {} {}", "arg1")
66 }
67 fn fut_success() -> Result<u8, Status> {
68 catch_panic!(Ok(42), "panic: {} {}", "arg1")
69 }
70 let res = fut_panic();
71 assert!(res.is_err());
72 let status = res.unwrap_err();
73 assert_eq!(status.code(), Code::Internal);
74 assert_eq!(status.message(), "panic: test arg1");
75
76 let res = fut_success();
77 assert_eq!(res.unwrap(), 42);
78 }
79
80 #[test]
81 fn test_parse_log_level_filter() {
82 let valid_levels = [
83 ("OFF", LevelFilter::Off),
84 ("ERROR", LevelFilter::Error),
85 ("WARN", LevelFilter::Warn),
86 ("INFO", LevelFilter::Info),
87 ("DEBUG", LevelFilter::Debug),
88 ("TRACE", LevelFilter::Trace),
89 ];
90
91 for (name, expected_filter) in valid_levels.iter() {
92 let result = parse_log_level_filter(name.to_string());
93 assert!(result.is_ok());
94 assert_eq!(result.unwrap(), *expected_filter);
95 }
96
97 let invalid_level = "INVALID".to_string();
99 let result = parse_log_level_filter(invalid_level);
100 assert!(result.is_err());
101 assert_eq!(result.unwrap_err().to_string(), "invalid log level: INVALID");
102 }
103}