Making WordPress.org


Ignore:
Timestamp:
08/31/2016 07:52:23 PM (8 years ago)
Author:
jmdodd
Message:

Support Forums: Stop using SQL_CALC_FOUND_ROWS on single forum queries.

A better search is more valuable than completely accurate pagination, as the page content will always be in flux as more topics are added to the beginning of the stack.

Order by PRIMARY KEY whenever possible.

File:
1 edited

Legend:

Unmodified
Added
Removed
  • sites/trunk/wordpress.org/public_html/wp-content/plugins/support-forums/inc/class-performance-optimizations.php

    r3860 r3895  
    55class Performance_Optimizations {
    66
     7    var $term = null;
     8    var $query = null;
     9
    710    function __construct() {
    811        // Gravatar suppression on lists of topics.
    9         add_filter( 'bbp_after_get_topic_author_link_parse_args', array( __CLASS__, 'get_author_link' ) );
    10         add_filter( 'bbp_after_get_reply_author_link_parse_args', array( __CLASS__, 'get_author_link' ) );
     12        add_filter( 'bbp_after_get_topic_author_link_parse_args', array( $this, 'get_author_link' ) );
     13        add_filter( 'bbp_after_get_reply_author_link_parse_args', array( $this, 'get_author_link' ) );
    1114
    1215        // Query simplification.
    13         add_filter( 'bbp_after_has_topics_parse_args', array( __CLASS__, 'has_topics' ) );
     16        add_filter( 'bbp_after_has_topics_parse_args', array( $this, 'has_topics' ) );
    1417    }
    1518
     
    1720     * Remove unnecessary Gravatar display on lists of topics.
    1821     */
    19     public static function get_author_link( $r ) {
     22    public function get_author_link( $r ) {
    2023        if ( ! bbp_is_single_topic() || bbp_is_topic_edit() ) {
    2124            $r['type'] = 'name';
     
    2528
    2629    /**
    27      * Optimize queries for has_topics as much as possible to avoid breaking things.
     30     * Optimize queries for has_topics as much as possible.
    2831     */
    29     public static function has_topics( $r ) {
     32    public function has_topics( $r ) {
    3033        /**
    31          * Filter view queries so they only look at the last N days of topics.
    32          */
    33         if ( bbp_is_single_view() ) {
    34             $view = bbp_get_view_id();
    35             // Exclude plugin and theme views from this restriction.
    36             // @todo Update date to a reasonable range once we're done importing.
    37             if ( ! in_array( $view, array( 'plugin', 'theme', 'review' ) ) ) {
    38                 $r['date_query'] = array( 'after' => '19 months ago' );
    39             } else {
    40                 $term = self::get_term();
    41 
    42                 // If there are a lot of results for a single plugin or theme,
    43                 // order by post_date to avoid an INNER JOIN ON.
    44                 if ( $term && ! is_wp_error( $term ) && property_exists( $term, 'count' ) ) {
    45                     if ( $term->count > 10000 ) {
    46                         unset( $r['meta_key'] );
    47                         unset( $r['meta_type'] );
    48 
    49                         $r['orderby'] = 'post_date';
    50                     }
    51                 }
    52             }
    53 
    54         /**
    55          * Filter forum queries so they are not sorted by the post meta value of
     34         * Filter queries so they are not sorted by the post meta value of
    5635         * `_bbp_last_active_time`. This query needs additional optimization
    5736         * to run over large sets of posts.
     
    5938         * - https://bbpress.trac.wordpress.org/ticket/1925
    6039         */
    61         } elseif ( bbp_is_single_forum() ) {
    62             unset( $r['meta_key'] );
    63             unset( $r['meta_type'] );
     40        if ( isset( $r['post_type'] ) && 'topic' == $r['post_type'] ) {
     41            // Theme and plugin views rely on taxonomy queries.
     42            if ( isset( $r['tax_query'] ) ) {
     43                return $r;
     44            }
    6445
    65             // This only works because we don't edit dates on forum topics.
    66             $r['orderby'] = 'post_date';
     46            // has_topics() uses this by default.
     47            if ( isset( $r['meta_key'] ) && '_bbp_last_active_time' == $r['meta_key'] ) {
     48                unset( $r['meta_key'] );
     49                unset( $r['meta_type'] );
     50                $r['orderby'] = 'ID';
     51            }
     52
     53            // If this is a forum, limit the number of pages we're dealing with.
     54            if ( isset( $r['post_parent'] ) && get_post_type( $r['post_parent'] ) === bbp_get_forum_post_type() ) {
     55                $r['no_found_rows'] = true;
     56                add_filter( 'bbp_topic_pagination', array( $this, 'forum_pagination' ) );
     57                $this->query = $r;
     58            }
    6759        }
     60        return $r;
     61    }
     62
     63    public function forum_pagination( $r ) {
     64        global $wpdb;
     65
     66        // Try the stored topic count.
     67        $count = get_post_meta( $this->query['post_parent'], '_bbp_topic_count', true );
     68        if ( ! empty( $count ) ) {
     69            $r['total'] = $count / bbp_get_topics_per_page();
     70            return $r;
     71        }
     72
     73        // Try SQL.
     74        if ( ! is_null( $this->query ) ) {
     75            $count = $wpdb->query( $wpdb->prepare( "SELECT COUNT(*) FROM $wpdb->posts WHERE post_parent = %d AND post_type = 'topic' AND post_status = 'publish' LIMIT 1", $this->query['post_parent'] ) );
     76            if ( $count ) {
     77                $r['total'] = $count / bbp_get_topics_per_page();
     78                return $r;
     79            }
     80        }
     81
     82        // If all else fails...
     83        $r['total'] = 10;
    6884        return $r;
    6985    }
     
    7288     * Get the term for a plugin or theme view from query_var.
    7389     */
    74     public static function get_term() {
     90    public function get_term() {
     91        if ( null !== $this->term ) {
     92            return $this->term;
     93        }
     94
     95        $slug = false;
    7596        if ( ! empty( get_query_var( Plugin::get_instance()->plugins->query_var() ) ) ) {
    7697            $slug = Plugin::get_instance()->plugins->slug();
     
    80101            $tax  = Plugin::get_instance()->themes->taxonomy();
    81102        }
    82         $term = get_term( $slug, $tax );
     103        if ( $slug ) {
     104            $term = get_term_by( 'slug', $slug, $tax );
     105        } else {
     106            return false;
     107        }
    83108        return $term;
    84109    }
Note: See TracChangeset for help on using the changeset viewer.