use console::Term;
use tracing::Level;
use tracing_subscriber::EnvFilter;
#[derive(Debug, Clone, Copy, PartialEq, Eq)]
pub enum OutputMode {
Cli,
Mcp,
}
#[derive(Debug)]
pub struct OutputConfig {
mode: OutputMode,
color_enabled: bool,
log_level: Level,
}
impl OutputConfig {
pub fn new(mode: OutputMode) -> Self {
let color_enabled = match mode {
OutputMode::Cli => Term::stdout().features().colors_supported(),
OutputMode::Mcp => false, };
let log_level = match std::env::var("RUST_LOG") {
Ok(level) => match level.to_lowercase().as_str() {
"trace" => Level::TRACE,
"debug" => Level::DEBUG,
"info" => Level::INFO,
"warn" => Level::WARN,
"error" => Level::ERROR,
_ => match mode {
OutputMode::Cli => Level::INFO,
OutputMode::Mcp => Level::WARN, },
},
Err(_) => match mode {
OutputMode::Cli => Level::INFO,
OutputMode::Mcp => Level::WARN,
},
};
Self {
mode,
color_enabled,
log_level,
}
}
pub fn mode(&self) -> OutputMode {
self.mode
}
pub fn colors_enabled(&self) -> bool {
self.color_enabled
}
pub fn log_level(&self) -> Level {
self.log_level
}
pub fn set_verbose(&mut self) {
self.log_level = Level::DEBUG;
}
pub fn init_tracing(&self) {
let builder = tracing_subscriber::fmt()
.with_env_filter(EnvFilter::from_default_env().add_directive(self.log_level.into()))
.with_target(false)
.with_level(true);
match self.mode {
OutputMode::Cli => {
builder
.with_ansi(self.color_enabled)
.with_writer(std::io::stderr)
.init();
}
OutputMode::Mcp => {
builder
.with_ansi(false)
.with_writer(std::io::stderr)
.without_time() .compact() .init();
}
}
}
}