PluginProbe
Password Protected — Lock Entire Site, Pages, Posts, Categories, and Partial Content / 2.6
Password Protected — Lock Entire Site, Pages, Posts, Categories, and Partial Content v2.6
2.8.4 2.8.3 2.8.2 2.8.1 trunk 1.0 1.1 1.2 1.2.1 1.2.2 1.3 1.4 1.5 1.6 1.6.1 1.6.2 1.7 1.7.1 1.7.2 1.8 1.9 2.0 2.0.1 2.0.2 2.0.3 All 63 releases
password-protected / password-protected.php

password-protected.php in Password Protected — Lock Entire Site, Pages, Posts, Categories, and Partial Content 2.6, at password-protected.php

896 lines 23.2 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2 /*
3 Plugin Name: Password Protected
4 Plugin URI: https://wordpress.org/plugins/password-protected/
5 Description: A very simple way to quickly password protect your WordPress site with a single password. Please note: This plugin does not restrict access to uploaded files and images and does not work with some caching setups.
6 Version: 2.6.0
7 Author: WPExperts
8 Text Domain: password-protected
9 Author URI: https://wpexperts.io/
10 License: GPLv2
11 */
12 /*
13 This program is free software; you can redistribute it and/or modify
14 it under the terms of the GNU General Public License, version 2, as
15 published by the Free Software Foundation.
16
17 This program is distributed in the hope that it will be useful,
18 but WITHOUT ANY WARRANTY; without even the implied warranty of
19 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
20 GNU General Public License for more details.
21
22 You should have received a copy of the GNU General Public License
23 along with this program; if not, write to the Free Software
24 Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
25 */
26
27 /**
28 * @todo Use wp_hash_password() ?
29 * @todo Remember me
30 */
31
32 define( 'PASSWORD_PROTECTED_SUBDIR', '/' . str_replace( basename( __FILE__ ), '', plugin_basename( __FILE__ ) ) );
33 define( 'PASSWORD_PROTECTED_URL', plugins_url( PASSWORD_PROTECTED_SUBDIR ) );
34 define( 'PASSWORD_PROTECTED_DIR', plugin_dir_path( __FILE__ ) );
35
36 global $Password_Protected;
37 $Password_Protected = new Password_Protected();
38
39 class Password_Protected {
40
41 var $version = '2.6.0';
42 var $admin = null;
43 var $errors = null;
44
45 /**
46 * Constructor
47 */
48 public function __construct() {
49
50 $this->errors = new WP_Error();
51
52 register_activation_hook( __FILE__, array( &$this, 'install' ) );
53
54 add_action( 'plugins_loaded', array( $this, 'load_plugin_textdomain' ) );
55
56 add_filter( 'password_protected_is_active', array( $this, 'allow_ip_addresses' ) );
57
58 add_action( 'init', array( $this, 'disable_caching' ), 1 );
59 add_action( 'init', array( $this, 'maybe_process_logout' ), 1 );
60 add_action( 'init', array( $this, 'maybe_process_login' ), 1 );
61 add_action( 'wp', array( $this, 'disable_feeds' ) );
62 add_action( 'template_redirect', array( $this, 'maybe_show_login' ), -1 );
63 add_filter( 'pre_option_password_protected_status', array( $this, 'allow_feeds' ) );
64 add_filter( 'pre_option_password_protected_status', array( $this, 'allow_administrators' ) );
65 add_filter( 'pre_option_password_protected_status', array( $this, 'allow_users' ) );
66 add_filter( 'rest_authentication_errors', array( $this, 'only_allow_logged_in_rest_access' ) );
67 add_action( 'init', array( $this, 'compat' ) );
68 add_action( 'password_protected_login_messages', array( $this, 'login_messages' ) );
69 add_action( 'login_enqueue_scripts', array( $this, 'load_theme_stylesheet' ), 5 );
70
71 add_action('password_protected_above_password_field', array( $this, 'password_protected_above_password_field' ));
72 add_action('password_protected_below_password_field', array( $this, 'password_protected_below_password_field' ));
73
74 // Available from WordPress 4.3+
75 if ( function_exists( 'wp_site_icon' ) ) {
76 add_action( 'password_protected_login_head', 'wp_site_icon' );
77 }
78
79 add_shortcode( 'password_protected_logout_link', array( $this, 'logout_link_shortcode' ) );
80
81 include_once dirname( __FILE__ ) . '/admin/admin-bar.php';
82
83 if ( is_admin() ) {
84
85
86 include_once dirname( __FILE__ ) . '/admin/admin-caching.php';
87 include_once dirname( __FILE__ ) . '/admin/admin.php';
88
89 $this->admin_caching = new Password_Protected_Admin_Caching( $this );
90 $this->admin = new Password_Protected_Admin();
91
92
93 }
94 include_once dirname( __FILE__ ) . '/admin/class-recaptcha.php';
95 new Password_Protected_reCAPTCHA();
96
97 }
98
99 /**
100 * I18n
101 */
102 public function load_plugin_textdomain() {
103
104 load_plugin_textdomain( 'password-protected', false, basename( dirname( __FILE__ ) ) . '/languages' );
105
106 }
107
108 /**
109 * Disable Page Caching
110 */
111 public function disable_caching() {
112
113 if ( $this->is_active() && ! defined( 'DONOTCACHEPAGE' ) ) {
114 define( 'DONOTCACHEPAGE', true );
115 }
116
117 }
118
119 /**
120 * Is Active?
121 *
122 * @return boolean Is password protection active?
123 */
124 public function is_active() {
125
126 global $wp_query;
127
128 // Always allow access to robots.txt
129 if ( isset( $wp_query ) && is_robots() ) {
130 return false;
131 }
132
133 if ( (bool) get_option( 'password_protected_status' ) ) {
134 $is_active = true;
135 } else {
136 $is_active = false;
137 }
138
139 $is_active = apply_filters( 'password_protected_is_active', $is_active );
140
141 if ( isset( $_GET['password-protected'] ) ) {
142 $is_active = true;
143 }
144
145 return $is_active;
146
147 }
148
149 /**
150 * Disable Feeds
151 *
152 * @todo An option/filter to prevent disabling of feeds.
153 */
154 public function disable_feeds() {
155
156 if ( $this->is_active() ) {
157 add_action( 'do_feed', array( $this, 'disable_feed' ), 1 );
158 add_action( 'do_feed_rdf', array( $this, 'disable_feed' ), 1 );
159 add_action( 'do_feed_rss', array( $this, 'disable_feed' ), 1 );
160 add_action( 'do_feed_rss2', array( $this, 'disable_feed' ), 1 );
161 add_action( 'do_feed_atom', array( $this, 'disable_feed' ), 1 );
162 }
163
164 }
165
166 /**
167 * Disable Feed
168 *
169 * @todo Make Translatable
170 */
171 public function disable_feed() {
172
173 wp_die( sprintf( __( 'Feeds are not available for this site. Please visit the <a href="%s">website</a>.', 'password-protected' ), get_bloginfo( 'url' ) ) );
174
175 }
176
177 /**
178 * Allow Feeds
179 *
180 * @param boolean $bool Allow feeds.
181 * @return boolean True/false.
182 */
183 public function allow_feeds( $bool ) {
184
185 if ( is_feed() && (bool) get_option( 'password_protected_feeds' ) ) {
186 return 0;
187 }
188
189 return $bool;
190
191 }
192
193 /**
194 * Allow Administrators
195 *
196 * @param boolean $bool Allow administrators.
197 * @return boolean True/false.
198 */
199 public function allow_administrators( $bool ) {
200
201 if ( ! is_admin() && current_user_can( 'manage_options' ) && (bool) get_option( 'password_protected_administrators' ) ) {
202 return 0;
203 }
204
205 return $bool;
206
207 }
208
209 /**
210 * Allow Users
211 *
212 * @param boolean $bool Allow administrators.
213 * @return boolean True/false.
214 */
215 public function allow_users( $bool ) {
216
217 if ( ! is_admin() && is_user_logged_in() && (bool) get_option( 'password_protected_users' ) ) {
218 return 0;
219 }
220
221 return $bool;
222
223 }
224
225 /**
226 * Allow IP Addresses
227 *
228 * If user has a valid email address, return false to disable password protection.
229 *
230 * @param boolean $bool Allow IP addresses.
231 * @return boolean True/false.
232 */
233 public function allow_ip_addresses( $bool ) {
234
235 $ip_addresses = $this->get_allowed_ip_addresses();
236
237 if ( isset( $_SERVER['REMOTE_ADDR'] ) && in_array( $_SERVER['REMOTE_ADDR'], $ip_addresses ) ) {
238 $bool = false;
239 }
240
241 return $bool;
242
243 }
244
245 /**
246 * Get Allowed IP Addresses
247 *
248 * @return array IP addresses.
249 */
250 public function get_allowed_ip_addresses() {
251
252 return explode( "\n", get_option( 'password_protected_allowed_ip_addresses' ) );
253
254 }
255
256 /**
257 * Allow the remember me function
258 *
259 * @return. boolean
260 */
261 public function allow_remember_me() {
262
263 return (bool) get_option( 'password_protected_remember_me' );
264
265 }
266
267 /**
268 * Encrypt Password
269 *
270 * @param string $password Password.
271 * @return string Encrypted password.
272 */
273 public function encrypt_password( $password ) {
274
275 return md5( $password );
276
277 }
278
279 /**
280 * Maybe Process Logout
281 */
282 public function maybe_process_logout() {
283
284 if ( isset( $_REQUEST['password-protected'] ) && sanitize_text_field( $_REQUEST['password-protected'] ) == 'logout' ) {
285
286 $this->logout();
287
288 if ( isset( $_REQUEST['redirect_to'] ) ) {
289 $redirect_to = remove_query_arg( 'password-protected', esc_url_raw( $_REQUEST['redirect_to'], array( 'http', 'https' ) ) );
290 } else {
291 $redirect_to = home_url( '/' );
292 }
293
294 $this->safe_redirect( $redirect_to );
295 exit();
296
297 }
298
299 }
300
301 /**
302 * Maybe Process Login
303 */
304 public function maybe_process_login() {
305
306 if ( $this->is_active() && isset( $_REQUEST['password_protected_pwd'] ) ) {
307
308 $password_protected_pwd = $_REQUEST['password_protected_pwd'];
309 $default_password = get_option( 'password_protected_password' );
310 $pwd[] = $default_password;
311
312 $pwd = array_filter( $pwd );
313
314 $this->errors = apply_filters( 'password_protected_verify_recaptcha', $this->errors );
315 if( count( @$this->errors->errors ) > 0 ) return;
316
317 $pwd = apply_filters( 'password_protected_passwords', $pwd );
318 $auth = false;
319
320 foreach( $pwd as $i => $p ) {
321 // If correct password...
322 if ( ( hash_equals( $p, $this->encrypt_password( $password_protected_pwd ) ) && $pwd != '' ) || apply_filters( 'password_protected_process_login', false, $password_protected_pwd ) ) {
323 // $auth = true;
324 $auth = apply_filters( 'password_protected_login_password_matched', $p, $this->errors );
325 break;
326 }
327 }
328
329 $this->password_protected_process_login( $auth );
330
331 }
332
333 }
334
335 private function password_protected_process_login( bool $auth ) {
336
337 if( $auth )
338 $throttle = apply_filters( 'password_protected_check_for_throttling', true );
339
340
341 if( $auth && $throttle ) {
342
343 do_action( 'password_protected_success_login_attempt' );
344 $remember = isset( $_REQUEST['password_protected_rememberme'] ) ? boolval( $_REQUEST['password_protected_rememberme'] ) : false;
345
346 if ( ! $this->allow_remember_me() ) {
347 $remember = false;
348 }
349 $this->set_auth_cookie( $remember );
350
351 $redirect_to = isset( $_REQUEST['redirect_to'] ) ? esc_url($_REQUEST['redirect_to']) : '';
352 $redirect_to = apply_filters( 'password_protected_login_redirect', $redirect_to );
353
354 if ( ! empty( $redirect_to ) ) {
355 $this->safe_redirect( remove_query_arg( 'password-protected', $redirect_to ) );
356 exit;
357 } elseif ( isset( $_GET['password_protected_pwd'] ) ) {
358 $this->safe_redirect( remove_query_arg( 'password-protected' ) );
359 exit;
360 } else {
361 $this->safe_redirect( site_url() );
362 exit;
363 }
364 } else {
365 do_action( 'password_protected_failure_login_attempt' );
366
367 // ... otherwise incorrect password
368 $this->clear_auth_cookie();
369
370 $show_default_error = apply_filters( 'password_protected_throttling_error_messages', true );
371
372 if( $show_default_error )
373 $this->errors->add( 'incorrect_password', __( 'Incorrect Password', 'password-protected' ) );
374 }
375 }
376
377 /**
378 * Is User Logged In?
379 *
380 * @return boolean
381 */
382 public function is_user_logged_in() {
383
384 return $this->is_active() && $this->validate_auth_cookie();
385
386 }
387
388 /**
389 * Maybe Show Login
390 */
391 public function maybe_show_login() {
392
393 if ( class_exists( 'Login_designer' ) ) {
394 if ( is_customize_preview() ) {
395 return 1;
396 }
397 }
398
399 // Filter for adding exceptions.
400 $show_login = apply_filters( 'password_protected_show_login', $this->is_active() );
401
402 // Logged in
403 if ( $this->is_user_logged_in() ) {
404 $show_login = false;
405 }
406
407 if ( ! $show_login ) {
408 return 1;
409 }
410
411 // Show login form
412 if ( isset( $_REQUEST['password-protected'] ) && 'login' == sanitize_text_field( $_REQUEST['password-protected'] ) ) {
413
414 $default_theme_file = locate_template( array( 'password-protected-login.php' ) );
415
416 if ( empty( $default_theme_file ) ) {
417 $default_theme_file = dirname( __FILE__ ) . '/theme/password-protected-login.php';
418 }
419
420 $theme_file = apply_filters( 'password_protected_theme_file', $default_theme_file );
421 if ( ! file_exists( $theme_file ) ) {
422 $theme_file = $default_theme_file;
423 }
424
425 load_template( $theme_file );
426 exit();
427
428 } else {
429
430 $redirect_to = add_query_arg( 'password-protected', 'login', home_url() );
431
432 // URL to redirect back to after login
433 $redirect_to_url = apply_filters( 'password_protected_login_redirect_url', ( is_ssl() ? 'https://' : 'http://' ) . $_SERVER['HTTP_HOST'] . $_SERVER['REQUEST_URI'] );
434 if ( ! empty( $redirect_to_url ) ) {
435 $redirect_to = add_query_arg( 'redirect_to', urlencode( $redirect_to_url ), $redirect_to );
436 }
437
438 nocache_headers();
439 wp_redirect( $redirect_to );
440 exit();
441
442 }
443 }
444
445 /**
446 * Get Site ID
447 *
448 * @return string Site ID.
449 */
450 public function get_site_id() {
451
452 global $blog_id;
453 return 'bid_' . apply_filters( 'password_protected_blog_id', $blog_id );
454
455 }
456
457 /**
458 * Login URL
459 *
460 * @return string Login URL.
461 */
462 public function login_url() {
463
464 return add_query_arg( 'password-protected', 'login', home_url( '/' ) );
465
466 }
467
468 /**
469 * Logout
470 */
471 public function logout() {
472
473 $this->clear_auth_cookie();
474 do_action( 'password_protected_logout' );
475
476 }
477
478 /**
479 * Logout URL
480 *
481 * @param string $redirect_to Optional. Redirect URL.
482 * @return string Logout URL.
483 */
484 public function logout_url( $redirect_to = '' ) {
485
486 $query = array(
487 'password-protected' => 'logout',
488 'redirect_to' => esc_url_raw( $redirect_to ),
489 );
490
491 if ( empty( $query['redirect_to'] ) ) {
492 unset( $query['redirect_to'] );
493 }
494
495 return add_query_arg( $query, home_url() );
496
497 }
498
499 /**
500 * Logout Link
501 *
502 * @param array $args Link args.
503 * @return string HTML link tag.
504 */
505 public function logout_link( $args = null ) {
506
507 // Only show if user is logged in
508 if ( ! $this->is_user_logged_in() ) {
509 return '';
510 }
511
512 $args = wp_parse_args(
513 $args,
514 array(
515 'redirect_to' => '',
516 'text' => __( 'Logout', 'password-protected' ),
517 )
518 );
519
520 if ( empty( $args['text'] ) ) {
521 $args['text'] = __( 'Logout', 'password-protected' );
522 }
523
524 return sprintf( '<a href="%s">%s</a>', esc_url( $this->logout_url( $args['redirect_to'] ) ), esc_html( $args['text'] ) );
525
526 }
527
528 /**
529 * Logout Link Shortcode
530 *
531 * @param array $args Link args.
532 * @return string HTML link tag.
533 */
534 public function logout_link_shortcode( $atts, $content = null ) {
535
536 $atts = shortcode_atts(
537 array(
538 'redirect_to' => '',
539 'text' => $content,
540 ),
541 $atts,
542 'logout_link_shortcode'
543 );
544
545 return $this->logout_link( $atts );
546
547 }
548
549 /**
550 * Get Hashed Password
551 *
552 * @return string Hashed password.
553 */
554 public function get_hashed_password() {
555
556 return md5( get_option( 'password_protected_password' ) . wp_salt() );
557
558 }
559
560 /**
561 * Validate Auth Cookie
562 *
563 * @param string $cookie Cookie string.
564 * @param string $scheme Cookie scheme.
565 * @return boolean Validation successful?
566 */
567 public function validate_auth_cookie( $cookie = '', $scheme = '' ) {
568
569 if ( ! $cookie_elements = $this->parse_auth_cookie( $cookie, $scheme ) ) {
570 do_action( 'password_protected_auth_cookie_malformed', $cookie, $scheme );
571 return false;
572 }
573
574 extract( $cookie_elements, EXTR_OVERWRITE );
575
576 $expired = $expiration;
577
578 // Allow a grace period for POST and AJAX requests
579 if ( defined( 'DOING_AJAX' ) || 'POST' == $_SERVER['REQUEST_METHOD'] ) {
580 $expired += 3600;
581 }
582
583 // Quick check to see if an honest cookie has expired
584 if ( $expired < current_time( 'timestamp' ) ) {
585 do_action( 'password_protected_auth_cookie_expired', $cookie_elements );
586 return false;
587 }
588
589 $key = md5( $this->get_site_id() . $this->get_hashed_password() . '|' . $expiration );
590 $hash = hash_hmac( 'md5', $this->get_site_id() . '|' . $expiration, $key );
591
592 if ( $hmac != $hash ) {
593 do_action( 'password_protected_auth_cookie_bad_hash', $cookie_elements );
594 return false;
595 }
596
597 if ( $expiration < current_time( 'timestamp' ) ) { // AJAX/POST grace period set above
598 $GLOBALS['login_grace_period'] = 1;
599 }
600
601 return true;
602
603 }
604
605 /**
606 * Generate Auth Cookie
607 *
608 * @param int $expiration Expiration time in seconds.
609 * @param string $scheme Cookie scheme.
610 * @return string Cookie.
611 */
612 public function generate_auth_cookie( $expiration, $scheme = 'auth' ) {
613
614 $key = md5( $this->get_site_id() . $this->get_hashed_password() . '|' . $expiration );
615 $hash = hash_hmac( 'md5', $this->get_site_id() . '|' . $expiration, $key );
616 $cookie = $this->get_site_id() . '|' . $expiration . '|' . $hash;
617
618 return $cookie;
619
620 }
621
622 /**
623 * Parse Auth Cookie
624 *
625 * @param string $cookie Cookie string.
626 * @param string $scheme Cookie scheme.
627 * @return string Cookie string.
628 */
629 public function parse_auth_cookie( $cookie = '', $scheme = '' ) {
630
631 if ( empty( $cookie ) ) {
632
633 $cookie_name = $this->cookie_name();
634
635 if ( empty( $_COOKIE[ $cookie_name ] ) ) {
636 return false;
637 }
638
639 $cookie = $_COOKIE[ $cookie_name ];
640
641 }
642
643 $cookie_elements = explode( '|', $cookie );
644
645 if ( count( $cookie_elements ) != 3 ) {
646 return false;
647 }
648
649 list( $site_id, $expiration, $hmac ) = $cookie_elements;
650
651 return compact( 'site_id', 'expiration', 'hmac', 'scheme' );
652
653 }
654
655 /**
656 * Set Auth Cookie
657 *
658 * @todo
659 *
660 * @param boolean $remember Remember logged in.
661 * @param string $secure Secure cookie.
662 */
663 public function set_auth_cookie( $remember = false, $secure = '' ) {
664
665 if ( $remember ) {
666 $expiration_time = apply_filters( 'password_protected_auth_cookie_expiration', get_option( 'password_protected_remember_me_lifetime', 14 ) * DAY_IN_SECONDS, $remember );
667 $expiration = $expire = current_time( 'timestamp' ) + $expiration_time;
668 } else {
669 $expiration_time = apply_filters( 'password_protected_auth_cookie_expiration', DAY_IN_SECONDS * 20, $remember );
670 $expiration = current_time( 'timestamp' ) + $expiration_time;
671 $expire = 0;
672 }
673
674 if ( '' === $secure ) {
675 $secure = is_ssl();
676 }
677
678 $secure_password_protected_cookie = apply_filters( 'password_protected_secure_password_protected_cookie', false, $secure );
679 $password_protected_cookie = $this->generate_auth_cookie( $expiration, 'password_protected' );
680
681 setcookie( $this->cookie_name(), $password_protected_cookie, $expire, COOKIEPATH, COOKIE_DOMAIN, $secure_password_protected_cookie, true );
682 if ( COOKIEPATH != SITECOOKIEPATH ) {
683 setcookie( $this->cookie_name(), $password_protected_cookie, $expire, SITECOOKIEPATH, COOKIE_DOMAIN, $secure_password_protected_cookie, true );
684 }
685
686 }
687
688 /**
689 * Clear Auth Cookie
690 */
691 public function clear_auth_cookie() {
692
693 setcookie( $this->cookie_name(), ' ', current_time( 'timestamp' ) - 31536000, COOKIEPATH, COOKIE_DOMAIN );
694 setcookie( $this->cookie_name(), ' ', current_time( 'timestamp' ) - 31536000, SITECOOKIEPATH, COOKIE_DOMAIN );
695
696 }
697
698 /**
699 * Cookie Name
700 *
701 * @return string Cookie name.
702 */
703 public function cookie_name() {
704
705 /**
706 * Filters the cookie name
707 */
708 return apply_filters( 'password_protected_cookie_name', $this->get_site_id() . '_password_protected_auth', $this );
709
710 }
711
712 /**
713 * Install
714 */
715 public function install() {
716
717 $old_version = get_option( 'password_protected_version' );
718
719 // 1.1 - Upgrade to MD5
720 if ( empty( $old_version ) || $old_version == '1.1' ) {
721 $pwd = get_option( 'password_protected_password' );
722 if ( ! empty( $pwd ) ) {
723 $new_pwd = $this->encrypt_password( $pwd );
724 update_option( 'password_protected_password', $new_pwd );
725 }
726 }
727
728 update_option( 'password_protected_version', $this->version );
729
730 }
731
732 /**
733 * Compat
734 *
735 * Support for 3rd party plugins:
736 *
737 * - Login Logo https://wordpress.org/plugins/login-logo/
738 * - Uber Login Logo https://wordpress.org/plugins/uber-login-logo/
739 */
740 public function compat() {
741
742 if ( class_exists( 'CWS_Login_Logo_Plugin' ) ) {
743
744 // Add support for Mark Jaquith's Login Logo plugin
745 add_action( 'password_protected_login_head', array( new CWS_Login_Logo_Plugin(), 'login_head' ) );
746
747 } elseif ( class_exists( 'UberLoginLogo' ) ) {
748
749 // Add support for Uber Login Logo plugin
750 add_action( 'password_protected_login_head', array( 'UberLoginLogo', 'replaceLoginLogo' ) );
751
752 }
753
754 }
755
756 /**
757 * Login Messages
758 * Outputs messages and errors in the login template.
759 */
760 public function login_messages() {
761
762 // Add message
763 $message = apply_filters( 'password_protected_login_message', '' );
764 if ( ! empty( $message ) ) {
765 echo $message . "\n";
766 }
767
768 if ( $this->errors->get_error_code() ) {
769
770 $errors = '';
771 $messages = '';
772
773 foreach ( $this->errors->get_error_codes() as $code ) {
774 $severity = $this->errors->get_error_data( $code );
775 foreach ( $this->errors->get_error_messages( $code ) as $error ) {
776 if ( 'message' == $severity ) {
777 $messages .= $error . '<br />';
778 } else {
779 $errors .= $error . '<br />';
780 }
781 }
782 }
783
784 if ( ! empty( $errors ) ) {
785 echo '<div id="login_error">' . apply_filters( 'password_protected_login_errors', $errors ) . "</div>\n";
786 }
787 if ( ! empty( $messages ) ) {
788 echo '<p class="message">' . apply_filters( 'password_protected_login_messages', $messages ) . "</p>\n";
789 }
790 }
791
792 }
793
794 /**
795 * Load Theme Stylesheet
796 *
797 * Check wether a 'password-protected-login.css' stylesheet exists in your theme
798 * and if so loads it.
799 *
800 * Works with child themes.
801 *
802 * Possible to specify a different file in the theme folder via the
803 * 'password_protected_stylesheet_file' filter (allows for theme subfolders).
804 */
805 public function load_theme_stylesheet() {
806
807 $filename = apply_filters( 'password_protected_stylesheet_file', 'password-protected-login.css' );
808
809 $located = locate_template( $filename );
810
811 if ( ! empty( $located ) ) {
812
813 $stylesheet_directory = trailingslashit( get_stylesheet_directory() );
814 $template_directory = trailingslashit( get_template_directory() );
815
816 if ( $stylesheet_directory == substr( $located, 0, strlen( $stylesheet_directory ) ) ) {
817 wp_enqueue_style( 'password-protected-login', get_stylesheet_directory_uri() . '/' . $filename );
818 } elseif ( $template_directory == substr( $located, 0, strlen( $template_directory ) ) ) {
819 wp_enqueue_style( 'password-protected-login', get_template_directory_uri() . '/' . $filename );
820 }
821 }
822
823 }
824
825 /**
826 * Safe Redirect
827 *
828 * Ensure the redirect is to the same site or pluggable list of allowed domains.
829 * If invalid will redirect to ...
830 * Based on the WordPress wp_safe_redirect() function.
831 */
832 public function safe_redirect( $location, $status = 302 ) {
833
834 $location = wp_sanitize_redirect( $location );
835 $location = wp_validate_redirect( $location, home_url() );
836
837 wp_redirect( $location, $status );
838
839 }
840
841 /**
842 * Is Plugin Supported?
843 *
844 * Check to see if there are any known reasons why this plugin may not work in
845 * the user's hosting environment.
846 *
847 * @return boolean
848 */
849 static function is_plugin_supported() {
850
851 return true;
852
853 }
854
855 /**
856 * Check whether a given request has permissions
857 *
858 * Always allow logged in users who require REST API for Gutenberg
859 * and other admin/plugin compatibility.
860 *
861 * @param WP_REST_Request $access Full details about the request.
862 * @return WP_Error|boolean
863 */
864 public function only_allow_logged_in_rest_access( $access ) {
865
866 // If user is not logged in
867 if ( $this->is_active() && ! $this->is_user_logged_in() && ! is_user_logged_in() && ! (bool) get_option( 'password_protected_rest' ) ) {
868 return new WP_Error( 'rest_cannot_access', __( 'Only authenticated users can access the REST API.', 'password-protected' ), array( 'status' => rest_authorization_required_code() ) );
869 }
870
871 return $access;
872
873 }
874
875 /**
876 * Print text above password field
877 * @return void.
878 */
879 public function password_protected_above_password_field() {
880 $text = get_option('password_protected_text_above_password');
881 if( !empty($text) )
882 echo '<div class="password-protected-text-above">' . esc_attr( $text ) . '</div>';
883 }
884
885 /**
886 * Print text below password field
887 * @return void.
888 */
889 public function password_protected_below_password_field() {
890 $text = get_option('password_protected_text_below_password');
891 if( !empty($text) )
892 echo '<div class="password-protected-text-below">' . esc_attr( $text ) . '</div>';
893 }
894
895 }
896