ORA-00907: "missing right parenthesis" - sql

First of all, I apologize for asking the same question again but the information on the old topics did not work in my oraclesql code and secondly there may be some syntax errors, I learned mysql in school last semester, but now we are learning oraclesql with old mysql information in the lesson, so i am a bit confused.
So my question is i want to create 3 related table (movie-casts-actor) but i am getting missing right parenthesis. trying to connect casts table to movie table with foreign key and actor table to casts table. what am i doing wrong? how spagetti is it?
CREATE TABLE Movie (
movie_id NUMBER(7) NOT NULL,
movie_name varchar2(50) NOT NULL ,
movie_director varchar2(50) NOT NULL ,
movie_year INT(4) NOT NULL ,
movie_duration INT(3) ,
movie_language varchar2(15) ,
movie_rating number(4,2) ,
PRIMARY KEY(movie_id),
CONSTRAINT is_unique UNIQUE(movie_id),
CONSTRAINT movie_id_checker CHECK(movie_id>0 and movie_id<=9999999)
);
CREATE TABLE Casts (
movie_id_fk INT(7) FOREIGN KEY REFERENCES Movie(movie_id) ,
cast_id INT(7) NOT NULL,
actor_fullname varchar2(50) NOT NULL ,
actor_role varchar2(50) ,
PRIMARY KEY(cast_id),
CONSTRAINT is_unique UNIQUE(cast_id),
CONSTRAINT cast_id_checker CHECK(cast_id>0 and cast_id<=9999999)
);
CREATE TABLE Actor (
cast_id_fk INT(7) FOREIGN KEY REFERENCES Casts(cast_id) ,
actor_id INT(7) NOT NULL,
actor_name CHAR(30) ,
actor_surname CHAR(25) ,
actor_gender CHAR(5) ,
actor_age CHAR(3) CONSTRAINT real_age_check CHECK(actor_age>0 AND actor_age<=150),
PRIMARY KEY(actor_id),
CONSTRAINT is_unique UNIQUE(actor_id),
CONSTRAINT actor_id_checker CHECK(actor_id>0 and actor_id<=9999999)
)

The errors are:
INT or NUMBER(4,0) and not INT(4)
You cannot have a unique key and a primary key on the same column.
An inline foreign key just need the REFERENCES keyword and does not need FOREIGN KEY.
Other issues:
You probably don't want actor name/surname as fixed-length CHAR strings and want to us variable-length VARCHAR2.
You probably want gender to be a code from a fixed list (which can be as long or as short as you find appropriate to describe the actors) rather than as a string.
You probably don't want to have an AGE column as that will be out of date as soon as the first birthday of an actor occurs; instead have a DATE_OF_BIRTH column that is a DATE data type and then you can calculate the age as and when necessary.
Using the table name as a prefix for every column is a waste of key strokes; you would be better to just name the columns for what they are without the prefix. Similar with fk as a suffix.
If you are using a NUMBER(7,0) for id values then you don't need to check that it is less than or equal to 9999999 as it is impossible to be a greater value; however, you can have zero or negative values so the check constraint for the lower bound may still be valid.
If you are using Oracle 12c or later then you should probably be using an IDENTITY column for the id values unless you are taking the id values from a 3rd party.
CREATE TABLE Movie (
id NUMBER(7,0) NOT NULL,
name varchar2(50) NOT NULL ,
director varchar2(50) NOT NULL ,
year NUMBER(4,0) NOT NULL ,
duration NUMBER(3,0),
language varchar2(15) ,
rating number(4,2) ,
PRIMARY KEY(id),
CONSTRAINT movie_id_checker CHECK(id>0)
);
CREATE TABLE Casts (
movie_id INT REFERENCES Movie(id) ,
id NUMBER(7,0) NOT NULL,
fullname varchar2(50) NOT NULL ,
role varchar2(50) ,
PRIMARY KEY(id),
CONSTRAINT cast_id_checker CHECK(id>0)
);
CREATE TABLE Actor (
cast_id NUMBER(7,0) REFERENCES Casts(id) ,
id NUMBER(7,0) NOT NULL,
name VARCHAR2(30) ,
surname VARCHAR2(25) ,
gender CHAR(1)
CHECK ( gender IN ( 'M', 'F', 'X', 'Y', 'Z' ) ),
date_of_birth DATE
CONSTRAINT real_age_check CHECK(date_of_birth >= DATE '1870-01-01' ),
PRIMARY KEY(id),
CONSTRAINT actor_id_checker CHECK(id>0)
);
db<>fiddle here

Related

cant reference sport CHAR(6) to other column error

As the title says, for some reason it gives me the error that the sport variable cant reference to another column when I am not even referencing it, any reason for this?
CREATE TABLE club_rates
(club_id NUMBER(4)
CONSTRAINT rates_club_fk REFERENCES club_subscriptiontypes(club_id,subscriptiontype)
,sport CHAR(6)
,subscriptiontype CHAR(11)
,subscription_startdate DATE
,subscription_rate_existing NUMBER(2)
,subscription_rate_new NUMBER(2)
,subscription_enddate DATE
,registration_startdate DATE
,registration_enddate DATE,
CONSTRAINT rates_clubsportsub_pk PRIMARY KEY (club_id, sport, subscriptiontype, subscription_startdate)
);
Assuming you have the table:
CREATE TABLE club_subscriptiontypes(
club_id NUMBER(4),
subscriptiontype CHAR(11),
PRIMARY KEY (club_id,subscriptiontype)
);
Then you do not want to declare a composite primary key column inline against a single column or you get the error:
ORA-02256: number of referencing columns must match referenced columns
Instead, declare it out-of-line at the end of the statement:
CREATE TABLE club_rates(
club_id NUMBER(4)
, sport CHAR(6)
, subscriptiontype CHAR(11)
, subscription_startdate DATE
, subscription_rate_existing NUMBER(2)
, subscription_rate_new NUMBER(2)
, subscription_enddate DATE
, registration_startdate DATE
, registration_enddate DATE
, CONSTRAINT rates_club_fk
FOREIGN KEY (club_id, subscriptiontype)
REFERENCES club_subscriptiontypes(club_id,subscriptiontype)
, CONSTRAINT rates_clubsportsub_pk
PRIMARY KEY (club_id, sport, subscriptiontype, subscription_startdate)
);
As an aside, you probably don't want to use fixed-length CHAR strings and, instead, want variable-length VARCHAR2 strings.
db<>fiddle here

Is there a way to make two primary keys, with only one foreign key that references another tables primary key

I'm new to SQL and trying to make it so that there are two primary keys and one foreign key that references other tables primary key.
I've tried adding the attribute that is a primary key that is missing the table that needs referencing and then making that a foreign key but still getting the message that "number of referencing columns must match references columns".
if there is a solution to what I'm trying to achieve it would be much appreciated.
CREATE TABLE Next_of_Kin
(
Employee_No VARCHAR2(8) NOT NULL,
kin_Number VARCHAR2(8) NOT NULL,
Name VARCHAR2(40) NOT NULL,
relationship VARCHAR2(40) NOT NULL,
contact_number VARCHAR2(11) NOT NULL,
PRIMARY KEY (Employee_No, Kin_Number),
FOREIGN KEY (Employee_No, Kin_Number) REFERENCES Employee(Employee_No)
);
CREATE TABLE Employee
(
Employee_No VARCHAR2(8) NOT NULL,
family_Name VARCHAR2(40) NOT NULL,
given_Name VARCHAR2(40) NOT NULL,
address VARCHAR2(80) NOT NULL,
date_of_Birth DATE NOT NULL,
date_Hired DATE NOT NULL,
supervisor VARCHAR2(40) NULL,
PRIMARY KEY (Employee_No, Supervisor),
FOREIGN KEY (Employee_No,Supervisor)
REFERENCES Employee(Employee_No, Supervisor)
);
Presumably supervisor references an employee number (because the supervisor is also an employee), so it should only be one column.
Also, there's no reason why a next of kin entry should refer to another next of kin. All you need to enforce is that the employee number refers to an existing employee.
Single-column keys can be declared as part of the column definition, which simplifies the syntax and also allows the datatype of foreign key columns to be inherited from the parent.
create table employee
( employee_no varchar2(8) primary key
, family_name varchar2(40) not null
, given_name varchar2(40) not null
, address varchar2(80) not null
, date_of_birth date not null
, date_hired date not null
, supervisor references employee(employee_no)
);
create table next_of_kin
( employee_no references employee (employee_no) not null
, kin_number varchar2(8) not null
, name varchar2(40) not null
, relationship varchar2(40) not null
, contact_number varchar2(11) not null
, primary key (employee_no, kin_number)
);
A table can have as many unique constraints as you like, but only one primary key. In your example though, you are trying to define one primary key with two columns, which is allowed (although not needed here). You can also have a foreign key with more than one column, as long as it matches a corresponding primary or unique constraint in the specified table.
I don't know your company, but I'm pretty sure that the employee number is unique. Thus, the primary key of your employee table should be Employee_No, without the supervisor.
The foreign key in your employee table does not make sense. Remove it.
In your next of kin table, leave the primary key as it is, but make only the employee number a foreign key:
FOREIGN KEY (Employee_No) REFERENCES Employee(Employee_No)
It looks like you want to have EMPLOYEE_NO be the primary key on EMPLOYEE, but you also want (EMPLOYEE_NO, SUPERVISOR) to be unique. Note that this unique key is unnecessary - becaue EMPLOYEE_NO is the primary key on EMPLOYEE it's guaranteed to be unique, and thus any combination of (EMPLOYEE_NO, <some other column on EMPLOYEE) will automatically be unique - but sometimes I throw in a unique key like this just as documentation, or to make it referenceable in a foreign key constraint from another table.
So anyways, consider using:
(
Employee_No VARCHAR2(8) NOT NULL,
kin_Number VARCHAR2(8) NOT NULL,
Name VARCHAR2(40) NOT NULL,
relationship VARCHAR2(40) NOT NULL,
contact_number VARCHAR2(11) NOT NULL,
PRIMARY KEY (Employee_No, Kin_Number),
FOREIGN KEY (Employee_No) REFERENCES Employee(Employee_No)
);
CREATE TABLE Employee
(
Employee_No VARCHAR2(8) NOT NULL,
family_Name VARCHAR2(40) NOT NULL,
given_Name VARCHAR2(40) NOT NULL,
address VARCHAR2(80) NOT NULL,
date_of_Birth DATE NOT NULL,
date_Hired DATE NOT NULL,
supervisor VARCHAR2(40) NULL,
PRIMARY KEY (Employee_No),
UNIQUE KEY (Employee_No, Supervisor)
);
Since (EMPLOYEE_NO, KIN_NUMBER) is the primary key on NEXT_OF_KIN it makes no sense to have a self-referencing foreign key utilizing (EMPLOYEE_NO, KIN_NUMBER) as the row would always-and-only refer to itself.

I'm getting "Invalid Identifier Error" for one of my Oracle Apex Queries

I'm trying to run a script on Oracle Apex and so far all the tables and queries work except the last one. It returns the error "ORA-00904: : invalid identifier ORA-06512: at "SYS.WWV_DBMS_SQL_APEX_200200", line 626 ORA-06512: at "SYS.DBMS_SYS_SQL", line 1658 ORA-06512: at "SYS.WWV_DBMS_SQL_APEX_200200", line 612 ORA-06512: at "APEX_200200.WWV_FLOW_DYNAMIC_EXEC", line 1749." What should I do to fix this error?
CREATE TABLE customer(
VIN VARCHAR2(17)
CONSTRAINT vehicles__VIN__fk
REFERENCES vehicles (VIN) ON DELETE SET NULL,
sale_date DATE
CONSTRAINT sales__sale_date__fk
REFERENCES sales (sale_date) ON DELETE SET NULL,
c_name VARCHAR2(50)
CONSTRAINT sales__c_name__nn NOT NULL,
address VARCHAR2(50)
CONSTRAINT sales__address__nn NOT NULL,
phone VARCHAR2(11)
CONSTRAINT sales__phone__nn NOT NULL,
gender VARCHAR2(6)
CONSTRAINT sales__gender__nn NOT NULL,
a_income VARCHAR2(30)
CONSTRAINT sales__a_income__nn NOT NULL,
);
I don't know if it helps but VIN and sale_date reference these two working queries:
CREATE TABLE vehicles(
VIN VARCHAR2(17)
CONSTRAINT vehicles__VIN__pk PRIMARY KEY,
brand VARCHAR2(20)
CONSTRAINT vehicles__brand__nn NOT NULL,
model VARCHAR2(20)
CONSTRAINT vehicles__model__nn NOT NULL,
color VARCHAR2(10)
CONSTRAINT vehicles__color__nn NOT NULL
);
CREATE TABLE sales(
sale_date DATE,
price VARCHAR2(30)
CONSTRAINT sales__price__nn NOT NULL,
VIN VARCHAR2(17)
CONSTRAINT vehicles__VIN__fk
REFERENCES vehicles (VIN) ON DELETE SET NULL,
d_id VARCHAR2(10)
CONSTRAINT dealer__d_id__fk
REFERENCES dealer (d_id) ON DELETE SET NULL,
CONSTRAINT sales__sale_date__pk PRIMARY KEY (sale_date)
);
Remove the last comma.
Also, if your constraints have the naming convention <tablename>__<columnname>__<constrainttype> then don't just copy/paste from another table and update the column name; you need to update the table name as well or you will find you have duplicate constraint names which will raise an exception.
CREATE TABLE customer(
VIN VARCHAR2(17)
CONSTRAINT customer__VIN__fk
REFERENCES vehicles (VIN) ON DELETE SET NULL,
sale_date DATE
CONSTRAINT customer__sale_date__fk
REFERENCES sales (sale_date) ON DELETE SET NULL,
c_name VARCHAR2(50)
CONSTRAINT customer__c_name__nn NOT NULL,
address VARCHAR2(500)
CONSTRAINT customer__address__nn NOT NULL,
phone VARCHAR2(11)
CONSTRAINT customer__phone__nn NOT NULL,
gender CHAR(1)
CONSTRAINT customer__gender__nn NOT NULL
CONSTRAINT customer__gender__chk
CHECK ( gender IN ( 'M', 'F' /*, 'A', 'B', 'C'*/ ) ),
a_income NUMBER(12,2)
CONSTRAINT customer__a_income__nn NOT NULL
);
Then comes the other questions:
Why does a customer have a VIN (vehicle identification number)? A customer is not limited to owning a single car.
Why does a customer have a sale_date? If you are referring to a car sale then why is the customer limited to a single sale? You probably want to fix both these two by moving the data to a separate table called customer_cars (or something similar) so that each customer can own multiple cars and each car can be owned by multiple customers (at different times).
Do you expect all customers' addresses to fit in 50 characters?
Why is gender a VARCHAR(6) and not a CHAR(1) with values M/F (extend with additional character codes as appropriate)?
Why is a_income a string and not a NUMBER?

beginner sql missing keyword and invalid identifier

CREATE table Book
(
book_title varchar (100) not null ,
book_genre char(60) not null,
Date_of_publish date not null,
user_code char(7) not null ,
book_id char (7) primary key not null ,
constraint writer__id_fk foreign key (writer_id),
constraint publisher__id_fk foreign key (publisher_id)
);
I'm getting
[ORA-00905: missing keyword]
in publisher table
CREATE table publisher
(
publisher_id char (7) primary key not null,
publisher_name char(20) not null,
publisher_number char(10) not null,
publisher_email varchar2(60) not null,
publisher_address varchar2(60) not null,
);
I'm getting
[ORA-00904: : invalid identifier]
The following SQL creates a FOREIGN KEY on the "PersonID" column when the "Orders" table is created:
CREATE TABLE Orders (
OrderID int NOT NULL,
OrderNumber int NOT NULL,
PersonID int,
PRIMARY KEY (OrderID),
FOREIGN KEY (PersonID) REFERENCES Persons(PersonID)
);
Refer this link for more details
https://www.w3schools.com/sql/sql_foreignkey.asp
Hope this helps.
Welcome to the wonderful world of SQL! :-)
General remark:
Please tell us what kind of DBMS you're using. MySQL? SQL Server? Oracle? SQlite? Different systems use different kinds of syntaxes.
First statement:
The problem seems to be in the FOREIGN KEY-portion.
Usually, you'll state something like:
CONSTRAINT [constraint_name] FOREIGN KEY([column_in_this_table]) REFERENCES OTHER_TABLE([column_in_other_table])
edit (added):
The [column_in_this_table] has to exist in your DDL (CREATE TABLE-statement), like so:
CREATE TABLE Book ( book_title ... etc., publisher_id INT, CONSTRAINT FK_publ_id FOREIGN KEY(publisher_id) REFERENCES publisher(publisher_id));
Here, you'll have a 'original' column called 'publisher_id', in the 'publisher'-table. You refer to it from within the 'Book'-table, by first having a 'publisher_id' column in the 'Book'-table (which should have the same DDL as the original column by the way). Next, you'll add a FOREIGN KEY to the 'Book'-table, that is imposed on the Book(publisher_id) column. Note, that you could also name the column in your 'Book'-table differently -- like, say, 'Spongebob' or 'Patrick'. But for future use, you'd like naming conventions that tell what you might expect to find in a column. So you'd name columns for what they contain.
Second statement:
The problem is with the last portion of your statement, where there's a comma after the NOT NULL portion for column publisher_address.
(Part of) your statement:
publisher_address varchar2(60) not null, );
Try replacing that with:
publisher_address VARCHAR2(60) NOT NULL);
edit (note to self):
VARCHAR2 turns out to be a valid datatype in Oracle databases (see:
Oracle documentation)
For your first table, the Foreign Keys do not reference any table. For your second table, I would imagine that comma after your last column isn't helping anything.
So this is the answer.
CREATE table Book
(
book_title varchar (100) not null ,
book_genre char(60) not null,
Date_of_publish date not null,
user_code char(7) not null ,
publisher_id char (7) not null,
writer_id char(7) not null,
book_id char (7) primary key not null ,
CONSTRAINT book_writer_id_fk FOREIGN KEY(writer_id) REFERENCES writer(writer_id),
CONSTRAINT book_publisher_id_fk FOREIGN KEY(publisher_id) REFERENCES publisher(publisher_id)
);
CREATE table publisher
(
publisher_id char (7) primary key not null,
publisher_name char(20) not null,
publisher_number char(10) not null,
publisher_email varchar2(60) not null,
publisher_address varchar2(60) not null
);

Simple SQL issues, cannot figure out what I'm doing wrong to get these errors - ORA-00942 / 907 / 922

This is a supposed to be a simple SQL project, but I'm stuck on the first step. I've never worked with SQL before, so I'm pretty lost. Can someone please tell me what I did wrong that's causing these errors?
Here is the file:
SPOOL output.log;
DROP TABLE rental CASCADE CONSTRAINTS;
DROP TABLE movie CASCADE CONSTRAINTS;
DROP TABLE customer CASCADE CONSTRAINTS;
DROP TABLE distributor CASCADE CONSTRAINTS;
DROP TABLE rental_store CASCADE CONSTRAINTS;
CREATE TABLE rental (
inventory_id CHAR(10) PRIMARY KEY,
transaction_id CHAR(10) NOT NULL UNIQUE,
late DECIMAL(6,2),
damaged DECIMAL(6,2),
fail_rewind DECIMAL(6,2),
taxes DECIMAL(6,2) NOT NULL,
discount DECIMAL(6,2),
customer_id CHAR(10) NOT NULL UNIQUE,
CONTRAINT rental_FK FOREIGN KEY (customer_id) REFERENCES customer (customer_id));
CREATE TABLE movie (
title_id_number CHAR(10) PRIMARY KEY,
genre VARCHAR2(20) NOT NULL,
actor VARCHAR2(30) NOT NULL,
director VARCHAR2(30) NOT NULL,
awards VARCHAR2(30),
running_length INTEGER NOT NULL,
rating VARCHAR2(5) NOT NULL,
year_released INTEGER NOT NULL,
media_type CHAR(5) NOT NULL,
inventory_id CHAR(10) NOT NULL UNIQUE,
title VARCHAR2(30) NOT NULL,
distrib_serial INTEGER NOT NULL UNIQUE,
cat_mov_id CHAR(10) NOT NULL UNIQUE));
CREATE TABLE customer (
customer_id CHAR(10) PRIMARY KEY,
name VARCHAR2(30) NOT NULL,
address VARCHAR2(50) NOT NULL,
tele_number CHAR(10) NOT NULL UNIQUE,
rent_history INTEGER NOT NULL));
CREATE TABLE distributor (
distributor_name VARCHAR2(30) PRIMARY KEY,
catalog VARCHAR2(30) NOT NULL,
genres_offered VARCHAR2(50) NOT NULL));
CREATE TABLE rental_store (
store_name VARCHAR2(30) PRIMARY KEY,
address VARCHAR2(50) NOT NULL,
owner VARCHAR2(30) NOT NULL));
SPOOL OFF;
The errors for the DROP statements are to be expected because the tables do not yet exist. You can safely ignore them.
Most of your problems come from the second closing parenthesis, e.g.
CREATE TABLE movie (
...
cat_mov_id CHAR(10) NOT NULL UNIQUE));
^ ---- here
You need to remove them. It is only needed in the first statement because of the column list of the foreign key.
The first (real) error you get is because you misspelled CONSTRAINT (you wrote CONTRAINT. The full clause needs to be
CONSTRAINT rental_FK FOREIGN KEY (customer_id) REFERENCES customer (customer_id)
^ -- the "s" was missing here
However you can't create a foreign key constraint to a table that does not exist. So you need to change the order of the create statements to first create the customer table, then you can create the rental table.
Putting all that together, your script should look like this:
DROP TABLE rental CASCADE CONSTRAINTS;
DROP TABLE movie CASCADE CONSTRAINTS;
DROP TABLE customer CASCADE CONSTRAINTS;
DROP TABLE distributor CASCADE CONSTRAINTS;
DROP TABLE rental_store CASCADE CONSTRAINTS;
CREATE TABLE customer (
customer_id CHAR(10) PRIMARY KEY,
name VARCHAR2(30) NOT NULL,
address VARCHAR2(50) NOT NULL,
tele_number CHAR(10) NOT NULL UNIQUE,
rent_history INTEGER NOT NULL
);
CREATE TABLE rental (
inventory_id CHAR(10) PRIMARY KEY,
transaction_id CHAR(10) NOT NULL UNIQUE,
late DECIMAL(6,2),
damaged DECIMAL(6,2),
fail_rewind DECIMAL(6,2),
taxes DECIMAL(6,2) NOT NULL,
discount DECIMAL(6,2),
customer_id CHAR(10) NOT NULL UNIQUE,
CONSTRAINT rental_FK FOREIGN KEY (customer_id) REFERENCES customer (customer_id)
);
CREATE TABLE movie (
title_id_number CHAR(10) PRIMARY KEY,
genre VARCHAR2(20) NOT NULL,
actor VARCHAR2(30) NOT NULL,
director VARCHAR2(30) NOT NULL,
awards VARCHAR2(30),
running_length INTEGER NOT NULL,
rating VARCHAR2(5) NOT NULL,
year_released INTEGER NOT NULL,
media_type CHAR(5) NOT NULL,
inventory_id CHAR(10) NOT NULL UNIQUE,
title VARCHAR2(30) NOT NULL,
distrib_serial INTEGER NOT NULL UNIQUE,
cat_mov_id CHAR(10) NOT NULL UNIQUE
);
CREATE TABLE distributor (
distributor_name VARCHAR2(30) PRIMARY KEY,
catalog VARCHAR2(30) NOT NULL,
genres_offered VARCHAR2(50) NOT NULL
);
CREATE TABLE rental_store (
store_name VARCHAR2(30) PRIMARY KEY,
address VARCHAR2(50) NOT NULL,
owner VARCHAR2(30) NOT NULL
);
Unrelated, but: you do not want to use the CHAR data type. It's more efficient and will give you less headaches if you use VARCHAR for every character column.
Of course the first time you run the script your DROP TABLEs will fail because you haven't created them yet. That's to be expected and is acceptable in such a script.
Beyond that, if you are going to create FK relationships, you need to create the parent table before you create the child, which you will see after you correct your misspelled key word.
I will leave it as an exercise for the student to take that clue and locate the mis-spelled key word in the first CREATE TABLE statement.