Re: delta relations in AFTER triggers

From: Noah Misch <noah(at)leadboat(dot)com>
To: Kevin Grittner <kgrittn(at)gmail(dot)com>
Cc: Neha Sharma <neha(dot)sharma(at)enterprisedb(dot)com>, Thomas Munro <thomas(dot)munro(at)enterprisedb(dot)com>, Prabhat Sahu <prabhat(dot)sahu(at)enterprisedb(dot)com>, Tom Lane <tgl(at)sss(dot)pgh(dot)pa(dot)us>, Robert Haas <robertmhaas(at)gmail(dot)com>, Haribabu Kommi <kommi(dot)haribabu(at)gmail(dot)com>, Jim Nasby <Jim(dot)Nasby(at)bluetreble(dot)com>, Craig Ringer <craig(at)2ndquadrant(dot)com>, Michael Paquier <michael(dot)paquier(at)gmail(dot)com>, David Fetter <david(at)fetter(dot)org>, Kevin Grittner <kgrittn(at)ymail(dot)com>, Amit Khandekar <amit(dot)khandekar(at)enterprisedb(dot)com>, Alvaro Herrera <alvherre(at)2ndquadrant(dot)com>, Pg Hackers <pgsql-hackers(at)postgresql(dot)org>, Corey Huinker <corey(dot)huinker(at)gmail(dot)com>
Subject: Re: delta relations in AFTER triggers
Date: 2017-05-06 05:34:46
Message-ID: 20170506053446.GF843225@rfd.leadboat.com
Views: Raw Message | Whole Thread | Download mbox | Resend email
Thread:
Lists: pgsql-hackers

On Fri, May 05, 2017 at 08:23:33AM +1200, Thomas Munro wrote:
> On Fri, May 5, 2017 at 12:39 AM, Neha Sharma
> <neha(dot)sharma(at)enterprisedb(dot)com> wrote:
> > While testing the feature we encountered one more crash,below is the
> > scenario to reproduce.
> >
> > create table t1 ( a int);
> > create table t2 ( a int);
> > insert into t1 values (11),(12),(13);
> >
> > create or replace function my_trig() returns trigger
> > language plpgsql as $my_trig$
> > begin
> > insert into t2(select a from new_table);
> > RETURN NEW;
> > end;
> > $my_trig$;
> >
> > create trigger my_trigger
> > after truncate or update on t1
> > referencing new table as new_table old table as oldtab
> > for each statement
> > execute procedure my_trig();
> >
> > truncate t1;
> > server closed the connection unexpectedly
> > This probably means the server terminated abnormally
> > before or while processing the request.
> > The connection to the server was lost. Attempting reset: Failed.
>
> Thanks. Reproduced here. The stack looks like this:
>
> frame #3: 0x0000000103e5e8b0
> postgres`ExceptionalCondition(conditionName="!((((((trigdata->tg_event)
> & 0x00000003) == 0x00000000) || (((trigdata->tg_event) & 0x00000003)
> == 0x00000002) || (((trigdata->tg_event) & 0x00000003) == 0x00000001))
> && (((trigdata->tg_event) & 0x00000018) == 0x00000000) &&
> !(trigdata->tg_event & 0x00000020) && !(trigdata->tg_event &
> 0x00000040)) || (trigdata->tg_oldtable == ((void*)0) &&
> trigdata->tg_newtable == ((void*)0)))", errorType="FailedAssertion",
> fileName="trigger.c", lineNumber=2045) + 128 at assert.c:54
> frame #4: 0x0000000103a6f542
> postgres`ExecCallTriggerFunc(trigdata=0x00007fff5c40bad0, tgindx=0,
> finfo=0x00007fd8ba0817b8, instr=0x0000000000000000,
> per_tuple_context=0x00007fd8b906f928) + 258 at trigger.c:2039
> frame #5: 0x0000000103a754ed
> postgres`AfterTriggerExecute(event=0x00007fd8ba092460,
> rel=0x00000001043fd9c0, trigdesc=0x00007fd8ba068758,
> finfo=0x00007fd8ba0817b8, instr=0x0000000000000000,
> per_tuple_context=0x00007fd8b906f928,
> trig_tuple_slot1=0x0000000000000000,
> trig_tuple_slot2=0x0000000000000000) + 1469 at trigger.c:3860
> frame #6: 0x0000000103a73080
> postgres`afterTriggerInvokeEvents(events=0x00007fd8ba07fb00,
> firing_id=1, estate=0x00007fd8ba090440, delete_ok='\x01') + 592 at
> trigger.c:4051
> frame #7: 0x0000000103a72b7b
> postgres`AfterTriggerEndQuery(estate=0x00007fd8ba090440) + 203 at
> trigger.c:4227
> frame #8: 0x0000000103a498aa
> postgres`ExecuteTruncate(stmt=0x00007fd8ba059f40) + 2026 at
> tablecmds.c:1485
>
> There's an assertion that it's (one of INSERT, UPDATE, DELETE, an
> AFTER trigger, not deferred) *or* there are no transition tables.
> Here it's TRUNCATE and there are transition tables, so it fails:
>
> /*
> * Protect against code paths that may fail to initialize transition table
> * info.
> */
> Assert(((TRIGGER_FIRED_BY_INSERT(trigdata->tg_event) ||
> TRIGGER_FIRED_BY_UPDATE(trigdata->tg_event) ||
> TRIGGER_FIRED_BY_DELETE(trigdata->tg_event)) &&
> TRIGGER_FIRED_AFTER(trigdata->tg_event) &&
> !(trigdata->tg_event & AFTER_TRIGGER_DEFERRABLE) &&
> !(trigdata->tg_event & AFTER_TRIGGER_INITDEFERRED)) ||
> (trigdata->tg_oldtable == NULL && trigdata->tg_newtable == NULL));
>
>
> We can't possibly support transition tables on TRUNCATE (the whole
> point of TRUNCATE is not to inspect all the rows so we can't collect
> them), and we already reject ROW triggers on TRUNCATE, so we should
> reject transition tables on STATEMENT triggers for TRUNCATE at
> creation time too. See attached. Thoughts?

[Action required within three days. This is a generic notification.]

The above-described topic is currently a PostgreSQL 10 open item. Kevin,
since you committed the patch believed to have created it, you own this open
item. If some other commit is more relevant or if this does not belong as a
v10 open item, please let us know. Otherwise, please observe the policy on
open item ownership[1] and send a status update within three calendar days of
this message. Include a date for your subsequent status update. Testers may
discover new open items at any time, and I want to plan to get them all fixed
well in advance of shipping v10. Consequently, I will appreciate your efforts
toward speedy resolution. Thanks.

[1] https://www.postgresql.org/message-id/20170404140717.GA2675809%40tornado.leadboat.com

In response to

Responses

Browse pgsql-hackers by date

  From Date Subject
Next Message Noah Misch 2017-05-06 05:48:23 Re: Should pg_current_wal_location() become pg_current_wal_lsn()
Previous Message Noah Misch 2017-05-06 05:33:24 Re: delta relations in AFTER triggers