From b09d4a1df09208efa7bdf8c4513d6f330d091b6a Mon Sep 17 00:00:00 2001 From: totaj Date: Tue, 11 Jul 2023 10:51:10 +0800 Subject: [PATCH] Fix drop package body. --- src/common/backend/catalog/gs_package.cpp | 24 ++++++++++++++++++- src/common/backend/catalog/objectaddress.cpp | 2 +- .../optimizer/commands/functioncmds.cpp | 1 + .../optimizer/commands/packagecmds.cpp | 2 +- src/include/catalog/gs_package.h | 2 +- .../regress/expected/plpgsql_override_out.out | 7 ++++++ src/test/regress/sql/plpgsql_override_out.sql | 4 ++++ 7 files changed, 38 insertions(+), 4 deletions(-) mode change 100644 => 100755 src/common/backend/catalog/gs_package.cpp diff --git a/src/common/backend/catalog/gs_package.cpp b/src/common/backend/catalog/gs_package.cpp old mode 100644 new mode 100755 index 553066b9f8..7186bd80c7 --- a/src/common/backend/catalog/gs_package.cpp +++ b/src/common/backend/catalog/gs_package.cpp @@ -176,7 +176,7 @@ bool IsExistPackageName(const char* pkgname) return false; } -Oid PackageNameListGetOid(List* pkgnameList, bool missing_ok) +Oid PackageNameListGetOid(List* pkgnameList, bool missing_ok, bool isPkgBody) { Oid pkgOid = InvalidOid; char* schemaname = NULL; @@ -196,6 +196,28 @@ Oid PackageNameListGetOid(List* pkgnameList, bool missing_ok) } else { pkgOid = PackageNameGetOid(pkgname); } + if (isPkgBody && OidIsValid(pkgOid)) { + HeapTuple tuple = SearchSysCache1(PACKAGEOID, ObjectIdGetDatum(pkgOid)); + if (!HeapTupleIsValid(tuple)) { + ereport(ERROR, + (errmodule(MOD_PLSQL), errcode(ERRCODE_CACHE_LOOKUP_FAILED), + errmsg("cache lookup failed for package %u", pkgOid), + errdetail("cache lookup failed"), + errcause("System error"), + erraction("rebuild package"))); + } + bool isNull = false; + (void)SysCacheGetAttr(PACKAGEOID, tuple, Anum_gs_package_pkgbodydeclsrc, &isNull); + if (isNull && !missing_ok) { + ereport(ERROR, + (errcode(ERRCODE_UNDEFINED_PACKAGE), + errmsg("package body %s does not exist", NameListToString(pkgnameList)))); + } else if (isNull && missing_ok) { + ReleaseSysCache(tuple); + return InvalidOid; + } + ReleaseSysCache(tuple); + } if (!OidIsValid(pkgOid) && !missing_ok) { ereport(ERROR, (errcode(ERRCODE_UNDEFINED_PACKAGE), diff --git a/src/common/backend/catalog/objectaddress.cpp b/src/common/backend/catalog/objectaddress.cpp index d5200fb6c0..dc4bc41ada 100644 --- a/src/common/backend/catalog/objectaddress.cpp +++ b/src/common/backend/catalog/objectaddress.cpp @@ -835,7 +835,7 @@ ObjectAddress get_object_address( break; case OBJECT_PACKAGE_BODY: address.classId = PackageRelationId; - address.objectId = PackageNameListGetOid(objname, missing_ok); + address.objectId = PackageNameListGetOid(objname, missing_ok, true); address.objectSubId = (int32)address.objectId; /* same as objectId for package body */ break; case OBJECT_OPERATOR: diff --git a/src/gausskernel/optimizer/commands/functioncmds.cpp b/src/gausskernel/optimizer/commands/functioncmds.cpp index 088e1711c3..2e87617a7e 100644 --- a/src/gausskernel/optimizer/commands/functioncmds.cpp +++ b/src/gausskernel/optimizer/commands/functioncmds.cpp @@ -1673,6 +1673,7 @@ void RemovePackageById(Oid pkgOid, bool isBody) HeapTuple newtup = heap_modify_tuple(pkgtup, RelationGetDescr(relation), values, nulls, replaces); DropErrorByOid(PLPGSQL_PACKAGE_BODY, pkgOid); simple_heap_update(relation, &newtup->t_self, newtup); + CatalogUpdateIndexes(relation, newtup); } ReleaseSysCache(pkgtup); diff --git a/src/gausskernel/optimizer/commands/packagecmds.cpp b/src/gausskernel/optimizer/commands/packagecmds.cpp index e5825ffbde..b2d6c63ec2 100644 --- a/src/gausskernel/optimizer/commands/packagecmds.cpp +++ b/src/gausskernel/optimizer/commands/packagecmds.cpp @@ -237,7 +237,7 @@ ObjectAddress AlterPackageOwner(List* name, Oid newOwnerId) ereport(ERROR, (errcode(ERRCODE_FEATURE_NOT_SUPPORTED), errmsg("package not supported in distributed database"))); #endif - Oid pkgOid = PackageNameListGetOid(name, false); + Oid pkgOid = PackageNameListGetOid(name, false, false); Relation rel; HeapTuple tup; ObjectAddress address; diff --git a/src/include/catalog/gs_package.h b/src/include/catalog/gs_package.h index 2441a1a3e7..94b94c6bc2 100644 --- a/src/include/catalog/gs_package.h +++ b/src/include/catalog/gs_package.h @@ -48,7 +48,7 @@ extern Oid SysynonymPkgNameGetOid(const char* pkgname, Oid namespaceId); extern Oid saveCallFromPkgOid(Oid pkgOid); extern void restoreCallFromPkgOid(Oid pkgOid); extern NameData* GetPackageName(Oid packageOid); -extern Oid PackageNameListGetOid(List* pkgnameList, bool missing_ok=false); +extern Oid PackageNameListGetOid(List* pkgnameList, bool missing_ok=false, bool isPkgBody = false); extern Oid GetPackageNamespace(Oid packageOid); extern bool IsExistPackageName(const char* pkgname); extern void BuildSessionPackageRuntimeForAutoSession(uint64 sessionId, uint64 parentSessionId, diff --git a/src/test/regress/expected/plpgsql_override_out.out b/src/test/regress/expected/plpgsql_override_out.out index 2b2bcf4ec9..0a71ab4be0 100644 --- a/src/test/regress/expected/plpgsql_override_out.out +++ b/src/test/regress/expected/plpgsql_override_out.out @@ -1005,6 +1005,13 @@ end; ERROR: Named argument "b" can not be a const CONTEXT: compilation of PL/pgSQL function "inline_code_block" near line 4 set plsql_compile_check_options=''; +drop package body if exists pck1; +drop package body pck1; +ERROR: package body pck1 does not exist +drop package body pck1; +ERROR: package body pck1 does not exist +drop package body if exists pck1; +NOTICE: package pck1() does not exist, skipping drop package if exists pck1; NOTICE: drop cascades to 2 other objects --?.* diff --git a/src/test/regress/sql/plpgsql_override_out.sql b/src/test/regress/sql/plpgsql_override_out.sql index 0073d6c986..096ce1f162 100644 --- a/src/test/regress/sql/plpgsql_override_out.sql +++ b/src/test/regress/sql/plpgsql_override_out.sql @@ -697,5 +697,9 @@ end; / set plsql_compile_check_options=''; +drop package body if exists pck1; +drop package body pck1; +drop package body pck1; +drop package body if exists pck1; drop package if exists pck1; drop schema if exists plpgsql_override_out cascade; -- Gitee