From 9540cc9f76178f71e2d4f7ca9621064281207131 Mon Sep 17 00:00:00 2001
From: Jeff Davis <jeff@j-davis.com>
Date: Wed, 18 Mar 2026 10:31:38 -0700
Subject: [PATCH v23 4/4] Add dependency entry for FDW connection function.

Missed in commit 8185bb5347.

Catalog version bump.
---
 src/backend/commands/foreigncmds.c         | 40 +++++++++++++++++++++-
 src/include/catalog/catversion.h           |  2 +-
 src/test/regress/expected/subscription.out |  9 +++++
 src/test/regress/sql/subscription.sql      |  8 +++++
 4 files changed, 57 insertions(+), 2 deletions(-)

diff --git a/src/backend/commands/foreigncmds.c b/src/backend/commands/foreigncmds.c
index 45681235782..61ee25b345d 100644
--- a/src/backend/commands/foreigncmds.c
+++ b/src/backend/commands/foreigncmds.c
@@ -707,6 +707,14 @@ CreateForeignDataWrapper(ParseState *pstate, CreateFdwStmt *stmt)
 		recordDependencyOn(&myself, &referenced, DEPENDENCY_NORMAL);
 	}
 
+	if (OidIsValid(fdwconnection))
+	{
+		referenced.classId = ProcedureRelationId;
+		referenced.objectId = fdwconnection;
+		referenced.objectSubId = 0;
+		recordDependencyOn(&myself, &referenced, DEPENDENCY_NORMAL);
+	}
+
 	recordDependencyOnOwner(ForeignDataWrapperRelationId, fdwId, ownerId);
 
 	/* dependency on extension */
@@ -814,6 +822,28 @@ AlterForeignDataWrapper(ParseState *pstate, AlterFdwStmt *stmt)
 	{
 		repl_val[Anum_pg_foreign_data_wrapper_fdwconnection - 1] = ObjectIdGetDatum(fdwconnection);
 		repl_repl[Anum_pg_foreign_data_wrapper_fdwconnection - 1] = true;
+
+		/*
+		 * If the connection function is changed, behavior of dependent
+		 * subscriptions can change.  If NO CONNECTION, dependent
+		 * subscriptions will fail.
+		 */
+		if (OidIsValid(fdwForm->fdwconnection))
+		{
+			if (OidIsValid(fdwconnection))
+				ereport(WARNING,
+						(errmsg("changing the foreign-data wrapper connection function can cause "
+								"the options for dependent objects to become invalid")));
+			else
+				ereport(WARNING,
+						(errmsg("removing the foreign-data wrapper connection function will cause "
+								"dependent subscriptions to fail")));
+		}
+	}
+	else
+	{
+		/* connection function unchanged */
+		fdwconnection = fdwForm->fdwconnection;
 	}
 
 	/*
@@ -854,7 +884,7 @@ AlterForeignDataWrapper(ParseState *pstate, AlterFdwStmt *stmt)
 	ObjectAddressSet(myself, ForeignDataWrapperRelationId, fdwId);
 
 	/* Update function dependencies if we changed them */
-	if (handler_given || validator_given)
+	if (handler_given || validator_given || connection_given)
 	{
 		ObjectAddress referenced;
 
@@ -884,6 +914,14 @@ AlterForeignDataWrapper(ParseState *pstate, AlterFdwStmt *stmt)
 			referenced.objectSubId = 0;
 			recordDependencyOn(&myself, &referenced, DEPENDENCY_NORMAL);
 		}
+
+		if (OidIsValid(fdwconnection))
+		{
+			referenced.classId = ProcedureRelationId;
+			referenced.objectId = fdwconnection;
+			referenced.objectSubId = 0;
+			recordDependencyOn(&myself, &referenced, DEPENDENCY_NORMAL);
+		}
 	}
 
 	InvokeObjectPostAlterHook(ForeignDataWrapperRelationId, fdwId, 0);
diff --git a/src/include/catalog/catversion.h b/src/include/catalog/catversion.h
index 55a8fbbd509..a4f0d02af9c 100644
--- a/src/include/catalog/catversion.h
+++ b/src/include/catalog/catversion.h
@@ -57,6 +57,6 @@
  */
 
 /*							yyyymmddN */
-#define CATALOG_VERSION_NO	202603171
+#define CATALOG_VERSION_NO	202603181
 
 #endif
diff --git a/src/test/regress/expected/subscription.out b/src/test/regress/expected/subscription.out
index f57f359127b..7e3cabdb93f 100644
--- a/src/test/regress/expected/subscription.out
+++ b/src/test/regress/expected/subscription.out
@@ -185,6 +185,15 @@ DROP SUBSCRIPTION regress_testsub6;
 SET SESSION AUTHORIZATION regress_subscription_user;
 REVOKE CREATE ON DATABASE REGRESSION FROM regress_subscription_user3;
 DROP SERVER test_server;
+-- fail, FDW is dependent
+DROP FUNCTION test_fdw_connection(oid, oid, internal);
+ERROR:  cannot drop function test_fdw_connection(oid,oid,internal) because other objects depend on it
+DETAIL:  foreign-data wrapper test_fdw depends on function test_fdw_connection(oid,oid,internal)
+HINT:  Use DROP ... CASCADE to drop the dependent objects too.
+-- warn
+ALTER FOREIGN DATA WRAPPER test_fdw NO CONNECTION;
+WARNING:  removing the foreign-data wrapper connection function will cause dependent subscriptions to fail
+DROP FUNCTION test_fdw_connection(oid, oid, internal);
 DROP FOREIGN DATA WRAPPER test_fdw;
 -- fail - invalid connection string during ALTER
 ALTER SUBSCRIPTION regress_testsub CONNECTION 'foobar';
diff --git a/src/test/regress/sql/subscription.sql b/src/test/regress/sql/subscription.sql
index a642b368183..6c3d9632e8a 100644
--- a/src/test/regress/sql/subscription.sql
+++ b/src/test/regress/sql/subscription.sql
@@ -138,6 +138,14 @@ SET SESSION AUTHORIZATION regress_subscription_user;
 REVOKE CREATE ON DATABASE REGRESSION FROM regress_subscription_user3;
 
 DROP SERVER test_server;
+
+-- fail, FDW is dependent
+DROP FUNCTION test_fdw_connection(oid, oid, internal);
+-- warn
+ALTER FOREIGN DATA WRAPPER test_fdw NO CONNECTION;
+
+DROP FUNCTION test_fdw_connection(oid, oid, internal);
+
 DROP FOREIGN DATA WRAPPER test_fdw;
 
 -- fail - invalid connection string during ALTER
-- 
2.43.0

