Как получить красиво отформатированные результаты из процедура Oracle, которая возвращает ссылочный курсор?

В MS SQL Server, если я хочу проверить результаты хранимой процедуры, я мог бы выполнить следующее в Management Studio.

--SQL SERVER WAY
exec sp_GetQuestions('OMG Ponies')

Вывод результатов панель может выглядеть следующим образом.

ID    Title                                             ViewCount   Votes 
----- ------------------------------------------------- ---------- --------
2165  Indexed View vs Indexes on Table                  491         2  
5068  SQL Server equivalent to Oracle’s NULLS FIRST     524         3 
1261  Benefits Of Using SQL Ordinal Position Notation?  377         2 

(3 row(s) affected)

Нет необходимости писать циклы или операторы PRINT.

Чтобы сделать то же самое в Oracle, я мог бы выполнить следующий анонимный блок в SQL Developer.

--ORACLE WAY
    DECLARE
        OUTPUT  MYPACKAGE.refcur_question;
        R_OUTPUT MYPACKAGE.r_question;
        USER    VARCHAR2(20);

BEGIN

  dbms_output.enable(10000000);
  USER:= 'OMG Ponies';
  recordCount := 0;



  MYPACKAGE.GETQUESTIONS(p_OUTPUT => OUTPUT, 
  p_USER=> USER, 

  ) ;




  DBMS_OUTPUT.PUT_LINE('ID |  Title | ViewCount | Votes' );

  LOOP 
    FETCH OUTPUT
    INTO R_OUTPUT;

         DBMS_OUTPUT.PUT_LINE(R_OUTPUT.QUESTIONID || '|' || R_OUTPUT.TITLE 
               '|' || R_OUTPUT.VIEWCOUNT '|' || R_OUTPUT.VOTES);
          recordCount := recordCount+1;




 EXIT WHEN OUTPUT % NOTFOUND;  
      END LOOP;
      DBMS_OUTPUT.PUT_LINE('Record Count:'||recordCount);
      CLOSE OUTPUT;


    END;

Это выводит наподобие

ID|Title|ViewCount|Votes 
2165|Indexed View vs Indexes on Table|491|2  
5068|SQL Server equivalent to Oracle’s NULLS FIRST|524|3 
1261|Benefits Of Using SQL Ordinal Position Notation?|377|2 
Record Count: 3

. Таким образом, версия SQL имеет 1 строку, а оракул - 18, а вывод уродлив. Это усугубляется, если столбцов много и / или данные числовые.

Что странно для меня, так это то, что если я напишу это утверждение в SQL Developer или Management studio ...

SELECT 
ID, 
Title, 
ViewCount, 
Votes
FROM votes where user = 'OMG Ponies'  

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

19
задан Conrad Frix 14 November 2013 в 22:29
поделиться

1 ответ

Если GetQuestions - это функция, возвращающая рефкурсор, что похоже на то, что у вас есть в версии SQL Server, то вы можете сделать что-то вроде этого:

select * from table(MyPackage.GetQuestions('OMG Ponies'));

Или, если вам это нужно в блоке PL / SQL, вы можете использовать тот же выбор в курсоре.

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

Редактировать

Хммм, я не уверен, что можно преобразовать () возвращаемый рефкурсор в пригодный для использования тип, если только вы не хотите объявить свой собственный тип (и таблицу этого типа) вне пакет. Однако вы можете сделать это, просто чтобы вывести результаты:

create package mypackage as
    function getquestions(user in varchar2) return sys_refcursor;
end mypackage;
/

create package body mypackage as
    function getquestions(user in varchar2) return sys_refcursor as
        r sys_refcursor;
    begin
        open r for
            /* Whatever your real query is */
            select 'Row 1' col1, 'Value 1' col2 from dual
            union
            select 'Row 2', 'Value 2' from dual
            union
            select 'Row 3', 'Value 3' from dual;
            return r;
    end;
end mypackage;
/

var r refcursor;
exec :r := mypackage.getquestions('OMG Ponies');
print r;

И вы можете использовать результат вызова в другой процедуре или функции; это просто добраться до него за пределами PL / SQL, что кажется немного сложным.

Отредактировано для добавления: При таком подходе, если это процедура, вы можете сделать по существу то же самое:

var r refcursor;
exec mypackage.getquestions(:r, 'OMG Ponies');
print r;
18
ответ дан 30 November 2019 в 04:52
поделиться
Другие вопросы по тегам:

Похожие вопросы: