Sunday, September 2, 2012

Pipeline Functions - PLS-00653

Breaking large chunks into smaller pieces, can run in parallel has got one word in PLSQL/SQL it is Pipeline. 

     The pipeline functions heavily reduces the strain on memory and developers can leverage this functions to convert PLSQL functions into row source operations.

Lets see one simple example with Pipeline Function, 


SQL> 
SQL> create table tbl_pipeline as
  2  select rownum as ACCOUNT_NBR,
  3         'A' as GROUP_IND,
  4         'B' as INCONSISTENT_PRICE
  5  from dual connect by level < 10
  6  /

Table created.

SQL> CREATE or REPLACE PACKAGE pkg_pipeline is
  2  
  3  TYPE t_objects_row IS record(ACCOUNT_NBR  NUMBER ,GROUP_IND CHAR(1),INCONSISTENT_PRICE VARCHAR2(1));
  4  TYPE t_objects_tab IS TABLE OF t_objects_row;
  5  FUNCTION  F1 return t_objects_tab PIPELINED;
  6  end pkg_pipeline;
  7  /

Package created.

SQL> CREATE or REPLACE PACKAGE BODY pkg_pipeline is
  2  FUNCTION  F1 RETURN t_objects_tab  PIPELINED
  3    IS
  4      l_row      t_objects_row;
  5  
  6  
  7  Cursor C1 is
  8  SELECT
  9   ACCOUNT_NBR,
 10   GROUP_IND,
 11   INCONSISTENT_PRICE
 12  FROM tbl_pipeline
 13  WHERE ROWNUM < 2;
 14  
 15  BEGIN
 16  FOR c1_rec  in 1..10
 17  LOOP
 18     Open C1;
 19     LOOP
 20      FETCH C1 INTO
 21          l_row.ACCOUNT_NBR,
 22          l_row.GROUP_IND,
 23          l_row.INCONSISTENT_PRICE;
 24      EXIT WHEN C1%NOTFOUND;
 25      PIPE ROW (l_row);
 26     END LOOP;
 27     Close C1;
 28  END LOOP;
 29  RETURN;
 30  EXCEPTION
 31    WHEN OTHERS
 32      THEN
 33  
 34          raise_application_error(-20001,sqlerrm);
 35  END F1;
 36  
 37  END pkg_pipeline;
 38  /

Package body created.

SQL> REM - INVOKING THE PIPELINE FUCNTION
SQL> 
SQL> DECLARE
  2    X_TAB pkg_pipeline.t_objects_tab;
  3    Begin
  4    X_TAB  := F1;
  5    end;
  6    /
  X_TAB pkg_pipeline.t_objects_tab;
  *
ERROR at line 2:
ORA-06550: line 1, column 11: 
PLS-00653: aggregate/table functions are not allowed in PL/SQL scope 

Ops whats the issue here, every seems to be right.  Lets try invoking the pipeline function from SQL.

SQL> REM - INVOKING PIPELINE FROM SQL
SQL> 
SQL> SELECT * FROM TABLE(PKG_PIPELINE.F1);

ACCOUNT_NBR G I                                                                 
----------- - -                                                                 
          1 A B                                                                 
          1 A B                                                                 
          1 A B                                                                 
          1 A B                                                                 
          1 A B                                                                 
          1 A B                                                                 
          1 A B                                                                 
          1 A B                                                                 
          1 A B                                                                 
          1 A B                                                                 

10 rows selected.

    
Bingo, Pipeline functions are meant for SQL. 

            The error PLS-00653 is due to overloading of pipeline function, which is a PLSQL restriction . Therefore do not overload an pipeline function. 

No comments:

Post a Comment