You are on page 1of 11

Baza de date pentru gestiunea activitatii unei firme de publicitate

Se dorete implementarea n SQL Server a unei baze de date privind gestiunea activitii unei firme de publicitate. In acest sens se cunosc urmatoarele: Angajatii firmei sunt persoane fizice caracterizate prin nume, prenume si adresa. Acestia lucreaza in diferite departamente ale agentiei de publicitate. Departamentele firmei sunt identificate in mod unic prin codul departamentului. Agentia de publicitate incheie contracte de publicitate cu clientii. Fiecare contract este caracterizat printr-un cod si o data. Clientii sunt persoane juridice ce detin un nume, o adresa si un telefon. Pe baza contractelor, agentia de publicitate incaseaza de la clientii contravaloarea pentru serviciile oferite.

Dictionarul Atributelor: CNP, NumeAngajat, PrenumeAngajat, AdresaAngajat, CodClient, NumeClient, AdresaClient, TelefonClient, CodContract, DataContract, CodDepartament, DenumireDepartament, CodIncasare, DataIncasare, ValoareIncasata.

Reguli de gestiune: Un departament cuprinde mai multi angajati Un angajat lucreaza intr-un singur departament. Un client incheie mai multe contracte. O incasare se efectueaza de la un singur client.

Restrictii de integritate - valoare incasata<10000 - datacontract<getdate() - dataincasare<getdate() - dataincasare>datacontract - prima cifra din CNP poate fi 1 sau 2

Modelul relaional al datelor

1) Angajati (CNP, NumeAngajat, PrenumeAngajat, AdresaAngajat,CodDepartament)

2) Departamente (CodDepartament, DenumireDepartament, CodContract)

3) Contracte (CodContract, DataContract, CodClient)

4) Clienti (CodClient, NumeClient, AdresaClient, TelefonClient, CodIncasare)

5) Incasari (CodIncasare, DataIncasare, ValoareIncasata)

I.View-uri 1) Sa se afiseze angajatii nascutii in luna februarie. SELECT FROM WHERE TOP (100) PERCENT CNP AS Expr1, NumeAngajat, PrenumeAngajat dbo.Angajati (SUBSTRING(CNP, 4, 2) = '02')

2) Sa se afiseze clientii din Bucuresti si numarul de zile in care ei au achitat contravolarea contractului de publicitate. SELECT dbo.Clienti.CodClient, dbo.Clienti.NumeClient, dbo.Clienti.AdresaClient, DATEDIFF(day, dbo.Contracte.DataContract, dbo.Incasari.DataIncasare) AS NrZIle FROM JOIN dbo.Contracte ON dbo.Clienti.CodClient = dbo.Contracte.CodClient WHERE (dbo.Clienti.AdresaClient LIKE 'Bucuresti') dbo.Incasari INNER JOIN dbo.Clienti ON dbo.Incasari.CodIncasare = dbo.Clienti.CodIncasare INNER

3) Sa se afiseze valoarea totala a contractelor incasate in trimestrul 1 al anului 2008. SELECT FROM SUM(dbo.Incasari.ValoareIncasata) AS ValoareTotalaIncasata dbo.Incasari INNER JOIN dbo.Clienti ON dbo.Incasari.CodIncasare = dbo.Clienti.CodIncasare WHERE (dbo.Incasari.DataIncasare BETWEEN '2008-01-01' AND '2008-03-31')

4) Sa se afiseze departamentele care au incheiate contracte.

SELECT FROM

dbo.Departamente.CodDepartament, dbo.Departamente.DenumireDepartament dbo.Departamente INNER JOIN dbo.Contracte ON dbo.Departamente.CodContract =

dbo.Contracte.CodContract WHERE (dbo.Departamente.CodContract IN (SELECT FROM CodContract AS Expr1 dbo.Contracte AS Contracte_1))\

5) Sa se afiseze numarul angajatilor care lucreaza in agentia de publicitate. SELECT FROM COUNT(CNP) AS NrAngajati dbo.Angajati

6) Sa se afiseze clientii care au platit mai mult de 5500 lei si mai putin de 1200 lei. SELECT FROM dbo.Clienti.CodClient, dbo.Clienti.NumeClient, dbo.Incasari.ValoareIncasata Clienti INNER JOIN Incasari ON Clienti.CodIncasare = Incasari.CodIncasare WHERE UNION SELECT FROM dbo.Clienti.CodClient, dbo.Clienti.NumeClient, dbo.Incasari.ValoareIncasata Clienti INNER JOIN Incasari ON Clienti.CodIncasare = Incasari.CodIncasare WHERE valoareincasata < 1200 valoareincasata > 5500

7) Sa se afiseze valoarea maxima incasata. SELECT FROM MAX(dbo.Incasari.ValoareIncasata) AS Max dbo.Incasari INNER JOIN dbo.Clienti ON dbo.Incasari.CodIncasare = dbo.Clienti.CodIncasare

8) Se afiseze barbatii din firma care s-au nascut in anul 1977. SELECT CNP, NumeAngajat, PrenumeAngajat, AdresaAngajat

FROM WHERE

dbo.Angajati (LEFT(CNP, 3) = '177')

9) Sa se afiseze contractile incheiate in luna februarie a anului 2008. SELECT FROM WHERE = 2008) CodContract, DataContract dbo.Contracte (DATEPART(month, DataContract) = 2) AND (DATEPART(year, DataContract)

10) Sa se afiseze valoare minima pe care a platit-o un client din Bucuresti. SELECT FROM MIN(dbo.Incasari.ValoareIncasata) AS MIN, dbo.Clienti.AdresaClient dbo.Incasari INNER JOIN dbo.Clienti ON dbo.Incasari.CodIncasare = dbo.Clienti.CodIncasare WHERE (dbo.Clienti.AdresaClient = 'Bucuresti')

GROUP BY dbo.Clienti.AdresaClient

II. Triggere
1) Realizati un trigger care sa nu permita modificarea valorii incasate de la client sub

limita existenta in momentul actualizarii. create trigger ModificareValoare on incasari for update as if exists (select * from deleted,inserted where deleted.codincasare=inserted.codincasare and deleted.valoareincasata=inserted.valoareincasata) begin raiserror ('Nu se poate modifica sub minimul actual',18,3) rollback transaction end

2) Sa se creeze un trigger care sa nu permita stergerea clientilor din orasul Bucuresti.

CREATE trigger [dbo].[Stergere] on [dbo].[Clienti] after delete as if exists (select * from deleted where adresaclient like 'bucuresti')

begin raiserror('Nu se pot sterge clientii din Bucuresti',18,1) rollback transaction end

3) Sa se creeze o procedura care sa nu permita adaugarea unui nou angajat in tabela

angajati decat daca adresa este Bucuresti.

ALTER trigger [dbo].[Adaugare] on [dbo].[Angajati] after insert as if exists (select * from inserted where adresaangajat not like 'bucuresti') begin raiserror ('Angajatul nu poate fi adaugat pentru ca nu este din Bucuresti',18,2) rollback transaction end III. Proceduri 1) Sa se creeze o procedura care sa atribuie numar de ordin, rang si sa imparta in categorii valoarea incasata de agentia de publicitate.

create proc [dbo].[AtribuieNr] as select CodIncasare,valoareincasata, row_number() over(order by valoareincasata desc) as ex1, rank()over(order by valoareincasata desc) as ex2, NTILE(3)over (order by valoareincasata desc)as ex3 from Incasari order by valoareincasata desc exec AtribuieNr

2) Sa se creeze o procedura care sa afiseze valorile incasate mai mici decat o valoare

introdusa ca parametru. create proc [dbo].[valoare] @ValoareIntrodusa as money as select CodIncasare,sum(valoareincasata )as valoare from incasari group by codincasare having sum(ValoareIncasata)<@ValoareIntrodusa

exec proc valoare 1000

3) Sa se creeze o procedura care sa afiseze clientii care au sediul intr-o anumita localitate transmisa ca parametru. create proc AfisClienti @localitate as nvarchar(50) as select codclient,numeclient,adresaclient from clienti where AdresaClient=@localitate

exec AfisClienti Bucuresti

4) Sa se creeze o procedura care sa afiseze media valorii incasate de la clienti in primul

semestru al anului 2008.

create proc valmedieincasata as select valoareincasata,codincasare from incasari where month(DataIncasare)<6 and YEAR(dataincasare)=2008 order by valoareincasata compute avg(valoareincasata)

exec valmedieincasata

5) Sa se creeze o procedura care sa afiseze clientii care au incheiat contracte intr-un interval de timp transmis ca parametru. create procedure [dbo].[Interval] @dataincepere date, @datasfarsit date as select clienti.codclient,numeclient from clienti inner join Contracte on Clienti.CodClient=Contracte.CodClient

where datacontract between @dataincepere and @datasfarsit

exec interval '2008-01-01' ,'2008-03-03'

6) Sa se defineasca o procedura stocata care sa foloseasca un cursor pentru urmatoarele operatii:

- parcurgerea unui set de inregistrari virtuale, secvential, inainte, care contin media
generala a valorilor incasate de la fiecare client - daca media valorilor incasate de la fiecare client din cursor este mai mare decat o valoare transmisa printr-un parametru procedurii stocate se va majora cu 10% valoarea incasata (in tabelul Incasari) (Cursor) create PROCEDURE [dbo].[TCursor] @Parametru as money AS DECLARE cursorEx CURSOR STATIC SCROLL FOR SELECT Codincasare, AVG(valoareincasata) as Medie FROM incasari GROUP BY Codincasare declare @pcodincasare as bigint, @pMedie as money SELECT Codincasare, AVG(valoareincasata) as Medie FROM Incasari GROUP BY CodIncasare SELECT * FROM Incasari OPEN cursorEx FETCH NEXT FROM cursorEx INTO @pCodincasare, @pMedie WHILE @@FETCH_STATUS = 0 BEGIN IF @pMedie>@Parametru BEGIN UPDATE Incasari SET ValoareIncasata = ValoareIncasata * 1.1 WHERE CodIncasare = @pcodincasare END FETCH NEXT FROM cursorEx INTO @pCodincasare, @pMedie END SELECT * FROM incasari

CLOSE cursorEx DEALLOCATE cursorEx exec Tcursor 1000

7) Sa se creeze o procedura stocata pentru a afisa datele unui angajat al carui CNP este specificat ca parametru. In cazul in care parametrul nu este specificat (ramane NULL) se va afisa un mesaj de eroare.

create proc afisangajat @pCNP nvarchar(13)=NULL as if @pCNP is null begin print 'Nu ati furnizat un CNP' end else select * from Angajati where CNP=@pCNP exec afisangajat 2860206511616

8) Sa se creeze o procedura stocata care sa afiseje toti colaboratori care au acelasi

domiciliu ca si Muraru Andrei. create proc [dbo].[DomiciliuColab] as select nume from colaboratori where domiciliu=any(select domiciliu from colaboratori where nume='Muraru Andrei')

exec DomiciliuColab

9) Sa se creeza o procedure stocata care sa calculeze media valorilor incasate care sunt

mai mici decat o valoare introdusa ca parametru.

create proc valincas @param as money as select * from Incasari where ValoareIncasata<@param

order by ValoareIncasata compute avg(valoareincasata)

exec valincas 1000

10)

Sa se creeze o procadura stocata care sa afiseze departamentul care a incheiat contractul cu numarul 100.

create proc afisdepartament @pcodcontract as int as select CodDepartament,DenumireDepartament from departamente where codcontract=@pcodcontract

exec afisdepartament 100

IV. Functii

1) Sa se realizeze o functie scalara care doreste alocarea unui cod fiecarui angajat in

parte. Codurile vor fi alcatuite din intiala prenumelui, initiala numelui si ultimele doua cifre ale CNP-ului.

create function [dbo].[Cod](@cnp as nvarchar (13), @pNume nvarchar(50), @pPrenume nvarchar(50) ) returns nvarchar(200) AS BEGIN RETURN LEFT(@pPrenume,1) + Left(@pNume,1)+ right(@cnp,2) END

select dbo.cod(CNP,NumeAngajat,PrenumeAngajat) as Codatribuit from Angajati

2) Sa se realizeze o functie scalara care sa calculeze reducerea ce trebuie calculata pentru valoarea incasata astfel:

- Daca valoarea contractului a fost incasata in primul semestru si valoare incasata este
mai mica decat 1500 atunci se aplica o cota de 0,01%.

- Daca valoarea contractului a fost incasata in al doilea semestru si valoare incasata este
mai mare decat 1500 atunci se aplica o cota de 0,02%.

- Altfel se aplica o cota de 0,03%.

alter function [dbo].[Reducere] (@dataincasare as date,@valoareincasata as money) returns money as begin return case when @dataincasare<'2008-06-01'and @valoareincasata<=1500 then @valoareincasata*0.01 when @dataincasare>'2008-06-01'and @valoareincasata>2000 then @valoareincasata*0.02 else @valoareincasata*0.03 end end

select dbo.reducere(dataincasare,valoareincasata) from Incasari 3) Sa se creeze o functie tabelara multiinstructiune care sa afiseze valoarea incasata de la un anumit client si printru-o anumita incasare specificate ca parametru. create FUNCTION [dbo].[Valoriincasate](@CodClient int,@CodIncasare int) RETURNS @Tabel TABLE (Valoareincasata money, Dataincasare date) AS BEGIN INSERT @Tabel SELECT Valoareincasata, dataincasare FROM incasari inner join clienti on incasari.codincasare=clienti.codincasare WHERE (clienti.codclient=@codclient)and (incasari.codincasare=@codincasare) Return END select * from dbo.valoriincasate ('1001','10')

You might also like