Mysql
 sql >> Base de Dados >  >> RDS >> Mysql

Obtenha postagens do WP com base em vários pares de meta-chave/valor usando IN


Você precisa se juntar ao post_meta mesa duas vezes. Aqui está alguma teoria de banco de dados.

Quando você junta tabelas, em teoria, uma tabela temporária contém todos os itens da primeira tabela combinados com todos os itens da segunda tabela é criada e filtrada. Portanto, se, por exemplo, você tiver apenas 1 meta item por postagem e tiver 3 postagens, terá
+-------+----------+
|post_id|post_title|
+-------+----------+
|   1   | 'Post 1' |
|   2   | 'Post 2' |
|   3   | 'Post 3' |
+-------+----------+

e
+-------+----------+----------+------------+
|meta_id| post_id  | meta_key | meta_value |
+-------+----------+----------+------------+
|   10  | 1        |  k1      | v1         |
|   11  | 2        |  k1      | v2         |
|   12  | 3        |  k1      | v3         |
+-------+----------+----------+------------+

E a tabela unida temporária "teórica" ​​é:
+---------+------------+----------+----------+-----------+-------------+
|p.post_id|p.post_title|pm.meta_id|pm.post_id|pm.meta_key|pm.meta_value|
+---------+------------+----------+----------+-----------+-------------+
|   1     | 'Post 1'   |   10     | 1        |  k1       | v1          |
|   1     | 'Post 1'   |   11     | 2        |  k1       | v2          |
|   1     | 'Post 1'   |   12     | 3        |  k1       | v3          |
|   2     | 'Post 2'   |   10     | 1        |  k1       | v1          |
|   2     | 'Post 2'   |   11     | 2        |  k1       | v2          |
|   2     | 'Post 2'   |   12     | 3        |  k1       | v3          |
|   3     | 'Post 3'   |   10     | 1        |  k1       | v1          |
|   3     | 'Post 3'   |   11     | 2        |  k1       | v2          |
|   3     | 'Post 3'   |   12     | 3        |  k1       | v3          |
+---------+------------+----------+----------+-----------+-------------+

Você então diz:WHERE p.id =pm.post_id

e isso filtra a tabela temporária para ser:
+---------+------------+----------+----------+-----------+-------------+
|p.post_id|p.post_title|pm.meta_id|pm.post_id|pm.meta_key|pm.meta_value|
+---------+------------+----------+----------+-----------+-------------+
|   1     | 'Post 1'   |   10     | 1        |  k1       | v1          |
|   2     | 'Post 2'   |   11     | 2        |  k1       | v2          |
|   3     | 'Post 3'   |   12     | 3        |  k1       | v3          |
+---------+------------+----------+----------+-----------+-------------+

Então você só tem uma linha para cada post + meta valor. Sua consulta está solicitando linhas que tenham meta_key = category e meta_key =book_genre` que não existem.

Então você precisa de uma tabela que junte o postmeta mesa em DUAS VEZES.

Você pode fazer isso criando um alias na tabela ao juntá-las. Perdoe-me por simplificar:
SELECT wp_posts.*, pm1.*, pm2.*
FROM
  wp_posts
  wp_postmeta as pm1
  wp_postmeta as pm2
WHERE pm1.post_id = wp_posts.ID
  AND pm2.post_id = wp_posts.ID
  AND ...etc

Aqui você tem duas cópias unidas da tabela postmeta com alias de pm1 e pm2 (como ambos não podem ser chamados de wp_postmeta na consulta.

Você pode então pedir:
AND pm1.meta_key = 'category'
AND pm1.meta_value = X
AND pm2.meta_key = 'book_genre'
AND pm2.meta_key IN (123,456)

Espero que você possa costurar o resto disso.

Eu também acho que você pode fazer isso com WP_Query se quiser seguir esse caminho.