diff --git a/Cargo.toml b/Cargo.toml index 6511d80..4515626 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "rust_util" -version = "0.6.40" +version = "0.6.41" authors = ["Hatter Jiang "] edition = "2018" description = "Hatter's Rust Util" diff --git a/examples/log.rs b/examples/log.rs index 44443aa..8df6fd0 100644 --- a/examples/log.rs +++ b/examples/log.rs @@ -1,6 +1,7 @@ #[macro_use] extern crate rust_util; use rust_util::{XResult, SimpleError}; +use rust_util::util_msg::set_logger_std_out; // cargo run --example log fn main() -> XResult<()> { @@ -20,6 +21,11 @@ error or ^"##); println!("{:?}", test_opt_result()); + set_logger_std_out(false); + information!("Std err!"); + warning!("Std err!"); + set_logger_std_out(true); + simple_error!("helloworld {}", 1) } diff --git a/src/util_msg.rs b/src/util_msg.rs index b6c7629..26bf36c 100644 --- a/src/util_msg.rs +++ b/src/util_msg.rs @@ -1,13 +1,19 @@ use std::env; use std::io::{self, Write}; -use std::sync::{Arc, Mutex}; +use std::sync::{Arc, Mutex, RwLock}; lazy_static! { pub static ref IS_ATTY: bool = is_atty(); static ref LOGGER_LEVEL: MessageType = get_logger_level(); + static ref LOGGER_TO_STDOUT: Arc> = Arc::new(RwLock::new(true)); static ref PRINT_MESSAGE_LOCK: Arc> = Arc::new(Mutex::new(())); } +pub fn set_logger_std_out(is_std_out: bool) { + let mut std_out = LOGGER_TO_STDOUT.write().unwrap(); + *std_out = is_std_out; +} + #[allow(clippy::upper_case_acronyms)] #[derive(Clone, Copy)] pub enum MessageType { DEBUG, INFO, OK, WARN, ERROR } @@ -16,9 +22,9 @@ impl MessageType { pub fn get_u8_value(&self) -> u8 { match self { MessageType::DEBUG => 0, - MessageType::INFO => 1, - MessageType::OK => 2, - MessageType::WARN => 3, + MessageType::INFO => 1, + MessageType::OK => 2, + MessageType::WARN => 3, MessageType::ERROR => 4, } } @@ -26,18 +32,18 @@ impl MessageType { pub fn get_logger_level() -> MessageType { if let Some(logger_level) = env::var("LOGGER_LEVEL").ok() - .or_else(|| env::var("LOGGER").ok()) - .or_else(|| env::var("LEVEL").ok()) { + .or_else(|| env::var("LOGGER").ok()) + .or_else(|| env::var("LEVEL").ok()) { match logger_level.trim().to_lowercase().as_str() { "debug" | "*" => MessageType::DEBUG, - "info" | "?" => MessageType::INFO, - "ok" | "#" => MessageType::OK, - "warn" | "!" => MessageType::WARN, + "info" | "?" => MessageType::INFO, + "ok" | "#" => MessageType::OK, + "warn" | "!" => MessageType::WARN, "error" | "^" => MessageType::ERROR, _ => { print_message_ex(Some(term::color::YELLOW), "[WARN ]", &format!("Unknown logger level: {}, set to default INFO", logger_level)); MessageType::INFO - }, + } } } else { MessageType::INFO @@ -49,42 +55,73 @@ pub fn is_atty() -> bool { stdout_fileno != 0 } -pub fn print_color(color: Option, is_bold: bool, m: &str) { - match term::stdout() { - Some(mut t) => { - if *IS_ATTY { - if let Some(c) = color { - t.fg(c).ok(); +pub fn print_color(is_std_out: bool, color: Option, is_bold: bool, m: &str) { + if is_std_out { + match term::stdout() { + Some(mut t) => { + if *IS_ATTY { + if let Some(c) = color { + t.fg(c).ok(); + } + if is_bold { + t.attr(term::Attr::Bold).ok(); + } + write!(t, "{}", m).ok(); + t.reset().ok(); + } else { + write!(t, "{}", m).ok(); } - if is_bold { - t.attr(term::Attr::Bold).ok(); - } - write!(t, "{}", m).ok(); - t.reset().ok(); - } else { - write!(t, "{}", m).ok(); } - }, - None => print!("{}", m), + None => print!("{}", m), + } + } else { + match term::stderr() { + Some(mut t) => { + if *IS_ATTY { + if let Some(c) = color { + t.fg(c).ok(); + } + if is_bold { + t.attr(term::Attr::Bold).ok(); + } + write!(t, "{}", m).ok(); + t.reset().ok(); + } else { + write!(t, "{}", m).ok(); + } + } + None => eprint!("{}", m), + } } } pub fn print_color_and_flush(color: Option, is_bold: bool, m: &str) { - print_color(color, is_bold, m); + print_color(true, color, is_bold, m); flush_stdout(); } pub fn print_message_ex(color: Option, h: &str, message: &str) { + let is_std_out = { + *LOGGER_TO_STDOUT.read().unwrap() + }; let mut lock = PRINT_MESSAGE_LOCK.lock().unwrap(); - print_color(color, true, h); - println!(" {}", message); + print_color(is_std_out, color, true, h); + if is_std_out { + println!(" {}", message); + } else { + eprintln!(" {}", message) + } *lock = (); } -pub fn print_ok (message: &str) { print_message(MessageType::OK, message); } -pub fn print_warn (message: &str) { print_message(MessageType::WARN, message); } +pub fn print_ok(message: &str) { print_message(MessageType::OK, message); } + +pub fn print_warn(message: &str) { print_message(MessageType::WARN, message); } + pub fn print_error(message: &str) { print_message(MessageType::ERROR, message); } -pub fn print_info (message: &str) { print_message(MessageType::INFO, message); } + +pub fn print_info(message: &str) { print_message(MessageType::INFO, message); } + pub fn print_debug(message: &str) { print_message(MessageType::DEBUG, message); } #[inline] @@ -102,10 +139,10 @@ pub fn when(mt: MessageType, f: F) where F: Fn() { pub fn print_message(mt: MessageType, message: &str) { if is_logger_level_enabled(mt) { match mt { - MessageType::OK => print_message_ex(Some(term::color::GREEN), "[OK ]", message), - MessageType::WARN => print_message_ex(Some(term::color::YELLOW), "[WARN ]", message), - MessageType::ERROR => print_message_ex(Some(term::color::RED), "[ERROR]", message), - MessageType::INFO => print_message_ex(None, "[INFO ]", message), + MessageType::OK => print_message_ex(Some(term::color::GREEN), "[OK ]", message), + MessageType::WARN => print_message_ex(Some(term::color::YELLOW), "[WARN ]", message), + MessageType::ERROR => print_message_ex(Some(term::color::RED), "[ERROR]", message), + MessageType::INFO => print_message_ex(None, "[INFO ]", message), MessageType::DEBUG => print_message_ex(Some(term::color::MAGENTA), "[DEBUG]", message), } } @@ -148,13 +185,13 @@ pub fn get_term_width_message(message: &str, left: usize) -> String { Some((w, _h)) => { let len = message.len(); if w > len { - return message.to_string(); + return message.to_string(); } let mut s = String::new(); s.push_str(&message[0..find_char_boundary(&message, w - 10 - 5 - left)]); s.push_str("[...]"); s.push_str(&message[find_char_boundary(&message, len - 10)..]); s - }, + } } }