Error in Join query in mysql - mysql

I have 4 tables tbl_user, tbl_usedetails,tbl_aboutme,tbl_looking contains details of different users. These four tables have a field named userid in common. I want to join these four tables with the userid.
Consider my user id as 3
tbl_user is the root table where the userid is always present. But in other tables, userid may or may not be present.
I tried the following query but it fetch the userdetails with userid not equal to 3
select *
from `tbl_user` as u,
`tbl_usedetails` as ud,
`tbl_aboutme` as a,
`tbl_looking` as l
where (u.`userid`=ud.`userid` OR a.`userid`=l.`userid` )
AND (u.`userid`='3')
tbl_usedetails didnt have the row with userid 3, but it contains another row with userid 13, When execute query it also joins the row with the userid 13.

The question is not 100% clear and unambiguous but I think you want to pick up values from other tables where present. If rows are not present for a user in three of the tables, you still want results from other tables. That's a LEFT JOIN, as follows:
SELECT *
FROM `tbl_user` AS u
LEFT JOIN `tbl_usedetails` AS ud ON u.userd = ud.userid
LEFT JOIN `tbl_aboutme` AS a ON u.userd = a.userid
LEFT JOIN `tbl_looking ` AS l ON u.userd = l.userid
WHERE u.`userid` = '3'

try outer join so that you get the data even though there is no data in secondary table.
select *
from `tbl_user` as u,
left outer join tbl_usedetails ud on u.userid=ud.userid
left outer join tbl_aboutme a on a.userid=u.userid
left outer join tbl_looking l on l.userid=u.userid
where
u.userid='3'

select * from `tbl_user` as u,`tbl_usedetails`
as ud,`tbl_aboutme` as a,`tbl_looking` as l where
(u.`userid`=ud.`userid` OR a.`userid`=l.`userid` )
AND (u.`userid`='3')
add condition to ud table

Related

SQL Left Join a Table on a Left Joined Table

Iam currently trying to left join a table on a left joined table as follows.
I have the tables:
accounts (id, vorname, nachname)
projektkurse (id, accounts_id, projektwochen_id)
projektkurs_einzel (id, projektkurse_id)
projektkurs_einzel_zeiten (id, date, shift, projektkurs_einzel_id)
Now I want to get every account and the amount times they have an entry inside of projektkurs_einzel_zeiten, which should also be unique. So having the same date and shift multiple times does not count as multiple entries. The result should also be limited by the column projektwochen_id from the table projektkurse. This column should match a certain value for example 8.
Some Accounts don't have any entries in projektkurse, projektkurs_einzel and projektkurs_einzel_zeiten, this is why my first thought was using LEFT JOIN like this:
SELECT accounts.id, accounts.vorname, accounts.nachname, COUNT(DISTINCT projektkurs_einzel_zeiten.date, projektkurs_einzel_zeiten.shift) AS T
FROM accounts
LEFT JOIN projektkurse on accounts.id = projektkurse.creator_id
LEFT JOIN projektkurs_einzel on projektkurse.id = projektkurs_einzel.projektkurs_id
LEFT JOIN projektkurs_einzel_zeiten ON projektkurs_einzel.id = projektkurs_einzel_zeiten.projektkurs_einzel_id
WHERE projektkurse.projektwochen_id = 8
GROUP BY accounts.id
This query does not achieve exactly what I want. It only returns accounts that have atleast one entry in projektkurse even if they have none in projektkurs_einzel and projektkurs_einzel_zeiten. The Count is obviously 0 for them but the accounts that have no entries in projektkurse are being ignored completly.
How can I also show the accounts that don't have entries in any other table with the Count 0 aswell?
I would recommend writing the query like this:
SELECT a.id, a.vorname, a.nachname,
COUNT(DISTINCT pez.date, pez.shift) AS T
FROM accounts a LEFT JOIN
projektkurse
ON a.id = pk.creator_id AND
pk.projektwochen_id = 8 LEFT JOIN
projektkurs_einzel pe
ON pk.id = pe.projektkurs_id LEFT JOIN
projektkurs_einzel_zeiten pez
ON pe.id = pez.projektkurs_einzel_id
GROUP BY a.id, a.vorname, a.nachname;
Notes:
Your problem is fixed by moving the WHERE condition to the ON clause. Your WHERE turns the outer join into an inner join, because NULL values do not match.
Table aliases make the query easier to write and to read.
It is a best practice to include all unaggregated columns in the GROUP BY. However, assuming that id is unique, your formulation is okay (due to something called "functional dependencies").
You should not use eft join table's column ins where condition this work as inner join
You should move the where condition for a left joined table in the corresponding ON clause
SELECT accounts.id, accounts.vorname, accounts.nachname, COUNT(DISTINCT projektkurs_einzel_zeiten.date, projektkurs_einzel_zeiten.shift) AS T
FROM accounts
LEFT JOIN projektkurse on accounts.id = projektkurse.creator_id
AND projektkurse.projektwochen_id = 8
LEFT JOIN projektkurs_einzel on projektkurse.id = projektkurs_einzel.projektkurs_id
LEFT JOIN projektkurs_einzel_zeiten ON projektkurs_einzel.id = projektkurs_einzel_zeiten.projektkurs_einzel_id
GROUP BY accounts.id

How do you do multiple joins three joined tables to a fourth table in MYSQL

The database schema for this question is located here: db fiddle
I am trying to do the following:
Join table A (group table) to table J (grouprooms)
Join table B (room table) to table J (grouprooms)
Finally Join table C (users) table A - note table A already joined to J
I have written a query that accomplishes steps 1 and 2 but can't figure out how to join the users table to the group table.
Here's the query I have so far:
select rooms.room_name, groups.group_name, groups.group_ID
from grouprooms
left join rooms on grouprooms.room_ID = rooms.room_ID
left join groups on grouprooms.group_ID = groups.group_ID;
You could just add another LEFT JOIN to your query to link in table users :
select rooms.room_name, groups.group_name, users.name
from grouprooms
left join rooms on grouprooms.room_ID = rooms.room_ID
left join groups on grouprooms.group_ID = groups.group_ID
left join users on grouprooms.group_id = users.group_id
See your updated db fiddle :
grouproom 6 is showing no user because there is no user in group 3 (OPERATIONS)
grouproom 7 is not linked to a group, hence it has no group name and no user

MYSQL query with joins and WHERE condition not returning any rows

I'm trying to run a SQL query that joins with 2 other tables.
But, I need to still be able to use a WHERE condition in this query that uses the id of the main table. In this case the main table is timesheets.
I've tried the following but no rows were returned at all:
SELECT * FROM `timesheets` t
INNER JOIN `users` u ON `t`.`teacher_id` = `u`.`id`
INNER JOIN `schools` s ON `t`.`school_id` = `s`.`id`
WHERE t.id = 46
In this example I'm trying to filter to the row with ID 46 which definitely does exist.
If I do a simple query of just the timesheets table with the same where condition of id = 46 it works and returns that specific row.
When using EXPLAIN I get this message in the 'extra' column:
Impossible WHERE noticed after reading const table
Any ideas what I'm doing wrong?
As you have used INNER JOIN , so it will return data only if tables users and schools primary key has been used in timesheet as a foreign key.
use left join
SELECT * FROM timesheets t
LEFT JOIN users u ON t.teacher_id = u.id
LEFT JOIN schools s ON t.school_id = s.id
WHERE t.id = 46

Find unique values that do not exist in multiple columns and tables

A misconfigured manual import imported our entire AD into our help desk user database, creating a bunch of extraneous/duplicate accounts. Of course, no backup to restore from.
To facilitate the cleanup, I want to run a query that will find users not currently linked to any current or archived tickets. I have three tables, USER, HD_TICKET, and HD_ARCHIVE_TICKET. I want to compare the ID field in USER to the OWNER_ID and SUBMITTER_ID fields in the other two tables, returning the only the values in USER.ID that do not exist in any of the other four columns.
How can this be accomplished?
Do a left join for each relationship where the right table id is null:
select user.*
from user
left join hd_ticket on user.id = hd_ticket.owner_id
left join hd_ticket as hd_ticket2 on user.id = hd_ticket2.submitter_id
left join hd_archive_ticket on user.id = hd_archive_ticket.owner_id
left join hd_archive_ticket as hd_archive_ticket2 on user.id = hd_archive_ticket2.submitter_id
where hd_ticket.owner_id is null
and hd_ticket2.submitter_id is null
and hd_archive_ticket.owner_id is null
and hd_archive_ticket2.submitter_id is null
How about something like:
SELECT id
FROM user
WHERE id NOT IN
(
SELECT owner_id
FROM hd_ticket
UNION ALL
SELECT submitter_id
FROM hd_ticket
UNION ALL
SELECT owner_id
FROM hd_archive_ticket
UNION ALL
SELECT submitter_id
FROM hd_archive_ticket
)
If I understood you situation I would do this:
SELECT a.id FROM user a, hd_ticket b, hd_archive_ticket c WHERE a.id != b.id AND a.id != c.id
You would want to try something like below. Inner query where I am doing Inner join with other 2 tables, will return only those user id which exist in all 3 tables. Then in your outer query I am just filtering out those ID's returned by inner query; since your goal is to get only those USER ID which is not present in other tables.
select ID
FROM USER
WHERE ID NOT IN
(
select u.ID
from user u
inner join HD_TICKET h on u.ID = h.OWNER_ID
inner join HD_ARCHIVE_TICKET ha on u.ID = ha.SUBMITTER_ID
)

mySQL join 3 columns from each of two tables

I am trying to join data from two tables where the userid from table 1 is in table 2.
I have tried multiple variations with no luck and read a dozen posts here on SO on this topic.
The data in table one has an id, username, rolerequest, and appuserid. I am selecting the last three items and trying to join 3 items from table 2 when the appserid from table 1 is equal to the userid from table 2.
here is my latest attempt;
SELECT username, rolerequest, appuserid
FROM userrolespending
LEFT JOIN my_aspnet_membership.email,my_aspnet_membership.creationdate,my_aspnet_membership.lastlogindate
where my_aspnet_membership.userid = userrolespending.appuserid;
In this case, you don't need to use LEFT JOIN because you only want to return userid that are present from both tables. INNER JOIN returns records that the ID or the linking columns are both present on all tables.
SELECT a.*, b.* -- <== select the columns you want to appear
FROM userrolespending a
INNER JOIN my_aspnet_membership b
ON a.appserid = b.userID
or to be exact,
SELECT a.username, a.rolerequest, a.appuserid,
b.email,b.creationdate, b.lastlogindate
FROM userrolespending a
INNER JOIN my_aspnet_membership b
ON a.appserid = b.userID
i think this is what you need :
SELECT username, rolerequest, appuserid
FROM userrolespending
LEFT JOIN my_aspnet_membership
on my_aspnet_membership.userid = userrolespending.appuserid;