I'm creating a table that shows all the registered users to which the current user has not yet subscribed to. But once he has subscribed someone, I need to filter that list to exclude those.
Let's say the theres a table called subscribed which lists the User and to whom he is subscribed to.
|UserId||SubscriberID|
Its easy to make it into multiple queries, but I've been unsuccessfully trying to make it into one query, to save an extra loop of MySQL calls.
Here's What I have so far:
SELECT u.UserID, FullName, UserName from users u
LEFT JOIN subscribed t ON
((u.UserName LIKE '%$search%' OR
u.Email LIKE '%$search%') AND
({$_SESSION['ID']} = t.UserID
AND t.FollowerID != u.UserID)
)
I know the last part of the query is wrong, since I only compare if the UserID and the FollowerID don't match for one particular row, not the entire table.
To find a list of results in table A that are not in table B, you have two options. Either use the NOT IN syntax, or LEFT JOIN and look where the PK field in the B table is NULL.
NOT IN example:
SELECT a.id FROM a WHERE a.id NOT IN (SELECT b.id FROM b)
LEFT JOIN example:
SELECT a.id
FROM a
LEFT JOIN b ON (a.id = b.id)
WHERE (b.id IS NULL)
Related
I cannot correctly make the link between my 2 tables, I have a table that represents my users and another with appointments but I would like to make the link between the 2 to be able to display the appointments users.
My reservation table looks like this :
[tablebooking]
My user table looks like this :
[tableusers]
What I Tried :
[test]
If your appointment functionality is one to one relation like one appointment will have only one member then you can use below query(query followed fields from your screenshots)
SELECT
M.*, B.*
FROM
members AS M
INNER JOIN bookings AS B ON B.userid = M.userid
OR
if you want to have more than one members in one appointment, you need to have tables as below
[YOUR_USERS_TABLE_NAME] => Users list
[YOUR_BOOKINGS_TABLE_NAME] => List of appointments created
[YOUR_BOOKING_MEMBERS_TABLE_NAME] => It should have list of appointment id and members id(one(appointment) to many(users) relation)
and query will be like below
SELECT
B.*, U.*
FROM
[YOUR_BOOKINGS_TABLE_NAME] AS B
INNER JOIN [YOUR_BOOKING_MEMBERS_TABLE_NAME] AS M ON M.bookingid = B.id
INNER JOIN [YOUR_USERS_TABLE_NAME] AS U on M.userid = U.id
GROUP BY B.id, U.id
Hope my answer will help you.
Please add user_id in your bookings table and then run below query in your phpmyadmin.
select * from bookings as b INNER JOIN users as u ON u.id = b.user_id
Thanks.
You probably must use an external table to connect this tables.
EX:
foo{
id: primary,
idTableUser: external key,
idTableBooking: external key
}
my query looks like that:
SELECT
count(users.id)
FROM users
LEFT JOIN mail_sender_jobs_actions ON mail_sender_jobs_actions.userID = users.id
LEFT JOIN table2 ON table2.userID = users.id
LEFT JOIN table3 ON table3.userID = users.id
WHERE {$flexibleWhereClause}
Now, the mail_sender_jobs_actions table CAN (doesnt need to return anything) return multiple entries. I dont want to group the results but still limit the returns of mail_sender_jobs_actions to 1 so I dont get duplicates... Otherwise the count wouldnt work properly.
Scraped the whole web and found nothing working for me as I want to keep the where clause flexible. Any solution?
EDIT
so to explain the situation. We have a table with users (users). We have a table with actions (mail_seder_jobs_actions). We have other tables related to that query which are not relevant (table1, table2, table3)
If a user does an action, an entry is being created in the actions table.
The where clause is flexible, meaning it is possible that somebody wants to only show users with a specific action.
It is also possible that an action is not relevant to the user, so this entry gets ignored.
With where criteria you have there is no point using left join, since the where criteria applies to the table on the right hand side, effectively turning the left join into an inner join.
Apparently yo do not use any columns from the right hand side table, so instead of using joins, I would use an exists subquery.
SELECT
1 as count,
users.email
FROM users
WHERE EXISTS (SELECT 1
FROM mail_sender_jobs_actions
WHERE mail_sender_jobs_actions.userID = users.id
AND mail_sender_jobs_actions.type = '1'
AND mail_sender_jobs_actions.jobID = '106'
AND {$flexibleWhereClause})
However, there is little point in having the count() because it will always return 1. If you want to count how many records each user has in the mail_sender_jobs_actions table, then you have to use left join, group by, and move the where criteria into the join condition:
SELECT
count(mail_sender_jobs_actions.userID),
users.email
FROM users
LEFT JOIN mail_sender_jobs_actions ON mail_sender_jobs_actions.userID = users.id
AND mail_sender_jobs_actions.type = '1'
AND mail_sender_jobs_actions.jobID = '106'
AND {$flexibleWhereClause}
GROUP BY users.email
I need a little help setting up my query. I'm simply trying to access the amount of people who are in the same 'clan' by joining these two tables together, clan, users. Each users has a column 'clan' which is the same as the table clan's column 'roomOwner' and then I'm trying to get the table clan's information along with the amount of members so it would be like: room, roomOwner, members
So basically all I have is this:
SELECT c.*, count(u.clan) AS members FROM clans c inner join users u WHERE c.roomOwner = u.clan ORDER BY members;
It only shows one clan though. Any help please?
Your query has no GROUP BY clause. and I think it's only returning single record right? LEFT JOIN is needed here since there are possibilities that a clan has no member.
SELECT b.roomOwner, COUNT(a.clan) memberCount
FROM clan b
LEFT JOIN users a
ON a.clan = b.roomOwner
GROUP BY b.roomOwner
ORDER BY memberCount
You forgot GROUP BY. Do you have some "id" column in "clans" table? Group by that "id"
SELECT c.*, count(u.clan) AS members
FROM clans c
inner join users u ON c.roomOwner = u.clan
GROUP BY clans.id
And you need LEFT JOIN there instead of INNER JOIN if you want to see info about all clans, even having 0 users.
Perhaps this will help:
select c.*, count(links.id) as members
from clans c
left join users u on c.roomOwner = u,clan
group by u.clan
order by members
Creating a forum-type site and I have 3 tables, one for storing user information (users), one for the original post (threads), and one for an upvote system like SO has (votes).
The votes table has 3 columns, id, userid, and threadid. When a user upvotes a thread, a record is inserted into the votes table. When I query for the thread I want to know if the user has upvoted for it, essentially if a record exists in the votes table with the correct userid and threadid. I can do this in two queries, but I think there has to be a way to get everything in one.
My query currently:
"SELECT t.id, t.title, t.content u.id AS uid, u.username
FROM threads t, users u
WHERE t.id = '".$userid."'
AND t.author = '".$userid."'"
In case you need a better idea, the following will query the desired results ONLY if the user has upvoted. I need the query to still return if the record in the votes table doesn't exist (possibly return a vote value as null?).
"SELECT t.id, t.title, t.content u.id
AS uid, u.username v.id
FROM threads t, users u, votes v
WHERE t.id = '".$threadid."'
AND t.author = '".$userid."'
AND v.threadid = t.id
AND v.userid = '".$userid."'"
Also I taught myself (and am still learning) mysql and database design so if there's a better method/approach such as joining tables, please let me know. Thanks.
Your second query is doing inner joins, which would only return records that appear on both sides of the join. You'd want to do a left/right outer join on the votes table instead, so that you'd still get user+thread records even if there's no matching vote record.
SELECT t.id, t.title, t.content, u.id, u.username, v.id
FROM threads AS t
INNER JOIN users AS u ON t.userid = u.id
LEFT JOIN votes AS v ON (v.userid = u.id and t.id = v.threadid)
WHERE (u.id = $userid) AND (t.id = $threadid)
just guessing at this, but should be enough to get you started.
This is related to my other question:
Managing Foreign Keys
I am trying to join the table of matches and non-matches.
So I have a list of interests, a list of users, and a list of user interests.
I want the query to return all interests, whether the user has the interest or not (should be null in that case), only where the user = x. Every time I get the query working its only matching interests that the user specifically has, instead of all interests whether they have it or not.
You should rather use LEFT JOINS
Something like
SELECT *
FROM interests i LEFT JOIN
userinterests ui ON i.interestID = ui.interestID LEFT JOIN
users u ON ui.userID = u.uiserID
WHERE userID = ?
where is the user id you are looking for.
SELECT *
FROM interests i
LEFT JOIN userinterests ui ON i.interestID = ui.interestID
LEFT JOIN users u ON ui.userID = u.uiserID
and u.userID = ?
If you put a where condition on a table that should have no records inteh main tbale, you convert the join from a left join to an inner join. The only time you should ever have a condition inthe where clasue for something one the right side of a left join is when you are searching for records that don't match (where u.userid is null, for instance)
Of course you should define the fields to be selected and never use select * in production code especially not when you have a join as it sends repeated information across the network (the data inteh join feilds is repeated) and is a waste of resources and poor prgramming practice for multiple reasons.