Reputation: 20270
I have a job
table and a visit
table. A job can have multiple visits. I need to retrieve all jobs, which haven't been set as paid, with all visits tied to that job set as completed.
So basically I need to only retrieve a job if:
(paid = 'N')
(status = 2)
Obviously doing the following doesn't work as it will return any result where job.paid = 'N' and visit.status = '2'
:
SELECT *
FROM job INNER JOIN visit
ON job.id = visit.job_id
WHERE job.paid = 'N' AND
visit.status = 2;
I could retrieve the results, and run additional queries to check that all the visits for a job are complete, but I was wondering if it's possible to retrieve the data in a single query?
Upvotes: 3
Views: 143
Reputation: 1208
SELECT *
FROM job j
WHERE j.paid = 'N' AND
NOT EXISTS (SELECT 1 FROM visit WHERE job_id = j.id AND visit.status <> 2);
Upvotes: 1
Reputation: 263933
UPDATE 1
SELECT a.ID -- <<== add some columns here
FROM job a INNER JOIN visit b ON a.id = b.job_ID
WHERE a.paid = 'N'
GROUP BY a.ID
HAVING COUNT(DISTINCT b.Status) = 1 AND MAX(b.status) = 2
Upvotes: 1
Reputation: 6881
If you have the possibility of a Job that doesn't have any Visit records associated with it, and you'd want to still return that Job record if it has paid = 'N', then you'll want to LEFT JOIN.
SELECT *
FROM JOB j
LEFT JOIN VISIT v
ON j.id = v.job_id
WHERE j.paid = 'N'
AND j.id NOT IN (SELECT job_id FROM visit WHERE status != 2)
Upvotes: 1
Reputation: 58
SELECT * FROM job WHERE paid = 'N' AND id NOT IN (
SELECT job_id FROM visit WHERE status != 2)
Upvotes: 1