From 17470acb72b450bde5ee3fb228c262b294393777 Mon Sep 17 00:00:00 2001 From: Guillaume Gomez Date: Thu, 17 Jul 2025 18:00:23 +0200 Subject: [PATCH] Add `build.static-files-dir` config option --- src/config.rs | 5 +++++ src/renderer/html_handlebars/hbs_renderer.rs | 8 ++++++-- src/renderer/html_handlebars/static_files.rs | 19 ++++++++++++++++--- 3 files changed, 27 insertions(+), 5 deletions(-) diff --git a/src/config.rs b/src/config.rs index 7ef8bcef12..e887fa1743 100644 --- a/src/config.rs +++ b/src/config.rs @@ -496,6 +496,8 @@ pub struct BuildConfig { pub use_default_preprocessors: bool, /// Extra directories to trigger rebuild when watching/serving pub extra_watch_dirs: Vec, + /// Directory where to store static files. + pub static_files_dir: Option, } impl Default for BuildConfig { @@ -505,6 +507,7 @@ impl Default for BuildConfig { create_missing: true, use_default_preprocessors: true, extra_watch_dirs: Vec::new(), + static_files_dir: None, } } } @@ -872,6 +875,7 @@ mod tests { create_missing: false, use_default_preprocessors: true, extra_watch_dirs: Vec::new(), + static_files_dir: None, }; let rust_should_be = RustConfig { edition: None }; let playground_should_be = Playground { @@ -1083,6 +1087,7 @@ mod tests { create_missing: true, use_default_preprocessors: true, extra_watch_dirs: Vec::new(), + static_files_dir: None, }; let html_should_be = HtmlConfig { diff --git a/src/renderer/html_handlebars/hbs_renderer.rs b/src/renderer/html_handlebars/hbs_renderer.rs index b1ea752053..067dfc51d2 100644 --- a/src/renderer/html_handlebars/hbs_renderer.rs +++ b/src/renderer/html_handlebars/hbs_renderer.rs @@ -415,12 +415,16 @@ impl Renderer for HtmlHandlebars { } if html_config.hash_files { - static_files.hash_files()?; + static_files.hash_files(ctx.config.build.static_files_dir.as_deref())?; } debug!("Copy static files"); + if let Some(ref path) = ctx.config.build.static_files_dir { + fs::create_dir_all(path) + .with_context(|| "Unexpected error when constructing static files directory")?; + } let resource_helper = static_files - .write_files(&destination) + .write_files(destination) .with_context(|| "Unable to copy across static files")?; handlebars.register_helper("resource", Box::new(resource_helper)); diff --git a/src/renderer/html_handlebars/static_files.rs b/src/renderer/html_handlebars/static_files.rs index e1531f4209..91e8df7d68 100644 --- a/src/renderer/html_handlebars/static_files.rs +++ b/src/renderer/html_handlebars/static_files.rs @@ -167,9 +167,19 @@ impl StaticFiles { /// Updates this [`StaticFiles`] to hash the contents for determining the /// filename for each resource. - pub fn hash_files(&mut self) -> Result<()> { + pub fn hash_files(&mut self, static_folder: Option<&Path>) -> Result<()> { use sha2::{Digest, Sha256}; use std::io::Read; + + fn apply_static_folder(name: String, static_folder: Option<&Path>) -> String { + if let Some(static_folder) = static_folder { + if let Some(file_name) = name.split('/').last() { + return static_folder.join(file_name).display().to_string(); + } + } + name + } + for static_file in &mut self.static_files { match static_file { StaticFile::Builtin { @@ -187,7 +197,10 @@ impl StaticFiles { && !name.starts_with("FontAwesome/fonts/") { let hex = hex::encode(&Sha256::digest(data)[..4]); - let new_filename = format!("{}-{}.{}", name, hex, suffix); + let new_filename = apply_static_folder( + format!("{}-{}.{}", name, hex, suffix), + static_folder, + ); self.hash_map.insert(filename.clone(), new_filename.clone()); *filename = new_filename; } @@ -229,7 +242,7 @@ impl StaticFiles { pub fn write_files(self, destination: &Path) -> Result { use crate::utils::fs::write_file; use regex::bytes::{Captures, Regex}; - // The `{{ resource "name" }}` directive in static resources look like + // The `{{ resource "name" }}` directive in static resources looks like // handlebars syntax, even if they technically aren't. static RESOURCE: LazyLock = LazyLock::new(|| Regex::new(r#"\{\{ resource "([^"]+)" \}\}"#).unwrap());