SQL and Table
Constraints
CMSC 461
Michael Wilson
A few more basic commands
All
we’ve gone over so far, there’s two
more commands I’d like to elaborate on
Delete statement
To
get rid of existing rows in a table, use a
delete statement
DELETE FROM <table>
WHERE <where-clause>
Delete statement
DELETE
FROM AddressBook
Where phoneType = ‘Cell’;
Alter table
Say
you’ve discovered an issue in the
schema you’ve provided to your
database
How do you correct that?
Altering the table
There are several variants on this
Alter table
Basic
syntax:
ALTER TABLE <table>
<action>
<action> can be:
RENAME
<column> to <new_column>
RENAME to <new_table_name>
ADD <column> <data_type>
DROP <column> <data_type>
ALTER <column> TYPE <data_type>
Alter table
Alter
table can do much more than this
These are kind of the more frequently
applicable actions
Going to leave the example part of this as
an exercise for you
It’s
infrequently used and there are a lot of
nuances to it that make it difficult to show a
concrete example for
Table constraints
When
designing your tables, you should
often think about exactly how the data
should fall together
Putting together a database schema
should not be a quick step
SQL
and DBMSes have built in methods for
enforcing interrelated tables
Keys!
Remember
our talk of keys from before?
Extremely important when designing tables
In
general, most tables will have primary
keys
If you’re designing a table that doesn’t
have one, you should question whether or
not the table is designed properly
Primary key constraints
Your
table creation scripts should always
contain a primary key constraint
This requires a slight modification to our
create table statement
Let’s look at our AddressBook table
Primary key constraints
CREATE
TABLE AddressBook
(address varchar(256),
daysSinceContact integer,
contactPhoneNumber varchar(64),
numberType varchar(16),
contactName varchar(256));
Primary key constraints
Let’s
add an identifier to this that will be
our primary key
Primary key constraints
CREATE
TABLE AddressBook
(id integer PRIMARY KEY,
address varchar(256),
daysSinceContact integer,
contactPhoneNumber varchar(64),
numberType varchar(16),
contactName varchar(256));
Primary key constraints
id
address
lastContacted
contactPhoneNum
ber
numberType
contactName
1
111 Great
Street
1 day
ago
555
5555
Cell
Phil
2
123 Not So
Great
Street
Last
month
555
6666
Landline Henry
3
8 Get Out
of Here
Way
Last
week
555
7777
Work
Bob
4
7 RUN!
Drive
2 years
ago
555
8888
Cell
Octavio
Primary key constraints
Primary
If you try to insert an entry with a duplicate
primary key, it will give you an error
This is good – it enforces your DB schema for
you
Also,
keys must be unique
primary keys must be present
Cannot be NULL, which we’ll get into later
Primary key note
The
“id” method is pretty frequently used
in DB design
Easy way to have a key that you can
reference by a single number
Compound keys
Compound
keys are keys that consist of
multiple columns
Sometimes it requires several attributes to
identify an item
Compound keys
dogName
dogDOB
favoriteToy
Fido
2/20/2004
Chew toy
Benjamin
6/01/2007
Ball
Cujo
5/07/2008
Squeaky toy
Compound keys
CREATE
TABLE FavoriteDogToys
(dogName varchar(128),
dogDOB date,
favoriteToy varchar(256),
PRIMARY KEY (dogName, dogDOB));
Foreign keys
When
you have interrelated tables, often
times you’ll have a table that depends on
the primary key of another table
Very akin to the weak entities we saw in ER
Diagramming
Let’s take our previous AddressBook
example and imagine a new table, Calls
Foreign keys
addressBookId
callTime
callLength
1
2/4/13
0:20:00
1
5/2/12
1:23:00
4
12/12/13
0:05:00
3
07/7/12
0:02:00
4
07/8/12
0:59:00
Foreign keys
CREATE TABLE Calls (
addressBookId REFERENCES AddressBook,
callTime timestamp,
callLength interval
);
What is the primary key in this table?
Foreign keys
CREATE TABLE Calls (
addressBookId REFERENCES AddressBook,
callTime timestamp,
callLength interval,
PRIMARY KEY(addressBookId, callTime)
);
Foreign keys
We
are unable to create any entries in
the Calls table without there being a
corresponding addressBookId in the
AddressBook table
PostgreSQL will give us an error if we
attempt to do so
What to do about foreign keys
and deletes?
Say
we’ve got a situation where
somebody wants to delete a row that
we’re referencing
What behavior do we want to exhibit?
We can use ON DELETE to specify
ON DELETE
ON DELETE takes an action modifier
NO ACTION (by default)
RESTRICT
If a referenced row is deleted, this row is removed as well
SET NULL
Prevents the deletion of a referenced row
CASCADE
If somebody attempts to delete something that we’re
referencing, we do nothing and throw an error
If a referenced row is deleted, the value in this row is set
to NULL
SET DEFAULT
If a referenced row is deleted, the value in this row is set
to the DEFAULT value for that row
ON DELETE RESTRICT
CREATE TABLE Calls (
addressBookId REFERENCES AddressBook ON
DELETE RESTRICT,
callTime timestamp,
callLength interval
);
If we attempt to delete an entry from
AddressBook, what happens?
ON DELETE CASCADE
CREATE
TABLE Calls (
addressBookId REFERENCES
AddressBook ON DELETE CASCADE,
callTime timestamp,
callLength interval
);
If we attempt to delete an entry from
AddressBook, what happens?
Why?
Why
not just handle all this stuff in code?
Foreign keys, etc. don’t necessarily add
functionality
We could handle ON DELETES in code
Referential integrity
Referential
integrity is essentially ensuring
that relationships between tables remain
consistent
By declaring things as foreign keys, explicitly
stating ON DELETEs, you ensure that it’s
impossible to enter an inconsistent state
Impossible to have a foreign key reference
that no longer exists
Your
data is more predictable and
reliable