Вы находитесь на странице: 1из 12

Ministerul Educației și Tineretului al Republicii Moldova

Universitatea de Stat a Moldovei

Facultatea Matematica și Informatica

Индивидуальная работа
по курсу
“Базы данных”

Выполнил студент группы IA1902

Pascari Nikita

Кишинёв 2020
Структура и схема базы данных:
Постановка задачи:
Игровой сервер, который служит методом предоставления
игрокам места для времяпровождения. Игровой сервер работает
каждый день, для выполнения каких-либо работ и слежения за
информацией, администратору необходима база данных, в
которой будет отражено положение дел на текущий момент.
Каждый день регистрируются новый игроки, которым нужно
выдавать права, отображать информацию об их аккаунте и так
далее. Такая база данных будет содержать следующие сведения
о статистике и работе сервера:

 Будет отражаться общее количество игроков, вся


информация о них.
 Будут храниться все права, которыми наделены игроки и
работники данного сервера.
 Будут автоматически выдаваться права игрокам, которые
только что зарегистрировались.
 Общая информация о транзакциях, которые произошли
между игроками и работниками.
Создание и заполнение таблиц:
create table ACCOUNT (
ACCOUNT_ID number(10) not null,
PLAYER_ID number(10) not null,
OPEN_DATE date not null,
CLOSE_DATE date,
LAST_ACTIVITY_DATE date,
STATUS_ID number(10) not null,
BALANCE number(20),
CONSTRAINT ACCOUNT_pk primary key (ACCOUNT_ID)
);

create table PLAYERS (


PLAYER_ID number(20) not null,
FIRST_NAME varchar(20) not null,
LAST_NAME varchar(20) not null,
BIRTHDAY date,
SERVER_ID number(20) not null,
CONSTRAINT PLAYERS_pk primary key (PLAYER_ID)
);

create table SERVER(


SERVER_ID number(20) not null,
NAME varchar2(20) not null,
CONSTRAINT SERVER_pk primary key (SERVER_ID)
);

create table TRANSACTION(


TRANSACT_ID number(20) not null,
AMOUNT number(20) not null,
ACCOUNT_ID number(20) not null,
DATE_TRANSACT date not null,
TELLER_EMP_ID number(10) not null,
SERVER_ID number(20) not null,
CONSTRAINT TRANSACTION_pk primary key (TRANSACT_ID)
);

create table STATUS(


STATUS_ID number(20) not null,
S_TYPE varchar2(20) not null,
CONSTRAINT STATUS_pk primary key (STATUS_ID)
);

create table EMPLOYEE (


EMP_ID number(20) not null,
F_NAME varchar2(20) not null,
L_NAME varchar2(20) not null,
STATUS_ID number(20) not null,
DAY varchar2(20) not null,
START_DATE date not null,
END_DATE date,
SERVER_ID number(20) not null,
CONSTRAINT EMPLOYEE_pk primary key (EMP_ID)
)

alter table ACCOUNT


add constraint ACCOUNT_PLAYERS_FK
foreign key (PLAYER_ID)
references PLAYERS;

alter table ACCOUNT


add constraint ACCOUNT_STATUS_FK
foreign key (STATUS_ID)
references STATUS;
alter table ACCOUNT
add constraint ACCOUNT_SERVER_FK
foreign key (SERVER_ID)
references SERVER;

alter table TRANSACTION


add constraint TRANSACTION_ACCOUNT_FK
foreign key (ACCOUNT_ID)
references ACCOUNT;

alter table TRANSACTION


add constraint TRANSACTION_EMPLOYEE_FK
foreign key (EMP_ID)
references EMPLOYEE;

alter table TRANSACTION


add constraint TRANSACTION_SERVER_FK
foreign key (SERVER_ID)
references SERVER;

alter table EMPLOYEE


add constraint EMPLOYEE_SERVER_FK
foreign key (SERVER_ID)
references SERVER;

alter table EMPLOYEE


add constraint EMPLOYEE_STATUS_FK
foreign key (STATUS_ID)
references STATUS;

alter table EMPLOYEE


add constraint EMPLOYEE_ACCOUNT_FK
foreign key (ACCOUNT_ID)
references ACCOUNT;

alter table PLAYERS


add constraint PLAYERS_SERVER_FK
foreign key (SERVER_ID)
references SERVER;

BEGIN
insert into SERVER(SERVER_ID, NAME)
values (100,'SERVER1');
insert into SERVER(SERVER_ID, NAME)
values (101,'SERVER2');
insert into SERVER(SERVER_ID, NAME)
values (102,'SERVER3');
END

BEGIN
insert into STATUS(STATUS_ID, S_TYPE)
values (1,'PLAYER');
insert into SERVER(STATUS_ID, S_TYPE)
values (2,'MODERATOR');
insert into SERVER(STATUS_ID, S_TYPE)
values (3,'ADMINISTRATOR');
END

insert into EMPLOYEE (EMP_ID, F_NAME, L_NAME,


STATUS_ID,DAY,START_DATE, END_DATE, SERVER_ID,ACCOUNT_ID)
values (1, 'Michael', 'Smith',
(select STATUS_ID from STATUS where S_TYPE = 'ADMINISTRATOR'),
'MONDAY',
to_date('22-06-2012','dd-MM-yyyy'),
to_date('12-06-2015','dd-MM-yyyy'),
(select SERVER_ID from SERVER where NAME = 'SERVER1'),1000);

insert into EMPLOYEE (EMP_ID, F_NAME, L_NAME,


STATUS_ID,DAY,START_DATE, END_DATE, SERVER_ID,ACCOUNT_ID)
values (2, 'Serghei', 'Burlaku',
(select STATUS_ID from STATUS where S_TYPE = 'ADMINISTRATOR'),
'MONDAY',
to_date('23-06-2012','dd-MM-yyyy'),
to_date('15-06-2016','dd-MM-yyyy'),
(select SERVER_ID from SERVER where NAME = 'SERVER2'),1001);
Запросы
1)Выборка игроков, которые имеют статус ADMINISTRATOR;
select * from EMPLOYEE
where STATUS_ID = (select STATUS_ID from STATUS where S_TYPE =
'ADMINISTRATOR');

2)Выборка игроков, которые имеют статус MODERATOR;


select * from EMPLOYEE
where STATUS_ID = (select STATUS_ID from STATUS where S_TYPE =
'MODERATOR');

3) Выборка игроков, которые зарегистрировали аккаунты в


2011 и 2012 году и увеличение их баланса в 2 раза.
select OPEN_DATE, BALANCE
(case
when to_char(OPEN_DATE,'yyyy') = 2011 then BALANCE * 2
when to_char(OPEN_DATE,'yyyy') = 2012 then BALANCE * 2
end)
from ACCOUNT;
4)Выборка игроков, у которых баланс меньше 1000.
SELECT LAST_NAME
from PLAYERS
where ACCOUNT_ID in (select ACCOUNT_ID
from ACCOUNT
group by ACCOUNT_ID
having sum(BALANCE) <= 1000);

5)Выборка всех игроков и сортировка по убыванию id


серверов.
SELECT * from (select *
from PLAYERS
order by SERVER_ID desc)
where rownum <= 3
6)Выводит идентификаторы и фамилии тех игроков, у
которых есть одна или несколько транзакций.
SELECT EMP_ID, L_NAME
from EMPLOYEE
where EMP_ID in (select EMP_ID from EMPLOYEE
intersect
select EMP_ID from TRANSACTION);

7)Результирующую таблица в два столбца: название


таблицы и количество записей для таблиц: ACCOUNT,
PLAYERS, EMPLOYEE. Выходные данные, отсортированные
в возрастающем порядке значений второго столбца.
SELECT 'ACCOUNT_ID', count(*) as num from ACCOUNT
union
select 'PLAYER_ID', count(*) from PLAYERS
union
select 'EMP_ID', count(*) from EMPLOYEE
order by 2

8)Выборка тех игроков, которые не имеют аккаунтов на


серверах.
SELECT PLAYER_ID, LAST_NAME
from PLAYERS
where PLAYER_ID not in (select PLAYER_ID from PLAYERS
intersect
select PLAYER_ID from ACCOUNT);
9) Выборка тех игроков, которые передавали в одной
транзакции меньше 1000.
SELECT ACCOUNT_ID
from ACCOUNT
where ACCOUNT_ID in (select ACCOUNT_ID
from TRANSACTION
having (AMOUNT) <= 1000);
10)Выборка тех игроков, которые делали транзакции.
SELECT ACCOUNT_ID
from ACCOUNT
where ACCOUNT_ID in (select ACCOUNT_ID from ACCOUNT
intersect
select ACCOUNT_ID from TRANSACTION);

Представления
1)Представление, содержащее фамилии игроков, которые
играют на первом сервере.
create view SERVER1 as
select sp.LAST_NAME,sp.PLAYER_ID
from PLAYERS sp
where SERVER_ID in(select SERVER_ID from SERVER where NAME = 'SERVER1');
2)Представление, содержащее общую информацию о всех
игроках.
create view PLAYERS_INFO as
select * from PLAYERS;
3)Представление, содержащее идентификатор аккаунта,
идентификатор игрока и размер его транзакции.
create view TRANSACTIONS as
select m.ACCOUNT_ID, m.AMOUNT RAZMER, p.PLAYER_ID
from TRANSACTION m, PLAYERS p
where m.ACCOUNT_ID = p.ACCOUNT_ID;
4)Представление, содержащее фамилию игрока и сервер, на
котором он играет.
create view PLAYER as
select p.LAST_NAME, p.SERVER_ID
from PLAYERS p
where SERVER_ID between 100 and 102;
5)Представление, содержащее идентификатор игрока и его
период игры на сервере.
create view PLAYERS_DATE as
select c.ACCOUNT_ID, c.OPEN_DATE||','|| c.CLOSE_DATE as PERIOD
from ACCOUNT c;
Процедуры
1)Процедура, которая выдает права модератора игрокам с
определенной даты да определенной даты.
DECLARE
cursor c_1 is select ACCOUNT_ID, OPEN_DATE from ACCOUNT;
v_stat number;
BEGIN
for rec in c_1
loop
case
when rec.OPEN_DATE between '01/02/2000' and '12/30/2009' then v_stat:=2;
when rec.OPEN_DATE between '01/02/2010' and '12/30/2014' then v_stat:=2;
end case;
update ACCOUNT set STATUS_ID = v_stat
where ACCOUNT_ID=rec.ACCOUNT_ID;
end loop;
end;

2)Процедура, которая производит перевод всех игроков с


первого сервера на второй, а всех остальных игроков на
третий сервер.
create or replace procedure restruct is
p_d_id PLAYERS.SERVER_ID%type;
begin
update PLAYERS set SERVER_ID='101' where d_name='100';
update department set SERVER_ID='102' where d_name<>'100';
end restruct;
3)Процедура добавления нового сервера.
create or replace procedure add_SERVER
(p_d_id in SERVER.SERVER_ID%type, p_d_name in SERVER.SERVER_NAME%type) is
begin
insert into SERVER(SERVER_ID, SERVER_NAME) values (p_d_id, p_d_name);
end add_SERVER;
Функции
1)Функция, которая считает количество игроков на
определенном сервере.
create or replace function count_players
(p_d_id in PLAYERS.SERVER_ID%type)
return number
is
v_count integer;
e_count exception;
e_d_no integer;
begin
select count(*) into v_count from PLAYERS where p_d_id = SERVER_ID;
if v_count = 0 then raise e_count; end if;
return v_count;
EXCEPTION
when e_count then raise_application_error(-20001, 'No players with such server!');
end count_players;

2)Функция, которая считает общее количество передаваемых


денег игроком.
create or replace function f_amount_transact
(f_d_id in TRANSACTION.ACCOUNT_ID%type)
return number
IS
v_count integer;
v_d_no department.d_no%type;
BEGIN
select TRANSACT_ID into v_d_no from department where TRANSACT_ID=f_d_id;
select count(*) into v_count then d_no=v_d_no;
return v_count;
EXCEPTION
when no_data_found then raise_application_error(-20010, 'No such transaction!');
end f_amount_transact;

3)Подсчет общего количества передаваемых денег на


определенном сервере.
create or replace function total_transaction
(p_d_no in SERVER.SERVER_ID%type)
return number
is
v_count integer;
e_SERVER exception;
t_sum_transact TRANSACTION.AMOUNT%type;
e_d_no integer;
begin
select count(*) into v_count from SERVER where p_d_no = SERVER_ID;
if v_count = 0 then raise e_SERVER; end if;
e_d_no:= p_d_no;
select sum(AMOUNT) into t_sum_transact from employee where d_no = p_d_no and d_no =
e_d_no;
return t_sum_transact;
EXCEPTION
when e_SERVER then raise_application_error(-20601, 'No Such SERVER!');
end total_transaction;

Тригеры
1)Триггер, который запрещает выдачу прав во вторник.
Create or replace trigger status_permis
Before insert or update or delete on EMPLOYEE
DECLARE
e_permis exception;
BEGIN
If to_char(DAY,”TUESDAY”) then raise e_permis;
End if;
EXCEPTION
When e_permis then raise_application_error(-20001,”Today is TUESDAY”!!!),
END status_permis;

2) Триггер, который запрещает регистрацию аккаунта между


датами.
Create or replace trigger date_permis
Before insert or update or delete on ACCOUNT
DECLARE
e_permis exception;
BEGIN
if to_char(OPEN_DATE, 'dd-MM-yyyy') < “12-02-2012”
and
to_char(OPEN_DATE,’dd-MM-yyyy’) >”10-02-2012”
then
raise e_permis;
end if;
EXCEPTION
When e_permis then raise_application_error(-20001,” Еemporarily prohibited!!!”);
END date_permis;