style: format the whole tree with cargo fmt (stock defaults, #35)

One-time, mechanical reformat — no functional changes. The tree was not
rustfmt-clean (~1800 hunks across ~100 files); this brings it to stock
`cargo fmt` defaults so a `cargo fmt --check` CI gate can follow.
Behaviour-preserving: 2509 pass / 0 fail / 1 ignored (unchanged baseline),
clippy clean. A .git-blame-ignore-revs entry follows so `git blame`
skips this commit.
This commit is contained in:
claude@clouddev1
2026-06-17 21:39:19 +00:00
parent e9606b5f6d
commit 41b7e9a049
102 changed files with 8017 additions and 4975 deletions
+4 -16
View File
@@ -28,10 +28,7 @@ fn one_n_relationship_keyword_sequence_is_incomplete() {
#[test]
fn after_from_offers_table_names() {
let schema = schema_multi_table();
let a = assess_at_end(
"add 1:n relationship from ",
&schema,
);
let a = assess_at_end("add 1:n relationship from ", &schema);
assert!(matches!(a.state, InputState::IncompleteAtEof));
assert_candidate_present(&a, &["Customers", "Orders"]);
crate::snap!("after_from", a);
@@ -41,10 +38,7 @@ fn after_from_offers_table_names() {
fn after_parent_table_dot_narrows_to_parent_columns() {
// §2.2 follow-up — `from Customers.` narrows to Customers.
let schema = schema_multi_table();
let a = assess_at_end(
"add 1:n relationship from Customers.",
&schema,
);
let a = assess_at_end("add 1:n relationship from Customers.", &schema);
assert!(matches!(a.state, InputState::IncompleteAtEof));
assert_candidate_present(&a, &["id", "Name"]);
assert_no_candidate_named(&a, &["OrderId", "CustId", "Total"]);
@@ -54,10 +48,7 @@ fn after_parent_table_dot_narrows_to_parent_columns() {
#[test]
fn after_child_table_dot_narrows_to_child_columns() {
let schema = schema_multi_table();
let a = assess_at_end(
"add 1:n relationship from Customers.id to Orders.",
&schema,
);
let a = assess_at_end("add 1:n relationship from Customers.id to Orders.", &schema);
assert!(matches!(a.state, InputState::IncompleteAtEof));
assert_candidate_present(&a, &["OrderId", "CustId", "Total"]);
assert_no_candidate_named(&a, &["Name"]);
@@ -101,10 +92,7 @@ fn add_relationship_with_on_delete_clause_parses() {
#[test]
fn add_relationship_in_progress_after_dot_is_incomplete() {
let schema = schema_multi_table();
let a = assess_at_end(
"add 1:n relationship from Customers.id to ",
&schema,
);
let a = assess_at_end("add 1:n relationship from Customers.id to ", &schema);
assert!(matches!(a.state, InputState::IncompleteAtEof));
crate::snap!("in_progress_after_to", a);
}
+4 -1
View File
@@ -67,7 +67,10 @@ fn create_m2n_with_as_name_parses() {
#[test]
fn after_as_keyword_is_incomplete() {
let schema = schema_multi_table();
let a = assess_at_end("create m:n relationship from Customers to Orders as ", &schema);
let a = assess_at_end(
"create m:n relationship from Customers to Orders as ",
&schema,
);
assert!(matches!(a.state, InputState::IncompleteAtEof));
crate::snap!("after_as", a);
}
+3 -12
View File
@@ -83,25 +83,16 @@ fn after_pk_space_with_col_name_typed_expects_paren() {
#[test]
fn after_paren_expects_type_candidates() {
let schema = schema_empty();
let a = assess_at_end(
"create table Customers with pk Code(",
&schema,
);
let a = assess_at_end("create table Customers with pk Code(", &schema);
assert!(matches!(a.state, InputState::IncompleteAtEof));
assert_candidate_present(
&a,
&["text", "int", "serial", "shortid", "bool"],
);
assert_candidate_present(&a, &["text", "int", "serial", "shortid", "bool"]);
crate::snap!("after_paren", a);
}
#[test]
fn create_table_with_explicit_pk_parses() {
let schema = schema_empty();
let a = assess_at_end(
"create table Customers with pk Code(text)",
&schema,
);
let a = assess_at_end("create table Customers with pk Code(text)", &schema);
assert!(matches!(a.state, InputState::Valid));
crate::snap!("with_explicit_pk", a);
}
+4 -14
View File
@@ -42,13 +42,8 @@ fn after_where_offers_active_table_columns_no_leakage() {
#[test]
fn after_where_column_equals_offers_typed_prose() {
let schema = schema_serial_pk();
let a = assess_at_end(
"delete from Customers where Email=",
&schema,
);
let prose = hint_prose(&a).unwrap_or_else(|| {
panic!("expected Prose, got {:?}", a.hint)
});
let a = assess_at_end("delete from Customers where Email=", &schema);
let prose = hint_prose(&a).unwrap_or_else(|| panic!("expected Prose, got {:?}", a.hint));
assert!(
prose.contains("Email"),
"should name `Email`, got prose: {prose:?}",
@@ -63,10 +58,7 @@ fn after_where_column_equals_offers_typed_prose() {
#[test]
fn complete_delete_with_where_parses() {
let schema = schema_serial_pk();
let a = assess_at_end(
"delete from Customers where id=1",
&schema,
);
let a = assess_at_end("delete from Customers where id=1", &schema);
assert!(matches!(a.state, InputState::Valid));
assert_eq!(a.parse_result.as_deref(), Ok("Delete"));
crate::snap!("complete_delete", a);
@@ -76,9 +68,7 @@ fn complete_delete_with_where_parses() {
fn delete_with_datetime_column_says_yyyy_mm_dd_t() {
let schema = schema_every_type();
let a = assess_at_end("delete from Things where ts=", &schema);
let prose = hint_prose(&a).unwrap_or_else(|| {
panic!("expected Prose, got {:?}", a.hint)
});
let prose = hint_prose(&a).unwrap_or_else(|| panic!("expected Prose, got {:?}", a.hint));
assert!(
prose.contains("ts"),
"should name `ts`, got prose: {prose:?}",
+1 -4
View File
@@ -63,10 +63,7 @@ fn complete_drop_column_parses() {
#[test]
fn drop_column_with_table_keyword_parses() {
let schema = schema_serial_pk();
let a = assess_at_end(
"drop column from table Customers: Email",
&schema,
);
let a = assess_at_end("drop column from table Customers: Email", &schema);
assert!(matches!(a.state, InputState::Valid));
crate::snap!("with_table_keyword", a);
}
+3 -12
View File
@@ -30,10 +30,7 @@ fn after_relationship_keyword_offers_from_and_names() {
assert!(matches!(a.state, InputState::IncompleteAtEof));
// Both selector forms discoverable: `from` for endpoints,
// the relationship name for the by-name form.
assert_candidate_present(
&a,
&["from", "Orders_CustId_to_Customers"],
);
assert_candidate_present(&a, &["from", "Orders_CustId_to_Customers"]);
crate::snap!("after_relationship_keyword", a);
}
@@ -61,10 +58,7 @@ fn after_parent_table_dot_narrows_to_parent_columns() {
#[test]
fn after_to_offers_table_names() {
let schema = schema_with_relationship();
let a = assess_at_end(
"drop relationship from Orders.CustId to ",
&schema,
);
let a = assess_at_end("drop relationship from Orders.CustId to ", &schema);
assert!(matches!(a.state, InputState::IncompleteAtEof));
assert_candidate_present(&a, &["Customers", "Orders"]);
crate::snap!("after_to", a);
@@ -98,10 +92,7 @@ fn complete_drop_relationship_by_endpoints_parses() {
#[test]
fn complete_drop_relationship_by_name_parses() {
let schema = schema_with_relationship();
let a = assess_at_end(
"drop relationship Orders_CustId_to_Customers",
&schema,
);
let a = assess_at_end("drop relationship Orders_CustId_to_Customers", &schema);
assert!(matches!(a.state, InputState::Valid));
assert_eq!(a.parse_result.as_deref(), Ok("DropRelationship"));
crate::snap!("complete_by_name", a);
+2 -8
View File
@@ -66,10 +66,7 @@ fn complete_explain_show_data_parses_as_explain() {
#[test]
fn complete_explain_show_data_with_where_and_limit_parses() {
let schema = schema_serial_pk();
let a = assess_at_end(
"explain show data Customers where id = 1 limit 5",
&schema,
);
let a = assess_at_end("explain show data Customers where id = 1 limit 5", &schema);
assert!(matches!(a.state, InputState::Valid));
assert_eq!(a.parse_result.as_deref(), Ok("Explain"));
crate::snap!("complete_explain_show_data_where_limit", a);
@@ -95,10 +92,7 @@ fn after_explain_update_table_expects_set() {
#[test]
fn complete_explain_update_parses_as_explain() {
let schema = schema_serial_pk();
let a = assess_at_end(
"explain update Customers set Name='Bo' where id=1",
&schema,
);
let a = assess_at_end("explain update Customers set Name='Bo' where id=1", &schema);
assert!(matches!(a.state, InputState::Valid));
assert_eq!(a.parse_result.as_deref(), Ok("Explain"));
crate::snap!("complete_explain_update", a);
+16 -28
View File
@@ -143,10 +143,7 @@ fn after_values_keyword_expects_open_paren() {
// Trailing space so we're past the `values` word boundary
// — without it the partial-prefix logic re-offers `values`
// itself as the candidate that matches the typed prefix.
let a = assess_at_end(
"insert into Customers (Name) values ",
&schema,
);
let a = assess_at_end("insert into Customers (Name) values ", &schema);
assert!(matches!(a.state, InputState::IncompleteAtEof));
assert_candidate_present(&a, &["("]);
crate::snap!("after_values_keyword", a);
@@ -159,10 +156,7 @@ fn after_values_keyword_expects_open_paren() {
#[test]
fn after_values_open_paren_form_a_text_column_prose_names_column() {
let schema = schema_serial_pk();
let a = assess_at_end(
"insert into Customers (Name) values (",
&schema,
);
let a = assess_at_end("insert into Customers (Name) values (", &schema);
assert!(
hint_prose_contains(&a, "Name"),
"expected column name in prose, got {:?}",
@@ -179,13 +173,12 @@ fn after_values_open_paren_form_a_text_column_prose_names_column() {
#[test]
fn after_values_open_paren_form_a_serial_column_offers_null_to_auto_generate() {
let schema = schema_serial_pk();
let a = assess_at_end(
"insert into Customers (id, Name) values (",
&schema,
let a = assess_at_end("insert into Customers (id, Name) values (", &schema);
let prose = hint_prose(&a).unwrap_or_else(|| panic!("expected Prose hint, got {:?}", a.hint));
assert!(
prose.contains("id"),
"prose should name `id`, got {prose:?}"
);
let prose = hint_prose(&a)
.unwrap_or_else(|| panic!("expected Prose hint, got {:?}", a.hint));
assert!(prose.contains("id"), "prose should name `id`, got {prose:?}");
assert!(
prose.contains("null") && prose.contains("auto-generate"),
"prose should mention `null` to auto-generate, got {prose:?}",
@@ -200,8 +193,7 @@ fn mid_value_list_after_comma_advances_to_next_column_prose() {
"insert into Customers (Name, Email) values ('Alice', ",
&schema,
);
let prose = hint_prose(&a)
.unwrap_or_else(|| panic!("expected Prose hint, got {:?}", a.hint));
let prose = hint_prose(&a).unwrap_or_else(|| panic!("expected Prose hint, got {:?}", a.hint));
assert!(
prose.contains("Email"),
"prose should name `Email`, got {prose:?}",
@@ -281,9 +273,8 @@ fn form_a_complete_with_serial_in_list_parses() {
fn form_a_int_slot_prose_says_integer() {
let schema = schema_every_type();
let a = assess_at_end("insert into Things (k) values (", &schema);
let prose = hint_prose(&a).unwrap_or_else(|| {
panic!("expected Prose for int slot, got {:?}", a.hint)
});
let prose =
hint_prose(&a).unwrap_or_else(|| panic!("expected Prose for int slot, got {:?}", a.hint));
assert!(
prose.contains("integer"),
"int-slot prose should say `integer`, got {prose:?}",
@@ -295,9 +286,8 @@ fn form_a_int_slot_prose_says_integer() {
fn form_a_date_slot_prose_says_yyyy_mm_dd() {
let schema = schema_every_type();
let a = assess_at_end("insert into Things (dt) values (", &schema);
let prose = hint_prose(&a).unwrap_or_else(|| {
panic!("expected Prose for date slot, got {:?}", a.hint)
});
let prose =
hint_prose(&a).unwrap_or_else(|| panic!("expected Prose for date slot, got {:?}", a.hint));
assert!(
prose.contains("YYYY-MM-DD"),
"date-slot prose should reference YYYY-MM-DD format, got {prose:?}",
@@ -309,9 +299,8 @@ fn form_a_date_slot_prose_says_yyyy_mm_dd() {
fn form_a_bool_slot_prose_mentions_true_false() {
let schema = schema_every_type();
let a = assess_at_end("insert into Things (b) values (", &schema);
let prose = hint_prose(&a).unwrap_or_else(|| {
panic!("expected Prose for bool slot, got {:?}", a.hint)
});
let prose =
hint_prose(&a).unwrap_or_else(|| panic!("expected Prose for bool slot, got {:?}", a.hint));
assert!(
prose.contains("true") && prose.contains("false"),
"bool-slot prose should mention `true`/`false`, got {prose:?}",
@@ -323,9 +312,8 @@ fn form_a_bool_slot_prose_mentions_true_false() {
fn form_a_shortid_slot_prose_mentions_null_to_auto_generate() {
let schema = schema_every_type();
let a = assess_at_end("insert into Things (sid) values (", &schema);
let prose = hint_prose(&a).unwrap_or_else(|| {
panic!("expected Prose for shortid slot, got {:?}", a.hint)
});
let prose = hint_prose(&a)
.unwrap_or_else(|| panic!("expected Prose for shortid slot, got {:?}", a.hint));
assert!(
prose.contains("null") && prose.contains("auto-generate"),
"shortid-slot prose should mention `null` to auto-generate, got {prose:?}",
+23 -53
View File
@@ -38,7 +38,10 @@ fn form_b_first_value_skips_serial_column() {
let schema = schema_serial_pk();
let a = assess_at_end("insert into Customers values (", &schema);
let prose = hint_prose(&a).unwrap_or_else(|| {
panic!("expected Prose at first Form B value slot, got {:?}", a.hint)
panic!(
"expected Prose at first Form B value slot, got {:?}",
a.hint
)
});
// The value slot itself must be keyed on `Name` — the first
// non-auto column — not on the skipped `id`.
@@ -60,9 +63,7 @@ fn form_b_first_value_skips_serial_column() {
fn form_b_first_value_text_pk_names_first_column() {
let schema = schema_text_pk();
let a = assess_at_end("insert into Items values (", &schema);
let prose = hint_prose(&a).unwrap_or_else(|| {
panic!("expected Prose, got {:?}", a.hint)
});
let prose = hint_prose(&a).unwrap_or_else(|| panic!("expected Prose, got {:?}", a.hint));
assert!(
prose.contains("Code"),
"Form B should name the PK column `Code`, got prose: {prose:?}",
@@ -76,9 +77,7 @@ fn form_b_first_value_every_type_first_column_is_int() {
// must say `integer` and name `k`.
let schema = schema_every_type();
let a = assess_at_end("insert into Things values (", &schema);
let prose = hint_prose(&a).unwrap_or_else(|| {
panic!("expected Prose, got {:?}", a.hint)
});
let prose = hint_prose(&a).unwrap_or_else(|| panic!("expected Prose, got {:?}", a.hint));
assert!(
prose.contains("k"),
"should name column `k`, got prose: {prose:?}",
@@ -98,13 +97,9 @@ fn form_b_first_value_every_type_first_column_is_int() {
#[test]
fn form_b_after_first_value_advances_to_next_column() {
let schema = schema_serial_pk();
let a = assess_at_end(
"insert into Customers values ('Alice', ",
&schema,
);
let prose = hint_prose(&a).unwrap_or_else(|| {
panic!("expected Prose at second slot, got {:?}", a.hint)
});
let a = assess_at_end("insert into Customers values ('Alice', ", &schema);
let prose =
hint_prose(&a).unwrap_or_else(|| panic!("expected Prose at second slot, got {:?}", a.hint));
assert!(
prose.contains("Email"),
"second slot should name `Email`, got prose: {prose:?}",
@@ -121,10 +116,7 @@ fn form_b_after_first_value_advances_to_next_column() {
#[test]
fn form_b_in_progress_after_comma_is_incomplete() {
let schema = schema_serial_pk();
let a = assess_at_end(
"insert into Customers values ('Alice', ",
&schema,
);
let a = assess_at_end("insert into Customers values ('Alice', ", &schema);
assert!(
matches!(a.state, InputState::IncompleteAtEof),
"in-progress Form B should be Incomplete, got {:?}",
@@ -136,10 +128,7 @@ fn form_b_in_progress_after_comma_is_incomplete() {
#[test]
fn form_b_in_progress_without_closing_paren_is_incomplete() {
let schema = schema_serial_pk();
let a = assess_at_end(
"insert into Customers values ('Alice', 'a@b.c'",
&schema,
);
let a = assess_at_end("insert into Customers values ('Alice', 'a@b.c'", &schema);
assert!(matches!(a.state, InputState::IncompleteAtEof));
crate::snap!("form_b_in_progress_no_close_paren", a);
}
@@ -201,10 +190,7 @@ fn form_b_with_extra_value_for_serial_column_is_invalid() {
#[test]
fn form_b_with_correct_values_parses() {
let schema = schema_serial_pk();
let a = assess_at_end(
"insert into Customers values ('Alice', 'a@b.c')",
&schema,
);
let a = assess_at_end("insert into Customers values ('Alice', 'a@b.c')", &schema);
assert!(matches!(a.state, InputState::Valid));
assert_eq!(a.parse_result.as_deref(), Ok("Insert"));
crate::snap!("form_b_valid", a);
@@ -213,10 +199,7 @@ fn form_b_with_correct_values_parses() {
#[test]
fn form_b_text_pk_with_correct_values_parses() {
let schema = schema_text_pk();
let a = assess_at_end(
"insert into Items values ('SKU-1', 'Widget')",
&schema,
);
let a = assess_at_end("insert into Items values ('SKU-1', 'Widget')", &schema);
assert!(matches!(a.state, InputState::Valid));
assert_eq!(a.parse_result.as_deref(), Ok("Insert"));
crate::snap!("form_b_text_pk_valid", a);
@@ -240,9 +223,8 @@ fn form_b_text_pk_with_correct_values_parses() {
fn form_b_first_slot_mentions_skipped_serial_column() {
let schema = schema_serial_pk();
let a = assess_at_end("insert into Customers values (", &schema);
let prose = hint_prose(&a).unwrap_or_else(|| {
panic!("expected Prose at first Form B slot, got {:?}", a.hint)
});
let prose = hint_prose(&a)
.unwrap_or_else(|| panic!("expected Prose at first Form B slot, got {:?}", a.hint));
// Names the skipped auto-gen column.
assert!(
prose.contains("`id`"),
@@ -261,13 +243,9 @@ fn form_b_second_slot_omits_skip_note() {
// The note fires once, at the first slot only — not at
// every comma.
let schema = schema_serial_pk();
let a = assess_at_end(
"insert into Customers values ('Alice', ",
&schema,
);
let prose = hint_prose(&a).unwrap_or_else(|| {
panic!("expected Prose at second slot, got {:?}", a.hint)
});
let a = assess_at_end("insert into Customers values ('Alice', ", &schema);
let prose =
hint_prose(&a).unwrap_or_else(|| panic!("expected Prose at second slot, got {:?}", a.hint));
assert!(
!prose.contains("auto-generated"),
"second-slot hint must NOT repeat the skip note, got: {prose:?}",
@@ -280,9 +258,7 @@ fn form_b_text_pk_has_no_skip_note() {
// No auto-gen columns → no skip note.
let schema = schema_text_pk();
let a = assess_at_end("insert into Items values (", &schema);
let prose = hint_prose(&a).unwrap_or_else(|| {
panic!("expected Prose, got {:?}", a.hint)
});
let prose = hint_prose(&a).unwrap_or_else(|| panic!("expected Prose, got {:?}", a.hint));
assert!(
!prose.contains("auto-generated"),
"text-PK table has no auto-gen column — no skip note expected, got: {prose:?}",
@@ -295,13 +271,8 @@ fn form_a_first_slot_has_no_skip_note() {
// Form A lists columns explicitly — the user is in control,
// no pedagogical pointer needed.
let schema = schema_serial_pk();
let a = assess_at_end(
"insert into Customers (Name) values (",
&schema,
);
let prose = hint_prose(&a).unwrap_or_else(|| {
panic!("expected Prose, got {:?}", a.hint)
});
let a = assess_at_end("insert into Customers (Name) values (", &schema);
let prose = hint_prose(&a).unwrap_or_else(|| panic!("expected Prose, got {:?}", a.hint));
assert!(
!prose.contains("auto-generated"),
"Form A must not show the Form-B skip note, got: {prose:?}",
@@ -315,9 +286,8 @@ fn form_b_advances_through_every_type_first_to_real() {
// first value, prose must name `r` and say `number`.
let schema = schema_every_type();
let a = assess_at_end("insert into Things values (1, ", &schema);
let prose = hint_prose(&a).unwrap_or_else(|| {
panic!("expected Prose at 2nd slot, got {:?}", a.hint)
});
let prose =
hint_prose(&a).unwrap_or_else(|| panic!("expected Prose at 2nd slot, got {:?}", a.hint));
assert!(prose.contains("r"), "should name `r`, got prose: {prose:?}");
assert!(
prose.contains("number"),
+8 -27
View File
@@ -26,10 +26,7 @@ fn form_c_text_pk_correct_values_parses() {
// Items(Code:text, Title:text) — Form C expects two text
// values (no auto-gen columns to skip).
let schema = schema_text_pk();
let a = assess_at_end(
"insert into Items ('SKU-1', 'Widget')",
&schema,
);
let a = assess_at_end("insert into Items ('SKU-1', 'Widget')", &schema);
assert!(matches!(a.state, InputState::Valid));
assert_eq!(a.parse_result.as_deref(), Ok("Insert"));
crate::snap!("form_c_text_pk_valid", a);
@@ -40,10 +37,7 @@ fn form_c_serial_pk_correct_values_parses() {
// Customers(id:serial, Name:text, Email:text) — Form C
// skips the serial `id`, expects two text values.
let schema = schema_serial_pk();
let a = assess_at_end(
"insert into Customers ('Alice', 'a@b.c')",
&schema,
);
let a = assess_at_end("insert into Customers ('Alice', 'a@b.c')", &schema);
assert!(matches!(a.state, InputState::Valid));
assert_eq!(a.parse_result.as_deref(), Ok("Insert"));
crate::snap!("form_c_serial_pk_valid", a);
@@ -53,10 +47,7 @@ fn form_c_serial_pk_correct_values_parses() {
fn form_c_with_null_value_parses() {
// null is type-compatible with any slot.
let schema = schema_serial_pk();
let a = assess_at_end(
"insert into Customers (null, 'a@b.c')",
&schema,
);
let a = assess_at_end("insert into Customers (null, 'a@b.c')", &schema);
assert!(matches!(a.state, InputState::Valid));
crate::snap!("form_c_null_value", a);
}
@@ -71,10 +62,7 @@ fn form_c_rejects_number_for_text_column() {
// rejects it at parse time. Before Form-C type-awareness
// this parsed Valid and only failed at bind time.
let schema = schema_serial_pk();
let a = assess_at_end(
"insert into Customers (3.14, 'a@b.c')",
&schema,
);
let a = assess_at_end("insert into Customers (3.14, 'a@b.c')", &schema);
assert!(
!matches!(a.state, InputState::Valid),
"Form C should now type-check `3.14` against Name(text), got {:?}",
@@ -114,13 +102,9 @@ fn form_c_second_slot_shows_typed_prose_for_column() {
// First token `'Alice'` is a string literal → Form C. At
// the second slot the hint names the Email column.
let schema = schema_serial_pk();
let a = assess_at_end(
"insert into Customers ('Alice', ",
&schema,
);
let prose = hint_prose(&a).unwrap_or_else(|| {
panic!("expected Prose at Form C second slot, got {:?}", a.hint)
});
let a = assess_at_end("insert into Customers ('Alice', ", &schema);
let prose = hint_prose(&a)
.unwrap_or_else(|| panic!("expected Prose at Form C second slot, got {:?}", a.hint));
assert!(
prose.contains("Email"),
"Form C second slot should name `Email`, got prose: {prose:?}",
@@ -143,10 +127,7 @@ fn form_c_in_progress_after_comma_is_incomplete() {
#[test]
fn form_c_in_progress_without_close_paren_is_incomplete() {
let schema = schema_serial_pk();
let a = assess_at_end(
"insert into Customers ('Alice', 'a@b.c'",
&schema,
);
let a = assess_at_end("insert into Customers ('Alice', 'a@b.c'", &schema);
assert!(matches!(a.state, InputState::IncompleteAtEof));
crate::snap!("form_c_in_progress_no_close", a);
}
+23 -28
View File
@@ -22,25 +22,25 @@ use rdbms_playground::input_render::{
};
use rdbms_playground::mode::Mode;
pub mod add_relationship;
pub mod app_commands;
pub mod candidate_ordering;
pub mod constraints;
pub mod create_m2n;
pub mod create_table;
pub mod delete_all_rows;
pub mod delete_with_where;
pub mod drop_column;
pub mod drop_relationship;
pub mod explain;
pub mod index_ops;
pub mod insert_form_a;
pub mod insert_form_b;
pub mod insert_form_c;
pub mod update_with_where;
pub mod update_all_rows;
pub mod delete_with_where;
pub mod where_expression;
pub mod delete_all_rows;
pub mod explain;
pub mod create_table;
pub mod drop_column;
pub mod drop_relationship;
pub mod add_relationship;
pub mod create_m2n;
pub mod index_ops;
pub mod constraints;
pub mod rename_change_column;
pub mod app_commands;
pub mod candidate_ordering;
pub mod update_all_rows;
pub mod update_with_where;
pub mod where_expression;
// =========================================================
// Canonical schema shapes (handoff §1 — CANONICAL_SCHEMA_SHAPES)
@@ -81,10 +81,7 @@ pub fn schema_serial_pk() -> SchemaCache {
/// Exercises the no-auto-gen path: Form A and Form B both
/// require values for every column.
pub fn schema_text_pk() -> SchemaCache {
build_schema(&[(
"Items",
&[("Code", Type::Text), ("Title", Type::Text)],
)])
build_schema(&[("Items", &[("Code", Type::Text), ("Title", Type::Text)])])
}
/// Two tables sharing no column names.
@@ -96,10 +93,7 @@ pub fn schema_text_pk() -> SchemaCache {
/// the other table.
pub fn schema_multi_table() -> SchemaCache {
build_schema(&[
(
"Customers",
&[("id", Type::Serial), ("Name", Type::Text)],
),
("Customers", &[("id", Type::Serial), ("Name", Type::Text)]),
(
"Orders",
&[
@@ -436,10 +430,7 @@ fn smoke_assess_at_end_returns_each_field() {
#[test]
fn smoke_assess_parse_label_round_trips() {
let schema = schema_serial_pk();
let a = assess_at_end(
"insert into Customers values ('Alice', 'a@b.c')",
&schema,
);
let a = assess_at_end("insert into Customers values ('Alice', 'a@b.c')", &schema);
assert_eq!(a.parse_result.as_deref(), Ok("Insert"));
assert!(matches!(a.state, InputState::Valid));
}
@@ -462,7 +453,11 @@ fn seed_completion_and_validity() {
// Validity (ADR-0027): a known table seeds clean; an unknown one is
// flagged (same table slot as update/delete/show data).
let ok = assess_at_end("seed Customers 5", &schema);
assert!(matches!(ok.state, InputState::Valid), "known table: {:?}", ok.state);
assert!(
matches!(ok.state, InputState::Valid),
"known table: {:?}",
ok.state
);
// seed's unknown-table behaviour must match its closest sibling
// `show data` (same table-only slot), whatever that is.
let seed_ghost = assess_at_end("seed Ghost 5", &schema).state;
+3 -12
View File
@@ -34,10 +34,7 @@ fn rename_after_old_column_expects_to() {
#[test]
fn rename_after_to_is_new_name_slot() {
let schema = schema_serial_pk();
let a = assess_at_end(
"rename column in Customers: Email to ",
&schema,
);
let a = assess_at_end("rename column in Customers: Email to ", &schema);
assert!(matches!(a.state, InputState::IncompleteAtEof));
crate::snap!("rename_after_to", a);
}
@@ -45,10 +42,7 @@ fn rename_after_to_is_new_name_slot() {
#[test]
fn complete_rename_column_parses() {
let schema = schema_serial_pk();
let a = assess_at_end(
"rename column in Customers: Email to ContactEmail",
&schema,
);
let a = assess_at_end("rename column in Customers: Email to ContactEmail", &schema);
assert!(matches!(a.state, InputState::Valid));
assert_eq!(a.parse_result.as_deref(), Ok("RenameColumn"));
crate::snap!("complete_rename", a);
@@ -78,10 +72,7 @@ fn change_after_open_paren_offers_type_candidates() {
#[test]
fn complete_change_column_parses() {
let schema = schema_serial_pk();
let a = assess_at_end(
"change column in Customers: Email (text)",
&schema,
);
let a = assess_at_end("change column in Customers: Email (text)", &schema);
assert!(matches!(a.state, InputState::Valid));
assert_eq!(a.parse_result.as_deref(), Ok("ChangeColumnType"));
crate::snap!("complete_change", a);
+4 -16
View File
@@ -7,10 +7,7 @@ use rdbms_playground::input_render::InputState;
#[test]
fn before_all_rows_flag_is_incomplete() {
let schema = schema_serial_pk();
let a = assess_at_end(
"update Customers set Email='x' ",
&schema,
);
let a = assess_at_end("update Customers set Email='x' ", &schema);
assert!(matches!(a.state, InputState::IncompleteAtEof));
// Both `where` and `--all-rows` are valid continuations.
assert_candidate_present(&a, &["--all-rows"]);
@@ -20,10 +17,7 @@ fn before_all_rows_flag_is_incomplete() {
#[test]
fn complete_update_all_rows_parses() {
let schema = schema_serial_pk();
let a = assess_at_end(
"update Customers set Email='new@b.c' --all-rows",
&schema,
);
let a = assess_at_end("update Customers set Email='new@b.c' --all-rows", &schema);
assert!(matches!(a.state, InputState::Valid));
assert_eq!(a.parse_result.as_deref(), Ok("Update"));
crate::snap!("complete_all_rows", a);
@@ -33,10 +27,7 @@ fn complete_update_all_rows_parses() {
fn update_without_filter_clause_is_incomplete() {
// Per ADR-0014, update requires WHERE or --all-rows.
let schema = schema_serial_pk();
let a = assess_at_end(
"update Customers set Email='new@b.c'",
&schema,
);
let a = assess_at_end("update Customers set Email='new@b.c'", &schema);
assert!(matches!(a.state, InputState::IncompleteAtEof));
crate::snap!("no_filter_clause", a);
}
@@ -44,10 +35,7 @@ fn update_without_filter_clause_is_incomplete() {
#[test]
fn update_partial_flag_name_is_incomplete() {
let schema = schema_serial_pk();
let a = assess_at_end(
"update Customers set Email='x' --all",
&schema,
);
let a = assess_at_end("update Customers set Email='x' --all", &schema);
// Partial flag still in progress.
assert!(!matches!(a.state, InputState::Valid));
crate::snap!("partial_flag", a);
+8 -29
View File
@@ -64,9 +64,7 @@ fn after_set_column_expects_equals() {
fn after_equals_offers_typed_slot_prose_for_column() {
let schema = schema_serial_pk();
let a = assess_at_end("update Customers set Email=", &schema);
let prose = hint_prose(&a).unwrap_or_else(|| {
panic!("expected Prose, got {:?}", a.hint)
});
let prose = hint_prose(&a).unwrap_or_else(|| panic!("expected Prose, got {:?}", a.hint));
assert!(
prose.contains("Email"),
"should name `Email`, got prose: {prose:?}",
@@ -82,9 +80,7 @@ fn after_equals_offers_typed_slot_prose_for_column() {
fn after_equals_for_date_column_says_yyyy_mm_dd() {
let schema = schema_every_type();
let a = assess_at_end("update Things set dt=", &schema);
let prose = hint_prose(&a).unwrap_or_else(|| {
panic!("expected Prose, got {:?}", a.hint)
});
let prose = hint_prose(&a).unwrap_or_else(|| panic!("expected Prose, got {:?}", a.hint));
assert!(
prose.contains("YYYY-MM-DD"),
"date-slot prose should reference YYYY-MM-DD, got {prose:?}",
@@ -95,10 +91,7 @@ fn after_equals_for_date_column_says_yyyy_mm_dd() {
#[test]
fn mid_assignment_list_after_comma_offers_remaining_columns() {
let schema = schema_multi_table();
let a = assess_at_end(
"update Customers set Name='x', ",
&schema,
);
let a = assess_at_end("update Customers set Name='x', ", &schema);
assert!(matches!(a.state, InputState::IncompleteAtEof));
// Customers columns offered, no leakage.
assert_candidate_present(&a, &["id"]);
@@ -109,10 +102,7 @@ fn mid_assignment_list_after_comma_offers_remaining_columns() {
#[test]
fn after_assignments_expects_where_or_all_rows() {
let schema = schema_serial_pk();
let a = assess_at_end(
"update Customers set Email='new@b.c' ",
&schema,
);
let a = assess_at_end("update Customers set Email='new@b.c' ", &schema);
assert!(matches!(a.state, InputState::IncompleteAtEof));
assert_candidate_present(&a, &["where", "--all-rows"]);
crate::snap!("after_assignments", a);
@@ -125,10 +115,7 @@ fn after_assignments_expects_where_or_all_rows() {
#[test]
fn after_where_keyword_offers_active_table_columns() {
let schema = schema_multi_table();
let a = assess_at_end(
"update Customers set Name='x' where ",
&schema,
);
let a = assess_at_end("update Customers set Name='x' where ", &schema);
assert!(matches!(a.state, InputState::IncompleteAtEof));
assert_candidate_present(&a, &["id", "Name"]);
assert_no_candidate_named(&a, &["OrderId", "CustId", "Total"]);
@@ -138,13 +125,8 @@ fn after_where_keyword_offers_active_table_columns() {
#[test]
fn after_where_column_equals_offers_typed_prose() {
let schema = schema_serial_pk();
let a = assess_at_end(
"update Customers set Email='x' where id=",
&schema,
);
let prose = hint_prose(&a).unwrap_or_else(|| {
panic!("expected Prose, got {:?}", a.hint)
});
let a = assess_at_end("update Customers set Email='x' where id=", &schema);
let prose = hint_prose(&a).unwrap_or_else(|| panic!("expected Prose, got {:?}", a.hint));
assert!(
prose.contains("id"),
"should name where column `id`, got prose: {prose:?}",
@@ -159,10 +141,7 @@ fn after_where_column_equals_offers_typed_prose() {
#[test]
fn complete_update_with_where_parses() {
let schema = schema_serial_pk();
let a = assess_at_end(
"update Customers set Email='new@b.c' where id=1",
&schema,
);
let a = assess_at_end("update Customers set Email='new@b.c' where id=1", &schema);
assert!(matches!(a.state, InputState::Valid));
assert_eq!(a.parse_result.as_deref(), Ok("Update"));
crate::snap!("complete_update", a);
+1 -4
View File
@@ -95,10 +95,7 @@ fn show_data_after_where_predicate_offers_limit() {
#[test]
fn complete_show_data_with_where_and_limit_parses() {
let schema = schema_serial_pk();
let a = assess_at_end(
"show data Customers where id=1 limit 10",
&schema,
);
let a = assess_at_end("show data Customers where id=1 limit 10", &schema);
assert!(matches!(a.state, InputState::Valid));
assert_eq!(a.parse_result.as_deref(), Ok("ShowData"));
crate::snap!("complete_show_where_limit", a);