-
Notifications
You must be signed in to change notification settings - Fork 744
PG18 – Respect VACUUM/ANALYZE ONLY semantics for Citus tables #8365
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Conversation
1d606af to
c499b6b
Compare
efb93ff to
321d1d5
Compare
Codecov Report❌ Patch coverage is Additional details and impacted files@@ Coverage Diff @@
## main #8365 +/- ##
==========================================
- Coverage 88.94% 88.93% -0.02%
==========================================
Files 287 287
Lines 63146 63150 +4
Branches 7935 7938 +3
==========================================
- Hits 56164 56160 -4
- Misses 4672 4677 +5
- Partials 2310 2313 +3 🚀 New features to boost your workflow:
|
c499b6b to
459128f
Compare
321d1d5 to
ac691b1
Compare
colm-mchugh
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Lgtm, thanks for including the test on a distributed, partitioned table.
459128f to
bdd4c24
Compare
76f8090 to
d1b96e8
Compare
d1b96e8 to
02af7f8
Compare
fixes #8364
PostgreSQL 18 changes VACUUM/ANALYZE to recurse into inheritance children by default, and introduces
ONLYto limit processing to the parent. Upstream change:postgres/postgres@62ddf7ee9
For Citus tables, we should treat shard placements as “children” and avoid propagating
VACUUM/ANALYZEto shards when the user explicitly asks forONLY.This PR adjusts the Citus VACUUM handling to align with PG18 semantics, and adds regression coverage on both regular distributed tables and partitioned distributed tables.
Behavior changes
Introduce a per-relation helper struct:
This lets us keep both:
IsCitusTable, task building), andVacuumRelationnode (for column list and ONLY/inh flag).Replace the old
VacuumRelationIdList/ExtractVacuumTargetRelsflow with:VacuumRelationListnow:vacuumStmt->rels.relidviaRangeVarGetRelidExtendedwhenrelationis present.VacuumRelation->oidwhen only an OID is available.VACOPT_FULLfor lock mode andVACOPT_SKIP_LOCKEDfor locking behavior.List *ofCitusVacuumRelationentries.Update:
to operate on
CitusVacuumRelationinstead of bare OIDs.Implement
ONLYsemantics inExecuteVacuumOnDistributedTables:Effect:
VACUUM / ANALYZE(noONLY) on a Citus table: behavior unchanged, Citus creates tasks and propagates to shard placements.VACUUM ONLY <citus_table>/ANALYZE ONLY <citus_table>:The code compiles and behaves as before on pre-PG18; the new behavior becomes observable only when the core planner starts setting
inh = falseforONLY(PG18).Unqualified
VACUUM/ANALYZE(no rels) is unchanged and still handled viaExecuteUnqualifiedVacuumTasks.Remove now-redundant helpers:
VacuumColumnListExtractVacuumTargetRelsColumn lists are now taken directly from
vacuumRelation->va_colsviaCitusVacuumRelation.Testing
Extend
src/test/regress/sql/pg18.sqlandexpected/pg18.outwith two PG18-only blocks that verify we do not recurse into shard placements whenONLYis used:Simple distributed table (
pg18_vacuum_part)Create and distribute a regular table:
On the coordinator:
ANALYZE vac_analyze_only;and laterANALYZE ONLY vac_analyze_only;.VACUUM vac_analyze_only;and laterVACUUM ONLY vac_analyze_only;.On
worker_1:Capture
coalesce(max(last_analyze), 'epoch')frompg_stat_user_tablesforvac_analyze_only_%into:analyze_before_only, then assert:Capture
coalesce(max(last_vacuum), 'epoch')into:vacuum_before_only, then assert:Both checks return
t, confirmingONLYdoes not changelast_analyze/last_vacuumon shard tables.Partitioned distributed table (
pg18_vacuum_part_dist)Create a partitioned table whose parent is distributed:
On the coordinator:
ANALYZE part_dist;thenANALYZE ONLY part_dist;.VACUUM part_dist;thenVACUUM ONLY part_dist;(PG18 emits the expected warning:VACUUM ONLY of partitioned table "part_dist" has no effect).On
worker_1:Capture
coalesce(max(last_analyze), 'epoch')forpart_dist_%into:analyze_before_only, then assert:Capture
coalesce(max(last_vacuum), 'epoch')into:vacuum_before_only, then assert:Both checks return
t, confirming that even for a partitioned distributed parent,VACUUM/ANALYZE ONLYdoes not recurse into shard placements, and Citus behavior matches PG18’s “ONLY = parent only” semantics.