Skip to content

Commit d4545dc

Browse files
committed
Complain if a function-in-FROM returns a set when it shouldn't.
Throw a "function protocol violation" error if a function in FROM tries to return a set though it wasn't marked proretset. Although such cases work at the moment, it doesn't seem like something we want to guarantee will keep working. Besides, there are other negative consequences of not setting the proretset flag, such as potentially bad plans. No back-patch, since if there is any third-party code violating this expectation, people wouldn't appreciate us breaking it in a minor release. Discussion: https://postgr.es/m/1636062.1615141782@sss.pgh.pa.us
1 parent fed10d4 commit d4545dc

File tree

1 file changed

+11
-1
lines changed

1 file changed

+11
-1
lines changed

src/backend/executor/execSRF.c

+11-1
Original file line numberDiff line numberDiff line change
@@ -353,11 +353,21 @@ ExecMakeTableFunctionResult(SetExprState *setexpr,
353353
*/
354354
if (rsinfo.isDone != ExprMultipleResult)
355355
break;
356+
357+
/*
358+
* Check that set-returning functions were properly declared.
359+
* (Note: for historical reasons, we don't complain if a non-SRF
360+
* returns ExprEndResult; that's treated as returning NULL.)
361+
*/
362+
if (!returnsSet)
363+
ereport(ERROR,
364+
(errcode(ERRCODE_E_R_I_E_SRF_PROTOCOL_VIOLATED),
365+
errmsg("table-function protocol for value-per-call mode was not followed")));
356366
}
357367
else if (rsinfo.returnMode == SFRM_Materialize)
358368
{
359369
/* check we're on the same page as the function author */
360-
if (!first_time || rsinfo.isDone != ExprSingleResult)
370+
if (!first_time || rsinfo.isDone != ExprSingleResult || !returnsSet)
361371
ereport(ERROR,
362372
(errcode(ERRCODE_E_R_I_E_SRF_PROTOCOL_VIOLATED),
363373
errmsg("table-function protocol for materialize mode was not followed")));

0 commit comments

Comments
 (0)