base de datos i - unicen · triggerstriggers o disparadores o disparadores ... un tiempo de...

23
Base de Datos I Base de Datos I SQL PROCEDURAL Triggers y Stored Procedures Ing. Gustavo A. Correa Reina – UNCPBA – 2008

Upload: phungdien

Post on 14-Oct-2018

216 views

Category:

Documents


0 download

TRANSCRIPT

Base de Datos IBase de Datos I

SQL PROCEDURAL Triggers y Stored Procedures

Ing. Gustavo A. Correa Reina – UNCPBA – 2008

PosibilitaPosibilita elel usouso dede códigocódigo proceduralprocedural conjuntamenteconjuntamente conconsentenciassentencias SQLSQL queque sonson almacenadasalmacenadas dentrodentro dede lala BDBD.. ElEl códigocódigoproceduralprocedural eses ejecutadoejecutado porpor elel DBMSDBMS cuandocuando eses invocadoinvocado(directa(directa oo indirectamente)indirectamente) porpor elel usuariousuario dede lala BDBD..

SQL ProceduralSQL Procedural

Ventajas:Ventajas:Aísla partes comunes existentes en las aplicaciones, delegándolas en el DBMS.

Desventajas:Desventajas:Cada proveedor de BD tiene su propio lenguaje procedural. El SQL-1999 incorporó estas características, Poco de lo definido anteriormente se ajustaba a un estándar.

Se puede utilizar SQL Procedural para definir:Se puede utilizar SQL Procedural para definir:

TriggerTrigger: Es un procedimiento que es invocado : Es un procedimiento que es invocado automáticamente por el DBMS en respuesta a un automáticamente por el DBMS en respuesta a un evento especifico de la BD. evento especifico de la BD.

SQL ProceduralSQL Procedural

StoredStored ProcedureProcedure: Es un procedimiento que es : Es un procedimiento que es invocado explícitamente por el usuario.invocado explícitamente por el usuario.

Función: definida por el usuario para realizar Función: definida por el usuario para realizar operaciones específicas sobre los datos, y pueden ser operaciones específicas sobre los datos, y pueden ser invocadas desde un invocadas desde un triggertrigger, , storedstored procedureprocedure o o explícitamente. explícitamente.

Extensiones Procedimentales:

Sentencias compuestas (agruparlas en bloques begin end)

Extensión en SQLExtensión en SQL--19991999

SQLSQL--1999 ha extendido el SQL1999 ha extendido el SQL--1992 en varios aspectos, uno de 1992 en varios aspectos, uno de ellos el procedural. ellos el procedural.

Sentencias compuestas (agruparlas en bloques begin end)

Declaración de variables y constantes.

Sentencias de Flujo de control:

If-then-else (elsif)WhileFor (itera sobre los elementos de una tabla resultado)Loop y repeat

• PL-SQL

• Oracle

• Transact-SQL

• SQL Server

Extensión en SQLExtensión en SQL--19991999

Distintos de tipos de códigos Distintos de tipos de códigos ProceduralesProcedurales. .

• SQL Server

• Sybase

•Java

• Oracle

• DB2

•.net

• SQL Server

• Oracle

Puede ser visto como una regla eventoPuede ser visto como una regla evento--condicióncondición--acción (ECA), acción (ECA), es decir, “cuando ocurre un evento se evalúa una condición, si es decir, “cuando ocurre un evento se evalúa una condición, si ésta es verdadera se ejecuta una acción”. ésta es verdadera se ejecuta una acción”.

TriggersTriggers o disparadoreso disparadores

En SQLEn SQL--1999 un 1999 un triggertrigger puede ser creado, modificado o puede ser creado, modificado o eliminado con las siguientes sentencias:eliminado con las siguientes sentencias:

CREATE TRIGGER

ALTER TRIGGER

DROP TRIGGER

Los componentes de un Los componentes de un triggertrigger son:son:

Un nombre único que identifica al trigger dentro de la base

Un evento de disparo asociado (INSERT, UPDATE o DELETE).

Un tiempo de activación que puede ser BEFORE o AFTER de la

Triggers Triggers –– componentescomponentes

Un tiempo de activación que puede ser BEFORE o AFTER de la ejecución del evento

En Oracle, granularidad que puede ser FOR EACH ROW o FOR EACH STATEMENT (opción por defecto)

Una condición que puede ser cualquier condición SQL válida

Una acción que puede ser un conjunto de sentencias SQL procedurales

Renombrar las tuplas temporarias con REFERENCING NEW AS y REFERENCING OLD AS

Características principales:Características principales:La acción puede ejecutarse antes (BEFORE) del evento disparador,

después de él (AFTER) o en vez de él ( INSTEAD OF, leer documen-tación del DBMS ).

La acción puede referirse a valores anteriores y nuevos que seinsertaron, eliminaron o actualizaron en el evento que desencadenó laacción.

Triggers Triggers –– características:características:

acción.

Los eventos de actualización pueden especificar un atributo particular oun conjunto de atributos ( Depende del DBMS ).

Una condición puede especificarse con una cláusula WHEN, y laacción se ejecutará sólo si se dispara la regla y si se cumple lacondición cuando ocurre el evento disparador.

El programador tiene la opción de especificar que la acción se realice (dependiendo del DBMS):

una vez para cada tupla modificada. una vez para todas las tuplas que cambian en una operación de la base de datos.

TriggersTriggers –– forfor eacheach rowrow –– forfor eacheach statementstatement

DNI Nombre Cuota

1 Juan 133

2 Gustavo 222

3 Pedro 452

4 Mariana 164

5 Silvina 223

update cliente set cuota = cuota * 1.2

where dni > 2;

Cantidad de tuplas Afectadas ?5 Silvina 223

Un trigger for each row, se ejecuta 3 veces, una por cada tupla.

Un trigger for each statement, se ejecuta 1 vez.

En SQLEn SQL--99 la sintaxis de un trigger es la siguiente:99 la sintaxis de un trigger es la siguiente:

CREATE [O REPLACE] TRIGGER <nombre del trigger>

BEFORE | AFTER <evento> ON <nombre-tabla> evento

[ REFERENCING OLD | NEW AS <nombre-ref>]

Triggers Triggers –– sintaxis:sintaxis:

[ REFERENCING OLD | NEW AS <nombre-ref>]

[ FOR EACH { ROW | STATEMENT} ]

[ WHEN < condición > ] condición

BEGINcuerpo del trigger acción

END;

Evento: INSERT, DELETE O UPDATE [ OF <lista-atributos>]

Ej: AFTER DELETE ON nombre_tablaAFTER UPDATE OF nombre_columna ON nombre_tabla

Condición: puede ser cualquier condición SQL válida. Sólo para disparadores a nivel de fila

Triggers (EventoTriggers (Evento--CondiciónCondición--Acción)Acción)

Operadores relacionales: <, <=, >, >=, =, <>Operadores lógicos: AND, OR, NOT

OLD, NEW ( Si están el en cuerpo del trigger se referencian como :OLD ó :NEW)

Acción: pueden ser un conjunto de sentencias SQL procedurales.

Para renombrar las tuplas temporarias usar REFERENCING NEW AS y REFERENCING OLD AS.

Se disparan automáticamente al producirse el evento

La acción del trigger es un procedimiento atómico (Si cualquiersentencia del cuerpo del trigger falla, la acción completa del trigger se deshace, incluyendo la sentencia que lo disparó).

No se pueden incluir sentencias del DDL, ni COMMINT ni ROLLBACK.

Triggers Triggers -- comportamientocomportamiento

ROLLBACK.

Un trigger BEFORE no debe contener sentencias SQL que alterendatos (INSERT, UPDATE, DELETE)

Varios triggers pueden activarse ante un mismo evento.

Hay bases en donde se puede especificar el orden.

Si la activación de un trigger T1 dispara otro trigger T2: se suspende la ejecución de T1, se ejecuta el trigger anidado T2 y luego se retoma la ejecución de T1.

CREATE TRIGGER Ejemplo-filaAFTER DELETE ON tabla1FOR EACH ROWWHEN ((OLD.nombre=’pepe’) OR (OLD.edad > 35))BEGIN

DELETE FROM tabla2 WHERE tabla2.cod=:OLD.cod;END;

Triggers Triggers -- ejemplosejemplos

END;

CREATE TRIGGER Ejemplo_sentenciaAFTER DELETE ON tabla1REFERENCING OLD AS anteriorBEGIN

DELETE FROM tabla2 WHERE tabla2.cod=anterior.cod;END;

Ejemplo en Oracle: Ejemplo en Oracle:

CREATE OR REPLACE TRIGGER ejemploBEFORE INSERT OR UPDATE OR DELETE ON tablaBEGIN

IF DELETING THEN

Triggers Triggers –– ejemploejemplo

IF DELETING THENAcciones asociadas al borrado

ELSIF INSERTING THENAcciones asociadas a la inserción

ELSEAcciones asociadas a la modificación

END IF;

END;/

RAISE_APPLICATION_ERROR (nro_error, mensaje); [-20000 y -20999]

CREATE OR REPLACE TRIGGER ejemplo

Triggers Triggers –– ejemploejemplo

Para chequeos de integridad: Para chequeos de integridad:

CREATE OR REPLACE TRIGGER ejemploBEFORE DELETE ON tablaFOR EACH ROWBEGIN

IF tabla.columna = valor_no_borrable THENRAISE_APPLICATION_ERROR(-20000,‘La fila no se puede borrar’);

END IF;...END;

CREATE OR REPLACE TRIGGER chequear_salarioCREATE OR REPLACE TRIGGER chequear_salarioBEFORE INSERT OR UPDATE ON empleadoBEFORE INSERT OR UPDATE ON empleadoFOR EACH ROWFOR EACH ROWWHEN (new.trabajo<>’presidente’)WHEN (new.trabajo<>’presidente’)DECLAREDECLARE

Triggers Triggers –– ejemploejemplo

Ejemplo : “chequear que el salario de los empleados se encuentre en Ejemplo : “chequear que el salario de los empleados se encuentre en el rango correcto”el rango correcto”

DECLAREDECLAREv_salariomin INTEGER;v_salariomin INTEGER;v_salariomax INTEGER;v_salariomax INTEGER;

BEGINBEGINSELECT MAX(salario), MIN(salario) FROM empleadoSELECT MAX(salario), MIN(salario) FROM empleadoINTO v_salariomin, v_salariomaxINTO v_salariomin, v_salariomax

FROM empleadoFROM empleadoWHERE trabajo=:new.trabajo;WHERE trabajo=:new.trabajo;IF :new.salario < v_salariomin OR :new.salario > v_salariomax THENIF :new.salario < v_salariomin OR :new.salario > v_salariomax THEN

RAISE_APPLICATION_ERROR(RAISE_APPLICATION_ERROR(--20001, ‘Sueldo fuera de rango’);20001, ‘Sueldo fuera de rango’);END IF;END IF;

END;END;

Ejemplo : “registrar las modificaciones de los salarios”Ejemplo : “registrar las modificaciones de los salarios”

CREATE TRIGGER SAVE_SALARY_CHANGECREATE TRIGGER SAVE_SALARY_CHANGE

AFTER UPDATE ON EMPLOYEE FOR EACH ROWAFTER UPDATE ON EMPLOYEE FOR EACH ROW

BEGINBEGIN

IF (:old.salary <> :new.salary) THENIF (:old.salary <> :new.salary) THEN

Triggers Triggers –– ejemploejemplo

IF (:old.salary <> :new.salary) THENIF (:old.salary <> :new.salary) THEN

INSERT INTO salary_historyINSERT INTO salary_history

(emp_no, change_date, updater_id, old_salary, percent_change)(emp_no, change_date, updater_id, old_salary, percent_change)

VALUES VALUES

(:old.emp_no, 'NOW', user, :old.salary, (:new.salary (:old.emp_no, 'NOW', user, :old.salary, (:new.salary -- :old.salary) * :old.salary) * 100 / :old.salary);100 / :old.salary);

ENDEND

CREATE [O REPLACE] PROCEDURE ProcedureName [<input parameters>]

AS

Stored Procedures en OracleStored Procedures en Oracle

[ <local variable declarations>]BEGIN <procedure statements>

END;

Declaración de Variables.Declaración de Variables.

VarName Type;

CREATE PROCEDURE SHIP_ORDER( PO_NUM CHAR(8) ) AS

Stored Procedures en OracleStored Procedures en Oracle

AS ord_stat CHAR(7); cust_no INTEGER; any_po NUMERIC(15,2);

BEGIN ….

END

Ejemplo:Ejemplo:

CREATE PROCEDURE ADJUST_SALARY_RANGE (FACTOR NUMERIC(18,2) )

ASBEGINUPDATE JOB

Stored Procedures en OracleStored Procedures en Oracle

UPDATE JOB SET MIN_SALARY = MIN_SALARY * FACTOR,

MAX_SALARY = MAX_SALARY * FACTOR;END;

Para ejecutarlo:

exec ADJUST_SALARY_RANGE(1.1);

Create procedure …AS

var1 empleado.nombre%type;var2 empleado.sueldo%type;cursor c1 is

select nombre, sueldo from empleado order by sueldo;begin

open c1;

Juan 900

Pedro 920

Federico 1200

Cursores en OracleCursores en Oracle

Para acceder a las tuplas resultantes de consulta:Para acceder a las tuplas resultantes de consulta:

open c1;

fetch c1 into var1,var2;var2 = var2 + 100;insert into registro ( sysdate, var1, var2 );

fetch c1 into var1,var2;fetch c1 into var1,var2;

fetch c1 into var1,var2;var2 = var2 * 1.2;insert into registro ( sysdate, var1, var2 );

close c1;end;

Viviana 1400

Fernando 1800

Mariano 1900

…. ….

Cursores en conjunto con LOOP:Cursores en conjunto con LOOP:

Create procedure ……..AS

var1 empleado.nombre%type;var2 empleado.sueldo%type;cursor c1 is

select nombre, sueldo from empleado;begin

Cursores en OracleCursores en Oracle

beginopen c1;

if c1%isopen thenloop

fetch c1 into var1,var2;exit when c1%notfound;var2 = var2 * 1.15;insert into registro ( sysdate, var1, var2 );

end loop; end if;

close c1;end;

Otra forma de usarlos:Otra forma de usarlos:

Create procedure ……AS var1 empleado%rowtype;beginfor var1 in (select * from empleado)

Cursores en OracleCursores en Oracle

for var1 in (select * from empleado)loopinsert into registro (sysdate, var1.sueldo * 1.5 );

end loop;end;