2015-02-24 7 views
0

Я делаю пользовательский белый список, где моя основная таблица book_list, содержащий id - первичный ключ и другие столбцы, которые неважны. Другая таблица - это белый список, который содержит внешний ключ из book_list и другой ключ, который является user_id.MySQL белый список запросов

book_list стол

-------------- 
| id   | 
--------------- 
| 10   | 
| 11   | 
| 12   | 
| 13   | 
--------------- 

Whitelist стол

--------------------------- 
| book_list_id | user_id | 
---------------------------- 
| 10    | 1  | 
| 10    | 2  | 
---------------------------- 

Итак, когда user_id 1 просматривает, он/она должна увидеть все книги (10, 11, 12, 13), но если пользователь с id 5 выглядит он должен видеть только book_list ids (11, 12, 13)

Мой запрос был примерно таким, но он работает, если доступен только один идентификатор на book_id.

SELECT * FROM book_list bl 
LEFT JOIN whitelist w ON bl.id = w.book_list_id AND w.user_id <> 1 
WHERE w.book_list_id IS NULL 

Примечание: у меня всегда есть user_id из сеанса, поэтому он жестко закодирован.

+0

Я думаю, вам понадобится какой-то подзапрос, чтобы проверить, существует ли 'user_id' для этого' W.book_list_id'. – ryanyuyu

ответ

1
SELECT * 
FROM book_list 
LEFT JOIN whitelist 
    ON (whitelist.book_list_id = book_list.id) 
WHERE (COALESCE(whitelist.user_id, 1) = 1) 

отредактирован, чтобы включать в себя Пояснение

условную выполняет две вещи сразу. Если в книге нет записей в whitelist, функция COALESCE вернет идентификатор пользователя. Если в книге есть записи в whitelist, тогда условие будет предотвращать любые совпадения, если идентификатор пользователя не прикреплен к этой книге.

+0

Спасибо! Довольно простой и мощный одновременно. –

+0

Это интересное решение. Но имейте в виду, что если это приведет к ошибке, если пользователь с идентификатором 1 существует. Вместо этого я использовал бы другое число вне диапазона возможных идентификаторов пользователя, таких как 0 или -1. – bluecollarcoder

+0

На самом деле, '1' будет параметром для запроса, и вы бы использовали любое' user_id', соответствующее запросу. –

1

Ваш желаемый запрос фактически состоит из двух разных наборов результатов: 1) книги, которые не имеют белого списка, и 2) книги с белым списком, но текущий пользователь имеет доступ. Чтобы получить правильный результат, вам нужно сломать эти две части вниз, а затем СОЕДИНЯТЬ их в конце.

SELECT distinct bl.id FROM book_list bl 
LEFT JOIN whitelist w1 ON bl.id = w1.book_list_id AND w.user_id <> 1 
INNER JOIN whitelist w2 ON bl.id = w2.book_list_id AND w.user_id = 1 
WHERE w1.book_list_id IS NULL 
UNION 
SELECT distinct bl.id FROM book_list bl 
LEFT JOIN whitelist w ON bl.id = w.book_list_id 
WHERE w.book_list_id IS NULL 

Первый запрос исключает все книги не белый список для пользователя 1 и включает в себя все книги в белый список для пользователя 1. Второй запрос возвращает все книги, которые не имеют белого списка.

Смежные вопросы