mirror of
https://github.com/MariaDB/server.git
synced 2025-01-27 01:04:19 +01:00
1f4a9f086a
This was done after discussions with Igor, Sanja and Bar. The main reason for removing the deprication was to ensure that MariaDB is always backward compatible whenever possible. Other things: - Added statistics counters, mainly for the feedback plugin. - INTO OUTFILE - INTO variable - If INTO is using the old syntax (end of query)
270 lines
6.1 KiB
Text
270 lines
6.1 KiB
Text
drop database if exists demo;
|
|
create database demo;
|
|
use demo;
|
|
create table ab_physical_person (
|
|
person_id integer,
|
|
first_name VARCHAR(50),
|
|
middle_initial CHAR,
|
|
last_name VARCHAR(50),
|
|
primary key (person_id));
|
|
create table ab_moral_person (
|
|
company_id integer,
|
|
name VARCHAR(100),
|
|
primary key (company_id));
|
|
create table in_inventory (
|
|
item_id integer,
|
|
descr VARCHAR(50),
|
|
stock integer,
|
|
primary key (item_id));
|
|
create table po_order (
|
|
po_id integer auto_increment,
|
|
cust_type char, /* arc relationship, see cust_id */
|
|
cust_id integer, /* FK to ab_physical_person *OR* ab_moral_person */
|
|
primary key (po_id));
|
|
create table po_order_line (
|
|
po_id integer, /* FK to po_order.po_id */
|
|
line_no integer,
|
|
item_id integer, /* FK to in_inventory.item_id */
|
|
qty integer);
|
|
#
|
|
# Schema integrity enforcement
|
|
#
|
|
create procedure check_pk_person(in person_type char, in id integer)
|
|
begin
|
|
declare x integer;
|
|
declare msg varchar(128);
|
|
/*
|
|
Test integrity constraints for an 'arc' relationship.
|
|
Based on 'person_type', 'id' points to either a
|
|
physical person, or a moral person.
|
|
*/
|
|
case person_type
|
|
when 'P' then
|
|
begin
|
|
select count(person_id) from ab_physical_person
|
|
where ab_physical_person.person_id = id
|
|
into x;
|
|
if (x != 1)
|
|
then
|
|
set msg= concat('No such physical person, PK:', id);
|
|
SIGNAL SQLSTATE '45000' SET
|
|
MESSAGE_TEXT = msg,
|
|
MYSQL_ERRNO = 10000;
|
|
end if;
|
|
end;
|
|
when 'M' then
|
|
begin
|
|
select count(company_id) from ab_moral_person
|
|
where ab_moral_person.company_id = id
|
|
into x;
|
|
if (x != 1)
|
|
then
|
|
set msg= concat('No such moral person, PK:', id);
|
|
SIGNAL SQLSTATE '45000' SET
|
|
MESSAGE_TEXT = msg,
|
|
MYSQL_ERRNO = 10000;
|
|
end if;
|
|
end;
|
|
else
|
|
begin
|
|
set msg= concat('No such person type:', person_type);
|
|
SIGNAL SQLSTATE '45000' SET
|
|
MESSAGE_TEXT = msg,
|
|
MYSQL_ERRNO = 20000;
|
|
end;
|
|
end case;
|
|
end
|
|
$$
|
|
create procedure check_pk_inventory(in id integer)
|
|
begin
|
|
declare x integer;
|
|
declare msg varchar(128);
|
|
select count(item_id) from in_inventory
|
|
where in_inventory.item_id = id
|
|
into x;
|
|
if (x != 1)
|
|
then
|
|
set msg= concat('Failed integrity constraint, table in_inventory, PK:',
|
|
id);
|
|
SIGNAL SQLSTATE '45000' SET
|
|
MESSAGE_TEXT = msg,
|
|
MYSQL_ERRNO = 10000;
|
|
end if;
|
|
end
|
|
$$
|
|
create procedure check_pk_order(in id integer)
|
|
begin
|
|
declare x integer;
|
|
declare msg varchar(128);
|
|
select count(po_id) from po_order
|
|
where po_order.po_id = id
|
|
into x;
|
|
if (x != 1)
|
|
then
|
|
set msg= concat('Failed integrity constraint, table po_order, PK:', id);
|
|
SIGNAL SQLSTATE '45000' SET
|
|
MESSAGE_TEXT = msg,
|
|
MYSQL_ERRNO = 10000;
|
|
end if;
|
|
end
|
|
$$
|
|
create trigger po_order_bi before insert on po_order
|
|
for each row
|
|
begin
|
|
call check_pk_person(NEW.cust_type, NEW.cust_id);
|
|
end
|
|
$$
|
|
create trigger po_order_bu before update on po_order
|
|
for each row
|
|
begin
|
|
call check_pk_person(NEW.cust_type, NEW.cust_id);
|
|
end
|
|
$$
|
|
create trigger po_order_line_bi before insert on po_order_line
|
|
for each row
|
|
begin
|
|
call check_pk_order(NEW.po_id);
|
|
call check_pk_inventory(NEW.item_id);
|
|
end
|
|
$$
|
|
create trigger po_order_line_bu before update on po_order_line
|
|
for each row
|
|
begin
|
|
call check_pk_order(NEW.po_id);
|
|
call check_pk_inventory(NEW.item_id);
|
|
end
|
|
$$
|
|
#
|
|
# Application helpers
|
|
#
|
|
create procedure po_create_order(
|
|
in p_cust_type char,
|
|
in p_cust_id integer,
|
|
out id integer)
|
|
begin
|
|
insert into po_order set cust_type = p_cust_type, cust_id = p_cust_id;
|
|
set id = last_insert_id();
|
|
end
|
|
$$
|
|
create procedure po_add_order_line(
|
|
in po integer,
|
|
in line integer,
|
|
in item integer,
|
|
in q integer)
|
|
begin
|
|
insert into po_order_line set
|
|
po_id = po, line_no = line, item_id = item, qty = q;
|
|
end
|
|
$$
|
|
#
|
|
# Create sample data
|
|
#
|
|
insert into ab_physical_person values
|
|
( 1, "John", "A", "Doe"),
|
|
( 2, "Marry", "B", "Smith")
|
|
;
|
|
insert into ab_moral_person values
|
|
( 3, "ACME real estate, INC"),
|
|
( 4, "Local school")
|
|
;
|
|
insert into in_inventory values
|
|
( 100, "Table, dinner", 5),
|
|
( 101, "Chair", 20),
|
|
( 200, "Table, coffee", 3),
|
|
( 300, "School table", 25),
|
|
( 301, "School chairs", 50)
|
|
;
|
|
select * from ab_physical_person order by person_id;
|
|
person_id first_name middle_initial last_name
|
|
1 John A Doe
|
|
2 Marry B Smith
|
|
select * from ab_moral_person order by company_id;
|
|
company_id name
|
|
3 ACME real estate, INC
|
|
4 Local school
|
|
select * from in_inventory order by item_id;
|
|
item_id descr stock
|
|
100 Table, dinner 5
|
|
101 Chair 20
|
|
200 Table, coffee 3
|
|
300 School table 25
|
|
301 School chairs 50
|
|
#
|
|
# Entering an order
|
|
#
|
|
set @my_po = 0;
|
|
/* John Doe wants 1 table and 4 chairs */
|
|
call po_create_order("P", 1, @my_po);
|
|
call po_add_order_line (@my_po, 1, 100, 1);
|
|
call po_add_order_line (@my_po, 2, 101, 4);
|
|
/* Marry Smith wants a coffee table */
|
|
call po_create_order("P", 2, @my_po);
|
|
call po_add_order_line (@my_po, 1, 200, 1);
|
|
#
|
|
# Entering bad data in an order
|
|
#
|
|
call po_add_order_line (@my_po, 1, 999, 1);
|
|
ERROR 45000: Failed integrity constraint, table in_inventory, PK:999
|
|
#
|
|
# Entering bad data in an unknown order
|
|
#
|
|
call po_add_order_line (99, 1, 100, 1);
|
|
ERROR 45000: Failed integrity constraint, table po_order, PK:99
|
|
#
|
|
# Entering an order for an unknown company
|
|
#
|
|
call po_create_order("M", 7, @my_po);
|
|
ERROR 45000: No such moral person, PK:7
|
|
#
|
|
# Entering an order for an unknown person type
|
|
#
|
|
call po_create_order("X", 1, @my_po);
|
|
ERROR 45000: No such person type:X
|
|
/* The local school wants 10 class tables and 20 chairs */
|
|
call po_create_order("M", 4, @my_po);
|
|
call po_add_order_line (@my_po, 1, 300, 10);
|
|
call po_add_order_line (@my_po, 2, 301, 20);
|
|
select * from po_order;
|
|
po_id cust_type cust_id
|
|
1 P 1
|
|
2 P 2
|
|
3 M 4
|
|
select * from po_order_line;
|
|
po_id line_no item_id qty
|
|
1 1 100 1
|
|
1 2 101 4
|
|
2 1 200 1
|
|
3 1 300 10
|
|
3 2 301 20
|
|
select po_id as "PO#",
|
|
( case cust_type
|
|
when "P" then concat (pp.first_name,
|
|
" ",
|
|
pp.middle_initial,
|
|
" ",
|
|
pp.last_name)
|
|
when "M" then mp.name
|
|
end ) as "Sold to"
|
|
from po_order po
|
|
left join ab_physical_person pp on po.cust_id = pp.person_id
|
|
left join ab_moral_person mp on po.cust_id = company_id
|
|
;
|
|
PO# Sold to
|
|
1 John A Doe
|
|
2 Marry B Smith
|
|
3 Local school
|
|
select po_id as "PO#",
|
|
ol.line_no as "Line",
|
|
ol.item_id as "Item",
|
|
inv.descr as "Description",
|
|
ol.qty as "Quantity"
|
|
from po_order_line ol, in_inventory inv
|
|
where inv.item_id = ol.item_id
|
|
order by ol.item_id, ol.line_no;
|
|
PO# Line Item Description Quantity
|
|
1 1 100 Table, dinner 1
|
|
1 2 101 Chair 4
|
|
2 1 200 Table, coffee 1
|
|
3 1 300 School table 10
|
|
3 2 301 School chairs 20
|
|
drop database demo;
|