Take the 2-minute tour ×
WordPress Development Stack Exchange is a question and answer site for WordPress developers and administrators. It's 100% free, no registration required.

I would like to get all the comments for a group of post (not only one post.

I tried

$comment_args = array('number' => '14', 'post_id' => '10,20,30,40'  );
    $comments = get_comments($comment_args);
    foreach($comments as $comment) ...

But does not work. Any ideas?

share|improve this question

2 Answers 2

up vote 4 down vote accepted

The 'post_id' is converted to a positive integer in WP_Comment_Query, so you cannot successful pass anything else to get_comments().

You have to filter 'comments_clauses'. Here you can change the WHERE clause to use comment_post_ID IN ( $ids ) instead of comment_post_ID = $id.

I would use a static class as a wrapper for get_comments().

Sample code

/**
 * Query comments for multiple post IDs.
 */
class T5_Multipost_Comments
{
    /**
     * Post IDs, eg. array ( 1, 2, 40 )
     * @var array
     */
    protected static $post_ids = array ();

    /**
     * Called like get_comments.
     *
     * @param  array $args
     * @param  array $post_ids
     * @return array
     */
    public static function get( $args = array (), $post_ids = array () )
    {
        if ( array () !== $post_ids )
        {
            self::$post_ids = $post_ids;
            add_filter( 'comments_clauses', array ( __CLASS__, 'filter_where_clause' ) );
        }
        return get_comments( $args );
    }

    /**
     * Filter the comment query
     *
     * @param array $q Query parts, see WP_Comment_Query::query()
     *
     * @return array
     */
    public static function filter_where_clause( $q )
    {
        $ids       = implode( ', ', self::$post_ids );
        $_where_in = " AND comment_post_ID IN ( $ids )";

        if ( FALSE !== strpos( $q['where'], ' AND comment_post_ID =' ) )
        {
            $q['where'] = preg_replace(
                '~ AND comment_post_ID = \d+~',
                $_where_in,
                $q['where']
            );
        }
        else
        {
            $q['where'] .= $_where_in;
        }

        remove_filter( 'comments_clauses', array ( __CLASS__, 'filter_where_clause' ) );
        return $q;
    }
}

Usage example

$multi_comments = T5_Multipost_Comments::get(
    array ( 'number' => '14' ), // comment args
    array ( 149, 564, 151 )     // post IDs
);
print '<pre>' . htmlspecialchars( print_r( $multi_comments, TRUE ) ) . '</pre>';
share|improve this answer
    
+1 Still wonder, why you're using __CLASS__ when calling remove_filter, but not __FUNCTION/METHOD__. –  kaiser Jun 14 '12 at 15:18
    
@kaiser __CLASS__ for syntactical requirements by PHP, the function name for readability. –  toscho Jun 14 '12 at 15:21

Unfortunately, get_comments() doesn't quite work that way. If you specify a post ID, the function will only return comments for that post. The post ID parameter does not accept multiple IDs.

However, you could write a function to recursively fetch comments from an array of posts and use that instead:

get_comments_from_range( $post_ids ) {
    foreach( $post_ids as $post_id ) {
        $comment_collection[] = get_comments( array( 'post_id' => $post_id ) );
    }

    return $comment_collection;
}

$comments = get_comments_from_range( array( '10', '20', '30', '40' ) );

Once you have the array inside your function, you can order it however you need and limit it to only 14 or so comments ... it's up to you.

share|improve this answer

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.