Re: Generated column is not updated (Postgres 13)

From: Tom Lane <tgl(at)sss(dot)pgh(dot)pa(dot)us>
To: Vitaly Ustinov <vitaly(at)ustinov(dot)ca>
Cc: pgsql-bugs(at)lists(dot)postgresql(dot)org, Peter Eisentraut <peter(dot)eisentraut(at)enterprisedb(dot)com>
Subject: Re: Generated column is not updated (Postgres 13)
Date: 2021-05-19 22:03:21
Message-ID: 3513055.1621461801@sss.pgh.pa.us
Views: Raw Message | Whole Thread | Download mbox | Resend email
Thread:
Lists: pgsql-bugs

Vitaly Ustinov <vitaly(at)ustinov(dot)ca> writes:
> I would like to report the following:
> - a generated column is never updated if you pass the whole record to a
> stored procedure (an immutable function);

TBH, I think that this is insane and needs to be forbidden. What value
are you expecting that the function would see in the column of the
whole-row var that corresponds to the generated column? It surely
cannot be passed the value that it hasn't computed yet.

You could perhaps argue that it'd be okay to pass NULL. The problem
with that, though, is that it'd violate the NOT NULL constraint that
exists for the generated column. Quite aside from any confusion that
ensues at the user level, I'm afraid that that could result in C code
crashes --- there are, for example, places in tuple deforming that
assume that NOT NULL constraints are truthful.

Anyway, I tried your test case on a debug build and observed assertion
failures, which I traced to ATRewriteTable not being careful enough
to zero out the whole tuple each time through. Conceivably we could
fix that as per the attached quick hack. However, I think we ought
to disallow the case instead. I observe that we already disallow
generated columns depending on each other:

regression=# create table foo (f1 int);
CREATE TABLE
regression=# alter table foo add f2 int generated always as (f1+1) stored;
ALTER TABLE
regression=# alter table foo add f3 int generated always as (f2+1) stored;
ERROR: cannot use generated column "f2" in column generation expression
DETAIL: A generated column cannot reference another generated column.

But a whole-row var violates this concept completely: it makes the
generated column depend, not only on every other column, but on itself
too. Also, even if you don't mind null-for-not-yet-computed-value,
that would expose the computation order of the generated columns.

regards, tom lane

Attachment Content-Type Size
hack-to-stop-crash-with-self-referential-generated-column.patch text/x-diff 2.4 KB

In response to

Responses

Browse pgsql-bugs by date

  From Date Subject
Next Message Devrim Gündüz 2021-05-19 23:21:44 Re: BUG #17016: Cannot sync pgdg-common repo with reposync due to failed signature check
Previous Message Vitaly Ustinov 2021-05-19 19:18:03 Generated column is not updated (Postgres 13)