Tôi đã thử một vài cách tiếp cận khác nhau để xác minh email của người dùng. Hiện tại, những gì tôi đang làm là đây:
Khi người dùng đăng ký lần đầu, hãy đặt user_metadata 'email_not_verified' của người dùng thành 1.
add_action( 'user_register', 'sc_user_email_not_verified' );
function sc_user_email_not_verified( $user_id ) {
update_user_meta( $user_id, 'email_not_verified', 1 );
}
Sau đó, ghi đè wp_new_user_notification
chức năng để nó thêm 'email_verification_key' vào url đăng nhập. Nó cũng lưu khóa đó dưới dạng user_metadata.
function wp_new_user_notification( $user_id, $depreciated = null, $notify = '' ) {
...
$email_verification_key = wp_generate_password( 20, false );
update_user_meta( $user_id, 'email_verification_key', $email_verification_key );
$message = sprintf(__('Username: %s'), $user->user_login) . "\r\n\r\n";
$message .= __('To set your password, visit the following address:') . "\r\n\r\n";
$message .= '<' . network_site_url("wp-login.php?action=rp&key=$key&mail_key=$email_verification_key&login=" . rawurlencode($user->user_login), 'login') . ">\r\n\r\n";
$message .= wp_login_url() . "\r\n";
wp_mail($user->user_email, sprintf(__('[%s] Your username and password info'), $blogname), $message);
}
Sau đó, móc vào hành động 'validate_password_reset' để kiểm tra xem khóa xác minh email từ yêu cầu đặt lại mật khẩu có khớp với khóa đã lưu không. Nếu các khóa không khớp, hãy xóa người dùng và chuyển hướng họ trở lại biểu mẫu đăng ký với lỗi 'emailnotverified'. Nếu các khóa khớp nhau, hãy xóa siêu dữ liệu 'email_not_verified'.
add_action( 'validate_password_reset', 'sc_verify_user_email', 10, 2 );
function sc_verify_user_email( $errors, $user ) {
if ( isset( $_REQUEST['mail_key'] ) ) {
$email_verification_key = $_REQUEST['mail_key'];
$saved_key = get_user_meta( $user->ID, 'email_verification_key', true );
if ( ! ( $email_verification_key === $saved_key ) ) {
require_once( ABSPATH . 'wp-admin/includes/user.php' );
wp_delete_user( $user->ID );
wp_redirect( network_site_url( "wp-login.php?action=register&error=emailnotverified" ) );
exit;
} else {
delete_user_meta( $user->ID, 'email_not_verified' );
}
}
}
Nếu email không được xác minh, hãy thêm một thông báo sẽ được hiển thị trên trang đăng ký khi có lỗi 'emailnotverified'.
add_filter( 'login_message', 'sc_email_not_verified_message' );
function sc_email_not_verified_message() {
$action = isset( $_REQUEST['action'] ) ? $_REQUEST['action'] : '';
$error = isset( $_REQUEST['error'] ) ? $_REQUEST['error'] : '';
if ( 'register' === $action && 'emailnotverified' === $error ) {
$message = '<p class="message">' . __( 'Your email address could not be verified. Please try registering again.' ) . '</p>';
return $message;
}
}
Bên trong chức năng Đăng nhập một lần, nếu người dùng có siêu dữ liệu 'email_not_verified', đừng đăng nhập chúng vào ứng dụng khách. (Điều này có thể xảy ra nếu người dùng được tạo thông qua biểu mẫu đăng ký được thêm bởi một plugin.)
$current_user = wp_get_current_user();
if ( get_user_meta( $current_user->ID, 'email_not_verified', true ) ) {
echo( 'Invalid request.' ); // This needs to be changed to a redirect.
exit;
}
Tôi cũng đã thêm một hộp kiểm để hiển thị và ghi đè trạng thái xác minh email của người dùng trên trang 'chỉnh sửa người dùng'.
Biên tập:
Móc vào validate_password_reset
hành động có lẽ không phải là cách tốt nhất để làm điều này. Nó được gọi trước khi mật khẩu được đặt lại, vì vậy email sẽ được xác minh ngay cả khi có lỗi trong quá trình đặt lại mật khẩu (ví dụ: nếu khóa hết hạn hoặc không hợp lệ.)
Một cách tiếp cận tốt hơn dường như là móc vào resetpass_form
hành động và thêm một trường ẩn vào biểu mẫu đặt lại mật khẩu giữ giá trị của 'mail_key':
add_action( 'resetpass_form' 'sc_mail_key_field' );
function sc_mail_key_field() {
if ( isset( $_REQUEST['mail_key'] ) ) {
$mail_key = sanitize_key( wp_unslash( $_REQUEST['mail_key'] ) );
wp_nonce_field( 'verify_email', 'verify_email_nonce' );
echo '<input type="hidden" name="mail_key" value="' . esc_attr( $mail_key ) . '" />';
}
}
Sau đó có thể móc vào after_password_reset
hành động để xác minh khóa thư đã lưu so với $_POST['mail_key']
giá trị.
Một plugin ví dụ có thể được tìm thấy ở đây: plugin xác minh địa chỉ email
empty( get_userdata( $user_id )->user_activation_key )
nào?