From: | Peter Eisentraut <peter(dot)eisentraut(at)2ndquadrant(dot)com> |
---|---|
To: | Michael Paquier <michael(at)paquier(dot)xyz> |
Cc: | Tom Lane <tgl(at)sss(dot)pgh(dot)pa(dot)us>, dnsl48(at)gmail(dot)com, pgsql-bugs(at)lists(dot)postgresql(dot)org |
Subject: | Re: BUG #15631: Generated as identity field in a temporary table with on commit drop corrupts system catalogs |
Date: | 2019-03-13 09:28:11 |
Message-ID: | d58c7b32-1ef5-a029-a852-4665d2897780@2ndquadrant.com |
Views: | Raw Message | Whole Thread | Download mbox | Resend email |
Thread: | |
Lists: | pgsql-bugs |
On 2019-03-12 04:46, Michael Paquier wrote:
> I can reproduce the issue on a v10 server, for example:
> =# create temporary table foo ( bar int generated by default as identity ) on
> commit drop;
> CREATE TABLE
> =# \q
> $ psql
> =# create temporary table a (b varchar);
> ERROR: XX000: could not open relation with OID 16389
I've been trying to understand why the equivalent case with serial does
not fail even though the code is mostly the same, that is,
create temporary table foo ( bar serial ) on commit drop;
It turns out that there is some funny business going on that has only
been invisible so far.
If you run the above command with serial, the sequence is not temporary
and is not dropped. After the table is dropped (on commit), you still
have stale dependency entries lying around (start from empty instance to
get matching OIDs):
╔═════════╤═══════╤══════════╤════════════╤══════════╤═════════════╤═════════╗
║ classid │ objid │ objsubid │ refclassid │ refobjid │ refobjsubid │
deptype ║
╠═════════╪═══════╪══════════╪════════════╪══════════╪═════════════╪═════════╣
║ 1259 │ 16386 │ 0 │ 2615 │ 16384 │ 0 │ n
║
║ 1259 │ 16386 │ 0 │ 1259 │ 16388 │ 1 │ a
║
╚═════════╧═══════╧══════════╧════════════╧══════════╧═════════════╧═════════╝
(These are sequence -> namespace and sequence -> column.)
You can see that the catalog is faulty at this point by running
select pg_describe_object(refclassid, refobjid, refobjsubid) from pg_depend;
This is all eventually cleaned up because the sequence is in the pg_temp
schema and so will be cleaned up with the schema.
If you run the command with the identity syntax, you get almost the same
stale dependency entries:
╔═════════╤═══════╤══════════╤════════════╤══════════╤═════════════╤═════════╗
║ classid │ objid │ objsubid │ refclassid │ refobjid │ refobjsubid │
deptype ║
╠═════════╪═══════╪══════════╪════════════╪══════════╪═════════════╪═════════╣
║ 1259 │ 16386 │ 0 │ 2615 │ 16384 │ 0 │ n
║
║ 1259 │ 16386 │ 0 │ 1259 │ 16388 │ 1 │ i
║
╚═════════╧═══════╧══════════╧════════════╧══════════╧═════════════╧═════════╝
It's only because of the different deptype that something chokes when it
tries to clean up the temp schema.
Adding a CommandCounterIncrement() somewhere does fix all this. I was
thinking another option for placing this call would be in
ProcessUtilitySlow():
/* Need CCI between commands */
- if (lnext(l) != NULL)
CommandCounterIncrement();
I think we should also make the implicitly created sequence temporary.
Even though the permanent sequence is cleaned up properly, we should
avoid having those sequences write to the WAL.
--
Peter Eisentraut http://www.2ndQuadrant.com/
PostgreSQL Development, 24x7 Support, Remote DBA, Training & Services
From | Date | Subject | |
---|---|---|---|
Next Message | PG Bug reporting form | 2019-03-13 10:05:09 | BUG #15692: infinity loop |
Previous Message | Michael Paquier | 2019-03-13 08:08:15 | Re: pg_rewind : feature to rewind promoted standby is broken! |