docs: session handoff 42 — ADR-0035 Phase 4 complete; whole-phase /runda follow-ups

This commit is contained in:
claude@clouddev1
2026-05-26 14:57:07 +00:00
parent 22e5bf5d6a
commit 60d30dd54e
+168
View File
@@ -0,0 +1,168 @@
# Session handoff — 2026-05-26 (42)
Forty-second handover. This session **completed ADR-0035 Phase 4**: it
shipped **sub-phase 4i** (the verification sweep — items ae) on top of
4h, then ran a **whole-Phase-4 `/runda`** (4a4i seen as an integrated
whole). Phase 4 (advanced-mode SQL DDL) is **done**. The `/runda` found
the integrated implementation solid; it surfaced three **error-message /
capability follow-ups** (all user-decided "track", below) — no
correctness or data bugs.
> Note: this supersedes handoff-41, which predates 4i and still said "4i
> next". 4h + the case-insensitive-table-name fix (handoff-41's content)
> are also done and committed.
## §1. State at handoff
**Branch:** `main`. **HEAD `22e5bf5`.** **Tests: 1917 passing, 0 failing,
0 skipped, 1 ignored** (the `friendly/mod.rs` ` ```ignore ` doctest).
**Clippy:** clean (`cargo clippy --all-targets -- -D warnings`).
**Unpushed commits (all of this + the prior session's work; normal):**
```
f7e77a8 feat: ADR-0035 4h — ALTER TABLE … RENAME TO
a95c807 fix: resolve table names case-insensitively across all executors
ca64434 docs: session handoff 41 …
1afcf4e feat: ADR-0035 4i(d) — merge shared-entry-word completions
f852610 feat: ADR-0035 4i(e) — colour DSL vs SQL completions when mixed
c2eb8cb fix: ADR-0035 4i(c) — don't pre-flag a self-referencing FK parent
22e5bf5 feat: ADR-0035 4i(a,b) — CREATE TABLE help/usage + describe table constraints; Phase 4 complete
```
Push is the user's step; nothing blocks.
## §2. What shipped (4i + the Phase-4 `/runda`)
ADR-0035 **Phase 4 is complete (4a4i)**. 4i — the verification sweep —
landed in four commits (plan `docs/plans/20260526-adr-0035-sql-ddl-4i.md`):
- **4i(d)** (`1afcf4e`) — **shared-entry-word completion merge.** At the
advanced-mode entry-word boundary, `completion_probe_in_mode` walks
every candidate node and unions the viable (`Incomplete`) ones'
continuations, so `drop ` offers `table·index·column·relationship·
constraint` and `drop rel``relationship` (was an empty dead-end).
Completion-only; the parse path is untouched; deeper positions keep the
committed walk.
- **4i(e)** (`f852610`) — **simple-vs-advanced completion colour.** Each
continuation is classified `Both`/`Advanced`/`Simple`; **only when the
list mixes modes** it is coloured (`mode_advanced`/`mode_simple`; `Both`
= token-kind) and block-ordered **Both → Advanced → Simple**
(user-chosen). Single-mode lists keep token-kind colours. `Candidate`
gained a `mode` field (typing_surface snapshots regenerated, uniform
`mode: Both`).
- **4i(c)** (`c2eb8cb`) — **self-ref FK pre-submit indicator.**
`schema_existence_diagnostics` collects the CREATE TABLE target(s)
(`NewName`/`table_name`) into `created_tables` and exempts a `Tables`
ref matching one from the unknown-table flag. (Provably scoped: the
only two `NewName`/`table_name` grammar nodes are the SQL + simple
CREATE-TABLE targets — verified in the `/runda`.)
- **4i(a,b)** (`22e5bf5`) — **(b)** `describe` of table-level constraints
(`TableDescription` gained `unique_constraints` + `check_constraints`,
rendered in a "Table constraints:" section — composite UNIQUE + table
CHECK incl. named); **(a)** CREATE TABLE help/usage skeleton refreshed
for the DEFAULT/CHECK/REFERENCES/composite-UNIQUE/table-CHECK/FK forms.
**Phase 4 docs flipped to complete** (ADR Status + §13 4i + ADR index +
`requirements.md` Q1).
**Whole-Phase-4 `/runda` (2026-05-26).** Probed the feature combinations
no single slice tested, through the full pipeline + a *fresh* rebuild:
CREATE with FK + table CHECK + composite UNIQUE → ALTER → RENAME table →
fresh rebuild (all three still enforce); ALTER COLUMN TYPE on a column
inside a composite UNIQUE *and* a table CHECK (both preserved);
case-variant `alter`/`alter column type`/`add constraint` (all work +
round-trip). **All round-tripped** — strong evidence the two DDL
generators (`do_create_table` / `schema_to_ddl`) stay in sync across the
full feature set, metadata stays consistent, and the case-insensitivity
fix composes with every DDL path. No correctness/data bug; no ADR
divergence; vocab audit holds.
## §3. Tracked follow-ups from the Phase-4 `/runda` (user-decided "track")
All three are **error-message / capability** items on a rare **safe**
edge (dropping a column covered by a composite UNIQUE is correctly
*refused* — no corruption). None is a correctness or data bug.
- **F1 — friendly message for dropping a column a composite UNIQUE
covers.** `do_drop_column`'s "an index covers it — drop the index
first" guard reads `read_table_indexes`, which filters to `origin='c'`
(explicit `CREATE INDEX`) and **excludes the UNIQUE-constraint
auto-index** (`origin='u'`). So `drop column c` when `unique (b, c)`
spans `c` falls through to the raw engine refusal instead of a friendly
message. Fix: detect the column in `schema.unique_constraints` and
refuse with a clear engine-neutral message (e.g. "cannot drop `T.c`
it is part of a UNIQUE (b, c) constraint; recreate the table to change
it"). Message-only; small. (Interacts with F3.)
- **F2 — pre-existing generic-error rendering leaks a literal `{table}`
(broader than Phase 4).** Replay renders refused commands via
`DbError::friendly_message()` (`runtime.rs:~1202/1238`), which uses
`TranslateContext::default()` → the `error.generic.*` template comes
out with a **literal unsubstituted `{table}`** and `operation` (no
table/operation context). Affects **every** command refused during
replay (and other `friendly_message()` callsites, e.g. export) — not
Phase-4-specific. Fix needs care: it's a shared path; make the hint
degrade gracefully when no table is in context (drop the `… of
{table}` clause, or say "the table") and check snapshots. Scope it on
its own.
- **F3 — provide a way to drop a composite UNIQUE constraint (user-
raised; own ADR).** A composite UNIQUE is **anonymous** by design
(ADR-0035 §4a.2; 4g refused naming UNIQUE) — stored as a column-list
with no name, so no `drop constraint <name>` can target it, and it
can't be removed except by recreating the table. The user wants a way
to drop it. This is a **design decision / new capability** (likely a
new ADR or an ADR-0035 amendment): either name composite UNIQUEs, or a
positional `drop constraint unique (cols)` / `alter table T drop unique
(cols)` form, executed via the rebuild primitive. F1's message becomes
actionable once F3 lands.
## §4. Carried follow-ups (from handoff-41, still open)
- **H1 wording — `--create-fk` leak (4g).** `ALTER … ADD FOREIGN KEY` on
a missing child column reuses `do_add_relationship`'s error mentioning
the DSL flag `--create-fk` — off-key in SQL. Fix the SQL-path wording.
- **Case-only table rename** refusal (4h, autonomous decision) — `alter
table T rename to t` refused ("differ only in capitalization"). Left as
refuse unless the user wants it supported (would need a temp-name
two-step).
- **Column-name case strictness** — table names resolve case-insensitively
now; column names are still matched case-sensitively (wrong case → "no
such column"). Safe; a separate UX-consistency change if wanted.
- **Coverage gap — pre-4g 3-column `CHECK_TABLE` migration** in-place path
untested (can't fabricate a 3-col table via the public API).
- **H1 friendly wording** for the 4e CHECK-guard refusals + 4f
type-conversion diagnostics (engine-neutral but terse).
- The handoff-39 §8 items: app-lifecycle-command runtime-failure
journalling; M4 execution-time mode side-channel; `blob` value literal;
CI/TT5; DSL→SQL teaching echo (ADR-0030 Phase 5).
## §5. What's next (no committed scope)
ADR-0035 / Phase 4 of ADR-0030 is **done**. Open avenues (per
`requirements.md` / CLAUDE.md "deferred"): the SQL→English friendly layer
(H1), tutorial/lesson system, session-log + Markdown export (V4),
readline/multiline/tab-completion/syntax-highlight input polish, ER
diagram export (V3), CI (TT5), and the F1F3 follow-ups above. None is
started; pick with the user.
## §6. Process pins (unchanged)
- **Confirm every commit** (propose message, wait). No AI attribution.
**Push is the user's step.** Unpushed commits are normal.
- **Escalate ambiguity / long tails.** This session surfaced and
user-decided every fork (4h scope, case-safety scope, 4i(e) colour
design, and the F1F3 follow-ups).
- **`/runda` at planning exit AND on finished slices** — it earned its
keep repeatedly this session (the 4h CHECK-drift, the case-collision
leak, and confirming the integrated Phase 4 is sound).
- **Keep docs lockstep** — ADR status/§13 + index + requirements in the
same edit.
## §7. How to take over
1. **Read, in order:** this file → `CLAUDE.md` →
`docs/adr/0035-advanced-mode-sql-ddl.md` (now fully shipped) →
`docs/requirements.md`.
2. **Baseline:** `cargo test` (1917 / 0 / 0 / 1 ignored) + `cargo clippy
--all-targets -- -D warnings` (clean).
3. Phase 4 is complete; there is **no in-flight slice**. Pick the next
piece of work with the user (§5), or take an F1F3 follow-up.