Related
I am trying to figure out a method of creating a shortcut between three tables .
I have a master table, A, a table that references the first table, B, and a table that references B, C. I want to create a shortcut between A and C so I don't have to use table B.
In the below example, I want to ensure that the foreign keys FK_A_ID1 and FK_A_ID2 are always equal to each other, causing it to fail when the last insert statement is executed.
CREATE TABLE A (
ID int unique identity,
num int)
CREATE TABLE B (
ID int unique identity,
A_ID int NOT NULL,
CONSTRAINT FK_A_ID1 FOREIGN KEY (A_ID) REFERENCES A (ID))
CREATE TABLE C (
ID int unique identity,
A_ID int NOT NULL,
B_ID int NOT NULL,
CONSTRAINT FK_A_ID2 FOREIGN KEY (A_ID) REFERENCES A (ID),
CONSTRAINT FK_B_ID FOREIGN KEY (B_ID) REFERENCES B (ID))
INSERT INTO A VALUES (0);
DECLARE #A1 int = SCOPE_IDENTITY();
INSERT INTO A VALUES (1);
DECLARE #A2 int = SCOPE_IDENTITY();
INSERT INTO B Values (#A1);
DECLARE #B1 int = SCOPE_IDENTITY();
INSERT INTO C Values (#A2, #B1);
Is this possible by use of foreign keys or is there another built-in function that I don't know of?
The goal of this is to have a reliable 'shortcut' between tables A and C
One way to do this is with triggers. A trigger can do the joins necessary to ensure C.A = C.B->B.A. We use this method to verify parent keys match up between parent, child, and grandchild tables.
For example:
-- untested code
create trigger C_IU_Verify_A on C
for insert, update as
if exists
(
select 1
from inserted
inner join b on b.id = inserted.b_id
where b.a_id <> inserted.a_id
)
begin
raiserror('Parent table keys do not match.', 16, 1)
rollback
end
Another way to do this is with compound primary keys. Define the primary key of B as (a_id, id). Setup a foreign key from B(a_id) to A(id). Setup a second foreign key from C(a_id, b_id) to B(a_id, id). At this point, you have referential integrity between C.a_id and B.a_id.
For example:
create table a (id int primary key clustered)
create table b(a_id int, id int, primary key (a_id, id), unique(id))
create table c(a_id int, b_id int, id int, primary key (a_id, b_id, id), unique(id))
alter table B add constraint fk_b_aid foreign key (a_id) REFERENCES A(id)
alter table C add constraint fk_c_aid_bid foreign key (a_id, b_id) REFERENCES B(a_id, id)
insert into a (id) select 1
insert into a (id) select 2
insert into b (a_id, id) select 1, 1
insert into b (a_id, id) select 1, 2
--insert into b (a_id, id) select 2, 1 -- error: duplicate b.id
insert into b (a_id, id) select 2, 3
--insert into b (a_id, id) select 3, 1 -- error: there is no A with id = 3
insert into c (a_id, b_id, id) select 1, 1, 1
insert into c (a_id, b_id, id) select 1, 1, 2
insert into c (a_id, b_id, id) select 1, 2, 3
insert into c (a_id, b_id, id) select 2, 3, 4
--insert into c (a_id, b_id, id) select 1, 3, 5 -- error: there is no B with B.a_id = 1 and B.id = 3
drop table c;
drop table b;
drop table a;
I'm reasonably sure the following does what you want. Using psuedo code:
-- Has a primary key
CREATE TABLE A
(
A_id PrimaryKey
)
-- Has both a primary key and a compound unique constraint, as well as a foreign key to A
CREATE TABLE B
(
B_id PrimaryKey Unique_1of2
,A_id Unique_2of2 ForeignKey_to_A
)
-- Has a primary key and a compound foreign key to B
CREATE TABLE C
(
C_id PrimaryKey
,B_id ForeignKey_to_B_1of2
,A_id ForeignKey_to_B_2of2
)
Done this way:
It is not possible to put a value for A_id in B that is not also in A
it is not possible to put a values for A_id and B_id in table C that are not also a pair in B
NULL values may or may not mess with this--if you have to deal with them as well, you have bigger problems.
I can't insert data in a table where 2 foreign keys refer to one primary key...
The code is as follows:
create table Currency
(
ID int primary key identity(1,1),
Code nvarchar(8) not null,
Name nvarchar(128) not null,
Is_Active bit not null default(0),
Is_Base_Currency bit not null default(0),
Country_id int foreign key(ID) references Country(ID) not null
)
Create table Currency_rate
(
ID int primary key identity(1,1),
Currency_id int foreign key(ID) references Currency(ID) not null,
Base_currency_id int foreign key(ID) references Currency(ID) not null,
Rate decimal(16,6) not null,
Ts datetime default getDate()
)
Insert into Currency_rate(Currency_id, Base_currency_id, Rate, Ts)
values (1, 1, 121212.212121, '2008-11-11 13:23:44.111'),
(2, 2, 232323.323232, '2009-11-11 13:23:44.222'),
(3, 3, 343434.434343, '2010-11-11 13:23:44.333')
This is the error I get:
Msg 547, Level 16, State 0, Line 1
The INSERT statement conflicted with the FOREIGN KEY constraint "FK__Currency___Curre__239E4DCF". The conflict occurred in database "CryptoCurrencyData", table "dbo.Currency", column 'ID'.
The statement has been terminated.
Please help me - I can't find any solution surfing the internet...
Thank you all,
Regards,
Elias.H
Constrainsts are created to prevent corrupting data by inserting or updating your tables.
In your case, you are trying to insert data which is not existing. You are trying to insert into Currency_rate values ID's of Currency which are not existing in Currency table. So this is a whole goal of constraints - prevent corruption of data.
Just for demonstration purposes I've created Country table:
Create table Country (
ID int primary key identity(1,1),
CountryName nvarchar(50)
)
Then your first step would be:
INSERT INTO dbo.Country
(
--ID - this column value is auto-generated
CountryName
)
VALUES
(
-- ID - int
N'India' -- CountryName - nvarchar
)
, (N'Canada')
, (N'South America')
The second step will be:
INSERT INTO dbo.Currency
(
--ID - this column value is auto-generated
Code,
Name,
Is_Active,
Is_Base_Currency,
Country_id
)
VALUES
(
-- ID - int
N'Code1', -- Code - nvarchar
N'India Currency', -- Name - nvarchar
0, -- Is_Active - bit
0, -- Is_Base_Currency - bit
1 -- Country_id - int
)
, (
N'Code2', -- Code - nvarchar
N'Canada Currency', -- Name - nvarchar
0, -- Is_Active - bit
0, -- Is_Base_Currency - bit
2 -- Country_id - int
)
, (
N'Code3', -- Code - nvarchar
N'South America Currency', -- Name - nvarchar
0, -- Is_Active - bit
0, -- Is_Base_Currency - bit
3 -- Country_id - int
)
And the final step is the following:
Insert into Currency_rate(Currency_id,Base_currency_id,Rate,Ts)
values(1,1,121212.212121,'2008-11-11 13:23:44.111'),
(2,2,232323.323232,'2009-11-11 13:23:44.222'),
(3,3,343434.434343,'2010-11-11 13:23:44.333')
Hopefully someone can help. I have created two tables Customer and Order as follows;
CREATE TABLE Customer
CustomerID int NOT NULL PRIMARY KEY
CustomerName varchar(25)
The other columns in Customer table are not relevant to my question, so I will not include them here. My CustomerID numbers are from 1 through to 15, all unique.
The second table I created is Orders as follows
CREATE TABLE Orders
OrderID smallint NOT NULL PRIMARY KEY
OrderDate date NOT NULL
CustomerID int FOREIGN KEY REFERENCES Customer (CustomerID);
My insert values is as follows
INSERT INTO Orders (OrderID, OrderDate, CustomerID)
VALUES
(1001, '2008-10-21', 1),
(1002, '2008-10-21', 8),
(1003, '2008-10-22', 15),
(1004, '2008-10-22', 5),
(1005, '2008-10-24', 3),
(1006, '2008-10-24', 2),
(1007, '2008-10-27', 11),
(1008, '2008-10-30', 12),
(1009, '2008-11-05', 4),
(1010, '2008-11-05', 1);
When I try to insert my values into the Order table, I get the following error message....
Msg 547, Level 16, State 0, Line 1.....The INSERT statement conflicted
with the FOREIGN KEY constraint "FK__OrderT__Customer__2D27B809". The
conflict occurred table "dbo.Customer", column 'CustomerID'. The
statement has been terminated.
The numbers for CustomerID in my Order table, are (1; 1; 2; 3; 4; 5; 8; 11; 12 and 15). Therefore I have checked that all my CustomerID numbers in Order table are also in the Customer table.
So my questions are
1) Has the insert values failed because my CustomerID column in Customer table in NOT NULL and I in error made CustomerID column NULL in Order.
2) If the answer to the above question is yes, then is it possible for me to (a) drop the foreign key on the CustomerID column in Order (b) change the column to NOT NULL and (c) then add the foreign key constraint again to this column and then insert the values again?
It might be easier to drop and re-create the table Order. But I am curious if option 2 would work, re dropping and adding a foreign key on the same column.
Hopefully I am on the right track with why I think the error occurred, feel
to correct me if I am wrong.
Thanks everyone
Josie
1) It should be NOT NULL in both. However error is because you attempted to insert a CustomerId that is not in Customer table.
2) You can simply alter the table and make it NOT NULL (error was not that).
Sample:
CREATE TABLE Customer
(
CustomerID INT NOT NULL
PRIMARY KEY ,
CustomerName VARCHAR(25)
);
CREATE TABLE Orders
(
OrderID INT NOT NULL
PRIMARY KEY ,
OrderDate DATE NOT NULL ,
CustomerID INT FOREIGN KEY REFERENCES Customer ( CustomerID )
);
INSERT [Customer] ( [CustomerID], [CustomerName] )
VALUES ( 1, 'Customer 1' ),
( 2, 'Customer 2' ),
( 3, 'Customer 3' ),
( 4, 'Customer 4' ),
( 5, 'Customer 5' ),
( 6, 'Customer 6' );
INSERT [Orders] ( [OrderID], [OrderDate], [CustomerID] )
VALUES
( 1, GETDATE(), 1 ),
( 2, GETDATE(), 2 ),
( 3, GETDATE(), 3 ),
( 4, GETDATE(), 4 ),
( 5, GETDATE(), 5 ),
( 6, GETDATE(), 6 );
INSERT [Orders] ( [OrderID], [OrderDate], [CustomerID] )
VALUES ( 7, GETDATE(), 7 );
Last one would error, because Customer with CustomerID 7 doesn't exist.
Update: I later saw your sample insert. You can find the offending ID like this:
DECLARE #ids TABLE ( id INT );
INSERT #ids ( [id] )
VALUES ( 1 ),
( 8 ),
( 15 ),
( 5 ),
( 3 ),
( 2 ),
( 11 ),
( 12 ),
( 4 ),
( 1 );
SELECT *
FROM #ids AS [i]
WHERE id NOT IN ( SELECT CustomerID
FROM [Customer] AS [c] );
1) Has the insert values failed because my CustomerID column in
Customer table in NOT NULL and I in error made CustomerID column NULL
in Order.
No. The error is not related to allowing NULL in the Order table. A NULL value will be allowed and not checked for referential integrity.
The foreign key violation error means you are attempting to insert a non-NULL CustomerID value into the Order table that does not exist in Customer. If you are certain the CustomerID values exist, perhaps the column mapping is wrong. Try specifying an explicit column list on the INSERT statement.
This error happens whern you are trying to insert a value in foreign key column, which this value does not exists in it's parent table. for example you are trying to insert value X to CustomerId in Order table, which this value does not exists in Customer table. This error occurred because we need to have a good strategy for Referential Integrity. So the only you need to do, is to check your new values(which you are going to insert them into table) to find out that is there any value compromising this rule or not.
However if you want to get an answer for your second question, you can try the below script:
create table t1
(
Id int primary key,
Name varchar(50) null
)
create table t2
(
Id int,
FK int null foreign key references t1(id)
)
go
alter table t2
alter column FK int not null
The identity column is set up once when you create the table.
The id assigned by an identity column start by the seed and are never reused.
So if you find that your customer ids starts from 6, it means that in the past you have added 5 customers and removed it.
If, for any reason, you want to use fixed Id don't use identity. In that case you take full responsability to set a unique value.
I suggest to never rely on fixed ids, if you must add orders from a script use the CustomerName (if unique), or any natural unique key.
You could use a script like this
DECLARE #newOrders TABLE (OrderID INT, CustomerName VARCHAR(25), OrderDate DATE);
INSERT INTO #newOrders (OrderID, CustomerName, OrderDate) VALUES
(1001, 'some-username', '2008-10-21'),
(1002, 'another-username', '2008-10-21');
INSERT INTO Orders(OrderID, CustomerId, OrderDate)
SELECT
o.OrderID,
c.CustomerID,
o.OrderDate
FROM #newOrders o
JOIN Customer c
ON c.CustomerName = o.CustomerName;
In this way you insert the correct CustomerID.
Note that in very rare cases (think twice to use it) you could insert values in identity colums using SET IDENTITY_INSERT statement.
I have two tables: table A and table B. These two tables are linked with a primary key in A and a foreign key in B.
Table A:
CREATE TABLE [BIO].[table_A](
[table_A_id] [int] IDENTITY(1,1) NOT NULL,
[type_id] [nvarchar](2) NOT NULL
CONSTRAINT [PK_table_A] PRIMARY KEY CLUSTERED
(
[table_A_id] ASC
))
Table B:
CREATE TABLE [BIO].[table_B](
[table_B_id] [int] IDENTITY(1,1) NOT NULL,
[table_A_id] [int] NOT NULL,
[analysis_id] [tinyint] NOT NULL
CONSTRAINT [PK_table_B] PRIMARY KEY CLUSTERED
(
[table_B_id] ASC
))
ALTER TABLE [BIO].[table_B] WITH CHECK
ADD CONSTRAINT [FK_table_B_table_A] FOREIGN KEY([table_A_id])
REFERENCES [BIO].[table_A] ([table_A_id])
GO
ALTER TABLE [BIO].[table_B] CHECK CONSTRAINT [FK_table_B_table_A]
GO
Table B must contain only specific values according to the values in table A.
For example, if I have BL in table A, I can only have 1 or 3 in table B; if I have ST in table A, I can only have 2 or 4 in table B.
I have setup a bridge table which defines these combinations: BL→1 or 3, ST→2 or 4.
Bridge table:
CREATE TABLE [QRY].[bridge_table](
[type_id] [nvarchar](2) NOT NULL,
[analysis_id] [tinyint] NOT NULL,
CONSTRAINT [PK_bridge_table] PRIMARY KEY CLUSTERED
(
[type_id] ASC,
[analysis_id] ASC
))
I am currently using one constraint per table to be sure that any insert or update is correct according to the combinations defined in the bridge table. These two constraints are based on UDFs.
Constraint on table B:
ALTER TABLE [BIO].[Table_B] WITH CHECK
ADD CONSTRAINT [CK_chkAnalysisType]
CHECK (([QRY].[TypeAnalysisMatch_table_B]([table_A_id])>(0)))
GO
UDF:
CREATE FUNCTION [QRY].[TypeAnalysisMatch_table_B] (#table_A_id int)
RETURNS int
AS
BEGIN
RETURN
(
SELECT
Count(BIO.table_A.table_A_id) AS cnt_rec
FROM
QRY.bridge_table
INNER JOIN BIO.table_A ON QRY.bridge_table.type_id = BIO.table_A.type_id
INNER JOIN BIO.table_B ON
QRY.bridge_table.analysis_id = BIO.table_B.analysis_id
AND BIO.table_A.table_A_id = BIO.table_B.table_A_id
WHERE
BIO.table_A.table_A_id = #table_A_id
)
END
It works well for the INSERT but not consistently for the UPDATE. Moreover, as I read that UDFs in constraints should be avoided, I am looking for a better solution.
What would be an efficient alternative to these constraints?
You are right, having UDF in CHECK constraints can be tricky and some UPDATE statements may bypass the check:
http://sqlblog.com/blogs/tibor_karaszi/archive/2009/12/17/be-careful-with-constraints-calling-udfs.aspx
MSSQL: Update statement avoiding the CHECK constraint
As you can see in that SO question the answer recommended to use trigger for the check. Writing a correct efficient trigger is also not an easy task.
I assume that your bridge_table contains this data:
type_id analysis_id
BL 1
BL 3
ST 2
ST 4
I would set up these constraints using only foreign keys, without UDF. It would require some (minimal) duplication of the data, though. I assume that real table_A and table_B have more columns than this example.
1. In table_A include type_id in the primary key:
CREATE TABLE [table_A](
[table_A_id] [int] IDENTITY(1,1) NOT NULL,
[type_id] [nvarchar](2) NOT NULL,
CONSTRAINT [PK_table_A] PRIMARY KEY CLUSTERED
(
[table_A_id] ASC,
[type_id] ASC
))
2. Add a column type_id to the table_B. Yes, the same column as you already have in table_A. This is that duplication of data that I mentioned above:
CREATE TABLE [table_B](
[table_B_id] [int] IDENTITY(1,1) NOT NULL,
[table_A_id] [int] NOT NULL,
[type_id] [nvarchar](2) NOT NULL,
[analysis_id] [tinyint] NOT NULL
CONSTRAINT [PK_table_B] PRIMARY KEY CLUSTERED
(
[table_B_id] ASC
))
3. Make foreign key that links table_B with table_A on two columns (table_A_id, type_id):
ALTER TABLE [table_B] WITH CHECK
ADD CONSTRAINT [FK_table_B_table_A] FOREIGN KEY([table_A_id], [type_id])
REFERENCES [table_A] ([table_A_id], [type_id])
This constraint guarantees that type_id values that are duplicated in table_B will be consistent with original values from table_A.
4. Make foreign key that links table_B with bridge_table again on two columns (type_id, analysis_id):
ALTER TABLE [table_B] WITH CHECK
ADD CONSTRAINT [FK_table_B_bridge_table] FOREIGN KEY([type_id], [analysis_id])
REFERENCES [bridge_table] ([type_id], [analysis_id])
5. Now you can test that everything works as intended.
Add few rows to table_A:
INSERT INTO [table_A] ([type_id])
VALUES ('BL'), ('BL'), ('ST'), ('ZZ');
table_A_id type_id
1 BL
2 BL
3 ST
4 ZZ
Try to insert valid data into table_B:
INSERT INTO [dbo].[table_B] ([table_A_id],[type_id],[analysis_id])
VALUES (1,'BL',1)
INSERT INTO [dbo].[table_B] ([table_A_id],[type_id],[analysis_id])
VALUES (1,'BL',3)
INSERT INTO [dbo].[table_B] ([table_A_id],[type_id],[analysis_id])
VALUES (2,'BL',3)
INSERT INTO [dbo].[table_B] ([table_A_id],[type_id],[analysis_id])
VALUES (3,'ST',2)
INSERT INTO [dbo].[table_B] ([table_A_id],[type_id],[analysis_id])
VALUES (3,'ST',2)
table_B_id table_A_id type_id analysis_id
1 1 BL 1
2 1 BL 3
3 2 BL 3
4 3 ST 2
5 3 ST 2
Try to insert invalid data:
INSERT INTO [dbo].[table_B] ([table_A_id],[type_id],[analysis_id])
VALUES (3,'ST',1)
The INSERT statement conflicted with the FOREIGN KEY constraint "FK_table_B_bridge_table".
The conflict occurred in database "tempdb", table "dbo.bridge_table".
The statement has been terminated.
Which means, that ST can't have analysis_id=1
INSERT INTO [dbo].[table_B] ([table_A_id],[type_id],[analysis_id])
VALUES (3,'BL',1)
The INSERT statement conflicted with the FOREIGN KEY constraint "FK_table_B_table_A".
The conflict occurred in database "tempdb", table "dbo.table_A".
The statement has been terminated.
Which means, that the row in table_A with table_A_id=3 doesn't have BL in type_id.
Foreign keys would keep checking data consistency for all UPDATE statements as well:
UPDATE [dbo].[table_B]
SET [type_id] = 'ST'
WHERE [table_B_id] = 1
The UPDATE statement conflicted with the FOREIGN KEY constraint "FK_table_B_table_A".
The conflict occurred in database "tempdb", table "dbo.table_A".
The statement has been terminated.
UPDATE [dbo].[table_B]
SET [analysis_id] = 2
WHERE [table_B_id] = 1
The UPDATE statement conflicted with the FOREIGN KEY constraint "FK_table_B_bridge_table".
The conflict occurred in database "tempdb", table "dbo.bridge_table".
The statement has been terminated.
But this one works:
UPDATE [dbo].[table_B]
SET [analysis_id] = 3
WHERE [table_B_id] = 1
(1 row(s) affected)
I have a little strange issue with my SQL script and I was hoping someone could help me out with it.
I have a Database being created by using
IF EXISTS (SELECT name
FROM sysdatabases
WHERE name = 'travel')
DROP DATABASE travel
GO
CREATE DATABASE travel
GO
USE travel
GO
I then create 3 tables as shown below
CREATE TABLE customer
(
customerID INT,
lastname VARCHAR(70) NOT NULL,
firstname VARCHAR(70) NOT NULL,
phone VARCHAR(10) CONSTRAINT phoneCheck CHECK ((phone LIKE '[0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9]')),
category VARCHAR(7) NOT NULL CONSTRAINT categoryDefault DEFAULT 'A',
CONSTRAINT categoryCheck CHECK (category IN ('A', 'B', 'C')),
CONSTRAINT customerPK
PRIMARY KEY (customerID)
)
CREATE TABLE package /*Still need to do the Zero Padding*/
(
packageCode VARCHAR(6),
destination VARCHAR(70),
CONSTRAINT packageCodeCheck CHECK (packageCode LIKE ('YFK%')),
price MONEY NOT NULL CONSTRAINT priceCheck CHECK ((price BETWEEN 1000 AND 10000)),
passportRequired VARCHAR(7) NOT NULL CONSTRAINT passportRequiredDefault DEFAULT 'Y',
CONSTRAINT passportCheck CHECK (passportRequired IN ('Y', 'N')),
CONSTRAINT packagePK
PRIMARY KEY (packageCode)
)
CREATE TABLE booking /*Still need to do the Customer and Package delete*/
(
customerID VARCHAR(6),
bookingDate VARCHAR(70) NOT NULL DEFAULT GETDATE(),
amountPaid MONEY CONSTRAINT amountPaidDefault DEFAULT 0.00,
CONSTRAINT bookingPK
PRIMARY KEY (customerID)
)
Now heres the issue, I create a trigger as shown below
GO
CREATE TRIGGER customerDelete ON customer AFTER DELETE
AS
DELETE booking
FROM customer
WHERE customer.customerID = booking.customerID
GO
Which to my understanding it will delete all records in booking... that have the matching customerID WHEN a record is deleted from the customer Table. (I am new to triggers)
I INSERT Sample Data as shown below
INSERT INTO customer
(customerID, lastname, firstname, phone, category)
VALUES
(1, 'Picard', 'Corey', 1234567890, 'A'),
(2, 'Bond', 'Devon', 9876543210, 'B'),
(3, 'Douglas', 'Bryan', 6549871230, 'C')
INSERT INTO package
(packageCode, destination, price, passportRequired)
VALUES
('YFK001', 'Toronto', 1000.57, 'N'),
('YFK002', 'Orlando', 3000.98, 'Y')
INSERT INTO booking
(customerID, bookingDate, amountPaid)
VALUES
(1, GETDATE(), 1548),
(2, GETDATE(), 1586),
(3, GETDATE(), 1350),
(4, GETDATE(), 1650)
And Finally I delete the Customer from the TABLE customer with the customerID of 1 by using
DELETE customer
WHERE customerID = 1
However, when I attempt to see the results by using
SELECT * FROM customer
--WHERE customerID = 1 OR customerID = 2 OR customerID = 3
SELECT * FROM package
--WHERE packageCode = 'YFK001' OR packageCode = 'YFK002'
SELECT * FROM booking
--WHERE customerID = 1 OR customerID = 2 OR customerID = 3 OR customerID = 4
It displays bookings with customerID 1 and 4.
Can you let me know what I'm doing wrong?
The trigger is essentially used for the purpose of deleting the bookings with the same customerID of the customer we delete from the customer TABLE
All help is greatly appreciated.
Thanks,
Bryan
Change your delete to this:
DELETE B
FROM booking B
INNER JOIN DELETED D
ON B.customerID = D.customerID;
My Answer is not trigger, [ If you specially want to use Trigger then You can use Lamak's & Pradeep's Answer]
Here best way you can do is use Cacade on foreign Key in your case
Here is your Query I just updated cascade in it
CREATE TABLE customer
(
customerID INT,
lastname VARCHAR(70) NOT NULL,
firstname VARCHAR(70) NOT NULL,
phone VARCHAR(10) CONSTRAINT phoneCheck CHECK ((phone LIKE '[0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9]')),
category VARCHAR(7) NOT NULL CONSTRAINT categoryDefault DEFAULT 'A',
CONSTRAINT categoryCheck CHECK (category IN ('A', 'B', 'C')),
CONSTRAINT customerPK
PRIMARY KEY (customerID)
)
CREATE TABLE package /*Still need to do the Zero Padding*/
(
packageCode VARCHAR(6),
destination VARCHAR(70),
CONSTRAINT packageCodeCheck CHECK (packageCode LIKE ('YFK%')),
price MONEY NOT NULL CONSTRAINT priceCheck CHECK ((price BETWEEN 1000 AND 10000)),
passportRequired VARCHAR(7) NOT NULL CONSTRAINT passportRequiredDefault DEFAULT 'Y',
CONSTRAINT passportCheck CHECK (passportRequired IN ('Y', 'N')),
CONSTRAINT packagePK
PRIMARY KEY (packageCode)
ON DELETE CASCADE
ON UPDATE CASCADE
)
CREATE TABLE booking /*Still need to do the Customer and Package delete*/
(
customerID VARCHAR(6),
bookingDate VARCHAR(70) NOT NULL DEFAULT GETDATE(),
amountPaid MONEY CONSTRAINT amountPaidDefault DEFAULT 0.00,
CONSTRAINT bookingPK
PRIMARY KEY (customerID)
ON DELETE CASCADE
ON UPDATE CASCADE
)
This way when you are deleting or update [keyvalue] any entry of Table holding primary key will update its related foreign childs