fix: emit per-child column overrides in PARTITION OF (#499)#500
Conversation
… OF (#499) When a partition child overrides DEFAULT or NOT NULL relative to the parent, generate the column-element list inside the PARTITION OF statement so `pgschema plan` produces faithful DDL. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
There was a problem hiding this comment.
Pull request overview
This PR extends the CREATE TABLE ... PARTITION OF ... emission path so that partition children can include a typed-table element list when they override DEFAULT and/or NOT NULL relative to the parent, aligning generated DDL with PostgreSQL’s supported grammar and addressing issue #499.
Changes:
- Detect per-child column overrides for partition children and include them in the
PARTITION OF (...)element list. - Thread an
allTableslookup intogenerateTableSQLto compare child columns against the parent. - Add a new fixture-backed test case (
issue_499_partition_column_overrides) validating the emitted plan/DDL.
Reviewed changes
Copilot reviewed 8 out of 8 changed files in this pull request and generated 1 comment.
Show a summary per file
| File | Description |
|---|---|
internal/diff/table.go |
Adds partition-child column override detection and includes override elements in the PARTITION OF (...) list. |
internal/diff/qualify_schema_test.go |
Updates test helper calls for the new generateTableSQL(..., allTables) signature. |
testdata/diff/create_table/issue_499_partition_column_overrides/plan.txt |
New expected plan output for the added fixture. |
testdata/diff/create_table/issue_499_partition_column_overrides/plan.sql |
New expected SQL plan output for the added fixture. |
testdata/diff/create_table/issue_499_partition_column_overrides/plan.json |
New expected JSON plan output for the added fixture. |
testdata/diff/create_table/issue_499_partition_column_overrides/old.sql |
New fixture: empty starting schema. |
testdata/diff/create_table/issue_499_partition_column_overrides/new.sql |
New fixture: partitioned table + child overrides. |
testdata/diff/create_table/issue_499_partition_column_overrides/diff.sql |
New expected diff SQL for the fixture. |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
Greptile SummaryThis PR fixes issue #499 by emitting per-child column overrides (
Confidence Score: 3/5The fix correctly handles the tested scenario but silently produces wrong DDL in two real migration paths, making it unsafe to merge as-is. The allTables map is scoped to each call of generateCreateTablesSQL. Because diff.go calls that function twice with two disjoint table batches, a child in batch 2 cannot see a parent from batch 1. Separately, when a partition child is added to a pre-existing parent, the parent is absent from addedTables entirely. In both cases the override detection guard silently falls through, emitting bare PARTITION OF DDL without column overrides — and since PostgreSQL has no ALTER path to add them post-creation, the resulting schema is permanently wrong without any error or warning. internal/diff/table.go — specifically the allTables construction and the parentKey lookup inside generateTableSQL Important Files Changed
Flowchart%%{init: {'theme': 'neutral'}}%%
flowchart TD
A[generateCreateTablesSQL\ncalled with batch of new tables] --> B[Build allTables map\nfrom batch only]
B --> C[For each table in batch]
C --> D{table.PartitionOf != ''}
D -- No --> E[Emit standard CREATE TABLE]
D -- Yes --> F{parentKey in allTables?}
F -- No --> G[No override detection\n⚠ silent miss if parent\nin different batch or\nalready exists]
F -- Yes --> H[For each child column\ncompare with parent column]
H --> I{childDefault != parentDefault\nAND child has DEFAULT?}
I -- Yes --> J[Append DEFAULT override]
I -- No --> K{child NOT NULL\nAND parent nullable?}
J --> K
K -- Yes --> L[Append NOT NULL override]
K -- No --> M[Next column]
L --> M
M --> N{More columns?}
N -- Yes --> H
N -- No --> O[Combine elementParts + constraintParts]
O --> P{Any parts?}
P -- Yes --> Q[Emit PARTITION OF with column element list]
P -- No --> R[Emit bare PARTITION OF]
%%{init: {'theme': 'base', 'themeVariables': {"darkMode": true, "background": "#0d1117", "primaryColor": "#21262d", "primaryTextColor": "#e6edf3", "primaryBorderColor": "#8b949e", "lineColor": "#8b949e", "textColor": "#e6edf3", "edgeLabelBackground": "#161b22", "actorBkg": "#21262d", "actorBorder": "#8b949e", "actorTextColor": "#e6edf3", "actorLineColor": "#8b949e", "signalColor": "#8b949e", "signalTextColor": "#e6edf3", "noteBkgColor": "#373320", "noteBorderColor": "#d4a72c", "noteTextColor": "#f0e6c0", "labelBoxBkgColor": "#21262d", "labelBoxBorderColor": "#8b949e", "labelTextColor": "#e6edf3", "loopTextColor": "#e6edf3", "activationBkgColor": "#30363d", "activationBorderColor": "#8b949e"}}}%%
flowchart TD
A[generateCreateTablesSQL\ncalled with batch of new tables] --> B[Build allTables map\nfrom batch only]
B --> C[For each table in batch]
C --> D{table.PartitionOf != ''}
D -- No --> E[Emit standard CREATE TABLE]
D -- Yes --> F{parentKey in allTables?}
F -- No --> G[No override detection\n⚠ silent miss if parent\nin different batch or\nalready exists]
F -- Yes --> H[For each child column\ncompare with parent column]
H --> I{childDefault != parentDefault\nAND child has DEFAULT?}
I -- Yes --> J[Append DEFAULT override]
I -- No --> K{child NOT NULL\nAND parent nullable?}
J --> K
K -- Yes --> L[Append NOT NULL override]
K -- No --> M[Next column]
L --> M
M --> N{More columns?}
N -- Yes --> H
N -- No --> O[Combine elementParts + constraintParts]
O --> P{Any parts?}
P -- Yes --> Q[Emit PARTITION OF with column element list]
P -- No --> R[Emit bare PARTITION OF]
Reviews (1): Last reviewed commit: "fix: emit per-child column overrides (DE..." | Re-trigger Greptile |
Address review feedback from Copilot, Greptile, and @schema-codex: the parent lookup for column-override detection was scoped to the current add-table batch, silently missing existing parents and cross-batch parents. Now uses allNewTables (all tables from the target schema state) so override detection works regardless of whether the parent is new or pre-existing. Adds regression fixture for the incremental case (existing parent, new child with overrides). Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
|
Re-checked the latest head after 7decbf3 and 0c77576. The earlier blocker was real, but it is now addressed: parent lookup for partition-column override comparison is sourced from the full target IR, and the incremental existing-parent case is covered by the new regression fixture. The remaining CI failure was only the stale plan fixture hash, which 0c77576 corrected. Current CI is green on the latest head. Greptile's remaining summary is stale and refers to the older d775dc1 snapshot. No remaining findings from the reviewer pass; ready to merge. |
Keep the existing-parent case (stronger test — covers the review-flagged incremental scenario) and remove the redundant empty-schema case. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Summary
DEFAULTorNOT NULLrelative to its parent, thePARTITION OFstatement now includes the column-element list (e.g.priority DEFAULT 10, notes NOT NULL).allTablesmap togenerateTableSQLso it can compare child columns against the parent and detect overrides.issue_499_partition_column_overrideswith full diff/plan fixtures.Closes #499
Test plan
TestDiffFromFiles/create_table_issue_499_partition_column_overridespassesinternal/difftests pass🤖 Generated with Claude Code