mirror of
https://git.postgresql.org/git/postgresql.git
synced 2024-12-27 08:39:28 +08:00
Let ALTER TABLE Phase 2 routines manage the relation pointer
Struct AlteredRelationInfo gains a new Relation member, to be used only by Phase 2 (ATRewriteCatalogs); this allows ATExecCmd() subroutines open and close the relation internally. A future commit will use this facility to implement an ALTER TABLE subcommand that closes and reopens the relation across transaction boundaries. (It is possible to keep the relation open past phase 2 to be used by phase 3 instead of having to reopen it that point, but there are some minor complications with that; it's not clear that there is much to be won from doing that, though.) Author: Álvaro Herrera <alvherre@alvh.no-ip.org> Discussion: https://postgr.es/m/20200803234854.GA24158@alvherre.pgsql
This commit is contained in:
parent
4669cacbd4
commit
cd03c6e94b
@ -157,6 +157,8 @@ typedef struct AlteredTableInfo
|
||||
Oid relid; /* Relation to work on */
|
||||
char relkind; /* Its relkind */
|
||||
TupleDesc oldDesc; /* Pre-modification tuple descriptor */
|
||||
/* Transiently set during Phase 2, normally set to NULL */
|
||||
Relation rel;
|
||||
/* Information saved by Phase 1 for Phase 2: */
|
||||
List *subcmds[AT_NUM_PASSES]; /* Lists of AlterTableCmd */
|
||||
/* Information saved by Phases 1/2 for Phase 3: */
|
||||
@ -354,7 +356,7 @@ static void ATPrepCmd(List **wqueue, Relation rel, AlterTableCmd *cmd,
|
||||
AlterTableUtilityContext *context);
|
||||
static void ATRewriteCatalogs(List **wqueue, LOCKMODE lockmode,
|
||||
AlterTableUtilityContext *context);
|
||||
static void ATExecCmd(List **wqueue, AlteredTableInfo *tab, Relation rel,
|
||||
static void ATExecCmd(List **wqueue, AlteredTableInfo *tab,
|
||||
AlterTableCmd *cmd, LOCKMODE lockmode, int cur_pass,
|
||||
AlterTableUtilityContext *context);
|
||||
static AlterTableCmd *ATParseTransformCmd(List **wqueue, AlteredTableInfo *tab,
|
||||
@ -4569,7 +4571,6 @@ ATRewriteCatalogs(List **wqueue, LOCKMODE lockmode,
|
||||
{
|
||||
AlteredTableInfo *tab = (AlteredTableInfo *) lfirst(ltab);
|
||||
List *subcmds = tab->subcmds[pass];
|
||||
Relation rel;
|
||||
ListCell *lcmd;
|
||||
|
||||
if (subcmds == NIL)
|
||||
@ -4578,10 +4579,10 @@ ATRewriteCatalogs(List **wqueue, LOCKMODE lockmode,
|
||||
/*
|
||||
* Appropriate lock was obtained by phase 1, needn't get it again
|
||||
*/
|
||||
rel = relation_open(tab->relid, NoLock);
|
||||
tab->rel = relation_open(tab->relid, NoLock);
|
||||
|
||||
foreach(lcmd, subcmds)
|
||||
ATExecCmd(wqueue, tab, rel,
|
||||
ATExecCmd(wqueue, tab,
|
||||
castNode(AlterTableCmd, lfirst(lcmd)),
|
||||
lockmode, pass, context);
|
||||
|
||||
@ -4593,7 +4594,11 @@ ATRewriteCatalogs(List **wqueue, LOCKMODE lockmode,
|
||||
if (pass == AT_PASS_ALTER_TYPE)
|
||||
ATPostAlterTypeCleanup(wqueue, tab, lockmode);
|
||||
|
||||
relation_close(rel, NoLock);
|
||||
if (tab->rel)
|
||||
{
|
||||
relation_close(tab->rel, NoLock);
|
||||
tab->rel = NULL;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -4619,11 +4624,12 @@ ATRewriteCatalogs(List **wqueue, LOCKMODE lockmode,
|
||||
* ATExecCmd: dispatch a subcommand to appropriate execution routine
|
||||
*/
|
||||
static void
|
||||
ATExecCmd(List **wqueue, AlteredTableInfo *tab, Relation rel,
|
||||
ATExecCmd(List **wqueue, AlteredTableInfo *tab,
|
||||
AlterTableCmd *cmd, LOCKMODE lockmode, int cur_pass,
|
||||
AlterTableUtilityContext *context)
|
||||
{
|
||||
ObjectAddress address = InvalidObjectAddress;
|
||||
Relation rel = tab->rel;
|
||||
|
||||
switch (cmd->subtype)
|
||||
{
|
||||
@ -5730,6 +5736,7 @@ ATGetQueueEntry(List **wqueue, Relation rel)
|
||||
*/
|
||||
tab = (AlteredTableInfo *) palloc0(sizeof(AlteredTableInfo));
|
||||
tab->relid = relid;
|
||||
tab->rel = NULL; /* set later */
|
||||
tab->relkind = rel->rd_rel->relkind;
|
||||
tab->oldDesc = CreateTupleDescCopyConstr(RelationGetDescr(rel));
|
||||
tab->newrelpersistence = RELPERSISTENCE_PERMANENT;
|
||||
|
Loading…
Reference in New Issue
Block a user