Movatterモバイル変換


[0]ホーム

URL:


Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings

Commitc426f7c

Browse files
committed
Fix assertion failure with REINDEX and event triggers
A REINDEX CONCURRENTLY run on a table with no indexes would always popthe topmost snapshot from the active snapshot stack, making the snapshothandling inconsistent between the multiple-relation and single-relationcases. This commit slightly changes the snapshot stack handling so as asnapshot is popped only ReindexMultipleInternal() in this case after arelation has been reindexed, fixing a problem where an event triggerfunction may need a snapshot but does not have one. This also keeps theplaces where PopActiveSnapshot() is called closer to each other.While on it, this expands the existing tests to cover all the cases thatcould be faced with REINDEX commands and such event triggers, for one ormore relations, with or without indexes.This behavior is inconsistent since5dc92b8, but we've never had aneed for an active snapshot at the end of a REINDEX until now.Thanks also to Jian He for the input.Reported-by: Alexander LakhinDiscussion:https://postgr.es/m/cb538743-484c-eb6a-a8c5-359980cd3a17@gmail.com
1 parentc2a465b commitc426f7c

File tree

3 files changed

+99
-3
lines changed

3 files changed

+99
-3
lines changed

‎src/backend/commands/indexcmds.c

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -3347,6 +3347,8 @@ ReindexMultipleInternal(const ReindexStmt *stmt, const List *relids, const Reind
33473347

33483348
newparams.options |=REINDEXOPT_MISSING_OK;
33493349
(void)ReindexRelationConcurrently(stmt,relid,&newparams);
3350+
if (ActiveSnapshotSet())
3351+
PopActiveSnapshot();
33503352
/* ReindexRelationConcurrently() does the verbose output */
33513353
}
33523354
elseif (relkind==RELKIND_INDEX)
@@ -3698,10 +3700,7 @@ ReindexRelationConcurrently(const ReindexStmt *stmt, Oid relationOid, const Rein
36983700
* session until this operation completes.
36993701
*/
37003702
if (indexIds==NIL)
3701-
{
3702-
PopActiveSnapshot();
37033703
return false;
3704-
}
37053704

37063705
/* It's not a shared catalog, so refuse to move it to shared tablespace */
37073706
if (params->tablespaceOid==GLOBALTABLESPACE_OID)

‎src/test/regress/expected/event_trigger.out

Lines changed: 52 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -581,6 +581,12 @@ $$ LANGUAGE plpgsql;
581581
CREATE EVENT TRIGGER regress_reindex_end ON ddl_command_end
582582
WHEN TAG IN ('REINDEX')
583583
EXECUTE PROCEDURE reindex_end_command();
584+
-- Extra event to force the use of a snapshot.
585+
CREATE FUNCTION reindex_end_command_snap() RETURNS EVENT_TRIGGER
586+
AS $$ BEGIN PERFORM 1; END $$ LANGUAGE plpgsql;
587+
CREATE EVENT TRIGGER regress_reindex_end_snap ON ddl_command_end
588+
EXECUTE FUNCTION reindex_end_command_snap();
589+
-- With simple relation
584590
CREATE TABLE concur_reindex_tab (c1 int);
585591
CREATE INDEX concur_reindex_ind ON concur_reindex_tab (c1);
586592
-- Both start and end triggers enabled.
@@ -602,10 +608,56 @@ REINDEX INDEX concur_reindex_ind;
602608
NOTICE: REINDEX END: command_tag=REINDEX type=index identity=public.concur_reindex_ind
603609
REINDEX INDEX CONCURRENTLY concur_reindex_ind;
604610
NOTICE: REINDEX END: command_tag=REINDEX type=index identity=public.concur_reindex_ind
611+
-- without an index
612+
DROP INDEX concur_reindex_ind;
613+
REINDEX TABLE concur_reindex_tab;
614+
NOTICE: table "concur_reindex_tab" has no indexes to reindex
615+
REINDEX TABLE CONCURRENTLY concur_reindex_tab;
616+
NOTICE: table "concur_reindex_tab" has no indexes that can be reindexed concurrently
617+
-- With a Schema
618+
CREATE SCHEMA concur_reindex_schema;
619+
-- No indexes
620+
REINDEX SCHEMA concur_reindex_schema;
621+
REINDEX SCHEMA CONCURRENTLY concur_reindex_schema;
622+
CREATE TABLE concur_reindex_schema.tab (a int);
623+
CREATE INDEX ind ON concur_reindex_schema.tab (a);
624+
-- One index reported
625+
REINDEX SCHEMA concur_reindex_schema;
626+
NOTICE: REINDEX END: command_tag=REINDEX type=index identity=concur_reindex_schema.ind
627+
REINDEX SCHEMA CONCURRENTLY concur_reindex_schema;
628+
NOTICE: REINDEX END: command_tag=REINDEX type=index identity=concur_reindex_schema.ind
629+
-- One table on schema but no indexes
630+
DROP INDEX concur_reindex_schema.ind;
631+
REINDEX SCHEMA concur_reindex_schema;
632+
REINDEX SCHEMA CONCURRENTLY concur_reindex_schema;
633+
DROP SCHEMA concur_reindex_schema CASCADE;
634+
NOTICE: drop cascades to table concur_reindex_schema.tab
635+
-- With a partitioned table, and nothing else.
636+
CREATE TABLE concur_reindex_part (id int) PARTITION BY RANGE (id);
637+
REINDEX TABLE concur_reindex_part;
638+
REINDEX TABLE CONCURRENTLY concur_reindex_part;
639+
-- Partition that would be reindexed, still nothing.
640+
CREATE TABLE concur_reindex_child PARTITION OF concur_reindex_part
641+
FOR VALUES FROM (0) TO (10);
642+
REINDEX TABLE concur_reindex_part;
643+
REINDEX TABLE CONCURRENTLY concur_reindex_part;
644+
-- Now add some indexes.
645+
CREATE INDEX concur_reindex_partidx ON concur_reindex_part (id);
646+
REINDEX INDEX concur_reindex_partidx;
647+
NOTICE: REINDEX END: command_tag=REINDEX type=index identity=public.concur_reindex_child_id_idx
648+
REINDEX INDEX CONCURRENTLY concur_reindex_partidx;
649+
NOTICE: REINDEX END: command_tag=REINDEX type=index identity=public.concur_reindex_child_id_idx
650+
REINDEX TABLE concur_reindex_part;
651+
NOTICE: REINDEX END: command_tag=REINDEX type=index identity=public.concur_reindex_child_id_idx
652+
REINDEX TABLE CONCURRENTLY concur_reindex_part;
653+
NOTICE: REINDEX END: command_tag=REINDEX type=index identity=public.concur_reindex_child_id_idx
654+
DROP TABLE concur_reindex_part;
605655
-- Clean up
606656
DROP EVENT TRIGGER regress_reindex_start;
607657
DROP EVENT TRIGGER regress_reindex_end;
658+
DROP EVENT TRIGGER regress_reindex_end_snap;
608659
DROP FUNCTION reindex_end_command();
660+
DROP FUNCTION reindex_end_command_snap();
609661
DROP FUNCTION reindex_start_command();
610662
DROP TABLE concur_reindex_tab;
611663
-- test Row Security Event Trigger

‎src/test/regress/sql/event_trigger.sql

Lines changed: 45 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -443,7 +443,13 @@ $$ LANGUAGE plpgsql;
443443
CREATE EVENT TRIGGER regress_reindex_endON ddl_command_end
444444
WHEN TAGIN ('REINDEX')
445445
EXECUTE PROCEDURE reindex_end_command();
446+
-- Extra event to force the use of a snapshot.
447+
CREATEFUNCTIONreindex_end_command_snap() RETURNS EVENT_TRIGGER
448+
AS $$BEGIN PERFORM1; END $$ LANGUAGE plpgsql;
449+
CREATE EVENT TRIGGER regress_reindex_end_snapON ddl_command_end
450+
EXECUTE FUNCTION reindex_end_command_snap();
446451

452+
-- With simple relation
447453
CREATETABLEconcur_reindex_tab (c1int);
448454
CREATEINDEXconcur_reindex_indON concur_reindex_tab (c1);
449455
-- Both start and end triggers enabled.
@@ -455,11 +461,50 @@ REINDEX TABLE CONCURRENTLY concur_reindex_tab;
455461
ALTER EVENT TRIGGER regress_reindex_start DISABLE;
456462
REINDEX INDEX concur_reindex_ind;
457463
REINDEX INDEX CONCURRENTLY concur_reindex_ind;
464+
-- without an index
465+
DROPINDEX concur_reindex_ind;
466+
REINDEX TABLE concur_reindex_tab;
467+
REINDEX TABLE CONCURRENTLY concur_reindex_tab;
468+
469+
-- With a Schema
470+
CREATESCHEMAconcur_reindex_schema;
471+
-- No indexes
472+
REINDEX SCHEMA concur_reindex_schema;
473+
REINDEX SCHEMA CONCURRENTLY concur_reindex_schema;
474+
CREATETABLEconcur_reindex_schema.tab (aint);
475+
CREATEINDEXindONconcur_reindex_schema.tab (a);
476+
-- One index reported
477+
REINDEX SCHEMA concur_reindex_schema;
478+
REINDEX SCHEMA CONCURRENTLY concur_reindex_schema;
479+
-- One table on schema but no indexes
480+
DROPINDEXconcur_reindex_schema.ind;
481+
REINDEX SCHEMA concur_reindex_schema;
482+
REINDEX SCHEMA CONCURRENTLY concur_reindex_schema;
483+
DROPSCHEMA concur_reindex_schema CASCADE;
484+
485+
-- With a partitioned table, and nothing else.
486+
CREATETABLEconcur_reindex_part (idint) PARTITION BY RANGE (id);
487+
REINDEX TABLE concur_reindex_part;
488+
REINDEX TABLE CONCURRENTLY concur_reindex_part;
489+
-- Partition that would be reindexed, still nothing.
490+
CREATETABLEconcur_reindex_child PARTITION OF concur_reindex_part
491+
FORVALUESFROM (0) TO (10);
492+
REINDEX TABLE concur_reindex_part;
493+
REINDEX TABLE CONCURRENTLY concur_reindex_part;
494+
-- Now add some indexes.
495+
CREATEINDEXconcur_reindex_partidxON concur_reindex_part (id);
496+
REINDEX INDEX concur_reindex_partidx;
497+
REINDEX INDEX CONCURRENTLY concur_reindex_partidx;
498+
REINDEX TABLE concur_reindex_part;
499+
REINDEX TABLE CONCURRENTLY concur_reindex_part;
500+
DROPTABLE concur_reindex_part;
458501

459502
-- Clean up
460503
DROP EVENT TRIGGER regress_reindex_start;
461504
DROP EVENT TRIGGER regress_reindex_end;
505+
DROP EVENT TRIGGER regress_reindex_end_snap;
462506
DROPFUNCTION reindex_end_command();
507+
DROPFUNCTION reindex_end_command_snap();
463508
DROPFUNCTION reindex_start_command();
464509
DROPTABLE concur_reindex_tab;
465510

0 commit comments

Comments
 (0)

[8]ページ先頭

©2009-2025 Movatter.jp