PluginProbe
Jetpack – WP Security, Backup, Speed, & Growth / 16.3-beta
Jetpack – WP Security, Backup, Speed, & Growth v16.3-beta
16.3-beta 16.3-a.5 16.3-a.7 16.3-a.3 16.3-a.1 16.2 16.2-beta 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 All 507 releases
jetpack / jetpack_vendor / automattic / jetpack-connection / src / sso / class-force-2fa.php

class-force-2fa.php in Jetpack – WP Security, Backup, Speed, & Growth 16.3-beta, at jetpack_vendor/automattic/jetpack-connection/src/sso/class-force-2fa.php

187 lines 4.8 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2 /**
3 * Force Jetpack 2FA Functionality
4 *
5 * Ported from original repo at https://github.com/automattic/jetpack-force-2fa
6 *
7 * @package automattic/jetpack-connection
8 */
9
10 namespace Automattic\Jetpack\Connection\SSO;
11
12 use Automattic\Jetpack\Connection\SSO;
13 use Automattic\Jetpack\Modules;
14 use WP_Error;
15
16 /**
17 * Force users to use two-factor authentication.
18 *
19 * @phan-constructor-used-for-side-effects
20 */
21 class Force_2FA {
22 /**
23 * The role to force 2FA for.
24 *
25 * Defaults to manage_options via the plugins_loaded function.
26 * Can be modified with the jetpack_force_2fa_cap filter.
27 *
28 * @var string
29 */
30 private $role;
31
32 /**
33 * Constructor.
34 */
35 public function __construct() {
36 add_action( 'after_setup_theme', array( $this, 'plugins_loaded' ) );
37 }
38
39 /**
40 * Load the plugin via the plugins_loaded hook.
41 */
42 public function plugins_loaded() {
43 /**
44 * Filter the role to force 2FA for.
45 * Defaults to manage_options.
46 *
47 * @param string $role The role to force 2FA for.
48 * @return string
49 * @since jetpack-12.7
50 * @module SSO
51 */
52 $this->role = apply_filters( 'jetpack_force_2fa_cap', 'manage_options' );
53
54 // Bail if Jetpack SSO is not active
55 if ( ! ( new Modules() )->is_active( 'sso' ) ) {
56 add_action( 'admin_notices', array( $this, 'admin_notice' ) );
57 return;
58 }
59
60 $this->force_2fa();
61 }
62
63 /**
64 * Display an admin notice if Jetpack SSO is not active.
65 */
66 public function admin_notice() {
67 /**
68 * Filter if an admin notice is deplayed when Force 2FA is required, but SSO is not enabled.
69 * Defaults to true.
70 *
71 * @param bool $display_notice Whether to display the notice.
72 * @return bool
73 * @since jetpack-12.7
74 * @module SSO
75 */
76 if ( apply_filters( 'jetpack_force_2fa_dependency_notice', true ) && current_user_can( $this->role ) ) {
77 wp_admin_notice(
78 esc_html__( 'Jetpack Force 2FA requires Jetpack’s SSO feature.', 'jetpack-connection' ),
79 array(
80 'type' => 'warning',
81 )
82 );
83 }
84 }
85
86 /**
87 * Force 2FA when using Jetpack SSO and force Jetpack SSO.
88 *
89 * @return void
90 */
91 private function force_2fa() {
92 // Allows WP.com login to a local account if it matches the local account.
93 add_filter( 'jetpack_sso_match_by_email', '__return_true', 9999 );
94
95 // multisite
96 if ( is_multisite() ) {
97
98 // Hide the login form
99 add_filter( 'jetpack_remove_login_form', '__return_true', 9999 );
100 add_filter( 'jetpack_sso_bypass_login_forward_wpcom', '__return_true', 9999 );
101 add_filter( 'jetpack_sso_display_disclaimer', '__return_false', 9999 );
102
103 add_filter(
104 'wp_authenticate_user',
105 function () {
106 return new WP_Error( 'wpcom-required', $this->get_login_error_message() ); },
107 9999
108 );
109
110 add_filter( 'jetpack_sso_require_two_step', '__return_true' );
111
112 add_filter( 'allow_password_reset', '__return_false' );
113 } else {
114 // Not multisite.
115
116 // Completely disable the standard login form for admins.
117 add_filter(
118 'wp_authenticate_user',
119 function ( $user ) {
120 if ( is_wp_error( $user ) ) {
121 return $user;
122 }
123 if ( $user->has_cap( $this->role ) ) {
124 return new WP_Error( 'wpcom-required', $this->get_login_error_message(), $user->user_login );
125 }
126 return $user;
127 },
128 9999
129 );
130
131 add_filter(
132 'allow_password_reset',
133 function ( $allow, $user_id ) {
134 if ( user_can( $user_id, $this->role ) ) {
135 return false;
136 }
137 return $allow; },
138 9999,
139 2
140 );
141
142 add_action( 'jetpack_sso_pre_handle_login', array( $this, 'jetpack_set_two_step' ) );
143 }
144 }
145
146 /**
147 * Specifically set the two step filter for Jetpack SSO.
148 *
149 * @param Object $user_data The user data from WordPress.com.
150 *
151 * @return void
152 */
153 public function jetpack_set_two_step( $user_data ) {
154 $user = SSO::get_user_by_wpcom_id( $user_data->ID );
155
156 // Borrowed from Jetpack. Ignores the match_by_email setting.
157 if ( empty( $user ) ) {
158 $user = get_user_by( 'email', $user_data->email );
159 }
160
161 if ( $user && $user->has_cap( $this->role ) ) {
162 add_filter( 'jetpack_sso_require_two_step', '__return_true' );
163 }
164 }
165
166 /**
167 * Get the login error message.
168 *
169 * @return string
170 */
171 private function get_login_error_message() {
172 /**
173 * Filter the login error message.
174 * Defaults to a message that explains the user must use a WordPress.com account with 2FA enabled.
175 *
176 * @param string $message The login error message.
177 * @return string
178 * @since jetpack-12.7
179 * @module SSO
180 */
181 return apply_filters(
182 'jetpack_force_2fa_login_error_message',
183 sprintf( 'For added security, please log in using your WordPress.com account.<br /><br />Note: Your account must have <a href="%1$s" target="_blank">Two Step Authentication</a> enabled, which can be configured from <a href="%2$s" target="_blank">Security Settings</a>.', 'https://support.wordpress.com/security/two-step-authentication/', 'https://wordpress.com/me/security/two-step' )
184 );
185 }
186 }
187