Сложный запрос MySQL

Я создаю сайт в WordPress, который содержит информацию о телевизионных программах. Я использую настраиваемые поля для выбора каждого сообщения.

Таблица выглядит примерно так:

+----+---------+----------+------------+ | id | post_id | meta_key | meta_value | +----+---------+----------+------------+ | 1 | 1 | name | Smallville | | 2 | 1 | season | 1 | | 3 | 1 | episode | 1 | | 4 | 2 | name | Smallville | | 5 | 2 | season | 1 | | 6 | 2 | episode | 2 | +----+---------+----------+------------+ 

В основном, что мне нужно сделать, это выбрать все телевизионные шоу с именем «Smallville» и отсортировать их по сезонам, затем по эпизодам. Я думал, что это будет довольно просто, но все, что я пробовал, ничего не возвращает.

Не могли бы вы объяснить, как я могу это сделать?

Вы можете сделать что-то вроде этого:

 SELECT t1.post_id, t1.meta_value AS name, t2.meta_value AS season, t3.meta_value AS episode FROM ( SELECT * FROM the_table WHERE meta_key = 'name' ) t1 INNER JOIN ( SELECT * FROM the_table WHERE meta_key = 'season' ) t2 ON t1.post_id = t2.post_id INNER JOIN ( SELECT * FROM the_table WHERE meta_key = 'episode' ) t3 ON t1.post_id = t3.post_id 

Это даст вам результат:

 | post_id | name | season | episode | ------------------------------------------- | 1 | Smallville | 1 | 1 | | 2 | Smallville | 1 | 2 | 

В этой форме это намного проще для любых операций.

Вам нужно добавить:

 WHERE name = 'Smallville' ORDER BY season, episode 

Объедините строки, используя самостоятельное объединение, и вы хорошо пойдете:

 SELECT * FROM yourtable name INNER JOIN yourtable season on season.post_id = name.post_id and season.meta_key = 'season' INNER JOIN yourtable episode on episode.post_id = name.post_id and episode.meta_key = 'episode' WHERE name.meta_key = 'name' and name.meta_value = 'Smallville' ORDER BY season.meta_value, episode.meta_value 

Более общий случай: сортировка преобразования из вашего формата в более обычный формат реляционных БД:

 SELECT (SELECT meta_value FROM data t1 WHERE t1.post_id = t0.post_id AND meta_key = "season") AS season, (SELECT meta_value FROM data t1 WHERE t1.post_id = t0.post_id AND meta_key = "episode") AS episode FROM data t0 WHERE meta_key = "name" AND meta_value = "Smallville" 

Для фактической сортировки вы не можете повторно использовать значения сезона / эпизода (они еще не назначены при сортировке), поэтому вам нужно скопировать / вставить подзапрос в предложение ORDER BY:

 ORDER BY (SELECT ... "season") ASC, (SELECT ... "episode") ASC, 

Нет необходимости делать прямой SQL. У вас есть доступ к SQL-запросу через объект WP_Query. Проверьте фильтры, окружающие предложение where в объекте WP_Query (есть более чем один способ получить его) и просто измените части WP_Query по умолчанию, прежде чем они будут объединены вместе.

Начните с создания объекта WP_Query, который получает все сообщения по значению postmeta key и postmeta, а затем немного привязывается к предложению where, чтобы выполнить некоторые дополнительные условия.

Есть еще один фильтр, который позволяет вам получить раздел упорядочения SQL-запроса, чтобы вы могли его изменить.

Там нет оснований для того, чтобы вручную писать SQL здесь, просто измените то, что уже было создано для вас.

идея состоит в том, чтобы присоединиться к таблице к себе 3 раза, где для каждого из них берут строки для заданного мета-ключа:

 SELECT t1.meta_value name, t2.meta_value season, t3.meta_value episode FROM table t1 JOIN table t2 on t1.post_id = t2.post_id and t2.meta_key = 'season' JOIN table t3 on t1.post_id = t3.post_id and t3.meta_key = 'episode' WHERE t1.meta_key = 'name' AND t1.meta_value = 'Smallville' ORDER BY t2.meta_value, t3.meta_value