WP_Query times out

时间:2015-12-27 作者:N00b

我有一个包含20个输入的表单,它运行WP\\u查询并通过ajax接收结果。

出于某种原因:

当5个以上的输入被填充时,查询会变得相当慢,7个输入值需要10-15秒,8个输入值需要15-25秒,并且随着我填充的下一个输入值的增加,查询速度会越来越慢,最后大约有15-20个值,并且超时(服务器应该有300秒超时)

  • 值本身并不重要,与em>1的结果相同,Ajax不应该有任何影响,因为如果有两个输入被填充,则返回的数据要多得多,而Ajax在文件大小较大时速度仍然很快。更多的填充输入只会使查询字符串变长,但它应该返回更少的数据6 tax_queries14 meta_queries 总计

    这是什么原因造成的?

    <小时>

    Update:

    我有10个示例帖子20 seconds 有8个填充输入,现在有20个输入超时(超过300秒),只需进行1次更改0.0012 seconds. 我有一种感觉,因为我排除了foreachswitch 在过程中,使用ifelse if.

    Changes I\'ve made so far:

    • 是:

      • $meta_query[] = array(
            \'key\'           => \'some_key\',
            \'value\'         => $some_value,
            \'type\'          => \'NUMERIC\',
            \'compare\'       => \'>=\'
        );
        $meta_query[] = array(
            \'key\'           => \'some_key\',
            \'value\'         => $some_value,
            \'type\'          => \'NUMERIC\',
            \'compare\'       => \'<=\'
        );
        
        是:

      if ( $value_one && $value_two ) {
          $meta_query[] = array(
              \'key\'           => \'some_key\',
              \'value\'         => array( $value_one, $value_two ),
              \'type\'          => \'NUMERIC\',
              \'compare\'       => \'BETWEEN\'
          );
      }
      else if ( $value_one && ! $value_two ) {
          $meta_query[] = array(
              \'key\'           => \'some_key\',
              \'value\'         => $value_one,
              \'type\'          => \'NUMERIC\',
              \'compare\'       => \'>=\'
          );
      }
      else if ( ! $value_one && $value_two ) {
          $meta_query[] = array(
              \'key\'           => \'some_key\',
              \'value\'         => $value_two,
              \'type\'          => \'NUMERIC\',
              \'compare\'       => \'<=\'
          );
      }
      
      我还消除了使用LIKE 操作员和IT基本上会在每个帖子中搜索2轮内容-标题和内容。我认为,虽然用户有这么多的搜索可能性,但这种昂贵的移动是没有意义的。我确信用户更喜欢速度而不是关键字搜索

  • 1 个回复
    最合适的回答,由SO网友:s_ha_dum 整理而成

    你所看到的并不是“坏”的,你只是得到了一个非常劳动密集型的查询WP_Query 没有足够的智能来优化它--它甚至没有尝试。简单地说,你有很多JOINs、 你有两个LIKE 将读取该帖子类型表中每一行的条件OR 工作加倍的关系,你有很多比较--<=-- 还将读取表中每一行的运算符。正如你所看到的,所有这些都会随着你增加的每一个条件而变得更糟。你也是ORDER由两个价值观决定,这也是相当劳动密集型的。数据库引擎(不是WP_Query) 将尽一切努力优化查询,但这是一个很难优化的查询,您的数据库服务器无法应对压力。

    你必须设法帮助事情顺利进行。

    我注意到以下几行:

    AND ( mt2.meta_key = \'single_rooms\'
        AND Cast(mt2.meta_value AS signed) >= \'3453\' )
    AND ( mt3.meta_key = \'single_rooms\'
        AND Cast(mt3.meta_value AS signed) <= \'345\' )
    
    您没有发布查询参数,但我猜您有多个meta_query是这样的:

    \'meta_query\' => array(
        array(
            \'key\'     => \'single_room\',
            \'value\'   => \'3435\',
            \'compare\' => \'>=\',
        ),
    ),
    
    而不是像这样:

    \'meta_query\' => array(
        array(
            \'key\'     => \'single_room\',
            \'value\'   => array(3435,345),
            \'compare\' => \'BETWEEN\',
        ),
    ),
    
    这可能会减少JOINs和加快速度WP_Query 无法转换BETWEEN (这是一个有效的MySQL查询条件)。

    不要对查询排序。稍后在PHP中执行此操作。我认为,您需要一个过滤器来完全删除排序,但至少不要在您的参数中添加更多的工作。

    您可以防止SQL_CALC_FOUND_ROWS 通过添加\'no_found_rows\' => true 你的论点。这可以提高性能,但可能会打乱一些循环函数,所以请进行测试并注意。

    如果这还不够,请查询postmeta 表中分别列出了post ID,并通过post__in 论点您必须编写自己的SQL。我所知的核心功能中没有以您需要的方式查询post meta的功能(这是我定期抱怨的核心故障)

    除此之外,优化将意味着一些非常复杂的SQL。

    最后一点注意:Learn to love EXPLAIN.

    相关推荐

    Trim posts from WP-Query?

    我希望在我的首页上显示一些由以下标准确定的帖子:显示当月的所有帖子(实际上是从最近帖子对应的月份开始);但是如果这个数字少于(比如)8,那么就显示最近的8篇帖子。假设我知道每个月都不会有超过(比如)20篇文章,我会将posts\\u per\\u page设置为20,通常抓取最近的20篇文章,然后在php中进行适当的修剪(切片)。(在SQL中这样做似乎太复杂了)顺便说一句:起初我以为add_filter( \'posts_results\', ... ) 这很合适,但很难区分查询是与主循环相对应,还是与其