В настоящее время я пытаюсь написать запрос, который вернет всех пользователей, не занесенных в журнал для данной даты в нашей системе расписания. В настоящее время у нас есть 2 таблицы, расписания и пользователи. Я пытаюсь сделать запрос, который вернет список пользователей, которые не имеют записи в таблице расписаний для диапазона дат. В таблице расписаний в день есть только одна запись, это должно быть просто, но я не могу понять, как подойти к этому для жизни меня.
Любая помощь будет оценена:).
+-----------------------+------------------+------+-----+---------+----------------+ | Field | Type | Null | Key | Default | Extra | +-----------------------+------------------+------+-----+---------+----------------+ | timesheetID | int(11) unsigned | NO | PRI | NULL | auto_increment | | timesheetForUser | int(11) unsigned | NO | | | | | timesheetForDate | date | NO | | | | | timesheetForCheckIn | int(11) | YES | | NULL | | | timesheetNotes | text | YES | | NULL | | | timesheetIsFilled | tinyint(1) | NO | | | | | timesheetNoFillReason | int(11) unsigned | NO | | | | | timesheetCreatedOn | datetime | NO | | | | | timesheetCreatedBy | int(11) unsigned | NO | | | | | timesheetUpdatedOn | datetime | YES | | NULL | | | timesheetUpdatedBy | int(11) unsigned | YES | | NULL | | +-----------------------+------------------+------+-----+---------+----------------+
+--------------------------------+---------------+------+-----+---------+----------------+ | Field | Type | Null | Key | Default | Extra | +--------------------------------+---------------+------+-----+---------+----------------+ | userID | int(11) | NO | PRI | NULL | auto_increment | | userAccount | int(11) | YES | | NULL | | | userOrganization | int(11) | YES | | NULL | | | userIsEmployee | tinyint(4) | YES | | 0 | | | userEmployeeSince | date | YES | | NULL | | | userName | varchar(255) | YES | | NULL | | | userTitle | varchar(255) | YES | | NULL | | | userEmail | varchar(255) | YES | | NULL | | | userLogin | varchar(50) | YES | | NULL | | | userPassword | varchar(255) | YES | | NULL | | | userSendInvitation | tinyint(4) | YES | | NULL | | | userAddress1 | varchar(255) | YES | | NULL | | | userAddress2 | varchar(255) | YES | | NULL | | | userCity | varchar(255) | YES | | NULL | | | userCountry | char(2) | YES | | NULL | | | userState | varchar(6) | YES | | NULL | | | userStateOther | varchar(255) | YES | | NULL | | | userZip | varchar(20) | YES | | NULL | | | userPhone | varchar(50) | YES | | NULL | | | user_easypaycode | varchar(6) | YES | | NULL | | | userFax | varchar(50) | YES | | NULL | | | userCell | varchar(50) | YES | | NULL | | | userTimezone | int(11) | YES | | NULL | | | userNotes | text | YES | | NULL | | | userActive | tinyint(4) | NO | | 0 | | | userDisplayPictureType | tinyint(4) | YES | | NULL | | | userDisplayPicture | varchar(255) | YES | | NULL | | | userThumbnailPicture | varchar(255) | YES | | NULL | | | userCanWriteMessages | tinyint(4) | NO | | 0 | | | userCanWriteComments | tinyint(4) | NO | | 0 | | | userCanUploadFiles | tinyint(4) | NO | | 0 | | | userCanCreateEvents | tinyint(4) | NO | | 0 | | | userCanCreateTickets | tinyint(4) | NO | | 0 | | | userCanManageProjects | tinyint(4) | NO | | 0 | | | userCanManageUsers | tinyint(4) | NO | | 0 | | | userCanManageOrganizations | tinyint(4) | NO | | 0 | | | userCanManageUserGroups | tinyint(4) | NO | | 0 | | | userCanManageMessageCategories | tinyint(4) | NO | | 0 | | | userCanManageSetupOptions | tinyint(4) | NO | | 0 | | | userCanManageAllUsersItems | tinyint(4) | NO | | 0 | | | userCanEnterTimesheets | tinyint(4) | NO | | | | | userCanManageTimesheets | tinyint(4) | NO | | | | | userCanUseTimeclock | tinyint(4) | YES | | NULL | | | userCanOnlyUseTimeclock | tinyint(4) | YES | | NULL | | | userLastLogin | datetime | NO | | | | | userPWResetText | varchar(255) | YES | | NULL | | | userDeleted | tinyint(4) | NO | | 0 | | | userDeletedBy | int(11) | YES | | NULL | | | userDeletedOn | datetime | YES | | NULL | | | userMinHoursPerDay | decimal(10,1) | YES | | NULL | | +--------------------------------+---------------+------+-----+---------+----------------+
Кроме того, нет записи, созданной в расписаниях, если в течение дня нет времени.
SELECT * FROM Users U
WHERE U.UserNo NOT IN (
SELECT timesheetForUser FROM timesheets
WHERE timesheetForDate BETWEEN ??? AND ???
)
Первый запрос выбирает всех пользователей, у которых нет регистрации между @start и @end:
SELECT users.userName
FROM users
LEFT JOIN timesheets
ON timesheets.timesheetForUser = users.userID
AND timesheets.timesheetForDate BETWEEN @start AND @end
WHERE timesheets.timesheetForUser IS NULL
Этот запрос извлекает всех пользователей, у которых отсутствуют какие-либо дни и в какие дни они отсутствуют (как вы просили в комментарии к вашему вопросу):
SELECT dates.timesheetForDate, users.userName
FROM (SELECT DISTINCT timesheetForDate FROM timesheets) AS dates
CROSS JOIN users
LEFT JOIN timesheets
ON timesheets.timesheetForUser = users.userID
AND dates.timesheetForDate = timesheets.timesheetForDate
WHERE timesheets.timesheetForUser IS NULL
Испытательный стенд:
CREATE TABLE timesheets (timesheetForUser int, timesheetForDate datetime);
INSERT INTO timesheets (timesheetForUser, timesheetForDate) VALUES
(1, '2010-01-01'),
(2, '2010-01-01'),
(3, '2010-01-01'),
(1, '2010-01-02'),
(3, '2010-01-02'),
(2, '2010-01-03'),
(2, '2010-01-04'),
(3, '2010-01-04');
CREATE TABLE users (userId int, userName nvarchar(100));
INSERT INTO users (userId, userName) VALUES
(1, 'Foo'),
(2, 'Bar'),
(3, 'Baz');
Результат второго запроса с использованием тестового слоя:
'2010-01-02 00:00:00', 'Bar'
'2010-01-03 00:00:00', 'Foo'
'2010-01-03 00:00:00', 'Baz'
'2010-01-04 00:00:00', 'Foo'
Если вы хотите, вы также можете создать второй запрос в виде представления и запросить его так:
SELECT * FROM ViewMissingRegistrations
WHERE timesheetForDate BETWEEN @start AND @end
Вы можете попробовать
SELECT u.*
FROM Users u LEFT JOIN
timesheets t ON u.userid = t.userid
WHERE t.Date BETWEEN '01 Jan 2009' AND '31 Jan 2009'
AND t.userID IS NULL