Skip to main content

infinity_build_core/
artifact.rs

1use std::path::{Path, PathBuf};
2
3#[derive(Debug, Clone)]
4pub struct GeneratedFile {
5    pub path: PathBuf,
6    pub size_bytes: u64,
7    pub kind: FileKind,
8}
9
10#[derive(Debug, Clone, Copy, PartialEq, Eq)]
11pub enum FileKind {
12    Script,
13    Style,
14    Template,
15    Wasm,
16    SourceMap,
17    Other,
18}
19
20pub trait Artifact {
21    fn files(&self) -> &[GeneratedFile];
22
23    fn primary(&self) -> Option<&GeneratedFile> {
24        self.files().first()
25    }
26
27    fn total_bytes(&self) -> u64 {
28        self.files().iter().map(|f| f.size_bytes).sum()
29    }
30
31    fn name(&self) -> &str;
32}
33
34#[derive(Debug, Clone)]
35pub struct SimpleArtifact {
36    pub name: String,
37    pub files: Vec<GeneratedFile>,
38}
39
40impl SimpleArtifact {
41    pub fn new(name: impl Into<String>, files: Vec<GeneratedFile>) -> Self {
42        Self {
43            name: name.into(),
44            files,
45        }
46    }
47}
48
49impl Artifact for SimpleArtifact {
50    fn files(&self) -> &[GeneratedFile] {
51        &self.files
52    }
53
54    fn name(&self) -> &str {
55        &self.name
56    }
57
58    fn primary(&self) -> Option<&GeneratedFile> {
59        pick_primary(&self.files)
60    }
61}
62
63/// Pick the most natural "primary" file given a list. The JS bundle
64/// wins, then the HTML template, then anything else. Useful as a
65/// default for [`Artifact::primary`].
66pub fn pick_primary(files: &[GeneratedFile]) -> Option<&GeneratedFile> {
67    files
68        .iter()
69        .find(|f| matches!(f.kind, FileKind::Script))
70        .or_else(|| files.iter().find(|f| matches!(f.kind, FileKind::Template)))
71        .or_else(|| files.first())
72}
73
74/// Stat a file on disk and produce a [`GeneratedFile`]. Backends
75/// typically wrap the [`std::io::Error`] in [`crate::BuildError::io`].
76pub fn stat_file(path: &Path, kind: FileKind) -> std::io::Result<GeneratedFile> {
77    let meta = std::fs::metadata(path)?;
78    Ok(GeneratedFile {
79        path: path.to_path_buf(),
80        size_bytes: meta.len(),
81        kind,
82    })
83}