How to design a friend list in sql /sqlite - sql

Im relatively new to sql and Im trying to create a relationship between two users.
A friend request has to be sent and accepted to be friends with each other. Now I have a third table called items. A user should now be able to see all items that are owned by his friends. Im kinda stuck writing this query...
item table:
CREATE TABLE IF NOT EXISTS item(
id INTEGER PRIMARY KEY AUTOINCREMENT NOT NULL,
owner VARCHAR(50) NOT NULL,
borrowedBy VARCHAR(50),
imageUrl TEXT
);
friendship table:
CREATE TABLE IF NOT EXISTS friendship(
friendship_id INTEGER PRIMARY KEY AUTOINCREMENT NOT NULL
);
user_friendship
CREATE TABLE IF NOT EXISTS user_friendship(
username VARCHAR(50) NOT NULL,
friendship_id INTEGER NOT NULL,
status INTEGER NOT NULL,
PRIMARY KEY (username, friendship_id)
);

You need to look at tutorials on how to build a SQL database, mainly on table relationship.
Here, for example, you don't need separate friendship and user_friendship table.
You could have one friendship table:
CREATE TABLE IF NOT EXISTS friendship(
friendship_id INTEGER NOT NULL,
username1 VARCHAR(50) NOT NULL,
username2 VARCHAR(50) NOT NULL,
status INTEGER NOT NULL,
PRIMARY KEY (friendship_id, username1 , username2 )
);
Note that you should use integer value for foreign keys, not varchar(50).

Related

Can we update a record that is defined as a foreign key of a unique record define in a different table?

I am new to PostgreSQL and how i can update the records while they are related with a foreign key definition.
I am getting an error and that would be great if you can guide me with any hints
Let's say we have two different tables like below :
CREATE TABLE IF NOT EXISTS student
(
id_num VARCHAR(40) NOT NULL REFERENCES registered(student_id),
first_name VARCHAR(32) NOT NULL,
last_name VARCHAR(32) NOT NULL,
birthdate DATE NOT NULL,
PRIMARY KEY(id_num)
);
CREATE TABLE IF NOT EXISTS registered
(
student_id VARCHAR(40) NOT NULL UNIQUE,
paid_tuition BOOL NOT NULL,
PRIMARY KEY(paid_tuition)
);
Based on my understating i need to fill the registered table and then try to insert values to the student table that their id match the student_id value in registered table.
But when I try it I get the following error?
Any idea or recommendation?
Message:"update or delete on table "registered" violates foreign key
constraint "student_id_num_id_fkey" on table "student"",
Detail:"Key (id_num)=(idNum-1) is still referenced from table
"student".", Hint:"", Position:0, InternalPosition:0,
InternalQuery:"", Where:"", SchemaName:"", TableName:"student",
ColumnName:"", DataTypeName:"",
ConstraintName:"student_id_num_id_fkey", File:"ri_triggers.c",
Line:2490, Routine:"ri_ReportViolation"}
seems like you are linking tables in opposite direction , to me it makes more sense that "registered" table has been linked to student table by fk studentid .
also in your "student" table definition you are saying that column "id" is primary key while no "id" column has been declared.
so here is what I mean:
CREATE TABLE IF NOT EXISTS student
(
id_num VARCHAR(40) NOT NULL REFERENCES registered(student_id),
first_name VARCHAR(32) NOT NULL,
last_name VARCHAR(32) NOT NULL,
birthdate DATE NOT NULL,
PRIMARY KEY(id_num)
);
CREATE TABLE IF NOT EXISTS registered
(
student_id VARCHAR(40) NOT NULL REFERENCES student(id_num)
paid_tuition BOOL NOT NULL,
PRIMARY KEY(id_num)
);

How should I structure my simple database?

I am creating a database (for data from an online game) in which I need to store Players and their Villages. Each Player has at least 1 village. All Villages are unique and every Village has exactly 1 owner(Player).
It is probably important to mention, that I intend to create a new table/tables every day since the online game in question releases an updated game world data file once every 24hours. Once a table is created, I will never have to make changes in it, I will only need to read data from it.
I came up with 2 solutions for now, but I dont know what the right approach is.
Solution1:
CREATE TYPE village_t AS (
id INTEGER,
x INTEGER,
y INTEGER,
village_id INTEGER,
village_name VARCHAR,
pop INTEGER,
region VARCHAR
);
CREATE TABLE players (
tribe INTEGER NOT NULL,
user_id INTEGER PRIMARY KEY,
user_name VARCHAR(30) UNIQUE NOT NULL,
aliance_id INTEGER NOT NULL,
aliance_name VARCHAR(30) NOT NULL,
villages village_t[]
);
Solution2:
CREATE TABLE players (
tribe INTEGER NOT NULL,
user_id INTEGER PRIMARY KEY,
user_name VARCHAR(30) UNIQUE NOT NULL,
aliance_id INTEGER NOT NULL,
aliance_name VARCHAR(30) NOT NULL
);
CREATE TABLE villages (
id INTEGER NOT NULL,
x INTEGER NOT NULL,
y INTEGER NOT NULL,
village_id INTEGER NOT NULL,
village_name VARCHAR NOT NULL,
user_id INTEGER,
CONSTRAINT fk_con FOREIGN KEY(user_id) REFERENCES players(user_id),
pop INTEGER NOT NULL,
region VARCHAR
);
CREATE INDEX idx ON villages(user_id);
You have a 1-n relationship. Each village ("n") has one owner ("1"). Your second solution is the canonical way of storing this information in a database.
Your first solution does not even enforce the notion that a village as one owner, so I'm not sure why you are considering it. The second imposes this condition as part of the data model.
Your second solution has set up the recommend foreign key and indexes for what you describe, by the way, so it looks fine.
If you need to read village data frequently, Solution 1 is not recommended. This is because the list of village ids design removes the scope of joining the person and village table
Solution 2 is the most preferred way of going about as it keeps all your options open (whether you would frequently need village data or not)
Another way of going about solution 2 is to create a cross-reference table for user_id and village_id
CREATE TABLE players (
tribe INTEGER NOT NULL,
user_id INTEGER PRIMARY KEY,
user_name VARCHAR(30) UNIQUE NOT NULL,
aliance_id INTEGER NOT NULL,
aliance_name VARCHAR(30) NOT NULL
);
CREATE TABLE villages (
id INTEGER NOT NULL,
x INTEGER NOT NULL,
y INTEGER NOT NULL,
village_id INTEGER NOT NULL,
village_name VARCHAR NOT NULL,
pop INTEGER NOT NULL,
region VARCHAR
);
CREATE TABLE xref_players_villages (
user_id INTEGER,
CONSTRAINT fk_con1 FOREIGN KEY(user_id) REFERENCES players(user_id),
village_id INTEGER,
CONSTRAINT fk_con2 FOREIGN KEY(village_id ) REFERENCES villages(village_id ),
);

Create views for user profile management

I have the below schema for user profile management,
CREATE TABLE IF NOT EXISTS users
(
userid TEXT NOT NULL,
name TEXT NULL,
lmessage INTEGER NULL,
statusid INTEGER NULL,
/* statusid should refer to last status of the user in status table*/
locationid INTEGER NULL,
/* locationid should refer to last status of the user in locations table */
registered INTEGER NOT NULL,
tinypic INTEGER NULL
/* this refers to media id in media table */,
largepic INTEGER NULL
/* this also refers to media id in media table */,
groupid INTEGER NULL
/* this refers to id in groups table */ ,
PRIMARY KEY (userid)
);
CREATE TABLE IF NOT EXISTS locations
(
serial INTEGER,
locationid TEXT NOT NULL,
userid TEXT NOT NULL,
time INTEGER NULL,
PRIMARY KEY (serial)
);
CREATE TABLE IF NOT EXISTS status
(
serial INTEGER,
userid TEXT NULL,
message TEXT NOT NULL,
time INTEGER NULL,
PRIMARY KEY (serial)
);
CREATE TABLE IF NOT EXISTS messages
(
sno INTEGER,
messageid INTEGER NOT NULL,
sender TEXT NOT NULL,
receiver TEXT NOT NULL,
time INTEGER NULL,
message TEXT NULL,
image INTEGER NULL,
video INTEGER NULL,
audio INTEGER NULL,
PRIMARY KEY (sno)
);
CREATE TABLE IF NOT EXISTS media
(
mediaid TEXT NOT NULL UNIQUE,
url TEXT NULL,
downloaded INTEGER NULL,
thumbnail TEXT NULL,
PRIMARY KEY (mediaid)
);
CREATE TABLE IF NOT EXISTS groups
(
serial INTEGER,
name TEXT NOT NULL,
id INTEGER NOT NULL
PRIMARY KEY(serial)
);
CREATE UNIQUE INDEX IF NOT EXISTS id_unique ON users (userid ASC);
CREATE UNIQUE INDEX IF NOT EXISTS serial_unique ON status (serial ASC);
CREATE UNIQUE INDEX IF NOT EXISTS id_unique ON messages (sno ASC);
CREATE UNIQUE INDEX IF NOT EXISTS serial_unique ON patterns (serial DESC);
CREATE UNIQUE INDEX IF NOT EXISTS mediaid_unique ON media (mediaid ASC);
How can create views on user table to get list of users based on filter conditions. Please suggest me schema design is not good.
A view example that I would like to add on this schema :
Select all users who belong to group and all groups created after that group.
Select all users with last message, status, location and media urls included.
Thanks.
Please Note that I am SQL nube, please forgive me if you feel like this is immature question. All I need is, I want to learn from reviews of other people.
for 1 - you need to have timestamp (INTEGER id you go by UTC ticks) in group table - it is missing
for 2 - you can do it with join
bot case i don't think you need to have a view unless you have some specific reasons. You can go by select queries with join to get required data.
I recommend you to use http://www.sqliteexpert.com/download.html - try out creating the schema there and try out all your queries before you get in to implementing it in android

SQL Server : create error how to write database name with the table name

CREATE DATABASE agom COLLATE Arabic_CI_AS
CREATE TABLE Branches
(
ID INT PRIMARY KEY NOT NULL IDENTITY,
NAME VARCHAR(255) NOT NULL
)
CREATE TABLE agom.Brands
(
ID INT PRIMARY KEY NOT NULL IDENTITY,
NAME VARCHAR(255) NOT NULL
)
CREATE TABLE agom.Work_Order
(
NUMBER INT NOT NULL,
BRANCHID INT NOT NULL,
BRANDID INT NOT NULL,
WDATE DATE NOT NULL,
REPAIRSTATUS VARCHAR(255),
REPAIRCOST VARCHAR(255),
REMARK VARCHAR(500),
PRIMARY KEY (NUMBER,BRANCHID,BRANDID)
)
CREATE TABLE agom.Profiles
(
ID INT PRIMARY KEY NOT NULL IDENTITY,
USERNAME VARCHAR(25) NOT NULL,
PASS VARCHAR(25) NOT NULL
)
ALTER TABLE agom.Work_Order
ADD CONSTRAINT branchfk
FOREIGN KEY (BRANCHID) REFERENCES Branches(ID)
ALTER TABLE agom.Work_Order
ADD CONSTRAINT brandfk
FOREIGN KEY (BRANDID) REFERENCES Brands(ID)
I get an error that cannot create table
I try to write database name with the table name db.tablename but it's not working
I need to create the database then create the tables and its constraints but I don't know where is the error.I am a sql noob
It's never Database.Table.
It's either Table, or Schema.Table, or Database.Schema.Table, or Server.Database.Schema.Table.
You probably just want to insert USE agom right after create database, and then only refer to tables by name.
Alternatively, you can refer to your tables as agom.dbo.Work_Order, dbo being the default database schema.
See Using Identifiers As Object Names for general reference.

SQL Unknown number of attributes

I have a one-to-many relationship between two classes for this situation. I have a swimming competition and that competition can have x swimmers.
How can I create an SQL table for this, I know I will have to use the Primary Key of Swimmers as a foreign key in the Swimming competition but I have no idea how to represent the correct number of attributes since it's unknown.
This is called a m:n relationship and usually solved with a mapping table.
Something like this:
create table swimmer
(
id integer not null primary key,
lastname varchar(100) not null,
firstname varchar(100)
)
create table competition
(
id integer not null primary key,
name varchar(50) not null,
comp_date date not null
)
create table participant
(
swimmer_id integer not null,
competition_id integer not null,
rank_in_competetion integer,
primary key (swimmer_id, competition_id),
constraint fk_participant_swimmer (swimmer_id) references swimmer(id),
constraint fk_participant_competition (competition_id) references competition(id)
)