use lazy_static::lazy_static;
use log::{Level, Log, Metadata, Record, SetLoggerError};
use std::fs::OpenOptions;
use std::sync::Mutex;
lazy_static! {
pub static ref LOG_FILE: Mutex<std::fs::File> = {
Mutex::new(
OpenOptions::new()
.create(true)
.append(true)
.open("btcli_app.log")
.expect("无法创建日志文件"),
)
};
}
#[macro_export]
macro_rules! log_to_file {
($($arg:tt)*) => {
if let Ok(config) = crate::conf::try_init_conf() {
if config.enable_logging {
if let Ok(mut file) = crate::LOG_FILE.lock() {
use std::io::Write;
let log_msg = format!("[{}] {}\n", chrono::Local::now().format("%Y-%m-%d %H:%M:%S"), format_args!($($arg)*));
let _ = file.write_all(log_msg.as_bytes());
let _ = file.flush(); }
}
} else {
if let Ok(mut file) = crate::LOG_FILE.lock() {
use std::io::Write;
let log_msg = format!("[{}] {}\n", chrono::Local::now().format("%Y-%m-%d %H:%M:%S"), format_args!($($arg)*));
let _ = file.write_all(log_msg.as_bytes());
let _ = file.flush(); }
}
};
}
pub struct FileLogger;
impl Log for FileLogger {
fn enabled(&self, metadata: &Metadata) -> bool {
if let Ok(config) = crate::conf::try_init_conf() {
config.enable_logging && metadata.level() <= Level::Info
} else {
metadata.level() <= Level::Info
}
}
fn log(&self, record: &Record) {
if self.enabled(record.metadata()) {
if let Ok(mut file) = LOG_FILE.lock() {
use std::io::Write;
let log_msg = format!(
"[{}] [{}] {}\n",
chrono::Local::now().format("%Y-%m-%d %H:%M:%S"),
record.level(),
record.args()
);
let _ = file.write_all(log_msg.as_bytes());
let _ = file.flush();
}
}
}
fn flush(&self) {
if let Ok(file) = LOG_FILE.lock() {
let _ = file.sync_all();
}
}
}
impl FileLogger {
pub fn init() -> Result<(), SetLoggerError> {
log::set_boxed_logger(Box::new(FileLogger))
.map(|()| log::set_max_level(log::LevelFilter::Info))
}
}
pub mod cli;
pub mod conf;
pub mod expect_react;
pub mod extract_help;
pub mod fancy_egg;
pub mod fycore;
pub mod fyerrcodes;
#[cfg(feature = "ui")]
pub mod ui;
mod fydocsrv;