use sha2::{Digest, Sha256};

use crate::command::BundleSpec;

pub fn shared_bundle_id<R: std::io::Read + ?Sized>(
    spec: &BundleSpec<'_, R>,
    archive_digests: &[String],
) -> String {
    let mut hasher = Sha256::new();
    hasher.update(b"bdlx-bundle-v1\0");
    hasher.update(spec.cleanup.as_shell_value().as_bytes());
    hasher.update(b"\0");
    hasher.update(if spec.shared {
        &b"shared"[..]
    } else {
        &b"fresh"[..]
    });
    hasher.update(b"\0");

    for digest in archive_digests {
        hasher.update(b"archive\0");
        hasher.update(digest.as_bytes());
        hasher.update(b"\0");
    }

    for env in &spec.env {
        hasher.update(b"env\0");
        hasher.update(env.name.as_bytes());
        hasher.update(b"\0");
        hasher.update(env.value.as_bytes());
        hasher.update(b"\0");
    }

    hasher.update(b"cmd\0");
    hasher.update(spec.command.program.as_bytes());
    hasher.update(b"\0");
    for arg in &spec.command.args {
        hasher.update(arg.as_bytes());
        hasher.update(b"\0");
    }
    hex::encode(hasher.finalize())
}
