accenture plsql
TRANSCRIPT
PL/SQL – Basic Concepts
2© 2003 Accenture All Rights Reserved.
Prerequisites
• Prior knowledge of Oracle database
• Prior knowledge of DDL, DML & SQL Language
• Oracle 9i/10g installation on trainee desktop
• SQL*Plus utility installed
• Editor – Notepad / Wordpad
3© 2003 Accenture All Rights Reserved.
Introduction…
PL/SQL stands for Procedural Language/SQL
PL/SQL extends SQL by adding constructs found in procedural languages, resulting in a structural language that is more powerful than SQL
PL/SQL is a modern, block-structured programming language
PL/SQL provides several features that make developing powerful database applications very convenient
The basic unit in PL/SQL is a block. All PL/SQL programs are made up of blocks, which can be nested within each other
4© 2003 Accenture All Rights Reserved.
…Introduction
PL/SQL blocks can have both SQL data manipulation language (DML), and data definition language (DDL) statements
PL/SQL provides procedural constructs, such as loops and conditional statements, that are not available in standard SQL
PL/SQL offers features such as Data Encapsulation, Exception Handling, Information Hiding, Object Orientation
5© 2003 Accenture All Rights Reserved.
Architecture
6© 2003 Accenture All Rights Reserved.
Architecture• Stored procedure compilation produces object code which is
interpreted by pl/sql engine.• Native compilation into byte-code is possible from oracle 9i• Stored Procedures are loaded in Library cache in shared pool of
SGA. This is controlled by shared_pool_size init.ora parameter• Pin the stored procedure in memory to improve performance.
Oracle provides API to do this• execute dbms_shared_pool.keep('DBMS_ALERT'); • Pinning should be done after every start up• View v$db_object_cache provides list of all objects in shared pool
cache
7© 2003 Accenture All Rights Reserved.
Benefits of PL/SQL
Application Other DBMSs
ApplicationOracle with
PL/SQL
SQL
SQL
SQLSQL
SQL
Improved performance
PL/SQL can be used to group SQL statements together within a single block and to send the entire block to the server in a single call, thereby reducing networking traffic
SQLIF...THEN
SQLELSE
SQLEND IF;SQL
8© 2003 Accenture All Rights Reserved.
…Benefits of PL/SQL
Group logically related statements within blocks
Nest sub-blocks inside larger blocks to build powerful programs
Break down a complex problem into a set of manageable, well-defined, logical modules and implement the modules with blocks
PL/SQL is portable. Can be invoked from other environments
You can program with procedural language control structures
9© 2003 Accenture All Rights Reserved.
…Benefits of PL/SQL Error Handling
Improved data security and integrity
Improved performance allows you to :
Avoid reparsing for multiple users by exploiting the shared SQL area
Avoid PL/SQL parsing at run time by parsing at compile time
Reduce the number of calls to the database and decrease network traffic by bundling commands
10© 2003 Accenture All Rights Reserved.
Invoking Stored program units
xxxxxxxxxxxxxxvvvvvvvvvvvvvvxxxxxxxxxxxxxxvvvvvvvvvvvvvvxxxxxxxxxxxxxxvvvvvvvvvvvvvvxxxxxxxxxxxxxxvvvvvvvvvvvvvvxxxxxxxxxxxxxxvvvvvvvvvvvvvv
LOG_EXECUTIONprocedure
Scott
xxxxxxxxxxxxxxvvvvvvvvvvvvvvxxxxxxxxxxxxxxvvvvvvvvvvvvvvxxxxxxxxxxxxxxvvvvvvvvvvvvvvxxxxxxxxxxxxxxvvvvvvvvvvvvvvxxxxxxxxxxxxxxvvvvvvvvvvvvvv
Scott
Oracle Forms
Developer
Oracle Discoverer
Oracle Portal
1
2
3
4
11© 2003 Accenture All Rights Reserved.
Block Structure…• A PL/SQL block consists of
– an optional declaration section– an execution section and – one or more optional exception handler sections
• Declaration section declares PL/SQL variables, exceptions, and cursors
• Execution section contains PL/SQL code and SQL statements, control structures (loops), conditional statements (IF…END IF) and can contain nested blocks
• Exception handler section contain code that is called when the exception is raised, either as a predefined PL/SQL exception or as an exception that you define
12© 2003 Accenture All Rights Reserved.
…Block Structure
[<Block header>][declare]
<Constants><Variables><Cursors><User defined exceptions>
[begin]<PL/SQL statements>[exception]<Exception handling>
end;
DECLARE [Optional]
BEGIN [Mandatory]
END; [Mandatory]
EXCEPTION [Optional]
……
13© 2003 Accenture All Rights Reserved.
Types of PL/SQL
• Anonymous block
• Stored Procedure
• Function
• Package
• Trigger
14© 2003 Accenture All Rights Reserved.
Anonymous Block
• An anonymous block is a PL/SQL program unit that has no name
• An anonymous block – cannot take input arguments and return output values– cannot be called concurrently by multiple users– is not stored in the data dictionary
• Anonymous blocks are usually used interactively from a tool, such as SQL*Plus, or in a precompiler, OCI, or SQL*Module application
• They are usually used to call stored procedures or to open cursor
variables
15© 2003 Accenture All Rights Reserved.
Display output from Stored Procs
Package DBMS_OUTPUT enables you to print / display output from PL/SQL blocks and subprograms
The procedure put_line outputs information to a buffer in the SGA. You display the information by setting SERVEROUTPUT ON in SQL*Plus
SQL> SET SERVEROUTPUT ON
SQL> BEGIN
2 DBMS_OUTPUT.PUT_LINE(‘Hello World');
3 END;
4 /
Hello World
PL/SQL procedure successfully completed
16© 2003 Accenture All Rights Reserved.
Examples…
Example1:
SQL> set serveroutput on SQL> BEGIN 2 dbms_output.put_line(’Welcome to PL/SQL’);
3 END; 4 /
17© 2003 Accenture All Rights Reserved.
…ExamplesExample2:
DECLARE Emp_number INTEGER := 7369; Emp_name VARCHAR2(10); BEGIN SELECT Ename INTO Emp_name FROM EmpWHERE Empno = emp_number;DBMS_OUTPUT.PUT_LINE('Employee name is ' || Emp_name); EXCEPTION WHEN NO_DATA_FOUND THEN DBMS_OUTPUT.PUT_LINE('No such employee: ' ||
Emp_number); END; /
Declaring Variables
19© 2003 Accenture All Rights Reserved.
Agenda
• Basic PL/SQL Block and Its Sections
• Significance of Variables in PL/SQL
• Distinguishing Between PL/SQL and Non-PL/SQL Variables
• Declaring Variables and Constants
• Executing a PL/SQL Block
20© 2003 Accenture All Rights Reserved.
PL/SQL Block and Its Sections
DECLARE (Optional)
BEGIN (Mandatory)
EXCEPTION (Optional)
END; (Mandatory)
/
Variables, Cursors
Exceptions etc...
SQL Statements
PL/SQL Statements
Action to perform when error occurs...
Anonymous/Named Block or Stored Procedure or Function
Variable Declaration Section
Program Section
Exception Handling Section
21© 2003 Accenture All Rights Reserved.
Significance of Variables
• Variables can be used for:– Temporary storage of data– Manipulation of stored values– Reusability– Ease of maintenance
• This is facilitated by the way variables are handled in PL/SQL:– Variables are declared and initialized in the declaration section – Variables are assigned new values in the executable section– Values are passed to PL/SQL blocks through parameters– Output variables are used to view the results
22© 2003 Accenture All Rights Reserved.
Distinguishing PL/SQL and Non-PL/SQL Variables
• PL/SQL variables– Scalar (ex: NUMBER, VARCHAR2 etc...)– Composite (ex: TABLE, VARRAY etc...)– Reference (ex: REF cursors etc...)– LOB (large objects) (ex: LOB, BLOB etc...)
• Non-PL/SQL variables– Bind and host variables
23© 2003 Accenture All Rights Reserved.
PL/SQL Datatypes
24© 2003 Accenture All Rights Reserved.
Non PL/SQL Datatypes
• Bind and host variables– PL/SQL doesn’t have input or output capability of its own– iSQL*Plus host variables are used to pass run time values out
of the PL/SQL block back to the iSQL*Plus environment
Front EndDisplay
Server
O/SBind Variable
25© 2003 Accenture All Rights Reserved.
Example of using BIND Variables
SQL> variable h_sal numberSQL> variable h_ename varchar2(50)
SQL> begin2 select ename, sal3 into :h_ename, :h_sal4 from emp5 where empno=7369;6 end;/
SQL> print h_ename h_sal
26© 2003 Accenture All Rights Reserved.
Declaring Variables and Constants
v_hiredate DATE; v_deptno NUMBER(2) NOT NULL := 10; v_location VARCHAR2(13) := 'Atlanta'; v_mgr NUMBER(6) DEFAULT 100;
c_comm CONSTANT NUMBER := 1400;
identifier [CONSTANT]* datatype [NOT NULL]* [:= | DEFAULT expr]; * value must be assigned while declaring
The Variable name should not be more than 30 characters
Adopt a naming convention for PL/SQL identifiers:for example, v_variablename
Basic Syntax
Examples
27© 2003 Accenture All Rights Reserved.
Executing a PL/SQL Block
• From SQL* Plus editor– Once finished writing the block, press ‘/’– Specify the location of the file which contains the PL/SQL block (i.e.
SQL>@C:/PL-SQL/filename.sql)
• View Output– Use DBMS_OUTPUT.PUT_LINE() in the PL/SQL block– Type ‘set serverout on;’ from the SQL prompt
• View Error– Type ‘show errors;’ form the SQL prompt
28© 2003 Accenture All Rights Reserved.
Scope of VariableDeclareA number;Begin declare B number; begin declare C number; begin …..Statements…… end; …..Statements…….. end; …..Statements…….. end;/
Scope of Variable C is limited to the block displayed in RED
Scope of Variable B is limited to the block displayed in GREEN
Scope of Variable A is across block displayed in BLUE
Writing Control Structures
30© 2003 Accenture All Rights Reserved.
Agenda
• Identifying the Uses and Types of Control Structures
• Constructing Conditional Statements
• Constructing and Identifying Different Loop Statements
• Controlling Block Flow Using Nested Loops and Labels
31© 2003 Accenture All Rights Reserved.
Identifying the Uses and Types of Control Structures
TYPES of Control Structures
• IF Statement (IF ... THEN [ELSIF ... THEN ELSE ...] END IF;)
• CASE Statement
• Simple Loop
• While Loop
• FOR Loop
32© 2003 Accenture All Rights Reserved.
Constructing IF Statements
• IF Conditional Statement...
IF condition THEN
sequence_of_statements;
[ELSIF condition THEN
sequence_of_statements;]
[ELSE
sequence_of_statements;]
END IF;
• Conditions must evaluate to either ‘TRUE’ or ‘FALSE’.
• Statements are executed only when the associated condition evaluates to TRUE.
• If the condition evaluates to NULL, those statements corresponding to that condition will not be executed.
• Can have as many ELSIF sections as required, but only one IF and ELSE section.
33© 2003 Accenture All Rights Reserved.
Constructing CASE Statements…
CASE Statement
[<<label>>]
CASE test_variable
WHEN value1 THEN
sequence_of_statements;
WHEN value2 THEN
sequence_of_statements;
...
[ELSE
sequence_of_statements;]
END CASE [label];
• The test_variable can be simply a variable or an expression which call a function to get the value.
• ELSE section is optional, and if the expression does not match any value and if there is no ELSE section in the CASE statement, it will throw CASE_NOT_FOUND error.
• A label after END CASE is legal only if the CASE statement itself is labeled, and the two labels must match.
34© 2003 Accenture All Rights Reserved.
Example: IF StatementDeclareV_sal emp.sal%type;V_emp_name emp.ename%type;BeginSelect ename, sal into v_emp_name, v_sal from emp where empno = ‘7369’;If v_sal > 5000 then dbms_output.put_line(‘Salary is greater than 5000’);Else dbms_output.put_line(‘Salary is less than 5000’);End if;End;/
35© 2003 Accenture All Rights Reserved.
…Constructing CASE Statements
Searched CASE Statements
CASE WHEN bool_expr1 THEN
sequence_of_statements; WHEN bool_expr2 THEN
sequence_of_statements; ... [ELSE
sequence_of_statements;] END CASE;
36© 2003 Accenture All Rights Reserved.
Example:DECLARE
v_test1 NUMBER := 1;v_test2 VARCHAR2(20) := ‘ACN’;
BEGINCASE
WHEN v_test1 = 1 THENdbms_output.put_line(‘Value in v_test1 is ‘||to_char(v_test1)
);WHEN v_test2 = ‘ACN’ THENdbms_output.put_line(‘Value in v_test2 is ‘|| v_test2 );ELSEnull;
END CASE;END;/
…Constructing CASE Statements
37© 2003 Accenture All Rights Reserved.
LOOP Statements…
• LOOP Statement
LOOP
…statements;
EXIT [WHEN condition];
END LOOP;
• WHILE LOOP Statement
WHILE condition LOOP
…statements;
END LOOP;
•In a normal loop statement EXIT statement can come at any point in the sequence of statements inside the loop statement
• While loop can also contain an EXIT statement
• Number of iterations is not known in either of the LOOP or WHILE LOOP statements
• Loops also can be labeled, which will be useful while using nested loops
38© 2003 Accenture All Rights Reserved.
Example: While Loop
Declare
A number := 0;
begin
While a < 10 LOOP
a := a + 1 ;
Dbms_output.put_line(to_char(a) );
END LOOP;
END;
/
39© 2003 Accenture All Rights Reserved.
…LOOP Statements
FOR LOOP Statements
FOR counter IN [REVERSE] l_bound..u_bound
LOOP
…statements;END LOOP;
• Counter is an implicitly declared variable
• Difference of ‘l_bound’ and ‘u_bound’ specifies the number of iterations that a FOR LOOP will perform
• While entering FOR LOOP counter will be assigned the value of ‘l_bound’ and incremented by 1 for every iteration till it reaches the value of ‘u_bound’
• REVERSE key word is optional: If reverse key word is used, counter will be assigned the value of ‘u_bound’ and decremented by 1 for every iteration till it reaches the value of ‘l_bound’.
40© 2003 Accenture All Rights Reserved.
Example: FOR LoopDeclare
A number := 0;
begin
FOR i in 1..10 LOOP
a := a + i ;
Dbms_output.put_line(to_char(i) ||’ – ‘ || to_char(a) );
END LOOP;
END;
/
41© 2003 Accenture All Rights Reserved.
Example 2: FOR LoopDeclare
A number := 0;
begin
FOR i in REVERSE 1..10 LOOP
a := a + i ;
Dbms_output.put_line(to_char(i) ||’ – ‘ || to_char(a) );
END LOOP;
END;
/
Interacting with the Oracle Server
43© 2003 Accenture All Rights Reserved.
Agenda
• Writing a Successful SELECT Statement in PL/SQL
• Declaring the Data type and Size of a PL/SQL Variable Dynamically
• Writing Data Manipulation Language (DML) Statements in PL/SQL
• Controlling Transactions in PL/SQL
• Determining the outcome of SQL DML Statements
• Writing Explicit Cursors
44© 2003 Accenture All Rights Reserved.
Writing a Successful SELECT Statement…
• Select creates a virtual table, which exists only for the duration of execution of the SQL statement
• Select statement in PL/SQL uses “into” clause
• The SELECT INTO statement retrieves data from one or more database tables, then assigns the selected values to variables or fields
• The following SELECT statement returns an employee’s name, job title, and salary from the emp database table:
45© 2003 Accenture All Rights Reserved.
…Writing a Successful SELECT Statement in PL/SQL
SELECT ename, job, sal INTO my_ename,my_job,my_sal FROM emp
WHERE empno = my_empno;
• The select statement can be used with the BULK Collect clause. This is used to retrieve multiple rows of data
• When you use a SELECT INTO statement without the BULK COLLECT clause, it should return only one row. If it returns more than one row, PL/SQL raises the predefined exception TOO_MANY_ROWS
46© 2003 Accenture All Rights Reserved.
Declaring Data type and Size of a PL/SQL Variable Dynamically…• Variables can be declared dynamically by using two types of
attributes: %Rowtype %Type
• The %ROWTYPE attribute provides a record type that represents a row in a database table
• Fields in a record and corresponding columns in a row have the same names and datatypes
• The %ROWTYPE attribute can be used in variable declarations as a datatype specifier
47© 2003 Accenture All Rights Reserved.
…Declaring Data type and Size of a PL/SQL Variable Dynamically
• In the example below, %ROWTYPE is used to declare two records. The first record stores a row selected from the emp table. The second record stores a row fetched from the c1 cursor
1)DECLARE emp_rec emp%ROWTYPE; CURSOR c1 IS SELECT deptno, dname, loc FROM dept; 2)dept_rec c1%ROWTYPE;
48© 2003 Accenture All Rights Reserved.
…Declaring Data type and Size of a PL/SQL Variable Dynamically
• The %TYPE attribute provides the datatype of a field, record, nested table, database column, or variable
• In the following example, %TYPE provides the datatype of a variable:
credit REAL(7,2);debit credit%TYPE;
• The %TYPE attribute is particularly useful when declaring variables that refer to database columns Example:
my_dname scott.dept.dname%TYPE;
49© 2003 Accenture All Rights Reserved.
…Declaring the Data type and Size of a PL/SQL Variable Dynamically
• Using %TYPE to declare my_dname has two advantages. First, you need not know the exact datatype of dname. Second, if the database definition of dname changes, the datatype of my_dname changes accordingly at run time
50© 2003 Accenture All Rights Reserved.
Data Manipulation Language (DML) Statements in PL/SQL…
• The DML statements include: INSERT UPDATE DELETE
• Example of an Insert statement in pl/sql procedure: CREATE PROCEDURE create_dept ( my_deptno NUMBER, my_dname VARCHAR2, my_loc VARCHAR2) AS BEGIN INSERT INTO dept VALUES (my_deptno, my_dname, my_loc); END;
51© 2003 Accenture All Rights Reserved.
…Data Manipulation Language (DML) Statements in PL/SQL
Example 1 (UPDATE Statement in PL/SQL)
PROCEDURE raise_salary (emp_id Number, amount Number) ISBEGIN
UPDATE emp SET sal = sal + amount WHERE empno = emp_id;
END raise_salary;
52© 2003 Accenture All Rights Reserved.
…Data Manipulation Language (DML) Statements in PL/SQL
Example 2 (DELETE Statement in PL/SQL)
PROCEDURE fire_employee (emp_id INT) IS
BEGIN
DELETE FROM emp WHERE empno = emp_id;
END fire_employee;
53© 2003 Accenture All Rights Reserved.
Controlling Transactions in PL/SQL…
• A transaction is a series of SQL data manipulation statements that does a logical unit of work
• The transactions are controlled by using:
COMMIT ROLLBACK SAVEPOINT
• The COMMIT statement ends the current transaction and makes changes permanent. Until you commit the changes, other users cannot access the changed data; they see the data as it was before you made the changes
54© 2003 Accenture All Rights Reserved.
…Controlling Transactions in PL/SQL
• Example for commit: Consider a simple transaction that transfers money from one bank
account to another. The transaction requires two updates because it debits the first account, then credits the second. After crediting the second account commit is issued, which makes the changes permanent. Only then the other users can see the changes
• The ROLLBACK statement ends the current transaction and undoes any changes made during that transaction
55© 2003 Accenture All Rights Reserved.
…Controlling Transactions in PL/SQL
• The Rollback has two advantages:
- If you make a mistake like deleting the wrong row from a table, a rollback restores the original data
- If you start a transaction that you cannot finish because an exception is raised or a SQL statement fails, a rollback lets you
return to the starting point to take corrective action and perhaps try again
56© 2003 Accenture All Rights Reserved.
…Controlling Transactions in PL/SQL
• Consider the example, in which you insert information about an employee into three different database tables. All three tables have a column that holds employee numbers and is constrained by a unique index. If an INSERT statement tries to store a duplicate employee number, the predefined Exception DUP_VAL_ON_INDEX is raised. In that case, you want to undo all changes, so you issue a rollback in the exception handler
• SAVEPOINT names and marks the current point in the processing of a transaction
57© 2003 Accenture All Rights Reserved.
…Controlling Transactions in PL/SQL
• Used with the ROLLBACK TO statement, savepoints let you undo parts of a transaction instead of the whole transaction
• Example for save point:
Mark a savepoint before doing an insert. If the INSERT statement tries to store a duplicate value, the predefined exception DUP_VAL_ON_INDEX is raised. In that case, you rollback to the savepoint, undoing just the INSERT
58© 2003 Accenture All Rights Reserved.
Cursors in PL/SQL• CURSOR
1. For every SQL statement execution certain area in memory is allocated
2. PL/SQL allows you to name this area - Context Area/Cursor3. Cursor represents a structure or result set in memory
• CURSOR Variable1. Writing a Cursor in the PL/SQL - Declaring Cursor Variable2. Opening Cursor - Cursor Variable points to the Context
Area/Cursor
• Types of cursors1. Implicit Cursor 2. Explicit Cursor
59© 2003 Accenture All Rights Reserved.
CURSOR Attributes
%NOTFOUNDIt is a Boolean attribute, which evaluates to true, if the last fetch failed i.e. when there are no rows left in the cursor to fetch
%FOUNDBoolean variable, which evaluates to true if the last fetch, succeeded
%ROWCOUNTIt’s a numeric attribute, which returns number of rows fetched by the cursor so far
%ISOPENA Boolean variable, which evaluates to true if the cursor is opened otherwise to false
60© 2003 Accenture All Rights Reserved.
Distinguish between Implicit and Explicit Cursor• Implicit Cursors
– Any SQL or DML statements that are written in the PL/SQL executable section is declared as an implicit cursor by PL/SQL Engine
– Cursor operations are automatically performed by Oracle.– We do not have any programmatic control on the Implicit
cursors– Only recently executed SQL or DML statement’s information
can be read from the cursors attributes• Explicit Cursors
– Only SQL statements that are explicitly declared as cursors in the declaration section of the PL/SQL block is treated as an Explicit Cursor
61© 2003 Accenture All Rights Reserved.
Example1:BEGIN
UPDATE emp SET ename=‘RAM’;IF (SQL%NOTFOUND) THEN
INSERT INTO EMP(...) VALUES (...);END IF;
END;Example2:BEGIN UPDATE emp SET ename=‘RAM’; IF (SQL%ROWCOUNT = 0) THEN INSERT INTO EMP(...) VALUES (...); END IF;END;
…Implicit Cursor Attributes
62© 2003 Accenture All Rights Reserved.
CURSOR Operations
• DECLARECURSOR <cursor-name> IS <select statement>;
• OPEN
OPEN <cursor-name>;
• FETCHFETCH <cursor-name> INTO <var1,var2,...>;
• CLOSECLOSE <cursor-name>;
63© 2003 Accenture All Rights Reserved.
Cursor Example (Simple Loop...)
DECLARE
v_fname VARCHAR2(20);
CURSOR c_emp IS SELECT ename FROM emp;
BEGIN
OPEN c_emp;
LOOP
FETCH c_emp INTO v_fname;
EXIT WHEN c_emp%NOTFOUND;
DBMS_OUTPUT.PUT_LINE(‘Name: ‘ ||v_fname );
END LOOP;
CLOSE c_emp;
END;
/
64© 2003 Accenture All Rights Reserved.
Cursor Example (Simple Loop...)
DECLARE
v_fname VARCHAR2(20);
V_sal number;
CURSOR c_emp IS SELECT ename, sal FROM emp;
BEGIN
OPEN c_emp;
LOOP
FETCH c_emp INTO v_fname,v_sal;
EXIT WHEN c_emp%NOTFOUND;
DBMS_OUTPUT.PUT_LINE(‘Name: ‘ ||v_fname|| ‘ – ‘||to_char(v_sal) );
END LOOP;
CLOSE c_emp;
END;
/
65© 2003 Accenture All Rights Reserved.
Cursor Example (Simple Loop...)
DECLARE
v_emp emp%rowtype;
CURSOR c_emp IS SELECT * FROM emp;
BEGIN
OPEN c_emp;
LOOP
FETCH c_emp INTO v_emp;
EXIT WHEN c_emp%NOTFOUND;
DBMS_OUTPUT.PUT_LINE(‘Name: ‘ ||v_emp.ename||’ – ‘||to_char(v_emp.sal) );
END LOOP;
CLOSE c_emp;
END;
/
66© 2003 Accenture All Rights Reserved.
Cursor Example (WHILE Loop...) DECLARE v_name emp%ROWTYPE; CURSOR c_emp IS SELECT * FROM emp; BEGIN OPEN c_emp; WHILE c_emp%FOUND LOOP FETCH c_emp INTO v_name; DBMS_OUTPUT.PUT_LINE(‘Name: ‘ ||v_name.ename); END LOOP; CLOSE c_emp; END;/
67© 2003 Accenture All Rights Reserved.
Cursor FOR Loop
Cursor FOR loops have the advantage of providing the functionality of a cursor fetch loop simply and cleanly, with a minimum syntax...
• Declaring Cursor for FOR loop is same as the normal statement• Variables required to fetch the data from cursor need not be
declared• Type of the variable is automatically taken as cursor%ROWTYPE• Cursor Operations:
– Just before FOR loop starts, ‘OPEN’ operation is performed– At the beginning of every iteration, ‘FETCH’ operation is
performed and the %FOUND attribute is checked to make sure there are remaining rows in the active set
– When the active set is completely fetched, the cursor is closed as the loop ends by performing ‘CLOSE’ operation
68© 2003 Accenture All Rights Reserved.
Cursor Example (FOR Loop...)
DECLARE CURSOR c_emp IS SELECT ename FROM emp; BEGIN -- OPEN cursor implicitly executed here FOR v_name IN c_emp –- FETCH cursor implicitly executed here -- %FOUND Cursor checked for active records LOOP DBMS_OUTPUT.PUT_LINE(‘Name: ‘ || v_name.ename); END LOOP; -- CLOSE cursor implicitly executed here END;/
69© 2003 Accenture All Rights Reserved.
Cursor Example (FOR Loop...)
DECLARE CURSOR c_emp IS SELECT ename FROM emp; BEGIN -- OPEN cursor implicitly executed here FOR v_name IN c_emp –- FETCH cursor implicitly executed here -- %FOUND Cursor checked for active records LOOP DBMS_OUTPUT.PUT_LINE(‘Name: ‘ || v_name.ename); END LOOP; -- CLOSE cursor implicitly executed here END;/
70© 2003 Accenture All Rights Reserved.
Cursor Example (FOR Loop...)
BEGIN
FOR v_name IN (SELECT ename FROM emp)
LOOP
DBMS_OUTPUT.PUT_LINE(‘Name: ‘ || v_name.ename);
END LOOP;
END;
/
71© 2003 Accenture All Rights Reserved.
Parameterized Cursors
• A Parameterized Cursor takes arguments, similar to a PL/SQL Procedure or Function
• We do not have to hardcode any value in the WHERE clause, instead we can pass the variable as a parameter to the cursor
• If we are using the same SQL statement with different WHERE clauses, instead of writing cursors for each of the different criteria, we can generalize the cursor by declaring a parameterized cursor
• The scope of the cursor parameter is confined to that cursor• Only the syntax of ‘Declaring’ and ‘Opening’ the cursor differs, with
the normal cursor operation syntax• Observe that cursor can have ‘IN’ parameters only unlike in
procedures and functions we have ‘IN’, ‘OUT’ and ‘IN OUT’ as the mode of parameter
72© 2003 Accenture All Rights Reserved.
Parameterized Cursor Example DECLARE v_deptname varchar2(10) := 'SALES'; CURSOR c_emp (p_deptno emp.deptno%TYPE) IS SELECT ename FROM emp WHERE deptno = p_deptno; BEGIN
IF (v_deptname = 'SALES') THEN for t1 in c_emp(10) loop dbms_output.put_line(t1.ename); end loop;
ELSE
for t1 in c_emp(20) loop dbms_output.put_line(t1.ename); end loop;
END IF; END;/
73© 2003 Accenture All Rights Reserved.
FOR UPDATE Cursors…
• SELECT...FOR UPDATE cursor will be used to lock some set of records for modifying or updating
• SELECT...FOR UPDATE statement obtains exclusive row-level locks on all the rows identified by the SELECT statement
• After a ROLLBACK or COMMIT, we cannot further perform a FETCH against this type of cursor, as ROLLBACK or COMMIT closes or invalidates the cursor
• We can use FOR UPDATE clause in a SELECT against multiple statements
74© 2003 Accenture All Rights Reserved.
…FOR UPDATE CursorSyntax and Example
Syntax:– CURSOR c_name IS SELECT...FROM <table1>...FOR
UPDATE [OF <column_references>] [NOWAIT/WAIT n];
– UPDATE table1 SET ... WHERE CURRENT OF c_name;
• The OF list of the FOR UPDATE clause does not restrict you to changing only those columns listed
• NOWAIT/WAIT clause tells oracle not to wait/wait for n seconds before it acquires a lock. If this clause is not specified then oracle waits till the lock is released on the table and rows by other user
75© 2003 Accenture All Rights Reserved.
Example:
DECLARE CURSOR c_emp IS SELECT ename FROM emp FOR UPDATE
OF sal NOWAIT; BEGIN FOR v_emp IN c_emp LOOP UPDATE emp SET sal = (sal+comm)*1.2
WHERE CURRENT OF c_emp; END LOOP; END;
…FOR UPDATE CursorSyntax and Example
76© 2003 Accenture All Rights Reserved.
Reference Cursors (REF CURSOR)
• All the explicit cursors that we have seen till now are static cursors
• Static cursors are like constants because they can be associated with one runtime query
• A cursor variable, can be associated with different queries at runtime – REF Cursor
• Advantages of REF cursor is that we can pass a cursor variable as an argument to a procedure of function
77© 2003 Accenture All Rights Reserved.
Cursor Operations on REF Cursor• Declaring REF Cursor
TYPE c_name IS REF CURSOR [RETURN <return type>]A cursor with RETURN type is called strong cursorA cursor without RETURN type is called week cursor
• OPENING REF CursorOPEN c_name FOR <select statement>;
• FetchingFETCH c_name INTO <record name>;FETCH c_name INOT <var1,var2,...>;
• ClosingCLOSE c_name;
Note: Syntax for FETCH and CLOSE operations are same as that for static cursors...
78© 2003 Accenture All Rights Reserved.
REF CURSOR: Passing as a Parameter…
CREATE OR REPLACE PACKAGE ref_cursor_example AS TYPE c_emptype IS REF CURSOR; PROCEDURE sp_cur_example(pc_emp OUT c_emptype); END ref_cursor_example;
PROCEDURE sp_cur_example (pc_emp OUT c_emptype) AS BEGIN OPEN c_emp FOR select * FROM emp; END;
79© 2003 Accenture All Rights Reserved.
…REF Cursor: Passing as a ParameterSQL>DECLARE
c_emptable c_emptype;
v_emprec emp%ROWTYPE;
BEGIN
sp_cur_example(c_emptable);
LOOP
FETCH c_emptable INTO v_emprec;
DBMS_OUTPUT.PUT_LINE(v_emprec.first_name);
END LOOP;
END;
/
Composite Datatypes
81© 2003 Accenture All Rights Reserved.
Agenda
• PL/SQL Table
• PL/SQL Record
82© 2003 Accenture All Rights Reserved.
PL/SQL Table
• A PL/SQL table is a one-dimensional, unbounded, sparse collection of homogeneous elements, indexed by integers
• It is analogous to an array and a SQL table
• A PL/SQL table is one type of collection structure
83© 2003 Accenture All Rights Reserved.
PL/SQL Table Structure
Unique Identifier Field1 (data type)
Binary_Integer dept_name varchar2(14)
Example:
Accounting1
23
Research
Sales
84© 2003 Accenture All Rights Reserved.
PL/SQL Table Characteristics…
One-dimensionalA PL/SQL table can have only one column
Unbounded or UnconstrainedThere is no predefined limit to the number of rows in a PL/SQL table. The PL/SQL table grows dynamically as you add more rows to the table
No rows for PL/SQL tables are allocated for this structure when it is defined
85© 2003 Accenture All Rights Reserved.
…PL/SQL Table Characteristics Sparse
In a PL/SQL table, a row exists in the table only when a value is assigned to that row. Rows do not have to be defined sequentially. Can assign a value to any row in the table. Row 15 could have a value of `Fox' and row 15446 a value of `Red', with no other rows defined in between
Homogeneous elementsAs a PL/SQL table can have only a single column, all rows in a PL/SQL table contain values of the same datatype
Indexed by integersPL/SQL tables currently support a single indexing mode: by BINARY_INTEGER. This number acts as the "primary key" of the PL/SQL table. The range of a BINARY_INTEGER is from -231-1 to 231-1
86© 2003 Accenture All Rights Reserved.
…PL/SQL Table Characteristics The PL/SQL table structure is not a part of the SQL language
Standards restrictions with PL/SQL tables:
– There is no concept of transaction integrity with PL/SQL tables You cannot commit information to a PL/SQL table or roll back changes from the table
– You cannot SELECT from PL/SQL tables. There is no set based processing to retrieve data from a PL/SQL table. This is a programmatic construct in a programmatic language. Can use PL/SQL loops to move through the contents of a PL/SQL table, one row at a time
– Cannot issue DML statements (INSERTs, UPDATEs, and DELETEs) against PL/SQL tables
87© 2003 Accenture All Rights Reserved.
Declaring a PL/SQL Table
A PL/SQL table is declared in two stages:
Define a particular PL/SQL table structure (made up of strings, dates, etc.) using the table TYPE statement. The result of this statement is a datatype you can use in declaration statements
TYPE <table_type_name> IS TABLE OF <datatype> [ NOT NULL ] INDEX BY BINARY_INTEGER;
Declare the actual table based on that table type. The declaration of a PL/SQL table is a specific instance of a generic datatype
<table_name> <table_type>;
88© 2003 Accenture All Rights Reserved.
Referencing and Modifying PL/SQL Table Rows
Refer to a particular row in a PL/SQL table by specifying the name of
the table and the primary key value for that row
Syntax:
<table_name> ( <primary_key_value> )
89© 2003 Accenture All Rights Reserved.
Populate Rows of PL/SQL Table
Rows can be populated in PL/SQL Table in 3 methods
1) Direct assignment
2) Iterative assignment
3) Aggregate assignment
90© 2003 Accenture All Rights Reserved.
Direct assignmentDECLARE
TYPE tab_type IS TABLE OF NUMBER INDEX BY binary_integer;iter_tab tab_type;
BEGIN iter_tab(1) := 100; iter_tab(2) := 200; iter_tab(3) := 300; iter_tab(4) := 400; FOR j IN 1..iter_tab.count LOOP DBMS_OUTPUT.PUT_LINE(to_char(iter_tab(j))); END LOOP;END;/
91© 2003 Accenture All Rights Reserved.
Iterative assignmentDECLARE
TYPE tab_type IS TABLE OF NUMBER INDEX BY binary_integer;iter_tab tab_type;
BEGINFOR i IN 1..10 LOOP
iter_tab(i) := i+10;END LOOP;FOR j IN 1..10 LOOP
DBMS_OUTPUT.PUT_LINE(to_char(iter_tab(j)));END LOOP;
END;/
92© 2003 Accenture All Rights Reserved.
Aggregate assignment…DECLARE TYPE name_table IS TABLE OF VARCHAR2(100) INDEX BY
BINARY_INTEGER; old_names name_table; new_names name_table;BEGIN /* Assign values to old_names table */ old_names(1) := 'Smith'; old_names(2) := 'Harrison';
/* Assign values to new_names table */ new_names(111) := 'Hanrahan'; new_names(342) := 'Blimey';
93© 2003 Accenture All Rights Reserved.
/* Transfer values from new to old */
old_names := new_names;
/* This assignment will raise NO_DATA_FOUND */
DBMS_OUTPUT.PUT_LINE (old_names (1));
END;
/
…Aggregate assignment
94© 2003 Accenture All Rights Reserved.
Delete data from PL/SQL Table…
• Set a single row to NULL with the following kind of assignment: iter_tab (2) := NULL;
• To empty a PL/SQL table of all rows perform an aggregate assignment with a table that is empty
• Cannot perform a SQL DELETE statement on a PL/SQL table because it is not stored in the database
• Cannot DROP a PL/SQL table
95© 2003 Accenture All Rights Reserved.
…Delete data from PL/SQL TableExampleDECLARE
TYPE tab_type IS TABLE OF NUMBER INDEX BY binary_integer;iter_tab tab_type;null_tab tab_type;
BEGINFOR i IN 1..10 LOOP
iter_tab(i) := i+10;END LOOP;
FOR j IN 1..10 LOOP
DBMS_OUTPUT.PUT_LINE(TO_CHAR(iter_tab(j)));END LOOP;
96© 2003 Accenture All Rights Reserved.
iter_tab := null_tab;
DBMS_OUTPUT.PUT_LINE('Printing after setting to null');
FOR j IN 1..10 LOOP
DBMS_OUTPUT.PUT_LINE(to_char(iter_tab(j)));END LOOP;
DBMS_OUTPUT.PUT_LINE('After Print');END;/
…Delete data from PL/SQL Table
97© 2003 Accenture All Rights Reserved.
PL/SQL Table Built-In
Returns the greatest index of the PL/SQL table containing an element which is less than the specified index
PRIOR
Returns the smallest index of the PL/SQL table containing an element which is greater than the specified index
NEXT
Returns the greatest index of the PL/SQL table for which an element is defined
LAST
Returns the smallest index of the PL/SQL table for which an element is defined
FIRST
Returns FALSE if a reference to an element at the specified index would raise the NO_DATA_FOUND exception
EXISTS
Deletes one or more elements from the PL/SQL tableDELETE
Returns the number of elements currently contained in the PL/SQL table
COUNT
Description Operator
98© 2003 Accenture All Rights Reserved.
PL/SQL Record
• PL/SQL record is a composite data structure similar to a single-row of a database table
• PL/SQL record as a whole does not have value of its own; instead, each individual component or field has a value
• PL/SQL record gives you a way to store and access individual component values as a group
99© 2003 Accenture All Rights Reserved.
PL/SQL Record Structure
Field1 (data type) Field2 (data type) Field3 (data type)
10 ACCOUNTING NEW YORK
Field1 (data type) Field2 (data type) Field3 (data type)
dept_id number(2) dept_name varchar2(14) dept_loc varchar2(13)
Example:
100© 2003 Accenture All Rights Reserved.
PL/SQL Record Types
Each field is defined explicitly (its name and datatype) in the TYPE statement for that record; a field in a programmer-defined record can even be another record.
A record whose structure you, the programmer, get to define with a declaration statement.
Programmer-defined
Each field corresponds to a column or expression in the cursor SELECT statement
A record based on the cursor's SELECT statement.
Cursor-based
Each field corresponds to -- and has the same name as -- a column in a table.
A record based on a table's column structure
Table-based
Fields in RecordDescriptionRecord Type
101© 2003 Accenture All Rights Reserved.
Benefits of Using PL/SQL Records • Data abstraction
– Instead of working with individual attributes of an entity or object, PL/SQL record helps manipulate that entity as a "thing in itself"
• Aggregate operations – Helps perform operations which apply to all the columns of a
record• Leaner, cleaner code
– Helps write less code and more understandable code
102© 2003 Accenture All Rights Reserved.
Table based RecordA table-based record, or table record, is a record whose structure (set ofcolumns) is drawn from the structure (list of columns) of a table. Eachfield in the record corresponds to and has the same name as a column inthe table
DECLAREdept_rec dept%ROWTYPE;
BEGINSELECT * INTO dept_rec FROM dept WHERE deptno= 10;DBMS_OUTPUT.PUT_LINE('Dept name is : '||dept_rec.dname);DBMS_OUTPUT.PUT_LINE('Location is : '||dept_Rec.loc);
END;/
103© 2003 Accenture All Rights Reserved.
Cursor Based RecordsA cursor-based record, or cursor record, is a record whose structure isdrawn from the SELECT list of a cursor. Each field in the recordcorresponds to and has the same name as the column or aliasedexpression in the cursor's query
DECLARECURSOR dept_cursor is SELECT * FROM dept;dept_rec dept_cursor%ROWTYPE;BEGINOPEN dept_cursor;LOOP
FETCH dept_cursor INTO dept_Rec;EXIT WHEN dept_cursor%NOTFOUND;DBMS_OUTPUT.PUT_LINE('Dept name is : '||dept_rec.dname);
END LOOP;CLOSE dept_cursor;END;
104© 2003 Accenture All Rights Reserved.
Programmer-Defined Records
PL/SQL record which is a sub-set of table columns or from multiple tablesor views
DECLARETYPE emp_type IS RECORD (r_ename VARCHAR2(10), r_dname VARCHAR2(10));emp_rec emp_type;
BEGINSELECT ename,dname INTO emp_rec.r_ename, emp_rec.r_dname FROM dept,emp WHERE dept.deptno=emp.deptno and emp.empno= 7369;DBMS_OUTPUT.PUT_LINE('Dept name is : '||emp_rec.r_dname);DBMS_OUTPUT.PUT_LINE('Emp name is : '||emp_rec.r_ename);
END;/
Exception Handling
106© 2003 Accenture All Rights Reserved.
Agenda
• PL/SQL Error Handling
• Exception Handler Mechanism
• User Defined Exception
• PRAGMA Exception
107© 2003 Accenture All Rights Reserved.
PL/SQL Error Handling
In PL/SQL, errors of any kind (situations that should not occur ) aretreated as Exceptions in your program
An exception can be one of the following: An error generated by the system (such as "out of memory" or
"duplicate value in index") An error caused by a user actionA warning issued by the application to the user
PL/SQL traps and responds to errors using an architecture ofexception handlers
108© 2003 Accenture All Rights Reserved.
Exception Handler Mechanism The exception-handler mechanism allows you to clearly separate
your error processing code from your executable statements
It provides an event-driven model, as opposed to a linear code model, for processing errors
No matter how a particular exception is raised, it is handled by the same exception handler in the exception section
The processing in the current PL/SQL block's execution section halts and control is transferred to the separate exception section of your program, if one exists, to handle the exception
You cannot return to that block after you finish handling the
exception. Instead, control is passed to the enclosing block, if any
109© 2003 Accenture All Rights Reserved.
Advantages of Exception Model• Event-driven handling of errors
– You do not have to check repeatedly for a condition in your code, but instead can insert an exception for that condition once in the exception section and be certain that it will be handled throughout that block
• Clean separation of error-processing code – whenever an exception is raised, program control transfers
completely out of the normal execution sequence and into the exception section. Programmer can consolidate all of this logic into a single, separate section
• Improved reliability of error handling – errors will not go undetected with the PL/SQL error-handling
model. Even if there is no explicit handler for that error, normal code execution will still stop
110© 2003 Accenture All Rights Reserved.
Exception Types
• There are Two types of exceptions
– System Defined
• Raised automatically by the system when error occurs
– User Defined
• Raised explicitly in a sequence of statements using raise <exception name>
• Format
when <exception name> then <sequence of statements>;
111© 2003 Accenture All Rights Reserved.
Exception HandlingTrap the exception
DECLARE
BEGIN
END;
Exception is raised EXCEPTION
Exception is trapped
Propagate the exception
DECLARE
BEGIN
END;
Exception is raised
Exception is not trapped
Exception propagates to calling environment
112© 2003 Accenture All Rights Reserved.
Common Exceptions
System Exceptions the most common errors
Try to divide a number by 0.ORA-01476ZERO_DIVIDE
Expected one row but returned more than one
ORA-01422TOO_MANY_ROWS
Select statement returns no data
ORA-01403NO_DATA_FOUND
Invalid Cursor operation like fetching from a closed cursor
ORA-01001INVALID_CURSOR
Try to open a cursor which is already exist
ORA-06511CURSOR_ALREADY_OPEN
RemarksNumberException Name
113© 2003 Accenture All Rights Reserved.
Generic Exception
• OTHERS EXCEPTION HANDLERCan be used as a generic exception handler
ExampleDECLARE
a number;BEGIN
SELECT 1 INTO a FROM emp WHERE empno='99';
EXCEPTION WHEN OTHERS THEN DBMS_OUTPUT.PUT_LINE(‘Error –
‘||SQLCODE||' - '||SQLERRM);END;/
Note:
SQLCODE - Returns the number of the Oracle error for internal exceptions
SQLERRM - Returns the message associated with the error number
114© 2003 Accenture All Rights Reserved.
PL/SQL Exception Propagation…
115© 2003 Accenture All Rights Reserved.
…PL/SQL Exception Propagation
116© 2003 Accenture All Rights Reserved.
…PL/SQL Exception Propagation
117© 2003 Accenture All Rights Reserved.
User Defined Exceptions PL/SQL lets you define exceptions of your own
User-defined exceptions must be declared and must be raised explicitly by RAISE statements
The procedure RAISE_APPLICATION_ERROR lets you issue user-defined ORA error messages from stored subprograms. By using this built-in, you can report errors to your application and avoid returning unhandled exceptions
118© 2003 Accenture All Rights Reserved.
…User Defined Exceptions
Syntax :
Raise_application_error(error_number, message[, {TRUE | FALSE}]);
WHERE
error_number is a negative integer in the range
20000 .. -20999
message is a character string up to 2048 bytes long
If TRUE, the error is placed on the stack of previous errors
If FALSE (the default), the error replaces all previous errors
119© 2003 Accenture All Rights Reserved.
…User Defined Exceptions
RAISE_APPLICATION_ERROR is part of package DBMS_STANDARD, and as with package STANDARD, there is no need to qualify references to it
An application can call raise_application_error only from an executing stored subprogram (or method)
When called, raise_application_error ends the subprogram and returns a user-defined error number and message to the application
The error number and message can be trapped like any Oracle error
120© 2003 Accenture All Rights Reserved.
…User Defined ExceptionsDECLARE
emp_name varchar2(10);emp_number integer;empno_out_of_range EXCEPTION;
BEGINemp_number := 10001;IF emp_number > 9999 THEN
raise empno_out_of_range;ELSE
SELECT ename INTO emp_name FROM emp WHERE empno=emp_number;END IF;
EXCEPTIONWHEN empno_out_of_range THENDBMS_OUTPUT.PUT_LINE (‘Emp No' || to_char(emp_number) ||' is out of range.');
END;
121© 2003 Accenture All Rights Reserved.
PRAGMA Exception…• Apart from predefined exception, we can extend the list of exceptions
associated with an Oracle error within our PL/SQL code with the use of PRAGMA EXCEPTION_INIT keyword
• EXCEPTION PRAGMA is used to associate a named exception with a particular Oracle error
• This enable us to trap the error specifically, rather than via an OTHERS handle
• Only one user defined exception can be associated with one Oracle error with each occurrence of PRAGMA EXCEPTION_INIT
• This statement is a compiler directive that allows the developer to declare the Oracle-numbered error to be associated with a named exception in the block
122© 2003 Accenture All Rights Reserved.
…PRAGMA ExceptionExample
declare empname VARCHAR2(12); no_record EXCEPTION; PRAGMA EXCEPTION_INIT(no_record, 100);BEGIN select ename into empname from emp where empno=&9999; dbms_output.put_line('Name :'||empname);EXCEPTION when no_record then dbms_output.put_line('Error code is ' || SQLCODE); dbms_output.put_line('Error message is '||SQLERRM); dbms_output.put_line('No Record found');END;/
123© 2003 Accenture All Rights Reserved.
…PRAGMA ExceptionExample 2Trap for Oracle server error number –2292, an integrity constraint violationDECLARE p_deptno number := &deptno; e_emps_remaining EXCEPTION; PRAGMA EXCEPTION_INIT (e_emps_remaining, -2292);BEGIN DELETE FROM dept WHERE deptno = p_deptno; IF SQL%NOTFOUND THEN DBMS_OUTPUT.PUT_LINE ('No such dept '||to_char(p_deptno)); END IF;EXCEPTION WHEN e_emps_remaining THEN DBMS_OUTPUT.PUT_LINE ('Cannot remove dept ' || TO_CHAR(p_deptno)
|| '. Employees exist. ');END;
PL/SQL Subprograms
125© 2003 Accenture All Rights Reserved.
Agenda
• Subprogram Structure
• Stored Procedures
• Procedure Parameter Modes
• Functions
• Overloading
126© 2003 Accenture All Rights Reserved.
Sub Program StructureDeclare<Constants> <Variables> <Cursors>Begin<PL/SQL statements>
EXCEPTION …
<Exception handling>
END; /
Begin<PL/SQL statements>
Exception <Exception handling>
End;
127© 2003 Accenture All Rights Reserved.
Stored Program Unit
A Stored Procedure, Function, or Package is a PL/SQL program unit
that:
Has a name Can take input parameters, and can return output values Is stored in the data dictionary Can be called by many concurrent users Synonyms can be created on stored program units Data Access and execute privileges can be provided on stored
program units
128© 2003 Accenture All Rights Reserved.
Stored procedure…
• A named PL/SQL block that performs one or more actions and is called as an executable PL/SQL statement
• A Program can pass information into and out of a procedure through its parameter list
• A stored procedure is defined by the keywords CREATE PROCEDURE followed by the procedure name and its parameters
• There can be any number of parameters, each followed by a mode and a type. The possible modes are IN (read-only), OUT (write-only), and INOUT (read and write)
129© 2003 Accenture All Rights Reserved.
…Stored Procedure
Syntax
CREATE [or REPLACE] PROCEDURE <procedure name>
[(<list of parameters>)] IS <declarations>
BEGIN
<sequence of statements>
[EXCEPTION
<exception handling routines>]
END [<procedure name>];
IN | OUT | INOUTParameter
<parameter name> [IN | OUT | IN OUT] <data type> [{ := | DEFAULT} <expression>]
130© 2003 Accenture All Rights Reserved.
Procedure Parameter Modes
Callingenvironment
Procedure
procedure …
BEGIN
EXCEPTION
END;
IN parameter
OUT parameter
IN OUT parameter
131© 2003 Accenture All Rights Reserved.
Parameter Mode – IN…• IN - The IN parameter allows you to pass values in to the module,
but will not pass anything out of the module and back to the calling PL/SQL block
• IN parameters function like constants. Just like constants, the
value of the formal IN parameter cannot be changed within the program. You cannot assign values to the IN parameter or in any other way modify its value
• IN is the default mode for parameters • IN parameters can be given default values in the program header
132© 2003 Accenture All Rights Reserved.
ExampleCreate or Replace Procedure MyProc2 (I_empno IN number) is Emp_name VARCHAR2(10); Begin SELECT Ename INTO Emp_name FROM EmpWHERE Empno = i_empno;Dbms_output.put_line('Employee name is ' || Emp_name); Exception WHEN NO_DATA_FOUND THEN
Dbms_output.put_line('No such employee: ' || i_empno); End; /
…Parameter Mode - IN
133© 2003 Accenture All Rights Reserved.
Parameter Mode – OUT…• OUT - An OUT parameter is the opposite of the IN parameter. OUT
parameter is used to pass a value back from the program to the calling PL/SQL block
• OUT parameter is like the return value for a function, but it appears in
the parameter list and you can have as many OUT parameters as you like. Inside the program OUT parameter acts like a variable that has not been initialized
• OUT parameter has no value at all until the program terminates
successfully. During the execution of the program, any assignments to an OUT parameter are actually made to an internal copy of the OUT parameter. When the program terminates successfully and returns control to the calling block, the value in that local copy is then transferred to the actual OUT parameter. That value is then available in the calling PL/SQL block
134© 2003 Accenture All Rights Reserved.
Example
CREATE or REPLACE PROCEDURE MyProc3 (I_empno IN number, O_ename OUT Varchar2) is Emp_name VARCHAR2(10);
BEGIN SELECT Ename INTO O_ename FROM Emp WHERE Empno =
i_empno;EXCEPTION
WHEN NO_DATA_FOUND THENDBMS_OUTPUT.PUT_LINE('No such employee: ' || i_empno);
END; /
…Parameter Mode – OUT
135© 2003 Accenture All Rights Reserved.
Executing the Stored ProcedureDECLARE
v_ename varchar2(10);BEGIN Myproc3('7369',v_ename); DBMS_OUTPUT.PUT_LINE('Emp name is '||v_ename);END;
136© 2003 Accenture All Rights Reserved.
Parameter Mode – IN OUT• IN OUT - With an IN OUT parameter, you can pass values into the
program and return a value back to the calling program (either the original, unchanged value or a new value set within the program)
• IN OUT parameter shares two restrictions with the OUT
parameter:
- An IN OUT parameter cannot have a default value
- An IN OUT actual parameter or argument must be a variable. It cannot be a constant, literal, or expression, since
these formats do not provide a receptacle in which PL/SQL can place the outgoing value
137© 2003 Accenture All Rights Reserved.
Discovering Errors
PL/SQL does not always tell you about compilation errors. Instead, it
gives you a cryptic message such as "procedure created with
compilation errors"
To show the compilation error use the command
SQL> show errors procedure <procedure_name>;
Alternatively, you can type, SHO ERR (short for SHOW ERRORS) to
see the most recent compilation error
138© 2003 Accenture All Rights Reserved.
Function…• A named PL/SQL block that returns a single value and is used just
like a PL/SQL expression • A program can pass information into a function through its parameter
list
• Unlike a procedure, which is a standalone executable statement, a call to a function can only be part of an executable statement
• Because a function returns a value, it has a datatype
• A function can be used in place of an expression in a PL/SQL statement having the same datatype as the function
139© 2003 Accenture All Rights Reserved.
…Function
CREATE or <REPLACE> FUNCTION <func_name>(<param_list>)
RETURN <return_type> IS
BEGIN
<sequence of statements>
[EXCEPTION
<exception handling routines>]
END [<function name>];
140© 2003 Accenture All Rights Reserved.
…FunctionExample
CREATE or REPLACE FUNCTION total_sal (p_empno IN number)RETURN NUMBER is
n_total NUMBER;BEGIN
SELECT nvl(sal,0)+nvl(comm,0) INTO n_total FROM empWHERE empno = p_empno;RETURN(n_total);
EXCEPTION WHEN OTHERS THENDBMS_OUTPUT.PUT_LINE('Error occurred for emp : '||to_char(p_empno));RETURN(0);
END;/
141© 2003 Accenture All Rights Reserved.
Executing the FunctionDECLARE
a number;BEGIN
a := count_emp();END;/Functions can be called from SQL statements and DML Statements
Example:SELECT empno, ename, total_sal(empno) FROM emp WHERE empno =7369;
UPDATE employee SET sal = total_sal(7369) WHERE empno = 7369;
INSERT INTO employee(empno, salary) VALUES(7369, total_sal(7369));
142© 2003 Accenture All Rights Reserved.
Overloading• Two or more Procedures/Functions can have the same name with
different parameter lists • The parameter list of overloaded programs must differ by more than
parameter mode – Even if a parameter in one version is IN and that same parameter
is IN OUT in another version, PL/SQL cannot tell the difference at the point in which the program is called
• Overloaded functions must differ by more than their return type (the datatype specified in the RETURN clause of the function)
• All of the overloaded programs must be defined within the same
PL/SQL scope or block (anonymous block, module, or package)
143© 2003 Accenture All Rights Reserved.
Data dictionary tablesStored program units are available in 2 data dictionary tables
• USER_OBJECTS
• USER_SOURCE
SQL> select object_name, object_type, status fromuser_objects where object_name=‘MYPROC’;
SQL> select text from user_source wherename='MYPROC' order by line;
144© 2003 Accenture All Rights Reserved.
Dropping Function/Procedure
Syntax
To Drop a Stored Procedure– DROP <Procedure> <Procedure_Name>;
To Drop a Function– DROP <Function> <Function_Name>;
Example
DROP FUNCTION total_sal;
/
DROP PROCEDURE MyProc;
/
Triggers
146© 2003 Accenture All Rights Reserved.
Agenda
• Definition and Advantages
• Types of Triggers
• INSTEAD OF Triggers
• Manipulating Triggers
147© 2003 Accenture All Rights Reserved.
Definition and Advantages
• Triggers are a special PL/SQL construct similar to procedures
• Trigger is executed implicitly whenever the triggering event happens
• The trigger can be either row-level or statement-level, where the former fires once for each row affected by the triggering statement and the latter fires once for the whole statement
• Triggers may be used to
– supplement declarative referential integrity
– enforce complex business rules
– audit change to data
– monitor database related actions
148© 2003 Accenture All Rights Reserved.
• Oracle supports Event Triggers in addition to the SQL Statement and Row triggers
• Oracle statement and row triggers are based on three types of SQL statements: INSERT, UPDATE, and DELETE
• The trigger timing may be either “BEFORE" or “AFTER“
• Statement-level triggers fire only once per SQL statement, regardless of how many rows were processed
• Row-level triggers fire once for each row that is affected by the SQL statement
• In addition to these, Oracle supports “INSTEAD OF" triggers that are valid only on views
Types of Triggers
149© 2003 Accenture All Rights Reserved.
Row Level Trigger…
Syntax:
150© 2003 Accenture All Rights Reserved.
Within a ROW trigger, reference the value of a column before and after the data change by prefixing it with the OLD and NEW qualifier
The OLD and NEW qualifiers are available only in ROW triggers
Prefix these qualifiers with a colon (:) in every SQL and PL/SQL statement
Using OLD and NEW Qualifiers
…Row Level Trigger
151© 2003 Accenture All Rights Reserved.
Example
CREATE OR REPLACE TRIGGER Print_salary_changesAFTER UPDATE ON Emp FOR EACH ROW WHEN (new.Empno > 0)DECLARE sal_diff number;BEGIN sal_diff := :new.sal - :old.sal; dbms_output.put_line('Old salary: ' || :old.sal); dbms_output.put_line(' New salary: ' || :new.sal); dbms_output.put_line(' Difference ' || sal_diff);END;
…Row Level Trigger
152© 2003 Accenture All Rights Reserved.
Application
INSERT INTO my_view . . .;
MY_VIEW
INSTEAD OF Trigger
INSERT TABLE1
UPDATE TABLE2
INSTEAD OF Trigger
153© 2003 Accenture All Rights Reserved.
Example: INSTEAD OF triggercreate view Myemp as select empno, deptno, ename from emp/create or replace trigger MyEmp_update_viewinstead ofupdate on myempfor each rowbeginupdate emp set ename = :new.enamewhere empno = :new.empno;end;/Update myemp set ename = ‘Accenture’/Select empno, ename from emp/
154© 2003 Accenture All Rights Reserved.
System Event Triggers…
Syntax
CREATE [OR REPLACE] TRIGGER trigger_name
timing
[database_event1 [OR database_event2 OR ...]]
ON {DATABASE|SCHEMA}
trigger_body
Triggers are also used to monitor log on and log off
If you specify ON SCHEMA, the trigger fires for the specific user
If you specify ON DATABASE, the trigger fires for all users
155© 2003 Accenture All Rights Reserved.
Example
CONNECT SYSTEM/password
GRANT ADMINISTER DATABASE TRIGGER TO scott;
CONNECT SCOTT/TIGER
CREATE TABLE AUDITING(USERNAME VARCHAR2(12),LOGINDATE DATE);
CREATE OR REPLACE TRIGGER logontrig AFTER LOGON ON DATABASEBEGIN INSERT INTO AUDITING VALUES(ORA_LOGIN_USER,SYSDATE);END;
…System Event Triggers
156© 2003 Accenture All Rights Reserved.
Altering triggers:
ALTER TRIGGER trigger_name ENABLE|DISABLE;
ALTER TABLE table_name ENABLE|DISABLE all triggers;
Dropping triggers:
DROP TRIGGER trigger_name;
The following data dictionary views reveal information about triggers:
-USER_TRIGGERS
-ALL_TRIGGERS
-DBA_TRIGGERS
Manipulating Triggers
157© 2003 Accenture All Rights Reserved.
Packages• A package is a group of procedures, functions, variables and SQL
statements created as a single unit. It is used to store together related objects.
• A package has two parts, Package Specification or package header and Package Body.
• Package Specification acts as an interface to the package. Declaration of types, variables, constants, exceptions, cursors and subprograms is done in Package specifications. Package specification does not contain any code.
• Package Body is used to provide implementation for the subprograms, queries for the cursors declared in the package specification or spec.
158© 2003 Accenture All Rights Reserved.
Advantages of Packages
• Package allows you to group together related items, types and subprograms as a PL/SQL module.
• When a procedure in a package is called entire package is loaded, though it happens to be expensive first time the response is faster for subsequent calls.
• Package allows us to create types, variable and subprograms that are private or public
159© 2003 Accenture All Rights Reserved.
Package Header Syntax
Package <Package Name> is
[Declaration of Variables and Types]
[Declaration of Cursors]
[Specifications of modules]
End <package Name> ;
160© 2003 Accenture All Rights Reserved.
Package Body Syntax
Package Body <Package Name> is
[Declarations of variables and Types]
Specification of body of module
Begin
Executable statements
[Exception]
[Exception statements]
End <Package Name> ;
161© 2003 Accenture All Rights Reserved.
Example: Package Header
Create or replace Package P_Package1 as
Procedure P_Proc1;
Function P_Func1 return Varchar2;
End P_Package1;
/
162© 2003 Accenture All Rights Reserved.
Example: Package bodyCreate of Replace Package body P_Package1 asProcedure P_Proc1 is begin dbms_output.put_line(‘Hello from Procedure’); end P_Proc1;Function P_Func1 return Varchar2 is begin return (‘Hello from Function’); end P_Func1;End P_Package1;/
163© 2003 Accenture All Rights Reserved.
Example: Execute Package
SQL> Set serveroutput on
SQL> EXEC P_Package1. P_Proc1;
SQL> Select P_Package1. P_Func1 from Dual;
164© 2003 Accenture All Rights Reserved.
Example2: Package Header
Create or replace Package P_Dept asProcedure P_Insert_Dept(i_deptno number);
Procedure P_Insert_Dept(i_deptno number, i_dname varchar2, i_loc varchar2);
Procedure P_Update_Dept(i_deptno number, i_loc varchar2);
Procedure P_Delete_Dept(i_deptno number);
End P_Dept;
/
165© 2003 Accenture All Rights Reserved.
Example: Package bodyCreate or Replace Package body P_Dept as
Procedure P_Insert_Dept(i_deptno number) is
begin
insert into dept values(i_deptno, 'DefDname','DefLoc');
end P_Insert_Dept;
Procedure P_Insert_Dept(i_deptno number, i_dname varchar2, i_loc varchar2) is
begin
insert into dept values(i_deptno, i_dname, i_loc);
end P_Insert_Dept;
Procedure P_Update_Dept(i_deptno number, i_loc varchar2) is
begin
update dept set loc = i_loc
where deptno = i_deptno;
if sql%notfound then
dbms_output.put_line(‘ Your error text’);
end if;
end P_Update_Dept;
Procedure P_Delete_Dept(i_deptno number) is
begin
delete from dept
where deptno = i_deptno;
end P_Delete_Dept;
End P_Dept ;
/
166© 2003 Accenture All Rights Reserved.
Example: Execute Package
SQL> Set serveroutput on
SQL> EXEC P_dept. P_insert_dept(90, ‘QA’,’ROME’);
SQL> select * from dept;
SQL> EXEC P_dept.P_insert_dept(99);
SQL> select * from dept;
SQL> EXEC P_dept.p_update_dept(90,’Chn’);
SQL> select * from dept;
SQL> EXEC P_dept.p_delete_dept(90);
SQL> select * from dept;
167© 2003 Accenture All Rights Reserved.
DBMS_PROFILER Since Oracle 8i we can trace pl/sql like we can trace sql
with tkprof. With DBMS_PROFILER you can measure the execution time of a pl/sql program unit.
DBMS_PROFILER gives insight into the following statistics:- The number of times a piece of pl/sql was executed- The total time spend on a piece of pl/sql code, including sql statements.- Minimum and maximum time spend on a piece of pl/sql code- Which code is executed during profiling.
168© 2003 Accenture All Rights Reserved.
Prerequisites
• The DBMS_PROFILER package is not automatically created on install of the database.
• Before you can use it, you should run the following scripts: as sys user run the $ORACLE_HOME/rdbms/admin/profload.sql script.
• As user that uses the profiler (or as sys with grants) run: $ORACLE_HOME/rdbms/admin/proftab.sql
169© 2003 Accenture All Rights Reserved.
Procedures • The DBMS_PROFILER package has the following
procedures: • Start_Profiler: begin data collection Stop_Profiler: stop
data collection. Data is not automatically stored when the user disconnects.
• Flush_Data: flush data collected in user session. Can call at points in a run to get incremental data.
• Pause_Profiler: pause user data collection • Resume_Profiler: resume data collection Get_Version
(proc): gets the version of this api. • Internal_Version_Check: verify that the DBMS_Profiler
version works with this DB version.
170© 2003 Accenture All Rights Reserved.
Tables
• The profiler-information is stored in the following tables:
• plsql_profiler_runs - information on profiler runs
• plsql_profiler_units - information on each line profiled
• plsql_profiler_data - profiler data for each line profiled
171© 2003 Accenture All Rights Reserved.
Run profile session set serverout on enabled
declare run_id number; begin run_id := dbms_profiler.start_profiler(
to_char(sysdate,'DD-MM-YYYY HH24:MI:SS')); .. call pl/sql .. /* Clear data from memory and store it in profiler tables.*/ dbms_profiler.flush_data; dbms_profiler.stop_profiler; end;
172© 2003 Accenture All Rights Reserved.
Report on profile session • In Oracle 8i, Oracle supplied a sql
${ORACLE_HOME}/plsql/demo/profrep.sql to report of the profiling results.
In Oracle 10g a sql ${ORACLE_HOME}/plsql/demo/profsum.sql is provided.-- show procedures
• SELECT substr(u.unit_type,1,30),substr(u.unit_name,1,30), ROUND(d.total_time/10000000,2) total, d.total_occur, d.min_time, d.max_time FROM plsql_profiler_units u, plsql_profiler_data d WHERE u.runid = &1 AND u.unit_owner <> 'SYS' AND d.runid = u.runid AND d.unit_number = u.unit_number AND ROUND(d.total_time/1000000000,2) > 0.00 ORDER BY d.total_time DESC;
173© 2003 Accenture All Rights Reserved.
Top 10 Slow statementsSELECT * FROM ( select trim(decode(unit_type,'PACKAGE
SPEC','PACKAGE',unit_type)|| ' '||trim(pu.unit_owner)||'.'||trim(pu.unit_name))|| ' (line '|| pd.line#||')' object_name , pd.total_occur , pd.total_time , pd.min_time , pd.max_time , src.text , rownum sequencenr
from plsql_profiler_units pu , plsql_profiler_data pd , all_source src where pu.unit_owner = user and pu.runid = &1
and pu.runid=pd.runid and pu.unit_number = pd.unit_number and src.owner = pu.unit_owner and src.type = pu.unit_type and src.name = pu.unit_name and src.line = pd.line# ) where sequencenr <=10;