Files
sausage/host/tests/git_compat.rs
T

111 lines
3.8 KiB
Rust

//! Fresh worlds provide a Git identity and resolve conventional tool names through which.
use sausage::{
exec::{Command, Options, Stream},
world::World,
};
#[tokio::test(flavor = "current_thread")]
async fn default_identity_and_which() -> anyhow::Result<()> {
let repo = std::path::Path::new(env!("CARGO_MANIFEST_DIR")).join("..");
let userland = repo.join("userland");
assert!(
std::process::Command::new("nu")
.args(["--no-config-file", "cwd-init/build.nu"])
.current_dir(&userland)
.status()?
.success()
);
assert!(
std::process::Command::new("cargo")
.args([
"build",
"--release",
"-p",
"git",
"-p",
"sausage-exec-tools",
"--locked"
])
.current_dir(&userland)
.status()?
.success()
);
let target = std::path::PathBuf::from(std::env::var("CARGO_TARGET_DIR")?);
let bundle = tempfile::tempdir()?;
std::fs::create_dir_all(bundle.path().join("bin"))?;
std::fs::create_dir_all(bundle.path().join("src"))?;
for name in ["git", "which"] {
std::fs::copy(
target.join(format!("wasm32-wasip2/release/{name}.wasm")),
bundle.path().join(format!("bin/{name}.wasm")),
)?;
}
let dir = tempfile::tempdir()?;
let world = World::open_with_userland(dir.path(), Some(bundle.path()))?;
std::fs::create_dir_all(dir.path().join("world/repo"))?;
std::fs::write(dir.path().join("world/repo/file.txt"), "base\n")?;
let exec = sausage::process::exec(World {
root: world.root.clone(),
host_dir: world.host_dir.clone(),
processes: world.processes.clone(),
})?;
for (argv, expected) in [
(vec!["git", "-C", "/repo", "init", "-q", "-b", "main"], ""),
(
vec!["git", "-C", "/repo", "config", "--get", "user.name"],
"Sausage\n",
),
(
vec!["git", "-C", "/repo", "config", "--get", "user.email"],
"sausage@localhost\n",
),
(vec!["git", "-C", "/repo", "add", "."], ""),
(vec!["git", "-C", "/repo", "commit", "-q", "-m", "base"], ""),
(vec!["which", "git"], "/bin/git\n"),
(vec!["which", "-a", "git"], "/bin/git\n/bin/git.wasm\n"),
] {
let mut stdout = Vec::new();
let mut stderr = Vec::new();
let code = exec
.exec(
Command::Argv(argv.iter().map(|s| (*s).into()).collect()),
Options::default(),
&mut |stream, bytes| match stream {
Stream::Stdout => stdout.extend_from_slice(bytes),
Stream::Stderr => stderr.extend_from_slice(bytes),
},
)
.await?;
assert_eq!(code, 0, "{argv:?}: {}", String::from_utf8_lossy(&stderr));
assert_eq!(stdout, expected.as_bytes(), "{argv:?}");
}
std::fs::copy(
dir.path().join("world/bin/git.wasm"),
dir.path().join("world/usr/local/bin/git.wasm"),
)?;
let mut stdout = Vec::new();
assert_eq!(
exec.exec(
Command::Argv(vec!["which".into(), "git".into()]),
Options::default(),
&mut |stream, bytes| if matches!(stream, Stream::Stdout) {
stdout.extend_from_slice(bytes);
}
)
.await?,
0
);
assert_eq!(stdout, b"/usr/local/bin/git.wasm\n");
let config = dir.path().join("world/etc/gitconfig");
std::fs::write(
&config,
"[user]\nname = Custom\nemail = custom@example.test\n",
)?;
let _ = World::open(dir.path())?;
assert_eq!(
std::fs::read_to_string(config)?,
"[user]\nname = Custom\nemail = custom@example.test\n"
);
Ok(())
}