Completed
Push — update/dialogue-focus-on-conte... ( 9f1745...fa862f )
by
unknown
80:03 queued 71:18
created

class.wpcom-json-api-update-comment-endpoint.php (14 issues)

Upgrade to new PHP Analysis Engine

These results are based on our legacy PHP analysis, consider migrating to our new PHP analysis engine instead. Learn more

1
<?php
2
3
new WPCOM_JSON_API_Update_Comment_Endpoint( array(
4
	'description' => 'Create a comment on a post.',
5
	'group'       => 'comments',
6
	'stat'        => 'posts:1:replies:new',
7
8
	'method'      => 'POST',
9
	'path'        => '/sites/%s/posts/%d/replies/new',
10
	'path_labels' => array(
11
		'$site'    => '(int|string) Site ID or domain',
12
		'$post_ID' => '(int) The post ID'
13
	),
14
15
	'request_format' => array(
16
		// explicitly document all input
17
		'content'   => '(HTML) The comment text.',
18
//		@todo Should we open this up to unauthenticated requests too?
19
//		'author'    => '(author object) The author of the comment.',
20
	),
21
22
	'pass_wpcom_user_details' => true,
23
24
	'allow_fallback_to_jetpack_blog_token' => true,
25
26
	'example_request'      => 'https://public-api.wordpress.com/rest/v1/sites/82974409/posts/843/replies/new/',
27
	'example_request_data' =>  array(
28
		'headers' => array(
29
			'authorization' => 'Bearer YOUR_API_TOKEN'
30
		),
31
		'body' => array(
32
			'content' => 'Your reply is very interesting. This is a reply.'
33
		)
34
	)
35
) );
36
37
new WPCOM_JSON_API_Update_Comment_Endpoint( array(
38
	'description' => 'Create a comment as a reply to another comment.',
39
	'group'       => 'comments',
40
	'stat'        => 'comments:1:replies:new',
41
42
	'method'      => 'POST',
43
	'path'        => '/sites/%s/comments/%d/replies/new',
44
	'path_labels' => array(
45
		'$site'       => '(int|string) Site ID or domain',
46
		'$comment_ID' => '(int) The comment ID'
47
	),
48
49
	'request_format' => array(
50
		'content'   => '(HTML) The comment text.',
51
//		@todo Should we open this up to unauthenticated requests too?
52
//		'author'    => '(author object) The author of the comment.',
53
	),
54
55
	'pass_wpcom_user_details' => true,
56
57
	'allow_fallback_to_jetpack_blog_token' => true,
58
59
	'example_request'      => 'https://public-api.wordpress.com/rest/v1/sites/82974409/comments/29/replies/new',
60
	'example_request_data' => array(
61
		'headers' => array(
62
			'authorization' => 'Bearer YOUR_API_TOKEN'
63
		),
64
		'body' => array(
65
			'content' => 'This reply is very interesting. This is editing a comment reply via the API.',
66
		)
67
	)
68
) );
69
70
new WPCOM_JSON_API_Update_Comment_Endpoint( array(
71
	'description' => 'Edit a comment.',
72
	'group'       => 'comments',
73
	'stat'        => 'comments:1:POST',
74
75
	'method'      => 'POST',
76
	'path'        => '/sites/%s/comments/%d',
77
	'path_labels' => array(
78
		'$site'       => '(int|string) Site ID or domain',
79
		'$comment_ID' => '(int) The comment ID'
80
	),
81
82
	'request_format' => array(
83
		'author'       => "(string) The comment author's name.",
84
		'author_email' => "(string) The comment author's email.",
85
		'author_url'   => "(string) The comment author's URL.",
86
		'content'      => '(HTML) The comment text.',
87
		'date'         => "(ISO 8601 datetime) The comment's creation time.",
88
		'status'       => array(
89
			'approved'   => 'Approve the comment.',
90
			'unapproved' => 'Remove the comment from public view and send it to the moderation queue.',
91
			'spam'       => 'Mark the comment as spam.',
92
			'unspam'     => 'Unmark the comment as spam. Will attempt to set it to the previous status.',
93
			'trash'      => 'Send a comment to the trash if trashing is enabled (see constant: EMPTY_TRASH_DAYS).',
94
			'untrash'    => 'Untrash a comment. Only works when the comment is in the trash.',
95
		),
96
	),
97
98
	'example_request'      => 'https://public-api.wordpress.com/rest/v1/sites/82974409/comments/29',
99
	'example_request_data' => array(
100
		'headers' => array(
101
			'authorization' => 'Bearer YOUR_API_TOKEN'
102
		),
103
		'body' => array(
104
			'content' => 'This reply is now edited via the API.',
105
			'status'  => 'approved',
106
		)
107
	)
108
) );
109
110
new WPCOM_JSON_API_Update_Comment_Endpoint( array(
111
	'description' => 'Delete a comment.',
112
	'group'       => 'comments',
113
	'stat'        => 'comments:1:delete',
114
115
	'method'      => 'POST',
116
	'path'        => '/sites/%s/comments/%d/delete',
117
	'path_labels' => array(
118
		'$site'       => '(int|string) Site ID or domain',
119
		'$comment_ID' => '(int) The comment ID'
120
	),
121
122
	'example_request'      => 'https://public-api.wordpress.com/rest/v1/sites/82974409/comments/$comment_ID/delete',
123
	'example_request_data' => array(
124
		'headers' => array(
125
			'authorization' => 'Bearer YOUR_API_TOKEN'
126
		)
127
	)
128
) );
129
130
class WPCOM_JSON_API_Update_Comment_Endpoint extends WPCOM_JSON_API_Comment_Endpoint {
131
	function __construct( $args ) {
132
		parent::__construct( $args );
133
		if ( $this->api->ends_with( $this->path, '/delete' ) ) {
134
			$this->comment_object_format['status']['deleted'] = 'The comment has been deleted permanently.';
135
		}
136
	}
137
138
	// /sites/%s/posts/%d/replies/new    -> $blog_id, $post_id
139
	// /sites/%s/comments/%d/replies/new -> $blog_id, $comment_id
140
	// /sites/%s/comments/%d             -> $blog_id, $comment_id
141
	// /sites/%s/comments/%d/delete      -> $blog_id, $comment_id
142
	function callback( $path = '', $blog_id = 0, $object_id = 0 ) {
143
		if ( $this->api->ends_with( $path, '/new' ) )
144
			$blog_id = $this->api->switch_to_blog_and_validate_user( $this->api->get_blog_id( $blog_id ), false );
145
		else
146
			$blog_id = $this->api->switch_to_blog_and_validate_user( $this->api->get_blog_id( $blog_id ) );
147
		if ( is_wp_error( $blog_id ) ) {
148
			return $blog_id;
149
		}
150
151
		if ( $this->api->ends_with( $path, '/delete' ) ) {
152
			return $this->delete_comment( $path, $blog_id, $object_id );
153
		} elseif ( $this->api->ends_with( $path, '/new' ) ) {
154
			if ( false !== strpos( $path, '/posts/' ) ) {
155
				return $this->new_comment( $path, $blog_id, $object_id, 0 );
156
			} else {
157
				return $this->new_comment( $path, $blog_id, 0, $object_id );
158
			}
159
		}
160
161
		return $this->update_comment( $path, $blog_id, $object_id );
162
	}
163
164
	// /sites/%s/posts/%d/replies/new    -> $blog_id, $post_id
165
	// /sites/%s/comments/%d/replies/new -> $blog_id, $comment_id
166
	function new_comment( $path, $blog_id, $post_id, $comment_parent_id ) {
167
		if ( !$post_id ) {
168
			$comment_parent = get_comment( $comment_parent_id );
169
			if ( !$comment_parent_id || !$comment_parent || is_wp_error( $comment_parent ) ) {
170
				return new WP_Error( 'unknown_comment', 'Unknown comment', 404 );
0 ignored issues
show
The call to WP_Error::__construct() has too many arguments starting with 'unknown_comment'.

This check compares calls to functions or methods with their respective definitions. If the call has more arguments than are defined, it raises an issue.

If a function is defined several times with a different number of parameters, the check may pick up the wrong definition and report false positives. One codebase where this has been known to happen is Wordpress.

In this case you can add the @ignore PhpDoc annotation to the duplicate definition and it will be ignored.

Loading history...
171
			}
172
173
			$post_id = $comment_parent->comment_post_ID;
174
		}
175
176
		$post = get_post( $post_id );
177
		if ( !$post || is_wp_error( $post ) ) {
178
			return new WP_Error( 'unknown_post', 'Unknown post', 404 );
0 ignored issues
show
The call to WP_Error::__construct() has too many arguments starting with 'unknown_post'.

This check compares calls to functions or methods with their respective definitions. If the call has more arguments than are defined, it raises an issue.

If a function is defined several times with a different number of parameters, the check may pick up the wrong definition and report false positives. One codebase where this has been known to happen is Wordpress.

In this case you can add the @ignore PhpDoc annotation to the duplicate definition and it will be ignored.

Loading history...
179
		}
180
181
		if (
182
			-1 == get_option( 'blog_public' ) &&
183
			/**
184
			 * Filter allowing non-registered users on the site to comment.
185
			 *
186
			 * @module json-api
187
			 *
188
			 * @since 3.4.0
189
			 *
190
			 * @param bool is_user_member_of_blog() Is the user member of the site.
191
			 */
192
			! apply_filters( 'wpcom_json_api_user_is_member_of_blog', is_user_member_of_blog() ) &&
193
			! is_super_admin()
194
		) {
195
			return new WP_Error( 'unauthorized', 'User cannot create comments', 403 );
0 ignored issues
show
The call to WP_Error::__construct() has too many arguments starting with 'unauthorized'.

This check compares calls to functions or methods with their respective definitions. If the call has more arguments than are defined, it raises an issue.

If a function is defined several times with a different number of parameters, the check may pick up the wrong definition and report false positives. One codebase where this has been known to happen is Wordpress.

In this case you can add the @ignore PhpDoc annotation to the duplicate definition and it will be ignored.

Loading history...
196
		}
197
198
		if ( ! comments_open( $post->ID ) && ! current_user_can( 'edit_post', $post->ID ) ) {
199
			return new WP_Error( 'unauthorized', 'Comments on this post are closed', 403 );
0 ignored issues
show
The call to WP_Error::__construct() has too many arguments starting with 'unauthorized'.

This check compares calls to functions or methods with their respective definitions. If the call has more arguments than are defined, it raises an issue.

If a function is defined several times with a different number of parameters, the check may pick up the wrong definition and report false positives. One codebase where this has been known to happen is Wordpress.

In this case you can add the @ignore PhpDoc annotation to the duplicate definition and it will be ignored.

Loading history...
200
		}
201
202
		$can_view = $this->user_can_view_post( $post->ID );
203
		if ( !$can_view || is_wp_error( $can_view ) ) {
204
			return $can_view;
205
		}
206
207
		$post_status = get_post_status_object( get_post_status( $post ) );
208
		if ( !$post_status->public && !$post_status->private ) {
209
			return new WP_Error( 'unauthorized', 'Comments on drafts are not allowed', 403 );
0 ignored issues
show
The call to WP_Error::__construct() has too many arguments starting with 'unauthorized'.

This check compares calls to functions or methods with their respective definitions. If the call has more arguments than are defined, it raises an issue.

If a function is defined several times with a different number of parameters, the check may pick up the wrong definition and report false positives. One codebase where this has been known to happen is Wordpress.

In this case you can add the @ignore PhpDoc annotation to the duplicate definition and it will be ignored.

Loading history...
210
		}
211
212
		$args  = $this->query_args();
213
		$input = $this->input();
214 View Code Duplication
		if ( !is_array( $input ) || !$input || !strlen( $input['content'] ) ) {
215
			return new WP_Error( 'invalid_input', 'Invalid request input', 400 );
0 ignored issues
show
The call to WP_Error::__construct() has too many arguments starting with 'invalid_input'.

This check compares calls to functions or methods with their respective definitions. If the call has more arguments than are defined, it raises an issue.

If a function is defined several times with a different number of parameters, the check may pick up the wrong definition and report false positives. One codebase where this has been known to happen is Wordpress.

In this case you can add the @ignore PhpDoc annotation to the duplicate definition and it will be ignored.

Loading history...
216
		}
217
218
		$user = wp_get_current_user();
219
		if ( !$user || is_wp_error( $user ) || !$user->ID ) {
220
			$auth_required = false;
221
			if ( defined( 'IS_WPCOM' ) && IS_WPCOM ) {
222
				$auth_required = true;
223
			} elseif ( isset( $this->api->token_details['user'] ) ) {
224
				$user = (object) $this->api->token_details['user'];
225
				foreach ( array( 'display_name', 'user_email', 'user_url' ) as $user_datum ) {
226
					if ( !isset( $user->$user_datum ) ) {
227
						$auth_required = true;
228
					}
229
				}
230
				if ( !isset( $user->ID ) ) {
231
					$user->ID = 0;
232
				}
233
234
				$author = get_user_by( 'id', (int) $user->ID );
235
				// If we have a user with an external ID saved, we can use it.
236
				if (
237
					! $auth_required
238
					&& $user->ID
239
					&& $author
240
				) {
241
					$user = $author;
242
				}
243
			} else {
244
				$auth_required = true;
245
			}
246
247
			if ( $auth_required ) {
248
				return new WP_Error( 'authorization_required', 'An active access token must be used to comment.', 403 );
0 ignored issues
show
The call to WP_Error::__construct() has too many arguments starting with 'authorization_required'.

This check compares calls to functions or methods with their respective definitions. If the call has more arguments than are defined, it raises an issue.

If a function is defined several times with a different number of parameters, the check may pick up the wrong definition and report false positives. One codebase where this has been known to happen is Wordpress.

In this case you can add the @ignore PhpDoc annotation to the duplicate definition and it will be ignored.

Loading history...
249
			}
250
		}
251
252
		$insert = array(
253
			'comment_post_ID'      => $post->ID,
254
			'user_ID'              => $user->ID,
255
			'comment_author'       => $user->display_name,
256
			'comment_author_email' => $user->user_email,
257
			'comment_author_url'   => $user->user_url,
258
			'comment_content'      => $input['content'],
259
			'comment_parent'       => $comment_parent_id,
260
			'comment_type'         => 'comment',
261
		);
262
263
		if ( $comment_parent_id ) {
264
			if ( $comment_parent->comment_approved === '0' && current_user_can( 'edit_comment', $comment_parent->comment_ID ) ) {
265
				wp_set_comment_status( $comment_parent->comment_ID, 'approve' );
266
			}
267
		}
268
269
		$this->api->trap_wp_die( 'comment_failure' );
270
		$comment_id = wp_new_comment( add_magic_quotes( $insert ) );
271
		$this->api->trap_wp_die( null );
272
273
		$return = $this->get_comment( $comment_id, $args['context'] );
274
		if ( !$return ) {
275
			return new WP_Error( 400, __( 'Comment cache problem?', 'jetpack' ) );
0 ignored issues
show
The call to WP_Error::__construct() has too many arguments starting with 400.

This check compares calls to functions or methods with their respective definitions. If the call has more arguments than are defined, it raises an issue.

If a function is defined several times with a different number of parameters, the check may pick up the wrong definition and report false positives. One codebase where this has been known to happen is Wordpress.

In this case you can add the @ignore PhpDoc annotation to the duplicate definition and it will be ignored.

Loading history...
276
		}
277
		if ( is_wp_error( $return ) ) {
278
			return $return;
279
		}
280
281
		/** This action is documented in json-endpoints/class.wpcom-json-api-site-settings-endpoint.php */
282
		do_action( 'wpcom_json_api_objects', 'comments' );
283
		return $return;
284
	}
285
286
	// /sites/%s/comments/%d -> $blog_id, $comment_id
287
	function update_comment( $path, $blog_id, $comment_id ) {
288
		$comment = get_comment( $comment_id );
289
		if ( !$comment || is_wp_error( $comment ) ) {
290
			return new WP_Error( 'unknown_comment', 'Unknown comment', 404 );
0 ignored issues
show
The call to WP_Error::__construct() has too many arguments starting with 'unknown_comment'.

This check compares calls to functions or methods with their respective definitions. If the call has more arguments than are defined, it raises an issue.

If a function is defined several times with a different number of parameters, the check may pick up the wrong definition and report false positives. One codebase where this has been known to happen is Wordpress.

In this case you can add the @ignore PhpDoc annotation to the duplicate definition and it will be ignored.

Loading history...
291
		}
292
293
		if ( !current_user_can( 'edit_comment', $comment->comment_ID ) ) {
294
			return new WP_Error( 'unauthorized', 'User cannot edit comment', 403 );
0 ignored issues
show
The call to WP_Error::__construct() has too many arguments starting with 'unauthorized'.

This check compares calls to functions or methods with their respective definitions. If the call has more arguments than are defined, it raises an issue.

If a function is defined several times with a different number of parameters, the check may pick up the wrong definition and report false positives. One codebase where this has been known to happen is Wordpress.

In this case you can add the @ignore PhpDoc annotation to the duplicate definition and it will be ignored.

Loading history...
295
		}
296
297
		$args  = $this->query_args();
298
		$input = $this->input( false );
299
		if ( !is_array( $input ) || !$input ) {
300
			return new WP_Error( 'invalid_input', 'Invalid request input', 400 );
0 ignored issues
show
The call to WP_Error::__construct() has too many arguments starting with 'invalid_input'.

This check compares calls to functions or methods with their respective definitions. If the call has more arguments than are defined, it raises an issue.

If a function is defined several times with a different number of parameters, the check may pick up the wrong definition and report false positives. One codebase where this has been known to happen is Wordpress.

In this case you can add the @ignore PhpDoc annotation to the duplicate definition and it will be ignored.

Loading history...
301
		}
302
303
		$update = array();
304
		foreach ( $input as $key => $value ) {
305
			$update["comment_$key"] = $value;
306
		}
307
308
		$comment_status = wp_get_comment_status( $comment->comment_ID );
309
		if ( isset( $update['comment_status'] ) ) {
310
			switch ( $update['comment_status'] ) {
311
				case 'approved' :
312
					if ( 'approve' !== $comment_status ) {
313
						wp_set_comment_status( $comment->comment_ID, 'approve' );
314
					}
315
					break;
316
				case 'unapproved' :
317
					if ( 'hold' !== $comment_status ) {
318
						wp_set_comment_status( $comment->comment_ID, 'hold' );
319
					}
320
					break;
321
				case 'spam' :
322
					if ( 'spam' !== $comment_status ) {
323
						wp_spam_comment( $comment->comment_ID );
324
					}
325
					break;
326
				case 'unspam' :
327
					if ( 'spam' === $comment_status ) {
328
						wp_unspam_comment( $comment->comment_ID );
329
					}
330
					break;
331
				case 'trash' :
332
					if ( ! EMPTY_TRASH_DAYS ) {
333
						return new WP_Error( 'trash_disabled', 'Cannot trash comment', 403 );
0 ignored issues
show
The call to WP_Error::__construct() has too many arguments starting with 'trash_disabled'.

This check compares calls to functions or methods with their respective definitions. If the call has more arguments than are defined, it raises an issue.

If a function is defined several times with a different number of parameters, the check may pick up the wrong definition and report false positives. One codebase where this has been known to happen is Wordpress.

In this case you can add the @ignore PhpDoc annotation to the duplicate definition and it will be ignored.

Loading history...
334
					}
335
336
					if ( 'trash' !== $comment_status ) {
337
 						wp_trash_comment( $comment_id );
338
 					}
339
 					break;
340
				case 'untrash' :
341
					if ( 'trash' === $comment_status ) {
342
						wp_untrash_comment( $comment->comment_ID );
343
					}
344
					break;
345
				default:
346
					$update['comment_approved'] = 1;
347
					break;
348
			}
349
			unset( $update['comment_status'] );
350
		}
351
352
		if ( ! empty( $update ) ) {
353
			$update['comment_ID'] = $comment->comment_ID;
354
			wp_update_comment( add_magic_quotes( $update ) );
355
		}
356
357
		$return = $this->get_comment( $comment->comment_ID, $args['context'] );
358
		if ( !$return || is_wp_error( $return ) ) {
359
			return $return;
360
		}
361
362
		/** This action is documented in json-endpoints/class.wpcom-json-api-site-settings-endpoint.php */
363
		do_action( 'wpcom_json_api_objects', 'comments' );
364
		return $return;
365
	}
366
367
	// /sites/%s/comments/%d/delete -> $blog_id, $comment_id
368
	function delete_comment( $path, $blog_id, $comment_id ) {
369
		$comment = get_comment( $comment_id );
370
		if ( !$comment || is_wp_error( $comment ) ) {
371
			return new WP_Error( 'unknown_comment', 'Unknown comment', 404 );
0 ignored issues
show
The call to WP_Error::__construct() has too many arguments starting with 'unknown_comment'.

This check compares calls to functions or methods with their respective definitions. If the call has more arguments than are defined, it raises an issue.

If a function is defined several times with a different number of parameters, the check may pick up the wrong definition and report false positives. One codebase where this has been known to happen is Wordpress.

In this case you can add the @ignore PhpDoc annotation to the duplicate definition and it will be ignored.

Loading history...
372
		}
373
374
		if ( !current_user_can( 'edit_comment', $comment->comment_ID ) ) { // [sic] There is no delete_comment cap
375
			return new WP_Error( 'unauthorized', 'User cannot delete comment', 403 );
0 ignored issues
show
The call to WP_Error::__construct() has too many arguments starting with 'unauthorized'.

This check compares calls to functions or methods with their respective definitions. If the call has more arguments than are defined, it raises an issue.

If a function is defined several times with a different number of parameters, the check may pick up the wrong definition and report false positives. One codebase where this has been known to happen is Wordpress.

In this case you can add the @ignore PhpDoc annotation to the duplicate definition and it will be ignored.

Loading history...
376
		}
377
378
		$args  = $this->query_args();
379
		$return = $this->get_comment( $comment->comment_ID, $args['context'] );
380
		if ( !$return || is_wp_error( $return ) ) {
381
			return $return;
382
		}
383
384
		/** This action is documented in json-endpoints/class.wpcom-json-api-site-settings-endpoint.php */
385
		do_action( 'wpcom_json_api_objects', 'comments' );
386
387
		wp_delete_comment( $comment->comment_ID );
388
		$status = wp_get_comment_status( $comment->comment_ID );
389
		if ( false === $status ) {
390
			$return['status'] = 'deleted';
391
			return $return;
392
		}
393
394
		return $this->get_comment( $comment->comment_ID, $args['context'] );
395
	}
396
}
397