如何从另一个存储过程中调用postgresql存储过程并在查询中包含返回值

时间:2013-07-08 17:25:01

标签: postgresql stored-procedures

我有一个postgresql函数/存储过程执行以下操作: 1.调用另一个函数并将值保存到变量中。 2.使用我从第一步获得的值作为参数执行另一个sql语句。

我的问题是查询没有返回任何数据。也没有返回任何错误。 我刚接触postgresql所以我不知道最好的调试方法......但是我在第1步之后添加了一个RAISE NOTICE命令,如下所示:

SELECT INTO active_id get_widget_id(widget_desc);
RAISE NOTICE 'Active ID is:(%)', active_id;

在pgadmin3屏幕的“Messages”部分,我看到带有数据的调试消息:

注意:Active ID为:(2)

我想知道括号是否对我造成了问题 这是我试图在第2步中运行的SQL:

        SELECT d.id, d.contact_id, d.priority, cp.contact
        FROM widget_details d, contact_profile cp, contact_type ct
        WHERE d.rule_id=active_id
        AND d.active_yn = 't'
        AND cp.id=d.contact_id
        AND cp.contact_type_id=ct.id
        AND ct.name = 'email'
        Order by d.priority ASC

你会注意到在我的where子句中我引用了变量“active_id”。 我知道这个查询应该返回至少一行,因为当我运行一个直接的sql select(vs使用这个函数)并将值2替换为变量“active_id”时,我得到了我正在寻找的数据。

任何建议都将不胜感激。

感谢。

编辑1:

这是完整的功能定义:

CREATE TYPE custom_return_type AS (
    widgetnum integer,
    contactid integer,
    priority integer,
    contactdetails character varying
);

CREATE OR REPLACE FUNCTION test(widget_desc integer)
  RETURNS SETOF custom_return_type AS
$BODY$
DECLARE 
     active_id integer; 
     rec custom_return_type ;

BEGIN
SELECT INTO active_id get_widget_id(widget_desc);
    RAISE NOTICE 'Active ID is:(%)', active_id;

FOR rec IN 
    SELECT d.id, d.contact_id, d.priority, cp.contact
        FROM widget_details d, contact_profile cp, contact_type ct
        WHERE d.rule_id=active_id
        AND d.active_yn = 't'
        AND cp.id=d.contact_id
        AND cp.contact_type_id=ct.id
        AND ct.name = 'email'
        Order by d.priority ASC
    LOOP
     RETURN NEXT rec;
END LOOP;   

 END
 $BODY$

2 个答案:

答案 0 :(得分:1)

这是太复杂的几个层次(编辑:因为结果是Erwin already explained to you last time you posted the same thing)。首先使用RETURNS TABLERETURN QUERY

CREATE OR REPLACE FUNCTION test(fmfm_number integer)
RETURNS TABLE ( 
    widgetnum integer,
    contactid integer,
    priority integer,
    contactdetails character varying
) AS
$BODY$
BEGIN
    RETURN QUERY SELECT d.id, d.contact_id, d.priority, cp.contact
        FROM widget_details d, contact_profile cp, contact_type ct
        WHERE d.rule_id = get_widget_id(widget_desc)
        AND d.active_yn = 't'
        AND cp.id=d.contact_id
        AND cp.contact_type_id=ct.id
        AND ct.name = 'email'
        Order by d.priority ASC;
 END
 $BODY$ LANGUAGE plpgsql;

在这一点上,它可能很简单,可以变成一个简单的SQL函数甚至是一个视图。很难确定,因为这个函数并没有像写的那样有意义:

  • 您永远不会在任何地方使用参数fmfm_number;和
  • widget_desc永远不会被定义

所以这个功能永远不会运行。显然,您没有向我们展示真正的源代码,但某些“简化”代码与您真正遇到问题的代码不符。

答案 1 :(得分:0)

之间存在差异:
    选择INTO ...
[http://www.postgresql.org/docs/current/interactive/sql-selectinto.html]

    SELECT select_expressions INTO [STRICT] target FROM ...;
[http://www.postgresql.org/docs/current/interactive/plpgsql-statements.html#PLPGSQL-STATEMENTS-SQL-ONEROW]

我想你想要:
    SELECT get_widget_id(widget_desc)INTO active_id;