use log::warn;
use super::Result;
use std::fs::{self, File};
use std::io::prelude::*;
use std::path::{Path, PathBuf};
#[derive(Debug)]
pub enum Asset {
Disk(PathBuf),
Internal(InternalAsset),
}
#[derive(Debug)]
pub struct InternalAsset {
contents: &'static str,
name: &'static str,
}
impl Asset {
pub const fn internal(name: &'static str, contents: &'static str) -> Self {
Asset::Internal(InternalAsset { name, contents })
}
pub const fn path(path: PathBuf) -> Self {
Asset::Disk(path)
}
pub fn copy_to(&self, output: &Path) -> Result<()> {
match self {
Asset::Internal(int) => {
let path = output.join(int.name);
let mut file = File::create(&path)?;
write!(file, "{}", int.contents)?;
Ok(())
}
Asset::Disk(path) => copy_single(&path, output),
}
}
}
fn copy_single(path: &Path, target: &Path) -> Result<()> {
if path.is_dir() {
let mut target = PathBuf::from(target);
target.push(path.file_name().unwrap());
if !target.exists() {
fs::create_dir(&target)?;
}
copy_recurse(path, &target)?;
} else if let Some(name) = path.file_name() {
fs::copy(path, target.join(name))?;
} else {
warn!("Asset at {:?} does not appear to be copyable", path);
}
Ok(())
}
fn copy_recurse(source: &Path, target: &Path) -> Result<()> {
for entry in fs::read_dir(source)? {
let entry = entry?;
let path = entry.path();
copy_single(&path, target)?;
}
Ok(())
}