PostgreSQL 游标错误

标签 postgresql cursor plpgsql

我有代码:

 DECLARE 
      cliente_cursor CURSOR FOR SELECT * FROM cliente;
      cliente cliente.id_clie%TYPE;
      nom cliente.nom_clie%TYPE;  
    BEGIN
      OPEN cliente_cursor;
      FETCH cliente_cursor INTO cliente, nom;

但是我无法运行它。出现以下错误:

ERROR: syntax error at or near "cliente"
LINE 3: cliente cliente.id_clie% TYPE;
        ^

我有表“cliente”,其中有:

Table cliente

我想创建一个仅显示列内容的游标:上一个表的 id_clie、nom_clie。

我也用过:

create or replace function facturas_cliente()
  returns table (a int, b character varying(40))
  language plpgsql as $$
declare 
  x cliente%rowtype ;
  cliente_cursor cursor for select id_clie, nom_clie from cliente 
  order by id_clie;
begin
  for x in cliente_cursor loop
    return next x;
  end loop;
end $$;

但是我得到了错误:

ERROR: RETURN NEXT can not have parameters in a function with OUT parameters
LINE 9: return next x;
                    ^

我做错了什么?

最佳答案

第一期很奇怪。我在 PostgreSQL 9.5 上测试过(但相同的代码应该适用于 9.2 和更新版本):

CREATE TABLE cliente(id_clie int, tel_clie varchar(15), dir_clie varchar(15));

DO $$
DECLARE
  cliente_cursor CURSOR FOR SELECT * FROM cliente;
  cliente cliente.id_clie%TYPE;
  tel cliente.tel_clie%TYPE;
BEGIN
  OPEN cliente_cursor;
END;
$$;

而且它没有任何问题。看起来像是输入错误。

第二个问题很明确。当函数有一个 OUT 变量或声明为 TABLE 函数时,RETURN NEXT 必须没有表达式。返回的复合值基于 OUT 变量的实际上下文(TABLE 子句中声明的列也是 OUT 变量)。您的代码应该是:

create or replace function facturas_cliente() 
returns table (a int, b character varying(40))
language plpgsql as $$
declare 
  cliente_cursor cursor for select id_clie, nom_clie 
                            from cliente 
                            order by id_clie;
  r record;
begin
  for r in cliente_cursor -- a,b ~ OUT var declared in TABLE() clause
  loop
    a := r.id_clie; b := r.nom_clie; 
    return next;  -- not: return next x;
  end loop;
end $$;

这段代码可以通过两种方式在 PL/pgSQL 中减少:

  1. 使用 SQL 函数

    create or replace function facturas_cliente() 
    returns table (a int, b character varying(40))
    language sql as $$
      select id_clie, nom_clie from cliente order by id_clie;
    $$ language plpgsql;
    
  2. 在 plpgsql 中使用 RETURN QUERY 语句:

    create or replace function facturas_cliente() 
    returns table (a int, b character varying(40))
    language sql as $$
    BEGIN
       RETURN QUERY SELECT id_clie, nom_clie 
                    FROM cliente 
                    ORDER BY id_clie;
       RETURN;
    END;
    $$ language plpgsql;
    

注意:如果您在一些复杂的查询中使用这些函数,那么这些函数可能会阻塞 SQL 优化器。我个人不喜欢它。请改用 View 。它可以按您的需要工作,并且没有优化风险。

CREATE VIEW facturas_cliente
   AS SELECT id_clie, nom_clie 
      FROM cliente 
      ORDER BY id_clie;

关于PostgreSQL 游标错误,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/28007422/

相关文章:

postgresql - 截断 Postgres 数据库中的所有表

sql - plpgsql cte parameterizing with array 导致错误消息

database - 在 postgresql 9.5 中安装 Orafce

android - 无法从数据库中获取数据

android - 获取 java.lang.IllegalStateException : attempt to re-open an already-closed object: when using cursor in Android

Javascript - 在光标下显示图像

function - 尝试编写PostgreSQL 9.0函数

ruby-on-rails - Rails - PG::数据类型不匹配:错误

sql - rails-5 activerecord postgresql-9.6 enable_neSTLoop 用于单个 sql 查询

postgresql - Postgres 中的 Go 和 IN 子句