From c7dc1a0173a14e9cb52adcb09ae566cf7eeb314a Mon Sep 17 00:00:00 2001 From: Hermes Agent Date: Wed, 12 Aug 2026 06:02:57 +0000 Subject: Protect companion manifests from overwrite --- src/build.rs | 4 ++++ src/manifest.rs | 10 ++++++++-- 2 files changed, 12 insertions(+), 2 deletions(-) (limited to 'src') diff --git a/src/build.rs b/src/build.rs index 42c57ef..fcacfc0 100644 --- a/src/build.rs +++ b/src/build.rs @@ -42,6 +42,10 @@ impl BuildExecutor { if artifact.exists() { bail!("output artifact already exists; refusing to overwrite it: {}", artifact.display()); } + let manifest = ArtifactManifest::path_beside(artifact)?; + if manifest.exists() { + bail!("output manifest already exists; refusing to overwrite it: {}", manifest.display()); + } let parent = artifact .parent() .filter(|parent| !parent.as_os_str().is_empty()) diff --git a/src/manifest.rs b/src/manifest.rs index 0848a98..4cd256c 100644 --- a/src/manifest.rs +++ b/src/manifest.rs @@ -1,6 +1,6 @@ use std::collections::{BTreeMap, HashSet}; use std::fs; -use std::io::Read; +use std::io::{Read, Write}; use std::os::unix::fs::MetadataExt; use std::path::{Path, PathBuf}; @@ -51,7 +51,13 @@ impl ArtifactManifest { pub fn write_beside(&self, artifact: impl AsRef) -> Result { let path = Self::path_beside(artifact)?; let text = toml::to_string_pretty(self).context("serialize artifact manifest")?; - fs::write(&path, text).with_context(|| format!("write artifact manifest {}", path.display()))?; + fs::OpenOptions::new() + .write(true) + .create_new(true) + .open(&path) + .with_context(|| format!("create artifact manifest {}", path.display()))? + .write_all(text.as_bytes()) + .with_context(|| format!("write artifact manifest {}", path.display()))?; Ok(path) } -- cgit v1.2.3