Repository navigation
Weasel 9.27.0
Nine fixes since 9.26.0. Every one is a case where Weasel read a schema back as something other than what the database actually held. No DDL changes for a schema it was already reading correctly, and no configuration changes.
Full upgrade guide: Upgrading to 9.27
Three that could never converge
A delta that cannot converge is worse than a wrong one — the patch is applied, the read-back is still different, and the next run produces the identical patch indefinitely.
- A named foreign key on SQLite rebuilt the table on every run (#516).
pragma_foreign_key_listhas no name column, so the read invented one. Every foreign key Weasel had itself written came back under a name the model did not have — and on SQLite that is repaired by rebuilding the table and copying every row. - A partition-aligned index on SQL Server was dropped and recreated on every run (#512). The implicit
sys.index_columnsrow for the partitioning column was read as a declared key column, so the index compared unequal to itself. The rebuilt index read back the same way. - A concurrent index on a manager-owned partitioned table stayed permanently invalid (#520).
ListPartitioning.PartitionTableNamesignored the partition manager and returned the empty sequence, so only the metadata-only first step of the three-step sequence rendered. Strictly worse than the blockingCREATE INDEXit replaced.
One that failed outright
- A procedure, user-defined type or trigger broke any migration it shared (#515, #518). Introspection queries are concatenated into one command, so each must terminate itself. Several did not, and the next statement ran into the previous one —
42601: syntax error at or near "select". Any migration containing one of them plus another object failed, unless the unterminated one happened to be last. Fixed on PostgreSQL, SQLite and MySQL; SQL Server's were unaffected in practice but are terminated now too. Oracle stays deliberately unterminated, and a conformance test asserts all three facts.
Composite keys and index fidelity
- A composite foreign key could pair the wrong columns (#511, #516). Both sides were sorted independently, which kept each list tidy and destroyed the pairing between them.
- Composite primary key order was discarded on every provider (#511, #516, #517).
(a, b)and(b, a)are different indexes with different query plans. - An index's per-column sort direction was read as a whole-index flag (#513), marking the wrong column — so
(a DESC, b)read back as(a, b DESC), and a genuinely different index was never reported as drift. - Hash partitions compared by catalog order rather than by bound (#514), so a hash-partitioned table compared equal or unequal to itself depending on what
pg_inheritsreturned. - SQL Server column type arguments and IDENTITY were lost on read-back, and
IgnoreIndexwas ignored entirely (#511) — the generated patch dropped the very index it was meant to protect.
New API
SetPrimaryKeyOrder / HasExplicitPrimaryKeyOrder on TableBase, and DescendingColumns / CompareColumnDirection on SQL Server's IndexDefinition.
Both are opt-in, deliberately: reading order faithfully must not become comparing it for a model that never expressed one. A model that only flags columns cannot say (c, a), so comparing unconditionally would report drift the user cannot resolve — and "fixing" it is a table rebuild on a clustered key, or a full row copy on SQLite.
Verification
Built from a fresh clone against fresh containers for all five databases: 18 of 18 suites green, 0 failures, across net9.0 and net10.0 — PostgreSQL under both case-sensitivity settings.