Throw a more on-point error for functions depending on columns.

ALTER COLUMN TYPE wasn't expecting to find any pg_proc objects
depending on the column whose type is to be altered.  That indeed
wasn't possible when this code was written, but it is possible
since we introduced new-style SQL function bodies.

It's about as difficult to fix this case as it is to fix dependent
views, and we've been punting on those for years, so I don't feel
too awful about punting for functions too.  (I sure wouldn't risk
back-patching such code.)  So just throw a more user-facing error.
Also, adjust some of the existing comments to reflect that these
are all pretty much the same issue.

(This patch also fixes it so we will tolerate finding such a
dependency during ALTER COLUMN SET EXPRESSION; in that, we need
not do anything to the function, so no error is wanted.  That
problem is new in HEAD.)

Per bug #18449 from Alexander Lakhin.  Back-patch to v14 where
we added new-style SQL functions.

Discussion: https://postgr.es/m/18449-f8248467aaa294d5@postgresql.org
This commit is contained in:
Tom Lane 2024-04-28 14:34:21 -04:00
parent 3752e3d210
commit b19255ca66
1 changed files with 25 additions and 5 deletions

View File

@ -12731,8 +12731,29 @@ ATExecAlterColumnType(AlteredTableInfo *tab, Relation rel,
RememberConstraintForRebuilding(foundObject.objectId, tab);
break;
case OCLASS_PROC:
/*
* A new-style SQL function can depend on a column, if that
* column is referenced in the parsed function body. Ideally
* we'd automatically update the function by deparsing and
* reparsing it, but that's risky and might well fail anyhow.
* FIXME someday.
*/
ereport(ERROR,
(errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
errmsg("cannot alter type of a column used by a function or procedure"),
errdetail("%s depends on column \"%s\"",
getObjectDescription(&foundObject, false),
colName)));
break;
case OCLASS_REWRITE:
/* XXX someday see if we can cope with revising views */
/*
* View/rule bodies have pretty much the same issues as
* function bodies. FIXME someday.
*/
ereport(ERROR,
(errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
errmsg("cannot alter type of a column used by a view or rule"),
@ -12748,9 +12769,9 @@ ATExecAlterColumnType(AlteredTableInfo *tab, Relation rel,
* specified as an update target, or because the column is
* used in the trigger's WHEN condition. The first case would
* not require any extra work, but the second case would
* require updating the WHEN expression, which will take a
* significant amount of new code. Since we can't easily tell
* which case applies, we punt for both. FIXME someday.
* require updating the WHEN expression, which has the same
* issues as above. Since we can't easily tell which case
* applies, we punt for both. FIXME someday.
*/
ereport(ERROR,
(errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
@ -12822,7 +12843,6 @@ ATExecAlterColumnType(AlteredTableInfo *tab, Relation rel,
RememberStatisticsForRebuilding(foundObject.objectId, tab);
break;
case OCLASS_PROC:
case OCLASS_TYPE:
case OCLASS_CAST:
case OCLASS_COLLATION: