I want to add multiple foreign keys to existing table in Oracle database. Following sql query gives me an error. One by one I can add foreign key constraint. But I want to do this within one statement like below.
ALTER TABLE address
ADD CONSTRAINT fk_customer_id FOREIGN KEY (customer_id)
REFERENCES customer (id) ON DELETE CASCADE ,
ADD CONSTRAINT fk_city_id FOREIGN KEY (city_id)
REFERENCES city (id) ON DELETE CASCADE;
Any idea how to do this?
That's not entirely true (what #Thorsten has said). You can add two constraints at a time.
SQL> create table test (empno number, deptno number);
Table created.
SQL>
SQL> alter table test add
2 ( constraint fk_test_emp foreign key (empno) references emp (empno),
3 constraint fk_test_dept foreign key (deptno) references dept (deptno)
4 );
Table altered.
SQL>
Related
My problem is that i have two tables with each table having a foreign key to the other table.
Each time , i execute the SQL file containing the creation of the two tables, it gives me an error that he doesn't find the other table. I'm working with sqlplus to execute the sql file.
Here's an example of SQL file i tried with :
create table A(
Age number(3),
name number(3) constraint A_FK references B(name))
/
create table B(
Age number(3) constraint B_FK references A(Age),
name number(3))
And even if i reverse the order, it gives the same error.
Thanks for help.
This is a problem of cycles in foreign keys. One method is to add all foreign keys after table creation (as I think the other answers propose).
You can also just do that for the first table:
create table A (
Age number(3) primary key,
name number(3)
);
create table B (
name number(3) primary key,
Age number(3),
constraint B_FK foreign key (age) references A(Age)
);
alter table B add constraint A_FK foreign key (name) references B(name);
Here is a db<>fiddle.
Notes:
Foreign keys should reference primary keys, so I added that declaration as well.
I recommend making the primary key the first column in the table.
You can also define the constraint inline for one of the tables (i.e. age number(3) constraint b_fk references a(age)).
The table column(s) that is referred by a foreign key must exist at the time when the constraint is created. Since you have some kind of cyclic reference between the tables, you need to do this in three steps:
first create one table without the foreign key
create the second table (with its foreign key)
finally add the foreign key to the first table with an alter table statement
You also need the referred column to have a unique or primary key constraint set up, otherwise you would get error ORA-02270: no matching unique or primary key for this column-list.
create table A(
age number(3) primary key,
name number(3)
);
create table B(
age number(3) constraint B_FK references A(Age),
name number(3) primary key
);
alter table A add constraint A_FK foreign key (name) references B(name);
Demo on DB Fiddle
Side note: I am quite suspicious about your sample structure, but this could be because your oversimplified it in the question.
It fails because the reference table doesn't exist yet.
Create the tables without the key first. Then drop one and recreated it with the reference. Then drop the 2nd and recreate it with the reference.
Create table first and then ADD the CONSTRAINT
ALTER TABLE A
ADD FOREIGN KEY (name) REFERENCES B(name);
ALTER TABLE B
ADD FOREIGN KEY (age) REFERENCES A(age);
I create a table ASSIGNMENTS:
CREATE TABLE assignments (
id_project NUMBER(4) NOT NULL CONSTRAINT fk_assignments_01 REFERENCES projects (id_project),
empl_number NUMBER(6) NOT NULL CONSTRAINT fk_assignments_02 REFERENCES employees (empl_id),
start DATE DEFAULT SYSDATE,
end DATE,
CONSTRAINT chk_assignements_dates CHECK (end > start),
rate NUMBER(7, 2),
CONSTRAINT chk_assignements_rate CHECK (rate > 0),
role VARCHAR2(20),
CONSTRAINT chk_assignements_role CHECK (rola IN ('ANALYST', 'DEVELOPER'))
);
And now I have to modify constraint fk_assignments_02. I want to set fk_assignments_02 ON DELETE CASCADE. I tried do it as following:
ALTER TABLE assignments
MODIFY id_project NUMBER(4) NOT NULL CONSTRAINT fk_assignments_01 REFERENCES projects (id_project) ON DELETE CASCADE;
But I get an error:
ORA-02275: such a referential constraint already exists in the table
You can't do that - you'll have to drop and re-add the constraint. There is no provision in Oracle to change the ON DELETE action, which is part of the REFERENCES clause rather than being part of the constraint state.
So to accomplish this you'd need to do
ALTER TABLE ASSIGNMENTS DROP CONSTRAINT FK_ASSIGNMENTS_02;
followed by
ALTER TABLE ASSIGNMENTS
ADD CONSTRAINT FK_ASSIGNMENTS_02
FOREIGN KEY (ID_PROJECT) REFERENCES PROJECT (ID_PROJECT)
ON DELETE CASCADE;
Best of luck.
CREATE TABLE Emp OF Emp_t(eno PRIMARY KEY, edept REFERENCES Dept);
There near the PRIMARY KEY, it will display a syntax error as expected not null. I need to solve it.
Below is the rest of queries in that schema.
CREATE TYPE Emp_t AS OBJECT(eno number(4),ename varchar2(15),edept ref dept_t,salary number(8,2));
/
CREATE TYPE Dept_t AS OBJECT(dno number(2),dname varchar2(12),mgr ref emp_t);
/
CREATE TYPE Proj_t AS OBJECT(pno number(4),pname varchar2(15),pdept ref dept_t,budget number(10,2));
/
CREATE TABLE Dept OF Dept_t(dno PRIMARY KEY, mgr REFERENCES Emp);
CREATE TABLE Proj OF Proj_t(pno PRIMARY KEY, pdept REFERENCES dept);
Error is dispalyed as in the following image.
As #LostInAlabama suggested, you can create the tables and add the circular constraints afterwards:
CREATE TABLE Dept OF Dept_t(dno PRIMARY KEY);
CREATE TABLE Proj OF Proj_t(pno PRIMARY KEY);
CREATE TABLE Emp OF Emp_t(eno PRIMARY KEY);
ALTER TABLE Dept MODIFY (mgr REFERENCES Emp);
or preferably with named constraints:
ALTER TABLE Dept ADD (CONSTRAINT Dept_FK_Emp FOREIGN KEY (mgr) REFERENCES Emp);
ALTER TABLE Emp ADD (CONSTRAINT Emp_FK_Dept FOREIGN KEY (edept) REFERENCES Dept);
ALTER TABLE Proj ADD (CONSTRAINT Proj_FK_Dept FOREIGN KEY (pdept) REFERENCES Dept);
can't delete the primary and foreign key, it's simple table but i don't why this error
create table student (
s_ID int ,
S_NAMe varchar2 (10),
S_major varchar2(20),
D_ID number (10) ,
Constraint PK_s_ID primary key (s_ID),
constraint FK_D_ID foreign key (D_ID) references dep (D_ID) );
ALTER TABLE student DROP CONSTRAINT PK_s_ID cascade;
alter table student drop constraint FK_D_ID;
ERROR at line 1:
ORA-02443: Cannot drop constraint - nonexistent constraint
You SQL commands looks correct. You can use following command to make sure constraint exists.
SELECT * FROM user_cons_columns WHERE table_name = 'STUDENT'
If it returns no result, that means you either did not create a constraint or already dropped. You may be trying to re-run the same alter command more than once.
For exmple i have two tables
A
create table teachers(
id number(4) primary key,
name varchar(20)
);
B
create table students(
id number(4) primary key,
name varchar(20)
);
and a third table
AB
create table Teacher_Student(
T_Id number(4),
S_Id number(4)
);
and their relationship
alter table teacher_student
add constraint s_t_pk Primary key(T_Id, S_Id);
Is this relationship is created correctly? and what would be the insertion query if i want to add a new student or a teacher.
Suggestion: also add referential integrity constraints:
alter table teacher_student
add constraint s_t_fk_t foreign key (T_Id)
references teachers (id)
on delete cascade
on update cascade;
alter table teacher_student
add constraint s_t_fk_s foreign key (S_Id)
references students (id)
on delete cascade
on update cascade;
Usual manouever for this would require primary keys for student and teacher tables, and then foreign keys for T_Id and S_id to Teachers and Students from Teacher_Student.
When you've done that, inserting to student and teacher, would only check uniqueness of their keys, i.e , you can't have two student's with an id of 1.
Inserting to Teacher_Student would check uniqueness of the relationship, and that the inserted ids exist in their respective tables.
PS abbreviating database object names is a very objectionable habit.