我最近为一位房地产经纪人的客户开发了一个网站。项目中包含一个名为listing
. 此帖子类型用于他们的所有列表,其他信息存储在postmeta
表通过使用Advanced Custom Fields Pro
.
在网站的前端,我开发了一个过滤栏,用户可以通过几个过滤器进行选择并提交表单,然后生成一个复杂的WP\\u查询以返回匹配的列表。很简单!虽然大多数搜索都工作得很好,但一些更复杂的搜索将生成占用线程的SQL查询。当数据库需要刷新堆积的所有内容时,服务器基本上会冻结,直到有人终止进程。这在所有环境中都会发生,而不仅仅是在生产环境中。
例如,这里有一个查询,用于检查价格区间、卧室、浴室、列表是否包括家具、位置(post\\u id)以及帖子标题“1”。听起来不像是超级高级搜索,是吗?(这是生成的SQL)
SELECT DISTINCT 4x5LbPZ_posts.* FROM 4x5LbPZ_posts LEFT JOIN 4x5LbPZ_term_relationships ON (4x5LbPZ_posts.ID = 4x5LbPZ_term_relationships.object_id) INNER JOIN 4x5LbPZ_postmeta ON ( 4x5LbPZ_posts.ID = 4x5LbPZ_postmeta.post_id ) INNER JOIN 4x5LbPZ_postmeta AS mt1 ON ( 4x5LbPZ_posts.ID = mt1.post_id ) INNER JOIN 4x5LbPZ_postmeta AS mt2 ON ( 4x5LbPZ_posts.ID = mt2.post_id ) INNER JOIN 4x5LbPZ_postmeta AS mt3 ON ( 4x5LbPZ_posts.ID = mt3.post_id ) INNER JOIN 4x5LbPZ_postmeta AS mt4 ON ( 4x5LbPZ_posts.ID = mt4.post_id ) INNER JOIN 4x5LbPZ_postmeta AS mt5 ON ( 4x5LbPZ_posts.ID = mt5.post_id ) INNER JOIN 4x5LbPZ_postmeta AS mt6 ON ( 4x5LbPZ_posts.ID = mt6.post_id ) INNER JOIN 4x5LbPZ_postmeta AS mt7 ON ( 4x5LbPZ_posts.ID = mt7.post_id ) INNER JOIN 4x5LbPZ_postmeta AS mt8 ON ( 4x5LbPZ_posts.ID = mt8.post_id ) INNER JOIN 4x5LbPZ_postmeta AS mt9 ON ( 4x5LbPZ_posts.ID = mt9.post_id ) LEFT JOIN 4x5LbPZ_term_relationships AS trel ON (4x5LbPZ_posts.ID = trel.object_id) LEFT JOIN 4x5LbPZ_term_taxonomy AS ttax ON ( ( ttax.taxonomy = \'category\' ) AND trel.term_taxonomy_id = ttax.term_taxonomy_id) LEFT JOIN 4x5LbPZ_terms AS tter ON (ttax.term_id = tter.term_id) LEFT JOIN 4x5LbPZ_postmeta AS m ON (4x5LbPZ_posts.ID = m.post_id) WHERE 1=1 AND ( ( (
4x5LbPZ_term_relationships.term_taxonomy_id IN (3)
) AND (((((4x5LbPZ_posts.post_title LIKE \'%1%\') OR (4x5LbPZ_posts.post_content LIKE \'%1%\'))) OR ((tter.slug LIKE \'%1%\')) OR ((ttax.description LIKE \'%1%\')) OR ((m.meta_value LIKE \'%1%\')) )) AND (
( 4x5LbPZ_postmeta.meta_key = \'listing_status\' AND 4x5LbPZ_postmeta.meta_value NOT IN (\'pending\') )
AND
( mt1.meta_key = \'listing_status\' AND mt1.meta_value IN (\'for_sale\') )
AND
( mt2.meta_key = \'listing_price\' AND CAST(mt2.meta_value AS SIGNED) >= \'0\' )
AND
( mt3.meta_key = \'listing_price\' AND CAST(mt3.meta_value AS SIGNED) <= \'7500000\' )
AND
( mt4.meta_key = \'listing_bedrooms\' AND CAST(mt4.meta_value AS SIGNED) >= \'0\' )
AND
( mt5.meta_key = \'listing_bedrooms\' AND CAST(mt5.meta_value AS SIGNED) <= \'36\' )
AND
( mt6.meta_key = \'listing_bathrooms\' AND CAST(mt6.meta_value AS SIGNED) >= \'0\' )
AND
( mt7.meta_key = \'listing_bathrooms\' AND CAST(mt7.meta_value AS SIGNED) <= \'7\' )
AND
( mt8.meta_key = \'listing_furniture\' AND mt8.meta_value = \'true\' )
AND
( mt9.meta_key = \'listing_location\' AND mt9.meta_value = \'80\' )
) AND 4x5LbPZ_posts.post_type = \'listing\' AND (4x5LbPZ_posts.post_status = \'publish\' OR 4x5LbPZ_posts.post_status = \'acf-disabled\')) AND post_type != \'revision\') AND post_status != \'future\' GROUP BY 4x5LbPZ_posts.ID ORDER BY 4x5LbPZ_posts.post_date DESC;
我真的只使用
TYPE
,
KEY
,
VALUE
和
COMPARE
在
meta_query
数组,所以它的构建应该使用WordPress,但它变得极其缓慢。当这种情况发生时,请求将不断增加,直到整个站点没有响应为止。