Duplicate Entry for Primary Key - mysql

The task given is:
Create a new relational table to store information about the company names of all suppliers and the total number of products supplied by each supplier. Enforce, the appropriate consistencyconstraints on the new table. Next, copy into the new table information about the company names of all suppliers and the total number of products supplied by each supplier.
I'm recieving an error Duplicate Entry for key "PRIMARY" When i try and run this script
CREATE TABLE COMPANY_AND_SUPPLIERS (
COMPANY_NAME VARCHAR (40) NOT NULL DEFAULT 'EMPTY',
PRODUCT_NAME VARCHAR(40) NOT NULL DEFAULT 'EMPTY' ,
TOTAL_PRODUCTS VARCHAR(40) NOT NULL DEFAULT 'EMPTY',
CONSTRAINT SUPPLIER_PKEY PRIMARY KEY(COMPANY_NAME) ,
CONSTRAINT SUPPLIER_FKEY FOREIGN KEY (COMPANY_NAME) REFERENCES SUPPLIER(COMPANY_NAME)
);
INSERT INTO COMPANY_AND_SUPPLIERS(COMPANY_NAME, PRODUCT_NAME)
SELECT DISTINCT SUPPLIER.COMPANY_NAME, PRODUCT.PRODUCT_NAME
FROM SUPPLIER, PRODUCT;
UPDATE COMPANY_AND_SUPPLIERS
SET TOTAL_PRODUCTS = (SELECT COUNT(*) AS TOTALPRODUCTS
FROM PRODUCT);
The Whole purpose of the exercise is to copy company names of all suppliers and the total number of products supplied by each supplier.
TABLES GIVEN
CREATE TABLE SUPPLIER
(
COMPANY_NAME VARCHAR(40) NOT NULL,
CONTACT_NAME VARCHAR(30),
CONTACT_TITLE VARCHAR(30),
ADDRESS VARCHAR(60),
CITY VARCHAR(15),
REGION VARCHAR(15),
POSTAL_CODE VARCHAR(10),
COUNTRY VARCHAR(15),
PHONE VARCHAR(24),
FAX VARCHAR(24),
HOME_PAGE VARCHAR(500),
CONSTRAINT PK_SUPPLIER PRIMARY KEY (COMPANY_NAME)
);
CREATE TABLE PRODUCT
(
PRODUCT_NAME VARCHAR(40) NOT NULL,
SUPPLIER_NAME VARCHAR(40) NOT NULL,
CATEGORY_NAME VARCHAR(30) NOT NULL,
QUANTITY_PER_UNIT VARCHAR(20),
UNIT_PRICE DECIMAL(10,2) NOT NULL DEFAULT 0,
UNITS_IN_STOCK DECIMAL(9) NOT NULL DEFAULT 0,
UNITS_ON_ORDER DECIMAL(9) NOT NULL DEFAULT 0,
REORDER_LEVEL DECIMAL(9) NOT NULL DEFAULT 0,
DISCONTINUED CHAR(1) NOT NULL DEFAULT 'N',
CONSTRAINT PK_PRODUCT PRIMARY KEY (PRODUCT_NAME),
CONSTRAINT FK_CATEGORY_NAME FOREIGN KEY (CATEGORY_NAME) REFERENCES CATEGORY(CATEGORY_NAME),
CONSTRAINT FK_SUPPLIER_NAME FOREIGN KEY (SUPPLIER_NAME) REFERENCES SUPPLIER(COMPANY_NAME),
CONSTRAINT CK_PRODUCT_UNIT_PRICE CHECK (UNIT_PRICE >= 0),
CONSTRAINT CK_PRODUCT_UNITS_IN_STOCK CHECK (UNITS_IN_STOCK >= 0),
CONSTRAINT CK_PRODUCT_UNITS_ON_ORDER CHECK (UNITS_ON_ORDER >= 0),
CONSTRAINT CK_PRODUCT_REORDER_LEVEL CHECK (REORDER_LEVEL >= 0),
CONSTRAINT CK_PRODUCT_DISCONTINUED CHECK (DISCONTINUED in ('Y','N'))
);

The column company_name should not be a primary key because a primary key is a unique value.
Take this as an example
If a Database administrator creates a table with first_name as the primary key, it would be a disaster since there are a lot of people who has John as their first name
That is why most of the time, the primary key is a integer, then we make it unique using this method.

Your table isn't supposed to contain the product names, just the company and total products. The PRODUCTS table already has the supplier names in it for each product. So you just need to count the number of products for each supplier from that table.
CREATE TABLE Company_Totals (
Company_name VARCHAR(40) NOT NULL,
Total_Products INT(11) NOT NULL,
PRIMARY KEY (Company_name),
FOREIGN KEY (Company_name) REFERENCES Supplier(Company_name)
);
INSERT INTO Company_Totals (Company_name, Total_Products)
SELECT SUPPLIER_NAME, COUNT(*)
FROM PRODUCT
GROUP BY SUPPLIER_NAME;

Related

MySQL Error (HY000): Cannot add foreign key constraint

I'm trying to create a MySQL schema for a simple online shop. My existing tables are as follows:
user — user info
address — address info for users
product — product info
purchase — a shopping chart created and purchased by a user
I've created these tables using the following SQL code:
CREATE TABLE user(
user_id INT AUTO_INCREMENT,
first_name VARCHAR(20) NOT NULL,
middle_name VARCHAR(20) NOT NULL,
last_name VARCHAR(20) NOT NULL,
email VARCHAR(40) NOT NULL UNIQUE,
password VARCHAR(255) NOT NULL,
registered BOOLEAN NOT NULL,
phone VARCHAR(12),
PRIMARY KEY(user_id)
);
CREATE TABLE product(
product_id INT AUTO_INCREMENT,
name VARCHAR(40) NOT NULL UNIQUE,
price DECIMAL(5,2) NOT NULL,
description VARCHAR(100) UNIQUE,
PRIMARY KEY(product_id)
);
CREATE TABLE address(
user_id INT,
address_id INT,
city VARCHAR(15) NOT NULL,
district VARCHAR(20) NOT NULL,
details VARCHAR(50) NOT NULL,
is_default BOOLEAN NOT NULL,
FOREIGN KEY(user_id) REFERENCES user(user_id) ON DELETE CASCADE,
PRIMARY KEY(user_id, address_id)
);
CREATE TABLE purchase(
purchase_id INT AUTO_INCREMENT,
user_id INT,
total_price DECIMAL(8,2) NOT NULL,
state ENUM('placed', 'paid', 'shipped', 'received', 'completed', 'cancelled') DEFAULT 'placed',
user_name VARCHAR(40) NOT NULL,
full_address VARCHAR(85) NOT NULL,
FOREIGN KEY(user_id) REFERENCES user(user_id) ON DELETE SET NULL,
PRIMARY KEY(purchase_id)
);
Now I'm trying to create a final table to store individual items in a shopping chart like this:
CREATE TABLE purchase_item(
purchase_id INT,
product_id INT,
product_name VARCHAR(40) NOT NULL,
amount DECIMAL(4,2) NOT NULL,
price DECIMAL(8,2) NOT NULL,
FOREIGN KEY(purchase_id) REFERENCES purchase(purchase_id) ON DELETE CASCADE,
FOREIGN KEY(product_id) REFERENCES product(product_id) ON DELETE SET NULL,
PRIMARY KEY(purchase_id, product_id)
);
But I get the following error:
ERROR 1215 (HY000): Cannot add foreign key constraint
I don't any errors if I update the foreign key for products as follows:
FOREIGN KEY(product_id) REFERENCES product(product_id) ON DELETE CASCADE,
I want the purchase_item to be deleted if the corresponding purchase gets deleted, but not when the corresponding product gets deleted.
https://dev.mysql.com/doc/refman/8.0/en/create-table-foreign-keys.html says:
If you specify a SET NULL action, make sure that you have not declared the columns in the child table as NOT NULL.
But your purchase_item.product_id column is part of that table's primary key, which implicitly makes the column NOT NULL.
You cannot use the SET NULL action for the primary key on that column.

Multiplying Columns using a WITH clause

Hello all Im trying to Find the total value of an order Through Arthmetic(Quanity * Unit_price) which i can do BUT the question wants me to do so using a nest query and a WITH clause. How would I implement the WITH clause?
below is what ive done but not meeting the procedure requirements
SELECT ORDER_ID
FROM ORDERS
WHERE ORDER_ID IN
(SELECT(QUANTITY * UNIT_PRICE) AS TOTAL_VALUE
FROM ORDER_DETAIL)
ODER BY ORDER_ID ASC;
CREATE TABLE ORDERS
(
ORDER_ID DECIMAL(9) NOT NULL,
CUSTOMER_CODE VARCHAR(5) NOT NULL,
EMPLOYEE_ID DECIMAL(9) NOT NULL,
ORDER_DATE DATE NOT NULL,
REQUIRED_DATE DATE,
SHIPPED_DATE DATE,
SHIP_VIA VARCHAR(40),
FREIGHT DECIMAL(10,2) DEFAULT 0,
SHIP_NAME VARCHAR(40),
SHIP_ADDRESS VARCHAR(60),
SHIP_CITY VARCHAR(15),
SHIP_REGION VARCHAR(15),
SHIP_POSTAL_CODE VARCHAR(10),
SHIP_COUNTRY VARCHAR(15),
CONSTRAINT PK_ORDERS PRIMARY KEY (ORDER_ID),
CONSTRAINT FK_CUSTOMER_CODE FOREIGN KEY (CUSTOMER_CODE) REFERENCES CUSTOMER(CUSTOMER_CODE),
CONSTRAINT FK_EMPLOYEE_ID FOREIGN KEY (EMPLOYEE_ID) REFERENCES EMPLOYEE(EMPLOYEE_ID),
CONSTRAINT FK_SHIP_VIA FOREIGN KEY (SHIP_VIA) REFERENCES SHIPPER(COMPANY_NAME)
);
CREATE TABLE ORDER_DETAIL
(
ORDER_ID DECIMAL(9) NOT NULL,
PRODUCT_NAME VARCHAR(40) NOT NULL,
UNIT_PRICE DECIMAL(10,2) NOT NULL DEFAULT 0,
QUANTITY DECIMAL(9) NOT NULL DEFAULT 1 ,
DISCOUNT DECIMAL(4,2) NOT NULL DEFAULT 0,
CONSTRAINT PK_ORDER_DETAIL PRIMARY KEY (ORDER_ID, PRODUCT_NAME),
CONSTRAINT FK_ORDER_ID FOREIGN KEY (ORDER_ID) REFERENCES ORDERS (ORDER_ID),
CONSTRAINT FK_PRODUCT_NAME FOREIGN KEY (PRODUCT_NAME) REFERENCES PRODUCT (PRODUCT_NAME),
CONSTRAINT CK_ORDER_DETAIL_UNIT_PRICE CHECK (UNIT_PRICE >= 0),
CONSTRAINT CK_ORDER_DETAIL_QUANTITY CHECK (QUANTITY > 0),
CONSTRAINT CK_ORDER_DETAIL_DISCOUNT CHECK (DISCOUNT between 0 and 1)
);
i think i might need to use this table but i am unsure(TABLE PRODUCT)
CREATE TABLE PRODUCT
(
PRODUCT_NAME VARCHAR(40) NOT NULL,
SUPPLIER_NAME VARCHAR(40) NOT NULL,
CATEGORY_NAME VARCHAR(30) NOT NULL,
QUANTITY_PER_UNIT VARCHAR(20),
UNIT_PRICE DECIMAL(10,2) NOT NULL DEFAULT 0,
UNITS_IN_STOCK DECIMAL(9) NOT NULL DEFAULT 0,
UNITS_ON_ORDER DECIMAL(9) NOT NULL DEFAULT 0,
REORDER_LEVEL DECIMAL(9) NOT NULL DEFAULT 0,
DISCONTINUED CHAR(1) NOT NULL DEFAULT 'N',
CONSTRAINT PK_PRODUCT PRIMARY KEY (PRODUCT_NAME),
CONSTRAINT FK_CATEGORY_NAME FOREIGN KEY (CATEGORY_NAME) REFERENCES CATEGORY(CATEGORY_NAME),
CONSTRAINT FK_SUPPLIER_NAME FOREIGN KEY (SUPPLIER_NAME) REFERENCES SUPPLIER(COMPANY_NAME),
CONSTRAINT CK_PRODUCT_UNIT_PRICE CHECK (UNIT_PRICE >= 0),
CONSTRAINT CK_PRODUCT_UNITS_IN_STOCK CHECK (UNITS_IN_STOCK >= 0),
CONSTRAINT CK_PRODUCT_UNITS_ON_ORDER CHECK (UNITS_ON_ORDER >= 0),
CONSTRAINT CK_PRODUCT_REORDER_LEVEL CHECK (REORDER_LEVEL >= 0),
CONSTRAINT CK_PRODUCT_DISCONTINUED CHECK (DISCONTINUED in ('Y','N'))
);
This is the exact question
Insert into a file solution1.sql implementation of the following query as
SELECT statement with WITH clause.
Find all orders such that a value of each order is greater than an average value of all orders submitted so far. List in each line of output an order identifier, a total value of an order, and an average value of all orders. The results must be sorted in the descending order of a total value of each order.
"A total value of an order must be computed as the summation of unit price * quantityover all items included in the order. The query must be implemented as a sequence of subquery definitions following WITH keyword and ended with the final SELECT.
(i) The first subquery definition must find a total value of each order together with an order identifier (attribute order_id). "
im currently on (i)
Ignoring for a moment the subsequent requirements, the first block of code might look like this:
SELECT o.some
, o.columns
, o.from_orders
, x.total_value
FROM orders o
JOIN
( SELECT order_id
, SUM(quantity * unit_price) total_value
FROM order_detail
GROUP
BY order_id
) x
ON x.order_id = o.order_id

Recieving an Error when attemtping to Join 3 tables

Hello all hope all is well. Im still new to mysql and im beginning to use JOIN functions and solving a problem which involves the combination of 3 Tables. Ive followed the Syntax i found
SELECT t1.col, t3.col FROM table1 join table2 ON table1.primarykey = table2.foreignkey
join table3 ON table2.primarykey = table3.foreignkey
The question is:
"Find a name of product ordered and order date of all products ordered by a customer with customer code SAVEA and such that quantity of product is 10."
Here is my Solution
SELECT CUSTOMER.CUSTOMER_CODE, ORDERS.ORDER_DATE, ORDER_DETAIL.PRODUCT_NAME, ORDER_DETAIL.QUANTITY
FROM ORDERS
JOIN CUSTOMER ON CUSTOMER.CUSTOMER_CODE = ORDERS.CUSTOMER_CODE
JOIN ORDER_DETAIL ON ORDERS.ORDER_ID = ORDER_DETAIL.ORDER_ID
WHERE ORDER_DETAIL.QUANTITY = '10';
and here are the 3 tables i am using, labeled.
TABLE CUSTOMER
CREATE TABLE CUSTOMER
(
CUSTOMER_CODE VARCHAR(5) NOT NULL,
COMPANY_NAME VARCHAR(40) NOT NULL,
CONTACT_NAME VARCHAR(30),
CONTACT_TITLE VARCHAR(30),
ADDRESS VARCHAR(60),
CITY VARCHAR(15),
REGION VARCHAR(15),
POSTAL_CODE VARCHAR(10),
COUNTRY VARCHAR(15),
PHONE VARCHAR(24),
FAX VARCHAR(24),
CONSTRAINT PK_CUSTOMER PRIMARY KEY (CUSTOMER_CODE)
);
TABLE ORDERS
CREATE TABLE ORDERS
(
ORDER_ID DECIMAL(9) NOT NULL,
CUSTOMER_CODE VARCHAR(5) NOT NULL,
EMPLOYEE_ID DECIMAL(9) NOT NULL,
ORDER_DATE DATE NOT NULL,
REQUIRED_DATE DATE,
SHIPPED_DATE DATE,
SHIP_VIA VARCHAR(40),
FREIGHT DECIMAL(10,2) DEFAULT 0,
SHIP_NAME VARCHAR(40),
SHIP_ADDRESS VARCHAR(60),
SHIP_CITY VARCHAR(15),
SHIP_REGION VARCHAR(15),
SHIP_POSTAL_CODE VARCHAR(10),
SHIP_COUNTRY VARCHAR(15),
CONSTRAINT PK_ORDERS PRIMARY KEY (ORDER_ID),
CONSTRAINT FK_CUSTOMER_CODE FOREIGN KEY (CUSTOMER_CODE) REFERENCES CUSTOMER(CUSTOMER_CODE),
CONSTRAINT FK_EMPLOYEE_ID FOREIGN KEY (EMPLOYEE_ID) REFERENCES EMPLOYEE(EMPLOYEE_ID),
CONSTRAINT FK_SHIP_VIA FOREIGN KEY (SHIP_VIA) REFERENCES SHIPPER(COMPANY_NAME)
);
TABLE ORDER_DETAIL
CREATE TABLE ORDER_DETAIL
(
ORDER_ID DECIMAL(9) NOT NULL,
PRODUCT_NAME VARCHAR(40) NOT NULL,
UNIT_PRICE DECIMAL(10,2) NOT NULL DEFAULT 0,
QUANTITY DECIMAL(9) NOT NULL DEFAULT 1 ,
DISCOUNT DECIMAL(4,2) NOT NULL DEFAULT 0,
CONSTRAINT PK_ORDER_DETAIL PRIMARY KEY (ORDER_ID, PRODUCT_NAME),
CONSTRAINT FK_ORDER_ID FOREIGN KEY (ORDER_ID) REFERENCES ORDERS (ORDER_ID),
CONSTRAINT FK_PRODUCT_NAME FOREIGN KEY (PRODUCT_NAME) REFERENCES PRODUCT (PRODUCT_NAME),
CONSTRAINT CK_ORDER_DETAIL_UNIT_PRICE CHECK (UNIT_PRICE >= 0),
CONSTRAINT CK_ORDER_DETAIL_QUANTITY CHECK (QUANTITY > 0),
CONSTRAINT CK_ORDER_DETAIL_DISCOUNT CHECK (DISCOUNT between 0 and 1)
);
The exact error i get is ERROR 1054(42522) Unknown column 'CUSTOMER_CODE' in 'field list'. I believe i am follwing the right Syntax so maybe its an issue with a comma or my order. if anyone could help it would be much appreciated

how to call columns from different table using sub-queries in mysql with certain condition

//this is the question
Find customer name, order number and order amount if order amount is greater than average
sales amount of the customers and sort the record by customer name [Hint: use WHERE
clause].
SELECT
name, orderno, amount
FROM
customerinfo,
orderdetails
WHERE
amount > (SELECT
AVG(amount)
FROM
orderdetails)
ORDER BY name;
//this the result the result are not what i look for
this the table coding
CREATE TABLE customerinfo (
customercode VARCHAR(10) NOT NULL UNIQUE,
name VARCHAR(60) NOT NULL,
address VARCHAR(60),
poscode INT(5),
city VARCHAR(30),
state VARCHAR(30),
hpno VARCHAR(20),
email VARCHAR(50),
salesmanid VARCHAR(10),
PRIMARY KEY (customercode),
FOREIGN KEY (salesmanid)
REFERENCES salesman (salesmanid)
);
CREATE TABLE salesman (
salesmanid VARCHAR(10) NOT NULL UNIQUE,
salesmanname VARCHAR(60) NOT NULL,
PRIMARY KEY (salesmaniD)
);
CREATE TABLE orderinfo (
orderno INT(10) NOT NULL,
ordertype VARCHAR(50),
orderdate DATE,
deliverydate DATE,
PRIMARY KEY (orderno)
);
CREATE TABLE orderdetails (
orderno INT(10) NOT NULL,
itemcode VARCHAR(10) NOT NULL,
quantity INT(5),
amount DECIMAL(9 , 2 ),
PRIMARY KEY (orderno , itemcode),
FOREIGN KEY (orderno)
REFERENCES orderinfo (orderno),
FOREIGN KEY (itemcode)
REFERENCES item (itemcode)
);
CREATE TABLE item (
itemcode VARCHAR(10) NOT NULL UNIQUE,
itemdesc VARCHAR(60),
unit VARCHAR(10),
sellingprice DECIMAL(9 , 2 ) NOT NULL,
PRIMARY KEY (itemcode)
);
CREATE TABLE ordersalesmaninfo (
salesmanid VARCHAR(10) NOT NULL,
orderno INT(10) NOT NULL,
PRIMARY KEY (salesmanid),
FOREIGN KEY (salesmanid)
REFERENCES salesman(salesmanid),
FOREIGN KEY (orderno)
REFERENCES orderinfo (orderno)
);
i may have problem with the normalisation process but i think there will not cause any impact to the question .

How add a customer to an order when getting the customer details from a form

I am having trouble adding a customer and their order to an order table once they have checked out.
Here is my SQL for creating the four tables I am using:
CREATE TABLE IF NOT EXISTS Product(
ID int NOT NULL AUTO_INCREMENT,
Name varchar(255) NOT NULL,
Description text(65535) NOT NULL,
Quantity int NOT NULL,
Photo varchar(255),
Price float NOT NULL,
Category varchar(50),
PRIMARY KEY (ID)
) ENGINE=innoDB;
CREATE TABLE IF NOT EXISTS Customer(
ID int NOT NULL AUTO_INCREMENT,
FirstName varchar(255) NOT NULL,
LastName varchar(255) NOT NULL,
Email varchar(255) NOT NULL,
PhoneNumber varchar(11) NOT NULL,
Address varchar(50),
Town varchar(50),
County varchar(50),
PostCode varchar(50),
PRIMARY KEY (ID)
) ENGINE=innoDB;
CREATE TABLE IF NOT EXISTS OrderTable(
ID int NOT NULL AUTO_INCREMENT,
Date date NOT NULL,
PRIMARY KEY (ID),
TotalPrice float NOT NULL,
Customer_ID int NOT NULL,
CONSTRAINT fk_Order_1
FOREIGN KEY (Customer_ID)
REFERENCES coursework_db.Customer (ID)
) ENGINE=innoDB;
CREATE TABLE IF NOT EXISTS OrderItem(
ID int NOT NULL AUTO_INCREMENT,
PRIMARY KEY (ID),
Product_ID int NOT NULL,
Order_ID int NOT NULL,
Quantity int NOT NULL,
TotalPrice float NOT NULL,
CONSTRAINT fk_OrderItem_1
FOREIGN KEY (Product_ID)
REFERENCES coursework_db.Product(ID),
CONSTRAINT fk_OrderItem_2
FOREIGN KEY (Order_ID)
REFERENCES coursework_db.OrderTable(ID)
) ENGINE=innoDB;
The problem I am having is how to select the customer from the table once they have been added to the database to use as a foreign key in the OrderTable table.
At the moment I have the details of the customer stored in local storage which can easily be accessed, but once the customer is added to the database they will get an ID. This is the only way I could think to select a unique customer.
Insert the customer details first. Then get the ID of the newly inserted customer and use it while inserting the order details!
You could use the LAST_INSERT_ID() after you insert the user details to the db to get the ID of the customer.
Or if you are using PHP, then:
if you're using PDO, use PDO::lastInsertId
if you're using Mysqli, use mysqli::$insert_id
Hope this helps.