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

Commite5bc945

Browse files
committed
Explicitly list dependent types as extension members in pg_depend.
Auto-generated array types, multirange types, and relation rowtypesare treated as dependent objects: they can't be dropped separatelyfrom the base object, nor can they have their own ownership orpermissions. We previously felt that, for objects that are in anextension, only the base object needs to be listed as an extensionmember in pg_depend. While that's sufficient to prevent inappropriatedrops, it results in undesirable answers if someone asks whether adependent type belongs to the extension. It looks like the dependenttype is just some random separately-created object that happens todepend on the base object. Notably, this results in postgres_fdwconcluding that expressions involving an array type are not shippableto the remote server, even when the defining extension has beenwhitelisted.To fix, cause GenerateTypeDependencies to make extension dependenciesfor dependent types as well as their base objects, and adjustExecAlterExtensionContentsStmt so that object addition and removaloperations recurse to dependent types. The latter change means thatpg_upgrade of a type-defining extension will end with the dependenttype(s) now also listed as extension members, even if they werenot that way in the source database. Normally we want pg_upgradeto precisely reproduce the source extension's state, but it seemsdesirable to make an exception here.This is arguably a bug fix, but we can't back-patch it since itcauses changes in the expected contents of pg_depend. (Becauseit does, I've bumped catversion, even though there's no changein the immediate post-initdb catalog contents.)Tom Lane and David GeierDiscussion:https://postgr.es/m/4a847c55-489f-4e8d-a664-fc6b1cbe306f@gmail.com
1 parentdc8f2d7 commite5bc945

File tree

9 files changed

+265
-25
lines changed

9 files changed

+265
-25
lines changed

‎src/backend/catalog/pg_type.c

Lines changed: 12 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -539,7 +539,7 @@ TypeCreate(Oid newTypeOid,
539539
* etc.
540540
*
541541
* We make an extension-membership dependency if we're in an extension
542-
* script and makeExtensionDep is true (and isDependentType isn't true).
542+
* script and makeExtensionDep is true.
543543
* makeExtensionDep should be true when creating a new type or replacing a
544544
* shell type, but not for ALTER TYPE on an existing type. Passing false
545545
* causes the type's extension membership to be left alone.
@@ -599,7 +599,7 @@ GenerateTypeDependencies(HeapTuple typeTuple,
599599
ObjectAddressSet(myself,TypeRelationId,typeObjectId);
600600

601601
/*
602-
* Make dependencies on namespace, owner, ACL, extension.
602+
* Make dependencies on namespace, owner, ACL.
603603
*
604604
* Skip these for a dependent type, since it will have such dependencies
605605
* indirectly through its depended-on type or relation. An exception is
@@ -624,11 +624,18 @@ GenerateTypeDependencies(HeapTuple typeTuple,
624624

625625
recordDependencyOnNewAcl(TypeRelationId,typeObjectId,0,
626626
typeForm->typowner,typacl);
627-
628-
if (makeExtensionDep)
629-
recordDependencyOnCurrentExtension(&myself,rebuild);
630627
}
631628

629+
/*
630+
* Make extension dependency if requested.
631+
*
632+
* We used to skip this for dependent types, but it seems better to record
633+
* their extension membership explicitly; otherwise code such as
634+
* postgres_fdw's shippability test will be fooled.
635+
*/
636+
if (makeExtensionDep)
637+
recordDependencyOnCurrentExtension(&myself,rebuild);
638+
632639
/* Normal dependencies on the I/O and support functions */
633640
if (OidIsValid(typeForm->typinput))
634641
{

‎src/backend/commands/extension.c

Lines changed: 73 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -129,6 +129,9 @@ static void ApplyExtensionUpdates(Oid extensionOid,
129129
char*origSchemaName,
130130
boolcascade,
131131
boolis_create);
132+
staticvoidExecAlterExtensionContentsRecurse(AlterExtensionContentsStmt*stmt,
133+
ObjectAddressextension,
134+
ObjectAddressobject);
132135
staticchar*read_whole_file(constchar*filename,int*length);
133136

134137

@@ -3292,7 +3295,6 @@ ExecAlterExtensionContentsStmt(AlterExtensionContentsStmt *stmt,
32923295
ObjectAddressextension;
32933296
ObjectAddressobject;
32943297
Relationrelation;
3295-
OidoldExtension;
32963298

32973299
switch (stmt->objtype)
32983300
{
@@ -3347,6 +3349,38 @@ ExecAlterExtensionContentsStmt(AlterExtensionContentsStmt *stmt,
33473349
check_object_ownership(GetUserId(),stmt->objtype,object,
33483350
stmt->object,relation);
33493351

3352+
/* Do the update, recursing to any dependent objects */
3353+
ExecAlterExtensionContentsRecurse(stmt,extension,object);
3354+
3355+
/* Finish up */
3356+
InvokeObjectPostAlterHook(ExtensionRelationId,extension.objectId,0);
3357+
3358+
/*
3359+
* If get_object_address() opened the relation for us, we close it to keep
3360+
* the reference count correct - but we retain any locks acquired by
3361+
* get_object_address() until commit time, to guard against concurrent
3362+
* activity.
3363+
*/
3364+
if (relation!=NULL)
3365+
relation_close(relation,NoLock);
3366+
3367+
returnextension;
3368+
}
3369+
3370+
/*
3371+
* ExecAlterExtensionContentsRecurse
3372+
*Subroutine for ExecAlterExtensionContentsStmt
3373+
*
3374+
* Do the bare alteration of object's membership in extension,
3375+
* without permission checks. Recurse to dependent objects, if any.
3376+
*/
3377+
staticvoid
3378+
ExecAlterExtensionContentsRecurse(AlterExtensionContentsStmt*stmt,
3379+
ObjectAddressextension,
3380+
ObjectAddressobject)
3381+
{
3382+
OidoldExtension;
3383+
33503384
/*
33513385
* Check existing extension membership.
33523386
*/
@@ -3430,18 +3464,47 @@ ExecAlterExtensionContentsStmt(AlterExtensionContentsStmt *stmt,
34303464
removeExtObjInitPriv(object.objectId,object.classId);
34313465
}
34323466

3433-
InvokeObjectPostAlterHook(ExtensionRelationId,extension.objectId,0);
3434-
34353467
/*
3436-
* If get_object_address() opened the relation for us, we close it to keep
3437-
* the reference count correct - but we retain any locks acquired by
3438-
* get_object_address() until commit time, to guard against concurrent
3439-
* activity.
3468+
* Recurse to any dependent objects; currently, this includes the array
3469+
* type of a base type, the multirange type associated with a range type,
3470+
* and the rowtype of a table.
34403471
*/
3441-
if (relation!=NULL)
3442-
relation_close(relation,NoLock);
3472+
if (object.classId==TypeRelationId)
3473+
{
3474+
ObjectAddressdepobject;
34433475

3444-
returnextension;
3476+
depobject.classId=TypeRelationId;
3477+
depobject.objectSubId=0;
3478+
3479+
/* If it has an array type, update that too */
3480+
depobject.objectId=get_array_type(object.objectId);
3481+
if (OidIsValid(depobject.objectId))
3482+
ExecAlterExtensionContentsRecurse(stmt,extension,depobject);
3483+
3484+
/* If it is a range type, update the associated multirange too */
3485+
if (type_is_range(object.objectId))
3486+
{
3487+
depobject.objectId=get_range_multirange(object.objectId);
3488+
if (!OidIsValid(depobject.objectId))
3489+
ereport(ERROR,
3490+
(errcode(ERRCODE_UNDEFINED_OBJECT),
3491+
errmsg("could not find multirange type for data type %s",
3492+
format_type_be(object.objectId))));
3493+
ExecAlterExtensionContentsRecurse(stmt,extension,depobject);
3494+
}
3495+
}
3496+
if (object.classId==RelationRelationId)
3497+
{
3498+
ObjectAddressdepobject;
3499+
3500+
depobject.classId=TypeRelationId;
3501+
depobject.objectSubId=0;
3502+
3503+
/* It might not have a rowtype, but if it does, update that */
3504+
depobject.objectId=get_rel_type_id(object.objectId);
3505+
if (OidIsValid(depobject.objectId))
3506+
ExecAlterExtensionContentsRecurse(stmt,extension,depobject);
3507+
}
34453508
}
34463509

34473510
/*

‎src/include/catalog/catversion.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -57,6 +57,6 @@
5757
*/
5858

5959
/*yyyymmddN */
60-
#defineCATALOG_VERSION_NO202403041
60+
#defineCATALOG_VERSION_NO202403042
6161

6262
#endif

‎src/test/modules/test_extensions/Makefile

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@ MODULE = test_extensions
44
PGFILEDESC = "test_extensions - regression testing for EXTENSION support"
55

66
EXTENSION = test_ext1 test_ext2 test_ext3 test_ext4 test_ext5 test_ext6\
7-
test_ext7 test_ext8 test_ext_cine test_ext_cor\
7+
test_ext7 test_ext8test_ext9test_ext_cine test_ext_cor\
88
test_ext_cyclic1 test_ext_cyclic2\
99
test_ext_extschema\
1010
test_ext_evttrig\
@@ -13,6 +13,7 @@ EXTENSION = test_ext1 test_ext2 test_ext3 test_ext4 test_ext5 test_ext6 \
1313
DATA = test_ext1--1.0.sql test_ext2--1.0.sql test_ext3--1.0.sql\
1414
test_ext4--1.0.sql test_ext5--1.0.sql test_ext6--1.0.sql\
1515
test_ext7--1.0.sql test_ext7--1.0--2.0.sql test_ext8--1.0.sql\
16+
test_ext9--1.0.sql\
1617
test_ext_cine--1.0.sql test_ext_cine--1.0--1.1.sql\
1718
test_ext_cor--1.0.sql\
1819
test_ext_cyclic1--1.0.sql test_ext_cyclic2--1.0.sql\

0 commit comments

Comments
 (0)

[8]ページ先頭

©2009-2025 Movatter.jp