You are on page 1of 188

Oracle PL-SQL

Tata Consultancy Services ltd.

10 April 2012

Course Pre-requisites
A basic understanding of SQL in Oracle Understanding of a procedural language

Course Objectives
To provide an overview of PL-SQL in Oracle

Session Outline
Introduction Variable Declaration SQL in PL/SQL Conditional & Iterative Control Cursors Exception Handling Procedures & Packages Triggers ORDBMS

PL/SQL Introduction

PL/SQL Execution Environments - The PL/SQL Engine

PL/SQL BLOCK DECLARE Procedural Procedural BEGIN Procedural SQL Procedural SQL END;

PL/SQL BLOCK DECLARE Procedural Procedural BEGIN Procedural SQL Procedural SQL END; PROCEDURAL STATEMENT

EXECUTOR

To the SQL Statement Executors in the ORACLE RDBMS

PL/SQL BLOCK STRUCTURE

DECLARE

BEGIN

EXCEPTION

END

PL/SQL BLOCK STRUCTURE


Declaration Section Executable Section Exception Handler Section

Quick Note - Block structuring


1. Any block may contain sub-block. Sub-blocks may appear anywhere an executable statement may legally appear. 2. Statements end with a semi-colon (;) 3. Comments are preceded by -- or surrounded by /* */ 4. Declared objects exist within a certain scope

PL/SQL Variable Declaration

Variable Declarations Overview


Syntax of Declaration identifier [constant ] datatype [not null ] [:= plsql_expression ] ;

Quick Notes - Variable Declaration 1. The rules for identifiers are same as for SQL objects. 2. NOT NULL/CONSTANT may be optionally used

3. Only one identifier per line is allowed .


DECLARE firstname DECLARE firstname lastname

lastname CHAR(20) ; - illegal CHAR(20) ; -legal CHAR(20) ; - legal

10

Variable Declarations Overview


NUMBER Count revenue second_per_day running _total VARCHAR2 mid_initial last_name company_name DATE anniversary project_complexion next_checkup BOOLEAN over_budget available NUMBER; NUMBER (9,2); CONSTANT NUMBER := 60 * 60* 24 ; NUMBER (10,0) := 0; VARCHAR2 := K; VARCHAR2(10) NOT NULL; CONSTANT VARCHAR2(12); DATE := 05-NOV-78; DATE; DATE NOT NULL := 28-JUN-90; BOOLEAN NOT NULL := FALSE; BOOLEAN := NULL ;

11

Attribute Declaration
PL/SQL objects (such as variables and constants) and database objects (such as columns and tables ) are associated with certain attributes. %TYPE attribute DECLARE books_printed NUMBER (6); books_sold books.sold%TYPE ; maiden_name emp.ename%TYPE ; %ROWTYPE attribute DECLARE dept_row

dept%ROWTYPE ;

12

Variable Assignment
PL/SQL Expressions consist of Variables, Constants, Literals, and Function Calls. ASSIGNMENT Syntax plsql_variable := plsql_expression; Quick notes -Assignment 1. := (ASSIGNMENT ) whereas = (VALUE EQUALITY)

2. The datatype of the left and right hand side of an assignment must be the same or implicitly convertible to each other.
For ex. , N:=7 is legal because number may be implicitly converted to char.

3. Column or table reference are not allowed on either side of an assignment operator( : = ).
SCOTT.EMP.EMPNO := 1234; location := dept.loc.;

These are illegal

13

Scoping
SCOPE refers to the visibility of identifiers at different points in the PL/SQL block.

SCOPING RULES:
1. An identifier is visible in the block in which it is declared and all its subblocks unless rule #2 applies. 2. If an identifier in an enclosing block is redeclared in a sub-block, the original identifier declared in the enclosing block is no longer visible in the sub-block .However, the newly declared identifier has the rules of scope defined in rule #1.

14

Scoping Variables and Constants


DECLARE credit_limit CONSTANT NUMBER (6,2) : =2000; account NUMBER := 100; BEGIN DECLARE account CHAR(10) := ABC; new_balance NUMBER (9,2); BEGIN new_balance account credit_limit END; DECLARE account NUMBER := 200; old_balance NUMBER (9,2); BEGIN old_balance account credit_limit END; END; account credit_limit

15

PL/SQL SQL in PL/SQL

16

SQL & PL/SQL Overview


SQL Data Manipulation Language (DML) statement support 1. INSERT 2. UPDATE 3. DELETE 4. SELECT

QuickNotes - SQL DML Support


1. The full ORACLE syntax is supported for these statements 2. A PL/SQL variable may be placed anywhere a constant may be legally placed. 3. An identifier is first checked to see if it is a column in the database. If not, it is assumed to be a PL/SQL identifier. 4. These statements may not appear as part of an expression

17

SQL & PL/SQL Overview


INSERT DECLARE
my_sal NUMBER(7,2) := 3040.22; my_ename CHAR(25) := WANDA; my_hiredate DATE := 08-SEP-01; BEGIN INSERT INTO EMP (empno, ename, job, hiredate, sal , deptno) VALUES (2345, my_ename, cab Driver, my_hiredate, my_sal, 20); END;

EMPNO ENAME 7644 TURNER

SAL 1500

EMPNO ENAME 7644 TURNER 7400 ALLEN

SAL 1500 1600

INSERT 7400 ALLEN 1600


18

SQL & PL/SQL Overview


UPDATE DECLARE
max_allowed CONSTANT N UMBER := 5000; good_cust CHAR(8) := VIP; BEGIN

UPDATE ACCOUNT SET CREDIT_LIMIT = MAX_ALLOWED


WHERE TYPE = EMPLOYEE OR TYPE = good_cust; END;
EMPNO ENAME 7644 TURNER 7400 ALLEN SAL 1500 1600

EMPNO ENAME 7644 TURNER 7400 ALLEN

SAL 1500 1400

UPDATE
19

SQL & PL/SQL Overview


DELETE DECLARE
bad_child_type CHAR(8) := NAUGHTY; BEGIN DELETE FROM santas_gift_list WHERE kid_rating = bad_child_type ; END;

EMPNO ENAME 7644 TURNER 7400 ALLEN

SAL 1500 1600

EMPNO ENAME 7644 TURNER

SAL 1500

DELETE
20

SQL & PL/SQL Overview


APPLICATION VAR1 VAR2
EMPNO ENAME 7644 TURNER 7400 ALLEN SAL 1500 1600

VAR3

QuickNotes - SELECT INTO 1. A SELECT statement is the only DML that returns data. You must provide location for this data to be stored via the INTO clause. 2. A SELECT..INTO statement must return exactly one row. Zero or multiple returned rows result in an error. 3. For multi-row SELECTs use cursors.
21

SQL & PL/SQL Overview


SELECT Syntax
SELECT col1,col2INTO var1,var2.. FROM table_name WHERE ...

E.g.
DECLARE
part_name num_in_stock parts.name%TYPE; parts.num%TYPE;

BEGIN
SELECT name, num INTO part_name, num_in_stock

FROM PARTS
WHERE part_id = 234; -- manipulate the retrieved data here
22

Transaction processing
SAVEPOINT Syntax
SAVEPOINT <marker_name>;

ROLLBACK TO Syntax
ROLLBACK [WORK] TO SAVEPOINT <marker_name>;

SAVEPOINT and ROLLBACK TO Ex.


BEGIN INSERT INTO temp VALUES (1,1 ROW 1); SAVEPOINT A; INSERT INTO temp VALUES (2,2 ROW 2); SAVEPOINT B ; . ROLLBACK TO SAVEPOINT B; COMMIT ; END;

23

SQL Functions
SQL Functional Support (within a SQL Statement): 1. Numeric (e.g. SQRT, ROUND, POWER) 2. Character (e.g. LENGTH, UPPER) 3. Date (e.g. ADD_MONTHS, MONTH_BETWEEN); 4. Group(e.g. AVG, MAX, COUNT) INSERT INTO phonebook (lastname) VALUES (UPPER(my_lastname)); Other SQL Functional Support (outside of a SQL Statement):

MOST ORACLE SQL functional are available (except for group functions).
X := SQRT(y); lastname := UPPER (lastname); age_diff := MONTHS_BETWEEN(birthday1,birthday2)/12;

24

PL/SQL Conditional & Iterative Control

25

Logical Comparisons
Logical Comparisons form the basis of conditional control in PL/SQL The result of these comparisons are always either TRUE ,FALSE or NULL Anything compared with NULL results in a NULL value.

A NULL in an expression evaluates to NULL (except concatenation)


E.g. 5 + NULL evaluates to NULL

PL/ || NULL || SQL evaluates to PL/SQL


PL /SQL Datatypes NUMBER CHAR DATE BOOLEAN Operators

<,>
=, != <=, >=

26

IF Statements
IF Statements are used to conditionally execute the statement or sequence of statements.
IF Statement Syntax IF <condition> THEN <sequence of statements > [ELSEIF <condition> THEN <sequence of statements> ] -- ELSEIFs may be repeated [ELSE <sequence of statements>] END IF;

QuickNotes - IF Statement
1. <condition> must evaluate to a Boolean datatype (TRUE, FALSE, NULL) 2. If <condition> is TRUE, then the associated <sequence of statements> is executed; otherwise it is not

3. At most one <sequence of statements > gets executed

27

IF Statements
DECLARE num_jobs NUMBER(7); BEGIN SELECT COUNT(*) INTO num_jobs FROM auditions WHERE actorid=&&actor_id AND called_back =YES; IF num_jobs> 90 THEN UPDATE actor SET actor_rating = OSCAR time WHERE actorid = &&actor_id; ELSE IF num_jobs> 75 THEN UPDATE actor SET actor_rating = DAY time soaps WHERE actorid = &&actor_id; ELSE UPDATE actor SET actor_rating = Waiter WHERE actorid = &&actor_id; END IF; COMMIT; END;
28

The NULL Trap


BLOCK 1 .

IF Statements
BLOCK 2 . IF a < b THEN do_that ..; ELSE

IF a >= b THEN
do_this ..; ELSE do_that.; END IF;

do_this.;
END IF;

Given any pair of non-NULL values for a andb, will Block 1 and Block 2 do the same thing? What if either a orb (or both) is NULL?

29

Loop Statement Overview


Loops repeat a statement or sequence of statements multiple times. Four types of loops: 1. Simple Loops. 2. Numeric FOR Loops. 3. While Loops. 4. Cursor FOR Loops.

30

Loop Statements
Simple Loops repeat sequence of statements multiple times.
Simple Loop Syntax Loop <Sequence of Statements> END LOOP ; -- sometimes called an infinite loop

Exit statements exit any type of loop immediately Exit Syntax EXIT [WHEN <condition >]; -- infinite loop insurance

31

DECLARE ctr NUMBER(3) := 0; BEGIN LOOP INSERT INTO LOG VALUES (ctr, ITERATION COMPLETE); ctr := ctr +1; IF ctr = 1500 THEN EXIT; END IF; END LOOP; END; DECLARE ctr NUMBER(3) := 0; BEGIN LOOP UPDATE TABLE 1 SET COMMIT = UPDATES WHERE COUNT_COL = ctr; ctr := ctr +1; IF ctr = 1500 THEN EXIT; END IF; END LOOP; END;
32

Loop Statements Example

Loop Statements
Numeric FOR Loops repeat sequence of statements fixed number of times. Numeric FOR Loop Syntax
FOR <index> IN [REVERSE ] <integer>..<integer> LOOP <sequence of statements>

The Loop Index takes on each value in range , one of a time , either in forward or reverse order.
E.g. BEGIN FOR I IN 1..500 LOOP INSERT INTO temp(message)VALUES (I will not sleep in class.); END LOOP; END;

33

Loop Statements
QuickNotes - Index 1. It is implicitly of type NUMBER 2. It is only defined within the loop 3. Value may be referenced in an expression, but a new value may not be assigned to it within the loop
E.g. DECLARE my_index CHAR(20) := Fettuccini Alfredo; BEGIN FOR my index IN REVERSE 2130 LOOP /* redeclare s my_index*/ INSERT INTO temp(coll.)VALUES (my_index); /* insert the numbers 30 through 21*/ END LOOP; END;

FOR

i I N 1256 LOOP x := x + i ; -- legal i := I + 5; -- illegal END LOOP;


34

Loop Statements
WHILE Loops repeat a sequence of statements until a specific condition is no longer TRUE. While Loop Syntax WHILE <condition > LOOP <sequence of statements > END LOOP; QuickNotes - WHILE Loops 1. The term <condition> may be any legal PL/SQL condition (i.e. it must return a Boolean value of TRUE, FALSE or NULL) 2. The sequence of statements will be repeated as long as <condition> evaluates to TRUE DECLARE ctr NUMBER (3) := 0; BEGIN WHILE ctr < 500 LOOP INSERT INTO temp(message) VALUES (Well,I might sleep just a little); ctr := ctr +1 ; END LOOP; END;

35

GO TO Statement Overview
GO TO Statements jump to a different place in the PL/SQL block. GO TO Statements have 2 parts 1. The GOTO statement itself. 2. A statement label

GO TO Statement Syntax
<<label_name >> X :=X+1 ; - - statement label GOTO LABEL_NAME - - JUMPS TO x := x +1

36

GO TO Statements
NOT ALL GOTOs are Legal ! You can legally a GOTO a statement that is either: 1.in the same sequence of statements as the GOTO STATEMENT 2. In the sequence of statements that encloses the GOTO statement (I.e. an outer block)

<<dinner>>
x := x + 1 ; y := y + 1; IF a >= b THEN

GOTO your_brothers; IF a > b THEN b := b - a; <<your_brothers>> x := x - 1;

b : = b + c;
GOTO dinner; END IF;

END IF;

37

Other Uses for Statement Labels


Labels may label any statement In addition to their use as targets for GOTO statements, labels may be used for : 1. Blocks 2. Loops Labeling a block allows referencing of DECLARED objects that would otherwise not be visible because of Scoping rules. Syntax << label_name>> [ DECLARE -- declarations go here ] BEGIN -- executable statements go here [ EXCEPTION -- exception handlers go here ] END label_name ; -- must include the label_name
38

Other Uses for Statement Labels


E.g. << outer_block >> DECLARE n NUMBER; BEGIN n := 5; /* Start a sub block */ DECLARE x NUMBER := 10; n CHAR (10) := Fifteen; BEGIN INSERT INTO TEMP VALUES (outer_block.n , x , n ); COMMIT; END ; /* End of the sub block */ END outer_block;
39

Other Uses for Statement Labels


Labeling a Block allows you to reference a variable that might be hidden by a column name E.g. << sample >> DECLARE deptno NUMBER := 20; BEGIN UPDATE emp SET sal = sal * 1.1 WHERE deptno = sample.deptno; COMMIT; END sample;

40

Other Uses for Statement Labels


Labeling Loops allows you to reference objects that would otherwise not be visible because of scoping rules
E.g.

<< compute_loop >> For i IN 110 LOOP < statements . > DECLARE i NUMBER := 0 ; BEGIN INSERT INTO temp VALUES (i, compute_loop.i, COMPLETE ); END; END LOOP compute_loop; - must include loop name here

41

Other Uses for Statement Labels


Labeling EXITs is a convenient way to specify exits from outer loops E.g.

<< outer_loop >> WHILE a > b LOOP


b := b + 1; << inner_loop >> WHILE b > c LOOP

c := c + 2 ;
EXIT outer_loop WHEN c > 200 ; END LOOP inner_loop;

END LOOP outer_loop;

42

PL/SQL Cursors

43

Cursor Overview
Every SQL DML statement processed by PL/SQL has an associated CURSOR. Two Types of CURSORS 1. EXPLICIT Multiple row SELECT STATEMENTS 2. IMPLICIT All INSERT statements All UPDATE statements All DELETE statements Single row SELECT.INTO Statements

44

Using Explicit Cursors


STEP 1 . Declare the cursor DECLARE CURSOR <cursor name> IS <regular select statement> ;

QuickNotes - CURSOR Declaration


1. The < regular select statement > must NOT include the INTO clause required in a single-row SELECT.INTO statement
2. Declared cursors are scoped just like variables

Cursor Declaration Example DECLARE X NUMBER ( 7, 2 ) ; total NUMBER ( 5 ) lower_sal_limit CONSTANT NUMBER ( 4 ) := 1200 ; CURSOR c1 IS SELECT ename FROM emp WHERE sal > lower_sal_limit ; BEGIN ...
45

Using Explicit Cursors


STEP 2 . Open the cursor OPEN < cursor name > ; STEP 3 . Fetch data from the cursor

FETCH < cursor name >


Quick Notes - FETCH

INTO < var1 ,var2 > ;

1. Retrieves one row of data from the cursor and stores it in the specified variables (similar to how a single-row select works) 2. There must be exactly one INTO variable for each column selected by the SELECT statement 3. The first column gets assigned to var1 , the second to var2 , etc .

STEP 4 . Close the cursor


CLOSE < cursor name > ;
46

Explicit Cursors Attributes


%NOTFOUND E.g.

LOOP
FETCH my_cursor INTO my_ename , my_sal ; EXIT WHEN my_cursor%NOTFOUND ; -- process data here END LOOP ; %FOUND E.g.

FETCH my_cursor INTO my_ename ,my_sal ; WHILE my_cursor%FOUND LOOP -- process data here FETCH my_cursor INTO my_ename ,my_sal ; END LOOP ;
47

Explicit Cursor Attributes


%ROWCOUNT E.g. LOOP FETCH my_cursor INTO my_ename , my_sal ; EXIT WHEN (my_cursor%NOTFOUND) OR (my_cursor%ROWCOUNT > 10) ; -- process data here END LOOP %ISOPEN E.g. IF my_cursor%ISOPEN THEN FETCH my_cursor INTO my_ename , my_sal ; ELSE OPEN my_cursor ; END IF ;
48

Using Explicit Cursors


E.g.
DECLARE sal_limit NUMBER ( 4 ) := 0 ; my_ename emp.ename%TYPE ; my_sal emp.sal%TYPE ; CURSOR my_cursor IS SELECT ename , sal FROM emp WHERE sal > sal_limit ; BEGIN sal_limit := 1200 ; OPEN my_cursor INTO my_ename , my_sal ; LOOP FETCH my_cursor INTO my_ename , my_sal ; EXIT WHEN my_cursor%NOTFOUND ; -- nothing returned INSERT INTO new_table VALUES ( my_ename , my_sal ) ; END LOOP ; CLOSE my_cursor ; COMMIT ; END ;

49

Explicit Cursors -FOR Loops


Cursor FOR Loops specify a sequence of statements to be repeated once for each row that is returned by the cursor. Cursor FOR Loop Syntax FOR <record _name> IN <cursor_name> LOOP --- statements to be repeated go here END LOOP; Numeric FOR Loop Similarities 1. Specify a set of rows from a table by using the cursors name vs. specifying a set of integers (i.e. 110) 2. Index takes on the values of each row vs. index taking on integer values (i.e. 1 through 10) Implicitly Declared <record_name> record_name cursor _name%ROWTYPE; To reference an element of the record, use the record_name.column_name notation.

50

Explicit Cursors -FOR Loops


Conceptual Cursor Loop Model

Loops

When a cursor loop is initiated, an implicit OPEN cursor_name is executed.


For each row that satisfies the query associated with the cursor an, implicit FETCH is executed into the components of record_name.

Loops

Loops

When there are no more rows left to FETCH, an implicit CLOSE cursor_name is executed and the loop is exited.

51

Explicit Cursors - FOR Loops


E.g. DECLARE sal_limit NUMBER ( 4 ) := 0 ; total_sal NUMBER (9,2 ) := 0; CURSOR my_cursor IS SELECT ename , sal FROM emp WHERE sal > sal_limit ; BEGIN sal_limit := 1200 ; -- implicitly OPEN done next FOR cursor_row IN my_cursor LOOP -- an implicit fetch done here INSERT INTO new_table VALUES (cursor_row.ename ,cursor_row.sal ) ; total_sal := total_sal + cursor_row.sal; END LOOP ; --an implicit close done here. COMMIT ; END ;
52

Implicit Cursors - FOR Loops


An Implicit Cursor is automatically associated with any SQL DML statement that does not have an explicit cursor associated with it.

This includes : 1. ALL INSERT statements 2. ALL UPDATE statements 3. ALL DELETE statements 4. ALL SELECTINTO statements QuickNotes - Implicit Cursors
1. Implicit cursor is called the SQL cursor --it stores information concerning the processing of the last SQL statement not associated with an explicit cursor. 2.OPEN, FETCH, AND CLOSE dont apply. 3. All cursor attributes apply.
53

Implicit Cursors
SQL %NOTFOUND E.g. UPDATE emp SET sal = sal * 10.0 WHERE ename =WARD ; IF SQL %NOTFOUND THEN -- WARD wasnt found INSERT INTO emp (empno, ename ,sal) VALUES ( 1234,WARD 99999 ); END IF ;

54

Implicit Cursors
SQL%ROWCOUNT
E.g. DELETE FROM baseball_team

WHERE batting _avg. < .100;

IF SQL%ROWCOUNT > 5 THEN

INSERT INTO temp(message)


VALUES(Your team needs helps.); END IF;

55

PL/SQL Exception Handling

56

Exception Overview
In PL/SQL error are called exceptions
When an exception is raised, processing jumps to the exception handlers An exception handler is a sequence of statements to be processed

when a certain exception occurs


When an exception handler is complete processing of the block terminates

57

Exception Overview
Two Types of Exceptions 1. PREDEFINED INTERNAL EXCEPTIONS 2. USER-DEFINED EXCEPTIONS

PL/SQLs Exception Handlers


vs. Conventional Error Handling

58

Predefined Internal Exceptions


Any ORACLE error raises an exception automatically; some of the more common ones have names. TOO_MANY_ROWS ORA-(01427) - a single row SELECT returned more than one row NO_DATA_FOUND ORA-(01403) - a single row SELECT returned no data INVALID_CURSOR ORA-(01001) - invalid cursor was specified VALUE_ERROR ORA-(06502) - arithmetic ,numeric, string , conversion,or constraint error occurred. ZERO_DIVIDE ORA-(01476) - attempted to divide by zero DUP_VAL_ON_INDEX ORA-(00001) - attempted to insert a duplicate value into a column that has a unique index specified.

59

Syntax WHEN <exception_name [OR <exception_name]> then <sequence of statements> OR WHEN OTHERS THEN -- if used , must be last handler <sequence of statements> E.g. DECLARE employee_num emp.empno%TYPE; BEGIN SELECT empno INTO employee_num FROM emp; WHERE ename = BLAKE; INSERT INTO temp VALUES(NULL, empno,Blake's employee_num); DELETE FROM emp WHERE ename =BLAKE; EXCEPTION WHEN TOO_MANY_ROWS OR NO_DATA_FOUND THEN ROLLBACK; INSERT INTO temp VALUES (NULL,Blake not found, or more than one Blake); COMMIT;

Exception Handlers

WHEN OTHERS THEN ROLLBACK; END;


60

User - Defined Exceptions


User - defined Exceptions must be defined and explicitly raised by the user. E.g. DECLARE x NUMBER; my_exception EXCEPTION; -- a new object type. Raise your_exception; RAISE my_exception; Quick Notes -RAISE <exception_name> 1. Once an exception is RAISED manually, it is treated exactly the same as if it were a predefined internal exception.

2. Declared exceptions are scoped just like variables.


3. A user-defined exception is checked for manually and then RAISED , if appropriate.
61

User - Defined Exceptions


E.g. DECLARE my_ename emp.ename%TYPE :=BLAKE; assigned_projects NUMBER; too_few_projects EXCEPTION BEGIN ---- get no of projects assigned to BLAKE IF assigned_project < 3 THEN RAISE too_few_projects; END IF; EXCEPTION --begin the exception handlers WHEN too_few_projects THEN INSERT INTO temp VALUES(my_ename,assigned_projects,LESS THAN 3 PROJECTS!) COMMIT; END;
62

Exceptions Propagation
Step# 1 The current block is searched for a handler. If not found, go to step 2. Step# 2 If an enclosing block is found, it is searched for it handler. Step# 3 Step #1 and#2 are repeated until either there are no more enclosing blocks, or a handler is found . If there are no more enclosing blocks, the exception is passed back to the calling environment (SQL *Plus,SQL *Forms, a precompiled program,etc.) If the handler is found ,it is executed .when done the block in which the handler was found is terminated, and control is passed to thee enclosing block (if one exists), or to environment (if there is no enclosing block) Quick notes 1. Only one handler per block may be active at a time 2. If an exception is raised in a handler, the search for a handler for the new exception begins in the enclosing block of the current block

63

Exceptions Propagation
Example 1
BEGIN ...
BEGIN IF X=1 THEN RAISE A: ELSEIF X=2 THEN RAISE B; ELSE RAISE C; EXCEPTION WHEN A THEN ... END; EXCEPTION ... END;
WHEN B THEN
Exception A is handled locally and execution resumes in the outer block

64

Exceptions Propagation
Example 2
BEGIN ...
BEGIN IF X=1 THEN RAISE A: ELSEIF X=2 THEN RAISE B; ELSE RAISE C; EXCEPTION WHEN A THEN ... END; EXCEPTION ... END;
WHEN B THEN
Exception B handled and control is passed back to the calling environment Exception B PROPAGATES to the first outer block with an appropriate handler

65

Exceptions Propagation
Example 3
BEGIN ...
BEGIN IF X=1 THEN RAISE A: ELSEIF X=2 THEN RAISE B; ELSE RAISE C; EXCEPTION WHEN A THEN .. END; EXCEPTION
WHEN B THEN ..
Exception C has no handler and will result in runtime unhandled exception

END;
66

Other uses of RAISE


By itself ,the RAISE statement simply re-raise the current exception (as if it were being propagated) Syntax RAISE;

Quick Notes - RAISE


1. RAISE may only be used in an exception handler

67

Error Reporting Functions


SQLCODE and SQLERRM

1. Provided information on the exception currently being handled.


2. Especially useful in the OTHERS handler. SQLCODE 1. Returns the ORACLE error number of the exception or 1 if it was user-defined exception SQLERRM 1. Return the ORACLE error message currently associated with the current value of SQLCODE

2. May also use any ORACLE error number as an argument.


QuickNotes - Error Reporting 1. If no exception is active SQLCODE = 0 SQLERRM = normal , successful completion 2. SQLCODE and SQLERRM cannot be used within a SQL statement.
68

Error Reporting Functions


E.g.

DECLARE
sqlcode_val sqlcode_val NUMBER; CHAR(70);

BEGIN
EXCEPTION WHEN OTHERS THEN sqlcode _val := SQLCODE; -- cant insert directly sqlerrm_val := SQLERRM ; - -- cant insert directly INSERT INTO temp VALUES(sqlcode_val, NULL, sqlerrm_val); END;
69

PL/SQL Procedures & Packages

70

Stored Procedures and Functions

Collections of SQL and PL/SQL statements Stored in complied from in the database Can call other procedures

Can be called from all client environments


Procedures and function (including remote) are the same, except a function returns a values and a procedure does not.

71

Uses for Procedures


Define central well-known business functions. Create an order Delete a customer Store batch job in the database

Weekly account rollups


Encapsulate a transaction Gather and process information from remote nodes Funnel activity on a table through a single path All changes to employee salaries should change department budgets.
72

Procedure Arguments
Argument Modes

IN OUT

Data value comes in from the calling process and is not changed No data value comes in from the calling process; on normal exit ,value of argument is passed back to caller Data value comes in from the calling process, and another value is returned on normal exit

IN OUT

73

Creating a Procedure
E.g.
CREATE PROCEDURE fire_employee (empid NUMBER) AS BEGIN DELETE FROM emp WHERE empno= fire_employee.empid; END

Tip:Write each procedure in a text file, and save

74

Creating a Function
E.g.

CREATE FUNCTION
get_bal (acc_no NUMBER(4)) RETURN IS acc_bal NUMBER(11,2); NUMBER(11,2);

BEGIN
SELECT balance INTO acc_bal FROM accounts WHERE account_id_no=acc_no; RETURN (acc_bal); END;

75

Statements in procedures
Valid statements in a procedure or function
SQL DML or PL/SQL statements
Calls to other procedures and functions stored in the database Calls to other procedures and functions in a remote database Restricted statements

DDL
Dynamic SQL In trigger, COMMIT, SAVEPOINT and ROLLBACK

76

Executing a stored procedure


From within a PL/SQL block fire_employee (empno);
scott.fire_employee (empno); On a remote node scott.fire_employee@ny (empno); From SQL*DBA and some ORACLE tools EXECUTE fire_employee (1043) Within an anonymous block (when EXECUTE not available) SQLPLUS> BEGIN FIRE_EMPLOYEE(1043); END; From a precompiler application EXEC SQL FIRE_EMPLOYEE(:empno);

77

Specifying procedure arguments


E.g.
CREATE PROCEDURE update_sal (empno NUMBER, bonus NUMBER, sal_incr NUMBER) .;

Positional Method
List values in the order they are declared

update_sal (7000,20,500);

Named Method
List argument names and values in any order, using special syntax update_sal (bonus => 20, sal_incr => 500, empno => 7000);

78

Specifying procedure arguments


Combination method Use both positional and named methods Once you specify a named parameter, must use named method for all remaining parameters update_sal (7000,sal_incr=>500,bonus=>20); update_sal (empno=>7000, sal_incr=>500,20); Illegal Legal

79

How procedures are entered into the database


PL/SQL Engine compiles the source code ORACLE stores a procedure in a database: Object name Source code Parse tree Pseudo code(P-code) Syntax errors in dictionary table Dependency information SQL in procedure not stored in parsed form Uses shared and cached SQL Allows SQL to be optimized dynamically (without recompiling referencing procedures)

80

PL/SQL Compilation Errors


Compile done by PL/SQL engine in RDBMS
Error stored in the database To view errors:
Use SQL*DBA command SHOW ERRORS Select from errors views USER_ERRORS ALL_ERRORS DBA_ERRORS

81

PL/SQL Compilation Errors


Executing SHOW ERRORS
SQLDBA>create procedure test1 is begin test2;end;

DBA-00072: Warning: PROCEDURE TEST1


created with compilation errors. SQLDBA>show errors

ERRORS FOR PROCEDURE TEST1:


LINE/COL ERROR --------------------------------------------------------------------------------------------1/0 1/33 PL/SQL: Compilation unit PL/SQL-00219:test2 is not defined

analysis terminated
2 rows selected

82

PL/SQL Compilation Errors


Fields in ERRORS views
NAME:name of the object

TYPE: one of the following:


PROCEDURE FUNCTION PACKAGE

PACKAGE BODY
LINE:line number where error occurs TEXT:text of error

83

USER-DEFINED System Errors


Any procedure can raise an error and return a user defined error message and
error number

Error number range is -20000 to -20999


Range always reserved for user defined errors Oracle does not check if user defined error numbers are used uniquely

Raise error within PL/SQL block with procedure raise_application_error


(error_number,text of the message) Full pathname of procedure may be needed in early releases

sys.standard_utilities.
raise_application_error

84

USER-DEFINED System Errors


Example
CREATE PROCEDURE fire_employee (empid NUMBER) AS BEGIN IF empid <=0 THEN raise_application_error (-20100,Employee number must be> 0); ELSE DELETE FROM emp WHERE EMPNO =EMPID; END IF; END; SQLDBA> EXECUTE FIRE_EMPLOYEE(-1); ORA=-20100: Employee number must be >0

85

Dependencies and Procedures


A procedure is dependent on:
every database object to which it refers (direct dependency) procedures, functions, packages, tables, views, synonyms, sequences the database objects those objects depend on (indirect dependency)

Two types of dependencies


local: objects are on the same node remote: objects are on separate nodes

ORACLE automatically checks dependencies

86

Recompilation of Dependent procedures


When an object changes, its dependent objects are marked for recompilation Any change to definition of referenced object implies new version of reference object Dependent objects must be recompiled if referenced object changes Recompilation of dependent objects takes place automatically at runtime Reasons recompilation could fail
Changing parameter list in called procedure Changing definition of or removing referenced column from referenced table Dropping referenced table

87

Recompilation
Procedure/function can be recompiled be either
RDBMS automatically, when next accessed (only if marked for recompilation) Manually by the user, using ALTER PROCEDURE command

If recompilation fails, error information is put to error table

88

Manual Recompilation
ALTER PROCEDURE

Procedure COMPILE

schema
Example
ALTER PROCEDURE
add_department COMPILE

89

Changing a Procedure
To modify a procedure, replace it:
CREATE OR REPLACE PROCEDURE fire_employee AS . . . END;

OR REPLACE option:
Recreates the procedure even if it already exists

Retains existing grants (need not reissue)


Creates procedure even if there are syntax errors Marks dependent objects for recompilation Users executing old procedure finish that call: next invocation gets new procedure Facilitates development (one step)

CREATE without OR REPLACE on existing procedure fails

90

Dropping a Procedure

DROP PROCEDURE

Procedure

schema
Example
DROP PROCEDURE fire_employee;

Marks dependent objects for recompilation

91

Privileges for Procedures


Examples
GRANT EXECUTE ON scott.hire_fire TO mkennedy WITH GRANT OPTION;

Procedure executes under the authority of owner, not user executing procedure User of procedure need not have access to objects inside procedure Can only GRANT privileges on an entire package, not a procedure, function, or variable defined in the package

92

Privileges for Procedures


PROCEDURE system privileges apply to procedures, functions and packages
To do this CREATE Need either CREATE PROCEDURE or CREATE ANY PROCEDURE system privilege Own the procedure or ALTER ANY PROCEDURE system privilege Own the procedure or DROP ANY PROCEDURE system privilege And Owner must have access to all objects referenced in the procedure

ALTER

DROP

93

Privileges for Procedures

To do this Execute a procedure or access a package construct

Need either Own the procedure or be granted EXECUTE PRIVILEGE or EXECUTE ANY PROCEDURE system privilege

And Procedure owner must be explicitly granted access to all database objects in the procedure(not through roles)

94

Benefits of Procedures
Security
Executes under security domain of procedures owner Provides controlled indirect access to database objects to non- privileged users

Integrity
Defines allowed operations on data

Ensures related actions are performed together

Performance
Reduces number of calls to thedatabase

Decreases network traffic


Pre-parses PL/SQL statements

95

Benefits of Procedures
Memory savings
Takes advantages of shared SQL Requires only one copy of the code for multiple users

Productivity
Avoids redundant code for common procedures in multiple applications Reduces coding errors: no redundant code written

96

Benefits of Procedures
Maintainability
Enables system wide changes with one update Makes testing easier: duplicate testing not needed Dependency tracked by ORACLE

High availability
Allows changing procedured on-line while users execute previous version

97

Package
A database object that groups related package constructs
Procedures functions cursor definitions variables and constants exception definitions

Package comprises Specification Body

98

Parts of a Package
Package specification
Declares (specifies) package constructs, including names and parameters publicly available procedures and functions

Package body
May declare additional, private package constructs that are not publicly available

Defines all package constructs (public and private)


May be replaced without affecting package specification (Breaks dependency chain) Each session has own version of state

99

Public and Private Package Constructs


Public package constructs
Declared in the package specification Available to anyone who can run the package

Private package constructs


Only declared in the package body Available to other package constructs within the package body Allows hiding procedures from programmers referencing the public constructs

100

Public and Private Package Constructs


Public declarations
PACKAGE hire_fire IS PROCEDURE hire_employee (. .); PROCEDURE fire_employee (. .); valid CHAR(1); END; PACKAGE BODY hire_fire IS PROCEDURE hire_employee (. .); IS BEGIN. . . END; PROCEDURE fire_employee ( . .) IS BEGIN . . . END; FUNCTION check_num (. . ) RETURN. . IS BEGIN . . END; END;

Definition of public constructs

Definition of private function

101

Public and Private Package Constructs


Package PK Variable C

Package specification

Procedure A x :=pk.c;

Variable D Package Procedure B y :=d; z :=c; body

102

Uses of Packages
Group related constructs Declare globally accessible variables Declare variables with persistent state Organize development activity Define modules, collections of procedures known to on team Minimize name conflicts within a schema Personnel.audit inventory.audit Simplify security GRANT EXECUTE on entire package limit recompilation Change body of procedure or function without changing specification

103

Creating a Package Specification


Example
/* Package specification declaring procedures and variables for hiring and firing employees */ CREATE PACKAGE hire_fire AS /*Declare procedures */ PROCEDURE hire_employee (empno NUMBER, ename CHAR, mgr NUMBER, sal NUMBER, comm NUMBER, deptno NUMBER); PROCEDURE fire_employee (empid NUMBER); /*Global variable declaration*/ valid CHAR(1); END hire_fire;

104

Creating a package Body


Example
/*package body containing procedures to hire and ire employee */ CREATE PACKAGE BODY hire_fire AS /*Procedure to hire a employee*/ PROCEDURE hire_employee (empno NUMBER, ename CHAR, mgr NUMBER, sal NUMBER, comm NUMBER, deptno NUMBER); IS BEGIN /*VALID is declared in the package definition*/ valid :=check_sum(empno); /*IF valid empno then add user*/ IF valid =T THEN INSERT INTO EMP VALUES (empno,ename,mgr,sal,comm,deptno); END IF; END;
105

(continued)

Creating a package body


Example(continued)
/* Procedure to fire an employee number */ PROCEDURE fire_employee (empid NUMBER) IS BEGIN DELETE FROM emp WHERE empno =empid; END; /*function to check that the employee number>0.Local to the package */ FUNCTION check_sum (empno NUMBER) RETURN CHAR(1) IS answer CHAR(1); BEGIN answer :=T; IF empno <0 THEN answer := F; END IF; RETURN (answer); END; END hire_fire; /*End of package*/

106

Accessing package constructs


PROCEDURE employee_admin /* The action to perform and the employee ID have been entered previously*/ IF action =HIRETHEN scott.hire_fire.hire_employee ( employee,ename,mgr,sal,comm,deptno); IF scott.hire_fire.valid =T THEN /*sports_club is another package that handles membership to the company sports club*/

sports_club.add (employee)
END IF; ELSIF action =FIRE THEN scott.hire_fire.fire_employee (employee); sports_club.remove (employee); END IF;

107

Dropping a Package

DROP PACKAGE

PROCEDURE

schema
Example
DROP PACKAGE hire_fire;

108

Benefit Of Package
Performance Reduces disk I/O for subsequent calls - First call to package loads whole package into memory

Persistence state Security

Retain values of package constructs for an entire session


Access to the package allows access to public constructs in the package only. No need to issue GRANT for every procedure in package.
109

Benefit Of Package
Productivity
Stores related procedures and function together

Easier to manger changing the specification or definition of a construct.


Reduces cascading dependencies Dependencies are at package ,not procedure level Can change package body with changing or affecting package specification

110

PL/SQL Triggers

111

Triggers
Definition

Creating Triggers
Restrictions on Triggers Dropping and recompiling

Privileges for creating


Applications Benefits

112

Trigger Definition
Application UPDATE t SET .; INSERT INTO t..; Table T
INSERT(trigger)

Database
UPDATE(trigger)

DELETE
FROM t;
DELETE(trigger)

113

What is a Trigger
A user-defined PL/SQL block associated with a specific table, and implicitly fired (executed) when a triggering statement is issued against the table Made up of parts - Triggering event (INSERT/UPDATE/DELETE) - Trigger type (BEFORE/AFTER, per statement or per row) - Trigger restriction (optional) * WHEN clause - Trigger action * PL/SQL BLOCK Not the same as a SQL * Forms trigger
114

E.g. of a Trigger - Keeping salary in range for a job


CREATE TRIGGER scott.salary_check BEFORE INSERT OR UPDATE sal, job ON scott.emp FOR EACH ROW WHEN (NEW .job <> PRESIDENT) DECLARE minsal NUMBER; maxsal NUMBER; BEGIN /* get min and max salaries for the employees job from the SAL_GUIDE*/ SELECT minsal,maxsal INTO minsal,maxsal FROM sal_guide WHERE job = :NEW.job; /* If salary below min or above max,generate an error*/ IF (:NEW.sal < minsal.OR :NEW.sal > maxsal) THEN raise_application_error ( -20500,salary || :NEW.sal|| out of range for job|| :NEW.job|| for employee|| :NEW.ENAME); ENDIF; END; /* End of Trigger*/

115

Triggers and Stored procedures


Similarities

Made up of PL/SQL and SQL statements


Use shared SQL areas Cannot be Changed (must be dropped and recreated )

Dependencies tracked automatically by ORACLE

116

Triggers and Stored procedures


Differences

Triggers invoked implicitly ;procedures invoked explicitly


Triggers and procedures crated with different SQL statements No CREATE OR REPLACE TRIGGER statement

Triggers are associated with tables


COMMIT ,ROLLBACK,SAVEPOINT not allowed in Triggers (nor in procedures called by Triggers)

117

Triggers vs. SQL*Forms Triggers


Database trigger Fires while statement executes Fires independently of and in addition to SQL *From Triggers

Fired by SQL statement from any tool or application


Can prevent completion of SQL statement Fire as each statement is executed SQL * Form trigger Associated with particular form Only executes when from is run Can fire after each field is entered Pre/Post INSERT/UPDATE /DELETE Triggers execute when COMMIT key is pressed
118

Types of Triggers
Type of a trigger determines
The time when the trigger fires
BEFORE trigger: before the triggering action AFTER trigger: after the triggering action The item the trigger fires on Row trigger: once for each row affected by the triggering statement Statement trigger: once for the triggering statement, regardless of the number rows affected

Each table have up to 12 Triggers in all:


INSERT/UPDATE/DELETE) BEFORE/AFTER) STATEMENT/ROW)
119

Types of Triggers
How to use each type BEFORE statement trigger
To initialize global variables used in Triggers
To prevent update before it occurs

BEFORE row trigger


To compute derived fields in the new row To prevent updates before they occur

AFTER row trigger


For auditing (by value,by row) Used by ORACLE snapshot mechanism

AFTER statement trigger


For auditing

120

Trigger - Firing Sequence


INSERT,UPDATE or DELETE is applied to table statement to execute Execute BEFORE statement trigger For each row affected by the SQL statement: Execute BEFORE row trigger Change row and perform integrity constraint checking Execute AFTER row trigger Execute AFTER statement trigger Complete deferred integrity constraint checking Returns to application

121

Expressions in Triggers
Referring to values in row Triggers
To refer to the old and new values of a column in row Triggers, use the :OLD and :NEW prefixes: IF :NEW.sal < :OLD.sal. THEN Notes: Values available in row Triggers only

New and old both available for UPDATE


The old value in an INSERT is NULL The new value in a DELETE is NULL BEFORE row trigger can assign values to :NEW if it is not set by UPDATE SET clause or INSERT VALUES list Can replace :NEW and :OLD with other correlation names if desired Colon dropped in when clauses

122

Expressions in Triggers
Conditional Predicates
If a trigger can fire on more than one type of DML operation use pre defined PL/SQL boolean variables to determine which caused the trigger to fire: IF INSERTING . . . IF UPDATING . . . IF DELETING . . . To detect which column is being updated: IF UPDATING (columnname)

123

Expressions in Triggers
CREATE TRIGGER total_salary

AFTER DELETE OR INSERT OR UPDATE


OF deptno,sal ON emp FOR EACH ROW BEGIN

IF (DELETING) OR (UPDATING AND: OLD deptno <> :NEW deptno.)


THEN UPDATE dept SET total_sal = total_sal -:OLD.sal WHERE deptno. = :OLD.deptno;

END IF;
END;

124

Restrictions on Triggers
Maximum number of 12 Triggers for a table
Up to three (INSERT/UPDATE/DELETE) Triggers of each type

Prohibited statements in Triggers:


ROLLBACK COMMIT SAVEPOINT

N.B. Also applies to procedures called by Triggers (including remote procedures)

Cascading trigger limit


The action of a trigger may cause another trigger to fire and so on (called cascading Triggers) Limit the depth of cascading with an INIT.ORA parameter

125

Restrictions on Triggers
Original EMP
ENAME
SMITH JONES

Mutating tables

SAL
1000 1000

UPDATE emp SET sal = sal *1.1;


UPDATE(trigger)

mutating EMP
ENAME
SMITH JONES

SAL
1100 1000

SELECT sal FROM emp WHERE

A table that is being modified by an UPDATE, DELETE, or INSERT in a single user statement
A trigger cannot SELECT from or change a mutating table (except current row, using :NEW and :OLD)
126

Restrictions on Triggers
Changes to updated/inserted values
EMPNO
0450 0407

DEPTNO
20 10

UPDATE emp SET deptno=10 WHERE empno =0405;

mutating EMP EMPNO DEPTNO


0450 0407 10 10

UPDATE (trigger)

CREATE TRIGGER bad BEGIN NEW.deptno:=30 END;

A trigger cannot change values explicitly referenced in the UPDATE statement SET clause or INSERT statement
127

Enabling and disabling Triggers


Possible states for a trigger
Enabled

Executes its triggered action if both: an appropriate statement is issued. trigger WHEN clause evaluates to TRUE(if present). Disabled
Does not execute its triggered action

Triggers are automatically enabled on creation

128

Enabling and disabling Triggers


Reasons for disabling the trigger

Have to load a large amount of data, and want to proceed quickly without firing Triggers
Example: SQL*Loader using direct path automatically disables Triggers

Want to INSERT, UPDATE or DELETE on a table whose trigger references a database object that is not available

129

Enabling and disabling Triggers


With ALTER TRIGGER

ALTER TRIGGER schema

trigger

ENABLE DISABLE

Examples
ALTER TRIGGER reorder DISABLE;

ALTER TRIGGER reorder ENABLE;

130

Enabling and disabling Triggers


With ALTER TABLE

ALTER TABLE
SCHEMA ENABLE TRIGGER SCHEMA

TABLE

TRIGGER

DISABLE

Examples
ALTER TABLE INVENTORY
DISABLE TRIGGER REORDER; ALTER TABLE INVENTORY ENABLE TRIGGER REORDER;

131

Dropping Triggers
DROP TRIGGER SCHEMA TRIGGER

Example
DROP TRIGGER reorder;

Triggers cannot be altered; they must be dropped and recreated

132

Recompiling a trigger
ALTER TRIGGER SCHEMA TRIGGER COMPILE

Manually recompile to resolve dependencies (same as procedures)

Example
ALTER TRIGGER reorder COMPILE;

133

Applications of Triggers
Maintaining derived fields

Implementing complex security rules


Enforcing complex business rules Performing value-based auditing

Making implied changes


Maintaining table replication

134

Examples of using Triggers


Deriving column values Derive column values for a row based upon a value provided by an INSERT or UPDATE statement. Must use BEFORE ROW trigger
Value must be derived first so the INSERT or UPDATE statement can use it. Trigger must fire for each row affected.

Cannot assign to new values set by triggering INSERT or UPDATE.

135

Examples of using Triggers


Deriving column values
Emp no Ename 7329 7499 7566 Smith Allen Jones Uppername Soundexname Job Smith Allen Jones S530 A450 J520 Clerk Salesman Manager

CREATE TRIGGER upper_soundex BEFORE INSERT OR UPDATE OF ename, uppername, soundexname ON emp ; FOR EACH ROW BEGIN :NEW.uppername := UPPER (:NEW.ename); :NEW.soundexname := :SOUNDEX(:NEW.ename); END;
136

Examples of using Triggers


Complex Security Authorization
Allows more complex security checking than provided by ORACLE

Examples - Check for time of day,day of week


- Check for terminal being used - Permit updates of certain amounts by specific users

137

Examples of using Triggers


Complex Security Authorization
CREATE TRIGGER emp_permit_changes BEFORE INSERT OR DELETE OR UPDATE ON emp DECLARE dummy INTEGER; BEGIN IF(TO_CHAR (sysdate,DY) IN(SAT,SUN)) THEN raise_application_error(-20504,cannot change emp table during weekend); END IF; SELECT COUNT(* ) INTO dummy FROM company_holidays WHERE day = TRUNC(sysdate); IF dummy>0 THEN raise_application_error(-20505,cannot change emp table during holiday); END IF; IF (TO_NUMBER(sysdate,HH24) NOT BETWEEN 8 AND 18) THEN raise_application_error (-20506,cannot change emp table in of_hours); END IF; END;

138

Examples of using Triggers


Enforcing complex Business Rules Complex check constraints that are not definable using declarative constraints

Can be used to maintain data integrity across a distributed database


(declarative integrity cannot span distributed database) Note: simple constraints are best handled by declarative constraints features

139

Examples of using Triggers


Enforcing complex Business Rules
CREATE TRIGGER increase_chk BEFORE UPDATING OF sal ON emp FOR EACH ROW WHEN (NEW.sal <OLD.sal OR

NEW.sal >1.1 * OLD. Sal)


BEGIN raise_application_error(-20502, may not decreased salary. Increase must be <10%) END;

140

Examples of using Triggers


Enforcing complex Business Rules
CREATE TRIGGER scott.salary_check BEFORE INSERT OR UPDATE OR UPDATE OF sal, ON scott.emp FOR EACH ROW WHEN (NEW.job <>PRESIDENT) DECLARE minsal NUMBER; maxsal NUMBER; BEGIN SELECT minsal,maxsal INTO minsal,maxsal FROM sal_guide WHERE job= :NEW.job ; IF (:NEW.sal <minsal OR :NEW.sal > maxsal) THEN raise_application_error ( -20503,salary || :NEW.sal|| out of range for job||:NEW.job|| for employee|| :NEW.ENAME); END IF; END;

141

Examples of using Triggers


Value based auditing
Auditing that cannot be accomplished with standard RDBMS auditing features Allows
Exclusively DML auditing Per row auditing Storage of update details

However Triggers cannot audit:


DDL SELECTs

Logons

142

Examples of using Triggers


Value based auditing
CREATE TRIGGER audit_employee AFTER INSERT OR DELETE OR UPDATE ON emp FOR EACH ROW BEGIN IF auditpackage.reason IS NULL THEN raise_application_error(-20501,MUST specify reason for update before performing update;use auditpackage.set_reason()); END IF; INSERT INTO audit_employee VALUES ( :OLD.ssn, :OLD.name; :OLD.classification, :OLD.sal, :NEW.ssn; :NEW.name, :NEW.classification, :NEW.sal, auditpackage.reason,user,sysdate); END;

143

Examples of using Triggers


Implied data changes

PENDING_ORDERS
PART_NO
00234 00342

ORD_QTY
15 25

ORD_DATE
15-JAN-92 15-JAN-92

INVENTORY
PART_NO ON_HAND
00234 00342 34 52

REORD_PT
30 50

REORD_QTY
15 25

Transparently perform an action when a triggering is executed Example: Inventory check generates a new order
144

Examples of using Triggers


Implied data changes
CREATE TRIGGER inv_check AFTER UPDATE of on_hand ON inventory FOR EACH ROW WHEN (NEW.ON_HAND <= NEW.reord_pt) DECLARE x NUMBER; BEGIN SELECT COUNT(*) INTO x FROM pending_orders WHERE pending_orders.part_no = :NEW.part_no; IF x = 0 THEN INSERT INTO pending_orders VALUES (:NEW.part_no, :NEW.reord_qty, SYSDATE); END IF; END;

145

Examples of using Triggers


Synchronous Table Replication
Link identical tables(replicas) on different nodes so when replica is altered, changes are synchronously reflected in other replicas Replicas must contain a flag field that is set when they are updated to stop trigger cascading

EMP_REP1

EMP_REP2

UPDATE...

UPDATE...

146

Benefits of Triggers
Security
Allows sophisticated security checking Enables customized auditing mechanism to be built

Integrity
Ensures related operations on data are performed together

Can be used to enforce complex business rules

147

Benefits of Triggers
Performance
Reduces number of calls to the RDBMS Decreases network traffic

Memory savings
Takes advantage of shared SQL

Requires only one copy of the code for multiple users

Productivity
Requires only a single copy of the code be written and maintained(not multiple copies in client applications)

148

PL/SQL ORDBMS

149

Object Oriented Concepts


Relational Traditional RDBMS

Object-relational Abstract Datatypes, Varying Arrays, Nested Tables


Object-oriented Database using object-oriented analysis and design

Benefits:
Reusability Adherence to Standards

Defined access paths

150

Types of Objects
Abstract Datatypes

Object Views
Varying Arrays Nested Tables

References
Large Objects

151

Abstract Datatypes
Grouping related columns (subtypes) into objects create type ADDRESS_TY as object

( street
city state zip

VARCHAR2(50),
VARCHAR2(25), VARCHAR2(2), NUMBER);

create type PERSON_TY as object ( name VARCHAR2(25),

address ADDRESS_TY);
Owner needs to grant EXECUTE privilege on the Datatype to other users for them to use it
152

Abstract Datatypes
Table creation: create table CUSTOMER

( customer_id
person

NUMBER,
PERSON_TY);

Table can be described using set describe depth to 2, 3 etc. in order to view the attributes for abstract datatypes Insert operation: insert into CUSTOMER values ( 1, PERSON_TY(Peter, ADDRESS_TY(Street S, City C, ST, 11111)));

153

Abstract Datatypes
Select operation: select customer_id, c.person.name from customer c; select c.person.name, c.person.address.city from customer c

where c.person.address.city like F%;


Index creation: create index I_CUSTOMER_CITY on CUSTOMER(person.address.city);

154

Object Views
The ability to overlay object oriented structures on existing relational tables
create table CUSTOMER ( customer_id name street city NUMBER VARCHAR2(25), VARCHAR2(50), VARCHAR2(25), PRIMARY KEY,

state
zip ( street city state zip

VARCHAR2(2),
NUMBER); VARCHAR2(50), VARCHAR2(25), VARCHAR2(2), NUMBER);
155

create type ADDRESS_TY as object

Object Views
create type PERSON_TY as object ( name address VARCHAR2(25), ADDRESS_TY);

Object View creation:


create view CUSTOMER_OV (customer_id, person) as select customer_id, PERSON_TY(name, ADDRESS_TY(street, city, state, zip))

from customer
where state = DE; /* optional */

156

Object Views
Relational Insert operation:
insert into CUSTOMER values (123, Richard, 12 Farmside Close, Lewiston, NJ, 4352);

Object View Insert operation:


insert into CUSTOMER_OV values (123, PERSON_TY(Richard, ADDRESS_TY(12 Farmside Close, Lewiston, NJ, 4352)));

157

Object Views
INSTEAD OF Triggers:
BOOKSHELF_AUTHOR (title, author);
BOOKSHELF_PUBLISHER (title, publisher); create view AUTHOR_PUBLISHER as

select a.author, a.title, p.publisher


from BOOKSHELF_AUTHOR a, BOOKSHELF_PUBLISHER p where a.title = p.title;

update AUTHOR_PUBLISHER
set publisher = MARINER where author = HARDY; Gives error ORA-01779

158

Object Views
create trigger AUTHOR_PUBLISHER_UPDATE /* INSTEAD OF Trigger */ instead of UPDATE on AUTHOR_PUBLISHER for each row

begin
if :old.publisher <> :new.publisher then update BOOKSHELF_PUBLISHER set publisher = :new.publisher

where title = :old.title;


end if; if :old.author <> :new.author then update BOOKSHELF_AUTHOR

set author = :new.author


where title = :old.title; end if; end;
159

Object Views
Methods:
create type ANIMAL_TY as object ( breed VARCHARE2(25),

name

VARCHAR2(25),

birthdate DATE, member function age(birthdate IN DATE) return NUMBER);

create type body ANIMAL_TY as


member function age(birthdate DATE) return NUMBER is begin return ROUND(sysdate birthdate);

end;
end;
160

Object Views
Data Security:
create type ANIMAL_TY as object ( breed VARCHARE2(25),

name

VARCHAR2(25),

birthdate DATE, member function age(birthdate IN DATE) return NUMBER, PRAGMA RESTRICT_REFERENCES(age, WNDS)); WNDS = Write No Database State RNDS = Read No Database State WNPS = Write No Package State

RNPS = Read No Package State

161

Object Views
Using Methods:
create table ANIMAL ( Id animal NUMBER, ANIMAL_TY);

insert into ANIMAL values (11, ANIMAL_TY(Cow, Mimi, TO_DATE(01-JAN-1998, DD-MM-YYYY))); select a.animal.age(a.animal.birthdate) from animal;

162

Allows storage of repeating attributes of a record in a single row


create type TOOL_TY as object ( toolname VARCHAR2(25));

Varying Arrays

create type TOOLS_VA as varray(5) of TOOL_TY; /* Using abstract datatype */ create type TOOLS_VA as varray(5) of VARCHAR2(25); /* Using base datatype */ create table BORROWER ( name tools VARCHAR2(25) TOOLS_VA); PRIMARY KEY,

Data Dictionary Tables for more information:


USER_TYPES

USER_COLL_TYPES
163

Varying Arrays
Insert Operation:
insert into BORROWER values (AMY, TOOLS_VA(Hammer, Sledge, Axe)); insert into BORROWER values (DAVID, TOOLS_VA(Hammer, Axe, NULL, NULL, NULL));

164

Varying Arrays
Select Operation
Using PL/SQL:
declare cursor borrower_cur is select * from BORROWER;

begin
for borrower_rec in borrower_cur loop dbms_output.put_line(Contact Name: || borrower_rec.name);

for i in 1..borrower_rec.tools.count
loop dbms_output.put_line(Contact Name: || borrower_rec.tools(i)); end loop;

end loop;
end;
165

Varying Arrays
Select Operation Using Table Function:
select b.name, n.*

from BORROWER b, TABLE(b.tools) n;


Output:

NAME
AMY AMY AMY

COLUMN_VALUE
HAMMER SLEDGE AXE

DAVID
DAVID

HAMMER
AXE
166

Nested Tables
A Table within a Table
create type ANIMAL_TY as object ( breed name birthdate VARCHAR2(25), VARCHAR2(25), DATE);

create type ANIMAL_NT as table of ANIMAL_TY; create table BREEDER ( breedername animals VARCHAR2(25), ANIMAL_NT)

nested table ANIMALS store as ANIMALS_NT_TAB;

167

Nested Tables
Insert Operation:
insert into BREEDER values (JANE,

ANIMALS_NT(
ANIMAL_TY(DOG, SCOOBY, 31-MAR-01), ANIMAL_TY(DOG, BUZO, 05-JUN-01), ANIMAL_TY(DOG, KATIE, 10-JUL-01)

));

Using Table Function:


insert into TABLE(select animals from BREEDER where breedername = JANE) values (ANIMAL_TY(CAT, JEMIMA, 01-AUG-02));

168

Nested Tables
Select Operation: Using Table Function:
select breedername, n.name, n.birthdate
from BREEDER, TABLE(breeder.animals) n; select breedername, n.name, n.birthdate

from BREEDER, TABLE(breeder.animals) n


where n.name = SCOOBY;

169

References
Column Objects vs. Row Objects:
Column objects are embedded objects represented as columns in tables Based on extensions of features already in database

Accessed via main table


E.g. Abstract datatypes, varying arrays, nested tables or LOBs

Row objects are referenced objects accessible via references from other objects
Used to create references between rows of different tables Not embedded in main table. Main table contains a reference to another table

E.g. Object tables

170

References
Object Tables and OIDs
Each row is an object Each row has an Object Identifier (OID) Value assigned by Oracle during creation of the row Rows can be referenced by other objects within the database using OID

OIDs are not re-used by Oracle


create type ANIMAL_TY as object ( breed VARCHAR2(25),

name
birthdate

VARCHAR2(25),
DATE);

create table ANIMAL of ANIMAL_TY;

171

References
Insert Operation:
insert into ANIMAL values ( ANIMAL_TY(MULE, FRANCES, 01-APR-02));

Select Operation:
select name from ANIMAL;

Update Operation:
update ANIMAL set birthdate = 01-MAY-01 where name = FRANCES;

Delete Operation:
delete from ANIMAL where name = FRANCES;

172

References
REF Function:
Allows reference to existing row objects Allows selection of OID assigned to each row Takes as input alias given to the object table and returns reference value (OID)

select REF(a) from ANIMAL a where name = FRANCES;

REF(a) -----------------------------------------------------------------------------------0000280209FFD8EC317DA111D6B008444456464GF2452525032

173

References
DEREF Function:
Opposite of REF Takes as input a reference value (OID) and returns the value of the row object create type ANIMAL_TY as object

( breed
name birthdate create table KEEPER ( keepername animalkept

VARCHAR2(25),
VARCHAR2(25), DATE);

create table ANIMAL of ANIMAL_TY; VARCHAR2(25), REF ANIMAL_TY);

174

References
DEREF Function:
insert into KEEPER select CATHERINE, REF(a) from ANIMAL a where name = FRANCES; select * from KEEPER; Output: CATHERINE 0000280209FFD8EC317DA111D6B008444456464GF2452525032

select DEREF(k.animalkept) from KEEPER k where keepername = CATHERINE; Output: ANIMAL_TY(MULE, FRANCES, 01-APR-02)
175

References
VALUE Function:
To see the same structures from a query of the ANIMAL object table

select VALUE(a) From ANIMAL a where name = FRANCES; Output: ANIMAL_TY(MULE, FRANCES, 01-APR-02)

Invalid Reference: delete from ANIMAL where name = FRANCES; => Produces a dangling REF

176

References
FK relationships vs. References:
create table CUSTOMER ( customer_id name NUMBER constraint CUSTOMER_PK PRIMARY KEY, VARCHAR2(25),

street
city state zip

VARCHAR2(50),
VARCHAR2(25), VARCHAR2(2), NUMBER);

create table CUSTOMER_CALL ( customer_id call_number call_date NUMBER, NUMBER, DATE,

constraint CUSTOMER_CALL_PK PRIMARY KEY(customer_id, call_number), constraint CUSTOMER_CALL_FK FOREIGN KEY(customer_id) REFERENCES CUSTOMER(customer_id));

177

References
FK relationships vs. References:
create type CUSTOMER_TY as object ( customer_id name street NUMBER, VARCHAR2(25), VARCHAR2(50),

city
state zip

VARCHAR2(25),
VARCHAR2(2), NUMBER);

create view CUSTOMER_OV of CUSTOMER_TY


with object identifier (customer_id) as select customer_id, name, street, city, state, zip from CUSTOMER;

178

References
FK relationships vs. References:
create view CUSTOMER_CALL as select MAKE_REF(CUSTOMER_OV, customer_id) customer_id, call_number, call_date from CUSTOMER_CALL; select DEREF(ccov.customer_id) from CUSTOMER_CALL_OV ccov

where call_date = trunc(sysdate);

179

Object PL/SQL
declare cust1 CUSTOMER_TY;

begin
select VALUE(cov) into cust1 from CUSTOMER_OV cov where customer_id = 1; dbms_output.put_line(cust1.name); dbms_output.put_line(cust1.street);

end;
declare newCust CUSTOMER_TY;

begin
newCust := CUSTOMER_TY(345, NewCust, Street, City, ST, 0); insert into CUSTOMER_OV values(newCust); end;

180

Large Objects
LONG character data, 2 GB LONG RAW binary data, 2 GB

CLOB character LOB, 4 GB


BLOB binary LOB, 4 GB NCLOB CLOB with multi-byte character set support BFILE binary file, read-only binary data stored outside database, size OS dependent create table PROPOSAL ( proposal_id recipient_name NUMBER(10) VARCHAR2(25), PRIMARY KEY,

proposal_name
short_description proposal_text budget

VARCHAR2(25),
VARCHAR2(1000), CLOB, BLOB,

cover_letter

BFILE)
181

Large Objects
storage(INITIAL 50K NEXT 50K PCTINCREASE 0) tablespace PROPOSALS LOB(proposal_text, budget) store as ( tablespace PROPOSAL_LOB storage(INITIAL 100K NEXT 100K PCTINCREASE 0) CHUNK 16K PCTVERSION 10 NOCACHE LOGGING);

CHUNK Space allocated for each LOB manipulation. Default 1K, upto 32 K

PCTVERSION Max % of overall LOB storage space used for creating new version of the LOB
NOCACHE Not stored in memory LOGGING All operations against the LOB will be recorded in redo log files

182

Large Objects
Initialization:
BLOB EMPTY_BLOB( ) CLOB/NCLOB EMPTY_CLOB( ) BFILE BFILENAME(<directory name>, <file name>);

create directory proposal_dir as /u01/proposal/letters;

insert into PROPOSAL values


(2, M/S ABC, Energy Billing System, NULL, EMPTY_CLOB(), EMPTY_BLOB(), BFILENAME(proposal_dir, p1.doc));

Using Subqueries:
insert into PROPOSAL select 3, M/S XYZ, Credit Card Billing System, NULL, proposal_text, budget, cover_letter from PROPOSAL

where proposal_id = 1;
183

String Functions:

Large Objects

SUBSTR select SUBSTR(proposal_text, 1, 10) from PROPOSAL where proposal_id = 1; INSTR select INSTR(proposal_text, new, 1, 1) from PROPOSAL where proposal_id = 3;

INITCAP select INITCAP(proposal_text) from PROPOSAL where proposal_id = 3;


LTRIM/RTRIM select LTRIM(proposal_text) from PROPOSAL where proposal_id = 1;

DBMS_LOB Package:
READ, WRITE COPY, APPEND ERASE

SUBSTR, INSTR, GETLENGTH, TRIM


COMPARE

184

Large Objects
READ:
declare locator_var amount_var offset_var number; output_var varchar2(10); begin amount_var := 10; offset_var := 1; select proposal_text into locator_var from PROPOSAL where proposal_id = 1; DBMS_LOB.READ(locator_var, amount_var, offset_var, output_var); DBMS_OUTPUT.PUT_LINE(Start of proposal text: || output_var); end; CLOB; number;

185

Large Objects
WRITE:
declare locator_var amount_var offset_var number; buffer_var varchar2(12); begin amount_var := 12; offset_var := 10; buffer_var := ADD NEW TEXT; select proposal_text into locator_var from PROPOSAL where proposal_id = 3 for update; DBMS_LOB.WRITE(locator_var, amount_var, offset_var, buffer_var); end;
186

CLOB; number;

Summary
Introduction Variable Declaration SQL in PL/SQL Conditional & Iterative Control Cursors Exception Handling Procedures & Packages Triggers ORDBMS

187

References
PL-SQL programming Scott Urman, et al http://www.orafaq.com/faqplsql.htm

188

You might also like