File: /var/www/html/wp-content/plugins/wp-graphql/src/Mutation/CommentCreate.php
<?php
namespace WPGraphQL\Mutation;
use GraphQL\Error\UserError;
use GraphQL\Type\Definition\ResolveInfo;
use WPGraphQL\AppContext;
use WPGraphQL\Data\CommentMutation;
class CommentCreate {
/**
* Registers the CommentCreate mutation.
*
* @return void
* @throws \Exception
*/
public static function register_mutation() {
register_graphql_mutation(
'createComment',
[
'inputFields' => self::get_input_fields(),
'outputFields' => self::get_output_fields(),
'mutateAndGetPayload' => self::mutate_and_get_payload(),
]
);
}
/**
* Defines the mutation input field configuration.
*
* @return array<string,array<string,mixed>>
*/
public static function get_input_fields() {
return [
'approved' => [
'type' => 'String',
'description' => static function () {
return __( 'The approval status of the comment.', 'wp-graphql' );
},
'deprecationReason' => static function () {
return __( 'Deprecated in favor of the status field', 'wp-graphql' );
},
],
'author' => [
'type' => 'String',
'description' => static function () {
return __( 'The name of the comment\'s author.', 'wp-graphql' );
},
],
'authorEmail' => [
'type' => 'String',
'description' => static function () {
return __( 'The email of the comment\'s author.', 'wp-graphql' );
},
],
'authorUrl' => [
'type' => 'String',
'description' => static function () {
return __( 'The url of the comment\'s author.', 'wp-graphql' );
},
],
'commentOn' => [
'type' => 'Int',
'description' => static function () {
return __( 'The database ID of the post object the comment belongs to.', 'wp-graphql' );
},
],
'content' => [
'type' => 'String',
'description' => static function () {
return __( 'Content of the comment.', 'wp-graphql' );
},
],
'date' => [
'type' => 'String',
'description' => static function () {
return __( 'The date of the object. Preferable to enter as year/month/day ( e.g. 01/31/2017 ) as it will rearrange date as fit if it is not specified. Incomplete dates may have unintended results for example, "2017" as the input will use current date with timestamp 20:17 ', 'wp-graphql' );
},
],
'parent' => [
'type' => 'ID',
'description' => static function () {
return __( 'Parent comment ID of current comment.', 'wp-graphql' );
},
],
'status' => [
'type' => 'CommentStatusEnum',
'description' => static function () {
return __( 'The approval status of the comment', 'wp-graphql' );
},
],
'type' => [
'type' => 'String',
'description' => static function () {
return __( 'Type of comment.', 'wp-graphql' );
},
],
];
}
/**
* Defines the mutation output field configuration.
*
* @return array<string,array<string,mixed>>
*/
public static function get_output_fields() {
return [
'comment' => [
'type' => 'Comment',
'description' => static function () {
return __( 'The comment that was created', 'wp-graphql' );
},
'resolve' => static function ( $payload, $args, AppContext $context ) {
if ( ! isset( $payload['id'] ) || ! absint( $payload['id'] ) ) {
return null;
}
return $context->get_loader( 'comment' )->load_deferred( absint( $payload['id'] ) );
},
],
/**
* Comments can be created by non-authenticated users, but if the comment is not approved
* the user will not have access to the comment in response to the mutation.
*
* This field allows for the mutation to respond with a success message that the
* comment was indeed created, even if it cannot be returned in the response to respect
* server privacy.
*
* If the success comes back as true, the client can then use that response to
* dictate if they should use the input values as an optimistic response to the mutation
* and store in the cache, localStorage, cookie or whatever else so that the
* client can see their comment while it's still pending approval.
*/
'success' => [
'type' => 'Boolean',
'description' => static function () {
return __( 'Whether the mutation succeeded. If the comment is not approved, the server will not return the comment to a non authenticated user, but a success message can be returned if the create succeeded, and the client can optimistically add the comment to the client cache', 'wp-graphql' );
},
],
];
}
/**
* Defines the mutation data modification closure.
*
* @return callable(array<string,mixed>$input,\WPGraphQL\AppContext $context,\GraphQL\Type\Definition\ResolveInfo $info):array<string,mixed>
*/
public static function mutate_and_get_payload() {
return static function ( $input, AppContext $context, ResolveInfo $info ) {
/**
* Throw an exception if there's no input
*/
if ( ( empty( $input ) || ! is_array( $input ) ) ) {
throw new UserError( esc_html__( 'Mutation not processed. There was no input for the mutation or the comment_object was invalid', 'wp-graphql' ) );
}
$commented_on = get_post( absint( $input['commentOn'] ) );
if ( empty( $commented_on ) ) {
throw new UserError( esc_html__( 'The ID of the node to comment on is invalid', 'wp-graphql' ) );
}
/**
* Stop if post not open to comments
*/
if ( empty( $input['commentOn'] ) || 'closed' === $commented_on->comment_status ) {
throw new UserError( esc_html__( 'Sorry, this post is closed to comments at the moment', 'wp-graphql' ) );
}
if ( '1' === get_option( 'comment_registration' ) && ! is_user_logged_in() ) {
throw new UserError( esc_html__( 'This site requires you to be logged in to leave a comment', 'wp-graphql' ) );
}
/**
* Map all of the args from GraphQL to WordPress friendly args array
*/
$comment_args = [
'comment_author_url' => '',
'comment_type' => '',
'comment_parent' => 0,
'user_id' => 0,
'comment_date' => gmdate( 'Y-m-d H:i:s' ),
];
CommentMutation::prepare_comment_object( $input, $comment_args, 'createComment' );
/**
* Insert the comment and retrieve the ID
*/
$comment_id = wp_new_comment( $comment_args, true );
/**
* Throw an exception if the comment failed to be created
*/
if ( is_wp_error( $comment_id ) ) {
$error_message = $comment_id->get_error_message();
if ( ! empty( $error_message ) ) {
throw new UserError( esc_html( $error_message ) );
} else {
throw new UserError( esc_html__( 'The object failed to create but no error was provided', 'wp-graphql' ) );
}
}
/**
* If the $comment_id is empty, we should throw an exception
*/
if ( empty( $comment_id ) ) {
throw new UserError( esc_html__( 'The object failed to create', 'wp-graphql' ) );
}
/**
* This updates additional data not part of the comments table ( commentmeta, other relations, etc )
*
* The input for the commentMutation will be passed, along with the $new_comment_id for the
* comment that was created so that relations can be set, meta can be updated, etc.
*/
CommentMutation::update_additional_comment_data( $comment_id, $input, 'createComment', $context, $info );
/**
* Return the comment object
*/
return [
'id' => $comment_id,
'success' => true,
];
};
}
}