Add SupportRequestInlineInFrom planner support request.

This request allows a support function to replace a function call
appearing in FROM (typically a set-returning function) with an
equivalent SELECT subquery.  The subquery will then be subject
to the planner's usual optimizations, potentially allowing a much
better plan to be generated.  While the planner has long done this
automatically for simple SQL-language functions, it's now possible
for extensions to do it for functions outside that group.
Notably, this could be useful for functions that are presently
implemented in PL/pgSQL and work by generating and then EXECUTE'ing
a SQL query.

Author: Paul A Jungwirth <pj@illuminatedcomputing.com>
Reviewed-by: Tom Lane <tgl@sss.pgh.pa.us>
Discussion: https://postgr.es/m/09de6afa-c33d-4d94-a5cb-afc6cea0d2bb@illuminatedcomputing.com
This commit is contained in:
Tom Lane
2025-11-22 19:33:34 -05:00
parent c0bc9af151
commit b140c8d7a3
9 changed files with 511 additions and 171 deletions

View File

@@ -360,6 +360,40 @@ SELECT explain_mask_costs($$
SELECT * FROM generate_series(25.0, 2.0, 0.0) g(s);$$,
false, true, false, true);
--
-- Test SupportRequestInlineInFrom request
--
CREATE FUNCTION test_inline_in_from_support_func(internal)
RETURNS internal
AS :'regresslib', 'test_inline_in_from_support_func'
LANGUAGE C STRICT;
CREATE FUNCTION foo_from_bar(colname TEXT, tablename TEXT, filter TEXT)
RETURNS SETOF TEXT
LANGUAGE plpgsql
AS $function$
DECLARE
sql TEXT;
BEGIN
sql := format('SELECT %I::text FROM %I', colname, tablename);
IF filter IS NOT NULL THEN
sql := CONCAT(sql, format(' WHERE %I::text = $1', colname));
END IF;
RETURN QUERY EXECUTE sql USING filter;
END;
$function$ STABLE;
ALTER FUNCTION foo_from_bar(TEXT, TEXT, TEXT)
SUPPORT test_inline_in_from_support_func;
SELECT * FROM foo_from_bar('f1', 'text_tbl', NULL);
SELECT * FROM foo_from_bar('f1', 'text_tbl', 'doh!');
EXPLAIN (COSTS OFF) SELECT * FROM foo_from_bar('f1', 'text_tbl', NULL);
EXPLAIN (COSTS OFF) SELECT * FROM foo_from_bar('f1', 'text_tbl', 'doh!');
DROP FUNCTION foo_from_bar;
-- Test functions for control data
SELECT count(*) > 0 AS ok FROM pg_control_checkpoint();
SELECT count(*) > 0 AS ok FROM pg_control_init();