PluginProbe ʕ •ᴥ•ʔ
Jetpack – WP Security, Backup, Speed, & Growth / 13.2.4
Jetpack – WP Security, Backup, Speed, & Growth v13.2.4
12.0.3 12.1.3 12.2.3 12.3.2 12.4.2 12.5.2 12.6.4 12.7.3 12.8.3 12.9.5 13.0.2 13.1.5 13.2.4 13.3.3 13.4.5 13.5.2 13.6.2 13.7.2 13.8.3 13.9.2 14.0.1 14.1.1 14.2.2 14.3.1 14.4.2 14.5.1 14.6.1 14.7.1 14.8.1 14.9.2 15.0.3 15.1.2 15.2.1 15.3.2 15.4.1 15.5.1 15.6.1 15.7.2 15.8.1 15.9.2 16.0.2 16.1.3 16.2-a.5 16.2-a.3 16.1.2 16.2-a.1 16.1.1 16.1 16.1-beta 16.1-beta.2 16.1-beta.3 16.1-a.5 16.1-a.3 16.0.1 16.1-a.1 16.0 16.0-beta 16.0-a.7 16.0-a.5 15.9.1 16.0-a.3 16.0-a.1 15.9 15.9-beta 15.9-a.7 15.9-a.5 15.9-a.3 15.9-a.1 15.8 15.8-beta 15.8-a.7 15.8-a.5 5.2.5 5.3.4 5.4.4 5.5.5 5.6.5 5.7.5 5.8.4 5.9.4 6.0.4 6.1 6.1.1 6.1.2 6.1.3 6.1.4 6.1.5 6.2 6.2.1 6.2.2 6.2.3 6.2.4 6.2.5 6.3 6.3.1 6.3.2 6.3.3 6.3.4 6.3.5 6.3.6 6.3.7 6.4 6.4.1 6.4.2 6.4.3 6.4.4 6.4.5 6.4.6 6.5 6.5.1 6.5.2 6.5.3 6.5.4 6.6 6.6.1 6.6.2 6.6.3 6.6.4 6.6.5 6.7 6.7.1 6.7.2 6.7.3 6.7.4 6.8 6.8.1 6.8.2 6.8.3 6.8.4 6.8.5 6.9 6.9.1 6.9.2 6.9.3 6.9.4 7.0 7.0.1 7.0.2 7.0.3 7.0.4 7.0.5 7.1 7.1.1 7.1.2 7.1.3 7.1.4 7.1.5 7.2 7.2.1 7.2.1.1 7.2.2 7.2.3 7.2.4 7.2.5 7.3 7.3.0.1 7.3.1 7.3.1.1 7.3.2 7.3.3 7.3.4 7.3.5 7.4 7.4.1 7.4.2 7.4.3 7.4.4 7.4.5 7.5 7.5.0.1 7.5.1 7.5.2 7.5.3 7.5.4 7.5.5 7.5.6 7.5.7 7.6 7.6.1 7.6.2 7.6.3 7.6.4 7.7 7.7.1 7.7.2 7.7.3 7.7.4 7.7.5 7.7.6 7.8 7.8.1 7.8.2 7.8.3 7.8.4 7.9 7.9.1 7.9.2 7.9.3 7.9.4 8.0 8.0.1 8.0.2 8.0.3 8.1 8.1.1 8.1.2 8.1.3 8.1.4 8.2 8.2.0.1 8.2.1 8.2.2 8.2.3 8.2.4 8.2.5 8.2.6 8.3 8.3.1 8.3.2 8.3.3 8.4 8.4.1 8.4.2 8.4.3 8.4.4 8.4.5 8.5 8.5.1 8.5.2 8.5.3 8.6 8.6.1 8.6.2 8.6.3 8.6.4 8.7 8.7.0.1 8.7.1 8.7.2 8.7.3 8.7.4 8.8 8.8.1 8.8.2 8.8.3 8.8.4 8.8.5 8.9 8.9.1 8.9.2 8.9.3 8.9.4 9.0 9.0.1 9.0.2 9.0.3 9.0.4 9.0.5 9.1 9.1.1 9.1.2 9.1.3 9.2 9.2.1 9.2.2 9.2.3 9.2.4 9.3 9.3.1 9.3.2 9.3.3 9.3.4 9.3.5 9.4 9.4.1 9.4.2 9.4.3 9.4.4 9.5 9.5.1 9.5.2 9.5.3 9.5.4 9.5.5 9.6 9.6.1 9.6.2 9.6.3 9.6.4 9.7 9.7.1 9.7.2 15.7-beta.2 9.7.3 15.7.1 9.8 15.8-a.1 9.8.1 15.8-a.3 9.8.2 2.0.9 9.8.3 2.1.7 9.9 2.2.10 9.9.1 2.3.10 9.9.2 2.4.7 9.9.3 2.5.5 2.6.6 2.7.5 2.8.5 2.9.6 3.0.6 3.1.5 3.2.5 3.3.6 3.4.6 3.5.6 3.6.4 3.7.5 3.8.5 3.9.10 4.0.7 4.1.4 4.2.5 4.3.5 4.4.5 4.5.3 4.6.3 4.7.4 4.8.5 4.9.3 5.0.3 5.1.4 trunk 10.0 10.0.1 10.0.2 10.1 10.1.1 10.1.2 10.2 10.2.1 10.2.2 10.2.3 10.3 10.3.1 10.3.2 10.4 10.4.1 10.4.2 10.5 10.5.1 10.5.2 10.5.3 10.6 10.6.1 10.6.2 10.7 10.7.1 10.7.2 10.8 10.8.1 10.8.2 10.9 10.9.1 10.9.2 10.9.3 11.0 11.0.1 11.0.2 11.1 11.1.1 11.1.2 11.1.3 11.1.4 11.2 11.2.1 11.2.2 11.3 11.3.1 11.3.2 11.3.3 11.3.4 11.4 11.4.1 11.4.2 11.5 11.5.1 11.5.2 11.5.3 11.6 11.6.1 11.6.2 11.7 11.7.1 11.7.2 11.7.3 11.8 11.8.3 11.8.4 11.8.5 11.8.6 11.9 11.9.1 11.9.2 11.9.3 12.0 12.0.1 12.0.2 12.1 12.1.1 12.1.2 12.2 12.2.1 12.2.2 12.3 12.3.1 12.4 12.4.1 12.5 12.5.1 12.6 12.6.1 12.6.2 12.6.3 12.7 12.7.1 12.7.2 12.8 12.8.1 12.8.2 12.9 12.9.1 12.9.2 12.9.3 12.9.4 13.0 13.0.1 13.1 13.1.1 13.1.2 13.1.3 13.1.4 13.2 13.2.1 13.2.2 13.2.3 13.3 13.3.1 13.3.2 13.4 13.4.1 13.4.2 13.4.3 13.4.4 13.5 13.5.1 13.6 13.6.1 13.7 13.7.1 13.8 13.8.1 13.8.2 13.9 13.9.1 14.0 14.1 14.2 14.2.1 14.3 14.4 14.4.1 14.5 14.6 14.7 14.8 14.9 14.9.1 15.0 15.0.1 15.0.2 15.1 15.1.1 15.2 15.3 15.3.1 15.4 15.5 15.6 15.7 15.7-a.1 15.7-a.3 15.7-a.5 15.7-a.7 15.7-beta
jetpack / modules / likes.php
jetpack / modules Last commit date
calypsoify 2 years ago carousel 2 years ago cloudflare-analytics 4 years ago comment-likes 5 years ago comments 2 years ago contact-form 1 year ago custom-css 2 years ago custom-post-types 2 years ago geo-location 4 years ago google-analytics 2 years ago google-fonts 2 years ago gravatar 6 years ago infinite-scroll 2 years ago likes 2 years ago markdown 2 years ago masterbar 2 years ago memberships 2 years ago photon-cdn 2 years ago plugin-search 4 years ago post-by-email 3 years ago related-posts 2 years ago scan 2 years ago seo-tools 2 years ago sharedaddy 2 years ago shortcodes 2 years ago simple-payments 3 years ago site-icon 4 years ago sitemaps 2 years ago sso 2 years ago stats 2 years ago subscriptions 2 years ago theme-tools 2 years ago tiled-gallery 2 years ago verification-tools 4 years ago videopress 2 years ago widget-visibility 2 years ago widgets 2 years ago woocommerce-analytics 2 years ago wordads 2 years ago wpcom-block-editor 2 years ago wpcom-tos 5 years ago blaze.php 2 years ago carousel.php 2 years ago comment-likes.php 2 years ago comments.php 2 years ago contact-form.php 2 years ago copy-post.php 2 years ago custom-content-types.php 4 years ago custom-css.php 3 years ago enhanced-distribution.php 2 years ago geo-location.php 4 years ago google-analytics.php 4 years ago google-fonts.php 2 years ago gravatar-hovercards.php 2 years ago infinite-scroll.php 3 years ago json-api.php 5 years ago latex.php 4 years ago likes.php 2 years ago markdown.php 4 years ago masterbar.php 2 years ago module-extras.php 4 years ago module-headings.php 2 years ago module-info.php 2 years ago monitor.php 2 years ago notes.php 2 years ago photon-cdn.php 2 years ago photon.php 3 years ago plugin-search.php 2 years ago post-by-email.php 5 years ago post-list.php 4 years ago protect.php 3 years ago publicize.php 2 years ago related-posts.php 2 years ago search.php 4 years ago seo-tools.php 4 years ago sharedaddy.php 2 years ago shortcodes.php 2 years ago shortlinks.php 2 years ago sitemaps.php 4 years ago sso.php 2 years ago stats.php 2 years ago subscriptions.php 2 years ago theme-tools.php 3 years ago tiled-gallery.php 4 years ago vaultpress.php 2 years ago verification-tools.php 5 years ago videopress.php 4 years ago waf.php 3 years ago widget-visibility.php 4 years ago widgets.php 3 years ago woocommerce-analytics.php 2 years ago wordads.php 2 years ago wpgroho.js 6 years ago
likes.php
627 lines
1 <?php //phpcs:ignore WordPress.Files.FileName.InvalidClassFileName
2 /**
3 * Module Name: Likes
4 * Module Description: Give visitors an easy way to show they appreciate your content.
5 * First Introduced: 2.2
6 * Sort Order: 23
7 * Requires Connection: Yes
8 * Auto Activate: No
9 * Module Tags: Social
10 * Feature: Engagement
11 * Additional Search Queries: like, likes, wordpress.com
12 *
13 * @package automattic/jetpack
14 */
15 /**
16 * NOTE: While the front-end behavior currently varies, try to keep the data
17 * model here the same as on wpcom to facilitate Simple→Atomic moves and
18 * possible future work to recombine the front-ends.
19 */
20
21 // phpcs:disable Universal.Files.SeparateFunctionsFromOO.Mixed -- TODO: Move classes to appropriately-named class files.
22
23 use Automattic\Jetpack\Assets;
24
25 Assets::add_resource_hint(
26 array(
27 '//widgets.wp.com',
28 '//s0.wp.com',
29 '//0.gravatar.com',
30 '//1.gravatar.com',
31 '//2.gravatar.com',
32 ),
33 'dns-prefetch'
34 );
35
36 require_once __DIR__ . '/likes/jetpack-likes-master-iframe.php';
37 require_once __DIR__ . '/likes/jetpack-likes-settings.php';
38
39 /**
40 * Jetpack Like Class
41 */
42 class Jetpack_Likes {
43
44 /**
45 * Jetpack_Likes_Settings object
46 *
47 * @var Jetpack_Likes_Settings
48 */
49 public $settings;
50
51 /**
52 * Initialize class
53 */
54 public static function init() {
55 static $instance = null;
56
57 if ( ! $instance ) {
58 $instance = new Jetpack_Likes();
59 }
60
61 return $instance;
62 }
63
64 /**
65 * Constructs Likes class
66 */
67 public function __construct() {
68 $this->settings = new Jetpack_Likes_Settings();
69
70 // We need to run on wp hook rather than init because we check is_amp_endpoint()
71 // when bootstrapping hooks.
72 add_action( 'wp', array( $this, 'action_init' ), 99 );
73
74 add_action( 'admin_init', array( $this, 'admin_init' ) );
75
76 add_action( 'jetpack_activate_module_likes', array( $this, 'set_social_notifications_like' ) );
77 add_action( 'jetpack_deactivate_module_likes', array( $this, 'delete_social_notifications_like' ) );
78
79 Jetpack::enable_module_configurable( __FILE__ );
80 add_filter( 'jetpack_module_configuration_url_likes', array( $this, 'jetpack_likes_configuration_url' ) );
81 add_action( 'admin_print_scripts-settings_page_sharing', array( $this, 'load_jp_css' ) );
82 add_filter( 'sharing_show_buttons_on_row_start', array( $this, 'configuration_target_area' ) );
83
84 $active = Jetpack::get_active_modules();
85
86 if ( in_array( 'publicize', $active, true ) && ! in_array( 'sharedaddy', $active, true ) ) {
87 // we have a sharing page but not the global options area.
88 add_action( 'pre_admin_screen_sharing', array( $this->settings, 'sharing_block' ), 20 );
89 add_action( 'pre_admin_screen_sharing', array( $this->settings, 'updated_message' ), -10 );
90 }
91
92 if ( ! in_array( 'sharedaddy', $active, true ) ) {
93 add_action( 'admin_init', array( $this->settings, 'process_update_requests_if_sharedaddy_not_loaded' ) );
94 add_action( 'sharing_global_options', array( $this->settings, 'admin_settings_showbuttonon_init' ), 19 );
95 add_action( 'sharing_admin_update', array( $this->settings, 'admin_settings_showbuttonon_callback' ), 19 );
96 add_action( 'admin_init', array( $this->settings, 'add_meta_box' ) );
97 } else {
98 add_filter( 'sharing_meta_box_title', array( $this->settings, 'add_likes_to_sharing_meta_box_title' ) );
99 add_action( 'start_sharing_meta_box_content', array( $this->settings, 'meta_box_content' ) );
100 }
101
102 add_action( 'admin_init', array( $this, 'admin_discussion_likes_settings_init' ) ); // Likes notifications.
103
104 add_action( 'admin_bar_menu', array( $this, 'admin_bar_likes' ), 60 );
105
106 add_action( 'wp_enqueue_scripts', array( $this, 'load_styles_register_scripts' ) );
107
108 add_action( 'save_post', array( $this->settings, 'meta_box_save' ) );
109 add_action( 'edit_attachment', array( $this->settings, 'meta_box_save' ) );
110 add_action( 'sharing_global_options', array( $this->settings, 'admin_settings_init' ), 20 );
111 add_action( 'sharing_admin_update', array( $this->settings, 'admin_settings_callback' ), 20 );
112 }
113
114 /**
115 * Set the social_notifications_like option to `on` when the Likes module is activated.
116 *
117 * @since 3.7.0
118 */
119 public function set_social_notifications_like() {
120 update_option( 'social_notifications_like', 'on' );
121 }
122
123 /**
124 * Delete the social_notifications_like option that was set to `on` on module activation.
125 *
126 * @since 3.7.0
127 */
128 public function delete_social_notifications_like() {
129 delete_option( 'social_notifications_like' );
130 }
131
132 /**
133 * Overrides default configuration url
134 *
135 * @uses admin_url
136 * @return string module settings URL
137 */
138 public function jetpack_likes_configuration_url() {
139 return admin_url( 'options-general.php?page=sharing#likes' );
140 }
141
142 /**
143 * Loads Jetpack's CSS on the sharing page so we can use .jetpack-targetable
144 */
145 public function load_jp_css() {
146 /**
147 * Do we really need `admin_styles`? With the new admin UI, it's breaking some bits.
148 * Jetpack::init()->admin_styles();
149 */
150 }
151
152 /**
153 * Load scripts and styles for front end.
154 */
155 public function load_styles_register_scripts() {
156 wp_enqueue_style( 'jetpack_likes', plugins_url( 'likes/style.css', __FILE__ ), array(), JETPACK__VERSION );
157 wp_register_script(
158 'jetpack_likes_queuehandler',
159 Assets::get_file_url_for_environment(
160 '_inc/build/likes/queuehandler.min.js',
161 'modules/likes/queuehandler.js'
162 ),
163 array(),
164 JETPACK__VERSION,
165 true
166 );
167 }
168
169 /**
170 * Adds in the jetpack-targetable class so when we visit sharing#likes our like settings get highlighted by a yellow box
171 *
172 * @param string $html row heading for the sharedaddy "which page" setting.
173 * @return string $html with the jetpack-targetable class and likes id. tbody gets closed after the like settings
174 */
175 public function configuration_target_area( $html = '' ) {
176 $html = "<tbody id='likes' class='jetpack-targetable'>" . $html;
177 return $html;
178 }
179
180 /**
181 * Options to be added to the discussion page (see also admin_settings_init, etc below for Sharing settings page)
182 */
183 public function admin_discussion_likes_settings_init() {
184 // Add a temporary section, until we can move the setting out of there and with the rest of the email notification settings.
185 add_settings_section( 'likes-notifications', __( 'Likes Notifications', 'jetpack' ), array( $this, 'admin_discussion_likes_settings_section' ), 'discussion' );
186 add_settings_field( 'social-notifications', __( 'Email me whenever', 'jetpack' ), array( $this, 'admin_discussion_likes_settings_field' ), 'discussion', 'likes-notifications' );
187 // Register the setting.
188 register_setting( 'discussion', 'social_notifications_like', array( $this, 'admin_discussion_likes_settings_validate' ) );
189 }
190
191 /** Add email notification options to WordPress discussion settings */
192 public function admin_discussion_likes_settings_section() {
193 // Atypical usage here. We emit jquery to move likes notification checkbox to be with the rest of the email notification settings.
194 ?>
195 <script type="text/javascript">
196 jQuery( function( $ ) {
197 var table = $( '#social_notifications_like' ).parents( 'table:first' ),
198 header = table.prevAll( 'h2:first' ),
199 newParent = $( '#moderation_notify' ).parent( 'label' ).parent();
200
201 if ( !table.length || !header.length || !newParent.length ) {
202 return;
203 }
204
205 newParent.append( '<br/>' ).append( table.end().parent( 'label' ).siblings().andSelf() );
206 header.remove();
207 table.remove();
208 } );
209 </script>
210 <?php
211 }
212
213 /** Check if email notifications for likes is on or off.
214 *
215 * @param string $option - which option we're checking (social_notifications_like).
216 */
217 public function admin_likes_get_option( $option ) {
218 $option_setting = get_option( $option, 'on' );
219
220 return (int) ( 'on' === $option_setting );
221 }
222
223 /** Display email notification for likes setting in WordPress' discussion settings. */
224 public function admin_discussion_likes_settings_field() {
225 $like = $this->admin_likes_get_option( 'social_notifications_like' );
226 ?>
227 <label><input type="checkbox" id="social_notifications_like" name="social_notifications_like" value="1" <?php checked( $like ); ?> /> <?php esc_html_e( 'Someone likes one of my posts', 'jetpack' ); ?></label>
228 <?php
229 }
230
231 /**
232 * Validate email notification settings.
233 *
234 * @param string $input - determines if checbox is on or off.
235 */
236 public function admin_discussion_likes_settings_validate( $input ) {
237 // If it's not set (was unchecked during form submission) or was set to off (during option update), return 'off'.
238 if ( ! $input || 'off' === $input ) {
239 return 'off';
240 }
241 // Otherwise return 'on'.
242 return 'on';
243 }
244
245 /** Initialize admin settings */
246 public function admin_init() {
247 add_filter( 'manage_posts_columns', array( $this, 'add_like_count_column' ) );
248 add_filter( 'manage_pages_columns', array( $this, 'add_like_count_column' ) );
249 add_action( 'manage_posts_custom_column', array( $this, 'likes_edit_column' ), 10, 2 );
250 add_action( 'manage_pages_custom_column', array( $this, 'likes_edit_column' ), 10, 2 );
251 add_action( 'admin_print_styles-edit.php', array( $this, 'load_admin_css' ) );
252 add_action( 'admin_print_scripts-edit.php', array( $this, 'enqueue_admin_scripts' ) );
253 }
254
255 /** Initialize action */
256 public function action_init() {
257 /*
258 * Only check if the module is enabled here because
259 * we are not currently in The Loop and do not yet have access to check
260 * the switch_like_status post meta flag for the post to be loaded.
261 */
262 if ( is_admin() || ! $this->settings->is_likes_module_enabled() ) {
263 return;
264 }
265
266 if ( ( defined( 'XMLRPC_REQUEST' ) && XMLRPC_REQUEST ) ||
267 ( defined( 'APP_REQUEST' ) && APP_REQUEST ) ||
268 ( defined( 'REST_API_REQUEST' ) && REST_API_REQUEST ) ||
269 ( defined( 'COOKIE_AUTH_REQUEST' ) && COOKIE_AUTH_REQUEST ) ||
270 ( defined( 'JABBER_SERVER' ) && JABBER_SERVER ) ) {
271 return;
272 }
273
274 if (
275 class_exists( 'Jetpack_AMP_Support' )
276 && Jetpack_AMP_Support::is_amp_request()
277 ) {
278 return;
279 }
280
281 add_filter( 'the_content', array( $this, 'post_likes' ), 30, 1 );
282 add_filter( 'the_excerpt', array( $this, 'post_likes' ), 30, 1 );
283 }
284
285 /**
286 * Load the CSS needed for the wp-admin area.
287 */
288 public function load_admin_css() {
289 ?>
290 <style type="text/css">
291 .vers img { display: none; }
292 .metabox-prefs .vers img { display: inline; }
293 .fixed .column-likes { width: 5.5em; padding: 8px 0; text-align: left; }
294 .fixed .column-stats { width: 5em; }
295 .fixed .column-likes .post-com-count {
296 -webkit-box-sizing: border-box;
297 -moz-box-sizing: border-box;
298 box-sizing: border-box;
299 display: inline-block;
300 padding: 0 8px;
301 height: 2em;
302 margin-top: 5px;
303 -webkit-border-radius: 5px;
304 border-radius: 5px;
305 background-color: #787c82;
306 color: #FFF;
307 font-size: 11px;
308 line-height: 21px;
309 }
310 .fixed .column-likes .post-com-count::after { border: none !important; }
311 .fixed .column-likes .post-com-count:hover { background-color: #2271b1; }
312 .fixed .column-likes .vers:before {
313 font: normal 20px/1 dashicons;
314 content: '\f155';
315 speak: none;
316 -webkit-font-smoothing: antialiased;
317 -moz-osx-font-smoothing: grayscale;
318 }
319 @media screen and (max-width: 782px) {
320 .fixed .column-likes {
321 display: none;
322 }
323 }
324 </style>
325 <?php
326 }
327
328 /**
329 * Load the JS required for loading the like counts.
330 */
331 public function enqueue_admin_scripts() {
332 if ( empty( $_GET['post_type'] ) || 'post' === $_GET['post_type'] || 'page' === $_GET['post_type'] ) { //phpcs:ignore WordPress.Security.NonceVerification.Recommended
333 wp_enqueue_script(
334 'likes-post-count',
335 Assets::get_file_url_for_environment(
336 '_inc/build/likes/post-count.min.js',
337 'modules/likes/post-count.js'
338 ),
339 array( 'jquery' ),
340 JETPACK__VERSION,
341 $in_footer = false
342 );
343 wp_enqueue_script(
344 'likes-post-count-jetpack',
345 Assets::get_file_url_for_environment(
346 '_inc/build/likes/post-count-jetpack.min.js',
347 'modules/likes/post-count-jetpack.js'
348 ),
349 array( 'jquery', 'likes-post-count' ),
350 JETPACK__VERSION,
351 $in_footer = false
352 );
353 }
354 }
355
356 /**
357 * Add "Likes" column data to the post edit table in wp-admin.
358 *
359 * @param string $column_name - name of the column.
360 * @param int $post_id - the post id.
361 */
362 public function likes_edit_column( $column_name, $post_id ) {
363 if ( 'likes' === $column_name ) {
364
365 $blog_id = Jetpack_Options::get_option( 'id' );
366
367 $permalink = get_permalink( get_the_ID() );
368 ?>
369 <a title="" data-post-id="<?php echo (int) $post_id; ?>" class="post-com-count post-like-count" id="post-like-count-<?php echo (int) $post_id; ?>" data-blog-id="<?php echo (int) $blog_id; ?>" href="<?php echo esc_url( $permalink ); ?>#like-<?php echo (int) $post_id; ?>">
370 <span class="comment-count">0</span>
371 </a>
372 <?php
373 }
374 }
375
376 /**
377 * Add a "Likes" column header to the post edit table in wp-admin.
378 *
379 * @param array $columns - array of columns in wp-admin.
380 */
381 public function add_like_count_column( $columns ) {
382 $date = $columns['date'];
383 unset( $columns['date'] );
384
385 $columns['likes'] = '<span class="vers"><img title="' . esc_attr__( 'Likes', 'jetpack' ) . '" alt="' . esc_attr__( 'Likes', 'jetpack' ) . '" src="//s0.wordpress.com/i/like-grey-icon.png" /><span class="screen-reader-text">' . __( 'Likes', 'jetpack' ) . '</span></span>';
386 $columns['date'] = $date;
387
388 return $columns;
389 }
390
391 /**
392 * Append like button to content.
393 *
394 * @param string $content - content of the page.
395 */
396 public function post_likes( $content ) {
397 global $wp_current_filter;
398 $post_id = get_the_ID();
399
400 if ( ! is_numeric( $post_id ) || ! $this->settings->is_likes_visible() ) {
401 return $content;
402 }
403
404 // Do not output Likes on requests for ActivityPub requests.
405 if (
406 function_exists( '\Activitypub\is_activitypub_request' )
407 && \Activitypub\is_activitypub_request()
408 ) {
409 return $content;
410 }
411
412 // Ensure we don't display like button on post excerpts that are hooked inside the post content
413 if ( in_array( 'the_excerpt', (array) $wp_current_filter, true ) &&
414 in_array( 'the_content', (array) $wp_current_filter, true ) ) {
415 return $content;
416 }
417
418 $blog_id = Jetpack_Options::get_option( 'id' );
419 $url = home_url();
420 $url_parts = wp_parse_url( $url );
421 $domain = $url_parts['host'];
422
423 // Make sure to include the scripts before the iframe otherwise weird things happen.
424 add_action( 'wp_footer', 'jetpack_likes_master_iframe', 21 );
425
426 /**
427 * If the same post appears more then once on a page the page goes crazy
428 * we need a slightly more unique id / name for the widget wrapper.
429 */
430 $uniqid = uniqid();
431 /**
432 * Enable an alternate Likes layout.
433 *
434 * @since 12.9
435 *
436 * @module likes
437 *
438 * @param bool $new_layout Enable the new Likes layout. False by default.
439 */
440 $new_layout = apply_filters( 'likes_new_layout', true ) ? '&amp;n=1' : '';
441
442 $src = sprintf( 'https://widgets.wp.com/likes/?ver=%1$s#blog_id=%2$d&amp;post_id=%3$d&amp;origin=%4$s&amp;obj_id=%2$d-%3$d-%5$s%6$s', rawurlencode( JETPACK__VERSION ), $blog_id, $post_id, $domain, $uniqid, $new_layout );
443 $name = sprintf( 'like-post-frame-%1$d-%2$d-%3$s', $blog_id, $post_id, $uniqid );
444 $wrapper = sprintf( 'like-post-wrapper-%1$d-%2$d-%3$s', $blog_id, $post_id, $uniqid );
445 $headline = sprintf(
446 /** This filter is already documented in modules/sharedaddy/sharing-service.php */
447 apply_filters( 'jetpack_sharing_headline_html', '<h3 class="sd-title">%s</h3>', esc_html__( 'Like this:', 'jetpack' ), 'likes' ),
448 esc_html__( 'Like this:', 'jetpack' )
449 );
450
451 $title = esc_html__( 'Like or Reblog', 'jetpack' );
452
453 $html = "<div class='sharedaddy sd-block sd-like jetpack-likes-widget-wrapper jetpack-likes-widget-unloaded' id='$wrapper' data-src='$src' data-name='$name' data-title='$title'>";
454 $html .= $headline;
455 $html .= "<div class='likes-widget-placeholder post-likes-widget-placeholder' style='height: 55px;'><span class='button'><span>" . esc_html__( 'Like', 'jetpack' ) . '</span></span> <span class="loading">' . esc_html__( 'Loading...', 'jetpack' ) . '</span></div>';
456 $html .= "<span class='sd-text-color'></span><a class='sd-link-color'></a>";
457 $html .= '</div>';
458
459 // Let's make sure that the script is enqueued.
460 wp_enqueue_script( 'jetpack_likes_queuehandler' );
461
462 return $content . $html;
463 }
464
465 /** Checks if admin bar is visible.*/
466 public function is_admin_bar_button_visible() {
467 global $wp_admin_bar;
468
469 if ( ! is_object( $wp_admin_bar ) ) {
470 return false;
471 }
472
473 if ( ( ! is_singular( 'post' ) && ! is_attachment() && ! is_page() ) ) {
474 return false;
475 }
476
477 if ( ! $this->settings->is_likes_visible() ) {
478 return false;
479 }
480
481 if ( ! $this->settings->is_post_likeable() ) {
482 return false;
483 }
484
485 /**
486 * Filters whether the Like button is enabled in the admin bar.
487 *
488 * @module likes
489 *
490 * @since 2.2.0
491 *
492 * @param bool true Should the Like button be visible in the Admin bar. Default to true.
493 */
494 return (bool) apply_filters( 'jetpack_admin_bar_likes_enabled', true );
495 }
496
497 /** Adds like section in admin bar. */
498 public function admin_bar_likes() {
499 global $wp_admin_bar;
500
501 $post_id = get_the_ID();
502
503 if ( ! is_numeric( $post_id ) || ! $this->is_admin_bar_button_visible() ) {
504 return;
505 }
506
507 $protocol = 'http';
508 if ( is_ssl() ) {
509 $protocol = 'https';
510 }
511 $blog_id = Jetpack_Options::get_option( 'id' );
512 $url = home_url();
513 $url_parts = wp_parse_url( $url );
514 $domain = $url_parts['host'];
515
516 // Make sure to include the scripts before the iframe otherwise weird things happen.
517 add_action( 'wp_footer', 'jetpack_likes_master_iframe', 21 );
518
519 $src = sprintf( 'https://widgets.wp.com/likes/?ver=%1$s#blog_id=%3$d&amp;post_id=%4$d&amp;origin=%2$s://%5$s', rawurlencode( JETPACK__VERSION ), $protocol, $blog_id, $post_id, $domain );
520
521 $html = "<iframe class='admin-bar-likes-widget jetpack-likes-widget' scrolling='no' frameBorder='0' name='admin-bar-likes-widget' src='$src'></iframe>";
522
523 $node = array(
524 'id' => 'admin-bar-likes-widget',
525 'meta' => array(
526 'html' => $html,
527 ),
528 );
529
530 $wp_admin_bar->add_node( $node );
531 }
532 }
533
534 /**
535 * Callback to get the value for the jetpack_likes_enabled field.
536 *
537 * Warning: this behavior is somewhat complicated!
538 * When the switch_like_status post_meta is unset, we follow the global setting in Sharing.
539 * When it is set to 0, we disable likes on the post, regardless of the global setting.
540 * When it is set to 1, we enable likes on the post, regardless of the global setting.
541 *
542 * @param array $post - post data we're checking.
543 */
544 function jetpack_post_likes_get_value( array $post ) {
545 $post_likes_switched = get_post_meta( $post['id'], 'switch_like_status', true );
546
547 /** This filter is documented in modules/jetpack-likes-settings.php */
548 $sitewide_likes_enabled = (bool) apply_filters( 'wpl_is_enabled_sitewide', ! get_option( 'disabled_likes' ) );
549
550 // An empty string: post meta was not set, so go with the global setting.
551 if ( '' === $post_likes_switched ) {
552 return $sitewide_likes_enabled;
553 } elseif ( '0' === $post_likes_switched ) { // User overrode the global setting to disable likes.
554 return false;
555 } elseif ( '1' === $post_likes_switched ) { // User overrode the global setting to enable likes.
556 return true;
557 }
558 // No default fallback, let's stay explicit.
559 }
560
561 /**
562 * Callback to set switch_like_status post_meta when jetpack_likes_enabled is updated.
563 *
564 * Warning: this behavior is somewhat complicated!
565 * When the switch_like_status post_meta is unset, we follow the global setting in Sharing.
566 * When it is set to 0, we disable likes on the post, regardless of the global setting.
567 * When it is set to 1, we enable likes on the post, regardless of the global setting.
568 *
569 * @param bool $enable_post_likes - checks if post likes are enabled.
570 * @param object $post_object - object containing post data.
571 */
572 function jetpack_post_likes_update_value( $enable_post_likes, $post_object ) {
573 /** This filter is documented in modules/jetpack-likes-settings.php */
574 $sitewide_likes_enabled = (bool) apply_filters( 'wpl_is_enabled_sitewide', ! get_option( 'disabled_likes' ) );
575
576 $should_switch_status = $enable_post_likes !== $sitewide_likes_enabled;
577
578 if ( $should_switch_status ) {
579 // Set the meta to 0 if the user wants to disable likes, 1 if user wants to enable.
580 $switch_like_status = ( $enable_post_likes ? 1 : 0 );
581 return update_post_meta( $post_object->ID, 'switch_like_status', $switch_like_status );
582 } else {
583 // Unset the meta otherwise.
584 return delete_post_meta( $post_object->ID, 'switch_like_status' );
585 }
586 }
587
588 /**
589 * Add Likes post_meta to the REST API Post response.
590 *
591 * @action rest_api_init
592 * @uses register_rest_field
593 * @link https://developer.wordpress.org/rest-api/extending-the-rest-api/modifying-responses/
594 */
595 function jetpack_post_likes_register_rest_field() {
596 $post_types = get_post_types( array( 'public' => true ) );
597 foreach ( $post_types as $post_type ) {
598 register_rest_field(
599 $post_type,
600 'jetpack_likes_enabled',
601 array(
602 'get_callback' => 'jetpack_post_likes_get_value',
603 'update_callback' => 'jetpack_post_likes_update_value',
604 'schema' => array(
605 'description' => __( 'Are Likes enabled?', 'jetpack' ),
606 'type' => 'boolean',
607 ),
608 )
609 );
610
611 /**
612 * Ensures all public internal post-types support `likes`
613 * This feature support flag is used by the REST API and Gutenberg.
614 */
615 add_post_type_support( $post_type, 'jetpack-post-likes' );
616 }
617 }
618
619 // Add Likes post_meta to the REST API Post response.
620 add_action( 'rest_api_init', 'jetpack_post_likes_register_rest_field' );
621
622 // Some CPTs (e.g. Jetpack portfolios and testimonials) get registered with
623 // restapi_theme_init because they depend on theme support, so let's also hook to that.
624 add_action( 'restapi_theme_init', 'jetpack_post_likes_register_rest_field', 20 );
625
626 Jetpack_Likes::init();
627