On Fri, Aug 28, 2026 at 10:29 PM Richard Guo <[email protected]> wrote: > While working on the fix for qual pushdown past grouping through a > simple CASE [1], I modeled the v2 patch's handling of CaseTestExpr on > what eval_const_expressions does. Ewan Young pointed out that v2 > mishandled the CaseTestExpr in a JSON constructor's coercion > expression, which led me to notice that eval_const_expressions has the > same bug:
I found another related but separate problem by grepping all the
places that handle CaseTestExpr.
contain_context_dependent_node_walker() knows that a CaseTestExpr is
expected under a simple CaseExpr or in the elemexpr of an
ArrayCoerceExpr, but not that a JsonConstructorExpr whose RETURNING
type needs a coercion also carries one in that coercion. So
inline_function() refuses to inline any SQL function that is passed
such a constructor as an argument. As an example, consider:
create function f(text) returns text language sql immutable
as $$ select $1 || '!' $$;
explain (verbose, costs off)
select f(json_object('a': x returning text)) from generate_series(1,1) x;
QUERY PLAN
--------------------------------------------------
Function Scan on pg_catalog.generate_series x
Output: f(JSON_OBJECT('a' : x RETURNING text))
Function Call: generate_series(1, 1)
(3 rows)
The attached 0002 teaches the walker about the coercion of a
JsonConstructorExpr. It's basically just mirroring what it already
does for ArrayCoerceExpr.
0001 is a bug fix and should be back-patched to v16 where JSON
constructor was introduced. 0002 is a missed optimization so maybe we
can leave it to master-only?
- Richard
v2-0001-Fix-const-folding-of-JSON-constructors-inside-a-s.patch
Description: Binary data
v2-0002-Don-t-let-JSON-constructor-coercions-block-SQL-fu.patch
Description: Binary data
