Database design with creating a product that has two prices - sql

I'm creating a database design for our water refilling system and I'm just new to databases. I am stuck with creating table that provides two different prices for a product. To further explain my problem, here's an example, a product's ('5 GALLON') price changes when it is delivered or bought on point by a customer. For example a delivered ('5 GALLON') is 45 pesos while a bought on point gallon is only 40 pesos. Can someone help me please?
Here's my codes so far
create table Product (
product_id int primary key,
prodtype_id int,
product_name varchar(55),
product_quantity int
)
-----NOT SURE IF THESE TWO TABLES ARE CORRECT
create table DeliveryPrice (
prod_id int,
product_price money,
foreign key (prod_id) references Product
)
create table OnPointPrice(
prod_id int,
product_price money,
foreign key (prod_id) references Product
)

You're likely better off just having the two prices in the Product table. They are attributes of the product, so that's where they belong.
Also, you should specify which columns are NOT NULL in your database (which should be most of them).

So is this correct?
create table Product(
product_id int primary key,
product_name varchar(55) not null,
product_quantity int not null,
pickup_price money not null,
delivery_price money not null
)
create table Customer(
customer_id int primary key,
customer_name varchar (255) not null,
customer_address varchar(200),
customer_phone int
)
create table INVOICE(
inv_number int primary key,
customer_id varchar(5),
foreign key (customer_id) references Customer,
inv_date date not null,
bought_mode char(10) not null
)
create table LINE(
INV_NUMBER int,
foreign key (INV_NUMBER) references INVOICE,
LINE_NUMBER INT not null,
PRIMARY KEY (INV_NUMBER, LINE_NUMBER),
line_quantity int not null,
line_price money not null
)

Related

How to get details for a customer that is both a seller and a buyer

I have a database which contains customers that are both buyers and sellers.
the customers can buy and sell houses.
I need to get details for the customers separately and still have a connection between them so i could know which customer sold to which customer.
In case a customer buys a house from a different customer how can i get the details for each customer separately?
The table I made so far for the customers is :
CREATE TABLE Customers (
SellerID int,
BuyerID int,
HouseID int,
SaleID int,
FirstName varchar (50),
LastName varchar (50),
Adress varchar (50),
BirthDate Date,
City varchar (50),
HomePhone varchar (50),
PRIMARY KEY (SellerID, BuyerID),
FOREIGN KEY (HouseID) REFERENCES House(HouseID),
FOREIGN KEY (SaleID) REFERENCES Sale(SaleID),
);
I have a sale table
CREATE TABLE Sale (
SaleID int,
SalesManID int,
SaleDate Date,
SalePrice int,
PRIMARY KEY (SaleID),
FOREIGN KEY (SalesManID) REFERENCES SalesMan(SalesManID),
);
I have a table that contains both sale and customers
CREATE TABLE SaleToCustomers (
SaleID int,
CustomersID int,
PRIMARY KEY (SaleID, CustomersID)
);
Your entities are confused. A customer should be a person, with information about the persion. Then Sales should refer to it twice, once for buyers and o once for sellers:
CREATE TABLE Customers (
CustomerId int PRIMARY KEY,
FirstName varchar(50),
LastName varchar(50),
Adress varchar(50),
BirthDate Date,
City varchar(50),
HomePhone varchar(50)
);
CREATE TABLE Sales (
SaleID int PRIMARY KEY,
SellerId int,
BuyerId int,
HouseId int,
SaleDate Date,
SalePrice int,
FOREIGN KEY (SellerId) REFERENCES Customers(CustomerId),
FOREIGN KEY (BuyerId) REFERENCES Customers(CustomerId),
FOREIGN KEY (HouseID) REFERENCES House(HouseID)
);
In other words, "buyer" and "seller" are attributes of a sale, not of a person.

ERROR: No unique constraint matching given keys for referenced table

For some reason I'm getting an error* in my code. I'm quite new to PostgreSQL, and simply SQL. What is causing this error?
*there is no unique constraint matching given keys for referenced table "tech".
BEGIN;
CREATE TABLE Person (
person_id SERIAL PRIMARY KEY,
firstname VARCHAR(128),
lastname VARCHAR(128),
email_adr VARCHAR(128),
UNIQUE(person_id, email_adr)
);
CREATE TABLE Phone (
person_id INT REFERENCES Person(person_id),
phone_nr INT PRIMARY KEY,
UNIQUE(phone_nr)
);
CREATE TABLE Tech (
tech_id INT REFERENCES Person(person_id),
username VARCHAR(80) PRIMARY KEY,
password VARCHAR(80) NOT NULL,
location Varchar(128),
UNIQUE(username, tech_id)
);
CREATE TABLE Customer (
customer_id INT REFERENCES Persons(person_id),
addresse VARCHAR(255) NOT NULL,
UNIQUE(customer_id)
);
CREATE TABLE Task (
task_id SERIAL PRIMARY KEY,
payment MONEY,
tech INT REFERENCES Tech(tech_id) NOT NULL,
customer INT REFERENCES Customer(customer_id) NOT NULL,
start_date DATE NOT NULL,
end_dato DATE,
UNIQUE(tech, customer, start_date, end_date)
);
COMMIT;
In table Task you trying to reference to table Tech by tech_id. To do that you must add UNIQUE CONSTRAINT to tech_id in Tech.
Right now in table Tech you have UNIQUE(username, tech_id) that means that values in column tech_id could by doubled Ex.
Tech
-------------------------------
tech_id username, ....
------------------------------
1 'John'
2 'Tony'
1 'Nataly'
Acctually the better idea is to set reference by PRIMARY KEY, so in your case username in table Tech.
If you want to leave structure the way present in question, you should just add UNIQUE(tech_id) in column Tech.
What do you think of this code?
BEGIN;
CREATE TABLE Person (
person_id SERIAL PRIMARY KEY,
firstname VARCHAR(128),
lastname VARCHAR(128),
email_adr VARCHAR(128),
UNIQUE(person_id),
UNIQUE(email_adr)
);
CREATE TABLE Phone (
person_id INT,
phone_nr INT PRIMARY KEY,
);
CREATE TABLE Tech (
tech_id INT,
username VARCHAR(80) PRIMARY KEY,
password VARCHAR(80) NOT NULL,
location Varchar(128),
FOREIGN KEY(tech_id) REFERENCES Person(person_id),
UNIQUE(username),
UNIQUE(tech_id)
);
CREATE TABLE Customer (
customer_id INT REFERENCES Persons(person_id),
addresse VARCHAR(255) NOT NULL,
FOREIGN KEY(tech_id) REFERENCES Person(person_id),
UNIQUE(customer_id)
);
CREATE TABLE Task (
task_id SERIAL PRIMARY KEY,
payment MONEY,
tech varchar(80) REFERENCES Tech(username) NOT NULL,
customer INT REFERENCES Customer(customer_id) NOT NULL,
start_date DATE NOT NULL,
end_dato DATE,
UNIQUE(tech, customer, start_date, end_date)
);
COMMIT;

Shop database, SQL for order table

I have a University project and I have to create a DB for a plant shop.
I have a problem with the order table. At the moment it only allows a customer to buy one product at a time but in real life a customer buys many products at a time.
For example,
We have a customer John Doe, and he bus two products that are in the product table. How do I pull those two (or more) products and add them to one order table?
Below is the SQL code I wrote:
CREATE TABLE customer(
customer_id INT(3),
customer_fname VARCHAR(20),
customer_lname VARCHAR(20),
customer_gender CHAR(1),
customer_tel VARCHAR(20),
customer_email VARCHAR(30),
customer_dateJoined DATE,
address_id INT(3),
PRIMARY KEY(customer_id),
INDEX(customer_id),
FOREIGN KEY(customer_id) REFERENCES address);
CREATE TABLE address(
adress_id INT(3),
customer_street VARCHAR(30),
customer_town VARCHAR(30),
customer_postcode CHAR(7),
PRIMARY KEY(address_id),
INDEX(address_id),
FOREIGN KEY(address_id) REFERENCES customer(address_id),
FOREIGN KEY(address_id) REFERENCES employee(address_id));
CREATE TABLE product(
product_id INT(5),
product_name VARCHAR(20),
product_season VARCHAR(15),
product_price NUMERIC(4,2),
product_origin VARCHAR(15),
product_type VARCHAR(15),
product_inStock BOOLEAN,
PRIMARY KEY(product_id),
INDEX(product_id));
CREATE TABLE orders(
order_id INT(3),
customer_id INT(3),
employee_id INT(3),
product_name VARCHAR(20),
quantity INT(4),
order_date TIMESTAMP,
PRIMARY KEY(order_id),
INDEX(order_id));
CREATE TABLE employee(
employee_id INT(3),
employee_fname VARCHAR(20),
employee_lname VARCHAR(20),
address_id INT (3),
employee_pay NUMERIC(2,2),
employee_daysOff INT(2),
employee_hoursWorked INT(3),
PRIMARY KEY(staff_id),
INDEX(staff_id));
You have to create Kettle Table customer_orders, in this table you store customer_id and order_id and connect them with foreign keys to the customer and orders tables.
Like in the following query:
CREATE TABLE customer_orders(
customer_id INT(3),
order_id INT(3),
PRIMARY KEY(customer_id, order_id),
FOREIGN KEY(customer_id) REFERENCES customer(customer_id),
FOREIGN KEY(order_id) REFERENCES orders(order_id)
);
CREATE TABLE sales.stores (
store_id INT IDENTITY (1, 1) PRIMARY KEY,
store_name VARCHAR (255) NOT NULL,
phone VARCHAR (25),
email VARCHAR (255),
street VARCHAR (255),
city VARCHAR (255),
state VARCHAR (10),
zip_code VARCHAR (5)
);
One way to design this is to have two tables for Orders.
OrderHeader :- This contains order id with customer details.
OrderItem :- Contains Line items per order.
OrderHeader fields could be
order_id //primary key
customer_id
employee_id
order_date
OrderItem :- Fields could be
order_id //composite key
line_Item_id //composite key
product_id,
product_quant

Designing a rudimentary Shopping Cart database

create table [User]
(
UserId int primary key identity(1,1),
FirstName nvarchar(256) not null,
LastName nvarchar(256) not null,
)
create table Product
(
ProductId int primary key identity(1,1),
UnitPrice decimal(18,2) not null, //For catalog purposes.
Name nvarchar(1000) not null,
Description nvarchar(max) not null,
Stock int not null
)
create table [Order]
(
OrderId int primary key identity(1,1),
UserId int foreign key references [User](UserId),
ProductId int foreign key references Product(ProductId),
UnitCost decimal(18,2) not null, //How much it actually cost when the person bought it.
ItemCount int not null,
Subtotal decimal(18,2) not null
)
create table OrderDetail
(
OrderDetailId int primary key identity(1,1),
?
I'm stuck on the database design of the order system.
A user can choose n products to add to a order request. Any suggestions?
Following some advice given here, how would this feel? Any pitfalls?
create table [User]
(
UserId int primary key identity(1,1),
FirstName nvarchar(256) not null,
LastName nvarchar(256) not null,
)
create table Product
(
ProductId int primary key identity(1,1),
UnitPrice decimal(18,2) not null,
Name nvarchar(1000) not null,
Description nvarchar(max) not null,
Stock int not null
)
create table [Order]
(
OrderId int primary key identity(1,1),
UserId int foreign key references [User](UserId),
DateOfOrder datetime not null
)
create table OrderDetail
(
OrderDetailId int primary key identity(1,1),
OrderId int foreign key references [Order](OrderId),
ProductId int foreign key references Product(ProductId),
UnitCost decimal(18,2) not null,
ItemCount int not null,
Subtotal decimal(18,2) not null
)
Typically, you'd have the Order table with the top-level order information (who, when etc) and then an OrderItem (or OrderDetail) table which has a row for each product that forms part of the order including columns like:
OrderId
ProductId
Quantity
etc
Good candidate for a PK on this OrderItem/OrderDetail table would be on OrderId + ProductId.
So where you have columns like ProductId, UnitCost, ItemCount etc in the Order table, those are in the wrong place and should be in the OrderItem/OrderDetail table.
Update:
To set up a compound PK, you can do:
create table OrderDetail
(
OrderId int foreign key references [Order](OrderId),
ProductId int foreign key references Product(ProductId),
...other columns...,
CONSTRAINT PK_OrderDetail PRIMARY KEY(OrderId, ProductId)
)

ERD for ShoppingCart

I'm a bit confused about the entity relationship diagram for my application.
So far I have made tables for Product,Customer,Category
Should I make a table for UserAccounts that holds the id and password for the Customer or directly place the the id and password in the Customer table?
Secondly, each customer will have his own cart. So I have made a CartItem table
CartItemId,
ProductId,
CategoryId,
Description,
UnitPrice,
TotalPrice
But this table is not associating a customer with the cartItem in the shoppingcart. So Should i add the CustomerId here also?
Is there a need for Description and unit price, because those are already defined in the Product Table?
and for Cart Table,
CartId,
CartItemId,
CustomerId
I need to clear up a few things, before I find any mistakes in my application.
DDL:
CREATE DATABASE ShoppingCart
Create Table Customer(
CustomerId int PRIMARY KEY,
Firstname varchar(50),
Lastname varchar(50),
Address varchar(50),
City varchar(50),
State varchar(50),
Country varchar(50),
Mobile varchar(50),
Phone varchar(50),
Email varchar(50)
)
Create Table UserAccount(
UserName varchar(50),
PasswordHash varchar(50)
)
Create Table Category(
CategoryId int PRIMARY KEY,
CategoryName varchar(50),
CategoryDescription varchar(50),
CategoryImage varchar(50)
)
Create Table Products(
ProductId int PRIMARY KEY,
ProductName varchar(50),
Description varchar(50),
CategoryId int,
UnitPrice money,
DateAdded datetime,
thumn varchar(50),
CONSTRAINT fk_CategoryId FOREIGN KEY (CategoryId)
REFERENCES Category(CategoryId)
)
Create Table CartItem(
CartItemId int,
ProductId int,
CategoryId int,
Description varchar(50),
UnitPrice money,
TotalPrice money,
PRIMARY KEY (CartItemId),
CONSTRAINT fk_ProductId FOREIGN KEY (ProductId)
REFERENCES Products(ProductId),
CONSTRAINT fk_CartItem_CategoryId FOREIGN KEY (CategoryId)
REFERENCES Category(CategoryId)
)
Create Table Cart(
CartId int,
CartItemId int,
ProductId int,
CategoryId int,
Description varchar(50),
UnitPrice money,
TotalPrice money,
PRIMARY KEY (CartId),
CONSTRAINT fk_CartItemId FOREIGN KEY (CartItemId)
REFERENCES CartItem(CartItemId),
CONSTRAINT fk_CartItem_CategoryId FOREIGN KEY (CategoryId)
REFERENCES Category(CategoryId),
PRIMARY KEY (ProductId),
CONSTRAINT fk_CartItemId FOREIGN KEY (ProductId)
REFERENCES CProducts(productId)
)
#1 Do not store the password - store a salted hash.
Do not make the customer Id in the cart item table if it's already obtained through going through Cart table.
Right now, I think you are confused with having a Cart and CartItem table which are nearly identical.
UserAccount appears to be orphaned. It needs to be either in the Customer table or somehow linked.
I would drop CategoryId, Description, UnitPrice and TotalPrice from CartItem (since they are in Product) unless products are customized into the shopping cart for each customer. You also run the risk of letting a user check out with a product at an old price (unless you treat carts as quotes, which is a whole other business domain).
A CartItem needs a way to get to its Cart or Customer.
Here's what I would do:
Category (CategoryID (PK), etc.)
Customer (CustomerID (PK), etc.)
Product (ProductID (PK), CategoryID (FK), etc)
Cart (CartID (PK), CustomerID (FK), ProductID(FK), Quantity)
When a cart becomes an order, typically an order detail or invoice detail table will lock in the price, and perhaps the name of the product, and the cart will be emptied for a custoemr. A lot of this depends on further business needs.