Question

I'm trying to save an average of comments as a post meta that needs to be updated every time according to comment status.

/**
 * Gets comment average data.
 */

function sw_get_averagerev( $post_id ) {
    if (get_post_type($post_id) == 'review') {

    $prev_averating = get_post_meta( $post_id, 'wp_review_comments_rating_value', true );
    $prev_count = get_post_meta( $post_id, 'wp_review_comments_rating_count', true );

        $comments = get_comments(
                    array(
                        'post_id' => $post->ID,
                        'type'    => 'wp_review_comment',
                        'status'  => 'approve',
                    ));

    $ratings_sum = 0;

    foreach ( $comments as $comment ){
        $ratings_sum+= get_comment_meta($comment->comment_ID, 'wp_review_comment_rating', true);
    };

        $count  = count( $comments );
        $ave_reviews = $ratings_sum / $count;

        $averating = round($ave_reviews , 2);


        update_post_meta( $post_id, 'wp_review_comments_rating_value', $averating, $prev_averating );
        update_post_meta( $post_id, 'wp_review_comments_rating_count', $count, $prev_count );
}}


/**
 * Runs something when comment status change.
 */
function wp_review_on_change_comment_status( $new_status, $old_status, $comment="comment_type=wp_review_comment" ) {
     sw_get_averagerev( $post_id ); 
}
add_action( 'transition_comment_status', 'wp_review_on_change_comment_status', 10, 3 );

$comment="comment_type=wp_review_comment" might be incorrect on the function wp_review_on_change_comment_status( $new_status, $old_status, $comment="comment_type=wp_review_comment" ). So, I have also checked with the defalt $comment args, It still the same.

Was it helpful?

Solution

You have typo error in $post->ID as you don't have $post variable, and it really could cause you feel that it doesn't work, at least it will not calculate new value. So here's modified approach.

I've also used different hooks to trigger action when it's really necessary and not for every comment_status transition.

/**
 * Gets comment average data.
 *
 * @param int $post_id
 */
function sw_update_average_review_rating( $post_id ) {

    if ( get_post_type( $post_id ) === 'review' ) {

        $prev_averating = get_post_meta( $post_id, 'wp_review_comments_rating_value', true );
        $prev_count     = get_post_meta( $post_id, 'wp_review_comments_rating_count', true );

        $comments = get_comments(
            array(
                'post_id' => $post_id, // HERE was a typo error, you dont' have here a $post you have $post_id!
                'type'    => 'wp_review_comment',
                'status'  => 'approve',
            )
        );

        $ratings_sum = 0;

        foreach ( $comments as $comment ) {
            $ratings_sum += get_comment_meta( $comment->comment_ID, 'wp_review_comment_rating', true );
        };

        $count       = count( $comments );
        $ave_reviews = $ratings_sum / $count;

        $averating = round( $ave_reviews, 2 );

        update_post_meta( $post_id, 'wp_review_comments_rating_value', $averating, $prev_averating );
        update_post_meta( $post_id, 'wp_review_comments_rating_count', $count, $prev_count );
    }

}

/**
 * Hook action for to trigger recalculation after comment status got changed.
 *
 * @param $comment_id
 * @param WP_Comment $comment
 */
function sw_review_after_comment_status_changed( $comment_id, $comment ) {

    $post_id = $comment->comment_post_ID;
    $post    = get_post( $post_id );
    if ( 'review' === $post->post_type ) {
        // trigger calculation.
        sw_update_average_review_rating( $post_id );
    }

}

add_action('deleted_comment', 'sw_review_after_comment_status_changed', 10, 2);
add_action( 'trashed_comment', 'sw_review_after_comment_status_changed', 10, 2);

// hooks below can be tuned only to handle your custom comment type. 
add_action( 'comment_approved_', 'sw_review_after_comment_status_changed', 10, 2);
add_action( 'comment_unapproved_', 'sw_review_after_comment_status_changed', 10, 2);

// Tuned for your custom comment type to trigger only for them, use either these or pair of hooks above.
add_action( 'comment_approved_wp_review_comment', 'sw_review_after_comment_status_changed', 10, 2);
add_action( 'comment_unapproved_wp_review_comment', 'sw_review_after_comment_status_changed', 10, 2);
Licensed under: CC-BY-SA with attribution
Not affiliated with wordpress.stackexchange
scroll top