use crate::bootloader::FileEntry;
use crate::config::BootType;
use crate::core::context::Context;
use crate::core::error::Result;
use std::path::PathBuf;
#[cfg(feature = "iso")]
pub mod iso;
#[cfg(feature = "fat")]
pub mod fat;
pub mod directory;
mod template;
pub use template::TemplateProcessor;
pub trait ImageBuilder: Send + Sync {
fn build(&self, ctx: &Context, files: &[FileEntry]) -> Result<PathBuf>;
fn needs_rebuild(&self, ctx: &Context) -> Result<bool> {
let _ = ctx;
Ok(true)
}
fn output_path(&self, ctx: &Context) -> PathBuf;
fn supported_boot_types(&self) -> &[BootType];
fn clean(&self, ctx: &Context) -> Result<()> {
let output = self.output_path(ctx);
if output.exists() {
if output.is_dir() {
std::fs::remove_dir_all(&output)?;
} else {
std::fs::remove_file(&output)?;
}
}
Ok(())
}
fn name(&self) -> &str;
fn validate_boot_type(&self, ctx: &Context) -> Result<()> {
let configured = ctx.config.boot.boot_type;
let supported = self.supported_boot_types();
let is_supported = supported.iter().any(|&bt| match (bt, configured) {
(a, b) if a == b => true,
(BootType::Hybrid, _) | (_, BootType::Hybrid) => true,
_ => false,
});
if !is_supported {
return Err(crate::core::error::Error::unsupported(format!(
"{} does not support {:?} boot type (supported: {:?})",
self.name(),
configured,
supported
)));
}
Ok(())
}
}