> On 26 May 2017 at 23:05, Peter Eisentraut <
peter.eisentr...@2ndquadrant.com> wrote:
>
> > On 5/25/17 19:16, Petr Jelinek wrote:
> >> The reported error is just one of many errors that can happen when DROP
> >> SUBSCRIPTION tries to drop the slot (doens't exist, still active, no
> >> permission, etc.).  We don't want to give the hint that is effectively
> >> "just forget about the slot then" for all of them.  So we would need
> >> some way to distinguish "you can't do this right now" from "this would
> >> never work" (400 vs 500 errors).
> >>
> > This specific error returns ERRCODE_UNDEFINED_OBJECT error code so we
> > could check for it and offer hint only for this case.
>
> We would have to extend the walreceiver interface a little to pass that
> through, but it seems doable.

Just to make it clear for me. If I understand correctly, it should be more
or
less easy to extend it in that way, something like in the attached patch.
Or am I missing something?
diff --git a/src/backend/commands/subscriptioncmds.c b/src/backend/commands/subscriptioncmds.c
index 86eb31d..9f7d73c 100644
--- a/src/backend/commands/subscriptioncmds.c
+++ b/src/backend/commands/subscriptioncmds.c
@@ -941,10 +941,20 @@ DropSubscription(DropSubscriptionStmt *stmt, bool isTopLevel)
 		res = walrcv_exec(wrconn, cmd.data, 0, NULL);
 
 		if (res->status != WALRCV_OK_COMMAND)
-			ereport(ERROR,
-			(errmsg("could not drop the replication slot \"%s\" on publisher",
-					slotname),
-			 errdetail("The error was: %s", res->err)));
+		{
+			if (res->errcode == ERRCODE_UNDEFINED_OBJECT)
+				ereport(ERROR,
+				(errmsg("could not drop the replication slot \"%s\" on publisher",
+						slotname),
+				 errdetail("The error was: %s", res->err),
+				 errhint("Use ALTER SUBSCRIPTION ... SET (slot_name = NONE) "
+						 "to disassociate the subscription from the slot.")));
+			else
+				ereport(ERROR,
+				(errmsg("could not drop the replication slot \"%s\" on publisher",
+						slotname),
+				 errdetail("The error was: %s", res->err)));
+		}
 		else
 			ereport(NOTICE,
 					(errmsg("dropped replication slot \"%s\" on publisher",
diff --git a/src/backend/replication/libpqwalreceiver/libpqwalreceiver.c b/src/backend/replication/libpqwalreceiver/libpqwalreceiver.c
index ebe9c91..1caa051 100644
--- a/src/backend/replication/libpqwalreceiver/libpqwalreceiver.c
+++ b/src/backend/replication/libpqwalreceiver/libpqwalreceiver.c
@@ -873,6 +873,7 @@ libpqrcv_exec(WalReceiverConn *conn, const char *query,
 {
 	PGresult   *pgres = NULL;
 	WalRcvExecResult *walres = palloc0(sizeof(WalRcvExecResult));
+	const char *errorcode = NULL;
 
 	if (MyDatabaseId == InvalidOid)
 		ereport(ERROR,
@@ -915,6 +916,9 @@ libpqrcv_exec(WalReceiverConn *conn, const char *query,
 		case PGRES_FATAL_ERROR:
 		case PGRES_BAD_RESPONSE:
 			walres->status = WALRCV_ERROR;
+			errorcode = PQresultErrorField(pgres, PG_DIAG_SQLSTATE);
+			walres->errcode = MAKE_SQLSTATE(errorcode[0], errorcode[1], errorcode[2],
+											errorcode[3], errorcode[4]);
 			walres->err = pchomp(PQerrorMessage(conn->streamConn));
 			break;
 	}
diff --git a/src/include/replication/walreceiver.h b/src/include/replication/walreceiver.h
index 31d090c..b0582af 100644
--- a/src/include/replication/walreceiver.h
+++ b/src/include/replication/walreceiver.h
@@ -186,6 +186,7 @@ typedef struct WalRcvExecResult
 {
 	WalRcvExecStatus status;
 	char	   *err;
+	int			errcode;
 	Tuplestorestate *tuplestore;
 	TupleDesc	tupledesc;
 } WalRcvExecResult;
-- 
Sent via pgsql-hackers mailing list (pgsql-hackers@postgresql.org)
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers

Reply via email to