Skip to content

Commit 6e25012

Browse files
committed
test(mutants): cmd_revision_core collects interactive fill_with into migration
Adding a NOT-NULL, no-default, non-FK column requires an interactively collected fill_with value. A value-supplying mock provides a sentinel; the written migration must embed it. Pins the if !missing.is_empty() gate (mod.rs:492) - a delete-! mutant skips collection, omitting the value.
1 parent 7cd935c commit 6e25012

1 file changed

Lines changed: 51 additions & 0 deletions

File tree

crates/vespertide-cli/src/commands/revision/tests/branches_more.rs

Lines changed: 51 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,57 @@ use vespertide_core::{
88
schema::foreign_key::ForeignKeySyntax,
99
};
1010

11+
// Adding a NOT-NULL, no-default, non-FK column to an existing table requires a
12+
// fill_with value, collected interactively. A value-supplying mock provides a
13+
// unique sentinel; the written migration must embed it. Pins
14+
// `if !missing.is_empty()` (mod.rs:492): a `delete !` mutant would skip
15+
// collection entirely, leaving the sentinel out of the migration.
16+
#[tokio::test]
17+
#[serial_test::serial]
18+
async fn cmd_revision_core_collects_interactive_fill_with_into_migration() {
19+
let tmp = tempdir().unwrap();
20+
let _guard = CwdGuard::new(&tmp.path().to_path_buf());
21+
let cfg = write_config();
22+
let baseline = table_def(
23+
"users",
24+
vec![int_col("id", false)],
25+
vec![pk_constraint("id")],
26+
);
27+
let mut target = baseline.clone();
28+
// New NOT-NULL, no-default, non-FK column -> needs fill_with.
29+
target.columns.push(int_col("age", false));
30+
write_project_with_tables(&cfg, vec![baseline], vec![target]);
31+
32+
let fill_with: FillWithFn = |_, _| Ok("424242".to_string());
33+
let remap_enum_values: RemapEnumValuesFn = |_| Ok(true);
34+
let prompts = RevisionPromptFns {
35+
fill_with,
36+
remap_enum_values,
37+
..panic_guard_prompt_fns()
38+
};
39+
cmd_revision_core("add age".into(), vec![], vec![], prompts)
40+
.await
41+
.unwrap();
42+
43+
// Read the newly written migration (0002_*) and confirm the collected
44+
// sentinel landed in it.
45+
let new_migration = std::fs::read_dir(cfg.migrations_dir())
46+
.unwrap()
47+
.filter_map(Result::ok)
48+
.map(|e| e.path())
49+
.find(|p| {
50+
p.file_name()
51+
.and_then(|n| n.to_str())
52+
.is_some_and(|n| n.starts_with("0002"))
53+
})
54+
.expect("a second migration must be written");
55+
let body = std::fs::read_to_string(&new_migration).unwrap();
56+
assert!(
57+
body.contains("424242"),
58+
"interactively collected fill_with must be embedded in the migration: {body}"
59+
);
60+
}
61+
1162
#[tokio::test]
1263
#[serial_test::serial]
1364
async fn cmd_revision_core_fk_orphan_cancel_aborts() {

0 commit comments

Comments
 (0)