Skip to content

Commit 7f95550

Browse files
committed
twoliter: centralize toolsdir creation
Delete and re-create the tools dir inside of the install_tools function instead of requiring the caller to do it. This will lead to fewer bugs.
1 parent bf9fbba commit 7f95550

File tree

5 files changed

+73
-30
lines changed

5 files changed

+73
-30
lines changed

twoliter/src/cmd/build.rs

Lines changed: 0 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -50,9 +50,6 @@ impl BuildVariant {
5050
let project = project::load_or_find_project(self.project_path.clone()).await?;
5151
let token = project.token();
5252
let toolsdir = project.project_dir().join("build/tools");
53-
// Ignore errors because we want to proceed even if the directory does not exist.
54-
let _ = fs::remove_dir_all(&toolsdir).await;
55-
fs::create_dir_all(&toolsdir).await?;
5653
install_tools(&toolsdir).await?;
5754
let makefile_path = toolsdir.join("Makefile.toml");
5855
// A temporary directory in the `build` directory

twoliter/src/cmd/debug.rs

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,3 @@
1-
use crate::common::fs;
21
use crate::tools::install_tools;
32
use anyhow::Result;
43
use clap::Parser;
@@ -49,7 +48,6 @@ impl CheckToolArgs {
4948
.install_dir
5049
.clone()
5150
.unwrap_or_else(|| env::temp_dir().join(unique_name()));
52-
fs::create_dir_all(&dir).await?;
5351
install_tools(&dir).await?;
5452
println!("{}", dir.display());
5553
Ok(())

twoliter/src/cmd/make.rs

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,4 @@
11
use crate::cargo_make::CargoMake;
2-
use crate::common::fs;
32
use crate::project::{self};
43
use crate::tools::install_tools;
54
use anyhow::Result;
@@ -35,7 +34,6 @@ impl Make {
3534
pub(super) async fn run(&self) -> Result<()> {
3635
let project = project::load_or_find_project(self.project_path.clone()).await?;
3736
let toolsdir = project.project_dir().join("build/tools");
38-
let _ = fs::remove_dir_all(&toolsdir).await;
3937
install_tools(&toolsdir).await?;
4038
let makefile_path = toolsdir.join("Makefile.toml");
4139
CargoMake::new(&project, &self.arch)?

twoliter/src/common.rs

Lines changed: 49 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -64,6 +64,7 @@ pub(crate) async fn exec(cmd: &mut Command, quiet: bool) -> Result<Option<String
6464
pub(crate) mod fs {
6565
use anyhow::{Context, Result};
6666
use std::fs::Metadata;
67+
use std::io::ErrorKind;
6768
use std::path::{Path, PathBuf};
6869
use tokio::fs;
6970

@@ -130,10 +131,19 @@ pub(crate) mod fs {
130131
}
131132

132133
pub(crate) async fn remove_dir_all(path: impl AsRef<Path>) -> Result<()> {
133-
fs::remove_dir_all(path.as_ref()).await.context(format!(
134-
"Unable to remove directory (remove_dir_all) '{}'",
135-
path.as_ref().display()
136-
))
134+
match fs::remove_dir_all(path.as_ref()).await {
135+
Ok(_) => Ok(()),
136+
Err(e) => match e.kind() {
137+
ErrorKind::NotFound => {
138+
// not a problem, the directory isn't there
139+
Ok(())
140+
}
141+
_ => Err(e).context(format!(
142+
"Unable to remove directory (remove_dir_all) '{}'",
143+
path.as_ref().display()
144+
)),
145+
},
146+
}
137147
}
138148

139149
pub(crate) async fn rename(from: impl AsRef<Path>, to: impl AsRef<Path>) -> Result<()> {
@@ -163,3 +173,38 @@ pub(crate) mod fs {
163173
.context(format!("Unable to write to '{}'", path.as_ref().display()))
164174
}
165175
}
176+
177+
#[tokio::test]
178+
async fn test_remove_dir_all_no_dir() {
179+
use crate::common::fs;
180+
use tempfile::TempDir;
181+
182+
let tempdir = TempDir::new().unwrap();
183+
let does_not_exist = tempdir.path().join("nope");
184+
185+
// This should not error even though the directory is not present.
186+
fs::remove_dir_all(does_not_exist).await.unwrap();
187+
}
188+
189+
#[tokio::test]
190+
async fn test_create_and_remove_dir() {
191+
use crate::common::fs;
192+
use tempfile::TempDir;
193+
194+
let tempdir = TempDir::new().unwrap();
195+
let path = tempdir.path().join("yep").join("ok");
196+
197+
fs::create_dir_all(&path).await.unwrap();
198+
assert!(
199+
path.is_dir(),
200+
"Expected a directory to be created at '{}'",
201+
path.display()
202+
);
203+
204+
fs::remove_dir_all(&path).await.unwrap();
205+
assert!(
206+
!path.exists(),
207+
"Expected directories to be removed from this path '{}'",
208+
path.display()
209+
)
210+
}

twoliter/src/tools.rs

Lines changed: 24 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -24,9 +24,15 @@ const TUFTOOL: &[u8] = include_bytes!(env!("CARGO_BIN_FILE_TUFTOOL"));
2424
pub(crate) async fn install_tools(tools_dir: impl AsRef<Path>) -> Result<()> {
2525
let dir = tools_dir.as_ref();
2626
debug!("Installing tools to '{}'", dir.display());
27+
fs::remove_dir_all(dir)
28+
.await
29+
.context("Unable to remove tools directory before installing")?;
30+
fs::create_dir_all(dir)
31+
.await
32+
.context("Unable to create directory for tools")?;
2733

2834
// Write out the embedded tools and scripts.
29-
unpack_tarball(&dir)
35+
unpack_tarball(dir)
3036
.await
3137
.context("Unable to install tools")?;
3238

@@ -93,32 +99,31 @@ async fn unpack_tarball(tools_dir: impl AsRef<Path>) -> Result<()> {
9399
#[tokio::test]
94100
async fn test_install_tools() {
95101
let tempdir = tempfile::TempDir::new().unwrap();
96-
install_tools(&tempdir).await.unwrap();
102+
let toolsdir = tempdir.path().join("tools");
103+
install_tools(&toolsdir).await.unwrap();
97104

98105
// Assert that the expected files exist in the tools directory.
99106

100107
// Check that non-binary files were copied.
101-
assert!(tempdir.path().join("Dockerfile").is_file());
102-
assert!(tempdir.path().join("Makefile.toml").is_file());
103-
assert!(tempdir.path().join("docker-go").is_file());
104-
assert!(tempdir.path().join("partyplanner").is_file());
105-
assert!(tempdir.path().join("rpm2img").is_file());
106-
assert!(tempdir.path().join("rpm2kmodkit").is_file());
107-
assert!(tempdir.path().join("rpm2migrations").is_file());
108+
assert!(toolsdir.join("Dockerfile").is_file());
109+
assert!(toolsdir.join("Makefile.toml").is_file());
110+
assert!(toolsdir.join("docker-go").is_file());
111+
assert!(toolsdir.join("partyplanner").is_file());
112+
assert!(toolsdir.join("rpm2img").is_file());
113+
assert!(toolsdir.join("rpm2kmodkit").is_file());
114+
assert!(toolsdir.join("rpm2migrations").is_file());
108115

109116
// Check that binaries were copied.
110-
assert!(tempdir.path().join("bottlerocket-variant").is_file());
111-
assert!(tempdir.path().join("buildsys").is_file());
112-
assert!(tempdir.path().join("pubsys").is_file());
113-
assert!(tempdir.path().join("pubsys-setup").is_file());
114-
assert!(tempdir.path().join("testsys").is_file());
115-
assert!(tempdir.path().join("tuftool").is_file());
117+
assert!(toolsdir.join("bottlerocket-variant").is_file());
118+
assert!(toolsdir.join("buildsys").is_file());
119+
assert!(toolsdir.join("pubsys").is_file());
120+
assert!(toolsdir.join("pubsys-setup").is_file());
121+
assert!(toolsdir.join("testsys").is_file());
122+
assert!(toolsdir.join("tuftool").is_file());
116123

117124
// Check that the mtimes match.
118-
let dockerfile_metadata = fs::metadata(tempdir.path().join("Dockerfile"))
119-
.await
120-
.unwrap();
121-
let buildsys_metadata = fs::metadata(tempdir.path().join("buildsys")).await.unwrap();
125+
let dockerfile_metadata = fs::metadata(toolsdir.join("Dockerfile")).await.unwrap();
126+
let buildsys_metadata = fs::metadata(toolsdir.join("buildsys")).await.unwrap();
122127
let dockerfile_mtime = FileTime::from_last_modification_time(&dockerfile_metadata);
123128
let buildsys_mtime = FileTime::from_last_modification_time(&buildsys_metadata);
124129

0 commit comments

Comments
 (0)