PluginProbe
WP Approve User / 6
WP Approve User v6
13 12 trunk 1.0 1.1.0 1.1.1 10 11 2.0.0 2.1.0 2.1.1 2.2.0 2.2.1 2.2.2 2.2.3 2.4.0 3 4 5 6 7 8 9
wp-approve-user / wp-approve-user.php

wp-approve-user.php in WP Approve User 6, at wp-approve-user.php

1,110 lines 29.3 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2 /**
3 * Plugin Name: WP Approve User
4 * Plugin URI: http://en.wp.obenland.it/wp-approve-user/#utm_source=wordpress&utm_medium=plugin&utm_campaign=wp-approve-user
5 * Description: Adds action links to user table to approve or unapprove user registrations.
6 * Version: 6
7 * Author: Konstantin Obenland
8 * Author URI: http://en.wp.obenland.it/#utm_source=wordpress&utm_medium=plugin&utm_campaign=wp-approve-user
9 * Text Domain: wp-approve-user
10 * Domain Path: /lang
11 * License: GPLv2
12 *
13 * @package WP Approve User
14 */
15
16 if ( ! get_option( 'users_can_register' ) ) {
17 require_once 'noop.php';
18 return;
19 }
20
21
22 if ( ! class_exists( 'Obenland_Wp_Plugins_V4' ) ) {
23 require_once 'obenland-wp-plugins.php';
24 }
25
26 /**
27 * Class Obenland_Wp_Approve_User.
28 */
29 class Obenland_Wp_Approve_User extends Obenland_Wp_Plugins_V4 {
30
31 /**
32 * Class instance.
33 *
34 * @since 1.1.0 - 12.02.2012
35 * @access public
36 * @static
37 *
38 * @var Obenland_Wp_Approve_User
39 */
40 public static $instance;
41
42 /**
43 * The plugin options.
44 *
45 * @author Konstantin Obenland
46 * @since 2.0.0 - 31.03.2012
47 * @access protected
48 *
49 * @var array
50 */
51 protected $options;
52
53 /**
54 * Users flagged as unapproved.
55 *
56 * @author Konstantin Obenland
57 * @since 2.2.0 - 30.03.2013
58 * @access protected
59 *
60 * @var array
61 */
62 protected $unapproved_users = array();
63
64
65 /**
66 * Constructor
67 *
68 * @author Konstantin Obenland
69 * @since 1.0 - 29.01.2012
70 * @access public
71 */
72 public function __construct() {
73 parent::__construct( array(
74 'textdomain' => 'wp-approve-user',
75 'plugin_path' => __FILE__,
76 'donate_link_id' => 'G65Y5CM3HVRNY',
77 ) );
78
79 self::$instance = $this;
80 $this->options = wp_parse_args(
81 get_option( $this->textdomain, array() ),
82 $this->default_options()
83 );
84
85 if ( is_admin() ) {
86 $this->unapproved_users = get_users( array(
87 'meta_key' => 'wp-approve-user',
88 'meta_value' => false,
89 ) );
90 }
91
92 load_plugin_textdomain( 'wp-approve-user', false, 'wp-approve-user/lang' );
93
94 $this->hook( 'plugins_loaded' );
95 }
96
97
98 /**
99 * Approves all existing users.
100 *
101 * @author Konstantin Obenland
102 * @since 1.0 - 29.01.2012
103 * @access public
104 * @static
105 *
106 * @return void
107 */
108 public function activation() {
109 $user_ids = get_users( array(
110 'blog_id' => '',
111 'fields' => 'ID',
112 ) );
113
114 foreach ( $user_ids as $user_id ) {
115 update_user_meta( $user_id, 'wp-approve-user', true );
116 update_user_meta( $user_id, 'wp-approve-user-mail-sent', true );
117 }
118 }
119
120
121 /**
122 * Hooks in all the hooks :)
123 *
124 * @author Konstantin Obenland
125 * @since 1.1 - 12.02.2012
126 * @access public
127 *
128 * @return void
129 */
130 public function plugins_loaded() {
131 $this->hook( 'user_row_actions' );
132 $this->hook( 'ms_user_row_actions', 'user_row_actions' );
133 $this->hook( 'wp_authenticate_user' );
134 $this->hook( 'user_register' );
135 $this->hook( 'register_new_user', 0 );
136 $this->hook( 'wp_login_errors' );
137 $this->hook( 'shake_error_codes' );
138 $this->hook( 'admin_menu' );
139 $this->hook( 'network_admin_menu', 'admin_menu' );
140
141 $this->hook( 'admin_print_scripts-users.php' );
142 $this->hook( 'admin_print_scripts-site-users.php', 'admin_print_scripts_users_php' );
143 $this->hook( 'admin_print_styles-settings_page_wp-approve-user' );
144
145 $this->hook( 'load-users.php', 'map_action2' );
146 $this->hook( 'load-site-users.php', 'map_action2' );
147 $this->hook( 'admin_action_wpau_approve' );
148 $this->hook( 'admin_action_wpau_bulk_approve' );
149 $this->hook( 'admin_action_wpau_unapprove' );
150 $this->hook( 'admin_action_wpau_bulk_unapprove' );
151 $this->hook( 'admin_action_wpau_update' );
152
153 $this->hook( 'wpau_approve' );
154 $this->hook( 'delete_user' );
155 $this->hook( 'admin_init' );
156
157 if ( is_admin() ) {
158 $this->hook( 'views_users' );
159 $this->hook( 'views_users-network', 'views_users' );
160 $this->hook( 'views_site-users-network', 'views_users' );
161 $this->hook( 'pre_user_query' );
162 }
163 }
164
165
166 /**
167 * Enqueues the script
168 *
169 * @author Konstantin Obenland
170 * @since 1.1 - 12.02.2012
171 * @access public
172 *
173 * @return void
174 */
175 public function admin_print_scripts_users_php() {
176 $plugin_data = get_plugin_data( __FILE__, false, false );
177 $suffix = defined( 'SCRIPT_DEBUG' ) && SCRIPT_DEBUG ? '' : '.min';
178
179 wp_enqueue_script(
180 $this->textdomain,
181 plugins_url( "/js/{$this->textdomain}{$suffix}.js", __FILE__ ),
182 array( 'jquery' ),
183 $plugin_data['Version'],
184 true
185 );
186
187 wp_localize_script( $this->textdomain, 'wp_approve_user', array(
188 'approve' => __( 'Approve', 'wp-approve-user' ),
189 'unapprove' => __( 'Unapprove', 'wp-approve-user' ),
190 ) );
191 }
192
193
194 /**
195 * Enqueues the style on the settings page
196 *
197 * @author Konstantin Obenland
198 * @since 2.0.0 - 10.04.2012
199 * @access public
200 *
201 * @return void
202 */
203 public function admin_print_styles_settings_page_wp_approve_user() {
204 $plugin_data = get_plugin_data( __FILE__, false, false );
205 $suffix = defined( 'SCRIPT_DEBUG' ) && SCRIPT_DEBUG ? '' : '.min';
206
207 wp_enqueue_style(
208 $this->textdomain,
209 plugins_url( "/css/settings-page{$suffix}.css", __FILE__ ),
210 array(),
211 $plugin_data['Version']
212 );
213 }
214
215
216 /**
217 * Adds a link to a list view of unapproved users.
218 *
219 * @author Konstantin Obenland
220 * @since 2.2.0 - 30.03.2013
221 * @access public
222 *
223 * @param array $views List of registered user list views.
224 *
225 * @return array
226 */
227 public function views_users( $views ) {
228 if ( $this->unapproved_users ) {
229 // phpcs:ignore WordPress.CSRF.NonceVerification.NoNonceVerification
230 $site_id = isset( $_REQUEST['id'] ) ? intval( $_REQUEST['id'] ) : 0;
231 $url = 'site-users-network' === get_current_screen()->id ? add_query_arg( array( 'id' => $site_id ), 'site-users.php' ) : 'users.php';
232
233 $views['unapproved'] = sprintf(
234 '<a href="%1$s" class="%2$s">%3$s <span class="count">(%4$s)</span></a>',
235 esc_url( add_query_arg( array( 'role' => 'wpau_unapproved' ), $url ) ),
236 // phpcs:ignore WordPress.CSRF.NonceVerification.NoNonceVerification
237 'wpau_unapproved' === $this->get_role() ? 'current' : '',
238 esc_html__( 'Unapproved', 'wp-approve-users' ),
239 count( $this->unapproved_users )
240 );
241 }
242
243 return $views;
244 }
245
246
247 /**
248 * Resets the user query to handle request for unapproved users only.
249 *
250 * @author Konstantin Obenland
251 * @since 2.2.0 - 30.03.2013
252 * @access public
253 *
254 * @param WP_User_Query $query User query object.
255 *
256 * @return void
257 */
258 public function pre_user_query( $query ) {
259 // phpcs:ignore WordPress.CSRF.NonceVerification.NoNonceVerification, WordPress.VIP.ValidatedSanitizedInput
260 $role = empty( $query->query_vars['role'] ) && isset( $_REQUEST['role'] ) ? $_REQUEST['role'] : $query->query_vars['role'];
261
262 if ( 'wpau_unapproved' === $role ) {
263 unset( $query->query_vars['meta_query'] );
264 $query->query_vars['role'] = '';
265 $query->query_vars['meta_key'] = 'wp-approve-user';
266 $query->query_vars['meta_value'] = false;
267
268 remove_filter( 'pre_user_query', array( $this, 'pre_user_query' ) );
269 $query->prepare_query();
270 }
271 }
272
273
274 /**
275 * Adds the plugin's row actions to the existing ones.
276 *
277 * @author Konstantin Obenland
278 * @since 1.0 - 29.01.2012
279 * @access public
280 *
281 * @param array $actions User action links.
282 * @param WP_User $user_object User object.
283 *
284 * @return array
285 */
286 public function user_row_actions( $actions, $user_object ) {
287 if ( get_current_user_id() !== $user_object->ID && current_user_can( 'edit_user', $user_object->ID ) ) {
288 // phpcs:ignore WordPress.CSRF.NonceVerification.NoNonceVerification
289 $site_id = isset( $_REQUEST['id'] ) ? intval( $_REQUEST['id'] ) : 0;
290 $url = 'site-users-network' === get_current_screen()->id ? add_query_arg( array( 'id' => $site_id ), 'site-users.php' ) : 'users.php';
291
292 if ( get_user_meta( $user_object->ID, 'wp-approve-user', true ) ) {
293 $url = wp_nonce_url( add_query_arg( array(
294 'action' => 'wpau_unapprove',
295 'user' => $user_object->ID,
296 ), $url ), 'wpau-unapprove-users' );
297
298 $actions['wpau-unapprove'] = sprintf( '<a class="submitunapprove" href="%1$s">%2$s</a>', esc_url( $url ), esc_html__( 'Unapprove', 'wp-approve-user' ) );
299
300 } else {
301 $url = wp_nonce_url( add_query_arg( array(
302 'action' => 'wpau_approve',
303 'user' => $user_object->ID,
304 'role' => $this->get_role(),
305 ), $url ), 'wpau-approve-users' );
306
307 $actions['wpau-approve'] = sprintf( '<a class="submitapprove" href="%1$s">%2$s</a>', esc_url( $url ), esc_html__( 'Approve', 'wp-approve-user' ) );
308 }
309 }
310
311 return $actions;
312 }
313
314
315 /**
316 * Checks whether the user is approved. Throws error if not.
317 *
318 * @author Konstantin Obenland
319 * @since 1.0 - 29.01.2012
320 * @access public
321 *
322 * @param WP_User|WP_Error $userdata User object.
323 *
324 * @return WP_User|WP_Error
325 */
326 public function wp_authenticate_user( $userdata ) {
327 if ( ! is_wp_error( $userdata ) && ! get_user_meta( $userdata->ID, 'wp-approve-user', true ) && get_bloginfo( 'admin_email' ) !== $userdata->user_email ) {
328 $userdata = new WP_Error(
329 'wpau_confirmation_error',
330 wp_kses_post( __( '<strong>ERROR:</strong> Your account has to be confirmed by an administrator before you can login.', 'wp-approve-user' ) )
331 );
332 }
333
334 return $userdata;
335 }
336
337
338 /**
339 * Updates user_meta to approve user when created by an Administrator.
340 *
341 * @author Konstantin Obenland
342 * @since 1.1 - 12.02.2012
343 * @access public
344 *
345 * @param int $id User ID.
346 *
347 * @return void
348 */
349 public function user_register( $id ) {
350 update_user_meta( $id, 'wp-approve-user', current_user_can( 'create_users' ) );
351 update_user_meta( $id, 'wp-approve-user-new-registration', true );
352 }
353
354 /**
355 * Fires after a new user registration has been recorded.
356 *
357 * @author Konstantin Obenland
358 * @since 6 - 04.03.2019
359 * @access public
360 *
361 * @param int $user_id ID of the newly registered user.
362 */
363 public function register_new_user( $user_id ) {
364 if ( ! get_user_meta( $user_id, 'wp-approve-user', true ) ) {
365 remove_action( 'register_new_user', 'wp_send_new_user_notifications' );
366 add_action( 'register_new_user', 'wp_new_user_notification' );
367 }
368 }
369
370 /**
371 * Calls actions that depend on the `action` parameter.
372 *
373 * @author Konstantin Obenland
374 * @since 3 - 21.12.2017
375 * @access public
376 */
377 public function map_action2() {
378 // phpcs:disable WordPress.CSRF.NonceVerification.NoNonceVerification, WordPress.VIP.ValidatedSanitizedInput
379
380 if ( ! empty( $_REQUEST['action2'] ) && false !== stripos( $_REQUEST['action2'], 'wpau_' ) ) {
381 do_action( "admin_action_{$_REQUEST['action2']}" );
382 }
383
384 // phpcs:enable WordPress.CSRF.NonceVerification.NoNonceVerification, WordPress.VIP.ValidatedSanitizedInput
385 }
386
387
388 /**
389 * Updates user_meta to approve user.
390 *
391 * @author Konstantin Obenland
392 * @since 1.1 - 12.02.2012
393 * @access public
394 *
395 * @return void
396 */
397 public function admin_action_wpau_approve() {
398 check_admin_referer( 'wpau-approve-users' );
399 $this->approve();
400 }
401
402
403 /**
404 * Bulkupdates user_meta to approve user.
405 *
406 * @author Konstantin Obenland
407 * @since 1.1 - 12.02.2012
408 * @access public
409 *
410 * @return void
411 */
412 public function admin_action_wpau_bulk_approve() {
413 $action = 'users-network' === get_current_screen()->id ? 'bulk-users-network' : 'bulk-users';
414 check_admin_referer( $action );
415
416 $this->set_up_role_context();
417 $this->approve();
418 }
419
420
421 /**
422 * Updates user_meta to unapprove user.
423 *
424 * @author Konstantin Obenland
425 * @since 1.1 - 12.02.2012
426 * @access public
427 *
428 * @return void
429 */
430 public function admin_action_wpau_unapprove() {
431 check_admin_referer( 'wpau-unapprove-users' );
432 $this->unapprove();
433 }
434
435
436 /**
437 * Bulkupdates user_meta to unapprove user.
438 *
439 * @author Konstantin Obenland
440 * @since 1.1 - 12.02.2012
441 * @access public
442 *
443 * @return void
444 */
445 public function admin_action_wpau_bulk_unapprove() {
446 $action = 'users-network' === get_current_screen()->id ? 'bulk-users-network' : 'bulk-users';
447 check_admin_referer( $action );
448
449 $this->set_up_role_context();
450 $this->unapprove();
451 }
452
453
454 /**
455 * Adds the update message to the admin notices queue.
456 *
457 * @author Konstantin Obenland
458 * @since 1.1 - 12.02.2012
459 * @access public
460 *
461 * @return void
462 */
463 public function admin_action_wpau_update() {
464 // phpcs:disable WordPress.VIP.ValidatedSanitizedInput, WordPress.CSRF.NonceVerification.NoNonceVerification
465 if ( empty( $_REQUEST['update'] ) ) {
466 return;
467 }
468
469 $count = absint( $_REQUEST['count'] );
470
471 switch ( $_REQUEST['update'] ) {
472 case 'wpau-approved':
473 /* translators: Number of users. */
474 $message = esc_html( _n( '%d User approved.', '%d users approved.', $count, 'wp-approve-user' ) );
475 break;
476
477 case 'wpau-unapproved':
478 /* translators: Number of users. */
479 $message = esc_html( _n( '%d User unapproved.', '%d users unapproved.', $count, 'wp-approve-user' ) );
480 break;
481
482 default:
483 $message = apply_filters( 'wpau_update_message_handler', '', $_REQUEST['update'] );
484 }
485
486 if ( isset( $message ) ) {
487 add_settings_error(
488 $this->textdomain,
489 esc_attr( $_REQUEST['update'] ),
490 sprintf( $message, $count ),
491 'updated'
492 );
493
494 $this->hook( 'all_admin_notices' );
495 }
496
497 // Prevent other admin action handlers from trying to handle our action.
498 $_REQUEST['action'] = -1;
499
500 // phpcs:enable WordPress.VIP.ValidatedSanitizedInput, WordPress.CSRF.NonceVerification.NoNonceVerification
501 }
502
503 /**
504 * Filters the login page errors.
505 *
506 * @author Konstantin Obenland
507 * @since 6 - 04.03.2019
508 * @access public
509 *
510 * @param \WP_Error $errors WP Error object.
511 * @return \WP_Error
512 */
513 public function wp_login_errors( $errors ) {
514 if ( in_array( 'registered', $errors->get_error_codes(), true ) ) {
515 $message = __( 'Registration complete. You will receive an email once your registration was confirmed by an administrator.', 'wp-approve-user' );
516 $errors->remove( 'registered' );
517 $errors->add( 'registered', $message, 'message' );
518 }
519
520 return $errors;
521 }
522
523
524 /**
525 * Adds our error code to make the login form shake :)
526 *
527 * @author Konstantin Obenland
528 * @since 1.0 - 29.01.2012
529 * @access public
530 *
531 * @param array $shake_error_codes Error codes that trigger form shaking.
532 *
533 * @return array Shake error codes
534 */
535 public function shake_error_codes( $shake_error_codes ) {
536 $shake_error_codes[] = 'wpau_confirmation_error';
537
538 return $shake_error_codes;
539 }
540
541
542 /**
543 * Enhances the User menu item to reflect the amount of unapproved users.
544 *
545 * @author Konstantin Obenland
546 * @since 1.1 - 12.02.2012
547 * @access public
548 *
549 * @return void
550 */
551 public function admin_menu() {
552 if ( current_user_can( 'list_users' ) && version_compare( get_bloginfo( 'version' ), '3.2', '>=' ) ) {
553 global $menu;
554
555 foreach ( $menu as $key => $menu_item ) {
556 if ( array_search( 'users.php', $menu_item, true ) ) {
557
558 // No need for number formatting, count() always returns an integer.
559 $awaiting_mod = count( $this->unapproved_users );
560
561 // phpcs:ignore WordPress.Variables.GlobalVariables.OverrideProhibited
562 $menu[ $key ][0] .= " <span class='update-plugins count-{$awaiting_mod}'><span class='plugin-count'>{$awaiting_mod}</span></span>";
563
564 break; // Bail on success.
565 }
566 }
567 }
568
569 add_options_page(
570 esc_html__( 'Approve User', 'wp-approve-user' ), // Page Title.
571 esc_html__( 'Approve User', 'wp-approve-user' ), // Menu Title.
572 'promote_users', // Capability.
573 $this->textdomain, // Menu Slug.
574 array( $this, 'settings_page' ) // Function.
575 );
576 }
577
578
579 /**
580 * Registers the plugins' settings.
581 *
582 * @author Konstantin Obenland
583 * @since 1.0.0 - 02.03.2012
584 * @access public
585 *
586 * return void
587 */
588 public function admin_init() {
589 register_setting(
590 $this->textdomain,
591 'wp-approve-user',
592 array( &$this, 'sanitize' )
593 );
594
595 add_settings_section(
596 $this->textdomain,
597 esc_html__( 'Email contents', 'wp-approve-user' ),
598 array( $this, 'section_description_cb' ),
599 $this->textdomain
600 );
601
602 add_settings_field(
603 'wp-approve-user[send-approve-email]',
604 esc_html__( 'Send Approve Email', 'wp-approve-user' ),
605 array( $this, 'checkbox_cb' ),
606 $this->textdomain,
607 $this->textdomain,
608 array(
609 'name' => 'wpau-send-approve-email',
610 'description' => __( 'Send email on approval.', 'wp-approve-user' ),
611 )
612 );
613
614 add_settings_field(
615 'wp-approve-user[approve-email]',
616 esc_html__( 'Approve Email', 'wp-approve-user' ),
617 array( $this, 'textarea_cb' ),
618 $this->textdomain,
619 $this->textdomain,
620 array(
621 'label_for' => 'wpau-approve-email',
622 'name' => 'wpau-approve-email',
623 'setting' => 'wpau-send-approve-email',
624 )
625 );
626
627 add_settings_field(
628 'wp-approve-user[send-unapprove-email]',
629 esc_html__( 'Send Unapprove Email', 'wp-approve-user' ),
630 array( $this, 'checkbox_cb' ),
631 $this->textdomain,
632 $this->textdomain,
633 array(
634 'name' => 'wpau-send-unapprove-email',
635 'description' => __( 'Send email on unapproval.', 'wp-approve-user' ),
636 )
637 );
638 add_settings_field(
639 'wp-approve-user[unapprove-email]',
640 esc_html__( 'Unapprove Email', 'wp-approve-user' ),
641 array( $this, 'textarea_cb' ),
642 $this->textdomain,
643 $this->textdomain,
644 array(
645 'label_for' => 'wpau-unapprove-email',
646 'name' => 'wpau-unapprove-email',
647 'setting' => 'wpau-send-unapprove-email',
648 )
649 );
650 }
651
652
653 /**
654 * Displays the options page.
655 *
656 * @author Konstantin Obenland
657 * @since 2.0.0 - 31.03.2012
658 * @access public
659 *
660 * @return void
661 */
662 public function settings_page() {
663 ?>
664 <div class="wrap">
665 <?php screen_icon(); ?>
666 <h2><?php esc_html_e( 'Approve User Settings', 'wp-approve-user' ); ?></h2>
667
668 <div id="poststuff">
669 <div id="post-body" class="obenland-wp columns-2">
670 <div id="post-body-content">
671 <form method="post" action="options.php">
672 <?php
673 settings_fields( $this->textdomain );
674 do_settings_sections( $this->textdomain );
675 submit_button();
676 ?>
677 </form>
678 </div>
679 <div id="postbox-container-1">
680 <div id="side-info-column">
681 <?php do_action( 'obenland_side_info_column' ); ?>
682 </div>
683 </div>
684 </div>
685 </div>
686 </div>
687 <?php
688 }
689
690
691 /**
692 * Prints the section description.
693 *
694 * @author Konstantin Obenland
695 * @since 2.0.0 - 31.03.2012
696 * @access public
697 *
698 * @return void
699 */
700 public function section_description_cb() {
701 $tags = array( 'USERNAME', 'BLOG_TITLE', 'BLOG_URL', 'LOGINLINK' );
702 if ( is_multisite() ) {
703 $tags[] = 'SITE_NAME';
704 }
705
706 printf(
707 /* translators: Placeholders. */
708 esc_html_x( 'To take advantage of dynamic data, you can use the following placeholders: %s. Username will be the user login in most cases.', 'Placeholders', 'wp-approve-user' ),
709 sprintf( '<code>%s</code>', implode( '</code>, <code>', $tags ) ) // phpcs:ignore WordPress.XSS.EscapeOutput.OutputNotEscaped
710 );
711 }
712
713
714 /**
715 * Populates the setting field.
716 *
717 * @author Konstantin Obenland
718 * @since 2.0.0 - 31.03.2012
719 * @access public
720 *
721 * @param array $option Settings option.
722 *
723 * @return void
724 */
725 public function checkbox_cb( $option ) {
726 $option = (object) $option;
727 ?>
728 <label for="<?php echo esc_attr( sanitize_title_with_dashes( $option->name ) ); ?>">
729 <input type="checkbox" name="wp-approve-user[<?php echo esc_attr( $option->name ); ?>]" id="<?php echo esc_attr( sanitize_title_with_dashes( $option->name ) ); ?>" value="1" <?php checked( $this->options[ $option->name ] ); ?> />
730 <?php echo esc_html( $option->description ); ?>
731 </label><br />
732 <?php
733 }
734
735
736 /**
737 * Populates the setting field.
738 *
739 * @author Konstantin Obenland
740 * @since 2.0.0 - 31.03.2012
741 * @access public
742 *
743 * @param array $option Settings option.
744 *
745 * @return void
746 */
747 public function textarea_cb( $option ) {
748 $option = (object) $option;
749 ?>
750 <textarea id="<?php echo esc_attr( sanitize_title_with_dashes( $option->name ) ); ?>" class="large-text code" name="wp-approve-user[<?php echo esc_attr( $option->name ); ?>]" rows="10" cols="50" ><?php echo esc_textarea( $this->options[ $option->name ] ); ?></textarea>
751 <?php
752 }
753
754
755 /**
756 * Sanitizes the settings input.
757 *
758 * @author Konstantin Obenland
759 * @since 2.0.0 - 31.03.2012
760 * @access public
761 *
762 * @param array $input Form input.
763 *
764 * @return array The sanitized settings
765 */
766 public function sanitize( $input ) {
767 return array(
768 'wpau-send-approve-email' => (bool) isset( $input['wpau-send-approve-email'] ),
769 'wpau-send-unapprove-email' => (bool) isset( $input['wpau-send-unapprove-email'] ),
770 'wpau-approve-email' => isset( $input['wpau-approve-email'] ) ? trim( $input['wpau-approve-email'] ) : '',
771 'wpau-unapprove-email' => isset( $input['wpau-unapprove-email'] ) ? trim( $input['wpau-unapprove-email'] ) : '',
772 );
773 }
774
775
776 /**
777 * Sends the approval email.
778 *
779 * @author Konstantin Obenland
780 * @since 2.0.0 - 31.03.2012
781 * @access public
782 *
783 * @param int $user_id User ID.
784 *
785 * @return void
786 */
787 public function wpau_approve( $user_id ) {
788 if ( get_user_meta( $user_id, 'wp-approve-user-new-registration', true ) ) {
789 wp_new_user_notification( $user_id, null, 'user' );
790 delete_user_meta( $user_id, 'wp-approve-user-new-registration' );
791 }
792
793 // Check user meta if mail has been sent already.
794 if ( $this->options['wpau-send-approve-email'] && ! get_user_meta( $user_id, 'wp-approve-user-mail-sent', true ) ) {
795 $user = new WP_User( $user_id );
796 $blogname = wp_specialchars_decode( get_option( 'blogname' ), ENT_QUOTES );
797
798 // Send mail.
799 $sent = wp_mail(
800 $user->user_email,
801 /* translators: Blog name. */
802 sprintf( esc_html_x( '[%s] Registration approved', 'Blogname', 'wp-approve-user' ), $blogname ),
803 $this->populate_message( $this->options['wpau-approve-email'], $user )
804 );
805
806 if ( $sent ) {
807 update_user_meta( $user_id, 'wp-approve-user-mail-sent', true );
808 }
809 }
810 }
811
812
813 /**
814 * Sends the rejection email.
815 *
816 * @author Konstantin Obenland
817 * @since 2.0.0 - 31.03.2012
818 * @access public
819 *
820 * @param int $user_id User ID.
821 *
822 * @return void
823 */
824 public function delete_user( $user_id ) {
825 if ( $this->options['wpau-send-unapprove-email'] ) {
826 $user = new WP_User( $user_id );
827 $blogname = wp_specialchars_decode( get_option( 'blogname' ), ENT_QUOTES );
828
829 // Send mail.
830 wp_mail(
831 $user->user_email,
832 /* translators: Blog name. */
833 sprintf( esc_html_x( '[%s] Registration unapproved', 'Blogname', 'wp-approve-user' ), $blogname ),
834 $this->populate_message( $this->options['wpau-unapprove-email'], $user )
835 );
836
837 // No need to delete user_meta, since this user will be GONE.
838 }
839 }
840
841
842 /**
843 * Display all messages registered to this plugin.
844 *
845 * @author Konstantin Obenland
846 * @since 2.0.0 - 30.03.2012
847 * @access public
848 *
849 * @return void
850 */
851 public function all_admin_notices() {
852 settings_errors( $this->textdomain );
853 }
854
855
856 /**
857 * Updates user_meta to approve user.
858 *
859 * @author Konstantin Obenland
860 * @since 1.1 - 12.02.2012
861 * @access protected
862 *
863 * @return void
864 */
865 protected function approve() {
866 list( $user_ids, $url ) = $this->check_user();
867
868 foreach ( (array) $user_ids as $id ) {
869 $id = (int) $id;
870
871 if ( ! current_user_can( 'edit_user', $id ) ) {
872 wp_die( esc_html__( 'You can&#8217;t edit that user.' ), '', array(
873 'back_link' => true,
874 ) );
875 }
876
877 update_user_meta( $id, 'wp-approve-user', true );
878 do_action( 'wpau_approve', $id );
879 }
880
881 wp_safe_redirect( add_query_arg( array(
882 'action' => 'wpau_update',
883 'update' => 'wpau-approved',
884 'count' => count( $user_ids ),
885 'role' => $this->get_role(),
886 ), $url ) );
887 exit();
888 }
889
890
891 /**
892 * Updates user_meta to unapprove user.
893 *
894 * @author Konstantin Obenland
895 * @since 1.1 - 12.02.2012
896 * @access protected
897 *
898 * @return void
899 */
900 protected function unapprove() {
901 list( $user_ids, $url ) = $this->check_user();
902
903 foreach ( (array) $user_ids as $id ) {
904 $id = (int) $id;
905
906 if ( ! current_user_can( 'edit_user', $id ) ) {
907 wp_die( esc_html__( 'You can&#8217;t edit that user.' ), '', array(
908 'back_link' => true,
909 ) );
910 }
911
912 update_user_meta( $id, 'wp-approve-user', false );
913 do_action( 'wpau_unapprove', $id );
914 }
915
916 wp_safe_redirect( add_query_arg( array(
917 'action' => 'wpau_update',
918 'update' => 'wpau-unapproved',
919 'count' => count( $user_ids ),
920 'role' => $this->get_role(),
921 ), $url ) );
922 exit();
923 }
924
925
926 /**
927 * Checks permissions and assembles User IDs.
928 *
929 * @author Konstantin Obenland
930 * @since 2.0.0 - 15.03.2012
931 * @access protected
932 *
933 * @return array User IDs and URL
934 */
935 protected function check_user() {
936 // phpcs:disable WordPress.CSRF.NonceVerification.NoNonceVerification
937
938 $screen_id = get_current_screen()->id;
939 $users_key = 'user';
940
941 if ( false !== stripos( current_action(), 'wpau_bulk_' ) ) {
942 $users_key = 'users-network' === $screen_id ? 'allusers' : 'users';
943 }
944
945 $site_id = isset( $_REQUEST['id'] ) ? intval( $_REQUEST['id'] ) : 0;
946 $url = 'site-users-network' === $screen_id ? add_query_arg( array( 'id' => $site_id ), 'site-users.php' ) : 'users.php';
947
948 if ( empty( $_REQUEST[ $users_key ] ) && empty( $_REQUEST[ $users_key ] ) ) {
949 wp_safe_redirect( $url );
950 exit();
951 }
952
953 if ( ! current_user_can( 'promote_users' ) ) {
954 wp_die( esc_html__( 'You can&#8217;t unapprove users.', 'wp-approve-user' ), '', array(
955 'back_link' => true,
956 ) );
957 }
958
959 $user_ids = array_map( 'intval', (array) $_REQUEST[ $users_key ] );
960 $user_ids = array_diff( $user_ids, array( get_user_by( 'email', get_bloginfo( 'admin_email' ) )->ID ) );
961
962 return array( $user_ids, $url );
963
964 // phpcs:enable WordPress.CSRF.NonceVerification.NoNonceVerification
965 }
966
967
968 /**
969 * Replaces all the placeholders with their content.
970 *
971 * @author Konstantin Obenland
972 * @since 2.0.0 - 15.03.2012
973 * @access protected
974 *
975 * @param string $message Email body.
976 * @param WP_User $user User object.
977 *
978 * @return string
979 */
980 protected function populate_message( $message, $user ) {
981 $title = wp_specialchars_decode( get_option( 'blogname' ), ENT_QUOTES );
982
983 $message = str_replace( 'BLOG_TITLE', $title, $message );
984 $message = str_replace( 'BLOG_URL', home_url(), $message );
985 $message = str_replace( 'LOGINLINK', wp_login_url(), $message );
986 $message = str_replace( 'USERNAME', $user->user_nicename, $message );
987
988 if ( is_multisite() ) {
989 $message = str_replace( 'SITE_NAME', $GLOBALS['current_site']->site_name, $message );
990 }
991
992 return $message;
993 }
994
995
996 /**
997 * Returns the default options.
998 *
999 * @author Konstantin Obenland
1000 * @since 2.0.0 - 15.03.2012
1001 * @access protected
1002 *
1003 * @return array
1004 */
1005 protected function default_options() {
1006 $options = array(
1007 'wpau-send-approve-email' => false,
1008 'wpau-approve-email' => '
1009 Hi USERNAME,
1010 Your registration for BLOG_TITLE has now been approved.
1011
1012 You can log in, using your username and password that you created when registering for our website, at the following URL: LOGINLINK
1013
1014 If you have any questions, or problems, then please do not hesitate to contact us.
1015
1016 Name,
1017 Company,
1018 Contact details',
1019 'wpau-send-unapprove-email' => false,
1020 'wpau-unapprove-email' => '',
1021 );
1022
1023 return apply_filters( 'wpau_default_options', $options );
1024 }
1025
1026 /**
1027 * Sets the role context on bulk actions.
1028 *
1029 * On bulk actions the role parameter is not passed, since we're using a form
1030 * to submit information. The information is only available through the
1031 * `_wp_http_referer` parameter, so we get it from there and make it available
1032 * for the request.
1033 *
1034 * @author Konstantin Obenland
1035 * @since 3 - 04.09.2014
1036 * @access protected
1037 */
1038 protected function set_up_role_context() {
1039 // phpcs:disable WordPress.CSRF.NonceVerification.NoNonceVerification, WordPress.VIP.ValidatedSanitizedInput
1040
1041 if ( empty( $_REQUEST['role'] ) && ! empty( $_REQUEST['_wp_http_referer'] ) ) {
1042 $referrer = parse_url( $_REQUEST['_wp_http_referer'] ); // phpcs:ignore WordPress.WP.AlternativeFunctions.parse_url_parse_url
1043
1044 if ( ! empty( $referrer['query'] ) ) {
1045 $args = wp_parse_args( $referrer['query'] );
1046
1047 if ( ! empty( $args['role'] ) ) {
1048 $_REQUEST['role'] = $args['role'];
1049 }
1050 }
1051 }
1052 }
1053
1054 /**
1055 * Returns the current role.
1056 *
1057 * If the user list is in the context of a specific role, this function makes
1058 * sure that the requested role is valid. By returning `false` otherwise, we
1059 * make sure that parameter gets removed from the activation link.
1060 *
1061 * @author Konstantin Obenland
1062 * @since 3 - 04.09.2014
1063 * @access protected
1064 *
1065 * @return string|bool The role key if set, false otherwise.
1066 */
1067 protected function get_role() {
1068 $roles = array_keys( get_editable_roles() );
1069 $roles[] = 'wpau_unapproved';
1070 $role = false;
1071
1072 if ( isset( $_REQUEST['role'] ) && in_array( $_REQUEST['role'], $roles, true ) ) {
1073 $role = $_REQUEST['role'];
1074 }
1075
1076 return $role;
1077
1078 // phpcs:enable WordPress.CSRF.NonceVerification.NoNonceVerification, WordPress.VIP.ValidatedSanitizedInput
1079 }
1080
1081 /**
1082 * Re-runs the activation hook when registration is activated.
1083 *
1084 * If the plugin is activated and user registration is disabled, the plugin
1085 * activation hook never gets added, let alone fired. This a secondary
1086 * measure to make sure all existing users are approved on activation.
1087 *
1088 * @author Konstantin Obenland
1089 * @deprecated 2.3.0 - 13.08.2013
1090 * @access public
1091 *
1092 * @param string $old Old settings value.
1093 * @param int $new New settings value.
1094 *
1095 * @return void
1096 */
1097 public function update_option_users_can_register( $old, $new ) {
1098 _deprecated_function( __FUNCTION__, '2.3' );
1099 }
1100 } // End of class Obenland_Wp_Approve_User
1101
1102
1103 new Obenland_Wp_Approve_User();
1104
1105
1106 register_activation_hook( __FILE__, array(
1107 Obenland_Wp_Approve_User::$instance,
1108 'activation',
1109 ) );
1110