简体   繁体   中英

SQL Query for one to many relationship

Here's my database:

Employee Table:
employee_id int(10) NOT NULL,
firstname varchar(50) NOT NULL,
lastname varchar(50) NOT NULL,
username varchar(15) NOT NULL,
password varchar(25) NOT NULL DEFAULT 'password',
contact_number varchar(13) NOT NULL,
email_address varchar(50) NOT NULL,
position varchar(50) NOT NULL,
teamleader_id int(11) DEFAULT NULL

Service Table:
service_id int(10) NOT NULL,
ticket_id int(10) NOT NULL,
employee_id int(10) NOT NULL,
status varchar(15) NOT NULL,
start_time datetime NOT NULL,
time_in datetime DEFAULT NULL,
time_out datetime DEFAULT NULL,
service_notes varchar(500) DEFAULT NULL

Query:

SELECT * FROM employee AS e 
LEFT JOIN service AS s ON e.employee_id = s.employee_id
WHERE (s.status IS NULL OR s.status = 'Completed') 
AND e.teamleader_id = ?

EDITED:

I want to select all employees except the ones with service.status = 'Ongoing'

Assuming you just want a list of employees that have completed a service (excluding those who have not and only showing one service per employee)

SELECT employee.*, COUNT(service.status)
FROM employee, service
WHERE service.employee_id = employee.employee_id
AND ( service.status IS NULL OR service.status = 'Completed' )
AND teamleader_id = 1
GROUP BY employee.employee_id;

Or If you do want to list the employees who have not completed any service

SELECT employee.*, COUNT(service.status)
FROM employee LEFT JOIN service ON service.employee_id = employee.employee_id
WHERE ( service.status IS NULL OR service.status = 'Completed' )
AND teamleader_id = 1
GROUP BY employee.employee_id;

or if you want all except where service.status = 'Ongoing'

SELECT employee.*, COUNT(service.status)
FROM employee LEFT JOIN service ON service.employee_id = employee.employee_id
WHERE employee.employee_id NOT IN ( SELECT DISTINCT service.employee_id FROM service WHERE service.status = 'Ongoing')
AND teamleader_id = 1
GROUP BY employee.employee_id;

Tested in SQL Fiddle

CREATE TABLE employee ( employee_id INT(9) PRIMARY KEY, teamleader_id INT NOT NULL, name VARCHAR(99) NOT NULL );
CREATE TABLE service ( id INT(9) PRIMARY KEY, employee_id INT(9) NOT NULL, status VARCHAR(99) NOT NULL );
INSERT INTO employee VALUES (1, 1, 'Bob');
INSERT INTO employee VALUES (2, 1, 'Alice');
INSERT INTO service VALUES (1, 2, 'Complete');
INSERT INTO service VALUES (2, 2, 'WIP');
INSERT INTO service VALUES (3, 2, 'Ongoing');

You just have to add DISTINCT to your query :

SELECT DISTINCT e.* FROM employee e LEFT JOIN service s ON e.employee_id = s.employee_id
WHERE(s.status is null OR s.status = 'Completed') and teamleader_id = 3

it filters duplicated

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM