Base de Datos(Funciones, Vistas,Procedimientos Almacenados,Triggers)

19
“Año de la Consolidación del Mar de Grau” Escuela Tecnológica Superior de la Universidad Nacional de Piura (ETSUNP) Integrantes : Alama Vilela Daniel Bobadilla Ortiz Willian Ronald Carmen Santos Luis Pacherrez Jibaja Guillermo Curso : Base de Datos II Temas : - Funciones -Vistas -Procedimientos Almacenados -Triggers Profesor : Ing. José Moncada Morales PIURA- 2016

Transcript of Base de Datos(Funciones, Vistas,Procedimientos Almacenados,Triggers)

Page 1: Base de Datos(Funciones, Vistas,Procedimientos Almacenados,Triggers)

“Año de la Consolidación del

Mar de Grau”

Escuela Tecnológica Superior de la Universidad

Nacional de Piura (ETSUNP)

Integrantes : Alama Vilela Daniel

Bobadilla Ortiz Willian Ronald

Carmen Santos Luis

Pacherrez Jibaja Guillermo

Curso : Base de Datos II

Temas :

-Funciones

-Vistas

-Procedimientos Almacenados

-Triggers

Profesor : Ing. José Moncada Morales

PIURA- 2016

Page 2: Base de Datos(Funciones, Vistas,Procedimientos Almacenados,Triggers)

1. FUNCIONES: Las funciones SQL ejecutan una lista arbitraria de consultas SQL, devolviendo

los resultados de la última consulta de la lista. Las funciones SQL en general

devuelven conjuntos.

Una función es una rutina almacenada que recibe unos parámetros escalares de

entrada, luego los procesa según el cuerpo definido de la función y por ultimo

retorna en un resultado de un tipo específico que permitirá cumplir un objetivo.

A diferencia de MySQL las funciones definidas por el usuario en SQL Server

permiten retornar tablas en los resultados. Esta característica brinda al

programador facilidad a la hora de administrar sus bases de datos.

Existen 3 tipos:

• Funciones escalares

• Funciones con valores de tabla en línea

• Funciones con valores de tabla y múltiples instrucciones

La sintaxis de creación de las tres es muy similar, solo se diferencian en el tipo

de parámetros que retornan.

1.1. Funciones Escalares En SQL Server

Las funciones escalares son aquellas que reciben parámetros de entrada para

ser procesados y al final retornar en un tipo de dato sencillo. Cuando hablo de

sencillo me refiero a tipos de datos elementales como INT, FLOAT, VARCHAR,

etc.

SQL Server no permite que las funciones escalares retornen en los tipos text,

ntext, image, cursor y timestamp. Al igual que MySQL, usaremos la palabra

reservada RETURNS para indicar el tipo de dato en el cual retornará la función.

El cuerpo de una función escalar está contenido en un bloque de instrucciones

como en los procedimientos.

Ejemplo De Una Función Escalar De Una Aerolínea

A continuación, veremos un enunciado que debe ser solucionado con la creación

de una función escalar. El problema está basado en una base de datos de una

Aerolínea. Observa:

Averigüe cuantas veces ha viajado un pasajero en un lapso de tiempo. Use la

identificación del pasajero para consultar dicha información. En cuanto al lapso

de tiempo, especifique una fecha de inicio y una fecha final.

CREATE FUNCTION cuanto_ha_viajado(@idpasajero INT, @fecha_inicio

DATE , @fecha_final DATE)

RETURNS INT

AS

BEGIN

DECLARE @cantidad_ocasiones INT;

SELECT @cantidad_ocasiones = COUNT(a.idpasajero)

FROM Aerolinea.Boleto AS a

WHERE a.idpasajero = @idpasajero AND (fecha_compra BETWEEN

@fecha_inicio AND @fecha_final);

IF ( @cantidad_ocasiones IS NULL)

SET @cantidad_ocasiones = 0;

RETURN @cantidad_ocasiones;

END

Page 3: Base de Datos(Funciones, Vistas,Procedimientos Almacenados,Triggers)

1.2. Funciones Con Valores De Tabla En Línea

Este tipo de función tiene la misma sintaxis que una función escalar, la única

diferencia está en que retorna un tipo de dato TABLE, es decir, una tabla

compuesta de registros. Veamos la variación de la sintaxis:

CREATE FUNCTION nombre_función ([parámetro1, parámetro2,...])

RETURNS TABLE

[WITH ENCRYPTION | WITH SCHEMABINDING]

[AS]

RETURN (consulta_SELECT)

Las funciones que retornan tablas son muy útiles cuando tenemos consultas que

tengan JOINS debido a la reducción de complejidad.

Ejemplo De Función De Tabla Sobre Tienda Digital

Supón que tenemos una base de datos comercial de una Tienda Digital que

vende Hardware. Esta base de datos tiene la famosa relación entre clientes,

pedidos y artículos. El requerimiento dice así:

Consulte todas las compras realizadas de un producto específico. Use el código

del producto para generar los resultados y muestre el nombre del cliente que

compro ese producto, la fecha en que se compró, el precio que tenía en ese

momento y la cantidad comprada.

CREATE FUNCTION ventas_producto(@idproducto INT)

RETURNS TABLE

AS

RETURN(

SELECT C.NOMBRE, F.FECHA, DF.CANTIDAD, DF.PRECIO,P.IDPRODUCTO

FROM

CLIENTE AS C JOIN FACTURA AS F ON C.IDCLIENTE = F.IDCLIENTE

JOIN DETALLEFACTURA AS DF ON DF.IDFACTURA = F.IDFACTURA

JOIN PRODUCTO AS P ON P.IDPRODUCTO = DF.IDPRODUCTO

WHERE P.IDPRODUCTO = @idproducto)

La anterior función retorna en una tabla que representa todas las compras de un

producto realizadas hasta el momento por los clientes. Ahora podemos realizar

consultas sobre esta tabla, por ejemplo, si quisiéramos sumar el total de todas

las ventas del artículo con código 1003, podríamos hacer la siguiente consulta:

SELECT SUM(CANTIDAD*PRECIO) FROM ventas_producto(1003)

Con esa función la base de datos de nuestra tienda virtual de hardware ganará

velocidad de cálculo, además de ahorrar tiempo para los desarrolladores y

administradores.

Page 4: Base de Datos(Funciones, Vistas,Procedimientos Almacenados,Triggers)

1.3. Funciones Con Valores De Tabla Y Múltiples Instrucciones

Este tipo de funciones son similares a las funciones de tabla en linea, solo que

incluyen un bloque de sentencias para manipular la información antes de retornar

la tabla. Su sintaxis de creación es la siguiente:

CREATE FUNCTION nombre_función ( [parámetro1, parámetro2,...])

RETURNS @variable_tabla TABLE (nombre_columna tipo,...)

[WITH ENCRYPTION | WITH SCHEMABINDING]

[AS]

BEGIN

<bloque de instrucciones>

RETURN

END

La anterior definición parametriza la variable tipo TABLE en que retornará la

función. Es decir, definiremos cómo será su estructura antes de retornarla. Así

que debemos especificar cada parámetro y su tipo.

Ejemplo De Función Con Múltiple Instrucciones:

Fíjate en el siguiente enunciado:

Muestre todos los registros de la tabla EMPLEADO que tengan un salario mayor

o igual a un valor establecido como parámetro. Además de ello combine en un

solo campo el nombre y apellido del empleado y agregue un nuevo atributo que

muestre la cantidad de días que lleva el empleado desde su fecha de ingreso.

CREATE FUNCTION reporte1_empleados(@salarioemp INT)

RETURNS @tabla TABLE (

IDEMPLEADO INT PRIMARY KEY NOT NULL IDENTITY,

NOMBRE VARCHAR(200) NOT NULL,

SALARIO INT NOT NULL,

DIASLABORANDO INT NOT NULL)

AS

BEGIN

INSERT @tabla

SELECT E.NOMBRE+' '+E.APELLIDO,E.SALARIO,

DATEDIFF(DAY,E.FECHA_INGRESO,GETDATE())

FROM EMPLEADO AS E

WHERE E.SALARIO >= @salarioemp;

RETURN;

END

Con la anterior función retornamos en una nueva tabla personalizada como lo

pedía el enunciado. Nota que antes de escribir el bloque de instrucciones hemos

definido un variable tipo TABLE con una estructura de 4 columnas. Esta

definición se parece mucho a la sintaxis CREATE TABLE para crear tablas. Y al

final insertamos los datos con el formato que se pidió.

Si queremos ver que registros tiene la tabla retornada por la función, solo

realizamos una consulta de la siguiente forma.

SELECT * FROM reporte1_empleados (1000);

2. VISTAS: En teoría de bases de datos, una vista es una consulta que se presenta como una tabla

(virtual) a partir de un conjunto de tablas en una base de datos relacional.

Page 5: Base de Datos(Funciones, Vistas,Procedimientos Almacenados,Triggers)

Las vistas tienen la misma estructura que una tabla: filas y columnas. La única diferencia

es que sólo se almacena de ellas la definición, no los datos. Los datos que se recuperan

mediante una consulta a una vista se presentarán igual que los de una tabla. De hecho,

si no se sabe que se está trabajando con una vista, nada hace suponer que es así. Al

igual que sucede con una tabla, se pueden insertar, actualizar, borrar y seleccionar

datos en una vista. Aunque siempre es posible seleccionar datos de una vista, en

algunas condiciones existen restricciones para realizar el resto de las operaciones sobre

vistas.

Una vista se especifica a través de una expresión de consulta (una sentencia SELECT)

que la calcula y que puede realizarse sobre una o más tablas. Sobre un conjunto de

tablas relacionales se puede trabajar con un número cualquiera de vistas.

La mayoría de los SGBD soportan la creación y manipulación de vistas. Las vistas se

crean cuando se necesitan hacer varias sentencias para devolver una tabla final.

Las vistas se basan en una visión bases de datos de tres niveles, que lo componen:

Capa física: En el nivel inferior, se encuentran los datos reales almacenados en un disco.

Capa conceptual: Es la abstracción de las relaciones (o tabla) de los datos almacenados

en un disco.

Capa de lógica: la última capa es una abstracción por encima de las relaciones es lo

que se conoce como vistas (views).

Usos de las vistas:

Las vistas se emplean para:

Realizar consultas complejas más fácilmente: Las vistas permiten dividir la consulta en

varias partes.

Proporcionar tablas con datos específicos: Las vistas permiten ser utilizadas como

tablas que resumen todos los datos, así como también permiten ocultar ciertos datos.

Cuando ese se requiere un detalle que no corresponde precisamente a las relaciones.

Modularidad de acceso a base de datos: las vistas se pueden pensar en forma de

módulos que nos da acceso a partes de la base de datos. Cuando ese detalle que se

requiere no corresponde precisamente a las relaciones.

Las aplicaciones reales tienden a usar una o muchas vistas, por lo que cuanto más

grande es la aplicación, más necesario es que haya modularidad, para facilitar

determinadas consultas o para ocultar los datos. Las vistas entonces son el mecanismo

para alcanzar dichos objetivos.

En esta sección se proporciona la información necesaria para comprender, diseñar y

crear vistas.

Tema Descripción

Descripción

de vistas

Se explican los conceptos de vista, los tipos de vistas y los escenarios para

utilizar las vistas, con ejemplos.

Diseñar e

implementar

vistas

Se proporcionan directrices específicas para diseñar vistas estándar,

indizadas y con particiones, con vínculos a los temas necesarios para crear

vistas.

Modificar

vistas

Se describen los procedimientos y se incluyen los vínculos necesarios para

modificar la definición de una vista, modificar datos mediante una vista y

eliminar una vista.

Page 6: Base de Datos(Funciones, Vistas,Procedimientos Almacenados,Triggers)

En esta ilustración se muestra una vista basada en dos tablas.

2.1. Tipos de vistas.

Se pueden crear vistas estándar, vistas indizadas y vistas con particiones.

Vistas estándar:

La combinación de datos de una o más tablas mediante una vista estándar permite

satisfacer la mayor parte de las ventajas de utilizar vistas. Éstas incluyen centrarse en

datos específicos y simplificar la manipulación de datos.

Vistas indizadas:

Una vista indizada es una vista que se ha materializado. Esto significa que se ha

calculado y almacenado. Se puede indizar una vista creando un índice agrupado único

en ella. Las vistas indizadas mejoran de forma considerable el rendimiento de algunos

tipos de consultas. Las vistas indizadas funcionan mejor para consultas que agregan

muchas filas. No son adecuadas para conjuntos de datos subyacentes que se actualizan

frecuentemente.

Vistas con particiones:

Una vista con particiones junta datos horizontales con particiones de un conjunto de

tablas miembro en uno o más servidores. Esto hace que los datos aparezcan como si

fueran de una tabla. Una vista que junta tablas miembros en la misma instancia de SQL

Server es una vista con particiones local.

2.2. Para proporcionar compatibilidad con versiones anteriores

Las vistas permiten crear una interfaz compatible con versiones anteriores para una

tabla cuando su esquema cambia. Por ejemplo, una aplicación puede haber hecho

referencia a una tabla no normalizada que tiene el siguiente esquema:

Employee(Name, BirthDate, Salary, Department, BuildingName)

Para evitar el almacenamiento redundante de datos en la base de datos, puede

normalizar la tabla dividiéndola en las dos siguientes tablas:

Page 7: Base de Datos(Funciones, Vistas,Procedimientos Almacenados,Triggers)

Employee2(Name, BirthDate, Salary, DeptId)

Department(DeptId, BuildingName)

Para proporcionar una interfaz compatible con versiones anteriores que siga haciendo

referencia a los datos de Employee, puede eliminar la tabla Employee antigua y

reemplazarla por la siguiente vista:

CREATE VIEW Employee AS

SELECT Name, BirthDate, Salary, BuildingName

FROM Employee2 e, Department d

WHERE e.DeptId = d.DeptId

Las aplicaciones que realizaban consultas en la tabla Employee, ahora pueden obtener

sus datos desde la vista Employee. No es necesario cambiar la aplicación si sólo lee

desde Employee. A veces, las aplicaciones que actualizan Employee también pueden

admitirse agregando desencadenadores INSTEAD OF a la nueva vista para asignar

operaciones INSERT, DELETE y UPDATE en la vista a las tablas subyacentes.

2.3. Diseñar vistas indizadas

La capacidad del optimizador de consultas para sacar partido de las vistas indizadas al

procesar consultas ha mejorado respecto a versiones anteriores en los casos en que la

definición tanto de la vista como de la consulta contienen los siguientes elementos

coincidentes:

• Expresiones escalares. Por ejemplo, el optimizador de consultas puede hacer

coincidir la siguiente consulta con una expresión escalar en su predicado:

SELECT ColA, ColB FROM TableT WHERE ColC * (ColD + 10) > 50

Para un índice creado en esta vista:

CREATE VIEW V1 WITH SCHEMABINDING AS

SELECT ColA, ColB, ColC * (ColD + 10) AS ExpCol

FROM dbo.TableT

Las expresiones escalares que incluyen funciones definidas por el usuario también

pueden coincidir de una manera parecida.

• Funciones de agregado escalares. Por ejemplo, la siguiente consulta que

contiene una función de agregado escalar en su lista SELECT:

SELECT COUNT_BIG (*) FROM dbo.TableT

Puede coincidir con un índice creado en esta vista:

CREATE VIEW V2 WITH SCHEMABINDING AS

SELECT COUNT_BIG (*) AS Cnt

FROM dbo.TableT

El optimizador de consultas también considerará lo siguiente al seleccionar un plan de

consulta:

Page 8: Base de Datos(Funciones, Vistas,Procedimientos Almacenados,Triggers)

• Si un intervalo de valores definido en un predicado de consulta está comprendido

dentro de un intervalo definido en una vista indizada. Por ejemplo, suponga que se crea

un índice en la siguiente vista:

CREATE VIEW V1 WITH SCHEMABINDING AS

SELECT ColA, ColB, ColC FROM dbo.TableT

WHERE ColA > 1 and ColA < 10

Ahora suponga la siguiente consulta:

SELECT ColB, ColC FROM dbo.TableT

WHERE ColA > 3 and ColA < 7

El optimizador de consultas haría coincidir esta consulta con la vista V1 porque el

intervalo entre 3 y 7 definido en la consulta está comprendido dentro del intervalo entre

1 y 10 definido en la vista indizada.

• La medida en que una expresión definida en una consulta es equivalente a la

definida en una vista indizada. SQL Server intenta hacer coincidir expresiones según

sus referencias de columna, literales, los operadores lógicos AND, OR, NOT, BETWEEN

e IN, y los operadores de comparación =, <>, >, <, >= y <=. No se tienen en cuenta los

operadores aritméticos, como + y %, ni los parámetros.

Por ejemplo, el optimizador de consultas haría coincidir la siguiente consulta:

SELECT ColA, ColB from dbo.TableT

WHERE ColA < ColB

Con un índice creado en esta vista:

CREATE VIEW V1 WITH SCHEMABINDING AS

SELECT ColA, ColB FROM dbo.TableT

WHERE ColB > ColA

Recuerde que, como en todos los índices, SQL Server sólo elige utilizar una vista

indizada en su plan de consulta si el optimizador de consultas determina que es útil

hacerlo.

2.4. Directrices para diseñar una vista indizada

Las vistas indizadas mejoran el rendimiento de los siguientes tipos de consultas:

• Las combinaciones y agregaciones que procesan muchas filas.

• Las operaciones de combinación y agregación realizadas frecuentemente por

muchas consultas.

Por ejemplo, en una base de datos de proceso de transacciones en línea (OLTP) que

registra inventarios, se espera que muchas consultas combinen las tablas

ProductMaster, ProductVendor y VendorMaster. Aunque las consultas que realizan esta

combinación no procesen muchas filas cada una, el proceso de combinación general de

cientos de miles de estas consultas puede ser significativo. Puesto que no es probable

Page 9: Base de Datos(Funciones, Vistas,Procedimientos Almacenados,Triggers)

que estas relaciones se actualicen frecuentemente, el rendimiento global del sistema se

puede mejorar con sólo definir una vista indizada que almacene los resultados

combinados.

• Las cargas de trabajo de la ayuda a la toma de decisiones.

Los sistemas de análisis se caracterizan por la capacidad de almacenar datos

agregados resumidos que no se actualizan con frecuencia. La posterior agregación de

datos y combinación de muchas filas caracteriza a muchas consultas de ayuda a la toma

de decisiones. Además, los sistemas de ayuda a la toma de decisiones contienen

ocasionalmente tablas anchas con muchas columnas o columnas que son muy grandes,

o ambas cosas a la vez. Las consultas que hacen referencia a un subconjunto estrecho

de estas columnas pueden aprovecharse de una vista indizada que sólo incluye las

columnas de la consulta, o bien un superconjunto estrecho de estas columnas. La

creación de vistas indizadas estrechas que contienen un subconjunto de las columnas

de una sola tabla se conoce como estrategia de partición vertical porque divide las tablas

verticalmente.

Por ejemplo, suponga la existencia de la siguiente tabla y vista indizada:

CREATE TABLE wide_tbl(a int PRIMARY KEY, b int, ..., z int)

CREATE VIEW v_abc WITH SCHEMABINDING AS

SELECT a, b, c

FROM dbo.wide_tbl

WHERE a BETWEEN 0 AND 1000

CREATE UNIQUE CLUSTERED INDEX i_abc ON v_abc(a)

La siguiente consulta puede responderse utilizando únicamente v_abc:

SELECT b, count_big(*), SUM(c)

FROM wide_tbl

WHERE a BETWEEN 0 AND 1000

GROUP BY b

La vista v_abc ocupa muchas páginas menos que la tabla wide_tbl. Por lo tanto, será

mucho mejor para el optimizador elegirla como ruta de acceso para resolver la consulta

anterior.

Si desea dividir verticalmente una tabla entera en lugar de sólo uno de sus subconjuntos,

es aconsejable utilizar un índice no agrupado en la tabla que use la cláusula INCLUDE

para incluir únicamente las columnas que desee, en lugar de una vista indizada.

Las vistas indizadas no suelen mejorar el rendimiento de los siguientes tipos de

consultas:

• Los sistemas OLTP con muchas escrituras.

• Las bases de datos con muchas actualizaciones.

• Las consultas que no incluyen agregaciones ni combinaciones.

Page 10: Base de Datos(Funciones, Vistas,Procedimientos Almacenados,Triggers)

• Las agregaciones de datos con un alto grado de cardinalidad para la clave

GROUP BY. Un alto grado de cardinalidad significa que la clave contiene muchos

valores diferentes. Una clave única tiene el grado más alto de cardinalidad ya que cada

clave tiene un valor diferente. Las vistas indizadas mejoran el rendimiento mediante la

reducción del número de filas a las que tiene acceso una consulta. Si el conjunto de

resultados de la vista tiene casi tantas filas como la tabla base, lo que se gana en

rendimiento con respecto a la utilización de la vista es mínimo.

Por ejemplo, suponga que se realiza la siguiente consulta en una tabla con 1.000 filas:

SELECT PriKey, SUM(SalesCol)

FROM ExampleTable

GROUP BY PriKey

Si la cardinalidad de la clave de tabla es 100, una vista indizada que se genere mediante

el resultado de esta consulta sólo tendrá 100 filas. Las consultas que utilizan la vista

necesitarán una décima parte de las lecturas necesarias para la tabla base. Si la clave

es única, la cardinalidad de la clave es 1000 y el conjunto de resultados de la vista

devuelve 1000 filas. Si la vista y la tabla base ExampleTable tienen filas del mismo

tamaño, el rendimiento de una consulta no mejora utilizando esta vista indizada en lugar

de leer directamente la tabla base.

• Las combinaciones expandidas. Se trata de vistas cuyos conjuntos de resultados

son mayores que los datos originales de las tablas base.

Combinar vistas indizadas con consultas

Aunque las restricciones de los tipos de vistas que pueden indizarse pueden impedir

diseñar una vista que resuelva completamente un problema, cabe la posibilidad de

diseñar varias vistas indizadas más pequeñas que aceleren partes del proceso.

Considere el ejemplo siguiente:

• Una consulta de ejecución frecuente que agrega datos de varias tablas y, a

continuación, utiliza UNION para combinar los resultados. No se permite utilizar UNION

en una vista indizada. Se puede volver a diseñar vistas para realizar cada una de las

operaciones individuales de agregación. El optimizador puede seleccionar a

continuación las vistas indizadas para acelerar las consultas sin necesidad de volver a

codificarlas. Si bien no se mejora el procesamiento UNION, sí se mejoran los procesos

individuales de agregación.

Diseñe vistas indizadas que puedan satisfacer varias operaciones. Como el optimizador

puede utilizar una vista indizada aunque no está especificada en la cláusula FROM, una

vista indizada bien diseñada puede acelerar el procesamiento de muchas consultas.

Por ejemplo, considere la posibilidad de crear un índice en la siguiente vista:

CREATE VIEW ExampleView WITH SCHEMABINDING

AS

SELECT GroupKey, SUM(Colx) AS SumColx, COUNT_BIG(Colx) AS CountColx

FROM MyTable

GROUP BY GroupKey

Page 11: Base de Datos(Funciones, Vistas,Procedimientos Almacenados,Triggers)

Esta vista no sólo puede satisfacer consultas que hagan referencia directa a las

columnas de la vista, sino que también puede utilizarse para satisfacer consultas que

se realizan en la tabla base y contienen expresiones como SUM(Colx),

COUNT_BIG(Colx), COUNT(Colx) y AVG(Colx). Todas estas consultas serán más

rápidas porque sólo deben recuperar un número reducido de filas de la vista, en lugar

de leer el número total de filas de las tablas base.

De forma similar, una vista indizada que agrega datos y grupos cada día puede utilizarse

para satisfacer las consultas que se agregan durante distintos intervalos de más de 1

día, por ejemplo 7, 30 ó 90 días.

3. PROCEDIMIENTOS ALMACENADOS Un procedimiento almacenado es un programa (o procedimiento) almacenado

físicamente en una base de datos. Su implementación varía de un gestor de base de

datos a otro. La ventaja de un procedimiento almacenado es que, al ser ejecutado, en

respuesta a una petición de usuario, es ejecutado directamente en el motor de bases de

datos, el cual usualmente corre en un servidor separado. Como tal, posee acceso directo

a los datos que necesita manipular y sólo necesita enviar sus resultados de regreso al

usuario, deshaciéndose de la sobrecarga resultante de comunicar grandes cantidades

de datos salientes Estos procedimientos, se usan a menudo, pero no siempre, para

realizar consultas SQL sobre los objetos de la base de datos de una manera abstracta,

desde el punto de vista del cliente de la aplicación.

Un procedimiento almacenado permite agrupar en forma exclusiva parte de algo

específico que se desee realizar o, mejor dicho, el SQL apropiado para dicha acción.

Un procedimiento almacenado es una consulta que se almacena en una base de datos

en SQL Server en lugar de almacenarse en el código cliente (normalmente C# o Java)

en el equipo cliente.

Creación de procedimientos almacenados (Store Procedures):

La instrucción general para crear procedimientos almacenados es la siguiente:

CREATE PROC nombre_proc parametros

AS

INSTRUCCION SQL

Es necesario aclarar, que un procedimiento almacenado puede recibir parámetros de

entrada y devolver parámetros de salida.

Ejemplo 1:

Instrucción SQL

USE AdventureWorks

Select name, Color, ListPrice, SellStartDate

FROM Production.Product

WHERE SellStartDate > '1/1/2003' ORDER BY SellStartDate, Name

Procedimiento con instrucción anterior:

CREATE PROCEDURE PROCE1#CARNET AS

Select name, Color, ListPrice, SellStartDate

FROM Production.Product

WHERE SellStartDate > '1/1/2003' ORDER BY SellStartDate, Name

GO

Page 12: Base de Datos(Funciones, Vistas,Procedimientos Almacenados,Triggers)

Para probar el nuevo procedimiento, abra una nueva consulta de SQL Server y escriba

y ejecute el código siguiente.

USE AdventureWorks

EXEC PROCE1#CARNE

Ejemplo2:

Utilizando parámetros de entrada:

Ya conocemos la sintaxis básica para la creación de procedimientos que es:

CREATE PROCEDURE NOMBRE AS

Sentencias:

Ahora si queremos utilizar parámetros de entrada antes de escribir el comando AS,

debemos digitar los datos que recibirá el procedimiento y el tipo de dato de la siguiente

manera:

CREATE PROCEDURE NOMBRE

@parametro1 tipo,@parametro2 tipo,…

AS

Los parámetros tienen que llevar de prefijo el símbolo de @, así cuando se llame el

procedimiento y se ingresen los parámetros, estos se almacenaran en el orden que se

declararon.

USE library

CREATE PROCEDURE ingreso

@apellido varchar(15), @nombre varchar(15) AS

insert into member(lastname,firstname)

values(@apellido,@nombre)

PRINT 'eL REGISTRO SE HA INGRESADO CORRECTAMENTE'

Como puede ver el procedimiento pide dos parámetros apellido y nombre del tipo

varchar, cuando se llame al procedimiento deberá digitarse primero el apellido y

después el nombre, porque ese es el nombre que se le ha fijado en el desarrollo del

procedimiento. Para llamar este procedimiento utilice la siguiente sentencia.

USE library

EXEC ingreso 'Moran','Gustavo'

Para comprobar que se ingreso el registro utilice la siguiente instrucción y busque el

registro que acaba de ingresar con el procedimiento.

Select * from member

Si alguien ingresa un valor nulo

EXEC ingreso '','Jose'

El procedimiento lo aceptara sin enviar ningún error, entonces podemos modificar el

procedimiento de la siguiente manera:

ALTER PROCEDURE ingreso

@apellido varchar(15), @nombre varchar(15)

AS

IF((@nombre='') OR (@apellido='')) BEGIN

PRINT 'NO SE PUEDEN INGRESAR VALORES NULOS' RETURN

END

ELSE BEGIN

insert into member(lastname,firstname)

values(@apellido,@nombre)

PRINT 'el REGISTRO SE HA INGRESADO CORRECTAMENTE'

END

Page 13: Base de Datos(Funciones, Vistas,Procedimientos Almacenados,Triggers)

Los BEGIN y END son el inicio y fin del if Y RETURN provoca la salida del procedimiento

tras enviar un mensaje a la pantalla del usuario.

Pruebe ingresar nuevamente EXEC ingreso '','Karla'

3.1. Reglas de procedimientos almacenados:

Entre las reglas para la programación de procedimientos almacenados, cabe citar las

siguientes:

• La propia definición CREATE PROCEDURE puede incluir cualquier número y

tipo de instrucciones SQL, excepto las siguientes instrucciones CREATE, que no

pueden ser utilizadas nunca dentro de un procedimiento almacenado:

CREATE DEFAULT CREATE TRIGGER

CREATE PROCEDURE CREATE VIEW

CREATE RULE

• Se puede crear otros objetos de base de datos dentro de un procedimiento

almacenado. Puede hacer referencia a un objeto creado en el mismo

procedimiento almacenado, siempre que se cree antes de que se haga referencia al

objeto.

• Puede hacer referencia a tablas temporales dentro de un procedimiento

almacenado.

• Si ejecuta un procedimiento almacenado que llama a otro procedimiento

almacenado, el procedimiento al que se llama puede tener acceso a todos los objetos

creados por el primer procedimiento, incluidas las tablas temporales.

• El número máximo de parámetros en un procedimiento almacenado es de 1,024.

• El número máximo de variables locales en un procedimiento almacenado está

limitado únicamente por la memoria disponible.

3.2. Uso de variables locales.

Una variable local de Transact-SQL es un objeto que contiene un valor individual de

datos de un tipo específico.

Las variables locales se definen debajo de la sentencia AS y llevan el prefijo DECLARE.

Create PROCEDURE ingreso2

@nombre varchar(15), @apellido varchar(15) AS

Declare n varchar(4) Declare a int

Ejemplo 3:

Con el procedimiento anterior se verifico lo de ingresar valores nulos, ahora vamos a

ver que el nombre completo del usuario (nombre y apellido) no debe repetirse en la base

de datos, para ello utilizamos el siguiente código.

ALTER PROCEDURE ingreso

@apellido varchar(15), @nombre varchar(15)

AS

DECLARE @nom varchar(15)—-variable local

DECLARE @ape varchar(15)—-variable local

--revisamos que las variables no sean nulas

--PRIMER IF EXTERNO si las variables son diferentes de null entra al if

--de lo contario sale y mande que no pueden ser valores nulos

IF((@nombre<>'') AND (@apellido<>'')) BEGIN

--guardamos el nombre y el apellido en las variables locales @non y @ape

SELECT @nom=firstname, @ape=lastname from member where

firstname=@nombre and lastname=@apellido

--IF INTERNO comparamos el valor capturado en @nom y @ape y los comparamos

--con los parámetros de entrada

IF((@nom=@nombre) AND (@ape=@apellido)) BEGIN

PRINT 'EL USUARIO YA EXISTE EN LA BASE DE DATOS'

Page 14: Base de Datos(Funciones, Vistas,Procedimientos Almacenados,Triggers)

RETURN

END--END DEL IF INTERNO ELSE--ELSE DEL IF INTERNO

BEGIN

INSERT INTO member(lastname,firstname)

values(@apellido,@nombre)

PRINT 'EL REGISTRO SE HA INGRESADO CORRECTAMENTE' END--END DEL

ELSE INTERNO

END--END DEL IF EXTERNO ELSE--ELSE DEL IF EXTERNO BEGIN

PRINT 'NO SE PUEDEN INGRESAR VALORES NULOS'

RETURN

END--END DEL ELSE EXTERNO

Intente ingresar el nombre y el mismo apellido con este procedimiento

exec ingreso 'Moran', 'Gustavo'

Procedimiento

Ejecute el siguiente Script

CREATE DATABASE bodega

GO

use bodega

GO

CREATE TABLE PRODUCTOS (

idprod char(7) PRIMARY KEY,

descripcion varchar(25), existencias int

)

CREATE TABLE PEDIDOS (

idpedido char(7), idprod char(7), cantidad int

FOREIGN KEY(idprod) REFERENCES PRODUCTOS(idprod)

)

La tabla productos contiene información general de los productos y la tabla pedidos

contiene la información del pedido que se realiza de un cierto producto.

Ejemplos de datos

PRODUCTOS

idprod descripcion existencias

Proc01 manzanas 10

PEDIDOS

idpedido idprod cantidad

Ped01 Proc01 2

1. Crear un procedimiento almacenado que ingrese los valores en la tabla

PRODUCTOS, y deberá verificar que el código del producto no exista para poder

insertarlo, en caso que el código del producto ya exista enviar un mensaje que diga

ESTE PRODUCTO YA HA SIDO INGRESADO.

2. Crear un procedimiento almacenado que permita realizar un pedido EN

LA TABLA PEDIDOS, este procedimiento deberá verificar si el código del producto

ingresado existe en la tabla PRODUCTO, además si la cantidad a pedir del producto es

mayor a la existencia del producto deberá enviar un mensaje que diga EXISTENCIA

DEL PRODUCTO INSUFICIENTE, en caso que la cantidad a pedir sea menor o igual

deberá modificar el valor de la existencia.

Ejemplo:

idprod descripcion existencias

Proc01 manzanas 10

Page 15: Base de Datos(Funciones, Vistas,Procedimientos Almacenados,Triggers)

Se realiza un pedido del producto Proc01 y se pide de cantidad 6, al terminar el

procedimiento el registro de ese producto deberá ser:

idprod descripcion existencias

Proc01 manzanas 4

Procedimientos almacenados (eliminar) Puede eliminar un procedimiento almacenado

cuando ya no lo necesite. Si un procedimiento almacenado llama a otro que ya ha sido

eliminado, Microsoft SQL Server mostrará un mensaje de error al ejecutar el

procedimiento que realiza la llamada. No obstante, si se define un nuevo procedimiento

almacenado con el mismo nombre y los mismos parámetros para reemplazar al que se

ha eliminado, los procedimientos almacenados que hagan referencia al antiguo se

ejecutarán correctamente. Los procedimientos almacenados se eliminan con "drop

procedure". Sintaxis: drop procedure NOMBREPROCEDIMIENTO;

Procedimientos almacenados (Buscar) Cuando comenzamos a dar soporte o

continuidad a un proyecto ya iniciado, es necesario conocer donde se encuentran

algunos elementos, en este caso si necesitamos realizar la búsqueda de instrucciones

en los procedimientos almacenados y no perder tiempo buscando en cada uno de los

procedimientos es recomendable utilizar las funciones de búsqueda que SQL nos

ofrece, a continuación, se mostrara como funciona y el resultado que arroja.

. - declare @search varchar(50) SET @search = 'TEXTO' SELECT ROUTINE_NAME

ROUTINE_DEFINITION FROM INFORMATION_SCHEMA.ROUTINES WHERE

ROUTINE_DEFINITION LIKE '%' + @search + '%' AND ROUTINE_TYPE

='PROCEDURE' ORDER BY ROUTINE_NAME

.- SELECT SUBSTRING(text,0,40) FROM syscomments WHERE text LIKE

'%BUSQUEDA%'

3.3. Procedimientos almacenados (Ingresar):

Para crear un procedimiento en SQL Server usaremos la sentencia CREATE

PROCEDURE. Como habíamos visto en el artículo de creación de procedimientos

almacenados, un procedimiento es un conjunto de instrucciones relacionadas con un

objetivo específico. Dichas instrucciones se guardan bajo un nombre en el servidor, para

ser utilizadas de nuevo en el futuro.

CREATE [PROCEDURE|PROC] nombre_procedimiento [#|##] [(parámetro1,

parámetro2, ...)] [{FOR REPLICATION|WITH RECOMPILE}][WITH ENCRYPTION]

AS<bloque de sentencias>

3.4. Procedimientos almacenados (Modificar)

Usaremos ALTER PROCEDURE para modificar procedimientos en SQL Server. Con

esta sentencia se busca cambiar el cuerpo y las características de un procedimiento ya

creado: ALTER PROCEDURE nombre_procedimiento <nuevas características> AS

<nuevo bloque de instrucciones>

Vamos a, modificar un procedimiento llamado modificar_cliente, el cual actualiza los

datos de los registros de una tabla llamada CLIENTE. Lo que haremos será agregarle

la cláusula WITH ENCRYPTION para que el procedimiento sea encriptado, ya que no

lo está. Veamos:

ALTER PROCEDURE modificar_cliente (@id_cliente INT, @nombre_cliente

VARCHAR(20),@apellido_cliente VARCHAR(20)) WITH ENCRYPTION AS UPDATE

CLIENTE SET NOMBRE=@nombre_cliente,APELLIDO=@apellido_cliente WHERE

IDCLIENTE=@id_cliente;

Page 16: Base de Datos(Funciones, Vistas,Procedimientos Almacenados,Triggers)

4. TRIGGERS - (DML - DDL) Son procedimientos almacenados que se ejecutan automáticamente ante un evento

DML (Update – Delete – Insert) que afecta una tabla o vista.

- Se los puede utilizar para, una vez desencadenados:

- Forzar reglas de negocio

- Mantener la integridad de datos

- Crear otras tablas

- Ejecutar complejas instrucciones SQL

La integridad debiera ser forzada al nivel más bajo por índices que formen parte de un

Primary Key o Foreing Key contraints.

-Los CHECK Constraints son otra alternativa

-Para asegurar la Integridad Referencial nada mejor que los Foreing Key

-Los DML TRIGGERS son especialmente utilizados cuando,con el simple uso de un

constraint, no se cubren las necesidades de una aplicación.

4.1. Consideraciones Generales y Beneficios:

* No se pueden invocar por si mismos, se disparan automáticamente

* No reciben ni retornan parámetros

* A diferencia de los constraint “check” pueden hacer referencia a otras tablas

(por ejemplo se puede controlar una inserción en una tabla de ventas si y solo si el valor

de un campo stock de una tabla artículos sea mayor a x cantidad)

* Se pueden crear más de un trigger para un mismo evento en una tabla, con lo

cual se pueden controlar múltiples alternativas sobre la misma tabla.

* Permiten evaluar el estado de una tabla antes y después de una modificación y

tomar acciones acordes a la evaluación

* Permiten customizar mensajes de error, algo que los constraints en general no

permiten.

Sintaxis:

CREATE TRIGGER <Nombre del Trigger>

ON <Nombre de la Tabla>

AFTER <INSERT,DELETE,UPDATE>

AS

BEGIN

SET NOCOUNT ON;

-- Inserta aquí las instrucciones

END

Page 17: Base de Datos(Funciones, Vistas,Procedimientos Almacenados,Triggers)

4.2. Consideraciones Adicionales:

- Los triggers DML utilizan dos tablas especiales denominadas Inserted y Deleted.

- Son tablas creadas automáticamente por el SQL con la misma estructura que la

tabla sobre la cual está definido el trigger

- La tabla Inserted solo tiene datos en operaciones de Insert y Update

- La tabla Deleted sólo tiene datos en operaciones de Delete y Update

- En caso de un update las tablas Inserted y Deleted tienen data al mismo tiempo.

- No se pueden modificar los datos de estas tablas

Ejemplos:

a) Se graba un histórico de stock cada vez que se modifica un artículo de la tabla

“artículos

-- TRIGGER DML

-- Detalle: este trigger genera un histórico de stock cada vez

que se modifica la existencia de un artículo --

-----------------------------------------------------------------

CREATE TRIGGER TR_ARTICULOS

ON ARTICULOS

AFTER UPDATE

AS

BEGIN

INSERT INTO HCO_STOCK

(IDARTICULO, STOCK, FECHA)

SELECT IDARTICULO, STOCK, getdate()

FROM INSERTED

END

--- Con este evento UPDATE se desencadena el Trigger

UPDATE ARTICULOS

SET STOCK = STOCK + 10

WHERE IDARTICULO = 1

Page 18: Base de Datos(Funciones, Vistas,Procedimientos Almacenados,Triggers)

2) Podemos hacer que el trigger del ejemplo 1 se desencadene sólo si una columna

es afectada

CREATE TRIGGER TR_ARTICULOS

ON ARTICULOS

AFTER UPDATE

AS

BEGIN

IF UPDATE (STOCK) -- sólo si actualiza STOCK

BEGIN

INSERT INTO HCO_STOCK

(IDARTICULO, STOCK, FECHA)

SELECT IDARTICULO, STOCK, getdate()

FROM INSERTED

END

END

3) Podemos hacer que el trigger deshaga toda la operación incluyendo un ROLLBACK

CREATE TRIGGER TR_ARTICULOS

ON ARTICULOS

AFTER UPDATE

AS

BEGIN

INSERT INTO HCO_ARTICULOS

(IDARTICULO, STOCK, FECHA)

SELECT IDARTOCULO, STOCK, getdate()

FROM INSERTED

ROLLBACK

END

4) Podemos DESACTIVAR/ACTIVAR un Trigger o Todos lo Triggers de la tabla

-- Desactivar y Activar Todos los Triggers de una Tabla --

---------------------------------------------------------

-- Desactiva todos los trigger de la tabla ARTICULOS

ALTER TABLE ARTICULOS DISABLE TRIGGER ALL

GO

Page 19: Base de Datos(Funciones, Vistas,Procedimientos Almacenados,Triggers)

-- Activa todos los trigger de la tabla ARTICULOS

ALTER TABLE ARTICULOS ENABLE TRIGGER ALL

----------------------------------------------------

-- Desactivar y Activar Un Trigger en Particular --

---------------------------------------------------

-- Desactiva el trigger TR_STOCK

DISABLE TRIGGER TR_STOCK ON ARTICULOS

GO

-- Activa el trigger TR_STOCK

ENABLE TRIGGER TR_STOCK ON ARTICULOS

GO

2.5. DDL Triggers

· Son triggers especiales que se crean a nivel de base de datos y que disparan en

respuesta a eventos DML (Update – Delete – Insert)

· Suelen ser utilizados para ejecutar tareas administrativas en una base de datos

auditando y regulando cierta clase de eventos.

· Sintaxis:

CREATE TRIGGER <Nombre del Trigger>

ON DATABASE

FOR <DROP TABLE, ALTER TABLE>

AS

BEGIN

SET NOCOUNT ON;

-- Inserta aquí las instrucciones

END

Ejemplos:

1) El siguiente trigger impide que sentencias DROP TABLE y ALTER TABLE a nivel

de Base de Datos

CREATE TRIGGER TR_Seguridad

ON DATABASE FOR DROP_TABLE, ALTER_TABLE

AS

BEGIN

RAISERROR ('No está permitido borrar ni modificar tablas !' , 16, 1)

ROLLBACK TRANSACTION

END