im new on mysql workbench, and i tried so many things to put my script working but i simply cant... Ive got these tables:
CREATE TABLE Utilizador (email varchar(40) not null, nome varchar(50)
not null, dataNascimento date, profissao varchar(50) not null,
reputacao double(3,2) unsigned not null, constraint pk_Utilizador
primary key(email))
This is the first table created!
CREATE TABLE POI (email varchar(40) not null, designacaoPOI
varchar(10) not null, coordenadaX int, coordenadaY int,
descricaoPOI varchar(200), constraint pk_POI primary key(email,
designacaoPOI), constraint fk_POI foreign key(email) references
Utilizador(email) on delete cascade)
This is the second table created!
CREATE TABLE Utilizador_POI (email varchar(40) not null, designacaoPOI
varchar(10) not null, constraint pk_Utilizador_POI primary key(email,
designacaoPOI), constraint fk1_Utilizador_POI foreign key(email)
references Utilizador(email) on delete cascade, constraint
fk2_Utilizador_POI foreign key(designacaoPOI) references
POI(designacaoPOI) on delete cascade)
This table gives me the error: Error Code: 1215. Cannot add foreign key constraint
I did some tests and im almost sure that the problem is in the foreign key "designacaoPOI". The other FK ("email") dont give me any error, so maybe the problem is in the Table POI?
Thanks in advanced!
The problem here is twofold:
1/ Use ID
s for PRIMARY KEY
s
You should be using ID
s for primary keys rather than VARCHAR
s or anything that has any real-world "business meaning". If you want the email
to be unique within the Utilizador
table, the combination of email
and designacaoPOI
to be unique in the POI
table, and the same combination (email
and designacaoPOI
) to be unique in Utilizador_POI
, you should be using UNIQUE KEY
constraints rather than PRIMARY KEY
constraints.
2/ You cannot DELETE CASCADE
on a FOREIGN KEY
that doesn't reference the PRIMARY KEY
In your third table, Utilizador_POI
, you have two FOREIGN KEY
s references POI
. Unfortunately, the PRIMARY KEY
on POI
is a composite key, so MySQL has no idea how to handle a DELETE CASCADE
, as there is not a one-to-one relationship between the FOREIGN KEY
in Utilizador_POI
and the PRIMARY KEY
of POI
.
If you change your tables to all have a PRIMARY KEY
of ID
, as follows:
CREATE TABLE blah (
id INT(9) AUTO_INCREMENT NOT NULL
....
PRIMARY KEY (id)
);
Then you can reference each table by ID
, and both your FOREIGN KEY
s and DELETE CASCADE
s will work.
I think the problem is that Utilizador_POI.email
references POI.email
, which itself references Utilizador.email
. MySQL is probably upset at the double-linking.
Also, since there seems to be a many-to-many relationship between Utilizador
and POI
, I think the structure of Utilizador_POI
isn't what you really want. Instead, Utilizador_POI
should reference a primary key from Utilizador
, and a matching primary key from POI
.
The problem is in your second table. Your primary key is (email,designacaoPOI), when you try to reference that in your table it gives you error because of this:
InnoDB permits a foreign key to reference any index column or group of
columns. However, in the referenced table, there must be an index
where the referenced columns are listed as the first columns in the
same order.
For it to work, either change the order of your second tale PRIMARY KEY :
CREATE TABLE POI (
email VARCHAR(40) NOT NULL,
designacaoPOI VARCHAR(10) NOT NULL,
coordenadaX INT,
coordenadaY INT,
descricaoPOI VARCHAR(200),
CONSTRAINT pk_POI PRIMARY KEY (designacaoPOI,email), -- changed the order
CONSTRAINT fk_POI FOREIGN KEY (email)
REFERENCES Utilizador(email) ON DELETE CASCADE
);
sqlfiddle demo
or add an index for designacaoPOI:
CREATE TABLE POI (
email VARCHAR(40) NOT NULL,
designacaoPOI VARCHAR(10) NOT NULL,
coordenadaX INT,
coordenadaY INT,
descricaoPOI VARCHAR(200),
CONSTRAINT pk_POI PRIMARY KEY (designacaoPOI,email),
KEY key_designacaoPOI(designacaoPOI), -- added index for that column
CONSTRAINT fk_POI FOREIGN KEY (email)
REFERENCES Utilizador(email) ON DELETE CASCADE
);
sqlfiddle demo
Either of these solutions will let you create your third table without errors.