Apostila de
Programao de SGBD
ndice
ndice................................................................................................................................................................2
I. Conceitos bsicos........................................................................................................................................4
pg: 2
D
Programao de SGBD
Introduo.....................................................................................................................................................4
II PL/SQL _ Estrutura Bsica..........................................................................................................................5
Estrutura de um bloco PL/SQL (annimo)..................................................................................................6
Tipos de sub-rotinas de banco de dados.......................................................................................................8
Procedimentos..........................................................................................................................................9
Funes.....................................................................................................................................................9
Gatilhos...................................................................................................................................................10
Diferena entre blocos annimos e sub-rotinas.........................................................................................10
Variveis, constantes e tipos de dados........................................................................................................12
Operadores..................................................................................................................................................13
Variveis especiais......................................................................................................................................13
Estruturas de controle de fluxo de programa.............................................................................................14
IF .. END IF............................................................................................................................................14
LOOP ... EXIT [WHEN ...] ... END LOOP...........................................................................................15
WHILE ... LOOP ... END LOOP...........................................................................................................15
FOR... IN ... LOOP ... END LOOP........................................................................................................16
III PL/SQL construes principais.................................................................................................................17
Cursores explcitos.................................................................................................................................18
Manipulao de erros.................................................................................................................................25
Triggers.......................................................................................................................................................27
IV Estudo de caso...........................................................................................................................................29
Exerccio proposto..................................................................................................................................42
ABS( <expN> ).......................................................................................................................................44
ADD_MONTHS( <expD>, <expN> )...................................................................................................44
ASCII( <expC> )....................................................................................................................................44
AVG([ DISTINCT | ALL] <expN> )......................................................................................................44
CEIL( <expN> ).....................................................................................................................................44
CHARTOROWID(<expC> )..................................................................................................................44
CHR( <expN> )......................................................................................................................................45
COUNT([DISTINCT | ALL] {* I <exp> })..........................................................................................45
CONVERT( <expC> [, destino[,fonte]])................................................................................................45
DECODE ( <exp> , <exp1> , <exp2>, [,<exp3>]).............................................................................45
DUMP( <exp> [,formato[, expl1[, expl2]]])..........................................................................................46
FLOOR( <expN> ).................................................................................................................................47
GREATEST( <exp>,...)..........................................................................................................................47
INITICAP( <expC> ).............................................................................................................................47
INSTR( <expC1>, <expC2> [, <expI> [,expI]])...................................................................................47
LAST_DAY( <expD> )..........................................................................................................................47
LEAST( <exp>,... )................................................................................................................................48
LENGTH( <expC> )..............................................................................................................................48
LOWER( <expC> )................................................................................................................................48
LPAD( <expC1> , <expI>[, <expC2>]).................................................................................................48
LTRIM( <expC1> [, <expC2>] )...........................................................................................................48
MAX( [ DISTINCT | ALL ] <exp> )......................................................................................................49
MIN( [ DISTINCT | ALL ] <exp> ).......................................................................................................49
MOD( <expN1>, <expN2> )..................................................................................................................49
MONTHS_BETWEEN( <expD1>, <expD2> ).....................................................................................49
NEW_TIME( <expD>, <expC1>, <expC2> ).......................................................................................49
NEXT_DAY( <expD>, expC )...............................................................................................................50
NLSSORT( <expC> ).............................................................................................................................50
NVL( <exp1>, <exp2> )........................................................................................................................50
POWER( <expN>, <n> )......................................................................................................................50
REPLACE( <expC1>, <expC2>[, <expC3>] )......................................................................................51
ROUND( <expD> [, formato ])..............................................................................................................51
ROUND( <expN> [, <expI> ] )..............................................................................................................51
ROWIDTOCHAR( <ROWID> )............................................................................................................51
RPAD( <expC1>, <expI> [,<expC2> )..................................................................................................52
RTRIM( <expC1> [,<expC2> )..............................................................................................................52
pg: 3
D
Programao de SGBD
SIGN( <expN> ).....................................................................................................................................52
SOUNDEX( <expC> )...........................................................................................................................52
SQRT( <expN> )....................................................................................................................................52
STDDEV ([ DISCTINT | ALL<expN>).................................................................................................53
SUBSTR( <expC> , <expI1> [,<expI2>)...............................................................................................53
SUM( [DISTINCT | ALL] <expN> ).....................................................................................................53
TO_CHAR( <expN> [, formato ])..........................................................................................................53
TO_CHAR( <expD> [, formato ])..........................................................................................................53
TO_DATE( <expC> [, formato ])...........................................................................................................54
TO_NUMBER( <expC> )......................................................................................................................54
TRANSLATE( <expC1> , <expC2>, <expC3>)...................................................................................54
TRUNC( <expN> [, n ] )........................................................................................................................54
TRUNC( <expD> [, formato ] ).............................................................................................................55
UPPER( <expC> )..................................................................................................................................55
USERENV( <opo> )...........................................................................................................................55
VARIANCE( [ DISTINCT | ALL ] <expN> )........................................................................................56
VSIZE( <exp> )......................................................................................................................................56
Converso de tipo de dados........................................................................................................................56
Lista Nmero 1...................................................................................................................................57
ento valorConsulta = VrHonor * 0.8....................................................................................58
Ento valorConsulta = VrHonor * 0.7....................................................................58
Lista Nmero 2...................................................................................................................................59
pg: 4
Programao de SGBD
I. Conceitos bsicos
Introduo
Um nmero muito grande de operaes pode ser executado sobre um banco de dados atravs de
comandos SQL. Algumas dessas operaes podem ser bastante complexas, envolvendo um grande nmero
de tabelas e consultas, com aninhamento de comandos inclusive. Esses recursos da SQL no so
suficientes, entretanto, para solucionar muitos problemas comerciais tpicos, uma vez que a SQL no
oferece recursos de programao estruturada, como loopings e desvios, por exemplo. Por esse motivo, os
principais fornecedores de SGBDs criaram suas prprias extenses procedurais SQL (como a PL/SQL no
Oracle ou a Transact SQL no SQL Server), de maneira a prover recursos de programao em seus
gerenciadores. Essas extenses so verdadeiras linguagens de programao embutidas no SGBD, porm
so proprietrias, ou seja, variam de um produto para outro, apesar de implementarem alguns conceitos
bsicos comuns.
Assim, temos a implementao da SQL nos diversos gerenciadores de banco de dados ocorrendo
basicamente em 3 nveis, conforme a figura a seguir:
SQL padro
Extenses no
procedurais
SQL
Extenses
procedurais
SQL
No primeiro nvel, chamado de SQL padro na figura, h uma uniformidade na sintaxe de certos
recursos SQL, atravs de padronizaes internacionais controladas por rgos especiais como ANSI, ISO,
X-Open, etc. Entram nesta categoria uma grande parte dos comandos DML SQL, de maneira que a
sintaxe e o funcionamento de um SELECT por exemplo, tanto no Oracle como no SQL Server ou MSAccess so iguais para a maioria das consultas bsicas.
Para prover capacidades mais amplas em seus produtos, os fornecedores muitas vezes acrescentam
recursos adicionais ao mecanismo bsico, como por exemplo funes de agregao extras (para clculo de
desvio padro ou varincia, por exemplo), manipulao de strings, tipos de dados, tamanho de registro,
clusulas extras em comandos, etc. Esses recursos variam muito de um SGBD para outro, o que significa
que solues que os utilizem podem no funcionar em outros ambientes de banco de dados e so
representados na figura como Extenses no procedurais SQL.
O terceiro nvel, indicado como Extenses procedurais SQL representa a linguagem de
programao procedural suportada pelo SGBD, e constitui o tema desta apostila.
Com os recursos fornecidos pelas extenses procedurais dos gerenciadores de banco de dados
possvel construir rotinas de diversos tipos que funcionam dentro do SGBD, implementando operaes de
lgica mais complexa e capacidades de processamento linha a linha. Neste material utilizaremos como
pg: 5
Programao de SGBD
D
referncia o Oracle 7.3 Server e sua linguagem de programao, chamada PL/SQL (Procedural Language /
SQL).
Dentro de um arquivo texto na forma de um bloco annimo. Este tipo de bloco no cadastrado no
dicionrio de dados e sua execuo determinada atravs da chamada ao arquivo no qual ele se
encontra.
Declarado na forma de uma sub-rotina de banco de dados.
pg: 6
Programao de SGBD
D
DECLARE
BEGIN
EXCEPTION
END;
Exemplo 1:
Declare
wcarga_horaria number(5);
Begin
select carga_horaria into wcarga_horaria
from curso
where cod_curso = 5;
if wcarga_horaria is null then
update curso
set carga_horaria = 72;
commit;
end if ;
exception
when no_data_found then
insert into tab_erro values ( valor no encontrado);
end;
Observaes:
As palavras chaves Begin, End e Declare no so seguidas de ponto e vrgula.
As regras de sintaxe PL/SQL so semelhantes s do SQL:
Linhas de comando podem ser subdivididas
No podem ser usadas palavras reservadas.
Identificadores devem comear com uma letra e conter at 30 caracteres.
Campos de caracteres e datas devem ser usados entre aspas simples.
Comentrios devem ser delimitados por /* * /
So permitidos os comandos select, insert, delete, update
pg: 7
D
Programao de SGBD
Exerccio:
Testar o bloco PL/SQL do exemplo acima.
Inicialmente defina as tabelas Curso e tab_erro.
Depois execute o bloco sem a existncia do curso com cod = 5.
Inclua o curso com cdigo 5 e teste novamente.
pg: 8
Programao de SGBD
Usurio
Aplicao final
SGBD
Subrotina
Banco de Dados
Cliente
Servidor
Observe que a subrotina executada pelo SGBD, na mquina servidora, a pedido da estao
cliente.
pg: 9
Programao de SGBD
Procedimentos
Tambm chamados de procedimentos armazenados (stored procedures), representam pores de
cdigo SQL e no SQL que ficam armazenados de forma compilada no catlogo do SGBD e so ativados
explicitamente por aplicaes, triggers ou outras rotinas. Como nas linguagens tradicionais de
programao, um procedimento realiza um processamento qualquer e no devolve valor algum em seu
final.
Exemplo:
Ativao
Procedimento
EXEC CrDep(D8,COMPRAS)
Funes
A exemplo das procedures, as funes contm pores de cdigo SQL e no SQL; ficam
armazenadas de forma compilada no catlogo do SGBD e so ativadas explicitamente por aplicaes,
triggers ou outras rotinas. A diferena bsica entre o procedimento e a funo que uma funo, ao
realizar um processamento, produz um valor que devolvido (retornado) em seu final.
Exemplo:
Ativao
Funo
Ou
SELECT NmFunc,
CalcDobro( VrSalario )
FROM Funcionario ;
p2 NUMBER ;
BEGIN
p2 := p1 * 2 ;
RETURN p2 ;
END ;
pg: 10
Programao de SGBD
Gatilhos
Um gatilho (ou trigger) uma poro de cdigo composto por instrues SQL e no-SQL que
ficam armazenados no catlogo do SGBD e que so ativados automaticamente pelo gerenciador de banco
de dados quando um determinado evento ocorre. Em princpio um gatilho poderia ser entendido como
uma procedure ativada implicitamente pelo SGBD.
Exemplo:
Ativao
Gatilho
Neste material utilizaremos o termo Trigger para referenciar os gatilhos de banco de dados.
Exemplo 2:
001
002
003
004
005
006
007
008
009
010
011
012
013
014
015
016
017
018
019
020
021
022
023
-- Codigo p/ Update
BEGIN
vData := SYSDATE ;
UPDATE Funcionario
SET VrSalario = VrSalario * vPerc, DtUltAlt = vData
WHERE CdDepto = vDepto ;
INSERT INTO LogFunc ( DtOp, Usuario, Chave, CdOp )
VALUES ( vData, USER, VRSALARIO, cCdOp ) ;
COMMIT ;
-- Tratamento de excecoes
EXCEPTION
WHEN NO_DATA_FOUND THEN
raise_application_error ( 0001, Depto nao cadastrado ) ;
WHEN VALUE_ERROR THEN
raise_application_error ( 0002, Salario invalido ) ;
1
0
pg: 11
Programao de SGBD
024
WHEN OTHERS THEN
025
raise_application_error ( 9999, Erro geral ) ;
026 END ;
Esse exemplo representa um mdulo PL / SQL tpico (uma procedure, no caso), e permite
visualizar 4 regies bsicas, conforme o esquema:
Assinatura da rotina
(opcional)
Linha 001
rea de declaraes
(opcional)
rea de instrues
(obrigatria)
rea de excees
(opcional)
Exerccio 2:
Com base no modelo da vdeo-locadora definido em aulas anteriores, calcular o valor da multa na
devoluo da locao, considerando R$2,00 reais por dia de atraso. Atualizar a tabela de locao (campo
valorloc acrescido do valor da multa). O nmero da locao deve ser passado como parmetro. Usar
exception para testar se o nmero da locao no existe gravando mensagem de erro (tab_erro).
1
1
pg: 12
Programao de SGBD
Subtipos
DEC,
DECIMAL,
DOUBLE,
PRECISION, FLOAT, INT, INTEGER,
NUMERIC, REAL, SMALLINT
NATURAL, POSITIVE
CHAR
VARCHAR2
CHARACTER, STRING
VARCHAR
DATE
BOOLEAN
RECORD
TABLE
Descrio
Permite criar variveis ou constantes que
armazenem nmeros fixos ou de ponto
flutuante com preciso de at 38 dgitos.
Indicado para a criao de variveis ou
constantes que armazenem nmeros
inteiros com sinal, de forma a acelerar
algumas operaes com inteiros no
Oracle. A faixa de valores vlidos vai de
-231-1 at 231-1.
Permite texto de tamanho fixo at 32Kb.
Permite texto de tamanho varivel de at
32Kb.
Utilizado para armazenar datas, horas,
minutos e segundos.
Indicado para valores lgicos TRUE e
FALSE.
Utilizado para construir tipos complexos
estruturados, como imagens de registros
de tabelas, por exemplo.
Utilizado para conter conjuntos de dados
com vrias ocorrncias.
possvel tambm utilizar os atributos especiais %TYPE e %ROWTYPE para fazer com que uma
varivel ou constante herde o tipo de dado de um campo ou registro de tabela. Observe os exemplos a
seguir.
Exemplo 1:
DECLARE
NmUser
TxUnica
DtSist
QtFunc
VrSalario
QtCaixas
VARCHAR2( 30 ) ;
CONSTANT INTEGER := 2 ;
DATE := SYSDATE ;
NUMBER( 5, 0 ) ;
Funcionario.VrSalario%TYPE ;
QtFunc%TYPE ;
Exemplo 2:
DECLARE
TYPE RegCargo IS RECORD
( CdCargo CHAR( 2 ) NOT NULL := 0 ,
NmCargo CHAR( 30 ));
vCargo
RegCargo
1
2
pg: 13
Programao de SGBD
D
Exemplo 3:
DECLARE
RegFunc
Funcionario%ROWTYPE ;
Exemplo 4:
DECLARE
TYPE TabNrMatr IS TABLE OF CHAR(4) INDEX BY BINARY_INTEGER
;
vNrMatr
TabNrMatr ;
Operadores
A tabela abaixo apresenta o conjunto de operadores do PL / SQL.
Operador
+
*
/
**
=
>
<
>=
<=
<>
^=
!=
||
:=
-/*
*/
Significado
Adio
Subtrao
Multiplicao
Diviso
Exponenciao
Igual a
Maior que
Menor que
Maior ou igual a
Menor ou igual a
Diferente de
Diferente de
Diferente de
Concatenao de caracteres
Atribuio
Incio de comentrio (at fim da linha)
Incio de comentrio
Final de comentrio
Variveis especiais
Em um ambiente de programao Oracle existem disponveis para o programador algumas
variveis especiais bastante interessantes para determinadas aplicaes.
Varivel
USER
SYSDATE
UID
Tipo de Dado
Caracter
Date
Caracter / Number
Contedo
Nome do usurio corrente
Data e hora atuais do sistema
Nmero de identificao do usurio corrente
1
3
pg: 14
Programao de SGBD
Quando for necessrio obter o valor de uma dessas variveis a partir de um comando SELECT que
no referencia diretamente nenhuma tabela ou view normal do banco de dados, deve-se indicar a tabela
especial DUAL na clusula FROM do comando, conforme o exemplo a seguir.
SELECT SYSDATE, USER FROM Dual ;
IF .. END IF
utilizado para permitir que o fluxo do programa seja desviado para um determinado ponto da
lgica, conforme o resultado de uma comparao feita. Existem 3 variaes desta estrutura, cobrindo
desde o caso mais simples at possibilidades de desvio mltiplo.
Variao 1: Desvio simples, sem clusula ELSE
IF <expL> THEN
<operao1> ;
...
<operaoN> ;
END IF ;
;
;
;
1
4
pg: 15
Programao de SGBD
D
<operaoN> ; ]
END IF ;
Exemplo 1:
LOOP
<operao1> ;
...
<operaoN> ;
EXIT [ WHEN <expL> ] ;
<operaoN + 1> ;
...
END LOOP ;
...
LOOP
...
vCont := vCont + 1 ;
IF vCont > 10 THEN
EXIT ;
END IF ;
...
END LOOP ;
...
Exemplo 2:
...
LOOP
...
vCont := vCont + 1 ;
EXIT WHEN vCont > 10 ;
...
END LOOP ;
...
Exemplo:
...
vCont := 1 ;
WHILE vCont <= 10 LOOP
...
vCont := vCont + 1 ;
...
END LOOP ;
...
1
5
pg: 16
Programao de SGBD
...
FOR vCont IN 1 .. 10 LOOP
...
...
END LOOP ;
...
Observaes
A varivel utilizada para o controle do looping FOR criada automaticamente no incio da
estrutura, e por isso, no deve ser declarada explcitamente na rea de declaraes da rotina. O seu
incremento (ou decremento, se a clusula REVERSE for utilizada) tambm automtico. Operaes de
atribuio no podem ser feitas para essa varivel.
1
6
pg: 17
Programao de SGBD
CHAR( 4 ) ;
BEGIN
SELECT Funcionario.NrMatric
INTO vResult
FROM Funcionario
WHERE Funcionario.NrMatric = pNrMatric ;
RETURN vResult ;
EXCEPTION
WHEN NO_DATA_FOUND THEN
RETURN 9999 ;
END ;
Observe na linha 007 a presena da clusula INTO, indicando que o valor retornado pelo comando
ser colocado na varivel vResult, declarada na rotina. Caso houvesse mais de um valor a ser colocado em
variveis, a clusula INTO deveria conter uma lista com os nomes de todas as variveis, separadas por
vrgula. Essas variveis deveriam aparecer em uma ordem compatvel com os campos projetados pelo
SELECT.
Dois cuidados bsicos devem ser tomados ao utilizar-se cursores implcitos:
as variveis que recebero os dados obtidos pelo SELECT devero ser declaradas com tipo igual
ao do campo correspondente na tabela, o que torna bastante indicado nesses casos utilizar o
atributo %TYPE ao declarar a varivel, para evitar problemas de incompatibilidade;
o comando deve retornar no mximo uma nica linha, seno uma exceo
TOO_MANY_ROWS ser gerada.
No h uma declarao formal do cursor, apenas das variveis a serem atualizadas pelo comando.
Cursores explcitos
1
7
pg: 18
Programao de SGBD
Inicialmente, existe a declarao do cursor nas linhas 004 a 007, onde no aparece a clusula
INTO. O nome dado ao cursor segue as mesmas regras para os nomes de variveis. A sintaxe bsica dessa
declarao a seguinte:
CURSOR <nome do cursor> IS <declarao SELECT> ;
Ao fazermos a declarao, apenas foi definida uma estrutura que ser utilizada posteriormente,
quando o SELECT for executado e a recuperao das linhas for realizada. A primeira instruo realmente
executvel relativa ao cursor a sua abertura, feita na rea de instrues atravs do comando OPEN. no
momento da abertura que o SELECT executado e as linhas recuperadas tornam-se disponveis para uso.
Sintaxe dos comandos:
Open:
Fetch: Para processar as linhas armazenadas no cursor, preciso carregar os valores da linha corrente em
variveis. A linha corrente aquela em que o cursor est posicionado. Cada fetch funciona como um
read pois faz com que o cursor mude a linha corrente para a prxima.
Fetch <nome-do-cursor> into <rea-de-trabalho>;
Close: Limpa a rea de trabalho do cursor liberando a memria.
Close <nome-do-cursor>;
1
8
pg: 19
D
Programao de SGBD
Exemplo 2 :
Create or replace procedure patraso
is
begin
--Procedure para gravar socios em atraso
Declare
wdatfecha Date := '19-SEP-97';
cursor locacoes is
Select s.cdsocio, l.nrlocacao, dtprevdev,
valorloc, valormulta from locacao l, socio s
where s.cdsocio = l.cdsocio
and datadev is null
and dtprevdev <= wdatfecha;
--- define um registro com os mesmos campos de locacoes
-reg_locacoes locacoes%rowtype;
-- declara algumas variveis
-wdiatraso number(3);
wval_total locacao.valorloc%type;
wval_multa locacao.valormulta%type;
Begin
open locacoes;
fetch locacoes into reg_locacoes;
while locacoes%found loop
wdiatraso := wdatfecha - reg_locacoes.dtprevdev;
wval_multa := 2 * wdiatraso;
wval_total := reg_locacoes.valorloc + wval_multa;
update locacao
set valorloc = wval_total
where locacao.nrlocacao = reg_locacoes.nrlocacao;
insert into tlog
( dat_log,dsc_mensagem) values
(wdatfecha,'Socio'|| to_char(reg_locacoes.cdsocio) ||
' em atraso - locacao' || to_char(reg_locacoes.nrlocacao));
fetch locacoes into reg_locacoes;
end loop;
commit;
close locacoes;
end;
end;
/
No exemplo acima usamos comandos que permitem que uma varivel herde a estrutura de dados de outra
varivel. So eles:
Atributo %TYPE => Usado para indicar que uma varivel declarada herdar o mesmo tipo de outra
varivel previamente declarada. Isto util quando no sabemos o tipo de uma determinada coluna do
banco de dados alm de permitir alterao da coluna do banco de dados em runtime.
1
9
pg: 20
Programao de SGBD
D
Exemplo:
Declare
wcodsocio socio.codsocio%type
Neste caso a varivel wcodsocio herda o tipo da coluna codsocio da tabela socio.
Atributo %ROWTYPE => Semelhante ao %type, porm declara uma varivel herdando uma estrutura
de dados do banco de dados
Exemplo:
Declare
socio-reg socio%rowtype
Reg-scio herda toda a estrutura da tabela scio.
Alm dos recursos bsicos ligados aos cursores, existem trs outros que merecem ateno: a
possibilidade da passagem de parmetros para os cursores; os chamados
atributos de cursor e cursores explcitos via looping FOR.
Parmetros de cursor
Geralmente o comando SELECT de um cursor possui uma clusula WHERE que especifica uma
seleo de linhas a serem retornadas. Muitas vezes, temos necessidade de variar um dado a ser comparado
nessa clusula, e isso pode ser feito atravs de uma espcie de parmetro passado para o cursor no
momento de sua abertura. Observe o exemplo a seguir:
001 DECLARE
002
vMatr CHAR( 4 ) ;
003
vNome VARCHAR2( 30 ) ;
004
CURSOR LstFunc ( pSexo CHAR ) IS
005
SELECT NrMatric, NmFunc
006
FROM Funcionario
007
WHERE Sexo = pSexo ;
008
009 BEGIN
010
OPEN LstFunc( F ) ;
011
FETCH LstFunc INTO vMatr, vNome ;
012
CLOSE LstFunc ;
013
014
OPEN LstFunc( M ) ;
015
FETCH LstFunc INTO vMatr, vNome ;
016
CLOSE LstFunc ;
017
018 END ;
Ao abrirmos pela primeira vez, na linha 10, o cursor assume F como sendo o contedo da varivel
pSexo, e assim, recupera apenas os funcionrios do sexo feminino. Na segunda vez que aberto, o
parmetro passado M, e apenas os funcionrios de sexo masculino so processados.
Atributos de cursor
Durante a utilizao de um cursor em uma rotina, uma srie de valores podem ser testados, de
maneira a permitir a monitorao do estado corrente do processamento. Esses valores so obtidos atravs
de variveis especiais mantidas pelo sistema, chamadas de Atributos do cursor. Todos eles tm seu nome
comeando com o smbolo % (sinal de porcentagem) e so referenciados colocando-se o nome do cursor
imediatamente antes do %. A seguir um pequeno resumo com esses atributos e suas caractersticas
principais.
2
0
pg: 21
Programao de SGBD
D
Atributo
%ISOPEN
Tipo de Dado
BOOLEAN
Descrio
Indica se o cursor referenciado est aberto (TRUE) ou fechado (FALSE).
%ROWCOUNT
NUMBER
%NOTFOUND
BOOLEAN
%FOUND
BOOLEAN
Exemplo 2:
001
002
003
004
005
006
007
008
009
010
011
012
013
014
015
016
017
018
2
1
pg: 22
Programao de SGBD
D
Exemplo 3:
001 DECLARE
002
vMatr
CHAR( 4 ) ;
003
vSalario
Funcionario.VrSalario%TYPE ;
004
vTotSal
Funcionario.VrSalario%TYPE := 0 ;
005
CURSOR TesteCur IS
006
SELECT NrMatric, VrSalario
007
FROM Funcionario
008
ORDER BY VrSalario DESC ;
009
010 BEGIN
011
OPEN TesteCur ;
012
LOOP
013
FETCH TesteCur INTO vMatr, vSalario ;
014
EXIT WHEN TesteCur%NOTFOUND OR TesteCur%ROWCOUNT = 3 ;
015
vTotSal := vTotSal + vSalario ;
016
END LOOP ;
...
...
027
CLOSE TesteCur ;
028 END ;
2
2
pg: 23
Programao de SGBD
2
3
pg: 24
Programao de SGBD
Manipulao de erros
Toda linguagem deve proporcionar aos programadores recursos para uma fcil e adequada
interveno em casos de erro de execuo, de maneira a minimizar ou evitar problemas maiores sobre os
dados. Em PL/SQL isso obtido atravs de um mecanismo baseado no conceito de excees, que podem
ser classificadas em internas ou externas. Uma exceo nada mais do que uma notificao de erro,
realizada pelo programa, atravs de um conjunto de cdigos previamente definidos, que podem ser
detectadas na rea de excees de um mdulo. Tendo sido detectada a ocorrncia, fcil para o
programador associar uma seqncia de instrues para o tratamento daquela espcie de erro.
Ao conjunto de excees padro previamente definidas para o PL/SQL damos o nome de excees
internas, que so mostradas no quadro a seguir.
Exceo
CURSOR_ALREADY_OPEN
DUP_VAL_ON_INDEX
INVALID_CURSOR
INVALID_NUMBER
LOGIN_DENIED
NO_DATA_FOUND
NOT_LOGGED_ON
PROGRAM_ERROR
STORAGE_ERROR
TIMEOUT_ON_RESOURCE
TOO_MANY_ROWS
TRANSACTION_BACKED_OUT
VALUE_ERROR
ZERO_DIVIDE
Descrio
Indica uma tentativa de se abrir um cursor j aberto no programa.
Tentativa de se inserir uma chave duplicada em uma coluna definida
como nica.
Referncia a cursor invlido ou tentativa de operao invlida sobre o
cursor.
Indica que um valor no numrico est sendo usado onde era esperado
apenas nmeros.
Solicitao de login negada
No foram encontrados dados para atender a uma requisio feita
atravs de SELECT INTO.
Usurio no est conectado no Oracle no momento (est off-line).
Erro interno do PL/SQL
Erro de memria do PL/SQL
Ocorreu o atingimento do tempo designado para o usurio na sua conta.
A instruo SELECT ... INTO encontrou mais de uma linha.
Um servidor remoto desfez a transao
Erro de aritmtica, de converso, truncagem ou de restrio.
Tentativa de se dividir um nmero por zero.
A deteco e o tratamento da condio de erro feita conforme mostrado na rotina criada a seguir.
2
4
pg: 25
Programao de SGBD
D
001
002
003
004
005
006
007
008
009
010
011
012
013
014
015
016
017
018
019
020
021
022
023
024
025
026
-- Codigo p/ Update
BEGIN
vData := SYSDATE ;
UPDATE Funcionario
SET VrSalario = VrSalario * vPerc, DtUltAlt = vData
WHERE CdDepto = vDepto ;
INSERT INTO LogFunc ( DtOp, Usuario, Chave, CdOp )
VALUES ( vData, USER, VRSALARIO, cCdOp ) ;
COMMIT ;
-- Tratamento de excecoes
EXCEPTION
WHEN NO_DATA_FOUND THEN
raise_application_error ( 0001, Depto nao cadastrado ) ;
WHEN VALUE_ERROR THEN
raise_application_error ( 0002, Salario invalido ) ;
WHEN OTHERS THEN
raise_application_error ( 9999, Erro geral ) ;
END ;
2
5
pg: 26
Programao de SGBD
Triggers
Um trigger, ou gatilho, de banco de dados uma rotina associada a uma tabela e que disparada
automaticamente sempre que um evento especfico ocorre. Rotinas deste tipo possuem uma estrutura
muito particular, que possvel esquematizar da seguinte forma:
TRIGGER <nome do trigger>
<BEFORE | AFTER> <evento de banco de dados>
[FOR EACH ROW]
[DECLARE
... ]
BEGIN
...
END ;
Um trigger criado atravs da instruo CREATE TRIGGER, e fica armazenado no catlogo do
SGBD, que o ativa a cada vez que o evento de banco de dados definido para ele ocorre. Esses eventos so
as operaes que provocam algum tipo de atualizao nos dados de uma tabela, ou seja, instrues
INSERT, UPDATE ou DELETE. Dentro de um trigger possvel declarar e utilizar variveis, constantes,
cursores, desvios e loopings, como em rotinas de outros tipos. Tambm possvel ativar outras rotinas
(procedures e functions) em seu interior.
Para uma melhor compreenso das caractersticas e recursos disponveis com os triggers, observe
os exemplos a seguir, procurando identificar o efeito de cada um deles e as condies em que so
disparados.
Exemplo 1:
Ativao
Trigger
2
6
pg: 27
Programao de SGBD
D
Exemplo 2:
Ativao
Trigger
UPDATE Funcionario
SET VrSalario = VrSalario * 1.1
WHERE CdDepto IN ( D1,D3 );
Exemplo 3:
Ativao
Trigger
UPDATE Funcionario
CREATE TRIGGER AltSalFunc
SET VrSalario = VrSalario * 1.1; AFTER UPDATE OF VrSalario ON Funcionario
FOR EACH ROW
WHEN (new.VrSalario > 5000)
DECLARE
CdOp
CONSTANT CHAR := X ;
BEGIN
INSERT INTO LogFunc (DtOp, Usuario, TpOp )
VALUES ( SYSDATE, USER, CdOp ) ;
END ;
Exemplo 4:
Ativao
Trigger
UPDATE Cargo
SET NmCargo = OFICIAL ADMIN.
WHERE CdCargo = C4 ;
2
7
pg: 28
Programao de SGBD
IV Estudo de caso
Veremos agora um caso prtico que nos oferecer a oportunidade de utilizar alguns recursos muito
importantes de um gerenciador de banco de dados. Criao e alterao de tabelas, construo e utilizao
de rotinas no SGBD acompanhados de uma discusso sobre algumas questes pertinentes sobre o projeto
de bancos de dados so os tpicos que sero abordados, atravs do acompanhamento da evoluo de um
pequeno modelo de banco de dados para a manuteno de contas-corrente em um banco. O modelo
propositalmente simplificado, de maneira a ressaltar os tpicos centrais de nosso assunto: SQL Data
Definition Language e PL/SQL.
Inicialmente, o modelo a ser implantado seria o seguinte:
Observe que o modelo utiliza uma notao de modelagem de dados que combina a representao de
Peter Chen com uma forma particular de representao de cardinalidades. O projeto suporta contas
conjuntas, atravs do relacionamento N:N Mantm. Com isso, teremos 5 tabelas, correspondentes a cada
um dos arranjos de dados sugeridos no modelo:
2
8
pg: 29
Programao de SGBD
Entidade
Cliente
Mantm
Conta
Agncia
Movimento
Tabela
Cliente
CliConta
Conta
Agencia
Movimento
Utilizamos um arroba (@) para representar a chave primria de cada tabela e uma letra E para
designar cada uma das chaves estrangeiras. Todas as tabelas possuem uma chave primria simples, exceto
CliConta, que representa o relacionamento Mantm: nesse caso a chave primria composta, formada
pela combinao dos dois atributos (Cliente e Conta Corr.) que, individualmente, representam chaves
estrangeiras.
Alm dessas caractersticas, consideraremos ainda as seguintes especificaes adicionais sobre os
valores dos atributos:
Entidade
Cliente
Atributo
Nome
Endereo
Restries
obrigatrio, deve ser nico na tabela.
obrigatrio.
Agncia
Nome Agncia
Telefone
Conta
Data Abertura
Agncia
obrigatrio.
obrigatrio.
Mantm
Cliente
Conta Corr.
obrigatrio.
obrigatrio.
Movimento
Conta Corr.
Data Movim.
Tipo Movim.
Valor Movim.
Descr. Movim.
obrigatrio.
obrigatrio.
obrigatrio, deve ser C ou D.
obrigatrio, deve ser maior que zero.
obrigatrio.
Alm de observar essas restries deveremos, para criar as tabelas, levar em conta os tipos de dados
mais adequados a cada atributo, bem como definir nomes de campos que sejam mnemnicos e guardem
alguma correspondncia com os nomes dos atributos, mas que tambm obedeam s regras de nomes
impostas pelo Oracle.
2
9
pg: 30
Programao de SGBD
Observe o script SQL que gera as tabelas correspondentes ao modelo no Oracle 7.3:
----------
*
*
Arquivo:
*
*
Autor:
*
*
Data:
*
* Finalidade:
*
CriaBan.sql
Cesar
20/3/97
Criar as tabelas referentes ao Banco Simplificado
PRIMARY KEY,
NOT NULL UNIQUE,
NOT NULL ) ;
PRIMARY KEY,
NOT NULL UNIQUE,
NOT NULL,
PRIMARY KEY,
NOT NULL,
NOT NULL
REFERENCES Agencia);
REFERENCES Cliente,
REFERENCES Conta,
PRIMARY KEY,
NOT NULL
REFERENCES Conta,
NOT NULL,
NOT NULL
CHECK ( TpMov IN( 'C', 'D' ) ),
NUMBER(12,2) NOT NULL
CHECK ( VrMov > 0 ),
VARCHAR2(20) NOT NULL ) ;
-- *
-- * Fim deste script
-- *
Voc deve ter reparado que existe uma ordem certa para criar as tabelas, uma vez que
especificamos as restries de integridade referencial (chaves estrangeiras) no prprio comando que cria
as tabelas. Dessa forma, primeiro temos que criar as tabelas que so referenciadas pelas demais. Se esse
cuidado no for tomado, um comando CREATE TABLE que declare uma chave estrangeira para uma
tabela ainda no existente ir falhar.
3
0
pg: 31
Programao de SGBD
Uma alternativa seria criar as tabelas apenas com as restries bsicas de NULL / NOT NULL.
Aps criadas todas as tabelas, seriam emitidos comandos ALTER TABLE que acrescentariam a cada
tabela as respectivas restries para implementar as outras regras de integridade (CHECK, UNIQUE,
PRIMARY KEY, FOREIGN KEY). Nesse caso, como ao especificar as chaves estrangeiras todas as
tabelas j existem, no h problema algum relacionado com a ordem das declaraes.
Suponhamos que comandos INSERT tenham sido emitidos para povoar com dados cada uma das
tabelas de nosso modelo. Os dados para estudo sero os seguintes:
NMAGENCIA
---------------------Praca da Republica
Centro
Prefeitura
ENDAGENCIA
TELAGENCIA
------------------------------ ---------Praca da Republica, 200
555-4433
R 15 de Novembro, 800
555-2211
Av. Sao Paulo, 100
555-6612
3 rows selected.
NMCLIENTE
-------------------------------ANA JUNQUEIRA
JOAO DA SILVA
MAIRA FIGUEIREDO
PEDRO SANTOS
SILVIO PADILHA
ROBERTO ARRUDA
SILVANA FERREIRA
CLAUDIA MARCONDES
JULIANO AGUILERA
MARIANA SOARES
ENDCLIENTE
-------------------------------R SALVADOR, 40
AV CAMPINAS, 89
R OLAVO BILAC, 430
R RUI BARBOSA, 230
R INCONFIDENTES, 20
R BAHIA, 140
AV 7 DE SETEMBRO, 2740
R SALVADOR DALI, 430
R PORTUGAL, 121
R CANDIDO PORTINARI, 1340
10 rows selected.
3
1
pg: 32
Programao de SGBD
D
SQL> SELECT * FROM Conta;
NRCONTA
--------1021
1022
1023
1024
1025
1026
1027
1028
1029
1030
1031
1032
DTABERTUR
--------10-AUG-95
01-SEP-95
12-SEP-95
23-OCT-95
25-OCT-95
04-NOV-95
10-NOV-95
12-NOV-95
17-NOV-95
26-NOV-95
08-DEC-95
12-DEC-95
CDAG
---0040
0060
0040
0050
0060
0050
0040
0050
0050
0040
0060
0060
12 rows selected.
3
2
pg: 33
D
Programao de SGBD
Ao analisar a composio de cada tabela, esperamos que voc esteja imaginando como foram
escritos os comandos INSERT correspondentes. Voc tambm deve ter notado que o saldo de uma conta
corrente no se encontra disponvel explicitamente em lugar algum, mas pode ser obtido atravs de um
clculo. Essa soluo possvel mas no muito prtica. Suponha que queiramos acrescent-la, de
maneira que a recuperao desse valor no seja muito demorada. O melhor lugar para ela seria na tabela
de movimentos, conforme indicado na nova verso de nosso modelo Entidade / Relacionamento, mostrado
a seguir. O valor correspondente ao saldo dever ser calculado a cada alterao na base de dados e
colocado nesse novo campo, que mostrar assim o saldo atual da conta aps computado o movimento.
Evidentemente, o contedo do campo saldo no dever ser nulo em hiptese alguma para qualquer
movimento conhecido em qualquer conta.
3
3
pg: 34
D
Programao de SGBD
3
4
pg: 35
Programao de SGBD
Cliente
Mantm
@ Cd. Cliente
(E) Cliente
Nome
Endereo
Telefone
CPF
RG
3
5
pg: 36
D
Programao de SGBD
3
6
pg: 37
Programao de SGBD
Esse comando cria a nova coluna na tabela. O script a seguir cria o procedimento que ficar
armazenado no SGBD e quando ativado, calcular e atualizar o valor do saldo para cada movimento.
---------
*
*
Arquivo: CriProc0.sql
*
Autor: Cesar
*
Data: 2/9/97
* Finalidade: Exemplo de procedimento de banco de dados
*
(no caso, o procedimento AtuSaldoMov p/ atualizar
*
o saldo de uma conta na tabela de movimentos)
*
;
;
;
;
;
-- *
-- * Cursores p/ obter as contas a processar e seus movimentos
-- *
CURSOR CursorContas IS
SELECT Conta.NrConta
FROM Conta
ORDER BY Conta.NrConta ;
CURSOR CursorSaldoMov IS
SELECT Movimento.NrMov, Movimento.TpMov, Movimento.VrMov
FROM Movimento
WHERE Movimento.NrConta = vNrConta
ORDER BY Movimento.NrMov ;
-- * Corpo do procedimento
BEGIN
OPEN CursorContas ;
LOOP
3
7
pg: 38
Programao de SGBD
3
8
pg: 39
Programao de SGBD
Resta ento criar o trigger de banco de dados para que o valor de saldo seja calculado a cada
alterao ou incluso na tabela de movimentos. Isso feito atravs do script a seguir, que implementa a
lgica apenas para o caso de incluso na tabela, ficando como exerccio alter-lo para que preveja tambm
a possibilidade de alterao.
-------
*
*
Arquivo:
*
Autor:
*
Data:
* Finalidade:
*
CriTrig1.sql
Cesar
30/3/97
Criar um exemplo de gatilho de banco de dados
3
9
pg: 40
Programao de SGBD
4
0
pg: 41
D
Programao de SGBD
Exerccio proposto
Agora, vamos assumir que estudos concluram ser interessante desnormalizar a base de dados,
colocando o valor do saldo tambm na tabela de conta correntes. Essa alterao tornaria mais simples a
operao de consulta ao saldo de uma conta, minimizando o trfego na rede e a carga no servidor, mas
acrescentando uma maior complexidade nas operaes de atualizao da tabela de movimentos, pois o
novo valor do saldo deve ser atualizado tambm na tabela de contas. Assim, descreva o procedimento, os
comandos e as rotinas a serem criadas para implementar esse novo requisito. Como auxlio, fornecemos o
novo modelo Entidade / Relacionamento.
4
1
pg: 42
Programao de SGBD
Cliente
Mantm
@ Cd. Cliente
(E) Cliente
Nome
Endereo
Telefone
CPF
4
2
pg: 43
Programao de SGBD
Funes pr-definidas
ABS( <expN> )
Retorna o valor absoluto (nmero sem sinal) de expN.
Exemplo:
SELECT ABS( -1 ) FROM Dual ;
/* Resultado: 1 */
ASCII( <expC> )
Retorna o valor ASCII do primeiro caracter de expC.
Exemplo:
SELECT ASCII(CdDepto) FROM Depto
WHERE CdDepto = D1 ; /* Resultado: 68 */
/* Resultado: 1222*/
CEIL( <expN> )
Retorna o maior inteiro maior que ou igual a expN.
Exemplo:
SELECT CEIL(12.33) FROM DUAL ; /* Resultado: 13*/
CHARTOROWID(<expC> )
Retorna a expC convertido em um valor de ROWID.
O contedo da expC deve estar no formato da pseudo-coluna ROWID.
Exemplo:
4
3
pg: 44
Programao de SGBD
CHR( <expN> )
Retorna o caracter ASCII referente ao valor expN.
Exemplo:
SELECT CHR(75) FROM DUAL ;
/* Resultado: K*/
4
4
pg: 45
Programao de SGBD
4
5
pg: 46
Programao de SGBD
FLOOR( <expN> )
Retorna o menor inteiro igual a ou menor que expN.
Exemplo:
SELECT FLOOR( 12.8 ) FROM Dual ;
/* Resultado: 12 */
GREATEST( <exp>,...)
Retorna o maior valor de uma lista de valores exp.
Exemplo:
SELECT GREATEST(abcd, 123, defg ) FROM Dual ; /* Resultado: defg */
INITICAP( <expC> )
Retorna a expC com a primeira letra de cada palavra em maiscula e o resto da palavra em
minsculas.
Exemplo:
SELECT INITICAP(NmFunc) FROM Funcionario
WHERE NrMatric = 1004 ; /* Resultado: Lucio Torres */
LAST_DAY( <expD> )
Retorna a data do ltimo dia do ms contida na data expD.
Exemplo:
SELECT LAST_DAY( SYSDATE ) FROM Dual ;
/* Resultado: 31-MAR-98 */
4
6
pg: 47
Programao de SGBD
LEAST( <exp>,... )
Retorna o menor valor de uma lista de valores exp.
Exemplo:
SELECT LEAST( abc,123,defg ) FROM Dual ;
/* Resultado: 123 */
LENGTH( <expC> )
Retorna o nmero de caracteres em expC
Exemplo:
SELECT LENGTH( NmDepto ) FROM Depto
WHERE CdDepto = D1 ; /* Resultado: 13 */
LOWER( <expC> )
Retorna todas as letras da expC em minsculas.
Exemplo:
SELECT LOWER( NmCargo ) FROM Cargo
WHERE CdCargo = C1;
/* Resultado: cozinheira */
/* Resultado: ***valor */
/* Resultado: 1 */
4
7
pg: 48
Programao de SGBD
Retorna a data e a hora da zona expC2 quando a data e a hora da zona expC1 estiver na data e hora
Exemplo:
SELECT
TO_CHAR(
NEW_TIME(TO_DATE(20:16,hh24:mi),PST,GMT),
hh24:mi ) FROM Dual ; /* Resultado: 04:16 */
4
8
pg: 49
Programao de SGBD
NLSSORT( <expC> )
Retorna um valor sequencial de expC referente a linguagem nacional utilizada pelo sistema.
Quando a ordem sequencial baseada em valores numricos dos caracteres. Esta ordem chamada ordem
binria.
Exemplo:
SELECT NLSSORT( A ) FROM Dual ;
/* Resultado: 4100 */
/* Resultado: 64 */
4
9
pg: 50
Programao de SGBD
ROWIDTOCHAR( <ROWID> )
Converte o valor ROWID para um valor tipo caracter.
Exemplo:
SELECT ROWID FROM Funcionario
WHERE ROWIDTOCHAR(ROWID) LIKE %5AE1%;
5
0
pg: 51
Programao de SGBD
SIGN( <expN> )
Se expN for negativo retorna -1, se for positivo retorna 1, se for zero retorna 0.
Exemplo:
SELECT SIGN( 5432 ) FROM Dual ; /* Resultado: 1 */
SOUNDEX( <expC> )
Retorna uma representao fontica de cada palavra em expC (usa fontica da lingua inglesa).
Exemplo:
SELECT nome FROM TABELA
WHERE SOUNDEX( nome ) = SOUNDEX( SMYTH);
/* Resultado: SMITH */
SQRT( <expN> )
Retorna a raiz quadrada da expN, se expN for negativa, retorna nulo.
Exemplo:
SELECT SQRT( 144 ) FROM Dual ; /* Resultado: 12 */
5
1
pg: 52
Programao de SGBD
/* Resultado: 555.90267
*/
/* Resultado: BCD */
5
2
pg: 53
Programao de SGBD
TO_NUMBER( <expC> )
Converte um nmero do tipo caracter para o tipo de dado numrico.
Exemplo:
SELECT TO_NUMBER( SUBSTR(ABCD00193,5,5) )
FROM Dual ;
/* Resultado: 193 */
TRUNC( <expN> [, n ] )
Retorna expN truncado na n-sima casa decimal; se for omitido ou for zero, trunca para o valor
inteiro, se n for negativo , zera o dgito esquerda do ponto decimal.
Exemplo:
SELECT TRUNC( 785.143 ) FROM Dual ; /* Resultado: 785 */
SELECT TRUNC( 785.14, -2 ) FROM Dual ;
/* Resultado:100 */
5
3
pg: 54
Programao de SGBD
UPPER( <expC> )
Retorna a expC com todas as letras em maisculas
Exemplo:
SELECT UPPER( NmDepto )
FROM Depto
WHERE CDDEPTO = D1; /* Resultado: ADMINISTRACAO */
USERENV( <opo> )
Retorna informaes da opo escolhida sobre o usurio e/ou a seo corrente.
Opes :
ENTRYIDIdentificador de entrada
SESSIONID
Identificador de seo
TERMINAL
Identificador do terminal do usurio
LANGUAGE
Linguagem em uso
Exemplo:
SELECT USERENV( TERMINAL )
FROM Dual ;
/* Resultado: WINDOWS95 PC */
5
4
pg: 55
Programao de SGBD
VSIZE( <exp> )
Retorna o nmero de bytes usados para armazenar internamente exp.
Exemplo:
SELECT NmFunc, VSIZE( NmFunc )
FROM Funcionario
WHERE NrMatric = 1001;
/* Resultado: 12 */
Caracter
Nmero
Data
TO_CHAR
TO_CHAR
TO_NUMBER
ERRO
TO_DATE
TO_DATE
-
5
5
pg: 56
Programao de SGBD
Exerccios Prticos
Lista Nmero 1
Tpico: PL/SQL - Procedures
1) Escreva uma Stored Procedure que atualize a tabela Curso, substituindo uma descrio
existente por outra. Utilizar parametros para indicar a descrio antiga e a descrio nova.
Exemplo: Execute MudaDesc( 'Ingls' , 'B. Dados' );
Obs: a tabela curso deve conter os campos codigo_curso e descr_curso.
2) Considere o modelo E-R Paciente-Consulta j utilizado em aulas anteriores.
Escreva uma procedure que aceite o cdigo do Paciente como parmetro e:
- Calcule o Valor Total de suas consultas nos ltimos 3 meses
Se o valor for maior que 500,00
Gravar 'S' no campo Desconto da Tabela de Paciente
Caso contrrio
Gravar 'N' no campo Desconto da Tabela de Paciente.
- Utilizar o comando exception p/a capturar erros.
3) Faa o exerccio 2 que se encontra na pg 8 desta apostila.
4) Escreva uma procedure que valide senhas a partir de uma tabela de senhas.
Considere esta tabela com os campos:
Username varchar2(8)
Senha
varchar2(8).
A procedure ValidaSenha recebe como parmetro um username e uma password
e verifica se a password informada como parmetro igual a senha existente na tabela.
Se diferente gravar mensagem '#Password Invlida' em uma tabela tlog.
Se igual gravar #Password Vlida em uma tabela tlog.
Obs: Fazer o tratamento de exceo se houver erro na clusula select.
5) Realize o exerccio abaixo com base no modelo Paciente Consulta Mdico.
Criar um novo campo na tabela de mdico para conter o valor cobrado por consulta.
( sugesto: Chame este campo de VrHonor).
Atualize este campo com valores significativos, isto no deixe valores nulos.
Escreva uma procedure que grave um novo registro na tabela de consulta. Esta
procedure deve receber como parmetros os campos: codPaciente, codMedico e
Tipoconsulta. O valor da consulta deve ser calculado conforme algortmo abaixo.
5
6
pg: 57
D
Programao de SGBD
Se consulta do tipo Convnio (coluna TipoCon = C)
ento valorConsulta = VrHonor * 0.8
Seno, se paciente tem desconto ( coluna desconto = S)
Ento valorConsulta = VrHonor * 0.7
Seno valorConsulta = VrHonor ( cobrar preo normal)
5
7
pg: 58
Programao de SGBD
Lista Nmero 2
Tpico: PL/SQL Triggers
1- Sobre o modelo Paciente-Consulta, escreva um trigger que ao incluir uma consulta
verifique:
Se tipo = `C (convnio) gravar em uma tabela de guias a mensagem
"Emitir guia de convnio do paciente " <cod. Do paciente"> "-" <nome-do-paciente>.
A tabela de guias deve conter o campo Mensagem varchar2(70).
2- Escreva um trigger que ao se excluir uma consulta, grave uma linha na tabela Tlog.
A tabela Tlog deve conter :
data do sistema,
usurio que est efetuando a excluso (user),
cdigo da consulta excluda.
3- Sobre o modelo do Item-pedido, escreva um trigger que ao inserir um item do pedido
verifique se o cliente j possui mais de 10 pedidos com entrega no ms atual. Se sim,
aplicar um desconto de 15% ao preo do item que esta sendo cadastrado.
4- Crie um trigger que ao ser alterado o campo endereo da tabela de cliente, faa a
insero de uma linha na tabela de log com a mensagem "Observar mudana de
endereo" <codigo do cliente> <endereo velho><endereo novo>
Tablog (datalog,campo1,campo2).
5
8