fad06fd
mod dist_embed {
include!(concat!(env!("OUT_DIR"), "/dist_embed.rs"));
}
#[derive(Debug, Clone, Copy, PartialEq, Eq)]
pub struct Asset {
pub path: &'static str,
pub mime: &'static str,
pub content: &'static [u8],
}
pub fn index() -> Asset {
Asset {
path: "index.html",
mime: "text/html; charset=utf-8",
content: dist_embed::INDEX,
}
}
pub fn file(path: &str) -> Option<Asset> {
let key = normalize(path)?;
if key.is_empty() || key == "index.html" {
return Some(index());
}
dist_embed::FILES
.iter()
.find(|(p, _)| *p == key.as_str())
.map(|(p, content)| Asset {
path: p,
mime: mime_of(p),
content,
})
}
pub fn exists(path: &str) -> bool {
match normalize(path) {
None => false,
Some(key) => {
key.is_empty()
|| key == "index.html"
|| dist_embed::FILES.iter().any(|(p, _)| *p == key.as_str())
}
}
}
pub fn paths() -> &'static [&'static str] {
dist_embed::PATHS
}
fn normalize(path: &str) -> Option<String> {
let path = path.split(['?', '#']).next().unwrap_or(path);
let mut segs: Vec<&str> = Vec::new();
for seg in path.split('/') {
match seg {
"" | "." => {}
".." => return None,
s => segs.push(s),
}
}
Some(segs.join("/"))
}
fn mime_of(path: &str) -> &'static str {
let ext = path
.rsplit_once('.')
.map_or("", |(_, e)| e)
.to_ascii_lowercase();
match ext.as_str() {
"html" | "htm" => "text/html; charset=utf-8",
"js" | "mjs" => "text/javascript; charset=utf-8",
"css" => "text/css; charset=utf-8",
"json" | "map" => "application/json",
"webmanifest" => "application/manifest+json",
"svg" => "image/svg+xml",
"png" => "image/png",
"jpg" | "jpeg" => "image/jpeg",
"gif" => "image/gif",
"webp" => "image/webp",
"avif" => "image/avif",
"ico" => "image/x-icon",
"wasm" => "application/wasm",
"ttf" => "font/ttf",
"otf" => "font/otf",
"woff" => "font/woff",
"woff2" => "font/woff2",
"eot" => "application/vnd.ms-fontobject",
"txt" => "text/plain; charset=utf-8",
"xml" => "application/xml",
"pdf" => "application/pdf",
_ => "application/octet-stream",
}
}