1use {
4 lazy_static::lazy_static,
5 std::sync::{Arc, RwLock},
6};
7
8lazy_static! {
9 static ref LOGGER: Arc<RwLock<env_logger::Logger>> =
10 Arc::new(RwLock::new(env_logger::Logger::from_default_env()));
11}
12
13pub const DEFAULT_FILTER: &str = "solana=info,agave=info";
14
15struct LoggerShim {}
16
17impl log::Log for LoggerShim {
18 fn enabled(&self, metadata: &log::Metadata) -> bool {
19 LOGGER.read().unwrap().enabled(metadata)
20 }
21
22 fn log(&self, record: &log::Record) {
23 LOGGER.read().unwrap().log(record);
24 }
25
26 fn flush(&self) {}
27}
28
29fn replace_logger(logger: env_logger::Logger) {
30 log::set_max_level(logger.filter());
31 *LOGGER.write().unwrap() = logger;
32 let _ = log::set_boxed_logger(Box::new(LoggerShim {}));
33}
34
35pub fn setup_with(filter: &str) {
39 let logger =
40 env_logger::Builder::from_env(env_logger::Env::new().filter_or("_RUST_LOG", filter))
41 .format_timestamp_nanos()
42 .build();
43 replace_logger(logger);
44}
45
46pub fn setup_with_default(filter: &str) {
48 let logger = env_logger::Builder::from_env(env_logger::Env::new().default_filter_or(filter))
49 .format_timestamp_nanos()
50 .build();
51 replace_logger(logger);
52}
53
54pub fn setup_with_default_filter() {
56 setup_with_default(DEFAULT_FILTER);
57}
58
59pub fn setup() {
61 setup_with_default("error");
62}
63
64pub fn setup_file_with_default(logfile: &str, filter: &str) {
66 use std::fs::OpenOptions;
67 let file = OpenOptions::new()
68 .create(true)
69 .append(true)
70 .open(logfile)
71 .unwrap();
72 let logger = env_logger::Builder::from_env(env_logger::Env::new().default_filter_or(filter))
73 .format_timestamp_nanos()
74 .target(env_logger::Target::Pipe(Box::new(file)))
75 .build();
76 replace_logger(logger);
77}