use assert_cmd::Command;
use predicates::prelude::*;
use tempfile::tempdir;
fn tsafe() -> Command {
Command::cargo_bin("tsafe").unwrap()
}
fn init_vault(dir: &std::path::Path) {
tsafe()
.args(["init"])
.env("TSAFE_VAULT_DIR", dir)
.env("TSAFE_PASSWORD", "test-pw")
.assert()
.success();
}
#[test]
fn snapshot_list_empty_after_init() {
let dir = tempdir().unwrap();
init_vault(dir.path());
tsafe()
.args(["snapshot", "list"])
.env("TSAFE_VAULT_DIR", dir.path())
.env("TSAFE_PASSWORD", "test-pw")
.assert()
.success()
.stdout(predicates::str::contains("No snapshots"));
}
#[test]
fn snapshot_list_shows_entry_after_write() {
let dir = tempdir().unwrap();
init_vault(dir.path());
tsafe()
.args(["set", "SNAP_KEY", "snap-val"])
.env("TSAFE_VAULT_DIR", dir.path())
.env("TSAFE_PASSWORD", "test-pw")
.assert()
.success();
tsafe()
.args(["snapshot", "list"])
.env("TSAFE_VAULT_DIR", dir.path())
.env("TSAFE_PASSWORD", "test-pw")
.assert()
.success()
.stdout(predicates::str::contains("snapshot").or(predicates::str::contains(".snap")));
}
#[test]
fn snapshot_restore_rolls_back_write() {
let dir = tempdir().unwrap();
init_vault(dir.path());
tsafe()
.args(["set", "ROLLBACK_KEY", "rollback-val"])
.env("TSAFE_VAULT_DIR", dir.path())
.env("TSAFE_PASSWORD", "test-pw")
.assert()
.success();
tsafe()
.args(["get", "ROLLBACK_KEY"])
.env("TSAFE_VAULT_DIR", dir.path())
.env("TSAFE_PASSWORD", "test-pw")
.assert()
.success()
.stdout(predicates::str::contains("rollback-val"));
tsafe()
.args(["snapshot", "restore"])
.env("TSAFE_VAULT_DIR", dir.path())
.env("TSAFE_PASSWORD", "test-pw")
.assert()
.success()
.stdout(predicates::str::contains("restored"));
tsafe()
.args(["get", "ROLLBACK_KEY"])
.env("TSAFE_VAULT_DIR", dir.path())
.env("TSAFE_PASSWORD", "test-pw")
.assert()
.failure();
}
#[test]
fn snapshot_restore_without_snapshot_fails() {
let dir = tempdir().unwrap();
init_vault(dir.path());
tsafe()
.args(["snapshot", "restore"])
.env("TSAFE_VAULT_DIR", dir.path())
.env("TSAFE_PASSWORD", "test-pw")
.assert()
.failure()
.stderr(predicates::str::contains("snapshot").or(predicates::str::contains("no snapshot")));
}
#[test]
fn snapshot_multiple_writes_accumulate_snapshots() {
let dir = tempdir().unwrap();
init_vault(dir.path());
for i in 0..3 {
tsafe()
.args(["set", &format!("KEY_{i}"), &format!("val-{i}")])
.env("TSAFE_VAULT_DIR", dir.path())
.env("TSAFE_PASSWORD", "test-pw")
.assert()
.success();
}
let output = tsafe()
.args(["snapshot", "list"])
.env("TSAFE_VAULT_DIR", dir.path())
.env("TSAFE_PASSWORD", "test-pw")
.assert()
.success()
.get_output()
.stdout
.clone();
let stdout = String::from_utf8_lossy(&output);
assert!(
stdout.contains(".snap") || stdout.contains("snapshot"),
"expected snapshot list output, got: {stdout}"
);
}