mtm_2F_ini_hooks_and_filter();
self::mtm_2F_get_methodes();
}
/**
* Funktion die alle Hooks etc. beinhaltet
*
*
* @since 0.1
*/
function mtm_2F_ini_hooks_and_filter() {
add_action( 'plugins_loaded', array( $this, 'mtm_2F_load_textdomain' ) );
add_action( 'wp_login', array( $this, 'wp_login' ), 10, 2 );
add_action( 'login_form_mtm_2F', array( $this, 'mtm_2F_show_2F_login' ) );
add_action( 'login_form_mtm_2F_validate', array( $this, 'mtm_2F_validate_form' ) );
add_action( 'login_form_mtm_2F_resend_code', array( $this, 'mtm_2F_resend_code' ) );
//Wichtig ist Prio 25 um den Nutzer zu erhalten
//add_filter('authenticate', array($this , 'mtm_2F_filter_authenticate'), 25, 3);
}
/**
* Includiert alle 2F Methoden und Prüft ob diese includiert wurden
*
*
* @since 0.1
* @
*/
public static function mtm_2F_get_methodes() {
include_once( MTM_2F_DIR . "includes" . DIRECTORY_SEPARATOR . "Mtm_2F_Methode.php" );
/**
*
* @since 0.1
* @var array Stellt die Verschiedenen 2FA Möglichkeiten da
* @example "Mtm_2F_newMethode" => MTM_2F_DIR . "includes\Mtm-2F_newMethode.php"
*
*/
$mtm_2F_Methodes = array(
"Mtm_2F_EMail" => MTM_2F_DIR . "includes" . DIRECTORY_SEPARATOR . "Mtm_2F_EMail.php",
"Mtm_2F_SMS" => MTM_2F_DIR . "includes" . DIRECTORY_SEPARATOR . "Mtm_2F_SMS.php"
);
$methodes = array();
foreach ( $mtm_2F_Methodes as $class => $path ) {
include_once( $path );
/**
* Prüft ob die Klasse erfolgreich geladen wurde und holt die einzige Instance in den code.
*/
if ( class_exists( $class ) ) {
try {
$methodes[ $class ] = call_user_func( array( $class, 'get_instance' ) );
} catch ( Exception $e ) {
unset( $methodes[ $class ] );
}
}
}
return $methodes;
}
/**
* Hook Callback
* Nachdem ein benutzer eingeloggt ist
*
* @param $user_login
* @param $user
*/
public static function wp_login( $user_login, $user ) {
//Abfrage ob Benutzer 2FA Nutzt
if ( ! self::mtm_2F_is_user_using_2F( $user->ID ) ) {
//Wenn nicht ist man normal eingeloggt.
return;
}
// Wennn 2FA genutzt wird
// Lösch aktuellen Sitzungs Cookie damit man diesen nicht meh nutzen kann ohnen 2FA
wp_clear_auth_cookie();
wp_destroy_current_session();
//Zeigt eine Login Maske für die Einmalpasswort Eingabe
self::mtm_2F_show_2F_login( $user );
exit;
}
/**
* @param $userID
*
* @return bool
*/
function mtm_2F_is_user_using_2F( $userID ) {
$mtm_2F_use_2FA = get_user_meta( $userID, "mtm_2F_use_2FA" )[0];
if ( ! is_null( $mtm_2F_use_2FA ) && $mtm_2F_use_2FA == "1" ) {
return true;
}
return false;
}
/**
* @param $user
*/
function mtm_2F_show_2F_login( $user ) {
if ( ! $user ) {
$user = wp_get_current_user();
}
$login_nonce = wp_create_nonce( "mtm-2F-login-" . $user->ID );
if(isset($_POST['redirect_to'])){
$redirect_to = wp_sanitize_redirect($_POST['redirect_to']);
}else {
$redirect_to = get_bloginfo("url");
}
self::mtm_2F_login_html( $user, $login_nonce, $redirect_to , "" );
}
/**
* @param $user
* @param $login_nonce
* @param $redirect_to
* @param string $error_msg
* @param string $success_msg
*/
static function mtm_2F_login_html( $user, $login_nonce, $redirect_to, $error_msg = "", $success_msg = "" ) {
$user_methodes = Mtm_2F::mtm_2F_get_availeble_methode( $user->ID );
$methode_class = Mtm_2F::mtm_2F_get_user_primary_methode_classname( $user );
$methode = $user_methodes[ $methode_class ];
$pass_key = Mtm_2F_Methode::genPasswort( 8, "ABCDEFGHJKLMNPQRSTUVWXYZabcdefghijkmnopqrstuvwxyz123456789" );
if ( ! $methode->sendPasswort( $pass_key, $user ) ) {
$error_msg = "error on Sending Passcode";
}
update_user_meta( $user->ID, "mtm_2F_passkey", wp_hash_password( $pass_key ) );
echo $pass_key;
if(function_exists("login_header")){
login_header( __( "Two Factor Authentification", MTM_2F_TEXT_DOMAIN ) );
}
?>
' . esc_html( $error_msg ) . '
';
}
if ( ! empty( $success_msg ) ) {
echo '' . esc_html( $success_msg ) . '
';
}
?>
$methode ) {
if ( $methode->checkUserCanUseMethode( get_userdata( $user_id ) ) ) {
$user_available_methodes[ $class ] = $methode;
}
}
if ( isset( $_POST['mtm_2F_use_2FA'] ) && $_POST['mtm_2F_use_2FA'] == "1" ) {
if ( isset( $_POST['email'] ) ) {
$user_available_methodes[] = "Mtm_2F_EMail";
}
if ( isset( $_POST['phone_number'] ) ) {
$user_available_methodes[] = "Mtm_2F_SMS";
}
}
return $user_available_methodes;
}
/**
* @param $user
*
* @return string
*/
static function mtm_2F_get_user_primary_methode_classname( $user ) {
$classname = "";
$methodes = self::mtm_2F_get_methodes();
$user_premiere_methode = get_user_meta( $user->ID, "mtm_2F_primary_methode" )[0];
if ( isset( $user_premiere_methode ) && $user_premiere_methode != "" && ! is_null( $user_premiere_methode ) && is_string( $user_premiere_methode ) ) {
$classname = $user_premiere_methode;
} else {
$classname = "Mtm_2F_EMail";
}
return $classname;
}
public static function mtm_2F_create_login_url( $params = array(), $scheme = 'login' ) {
if ( ! is_array( $params ) ) {
$params = array();
}
$params = urlencode_deep( $params );
return add_query_arg( $params, site_url( 'wp-login.php', $scheme ) );
}
/**
*
*/
public static function mtm_2F_validate_form() {
//Prüft ob alle Wichtigen Parameter gesetzt sind
if ( ! isset( $_POST['mtm-2F-passkey'], $_POST['wp-auth-id'], $_POST['wp-auth-nonce'] ) ) {
return;
}
//Stellt sicher das es ein int ist
$authID = intval($_POST['wp-auth-id']);
//holt den benutzer anhand der ID
$wpUser = get_user_by( "ID", $authID);
//prüft ob der Benutzer erfolgreich abgerufen werden konnte
if ( ! $wpUser ) {
return;
}
//prüft ob redirect_to gesetzt ist und setzt diese entsprechend.
if ( isset( $_REQUEST['redirect_to'] ) ) {
$redirect_to = apply_filters( 'login_redirect', wp_sanitize_redirect($_REQUEST['redirect_to']), wp_sanitize_redirect($_REQUEST['redirect_to']), $wpUser );
} else {
$redirect_to = get_dashboard_url( $wpUser->ID );
}
$wpUserPasskey = sanitize_text_field($_POST['mtm-2F-passkey']);
$wpNonce = sanitize_text_field($_POST['wp-auth-nonce']);
if(!empty(get_user_meta( $wpUser->ID, "mtm_2F_passkey" )[0])) {
$wpUserMetaPasskey = get_user_meta( $wpUser->ID, "mtm_2F_passkey" )[0];
$wpUserMetaBackupCodes = array();
if(!empty(get_user_meta( $wpUser->ID, "mtm_2F_backup_codes" )[0])){
$wpUserMetaBackupCodes = get_user_meta( $wpUser->ID, "mtm_2F_backup_codes" )[0];
}
$wpNonceAction = "mtm-2F-login-" . $wpUser->ID;
//Prüft ob backup code genutzt
$CheckBackupCodes = false;
foreach ( $wpUserMetaBackupCodes as $key => $code ) {
if ( wp_check_password( $wpUserPasskey, $code ) ) {
$CheckBackupCodes = true;
unset( $wpUserMetaBackupCodes[ array_search( $code, $wpUserMetaBackupCodes ) ] );
update_user_meta( $wpUser->ID, 'mtm_2F_backup_codes', $wpUserMetaBackupCodes );
if ( count( get_user_meta( $wpUser->ID, "mtm_2F_backup_codes" )[0] ) == 1 ) {
wp_mail( $wpUser->user_email, __( "Your backup code are empty!", MTM_2F_TEXT_DOMAIN ), sprintf( __( "Hey %s,\nPlease regenerate new backup codes.\nOnly 1 are availeble!", MTM_2F_TEXT_DOMAIN ), $wpUser->display_name ) );
}
}
}
// Prüft passkey auf richtigkeit
if ( ( wp_check_password( $wpUserPasskey, $wpUserMetaPasskey ) || $CheckBackupCodes ) && ! empty( wp_verify_nonce( $wpNonce, $wpNonceAction ) ) ) {
wp_set_auth_cookie( $authID );
} else {
if ( ! wp_check_password( $wpUserPasskey, $wpUserMetaPasskey ) ) {
self::mtm_2F_login_html( $wpUser, $wpNonce, $redirect_to, __( "Passkey invalide. Try again!", MTM_2F_TEXT_DOMAIN ) );
exit;
} else if ( empty( wp_verify_nonce( $wpNonce, $wpNonceAction ) ) ) {
self::mtm_2F_login_html( $wpUser, $wpNonce, $redirect_to, __( "Login timed out please try again.", MTM_2F_TEXT_DOMAIN ) );
exit;
}
self::mtm_2F_login_html( $wpUser, $wpNonce, $redirect_to, __( "Passkey and login nonce check faild. Try again!", MTM_2F_TEXT_DOMAIN ) );
}
wp_safe_redirect( $redirect_to );
}else {
self::mtm_2F_login_html( $wpUser, $wpNonce, $redirect_to, __( "Passkey invalide. Try again!", MTM_2F_TEXT_DOMAIN ) );
exit;
}
exit;
}
/**
* Load plugin textdomain.
*/
function mtm_2F_load_textdomain() {
load_plugin_textdomain( MTM_2F_TEXT_DOMAIN, "", 'mtm-2F' . DIRECTORY_SEPARATOR . 'lang' . DIRECTORY_SEPARATOR );
//load_plugin_textdomain( MTM_2F_TEXT_DOMAIN, get_stylesheet_directory() . DIRECTORY_SEPARATOR . "languages" );
}
function mtm_2F_resend_code() {
//Prüft ob alle Wichtigen Parameter gesetzt sind
if ( ! isset( $_GET['wp-auth-id'], $_GET['wp-auth-nonce'] ) ) {
return;
}
//holt den benutzer anhand der ID
$wpUser = get_user_by( "ID", intval($_GET['wp-auth-id']) );
//prüft ob der Benutzer erfolgreich abgerufen werden konnte
if ( ! $wpUser ) {
return;
}
//prüft ob redirect_to gesetzt ist und setzt diese entsprechend.
if ( isset( $_REQUEST['redirect_to'] ) ) {
$redirect_to = apply_filters( 'login_redirect', wp_sanitize_redirect($_REQUEST['redirect_to']), wp_sanitize_redirect($_REQUEST['redirect_to']), $wpUser );
} else {
$redirect_to = get_dashboard_url( $wpUser->ID );
}
$wpNonce = $_GET['wp-auth-nonce'];
$wpNonceAction = "mtm-2F-login-" . $wpUser->ID;
if ( wp_verify_nonce( $wpNonce, $wpNonceAction ) == 1 ) {
$login_nonce = wp_create_nonce( "mtm-2F-login-" . $wpUser->ID );
self::mtm_2F_login_html( $wpUser, $login_nonce, wp_sanitize_redirect($_GET['redirect_to']), "" ,__("Passkey resend!", MTM_2F_TEXT_DOMAIN));
}
exit;
}
}