1

As an instant example:

A function that returns a table:

=> create or replace function testf(x integer)
     returns table(a integer, b integer)
   language sql
   as $function$
       select * from (values(1,2)) as foo(a,b)
   $function$;

Calling it so it returns a record (or whatever you call it):

=> select testf(3);
 testf
-------
 (1,2)

Calling it so it returns a table (good):

=> select * from  testf(3);
 a | b
---+---
 1 | 2

But how do I call it so the parameters come from a query?

=> select s.n, testf(s.n) from (select 3 as n union select 4) s;
 n | testf
---+-------
 3 | (1,2)
 4 | (1,2)            <-- not a table (or row with column names)


=> select * from  testf(s.n) from (select 3 as n) s;
 ERROR:  syntax error at or near "from"
 LINE 1: select * from  testf(s.n) from (select 3 as n) s;
Erwin Brandstetter
  • 605,456
  • 145
  • 1,078
  • 1,228
Sigfried
  • 2,943
  • 3
  • 31
  • 43

1 Answers1

2

Use a LATERAL subquery:

SELECT *
FROM  (VALUES (3), (4)) AS s(n)
     , testf(s.n);

The comma is short notation for CROSS JOIN LATERAL, since LATERAL is assumed automatically with set-returning functions in the FROM clause.

Related:

Community
  • 1
  • 1
Erwin Brandstetter
  • 605,456
  • 145
  • 1,078
  • 1,228