The term 'Foreign Key Constraint' is often tossed around. And I just want to clarify it's exact meaning. We have an employees table and a branches table. The employees table was created first but it should have a foreign key constraint on branch_id, which references the primary (surrogate) key of id on branches table:
CREATE TABLE employees (
id INT AUTO_INCREMENT,
first_name VARCHAR(40),
last_name VARCHAR(40),
birth_day DATE,
sex BOOLEAN,
salary INT,
supervisor_id INT,
branch_id INT,
PRIMARY KEY(id)
)
CREATE TABLE branches (
id INT AUTO_INCREMENT,
branch_name VARCHAR(40),
manager_id INT,
manager_start_date DATE,
PRIMARY KEY(id),
FOREIGN KEY(manager_id) REFERENCES employees(id) ON DELETE SET NULL
)
And now we add the Foreign Key Constraints:
ALTER TABLE employees
ADD FOREIGN KEY(branch_id)
REFERENCES branches(id)
ON DELETE SET NULL;
ALTER TABLE employees
ADD FOREIGN KEY(supervisor_id)
REFERENCES employees(id)
ON DELETE SET NULL;
Notice here I use Add Foreign Key and not Add Constraint constraint_name. Here would be an example of using ADD CONSTRAINT:
ALTER TABLE users
ADD CONSTRAINT check_users_age
CHECK (age>=18 AND city='Philadelphia');
Is ADD FOREIGN KEY and ADD CONSTRAINT constraint_name synonymous? Does ADD FOREIGN KEY, in effect, add a constraint without a name? And if ADD FOREIGN KEY does add a name, how can I find it in mysql?
Explicitly naming the constraint, i.e. use CONSTRAINT <name> FOREIGN KEY ... is optional. If you don't do it, i.e. just go with FOREIGN KEY ... the system generates a name.
The effects a constraint have are independent of its name. So both, explicitly naming the constraint and not doings so are synonym-ish -- that is except regarding the name.
You can query the constraints from the catalog, e.g. from information_schema.key_column_usage.
Consider the following example:
CREATE TABLE a
(id integer,
PRIMARY KEY (id));
CREATE TABLE b
(id integer,
PRIMARY KEY (id));
CREATE TABLE x
(a integer,
b integer,
FOREIGN KEY (a)
REFERENCES a
(id),
CONSTRAINT fancy_name
FOREIGN KEY (b)
REFERENCES b
(id));
SELECT table_name,
column_name,
constraint_name,
referenced_table_name,
referenced_column_name
FROM information_schema.key_column_usage
WHERE table_schema = database()
AND table_name = 'x';
This will result in something like:
| table_name | column_name | constraint_name | referenced_table_name | referenced_column_name |
| ---------- | ----------- | --------------- | --------------------- | ---------------------- |
| x | b | fancy_name | b | id |
| x | a | x_ibfk_1 | a | id |
DB Fiddle
You can see, the system picked a name for the constraint.
Related
Considering a tables schema as following below:
create schema simulado;
use simulado;
create table mo(
id integer Primary Key auto_increment,
groupTypologyId int,
typologyId int,
contractId varchar(45),
tradeDate datetime,
index (id)
);
create table eq(
id int,
typologyId int,
typologyName varchar(20),
delta decimal,
index(typologyId),
constraint fk_ideq foreign key (id) references mo (id)
);
create table cm(
id int,
typologyId int,
typologyName varchar(20),
shortleg decimal,
index(typologyId),
constraint fk_idcm foreign key (id) references mo (id)
);
create table ir(
id int,
typologyId int,
typologyName varchar(20),
isin varchar(20),
index(typologyId),
constraint fk_idir foreign key (id) references mo (id)
);
create table fx(
id int,
typologyId int,
typologyName varchar(20),
dma bit,
index(typologyId),
constraint fk_idfx foreign key (id) references mo (id)
);
alter table mo
add constraint fk_eq foreign key (typologyId) references eq(TypologyId),
add constraint fk_fx foreign key (typologyId) references fx(TypologyId),
add constraint fk_ir foreign key (typologyId) references ir(TypologyId),
add constraint fk_cm foreign key (typologyId) references cm(TypologyId);
I need to insert the data in such a way that, from the values of the groupTypologyId column by mo, the data is taken to columns referring to the groupTypologyId. For example, groupTypologyId = 1 refers to table eq, and groupTypologyId = 2 refers to table fx.
Mo Table
id | groupTypologyId | typologyId | contractId | tradeDate
1 | 1 | 1 | xxxxxxxxxx | 03/04/2020
2 | 2 | 5 | yyyyyyyyyy | 03/02/2020
Eq Table
id | TypologyId | TypologyName | Delta
1 | 1 | Eq A | 0.5
Fx Table
id | TypologyId | TypologyName | dma
2 | 5 | Fx A | 0
So, I would like to create a command that analyzes the value of groupTypolyId in mo, and from that analysis direct TypologyId to the table referring to its typology and then perform another insert with the specific columns of each table. Is it possible to do this in MySQL? I am trying, unsuccessfully, with the command below, which tries to get the Id inserted by hand, that even if it was successful, this is not the way I want to do it.
use simulado;
insert into mo values (1,1,1,'xxxx', now());
select Last_Insert_Id() into #gp;
insert into eq values(#gp, 1, 'eq a', 0.5);
In the given Images, There are two tables. In the table STUD_MEMBER, Dept_ID is a foreign key which is referring to Dept_ID in table DEPARTMENT.:
So when I add foreign key constraints in mysql at phpmyadmin like
CREATE TABLE DEPARTMENT(
Dept_ID INT,
Dept_Name VARCHAR(25));
INSERT INTO DEPARTMENT VALUES(1,"Information Technology");
INSERT INTO DEPARTMENT VALUES(2,"Electrical");
INSERT INTO DEPARTMENT VALUES(3,"Civil");
INSERT INTO DEPARTMENT VALUES(4,"Mechanical");
INSERT INTO DEPARTMENT VALUES(5,"Chemical");
CREATE TABLE STUD_MEMBER(
Roll_No INT NOT NULL PRIMARY KEY,
FName VARCHAR(20),
MName VARCHAR(20),
SName VARCHAR(20),
Dept_ID INT,
FOREIGN KEY (Dept_ID) REFERENCES DEPARTMENT(Dept_ID),
Semester INT,
Contact_No INT,
Gender VARCHAR(6));
It is showing an error that 1215- cannot add foreign key constraint. As far as I know, it is the correct way to add a foreign key, I am so confused why it is wrong. Please help in solving this.
It looks like the referenced column has to be either a primary key, or it has to have a unique index. The following CREATE TABLE statement worked for me:
CREATE TABLE DEPARTMENT (
Dept_ID INT PRIMARY KEY NOT NULL,
Dept_Name VARCHAR(25)
);
if you are defining foreign key in child, the parent field must have an index defined on it.
check reference from HERE
[CONSTRAINT [symbol]] FOREIGN KEY
[index_name] (index_col_name, ...)
REFERENCES tbl_name (index_col_name,...)
[ON DELETE reference_option]
[ON UPDATE reference_option]
reference_option:
RESTRICT | CASCADE | SET NULL | NO ACTION | SET DEFAULT
I have the following table:
CREATE TABLE IF NOT EXISTS profile_claim_ruling_tasks (
profile_claim_ruling_task_id BIGINT UNSIGNED NOT NULL AUTO_INCREMENT,
account_id BIGINT UNSIGNED NOT NULL,
profile_id BIGINT UNSIGNED NOT NULL,
admin_task_status_id BIGINT UNSIGNED NOT NULL,
profile_claim_ruling_task_ref_id VARCHAR(36) NOT NULL,
profile_claim_ruling_task_requested_at DATETIME NOT NULL,
CONSTRAINT pk_profile_claim_ruling_tasks PRIMARY KEY (profile_claim_ruling_task_id),
CONSTRAINT fk_profile_claim_ruling_task_account_id FOREIGN KEY (account_id) REFERENCES accounts (account_id),
CONSTRAINT fk_profile_claim_ruling_task_profile_id FOREIGN KEY (profile_id) REFERENCES accounts (profile_id),
CONSTRAINT fk_profile_claim_ruling_task_admin_task_status_id FOREIGN KEY (admin_task_status_id) REFERENCES admin_task_statuses (admin_task_status_id),
INDEX idx_profile_claim_ruling_tasks_admin_task_status_id(admin_task_status_id),
CONSTRAINT uc_profile_claim_ruling_tasks_profile_claim_ruling_tasks_ref_id UNIQUE (profile_claim_ruling_task_ref_id)
);
When I do a SELECT * on accounts:
+------------+--------------------------------------+------------+
| account_id | account_ref_id | profile_id |
+------------+--------------------------------------+------------+
| 1 | 521ef2cb-01f9-49f3-a214-42e1514d7dc2 | 1 |
+------------+--------------------------------------+------------+
And when I do a SELECT * on profiles:
+------------+--------------------------------------+
| profile_id | profile_ref_id |
+------------+--------------------------------------+
| 2 | 1d8caa66-e080-4cc6-88ff-a063e576bafa |
| 3 | 619a7ec6-813a-41f0-a1f9-16289893df5d |
| 4 | c50ceb2f-49f0-4319-b115-0a1454593c46 |
| 1 | d6369f9b-b66a-468c-86f9-a7e0abc75b65 |
+------------+--------------------------------------+
So far, so good! But when I run the following insert:
INSERT INTO profile_claim_ruling_tasks (
account_id,
profile_id,
admin_task_status_id,
profile_claim_ruling_task_ref_id,
profile_claim_ruling_task_requested_at
) VALUES (
1,
4,
1,
'4bed7334-e17b-462f-a7e6-454c3b2f5235',
'2018-01-29 13:12:57'
);
I get the following error:
ERROR 1452 (23000): Cannot add or update a child row: a foreign key constraint fails (`myapp_db`.`profile_claim_ruling_tasks`, CONSTRAINT `fk_profile_claim_ruling_task_profile_id` FOREIGN KEY (`profile_id`) REFERENCES `accounts` (`profile_id`))
What's going on here?!
FOREIGN KEY (profile_id) REFERENCES accounts (profile_id)
You are trying to insert data with profile_id=4 in table profile_claim_ruling_tasks, which is referring to accounts (profile_id).
But, you don't have profile_id=4 in accounts table. You need to populate accounts table first to resolve this issue.
You appear to have an error in your first SHOW CREATE TABLE,
CONSTRAINT fk_profile_claim_ruling_task_profile_id FOREIGN KEY (profile_id) REFERENCES accounts (profile_id),
should be
CONSTRAINT fk_profile_claim_ruling_task_profile_id FOREIGN KEY (profile_id) REFERENCES profiles (profile_id),
IMO.
I have created the following tables:
A3STUDENT
CREATE TABLE A3STUNDENT(
STD_ID INTEGER NOT NULL,
STD_NAME VARCHAR(30),
STD_MAJOR CHAR(4),
STD_RANK CHAR(2),
CONSTRAINT PK_A3STUDENT PRIMARY KEY (STD_ID)
);
CREATE TABLE A3COURSE(
CRS_TIME VARCHAR(10),
CRS_ROOM CHAR(5),
CRS_ID CHAR(7) NOT NULL,
CONSTRAINT PK_A3COURSE PRIMARY KEY (CRS_ID)
);
CREATE TABLE A3ENROLL(
ENR_GRADE CHAR(1),
STD_ID INTEGER NOT NULL,
CRS_ID CHAR(7) NOT NULL,
CONSTRAINT PK_A3ENROLL PRIMARY KEY (STD_ID, CRS_ID),
CONSTRAINT FK_STD_ENR FOREIGN KEY (STD_ID) REFERENCES A3STUDENT(STD_ID),
CONSTRAINT FK_CRS_ENR FOREIGN KEY (CRS_ID) REFERENCES A3COURSE(CRS_ID)
);
When I go to insert values such as this:
INSERT INTO A3ENROLL VALUES ('A', 100, 'MGMT445');
I receive this error:
#1452 - Cannot add or update a child row: a foreign key constraint fails (Hess.A3ENROLL, CONSTRAINT FK_CRS_ENR FOREIGN KEY
(CRS_ID) REFERENCES A3COURSE (CRS_ID))
I have can't seem to understand why my data won't insert. What am I overlooking?
This usually happens because have not data in the A3STUNDENT andA3COURSE tables.
The foreign key relationships means that a primary table that contains the central data values and a child table with identical values pointing to the parent, any INSERT or UPDATE operation that attempts to create a foreign key value in a child table is rejected if there is no matching candidate key value in the parent table.
The table A3ENROLL is taking as reference100 and MGMT445 that does not exist in the tables mentioned above.
Before inserting data in the A3ENROLL table, you must be sure that there are data in the other tables A3STUNDENT and A3COURSE, because the tableA3ENROLL has a foreign key of A3STUNDENT andA3COURSE, this means that you must have these data in those tables, for example:
Select * from A3STUNDENT;
STD_ID | STD_NAME | STD_MAJOR | STD_RANK
100 | 'Zack' | ... | ....
Select * from A3COURSE;
CRS_ID | CRS_ROOM | CRS_TIME
MGMT445 | ... | ....
You can try to insert data in the previous tables and then insert in the table A3ENROLL.
Here you have more info: https://dev.mysql.com/doc/refman/5.6/en/create-table-foreign-keys.html
I want to create a references to foreign table. but i'm getting the following error:
query:
CREATE TABLE category_ids (id INT, post_id INT,
INDEX par_ind (post_id),
FOREIGN KEY (post_id) REFERENCES post(id)
ON DELETE CASCADE
) ENGINE=INNODB;
SHOW ENGINE INNODB STATUS\G:
------------------------
LATEST FOREIGN KEY ERROR
------------------------
2013-08-23 00:11:06 7f6f49e7b700 Error in foreign key constraint of table fun/category_ids:
FOREIGN KEY (post_id) REFERENCES post(id)
ON DELETE CASCADE
) ENGINE=INNODB:
Cannot resolve table name close to:
(id)
ON DELETE CASCADE
) ENGINE=INNODB
posts table structure
mysql> describe post;
+-------------+-----------------------+------+-----+---------------------+----------------+
| Field | Type | Null | Key | Default | Extra |
+-------------+-----------------------+------+-----+---------------------+----------------+
| id | int(11) | NO | PRI | NULL | auto_increment |
...
+-------------+-----------------------+------+-----+---------------------+----------------+
22 rows in set (0.00 sec)
Only InnoDB supports Foreign keys, MyISAM doesn't.
Even if it would, you cannot create relations between tables of different type.
Therefore you need to convert the table post into InnoDB. ALTER TABLE post ENGINE = InnoDB;
This error can also come when parent table is partitioned. Removing partitioning from the parent table allows foreign constraint to be created without any problem.
For me works with this.
CREATE TABLE category_ids (id INT, post_id INT references post(id),
INDEX par_ind (post_id)
) ENGINE=INNODB;