use crate::template::{Context, find, parse}; use std::fs::write; use std::io::{Error, Result}; use std::path::Path; const FILENAME: &str = "index.html"; pub fn generate( _: &Path, template_directory: &Path, target: &Path, context: &Context, ) -> Result<()> { if let Some(template) = find(template_directory, FILENAME) { let parsed_template = parse(&template).ok_or_else(|| Error::other("Unable to parse HTML template"))?; let rendered_template = parsed_template.render(context)?; let location = target.join(FILENAME); write(location, rendered_template)?; } Ok(()) } #[cfg(test)] mod tests { use std::collections::HashMap; use std::fs::create_dir_all; use super::*; use crate::template::Value; use test_utilities::*; #[test] fn test_generates_html_with_default_layout() { let test_dir = setup_test_dir(); let static_dir = test_dir.join("static"); let template_dir = test_dir.join("templates"); let output_dir = test_dir.join("output"); create_dir_all(&static_dir).expect("Could not create static directory"); create_dir_all(&template_dir).expect("Could not create template directory"); create_dir_all(&output_dir).expect("Could not create output directory"); let context = HashMap::from([ ("has_posts".to_string(), Value::Bool(true)), ( "posts".to_string(), Value::Collection(vec![ HashMap::from([ ("index".to_string(), Value::Unsigned(2828)), ( "html".to_string(), Value::String("

Contextualization

".to_string()), ), ]), HashMap::from([ ("index".to_string(), Value::Unsigned(2828)), ( "html".to_string(), Value::String("

Contexternalization

".to_string()), ), ]), ]), ), ]); generate(&static_dir, &template_dir, &output_dir, &context).expect("Generate failed"); assert_file_contains(&output_dir.join("index.html"), "

Contextualization

"); assert_file_contains(&output_dir.join("index.html"), "

Contexternalization

"); cleanup_test_dir(&test_dir); } #[test] fn test_uses_custom_layout_if_available() { let test_dir = setup_test_dir(); let static_dir = test_dir.join("static"); let template_dir = test_dir.join("templates"); let output_dir = test_dir.join("output"); create_dir_all(&static_dir).expect("Could not create static directory"); create_dir_all(&template_dir).expect("Could not create template directory"); create_dir_all(&output_dir).expect("Could not create output directory"); create_test_file( &template_dir.join("index.html"), "\ {{~ posts:post }} {{= post.html }} {{~}} ", ); let context = HashMap::from([( "posts".to_string(), Value::Collection(vec![ HashMap::from([( "html".to_string(), Value::String("

Recontextualization

".to_string()), )]), HashMap::from([( "html".to_string(), Value::String("

Recontexternalization

".to_string()), )]), ]), )]); generate(&static_dir, &template_dir, &output_dir, &context).expect("Generate failed"); assert_file_contents( &output_dir.join("index.html"), "\

Recontextualization

Recontexternalization

", ); cleanup_test_dir(&test_dir); } #[test] fn test_fails_if_html_is_malformed() { let test_dir = setup_test_dir(); let static_dir = test_dir.join("static"); let template_dir = test_dir.join("templates"); let output_dir = test_dir.join("output"); create_dir_all(&static_dir).expect("Could not create static directory"); create_dir_all(&template_dir).expect("Could not create template directory"); create_dir_all(&output_dir).expect("Could not create output directory"); create_test_file( &template_dir.join("index.html"), "\ {{~ posts:post }} {{ post.html }} {{~}} ", ); let context = HashMap::new(); let result = generate(&static_dir, &template_dir, &output_dir, &context); assert!(result.is_err()); cleanup_test_dir(&test_dir); } #[test] fn test_fails_if_output_is_not_writable() { let test_dir = setup_test_dir(); let static_dir = test_dir.join("static"); let template_dir = test_dir.join("templates"); let output_dir = test_dir.join("output"); create_dir_all(&template_dir).expect("Could not create template directory"); create_test_file( &template_dir.join("index.html"), "\ {{~ posts:post }} {{= post.html }} {{~}} ", ); let context = HashMap::from([( "posts".to_string(), Value::Collection(vec![ HashMap::from([( "html".to_string(), Value::String("

Recontextualization

".to_string()), )]), HashMap::from([( "html".to_string(), Value::String("

Recontexternalization

".to_string()), )]), ]), )]); let result = generate(&static_dir, &template_dir, &output_dir, &context); assert!(result.is_err()); cleanup_test_dir(&test_dir); } }