From 733a81d74d3f77792fffdec847bcad94b0864447 Mon Sep 17 00:00:00 2001 From: Peter Wilson Date: Mon, 23 Oct 2017 22:11:11 +0000 Subject: [PATCH] Comments: Check if `wp_new_comment()` returns an error. Adds checks throughout to allow for `wp_new_comment()` returning a `WP_Error` instance. Updates the docs for the `pre_comment_approved` filter to include that it can be passed an error. Props enrico.sorcinelli, ryotsun. Fixes #39730. git-svn-id: https://develop.svn.wordpress.org/trunk@41980 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-admin/includes/ajax-actions.php | 5 ++++ src/wp-includes/class-wp-xmlrpc-server.php | 4 +++ src/wp-includes/comment.php | 6 +++-- src/wp-trackback.php | 7 ++++- tests/phpunit/tests/ajax/ReplytoComment.php | 30 +++++++++++++++++++++ 5 files changed, 49 insertions(+), 3 deletions(-) diff --git a/src/wp-admin/includes/ajax-actions.php b/src/wp-admin/includes/ajax-actions.php index 53f4b31d33..373d3436e3 100644 --- a/src/wp-admin/includes/ajax-actions.php +++ b/src/wp-admin/includes/ajax-actions.php @@ -1100,6 +1100,11 @@ function wp_ajax_replyto_comment( $action ) { } $comment_id = wp_new_comment( $commentdata ); + + if ( is_wp_error( $comment_id ) ) { + wp_die( $comment_id->get_error_message() ); + } + $comment = get_comment($comment_id); if ( ! $comment ) wp_die( 1 ); diff --git a/src/wp-includes/class-wp-xmlrpc-server.php b/src/wp-includes/class-wp-xmlrpc-server.php index 52d2d4e807..c35498cd97 100644 --- a/src/wp-includes/class-wp-xmlrpc-server.php +++ b/src/wp-includes/class-wp-xmlrpc-server.php @@ -6487,6 +6487,10 @@ class wp_xmlrpc_server extends IXR_Server { $comment_ID = wp_new_comment($commentdata); + if ( is_wp_error( $comment_ID ) ) { + return $this->pingback_error( 0, $comment_ID->get_error_message() ); + } + /** * Fires after a post pingback has been sent. * diff --git a/src/wp-includes/comment.php b/src/wp-includes/comment.php index eae3a80731..07fed8100e 100644 --- a/src/wp-includes/comment.php +++ b/src/wp-includes/comment.php @@ -769,9 +769,11 @@ function wp_allow_comment( $commentdata, $avoid_die = false ) { * Filters a comment's approval status before it is set. * * @since 2.1.0 + * @since 4.9.0 Returning a WP_Error value from the filter will shortcircuit comment insertion and + * allow skipping further processing. * - * @param bool|string $approved The approval status. Accepts 1, 0, or 'spam'. - * @param array $commentdata Comment data. + * @param bool|string|WP_Error $approved The approval status. Accepts 1, 0, 'spam' or WP_Error. + * @param array $commentdata Comment data. */ $approved = apply_filters( 'pre_comment_approved', $approved, $commentdata ); return $approved; diff --git a/src/wp-trackback.php b/src/wp-trackback.php index 86e17b965d..802bb2ba6d 100644 --- a/src/wp-trackback.php +++ b/src/wp-trackback.php @@ -126,7 +126,12 @@ if ( !empty($tb_url) && !empty($title) ) { $commentdata = compact('comment_post_ID', 'comment_author', 'comment_author_email', 'comment_author_url', 'comment_content', 'comment_type'); - wp_new_comment($commentdata); + $result = wp_new_comment( $commentdata ); + + if ( is_wp_error( $result ) ) { + trackback_response( 1, $result->get_error_message() ); + } + $trackback_id = $wpdb->insert_id; /** diff --git a/tests/phpunit/tests/ajax/ReplytoComment.php b/tests/phpunit/tests/ajax/ReplytoComment.php index 33a0650472..1537d32f6e 100644 --- a/tests/phpunit/tests/ajax/ReplytoComment.php +++ b/tests/phpunit/tests/ajax/ReplytoComment.php @@ -222,4 +222,34 @@ class Tests_Ajax_ReplytoComment extends WP_Ajax_UnitTestCase { } return $sql; } + + /** + * Raises WP_Error after Posted a new pre comment + * @ticket 39730 + * @return void + */ + public function test_pre_comments_approved() { + + // Become an administrator + $this->_setRole( 'administrator' ); + + // Set up a default request + $_POST['_ajax_nonce-replyto-comment'] = wp_create_nonce( 'replyto-comment' ); + $_POST['content'] = 'Lorem ipsum dolor sit amet, consectetur adipiscing elit.'; + $_POST['comment_post_ID'] = self::$comment_post->ID; + + // Simulate filter check error + add_filter( 'pre_comment_approved', array( $this, '_pre_comment_approved_filter' ), 10, 2 ); + + // Make the request + $this->setExpectedException( 'WPAjaxDieStopException', 'pre_comment_approved filter fails for new comment' ); + $this->_handleAjax( 'replyto-comment' ); + } + + /** + * Block comments from being saved 'pre_comment_approved', by returning WP_Error + */ + function _pre_comment_approved_filter( $approved, $commentdata ) { + return new WP_Error( 'comment_wrong', 'pre_comment_approved filter fails for new comment', 403 ); + } }