diff --git a/Cargo.toml b/Cargo.toml index cf461bf..c210775 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -80,10 +80,10 @@ ssg = [ # Full SSG functionality "dep:pulldown-cmark", "dep:tokio", "dep:dtt", - "dep:log", + # "dep:log", "dep:url", ] -logging = ["dep:log"] # Optional logging feature +# logging = ["dep:log"] # Optional logging feature # ----------------------------------------------------------------------------- # Dependencies @@ -95,12 +95,14 @@ anyhow = "1.0.93" serde = { version = "1.0.215", features = ["derive"] } serde_json = "1.0.133" serde_yml = "0.0.12" +time = { version = "0.3.36", features = ["formatting", "local-offset"] } + thiserror = "2.0.3" toml = "0.8.19" uuid = { version = "1.11.0", features = ["v4", "serde"] } # Optional logging (only included when "logging" feature is enabled) -log = { version = "0.4.22", optional = true } +log = "0.4.22" # Optional CLI and SSG dependencies - all must have optional = true clap = { version = "4.5.21", features = ["derive"], optional = true } diff --git a/README.md b/README.md index 7402e0c..008c2d7 100644 --- a/README.md +++ b/README.md @@ -41,27 +41,26 @@ This crate provides several feature flags to customise its functionality: - **default**: Core frontmatter parsing functionality only - **cli**: Command-line interface tools for quick operations - **ssg**: Static Site Generator functionality (includes CLI features) -- **logging**: Enables debug logging via the `log` crate (can be combined with other features) You can combine multiple features as needed: ```toml [dependencies] # Enable logging with CLI support -frontmatter-gen = { version = "0.0.4", features = ["cli", "logging"] } +frontmatter-gen = { version = "0.0.4", features = ["cli"] } # Enable all features -frontmatter-gen = { version = "0.0.4", features = ["ssg", "logging"] } +frontmatter-gen = { version = "0.0.4", features = ["ssg"] } ``` When installing via cargo install: ```bash # Install with CLI and logging support -cargo install frontmatter-gen --features="cli,logging" +cargo install frontmatter-gen --features="cli" # Install with SSG and logging support -cargo install frontmatter-gen --features="ssg,logging" +cargo install frontmatter-gen --features="ssg" ``` ## Getting Started 📦 @@ -271,14 +270,42 @@ When the `logging` feature is enabled, the library integrates with Rust's `log` ```rust use frontmatter_gen::extract; -use env_logger::Builder; -use log::LevelFilter; +use log::{debug, info, Level, Metadata, Record, set_logger, set_max_level}; + +struct SimpleLogger; + +impl log::Log for SimpleLogger { + fn enabled(&self, metadata: &Metadata) -> bool { + metadata.level() <= Level::Debug + } + + fn log(&self, record: &Record) { + if self.enabled(record.metadata()) { + println!( + "{} [{}] - {}", + record.target(), + record.level(), + record.args() + ); + } + } + + fn flush(&self) {} +} + +static LOGGER: SimpleLogger = SimpleLogger; + +fn init_logger() { + // Explicitly handle logger initialization error + if let Err(e) = set_logger(&LOGGER).map(|()| set_max_level(Level::Debug.to_level_filter())) { + eprintln!("Failed to initialize logger: {}", e); + } +} fn main() -> Result<(), Box> { - // Initialize logging with debug level - Builder::new() - .filter_level(LevelFilter::Debug) - .init(); + // Initialize the custom logger + init_logger(); + info!("Starting frontmatter extraction"); let content = r#"--- title: My Document @@ -286,9 +313,11 @@ date: 2025-09-09 --- # Content"#; - // Logging will now show detailed debug information + // Extract frontmatter and remaining content let (frontmatter, content) = extract(content)?; - + debug!("Extracted frontmatter: {:?}", frontmatter); + debug!("Remaining content: {:?}", content); + Ok(()) } ``` @@ -299,31 +328,40 @@ For more control over logging: ```rust use frontmatter_gen::{parser, Format}; -use env_logger::Builder; -use log::{LevelFilter, debug, info, warn}; -use std::io::Write; +use log::{debug, info, Level, Metadata, Record, set_logger, set_max_level}; -fn main() -> Result<(), Box> { - // Configure logging with timestamps and module paths - Builder::new() - .format(|buf, record| { - writeln!(buf, - "{} [{}] - {}", - chrono::Local::now().format("%Y-%m-%d %H:%M:%S"), - record.level(), - record.args() - ) - }) - .filter_module("frontmatter_gen", LevelFilter::Debug) - .filter_module("your_app", LevelFilter::Info) - .init(); +struct SimpleLogger; + +impl log::Log for SimpleLogger { + fn enabled(&self, metadata: &Metadata) -> bool { + metadata.level() <= Level::Debug + } + + fn log(&self, record: &Record) { + if self.enabled(record.metadata()) { + println!("[{}] - {}", record.level(), record.args()); + } + } - // Your frontmatter operations will now log detailed information + fn flush(&self) {} +} + +static LOGGER: SimpleLogger = SimpleLogger; + +fn init_logger() { + set_logger(&LOGGER).expect("Failed to set logger"); + set_max_level(Level::Debug.to_level_filter()); +} + +fn main() -> Result<(), Box> { + // Initialize the custom logger + init_logger(); info!("Starting frontmatter processing"); + let yaml = r#"title: Test Document"#; let frontmatter = parser::parse(yaml, Format::Yaml)?; debug!("Parsed frontmatter: {:?}", frontmatter); - + Ok(()) } ``` diff --git a/src/engine.rs b/src/engine.rs index cbd1cfa..fcb11d7 100644 --- a/src/engine.rs +++ b/src/engine.rs @@ -120,7 +120,6 @@ pub struct Engine { impl Engine { /// Creates a new `Engine` instance. pub fn new() -> Result { - #[cfg(feature = "logging")] log::debug!("Initializing SSG Engine"); Ok(Self { @@ -135,7 +134,6 @@ impl Engine { /// Orchestrates the complete site generation process. pub async fn generate(&self, config: &Config) -> Result<()> { - #[cfg(feature = "logging")] log::info!("Starting site generation"); fs::create_dir_all(&config.output_dir) @@ -147,7 +145,6 @@ impl Engine { self.generate_pages(config).await?; self.copy_assets(config).await?; - #[cfg(feature = "logging")] log::info!("Site generation completed successfully"); Ok(()) @@ -155,7 +152,6 @@ impl Engine { /// Loads and caches all templates from the template directory. pub async fn load_templates(&self, config: &Config) -> Result<()> { - #[cfg(feature = "logging")] log::debug!( "Loading templates from: {}", config.template_dir.display() @@ -184,7 +180,6 @@ impl Engine { content, ); - #[cfg(feature = "logging")] log::debug!( "Loaded template: {}", name.to_string_lossy() @@ -201,7 +196,6 @@ impl Engine { &self, config: &Config, ) -> Result<()> { - #[cfg(feature = "logging")] log::debug!( "Processing content files from: {}", config.content_dir.display() @@ -218,7 +212,6 @@ impl Engine { self.process_content_file(&path, config).await?; let _ = content_cache.insert(path.clone(), content); - #[cfg(feature = "logging")] log::debug!( "Processed content file: {}", path.display() @@ -280,7 +273,6 @@ impl Engine { template: &str, content: &ContentFile, ) -> Result { - #[cfg(feature = "logging")] log::debug!( "Rendering template for: {}", content.dest_path.display() @@ -308,7 +300,6 @@ impl Engine { pub async fn copy_assets(&self, config: &Config) -> Result<()> { let assets_dir = config.content_dir.join("assets"); if assets_dir.exists() { - #[cfg(feature = "logging")] log::debug!( "Copying assets from: {}", assets_dir.display() @@ -357,7 +348,6 @@ impl Engine { /// Generates HTML pages from processed content files. pub async fn generate_pages(&self, _config: &Config) -> Result<()> { - #[cfg(feature = "logging")] log::info!("Generating HTML pages"); let content_cache = self.content_cache.read().await; @@ -393,7 +383,6 @@ impl Engine { fs::write(&content_file.dest_path, rendered_html).await?; - #[cfg(feature = "logging")] log::debug!( "Generated page: {}", content_file.dest_path.display()