Completed
Push — master-stable ( 287111...36ed8c )
by
unknown
37:27 queued 29:06
created

handle_comment_contents_modification()   B

Complexity

Conditions 4
Paths 6

Size

Total Lines 28
Code Lines 13

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 4
eloc 13
nc 6
nop 3
dl 0
loc 28
rs 8.5806
c 0
b 0
f 0
1
<?php
2
3
class Jetpack_Sync_Module_Comments extends Jetpack_Sync_Module {
4
5
	public function name() {
6
		return 'comments';
7
	}
8
9
	public function get_object_by_id( $object_type, $id ) {
10
		$comment_id = intval( $id );
11
		if ( $object_type === 'comment' && $comment = get_comment( $comment_id ) ) {
12
			return $this->filter_comment( $comment );
13
		}
14
15
		return false;
16
	}
17
18
	public function init_listeners( $callable ) {
19
		add_action( 'wp_insert_comment', $callable, 10, 2 );
20
		add_action( 'deleted_comment', $callable );
21
		add_action( 'trashed_comment', $callable );
22
		add_action( 'spammed_comment', $callable );
23
		add_action( 'trashed_post_comments', $callable, 10, 2 );
24
		add_action( 'untrash_post_comments', $callable );
25
		add_action( 'comment_approved_to_unapproved', $callable );
26
		add_action( 'comment_unapproved_to_approved', $callable );
27
		add_action( 'jetpack_modified_comment_contents', $callable, 10, 2 );
28
		add_filter( 'wp_update_comment_data', array( $this, 'handle_comment_contents_modification' ), 10, 3 );
29
30
		// even though it's messy, we implement these hooks because
31
		// the edit_comment hook doesn't include the data
32
		// so this saves us a DB read for every comment event
33 View Code Duplication
		foreach ( array( '', 'trackback', 'pingback' ) as $comment_type ) {
34
			foreach ( array( 'unapproved', 'approved' ) as $comment_status ) {
35
				$comment_action_name = "comment_{$comment_status}_{$comment_type}";
36
				add_action( $comment_action_name, $callable, 10, 2 );
37
			}
38
		}
39
40
		// listen for meta changes
41
		$this->init_listeners_for_meta_type( 'comment', $callable );
42
		$this->init_meta_whitelist_handler( 'comment', array( $this, 'filter_meta' ) );
43
	}
44
45
	public function handle_comment_contents_modification( $new_comment, $old_comment, $new_comment_with_slashes ) {
46
		$content_fields = array(
47
			'comment_author',
48
			'comment_author_email',
49
			'comment_author_url',
50
			'comment_content',
51
		);
52
		$changes = array();
53
		foreach ( $content_fields as $field ) {
54
			if ( $new_comment_with_slashes[$field] != $old_comment[$field] ) {
55
				$changes[$field] = array( $new_comment[$field], $old_comment[$field] );
56
			}
57
		}
58
59
		if ( ! empty( $changes ) ) {
60
			/**
61
			 * Signals to the sync listener that this comment's contents were modified and a sync action
62
			 * reflecting the change(s) to the content should be sent
63
			 *
64
			 * @since 4.8.2
65
			 *
66
			 * @param int $new_comment['comment_ID'] ID of comment whose content was modified
67
			 * @param mixed $changes Array of changed comment fields with before and after values
68
			 */
69
			do_action( 'jetpack_modified_comment_contents', $new_comment['comment_ID'], $changes );
70
		}
71
		return $new_comment;
72
	}
73
74
	public function init_full_sync_listeners( $callable ) {
75
		add_action( 'jetpack_full_sync_comments', $callable ); // also send comments meta
76
	}
77
78
	public function init_before_send() {
79
		add_filter( 'jetpack_sync_before_send_wp_insert_comment', array( $this, 'expand_wp_insert_comment' ) );
80
81 View Code Duplication
		foreach ( array( '', 'trackback', 'pingback' ) as $comment_type ) {
82
			foreach ( array( 'unapproved', 'approved' ) as $comment_status ) {
83
				$comment_action_name = "comment_{$comment_status}_{$comment_type}";
84
				add_filter( 'jetpack_sync_before_send_' . $comment_action_name, array(
85
					$this,
86
					'expand_wp_insert_comment',
87
				) );
88
			}
89
		}
90
91
		// full sync
92
		add_filter( 'jetpack_sync_before_send_jetpack_full_sync_comments', array( $this, 'expand_comment_ids' ) );
93
	}
94
95
	public function enqueue_full_sync_actions( $config, $max_items_to_enqueue, $state ) {
96
		global $wpdb;
97
		return $this->enqueue_all_ids_as_action( 'jetpack_full_sync_comments', $wpdb->comments, 'comment_ID', $this->get_where_sql( $config ), $max_items_to_enqueue, $state );
98
	}
99
100
	public function estimate_full_sync_actions( $config ) {
101
		global $wpdb;
102
103
		$query = "SELECT count(*) FROM $wpdb->comments";
104
		
105
		if ( $where_sql = $this->get_where_sql( $config ) ) {
106
			$query .= ' WHERE ' . $where_sql;
107
		}
108
109
		$count = $wpdb->get_var( $query );
110
111
		return (int) ceil( $count / self::ARRAY_CHUNK_SIZE );
112
	}
113
114
	private function get_where_sql( $config ) {
115
		if ( is_array( $config ) ) {
116
			return 'comment_ID IN (' . implode( ',', array_map( 'intval', $config ) ) . ')';
117
		} 
118
119
		return null;
120
	}
121
122
	public function get_full_sync_actions() {
123
		return array( 'jetpack_full_sync_comments' );
124
	}
125
126
	public function count_full_sync_actions( $action_names ) {
127
		return $this->count_actions( $action_names, array( 'jetpack_full_sync_comments' ) );
128
	}
129
130
	function expand_wp_comment_status_change( $args ) {
131
		return array( $args[0], $this->filter_comment( $args[1] ) );
132
	}
133
134
	function expand_wp_insert_comment( $args ) {
135
		return array( $args[0], $this->filter_comment( $args[1] ) );
136
	}
137
138
	function filter_comment( $comment ) {
139
		/**
140
		 * Filters whether to prevent sending comment data to .com
141
		 *
142
		 * Passing true to the filter will prevent the comment data from being sent
143
		 * to the WordPress.com.
144
		 * Instead we pass data that will still enable us to do a checksum against the
145
		 * Jetpacks data but will prevent us from displaying the data on in the API as well as
146
		 * other services.
147
		 * @since 4.2.0
148
		 *
149
		 * @param boolean false prevent post data from bing synced to WordPress.com
150
		 * @param mixed $comment WP_COMMENT object
151
		 */
152
		if ( apply_filters( 'jetpack_sync_prevent_sending_comment_data', false, $comment ) ) {
153
			$blocked_comment                   = new stdClass();
154
			$blocked_comment->comment_ID       = $comment->comment_ID;
155
			$blocked_comment->comment_date     = $comment->comment_date;
156
			$blocked_comment->comment_date_gmt = $comment->comment_date_gmt;
157
			$blocked_comment->comment_approved = 'jetpack_sync_blocked';
158
159
			return $blocked_comment;
160
		}
161
162
		return $comment;
163
	}
164
165
	// Comment Meta
166
	function is_whitelisted_comment_meta( $meta_key ) {
167
		return in_array( $meta_key, Jetpack_Sync_Settings::get_setting( 'comment_meta_whitelist' ) );
168
	}
169
170
	function filter_meta( $args ) {
171
		return ( $this->is_whitelisted_comment_meta( $args[2] ) ? $args : false );
172
	}
173
174
	public function expand_comment_ids( $args ) {
175
		$comment_ids = $args[0];
176
		$comments    = get_comments( array(
177
			'include_unapproved' => true,
178
			'comment__in'        => $comment_ids,
179
		) );
180
181
		return array(
182
			$comments,
183
			$this->get_metadata( $comment_ids, 'comment', Jetpack_Sync_Settings::get_setting( 'comment_meta_whitelist' ) ),
184
		);
185
	}
186
}
187