Received: from malur.postgresql.org ([217.196.149.56]) by arkaria.postgresql.org with esmtps (TLS1.3:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.92) (envelope-from ) id 1kTQA3-0001mi-Ja for pgsql-hackers@arkaria.postgresql.org; Fri, 16 Oct 2020 13:52:48 +0000 Received: from localhost ([127.0.0.1] helo=malur.postgresql.org) by malur.postgresql.org with esmtp (Exim 4.92) (envelope-from ) id 1kTQA0-0000KH-Bw for pgsql-hackers@arkaria.postgresql.org; Fri, 16 Oct 2020 13:52:44 +0000 Received: from makus.postgresql.org ([2001:4800:3e1:1::229]) by malur.postgresql.org with esmtps (TLS1.3:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.92) (envelope-from ) id 1kTQ9z-0000KA-5v for pgsql-hackers@lists.postgresql.org; Fri, 16 Oct 2020 13:52:44 +0000 Received: from out2-smtp.messagingengine.com ([66.111.4.26]) by makus.postgresql.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.92) (envelope-from ) id 1kTQ9t-0003yI-SK for pgsql-hackers@postgresql.org; Fri, 16 Oct 2020 13:52:42 +0000 Received: from compute2.internal (compute2.nyi.internal [10.202.2.42]) by mailout.nyi.internal (Postfix) with ESMTP id 496A45C00A6; Fri, 16 Oct 2020 09:52:36 -0400 (EDT) Received: from mailfrontend2 ([10.202.2.163]) by compute2.internal (MEProxy); Fri, 16 Oct 2020 09:52:36 -0400 DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d= messagingengine.com; h=cc:content-type:date:from:in-reply-to :message-id:mime-version:subject:to:x-me-proxy:x-me-proxy :x-me-sender:x-me-sender:x-sasl-enc; s=fm1; bh=QoOnsuunPxOAVD+Bh SpFCzeIumTjniljVF4DPMQ0/M0=; b=MUfBWVnxQe/PSO39VeGUKGaorKXLS8FBh FVobuWSnxN5AXCK8+cYZ0g2pQSbAaenqi0sJfXrbeE/4u5K2DcRjl8eb1G231DC2 Crlbxe3U14MENeFdcl0SVOHvGRfAt1em1VD8/82s9s2r5hgCN6UECZ8v5kLhvKpY 0jDqB77jiqcUsWwv1L8OUE6z1ClpWdYAID69tbrjsFW7umJtwb3Wius/nyphNahZ guh9Do5WbvASBKJN2tVzxK/vxxrPs2z2rgSXjERUC7MV6KBGUlfOGI8XmyP/nMnX 53BpRA6Ojb54agUdG/ei+E70sm2GA+f746kTuhPmpupMP8hxUhD6A== X-ME-Sender: X-ME-Proxy-Cause: gggruggvucftvghtrhhoucdtuddrgedujedrieehgdejtdcutefuodetggdotefrodftvf curfhrohhfihhlvgemucfhrghsthforghilhdpqfgfvfdpuffrtefokffrpgfnqfghnecu uegrihhlohhuthemuceftddtnecusecvtfgvtghiphhivghnthhsucdlqddutddtmdenuc fjughrpeffhffvuffkgggtuggjfgesmhdtreertdervdenucfhrhhomheptehlvhgrrhho ucfjvghrrhgvrhgruceorghlvhhhvghrrhgvsegrlhhvhhdrnhhoqdhiphdrohhrgheqne cuggftrfgrthhtvghrnhepieeghfelueduheegtdekjeehueffvddujefgteduieekjefh udefgeefiedvjeetnecukfhppeduledtrddutdeirddufeegrddutddtnecuvehluhhsth gvrhfuihiivgeptdenucfrrghrrghmpehmrghilhhfrhhomheprghlvhhhvghrrhgvsegr lhhvhhdrnhhoqdhiphdrohhrgh X-ME-Proxy: Received: from perhan.alvh.no-ip.org (h100-n190-106-134.v8.fangio.net [190.106.134.100]) by mail.messagingengine.com (Postfix) with ESMTPA id 5EF953064683; Fri, 16 Oct 2020 09:52:35 -0400 (EDT) Received: by perhan.alvh.no-ip.org (Postfix, from userid 1000) id BFCB52A14D3; Fri, 16 Oct 2020 10:52:30 -0300 (-03) Date: Fri, 16 Oct 2020 10:52:30 -0300 From: Alvaro Herrera To: Justin Pryzby Cc: pgsql-hackers@postgresql.org, Amit Langote Subject: Re: CREATE TABLE .. PARTITION OF fails to preserve tgenabled for inherited row triggers Message-ID: <20201016135230.GA23633@alvherre.pgsql> MIME-Version: 1.0 Content-Type: multipart/mixed; boundary="dDRMvlgZJXvWKvBx" Content-Disposition: inline In-Reply-To: <20200930223450.GA14848@telsasoft.com> User-Agent: Mutt/1.10.1 (2018-07-13) List-Id: List-Help: List-Subscribe: List-Post: List-Owner: List-Archive: Precedence: bulk --dDRMvlgZJXvWKvBx Content-Type: text/plain; charset=us-ascii Content-Disposition: inline On 2020-Sep-30, Justin Pryzby wrote: > postgres=# SELECT tgrelid::regclass, tgenabled FROM pg_trigger WHERE tgrelid::regclass::text IN ('t1','t2'); > tgrelid | tgenabled > ---------+----------- > t1 | D > t2 | O > (2 rows) > > I consider this a bug, Yeah. > but CreateTrigStmt doesn't have any "enabled" member > (since it's impossible to CREATE TRIGGER .. DISABLED), so I'm not sure where > the fix should be. I suggest we add a new function, as in the attached. It's important to keep the ABI of CreateTrigger unchanged, for the sake of backpatchability, but ISTM it's equally important to keep its API unchanged, because outside callers such as ProcessUtility_slow does not have to care about the new trigger's enabled state. --dDRMvlgZJXvWKvBx Content-Type: text/x-diff; charset=us-ascii Content-Disposition: attachment; filename="disable-triggers.patch" diff --git a/src/backend/commands/tablecmds.c b/src/backend/commands/tablecmds.c index 511f015a86..f20b877f68 100644 --- a/src/backend/commands/tablecmds.c +++ b/src/backend/commands/tablecmds.c @@ -16879,10 +16879,10 @@ CloneRowTriggersToPartition(Relation parent, Relation partition) trigStmt->initdeferred = trigForm->tginitdeferred; trigStmt->constrrel = NULL; /* passed separately */ - CreateTrigger(trigStmt, NULL, RelationGetRelid(partition), - trigForm->tgconstrrelid, InvalidOid, InvalidOid, - trigForm->tgfoid, trigForm->oid, qual, - false, true); + CreateTriggerFiringOn(trigStmt, NULL, RelationGetRelid(partition), + trigForm->tgconstrrelid, InvalidOid, InvalidOid, + trigForm->tgfoid, trigForm->oid, qual, + false, true, trigForm->tgenabled); MemoryContextSwitchTo(oldcxt); MemoryContextReset(perTupCxt); diff --git a/src/backend/commands/trigger.c b/src/backend/commands/trigger.c index 3b4fbdadf4..b826b3595c 100644 --- a/src/backend/commands/trigger.c +++ b/src/backend/commands/trigger.c @@ -158,6 +158,24 @@ CreateTrigger(CreateTrigStmt *stmt, const char *queryString, Oid relOid, Oid refRelOid, Oid constraintOid, Oid indexOid, Oid funcoid, Oid parentTriggerOid, Node *whenClause, bool isInternal, bool in_partition) +{ + return + CreateTriggerFiringOn(stmt, queryString, relOid, refRelOid, + constraintOid, indexOid, funcoid, + parentTriggerOid, whenClause, isInternal, + in_partition, TRIGGER_FIRES_ON_ORIGIN); +} + +/* + * Like the above; additionally the firing condition + * (always/origin/replica/disabled) can be specified. + */ +ObjectAddress +CreateTriggerFiringOn(CreateTrigStmt *stmt, const char *queryString, + Oid relOid, Oid refRelOid, Oid constraintOid, + Oid indexOid, Oid funcoid, Oid parentTriggerOid, + Node *whenClause, bool isInternal, bool in_partition, + char trigger_fires_when) { int16 tgtype; int ncolumns; @@ -800,7 +818,7 @@ CreateTrigger(CreateTrigStmt *stmt, const char *queryString, CStringGetDatum(trigname)); values[Anum_pg_trigger_tgfoid - 1] = ObjectIdGetDatum(funcoid); values[Anum_pg_trigger_tgtype - 1] = Int16GetDatum(tgtype); - values[Anum_pg_trigger_tgenabled - 1] = CharGetDatum(TRIGGER_FIRES_ON_ORIGIN); + values[Anum_pg_trigger_tgenabled - 1] = trigger_fires_when; values[Anum_pg_trigger_tgisinternal - 1] = BoolGetDatum(isInternal || in_partition); values[Anum_pg_trigger_tgconstrrelid - 1] = ObjectIdGetDatum(constrrelid); values[Anum_pg_trigger_tgconstrindid - 1] = ObjectIdGetDatum(indexOid); @@ -1130,11 +1148,11 @@ CreateTrigger(CreateTrigStmt *stmt, const char *queryString, map_partition_varattnos((List *) qual, PRS2_NEW_VARNO, childTbl, rel); - CreateTrigger(childStmt, queryString, - partdesc->oids[i], refRelOid, - InvalidOid, indexOnChild, - funcoid, trigoid, qual, - isInternal, true); + CreateTriggerFiringOn(childStmt, queryString, + partdesc->oids[i], refRelOid, + InvalidOid, indexOnChild, + funcoid, trigoid, qual, + isInternal, true, trigger_fires_when); table_close(childTbl, NoLock); diff --git a/src/include/commands/trigger.h b/src/include/commands/trigger.h index a40ddf5db5..40b8154876 100644 --- a/src/include/commands/trigger.h +++ b/src/include/commands/trigger.h @@ -162,6 +162,11 @@ extern ObjectAddress CreateTrigger(CreateTrigStmt *stmt, const char *queryString Oid relOid, Oid refRelOid, Oid constraintOid, Oid indexOid, Oid funcoid, Oid parentTriggerOid, Node *whenClause, bool isInternal, bool in_partition); +extern ObjectAddress CreateTriggerFiringOn(CreateTrigStmt *stmt, const char *queryString, + Oid relOid, Oid refRelOid, Oid constraintOid, + Oid indexOid, Oid funcoid, Oid parentTriggerOid, + Node *whenClause, bool isInternal, bool in_partition, + char trigger_fires_when); extern void RemoveTriggerById(Oid trigOid); extern Oid get_trigger_oid(Oid relid, const char *name, bool missing_ok); --dDRMvlgZJXvWKvBx--