PluginProbe ʕ •ᴥ•ʔ
Jetpack – WP Security, Backup, Speed, & Growth / 16.0-beta
Jetpack – WP Security, Backup, Speed, & Growth v16.0-beta
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 / widgets / goodreads.php
jetpack / modules / widgets Last commit date
authors 7 months ago contact-info 7 months ago eu-cookie-law 7 months ago facebook-likebox 11 years ago flickr 7 months ago gallery 7 months ago goodreads 7 months ago google-translate 1 year ago image-widget 7 months ago instagram 4 months ago internet-defense-league 1 year ago milestone 4 months ago my-community 7 months ago social-icons 4 months ago social-media-icons 7 months ago top-posts 7 months ago wordpress-post-widget 1 week ago authors.php 7 months ago blog-stats.php 7 months ago class-jetpack-eu-cookie-law-widget.php 1 month ago class-jetpack-instagram-widget.php 6 months ago contact-info.php 1 month ago customizer-controls.css 7 months ago customizer-utils.js 1 year ago facebook-likebox.php 1 month ago flickr.php 7 months ago gallery.php 1 month ago goodreads.php 1 month ago google-translate.php 1 month ago gravatar-profile.css 7 months ago gravatar-profile.php 1 month ago image-widget.php 7 months ago internet-defense-league.php 7 months ago mailchimp.php 7 months ago milestone.php 7 months ago my-community.php 1 month ago rsslinks-widget.php 1 week ago simple-payments.php 7 months ago social-icons.php 1 month ago social-media-icons.php 7 months ago top-posts.php 1 month ago twitter-timeline-admin.js 1 year ago twitter-timeline.php 1 week ago upcoming-events.php 7 months ago wordpress-post-widget.php 7 months ago
goodreads.php
240 lines
1 <?php // phpcs:ignore WordPress.Files.FileName.InvalidClassFileName
2
3 if ( ! defined( 'ABSPATH' ) ) {
4 exit( 0 );
5 }
6
7 // phpcs:disable Universal.Files.SeparateFunctionsFromOO.Mixed -- TODO: Move classes to appropriately-named class files.
8
9 add_action( 'widgets_init', 'jetpack_goodreads_widget_init' );
10 /**
11 * Register the widget for use in Appearance -> Widgets
12 */
13 function jetpack_goodreads_widget_init() {
14 register_widget( 'WPCOM_Widget_Goodreads' );
15 }
16
17 /**
18 * Goodreads widget class
19 * Display a user's Goodreads shelf.
20 * Customize user_id, title, and shelf
21 */
22 class WPCOM_Widget_Goodreads extends WP_Widget {
23 /**
24 * Widget ID based on Goodreads user ID and shelf.
25 *
26 * @var int
27 */
28 private $goodreads_widget_id = 0;
29
30 /**
31 * WPCOM_Widget_Goodreads constructor.
32 */
33 public function __construct() {
34 parent::__construct(
35 'wpcom-goodreads',
36 /** This filter is documented in modules/widgets/facebook-likebox.php */
37 apply_filters( 'jetpack_widget_name', __( 'Goodreads', 'jetpack' ) ),
38 array(
39 'classname' => 'widget_goodreads',
40 'description' => __( 'Display your books from Goodreads', 'jetpack' ),
41 'customize_selective_refresh' => true,
42 'show_instance_in_rest' => true,
43 )
44 );
45 // For user input sanitization and display.
46 $this->shelves = array(
47 'read' => _x( 'Read', 'past participle: books I have read', 'jetpack' ),
48 'currently-reading' => __( 'Currently Reading', 'jetpack' ),
49 'to-read' => _x( 'To Read', 'my list of books to read', 'jetpack' ),
50 );
51
52 add_filter( 'widget_types_to_hide_from_legacy_widget_block', array( $this, 'hide_widget_in_block_editor' ) );
53 }
54
55 /**
56 * Remove the "Goodreads" widget from the Legacy Widget block
57 *
58 * @param array $widget_types List of widgets that are currently removed from the Legacy Widget block.
59 * @return array $widget_types New list of widgets that will be removed.
60 */
61 public function hide_widget_in_block_editor( $widget_types ) {
62 $widget_types[] = 'wpcom-goodreads';
63 return $widget_types;
64 }
65
66 /**
67 * Enqueue widget styles.
68 */
69 public function enqueue_style() {
70 wp_enqueue_style(
71 'goodreads-widget',
72 plugins_url( 'goodreads/css/goodreads.css', __FILE__ ),
73 array(),
74 JETPACK__VERSION
75 );
76 wp_style_add_data( 'goodreads-widget', 'rtl', 'replace' );
77 }
78
79 /**
80 * Display the widget.
81 *
82 * @param array $args Display arguments including before_title, after_title, before_widget, and after_widget.
83 * @param array $instance The settings for the particular instance of the widget.
84 */
85 public function widget( $args, $instance ) {
86 /** This action is documented in modules/widgets/gravatar-profile.php */
87 do_action( 'jetpack_stats_extra', 'widget_view', 'goodreads' );
88
89 /** This filter is documented in core/src/wp-includes/default-widgets.php */
90 $title = apply_filters( 'widget_title', $instance['title'] ?? '' );
91
92 if ( empty( $instance['user_id'] ) || 'invalid' === $instance['user_id'] ) {
93 if ( current_user_can( 'edit_theme_options' ) ) {
94 echo $args['before_widget']; // phpcs:ignore WordPress.Security.EscapeOutput.OutputNotEscaped
95 echo '<p>' . sprintf(
96 wp_kses(
97 /* translators: %1$s: link to the widget settings page. %2$s: support article URL for Goodreads widget. */
98 __( 'You need to enter your numeric user ID for the <a href="%1$s">Goodreads Widget</a> to work correctly. <a href="%2$s" target="_blank">Full instructions</a>.', 'jetpack' ),
99 array(
100 'a' => array(
101 'href' => array(),
102 'target' => array(),
103 ),
104 )
105 ),
106 esc_url( admin_url( 'widgets.php' ) ),
107 'https://wordpress.com/support/widgets/goodreads-widget/#set-up-the-widget'
108 ) . '</p>';
109 echo $args['after_widget']; // phpcs:ignore WordPress.Security.EscapeOutput.OutputNotEscaped
110 }
111 return;
112 }
113
114 if ( ! array_key_exists( $instance['shelf'], $this->shelves ) ) {
115 return;
116 }
117
118 // Enqueue front end assets.
119 $this->enqueue_style();
120
121 $instance['user_id'] = absint( $instance['user_id'] );
122
123 // Set widget ID based on shelf.
124 $this->goodreads_widget_id = $instance['user_id'] . '_' . $instance['shelf'];
125 $this->goodreads_widget_id = str_replace( '-', '_', $this->goodreads_widget_id ); // Goodreads' custom widget does not like dashes.
126
127 if ( empty( $title ) ) {
128 $title = esc_html__( 'Goodreads', 'jetpack' );
129 }
130
131 echo $args['before_widget']; // phpcs:ignore WordPress.Security.EscapeOutput.OutputNotEscaped
132 echo $args['before_title'] . $title . $args['after_title']; // phpcs:ignore WordPress.Security.EscapeOutput.OutputNotEscaped
133
134 $goodreads_url = 'https://www.goodreads.com/review/custom_widget/' . rawurlencode( (string) $instance['user_id'] ) . '.' . rawurlencode( $instance['title'] ) . ':%20' . rawurlencode( $instance['shelf'] ) . '?cover_position=&cover_size=small&num_books=5&order=d&shelf=' . rawurlencode( $instance['shelf'] ) . '&sort=date_added&widget_bg_transparent=&widget_id=' . rawurlencode( $this->goodreads_widget_id );
135
136 echo '<div class="jetpack-goodreads-legacy-widget gr_custom_widget" id="gr_custom_widget_' . esc_attr( $this->goodreads_widget_id ) . '"></div>' . "\n";
137 echo '<script src="' . esc_url( $goodreads_url ) . '"></script>' . "\n"; // phpcs:ignore WordPress.WP.EnqueuedResources.NonEnqueuedScript
138
139 echo $args['after_widget']; // phpcs:ignore WordPress.Security.EscapeOutput.OutputNotEscaped
140 }
141
142 /**
143 * Check if given Goodreads user ID exists.
144 *
145 * @param string $user_id User ID.
146 */
147 public function goodreads_user_id_exists( $user_id ) {
148 $url = "https://www.goodreads.com/user/show/$user_id/";
149 $response = wp_remote_head(
150 $url,
151 array(
152 'httpversion' => '1.1',
153 'timeout' => 10,
154 'redirection' => 2,
155 )
156 );
157 if ( 200 === wp_remote_retrieve_response_code( $response ) ) {
158 return true;
159 } else {
160 return false;
161 }
162 }
163
164 /**
165 * Update widget.
166 *
167 * @see WP_Widget::update()
168 *
169 * @param array $new_instance New widget instance data.
170 * @param array $old_instance Old widget instance data.
171 */
172 public function update( $new_instance, $old_instance ) {
173 $instance = $old_instance;
174
175 $instance['user_id'] = trim( wp_kses( stripslashes( $new_instance['user_id'] ), array() ) );
176 if ( ! empty( $instance['user_id'] ) && ( ! isset( $old_instance['user_id'] ) || $instance['user_id'] !== $old_instance['user_id'] ) ) {
177 if ( ! $this->goodreads_user_id_exists( $instance['user_id'] ) ) {
178 $instance['user_id'] = 'invalid';
179 }
180 }
181 $instance['title'] = wp_kses( stripslashes( $new_instance['title'] ), array() );
182 $shelf = wp_kses( stripslashes( $new_instance['shelf'] ), array() );
183 if ( array_key_exists( $shelf, $this->shelves ) ) {
184 $instance['shelf'] = $shelf;
185 }
186
187 return $instance;
188 }
189
190 /**
191 * Outputs the widget settings form.
192 *
193 * @param array $instance Current settings.
194 * @return string|void
195 */
196 public function form( $instance ) {
197 // Defaults.
198 $instance = wp_parse_args(
199 (array) $instance,
200 array(
201 'user_id' => '',
202 'title' => 'Goodreads',
203 'shelf' => 'read',
204 )
205 );
206
207 echo '<p><label for="' . esc_attr( $this->get_field_id( 'title' ) ) . '">' . esc_html__( 'Title:', 'jetpack' ) . '
208 <input class="widefat" id="' . esc_attr( $this->get_field_id( 'title' ) ) . '" name="' . esc_attr( $this->get_field_name( 'title' ) ) . '" type="text" value="' . esc_attr( $instance['title'] ) . '" />
209 </label></p>
210 <p><label for="' . esc_attr( $this->get_field_id( 'user_id' ) ) . '">';
211 printf(
212 wp_kses(
213 /* translators: %s: support article URL for Goodreads widget. */
214 __( 'Goodreads numeric user ID <a href="%s" target="_blank">(instructions)</a>:', 'jetpack' ),
215 array(
216 'a' => array(
217 'href' => array(),
218 'target' => array(),
219 ),
220 )
221 ),
222 'https://wordpress.com/support/widgets/goodreads-widget/#set-up-the-widget'
223 );
224 if ( 'invalid' === $instance['user_id'] ) {
225 printf( '<br /><small class="error">%s</small>&nbsp;', esc_html( __( 'Invalid User ID, please verify and re-enter your Goodreads numeric user ID.', 'jetpack' ) ) );
226 $instance['user_id'] = '';
227 }
228 echo '<input class="widefat" id="' . esc_attr( $this->get_field_id( 'user_id' ) ) . '" name="' . esc_attr( $this->get_field_name( 'user_id' ) ) . '" type="text" value="' . esc_attr( $instance['user_id'] ) . '" />
229 </label></p>
230 <p><label for="' . esc_attr( $this->get_field_id( 'shelf' ) ) . '">' . esc_html__( 'Shelf:', 'jetpack' ) . '
231 <select class="widefat" id="' . esc_attr( $this->get_field_id( 'shelf' ) ) . '" name="' . esc_attr( $this->get_field_name( 'shelf' ) ) . '" >';
232 foreach ( $this->shelves as $_shelf_value => $_shelf_display ) {
233 echo "\t<option value='" . esc_attr( $_shelf_value ) . "'" . selected( $_shelf_value, $instance['shelf'], false ) . '>' . $_shelf_display . "</option>\n"; // phpcs:ignore WordPress.Security.EscapeOutput.OutputNotEscaped
234 }
235 echo '</select>
236 </label></p>
237 ';
238 }
239 }
240