MySQL - How to create a composite table? - mysql

I am new to MySQL, I am about creating a database that manages information about diabetes patients. I have 6 tables, what important for here is 3 tables, diabetic table, diabetic_profile table and medication_profile table.
The last table (medication_profile) should be a composite table, which will have two primary foreign keys. These foreign keys are the diabetic_id(diabetic) and the profile_id (diabetic_profile). Translating that into MySQL code is the difficult part for me. I tried many ways but couldn't yet achieve that. below is the sql command I used:
CREATE TABLE Medication_Profile (
medication_type VARCHAR(10) NOT NULL,
profile_id INT NOT NULL,
diabetic int NOT NULL,
times_a_day NUMERIC(1) NOT NULL,
dose VARCHAR(20) NOT NULL,
PRIMARY KEY (medication_type, profile_id, diabetic),
FOREIGN KEY (profile_id, diabetic)
REFERENCES Diabetic_Profile (profile_id, diabetic_id)
);
please notice that the diabetic_id in this table is already a foreign key exists in Diabetic_profile table.
So any suggestions you may provide, please?
thanks in advance

You need a separate FOREIGN KEY clause for each foreign key, since they refer to different tables.
FOREIGN KEY (diabetic_id) REFERENCES diabetic (diabetic_id),
FOREIGN KEY (profile_id) REFERENCES diabetic_profile (profile_id)

Related

mysql foreign key using primary key

I have two tables,
diary with columns
id primary key
Narrative text
and
master with columns
id primary key
Diaryid int
EventDate date
Location int
I want to ensure that master(Diaryid) is always a valid diary(id)
Can I use foreign key to achieve this? Bearing in mind that one key is a primary key and the other int.
Any advice would be apprecaited.
Yes you cqan achieve this by using a FOREIGN KEY.
Also you should define it as NOT NULL, so that only exiasting diary keys are allowed
CREATE TABLE master(Diaryid BIGINT NOT NULL
, FOREIGN KEY (Diaryid)
REFERENCES diary(id)
);
You cqan add
ON DELETE CASCADE
So that the Master row will be deleted also when the diary rows gets removed
Don't know what is different but problem is solved.
CREATE TABLE diary(id int AUTO_INCREMENT, Narrative text, PRIMARY KEY(id))
CREATE TABLE master(id int AUTO_INCREMENT, Diaryid int,datemade date, FOREIGN KEY(Diaryid) REFERENCES diary(id), primary key (id))
So am now adding diary records and can have multiple master records so long as the Diaryid is valid
Thanks

MySQL - Error: 150 "Foreign key constraint is incorrectly formed")

Got an odd problem I cant solve after browsing dozens of forum posts, and my local SQL Books.
I've got two tables, and want to add a foreign key to one of them. The foreign key and primary key share the same datatype and charset and yet I cannot add the Foreign Key at all.
addon_account
name
type
comments
id
int(11)
Primary Key
name
varchar(60)
Primary Key
label
varchar(255)
shared
int(11)
addon_account_data
name
type
comments
id
int(11)
Primary Key
account_name
varchar(60)
Primary Key
money
double
owner
varchar()
The query I ran:
ALTER TABLE `addon_account_data` ADD FOREIGN KEY (`account_name`) REFERENCES `addon_account`(`name`) ON DELETE RESTRICT ON UPDATE RESTRICT;
Can't get it to work. Tosses out the same issue the entire time.
You are creating a foreign key on addon_account_data(account_name) that references addon_account(name). You have a composite primary the referred table : addon_account(id, name).
This is not allowed in MySQL, as explained in the documentation:
MySQL requires indexes on foreign keys and referenced keys so that foreign key checks can be fast and not require a table scan. In the referencing table, there must be an index where the foreign key columns are listed as the first columns in the same order.
Possible solutions:
add an additional column in the referring table: addon_account_data(account_id, account_name) and create a composite primary key to the corresponding columns in addon_account
create an index on addon_account(name) (probably the simplest solution)
change the order of the columns in the primary key of the referred table, like: addon_account(name, id) (you might want to first consider the impacts this may have in terms of performance)
I am not exactly a MySQL guy, but:
I believe the problem is that you are referencing only part of the primary key:
Your table addon_account has a composite key PK(id, name).
So, to put your relationship to work, you will need to add 'account_id' as part of the foreign key as well:
ALTER TABLE addon_account_data ADD FOREIGN KEY (account_id, account_name) REFERENCES addon_account(id, name)
This thread deals with something similar.
I hope this helps.
EDITED
I have installed a MySQL server instance on my local machine... (MySQL 8).
I have run the script below, and it worked (giving warnings about integer display being a deprecated feature, so I would recommend ommitting it):
CREATE TABLE addon_account(
id INT(11) NOT NULL,
`name` VARCHAR(60) NOT NULL,
label VARCHAR(255),
shared INT(11),
CONSTRAINT pk_addon_account PRIMARY KEY(id, `name`));
CREATE TABLE addon_account_data (
id INT(11) NOT NULL,
account_name VARCHAR(60) NOT NULL,
account_id INT(11),
money DOUBLE,
`owner` VARCHAR(255),
CONSTRAINT pk_addon_account_data PRIMARY KEY(id, account_name),
CONSTRAINT fk_addon_account_account_data FOREIGN KEY(account_id, account_name)
REFERENCES addon_account(id, `name`));
Could you try it and see if this works for you?
I am not that familiar with MySQL.
make sure that the 2 tables have the same collation
like
COLLATE='utf8_general_ci'

how to put foreign key in mysql

I want to know how to use a foreign key in a table,
I have a code here:
create table penerbit_buku(
id_buku char(8),
foreign key(id_buku) references buku(id_buku),
id_penerbit char(3),
foreign key(id_penerbit) references penerbit(id_penerbit)
)
Can I use this code instead:
create table penerbit_buku(
id_buku char(8) references buku(id_buku),
id_penerbit char(3) references penerbit(id_penerbit)
)
I have tried both and it succeed, is that correct?
No, MySQL parses but ignores the standard inline REFERENCES syntax.
When you declare a foreign key along with an individual column definition, it accepts the syntax as legitimate SQL, but then does not store the foreign key constraint. There's no error reported, but it's as if you didn't write the foreign key syntax at all.
You must declare foreign keys as table-level constraints (your first example above).
This is a case where MySQL is missing a feature of standard SQL. The issue was reported back in 2004, but never fixed! https://bugs.mysql.com/bug.php?id=4919
The reason for this issue is that historically, foreign key constraints were not supported by MySQL itself, but by the InnoDB storage engine, which was made by another company back then. They had to implement their own parser for CREATE TABLE and ALTER TABLE to support foreign keys, and they didn't feel like going the extra steps to support inline foreign key syntax, when table-level foreign key syntax would work.
The architect of InnoDB posted this response:
[6 Sep 2006 10:03] Heikki Tuuri
This will be fixed in MySQL foreign keys, when they are available for all table types.
The MySQL project is gradually working their way toward integrating foreign keys and similar features directly into the MySQL product. Perhaps in a few more years we'll see better support for standard FK syntax.
EXAMPLE:
CREATE TABLE Orders (
ID int NOT NULL,
Number int NOT NULL,
PersonID int,
PRIMARY KEY (ID),
FOREIGN KEY (PersonID) REFERENCES Persons(PersonID)
);
The foreign key must be referencing a primary key in another table
create table penerbit_buku
(id_buku char(8),
id_penerbit char(3),
foreign key(id_buku) references buku(id_buku),
foreign key(id_penerbit) references penerbit(id_penerbit)
);
I would need to see your other tables to give better help in the code
You can use this:
ALTER TABLE `table1`
ADD CONSTRAINT `FK_table1_table2` FOREIGN KEY (`fk_id`) REFERENCES `table2` (`id`);
first lets look at the description of FOREIGN KEY.
A FOREIGN KEY is a key used to link two tables together.
or
A FOREIGN KEY is a field (or collection of fields) in one table that refers to the PRIMARY KEY in another table.
Usually a table that has the foreign key is the child table. and the other table is the reference or parent table.
Since i Can not see your tables, ill give you different example.
Look at the following two tables:
Persons table:
Personal_id LastName FirstName age
1 pretty bob 20
2 angry jack 30
3 happy sue 28
Order Table:
OrderID OrderNumber Personal_id
1 77895 3
2 44678 3
3 22456 2
4 24562 1
Now look how Personal_id column in Orders table points to Personal_id in persons table.
The Personal_id in persons table is the primary key and the Personal_id in the orders table is the FOREIGN KEY.
now except linking how does foreign key help:
two general ways that i can think of:
1- foreign key is like a constrain that makes sure no action would destroy the links between tables
2- foreign key also acts as a constrain to stop invalid data from being inserted into the foreign key column, as it has to reference to the primary key column in the other table
code example in MySql:
CREATE TABLE Orders (
OrderID int NOT NULL,
OrderNumber int NOT NULL,
PersonID int,
PRIMARY KEY (OrderID),
FOREIGN KEY (Personal_id) REFERENCES Persons(Personal_id)
);
code example is SQL-Server/MS Access/ Oracle:
CREATE TABLE Orders (
OrderID int NOT NULL PRIMARY KEY,
OrderNumber int NOT NULL,
PersonID int FOREIGN KEY REFERENCES Persons(Personal_id)
);
Primary key of Orders table is the orderID.
Foreign key of Orders table is what links it to persons table.
Personal_id columns are the columns that link both tables.
Both of the code chunks do the same depends what are you working with.
real world example:
assuming:
customer_Table column to be a primary key in restaurant table and foreign key in orders table.
if a waiter is putting customer_Table number 20 in the machine, and he puts customer_Table 200 by mistake such key does not exist as a primary key in restaurant table so he cant.
Extra:
what if you want to allow naming of the FOREIGN KEY constraint, and define a FOREIGN KEY constraint on many columns?
MySQL / SQL Server / Oracle / MS Access:
CREATE TABLE Orders (
OrderID int NOT NULL,
OrderNumber int NOT NULL,
Personal_id int,
PRIMARY KEY (OrderID),
CONSTRAINT FK_PersonOrder FOREIGN KEY (Personal_id)
REFERENCES Persons(Personal_id)
);

A Foreign key referencing multiple unique key

I have 3 tables:
class_a
CREATE TABLE class_a (
id INT NOT NULL PRIMARY KEY AUTO_INCREMENT,
std_id INT NOT NULL UNIQUE,
name varchar(225) NOT NULL)
class_b
CREATE TABLE class_b (
id INT NOT NULL PRIMARY KEY AUTO_INCREMENT,
std_id INT NOT NULL UNIQUE,
name varchar(225) NOT NULL)
sn_number
CREATE TABLE sn_number (
id INT NOT NULL PRIMARY KEY AUTO_INCREMENT,
pin INT NOT NULL UNIQUE,
serial VARCHAR(255) NOT NULL UNIQUE,
std_id INT NULL DEFAULT NULL,
FOREIGN KEY(std_id) REFERENCES class_a(std_id)
)
How can I reference unique std_id in class_a and class_b table as a foreign key in sn_number table.
I want to achieve something like ALTER TABLE sn_number ADD FOREIGN KEY(std_id) REFERENCES class_a(std_id), class_b(std_id)
I have tried doing this ALTER TABLE sn_number ADD FOREIGN KEY(std_id) REFERENCES class_a(std_id)
followed by
ALTER TABLE sn_number ADD FOREIGN KEY(std_id) REFERENCES class_b(std_id) on sn_number table but will keep overwriting each other.
I have read these:
Foreign Key Referencing Multiple Tables and
Composite key as foreign key (sql)
But I can't find the solution to the problem am having.
Foreign key must reference only one parent table. This is fundamental to both SQL syntax, and relational theory.
What you can do, is add another table classes or students that contain all std_id , then just reference the FK to it.
Since you haven't explicitly given a constraint name in your FOREIGN KEY declarations, the DBMS makes one up from the table name sn_number. Your problem is that you are thus implicitly declaring the same constraint name each time, so the old info for the name is lost. Just use different explicit constraint names for different cases of table & column list REFERENCES table & column list.
CONSTRAINT fk_sn_number_a FOREIGN KEY(std_id) REFERENCES class_a(std_id)
CONSTRAINT fk_sn_number_b FOREIGN KEY(std_id) REFERENCES class_b(std_id)
Just learn about the basics of Using FOREIGN KEY Constraints.
PS As remarked in a comment, this is a poor design. But contrary to the comment & another answer, your need for two foreign keys from the same table & column list is not a symptom of poor design. But notice that the problems that people usually have with "Foreign Key Referencing Multiple Tables" in questionable designs is that they think that their tables as designed need a foreign key from one place to two places when they don't. Such a design doesn't even involve a foreign key, it just involves something reminiscent of a foreign key.

How do I create a MySQL table when it has two foreign keys?

What would be the code for creating a table with two foreign keys?
I have a USER table and a PICTURE table. Since a USER can be in many PICTURE and many PICTURE can be from a USER, I need a third table with both primary keys.
Thank you SO, as usual you are invaluable for a learning novice. :)
I can't speak specifically for mySQL but in most databases I have worked with you can put as many foreign keys as you need on a table. But you can only have one primary key. A third table with both keys is the right choice. Make a foreign key to each of the other two tables and a primary key consisting of both ids in the table.
If I understood correctly, you may need to do something like the following:
CREATE TABLE users (
user_id INT NOT NULL PRIMARY KEY,
name VARCHAR(50) NOT NULL
) ENGINE=INNODB;
CREATE TABLE pictures (
picture_id INT NOT NULL PRIMARY KEY,
filename VARCHAR(255) NOT NULL,
posted_by INT NOT NULL,
FOREIGN KEY (posted_by) REFERENCES users(user_id)
) ENGINE=INNODB;
CREATE TABLE users_in_pictures (
user_id INT NOT NULL,
picture_id INT NOT NULL,
PRIMARY KEY (user_id, picture_id),
FOREIGN KEY (user_id) REFERENCES users(user_id),
FOREIGN KEY (picture_id) REFERENCES pictures(picture_id)
) ENGINE=INNODB;
Note that each picture can be posted by a user. In fact the posted_by field is constrained by a foreign key that references the users table.
In addition, I assume that you want to tag pictures ala-facebook. In this case, you can use the third table, which is using a composite primary key on (user_id, picture_id) and both fields are also constrained to the appropriate table.