Как получить набор результатов из хранимой процедуры PostgreSQL? - PullRequest
1 голос
/ 22 октября 2019

Я создал хранимую процедуру в PostgreSQL 11 для выполнения операции CRUD, и она отлично работает для 1. Создать 2. Обновление 3. Удалить, но пока я запускаю команду чтения, передав Condition = 4 для выбора набора результатов, я получаюошибка ниже.

Я использовал функцию PostgreSQL, чтобы получить набор результатов, он работает для меня, но мне нужно получить результат, используя хранимую процедуру PostgreSQL.

Вот мой код для хранимой процедуры:

CREATE OR REPLACE PROCEDURE public.testSpCrud(
    fnam text,
    lnam text,
    id integer,
    condition integer)
LANGUAGE 'plpgsql'

AS $BODY$
declare
    countOfDisc int; 
BEGIN
if condition=1 then

INSERT INTO public.employee(
    employeeid, lname, fname, securitylevel, employeepassword, hphonearea, hphone, cphonearea, cphone, street, city, state, zipcode, extzip, name, email, groomerid, type, commission, inactive, carrierid, notoallemployees, languageid, isdogwalker, ispetsitter, ismobilegroomer, ssma_timestamp)
    VALUES (4,  'Test', 'Test', 2, 2, 32, 32, 32, 32, 32, 32,32, 32, 32, 22, 22, 2, 2, 2, false, 223,true, 223, true, true, true, '2019-08-27');
end if;
 if condition =2 then
    delete from Employee where employeeid=id;
    end if;
     if condition =3 then
    update Employee set fname='Test' where employeeid=id;
    end if;
     if condition =4 then
         Select * from Employee;
    end if;
    END;
$BODY$;
ERROR: query has no destination for result data
HINT: If you want to discard the results of a SELECT, use PERFORM instead.
CONTEXT: PL/pgSQL function testspcrud(text,text,integer,integer) line 22 at SQL statement
SQL state: 42601

1 Ответ

2 голосов
/ 23 октября 2019

Начиная с Postgres 12, невозможно вернуть что-либо напрямую из процедуры .

Скорее всего, вы попали в широко распространенное неправильное выражение "хранимая процедура" идействительно нужно взамен function, который может возвращать значение, строку или набор в соответствии с его объявлением.

Будет работать следующим образом:

CREATE OR REPLACE FUNCTION public.testSpCrud(
    fnam text,
    lnam text,
    id integer,
    condition integer)
  RETURNS SETOF Employee LANGUAGE plpgsql AS
$func$
BEGIN
   CASE condition
   WHEN 1 THEN
      INSERT INTO public.employee(
       employeeid, lname, fname, securitylevel, employeepassword, hphonearea, hphone, cphonearea, cphone, street, city, state, zipcode, extzip, name, email, groomerid, type, commission, inactive, carrierid, notoallemployees, languageid, isdogwalker, ispetsitter, ismobilegroomer, ssma_timestamp)
       VALUES (4,  'Test', 'Test', 2, 2, 32, 32, 32, 32, 32, 32,32, 32, 32, 22, 22, 2, 2, 2, false, 223,true, 223, true, true, true, '2019-08-27');

   WHEN 2 THEN
      DELETE FROM Employee WHERE employeeid=id;

   WHEN 3 THEN
      UPDATE Employee SET fname='Test' WHERE employeeid=id;

   WHEN 4 THEN
      RETURN QUERY
      SELECT * FROM Employee;

   ELSE
      RAISE EXCEPTION 'Unexpected condition value %!', condition;
   END CASE;
END
$func$;

Упрощенный с конструкцией CASE во время нахождения, и добавлен оператор ELSE. Адаптируйте к вашим потребностям.

Вызов с:

SELECT * FROM public.testSpCrud(...);

В стороне: все имена переменных блока plpgsql видны внутри вложенных команд SQL DML. Переменная с именем id - это проблема, ожидающая своего появления. Я предлагаю более безопасное соглашение об именах и / или квалификацию таблиц всех имен столбцов в выражениях DMLОдно популярное соглашение об именах заключается в добавлении имен переменных с подчеркиванием. Например: _id.

И рассмотрим допустимые строчные идентификаторы в SQL и PL / pgSQL.

...