Joining two tables twice in MySQL. Possible or Not??? - mysql

The table structures for the tables users,messages are like bellow,
Users - ID, Name
Messages - ID, Sender, Receiver, Message
I want to join two tables twice like joining the messages.sender with users.id and messages.receiver with users.id.
Is it possible to get the result with sender's id, sender's name, receiver's id, receiver's name, message...(etc) in a single query???...

Yes, you can join the tables as many times as needed.
SELECT
sender.ID AS `sender_id`,
sender.Name AS `sender_name`,
receiver.ID AS `receiver_id`,
receiver.Name AS `receiver_name`,
Messages.Message
FROM
Messages
INNER JOIN
Users AS sender
ON
sender.ID = Messages.Sender
INNER JOIN
Users AS receiver
ON
receiver.ID = Messages.Receiver

Yes you can do it by naming an inner join:
select id, s.Name, r.Name from Messages
inner join users as s on (message.sender = s.id)
inner join users as r on (merssage.receiver = r.id)

Related

SQL query to combine columns from 3 different tables?

So basically I have 3 differnet tables named member, phone_message and pc_message each with the following columns:
member = (id, cell_num)
phone_message = (phone_num, content, received_at)
pc_message = (member_id, content, sent_at)
What i'm trying to do here is to list all the messages including both phone and pc that are received or sent for each member. To do that i need to combine those tables into one using SQL queries like JOIN and UNION. Any help?
You can try below query, I have used inner join so that messages only sent by matching members will be diplayed.
In addition to that, I have added one extra column as device which will identify whether the message is sent on phone or pc.
select m.id as memberId, m.cell_num as phoneNumber, p.content as Message, p.received_at as recieveDate,'Phone' as device from member m
inner join phone_message p on m.cell_num = p.phone_num
union
select m.id as memberId, m.cell_num as phoneNumber, pc.content as Message, pc.sent_at as recieveDate,'PC' as device from member m
inner join pc_message pc on m.id = pc.member_id
Try this;
select m.id as memberId, m.cell_num as phoneNumber, p.content, p.received_at as recieveDate from member m
inner join phone_message p on m.cell_num = p.phone_num
union
select m.id as memberId, m.cell_num as phoneNumber, pc.content, pc.sent_at as recieveDate from member m
inner join pc_message pc on m.id = pc.member_id

Inner Join SQL table multiple times for the same table

I have two tables (msg and users). I am trying to join these two tables together and print out the first and last name of the sender and the recipient as well as all of the message content if the message is marked as flag. I keep getting errors though, and have not found a good way to do this yet.
Pictures of tables for reference: https://imgur.com/a/wYuptfR
SQL query I'm using right now:
SELECT msg.*, users.uuid AS users.ruuid, users.uuid AS users.suuid, users.firstName, users.lastName
FROM msg
INNER JOIN users ON users.ruuid = msg.recipient
AND INNER JOIN users ON users.suuid = msg.sender
WHERE msg.flag = 0
You can query the same table several times if you use different aliases. Also, note you shouldn't have an and between the two join clauses:
SELECT msg.*,
r.uuid AS ruuid, r.firstName AS rfirstname, r.lastName AS rlastname,
s.uuid AS suuid, s.firstName AS sfirstname, s.lastName AS slastname
FROM msg
INNER JOIN users r ON r.uuid = msg.recipient
INNER JOIN users s ON s.uuid = msg.sender
WHERE msg.flag = 0
Try This
SELECT msg.*, u.uuid , u.firstName, u.lastName, s.uuid , s.firstName, s.lastName
FROM msg
INNER JOIN users u ON u.uuid = msg.recipient
INNER JOIN users s ON s.uuid = msg.sender
WHERE msg.flag = 0

sql complex join

I have the three related tables that i would like to retrieve data from using joins: tbl_accounts containing the account details of users, tbl_users containing the personal details of users and tbl_t_records that contains the transaction details of all users.
In the tbl_accounts i have a foreign key column holder that helps link it to the tbl_users and in the tbl_t_records I have the foreign key columns oaccount and daccount each linking to tbl_accounts but the oaccount stores the details for the account from which the transaction originated while daccount stores the details for the account to which the transaction is destined
here is the snippet fro the tbl_accounts table
Here is the one for tbl_users
This is the one for tbl_t_records
I would like to create a query that return the name of a sender, receiver and the transaction id using joins.
so far this is what I have tried
SELECT tbl_t_records.id transaction_id,
CONCAT(tbl_users.lname,tbl_users.othername)as sender,
amount,
CONCAT(tbl_users.lname,tbl_users.othername)as receiver
FROM tbl_t_records
INNER JOIN tbl_accounts on oaccount = tbl_accounts.id
INNER JOIN tbl_users ON tbl_accounts.holder = tbl_users.id
this does not give me the details of the destination account rather it only presents the data fro the sender that it uses as the same for the reciever as shown here
What am I doing wrong?
You can join several times, as follows:
select
r.id transaction_id,
concat(u1.lname, u1.othername) sender,
concat(u2.lname, u2.othername) receiver,
r.amount
from tbl_t_records r
inner join tbl_accounts a1 on a1.id = r.oaccount
inner join tbl_users u1 on u1.id = a1.holder
inner join tbl_accounts a2 on a2.id = r.daccount
inner join tbl_users u2 on u2.id = a2.holder
This query starts from the transaction table and then follows the relationships related to oaccount through tbl_accounts (aliased a1) to tbl_users (aliased u1). Another series of joins starts from daccount and brings the related user data (aliases a2/u2).
You just need multiple joins -- a separate set for each name:
SELECT r.*,
CONCAT(uo.lname, uo.othername) as sender,
CONCAT(ud.lname, ud.othername) as receiver
FROM tbl_t_records r JOIN
tbl_accounts ao
ON r.oaccount = ao.id JOIN
tbl_users uo
ON ao.holder = uo.id JOIN
tbl_accounts ad
ON r.daccount = ad.id JOIN
tbl_users ud
ON ad.holder = ud.id;

MYSQL Many-to-many select (chats, latest message, username) in one statement

I'm trying to select a list of the user's chats in one statement, together with each chats latest message and the massage's sender's name.
The abstract problem is:
Ever chat can have multiple participating users.
A message is sent to a "chat", not a specific user.
These are the tables I came up with
TABLE users (id, username)
TABLE chats (id)
TABLE messages (id, message, chat_id, user_id)
And lastly a many-to-many relation table between chats and participants
TABLE chats_users (chat_id,user_id)
I want to list all the chats a certain user participates in, together with the latest message and it's sender's username.
How would I go about that in one statement?
Im running Mysql 5.0.9 and php 7.
This query:
select max(m.id) id
from chats_users cu
inner join users u on cu.user_id = u.id
inner join messages m on m.chat_id = cu.chat_id
where cu.chat_id in (select chat_id from chats_users where user_id = ?)
group by cu.chat_id
returns the last messages of all the chats that a certain user participates.
Use it in this query:
select m.chat_id, m.message, u.username
from messages m inner join users u
on u.id = m.user_id
where m.id in (
select max(m.id) id
from chats_users cu
inner join users u on cu.user_id = u.id
inner join messages m on m.chat_id = cu.chat_id
where cu.chat_id in (select chat_id from chats_users where user_id = ?)
group by cu.chat_id
)
to get the details of these messages.

Reference outside inner join query

I have the following query for a basic messaging system. It shows the messages that you've sent. However, it is showing the first_name and second_name for the account referenced by sender_id. Instead I want it to output the name columns referenced by receiver_id
ie) SELECT first_name, second_name WHERE accounts.account_id = messages.receiver_id
Do I need to write a seperate query for this or can I make this one output it in a single query? I've been thinking quite hard about this problem!
SELECT first_name, second_name, message_id, title, body, seen, urgent, type, messages.timestamp
FROM messages
INNER JOIN accounts
ON messages.sender_id=accounts.account_id
WHERE sender_id = ?
You can do this with two joins:
SELECT s.first_name as sender_first, s.second_name as sender_last,
r.first_name as rec_first, r.second_name as rec_last,
m.message_id, m.title, m.body, m.seen, m.urgent, m.type, m.timestamp
FROM messages m inner join
accounts s
ON m.sender_id = s.account_id inner join
accounts r
on m.receiver_id = r.account_id
WHERE m.sender_id = ?