🏠 Root
/
home
/
artorgp
/
www
/
wp-content
/
plugins
/
login-with-ajax
/
Editing: login-with-ajax.php
<?php /* Plugin Name: Login With Ajax Plugin URI: https://loginwithajax.com Description: Ajax driven login widget. Customisable from within your template folder, and advanced settings from the admin area. Author: Pixelite Version: 4.5.1 Author URI: https://pixelite.com/?utm_source=login-with-ajax&utm_medium=plugin-header&utm_campaign=plugins Tags: Login, Ajax, Redirect, BuddyPress, MU, MultiSite, security, sidebar, admin, widget Text Domain: login-with-ajax Copyright (C) 2025 Marcus Sykes This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with this program. If not, see <http://www.gnu.org/licenses/>. */ define('LOGIN_WITH_AJAX_VERSION', '4.5.1'); define('LOGIN_WITH_AJAX_PATH', dirname(__FILE__)); define('LOGIN_WITH_AJAX_URL', trailingslashit(plugin_dir_url(__FILE__))); class LoginWithAjax { /** * If logged in upon instantiation, it is a user object. * @var WP_User */ public static $current_user; /** * List of templates available in the plugin dir and theme (populated in init()) * @var array */ public static $templates = array(); /** * Name of the default template or the currently loaded template. Best not to mess with this and only use for reference. * @var string * @deprecated This will be converted to a private variable in future versions, use \LoginWithAjax::get_template() instead. */ public static $template; /** * lwa_data option * @var array */ public static $data; /** * Location of footer file if one is found when generating a widget, for use in loading template footers. * @var string */ public static $footer_loc; /** * URL for the AJAX Login procedure in templates (including callback and template parameters) * @var string * @deprecated Use \LoginWithAjax::get_login_url() instead. */ public static $url_login; /** * URL for the AJAX Remember Password procedure in templates (including callback and template parameters) * @var string * @deprecated Use \LoginWithAjax::get_remember_url() instead. */ public static $url_remember; /** * URL for the AJAX Registration procedure in templates (including callback and template parameters) * @var string * @deprecated Use \LoginWithAjax::get_register_url() instead. */ public static $url_register; public static $localized; public static $compat_mode = false; // Actions to take upon initial action hook public static function init(){ //Load LWA options self::$data = get_option('lwa_data'); if( !is_array(self::$data) ) self::$data = array(); self::$template = !empty(self::$data['template']) ? self::$data['template'] : 'default'; //Remember the current user, in case there is a logout self::$current_user = wp_get_current_user(); //Generate URLs for login, remember, and register - backward compatibility self::$url_login = static::get_login_url(); self::$url_register = self::get_register_url(); self::$url_remember = static::get_remember_url(); // load dependent files include_once('login-with-ajax-options.php'); include_once('blocks/login/login-block.php'); include_once('ajaxify/loader.php'); include_once('transports/transports.php'); include( 'passkeys/loader.php' ); include_once('2FA/2FA.php'); // add authentication filter for other LWA features/add-ons to hook into instead of directly to WP add_filter('authenticate', '\LoginWithAjax::authenticate', 9999, 1); // determine compat mode self::$data['compat_mode'] = isset(self::$data['compat_mode']) ? self::$data['compat_mode'] : 'auto'; if ( !empty( self::$data['compat_mode'] ) ) { if ( self::$data['compat_mode'] === 'auto' ) { if ( function_exists( 'buddypress' ) || defined( 'BP_VERSION' ) ) { self::$compat_mode = true; } } else { self::$compat_mode = true; } } do_action('lwa_pre_loaded'); //Make decision on what to display if ( !empty($_REQUEST["lwa"]) && (empty(self::$compat_mode) || empty($_REQUEST['action'])) ) { //AJAX Request do_action('lwa_loaded'); // loaded, will exit after this function self::ajax(); }elseif ( isset($_REQUEST["login-with-ajax-widget"]) ) { //Widget Request via AJAX do_action('lwa_loaded'); // loaded, will exit inside this clause $instance = ( !empty($_REQUEST["template"]) ) ? array('template' => $_REQUEST["template"]) : array(); $instance['profile_link'] = ( !empty($_REQUEST["lwa_profile_link"]) ) ? $_REQUEST['lwa_profile_link']:0; self::widget( $instance ); exit(); }else{ // add AJAX handler for compatibility with other plugins like BP that need to be fully loaded add_action( 'wp_ajax_nopriv_login-with-ajax', array( static::class, 'ajax') ); //Add logout/in redirection add_action('wp_logout', '\LoginWithAjax::logoutRedirect'); add_filter('logout_url', '\LoginWithAjax::logoutUrl'); add_filter('login_redirect', '\LoginWithAjax::loginRedirect', 1, 3); add_shortcode('login-with-ajax', '\LoginWithAjax::shortcode'); add_shortcode('lwa', '\LoginWithAjax::shortcode'); } do_action('lwa_loaded'); self::register_scripts_and_styles(); } public static function __callStatic($name, $arguments) { if( $name == 'getRegisterLink' ){ return static::get_register_url( $arguments ); } } public static function register_scripts_and_styles(){ //Enqueue scripts - Only one script enqueued here.... theme CSS takes priority, then default JS if( !empty(self::$data['legacy']) ){ wp_register_style( "login-with-ajax", self::locate_template_url('widget.css'), array(), LOGIN_WITH_AJAX_VERSION ); }else { $css_url = defined('WP_DEBUG') && WP_DEBUG ? 'login-with-ajax.css' : 'login-with-ajax.min.css'; wp_register_style("login-with-ajax", self::locate_template_url($css_url), array(), LOGIN_WITH_AJAX_VERSION); } //Enqueue scripts - Only one script enqueued here.... theme JS takes priority, then default JS if( !empty(self::$data['legacy']) ){ // if in legacy mode, we check first to see if theme overrides with old filenames, if not then use legacy filename extensions that ship with plugin update if( defined('WP_DEBUG') && WP_DEBUG ) { $js_url = self::locate_legacy_template('login-with-ajax.source.js') ? 'login-with-ajax.source.js':'login-with-ajax.legacy.js'; }else { $js_url = self::locate_legacy_template('login-with-ajax.js') ? 'login-with-ajax.js':'login-with-ajax.legacy.min.js'; } }else{ $js_url = defined('WP_DEBUG') && WP_DEBUG ? 'login-with-ajax.js':'login-with-ajax.min.js'; } wp_register_script( "login-with-ajax", self::locate_template_url($js_url), array( 'jquery' ), LOGIN_WITH_AJAX_VERSION ); add_action('wp_enqueue_scripts', 'LoginWithAjax::enqueue_scripts_and_styles'); do_action('lwa_register_scripts'); } public static function enqueue_scripts_and_styles( $force_load = null ){ if( $force_load || !is_admin() || (!empty($_REQUEST['legacy-widget-preview']['idBase']) && $_REQUEST['legacy-widget-preview']['idBase'] == 'loginwithajaxwidget') ) { wp_enqueue_script( 'login-with-ajax' ); wp_enqueue_style( 'login-with-ajax' ); //calendar translations static::localize_js(); do_action('lwa_enqueue', $force_load); } } public static function localize_js ( $handle = 'login-with-ajax' ) { if( static::$localized ) return; $schema = is_ssl() ? 'https':'http'; $js_vars = array('ajaxurl' => admin_url('admin-ajax.php', $schema), 'off' => false ); static::$localized = wp_localize_script($handle, 'LWA', apply_filters('lwa_js_vars', $js_vars, $handle)); } public static function is_rest() { if (defined('REST_REQUEST') && REST_REQUEST // (#1) || isset($_GET['rest_route']) // (#2) && strpos( $_GET['rest_route'] , '/', 0 ) === 0) return true; // (#3) global $wp_rewrite; if ($wp_rewrite === null) $wp_rewrite = new WP_Rewrite(); // (#4) $rest_url = wp_parse_url( trailingslashit( rest_url( ) ) ); $current_url = wp_parse_url( add_query_arg( array( ) ) ); return strpos( $current_url['path'], $rest_url['path'], 0 ) === 0; } public static function widgets_init(){ //Include and register widget include_once('login-with-ajax-widget.php'); register_widget("LoginWithAjaxWidget"); } public static function check_user_and_nonce( $nonce_action_prefix, $user = null, $ajax = true ) { if( empty($user) ) { if( !empty($_REQUEST['log']) ) { $user = get_user_by('login', $_REQUEST['log']); } elseif( !empty($_REQUEST['user_id']) ) { $user = get_user_by('user_id', $_REQUEST['user_id']); } elseif ( is_user_logged_in() ) { $user = wp_get_current_user(); } } if( !empty($user) && !empty($_REQUEST['nonce']) && wp_verify_nonce( $_REQUEST['nonce'], $nonce_action_prefix . $user->ID ) ) { return $user; } elseif( $ajax ) { echo LoginWithAjax::json_encode( array( 'result' => false, 'error' => 'Invalid nonce or user supplied.', // not translated as this is a bug and edge (if at all) ) ); exit(); } return false; } /* * LOGIN OPERATIONS */ // Decides what action to take from the ajax request public static function ajax(){ $return = array('result'=>false, 'error'=>'Unknown command requested'); if( !empty($_REQUEST['login-with-ajax']) ) { switch ( $_REQUEST["login-with-ajax"] ) { case 'login': //A login has been requested //remove known interferences add_filter( 'ws_plugin__s2member_login_redirect', '__return_false' ); $return = self::login(); break; case 'remember': //Remember the password $return = self::remember(); break; case 'register': //Register case 'registration': $return = self::register(); break; default: // backwards-compatible with templates where lwa = registration do_action( 'lwa_ajax_action_' . $_REQUEST["login-with-ajax"], $return ); break; } @header( 'Content-Type: application/javascript; charset=UTF-8', true ); //add this for HTTP -> HTTPS requests which assume it's a cross-site request // allow filters to intervene, including returning nothing to default to LWA error $response = apply_filters('lwa_ajax_'.$_REQUEST["login-with-ajax"], $return); if( !empty($response) ) { echo self::json_encode( $response ); } else { echo self::json_encode( $return ); } } else { echo self::json_encode( $return ); // no action } exit(); } // Reads ajax login creds via POSt, calls the login script and interprets the result public static function login(){ $return = array(); //What we send back $loginResult = false; if( !empty($_REQUEST['log']) && !empty($_REQUEST['pwd']) && trim($_REQUEST['log']) != '' && trim($_REQUEST['pwd'] != '') ){ $loginResult = wp_signon(); $return = static::login_result($loginResult); }else{ $return['result'] = false; $return['error'] = __('Please supply your username and password.', 'login-with-ajax'); } $return['action'] = 'login'; //Return the result array with errors etc. return apply_filters('lwa_login', $return, $loginResult); } public static function login_result( $loginResult ){ $return = array(); if ( $loginResult instanceof WP_User ) { //User login successful self::$current_user = $loginResult; /* @var $loginResult WP_User */ $return['result'] = true; $return['message'] = __("Login Successful, redirecting...",'login-with-ajax'); //Do a redirect if necessary $redirect = self::getLoginRedirect(self::$current_user); if( !empty($_REQUEST['redirect_to']) ) $redirect= wp_sanitize_redirect($_REQUEST['redirect_to']); if( $redirect != '' ){ $return['redirect'] = $redirect; } //If the widget should just update with ajax, then supply the URL here. if( isset($_REQUEST['refresh']) || !empty(self::$data['no_login_refresh']) && self::$data['no_login_refresh'] == 1 ){ if( isset($_REQUEST['refresh']) && empty($_REQUEST['refresh']) || !isset($_REQUEST['refresh']) ){ //Is this coming from a template? $query_vars = ( !empty($_REQUEST['template']) ) ? "&template=".esc_attr($_REQUEST['template']) : ''; $query_vars .= ( !empty($_REQUEST['lwa_profile_link']) ) ? "&lwa_profile_link=1" : ''; $return['widget'] = get_bloginfo('wpurl')."?login-with-ajax-widget=1$query_vars"; $return['message'] = __("Login successful, updating...",'login-with-ajax'); } } } elseif ( is_wp_error($loginResult) ) { //User login failed /* @var WP_Error $loginResult */ $return['result'] = false; $return['error'] = $loginResult->get_error_message(); } else { //Undefined Error $return['result'] = false; $return['error'] = __('An undefined error has ocurred', 'login-with-ajax'); } return $return; } /** * Checks post data and registers user, then exits * @return array */ public static function register(){ $return = array(); if( get_option('users_can_register') ){ $errors = register_new_user($_REQUEST['user_login'], $_REQUEST['user_email']); if ( !is_wp_error($errors) ) { //Success $return['result'] = true; $return['message'] = __('Registration complete. Please check your e-mail.','login-with-ajax'); //add user to blog if multisite if( is_multisite() ){ add_user_to_blog(get_current_blog_id(), $errors, get_option('default_role')); } }else{ //Something's wrong $return['result'] = false; $return['error'] = $errors->get_error_message(); } $return['action'] = 'register'; }else{ $return['result'] = false; $return['error'] = __('Registration has been disabled.','login-with-ajax'); } return $return; } // Reads ajax login creds via POST, calls the login script and interprets the result public static function remember(){ $return = array(); //What we send back //if we're not on wp-login.php, we need to load it since retrieve_password() is located there if( !function_exists('retrieve_password') ){ ob_start(); include_once(ABSPATH.'wp-login.php'); ob_clean(); } $result = retrieve_password(); if ( $result === true ) { //Password correctly remembered $return['result'] = true; $return['message'] = __("We have sent you an email", 'login-with-ajax'); } elseif ( strtolower(get_class($result)) == 'wp_error' ) { //Something went wrong /* @var $result WP_Error */ $return['result'] = false; $return['error'] = $result->get_error_message(); } else { //Undefined Error $return['result'] = false; $return['error'] = __('An undefined error has ocurred', 'login-with-ajax'); } $return['action'] = 'remember'; //Return the result array with errors etc. return $return; } //Added fix for WPML public static function logoutUrl( $logout_url ){ //Add ICL if necessary if( defined('ICL_LANGUAGE_CODE') ){ $logout_url .= ( strstr($logout_url,'?') !== false ) ? '&':'?'; $logout_url .= 'lang='.ICL_LANGUAGE_CODE; } return $logout_url; } // links to register, sign in or remember /** * Returns registration url (escaped) with template querystring if supplied * @param string $template * @return string * @see \LoginWithAjax::template_link() */ public static function get_register_url( $template = null ){ if ( function_exists('bp_get_signup_page') && (empty($_REQUEST['action']) || ($_REQUEST['action'] != 'deactivate' && $_REQUEST['action'] != 'deactivate-selected')) ) { //Buddypress $register_link = bp_get_signup_page(); }elseif ( is_multisite() ) { //MS $register_link = apply_filters( 'wp_signup_location', network_site_url( 'wp-signup.php' ) ); } else { $register_link = wp_registration_url(); } return static::template_link( $register_link, $template ); } /** * Returns forgotten password url (escaped) with template querystring if supplied * @param string $template * @return string * @see \LoginWithAjax::template_link() */ public static function get_remember_url( $template = null ){ $url = apply_filters('lwa_remember_url', wp_lostpassword_url(), $template ); return static::template_link( $url, $template ); } /** * Returns login url (escaped) with template querystring if supplied. * @param string $template * @return string * @see \LoginWithAjax::template_link() */ public static function get_login_url( $template = null ){ $url = apply_filters('lwa_login_url', wp_login_url(), $template); return static::template_link( $url, $template ); } /* * Redirect Functions */ public static function logoutRedirect(){ $redirect = self::getLogoutRedirect(); if($redirect != ''){ wp_safe_redirect($redirect); exit(); } } public static function getLogoutRedirect(){ $data = self::$data; //Global redirect $redirect = ''; if( !empty($data['logout_redirect']) ){ $redirect = $data['logout_redirect']; } //WPML global redirect $lang = !empty($_REQUEST['lang']) ? sanitize_text_field($_REQUEST['lang']):''; $lang = apply_filters('lwa_lang', $lang); if( !empty($lang) ){ if( isset($data["logout_redirect_".$lang]) ){ $redirect = $data["logout_redirect_".$lang]; } } //Role based redirect if( !empty($_REQUEST['redirect']) ){ $redirect = esc_url_raw($_REQUEST['redirect']); }elseif( strtolower(get_class(self::$current_user)) == "wp_user" ){ //Do a redirect if necessary $data = self::$data; $user_role = array_shift(self::$current_user->roles); //Checking for role-based redirects if( !empty($data["role_logout"]) && is_array($data["role_logout"]) && isset($data["role_logout"][$user_role]) ){ $redirect = $data["role_logout"][$user_role]; } //Check for language redirects based on roles if( !empty($lang) ){ if( isset($data["role_logout"][$user_role."_".$lang]) ){ $redirect = $data["role_logout"][$user_role."_".$lang]; } } } //final replaces if( !empty($redirect) ){ $redirect = str_replace("%LASTURL%", wp_get_raw_referer(), $redirect); if( !empty($lang) ){ $redirect = str_replace("%LANG%", $lang.'/', $redirect); } } return esc_url_raw($redirect); } public static function loginRedirect( $redirect, $redirect_notsurewhatthisis, $user ){ $data = self::$data; if( is_object($user) ){ $lwa_redirect = self::getLoginRedirect($user); if( $lwa_redirect != '' ){ $redirect = $lwa_redirect; } } return $redirect; } public static function getLoginRedirect($user){ $data = self::$data; //Global redirect $redirect = false; if( !empty($data['login_redirect']) ){ $redirect = $data["login_redirect"]; } //WPML global redirect $lang = !empty($_REQUEST['lang']) ? sanitize_text_field($_REQUEST['lang']):''; $lang = apply_filters('lwa_lang', $lang); if( !empty($lang) && isset($data["login_redirect_".$lang]) ){ $redirect = $data["login_redirect_".$lang]; } //Role based redirects if( strtolower(get_class($user)) == "wp_user" ){ $user_role = array_shift($user->roles); //Checking for role-based redirects if( isset($data["role_login"][$user_role]) ){ $redirect = $data["role_login"][$user_role]; } //Check for language redirects based on roles if( !empty($lang) && isset($data["role_login"][$user_role."_".$lang]) ){ $redirect = $data["role_login"][$user_role."_".$lang]; } //Do user string replacements $redirect = str_replace('%USERNAME%', $user->user_login, $redirect); $redirect = str_replace('%USERNICENAME%', $user->user_nicename, $redirect); } //Do string replacements if( !strstr( wp_get_referer(), wp_login_url()) ){ $redirect = str_replace("%LASTURL%", wp_get_referer(), $redirect); }else{ $redirect = str_replace('%LASTURL%', admin_url(), $redirect); } if( !empty($lang) ){ $redirect = str_replace("%LANG%", $lang.'/', $redirect); } return esc_url_raw($redirect); } /* * WIDGET OPERATIONS */ public static function output( $instance = array() ){ //Extract widget arguments //Merge instance options with global default options $lwa = wp_parse_args($instance, self::$data); $lwa['id'] = !empty($instance['id']) ? absint($instance['id']) : rand(0, 100000); // for html id fields to be unique $lwa['css_vars'] = array(); $lwa['css_style'] = ''; //Create HSL CSS for barebones color customization if( !empty($lwa['template_color']) ){ if( !is_array($lwa['template_color']) ){ $hsl = explode(',', str_replace(' ', '', $lwa['template_color'])); if( count($hsl) === 3 ) { $lwa['template_color']['H'] = $hsl[0]; $lwa['template_color']['S'] = $hsl[1]; $lwa['template_color']['L'] = $hsl[2]; }elseif( preg_match('/^#?[0-9A-Za-z]{3,6}$/', $lwa['template_color']) ){ // we assume it's hex, convert it to HSL require_once('assets/php/color.php'); try { $hsl = \Login_With_AJAX\Color::hexToHsl($lwa['template_color']); $lwa['template_color'] = array( 'H' => round($hsl['H']), 'S' => round($hsl['S'] * 100), 'L' => round($hsl['L'] * 100), ); }catch ( Exception $exception ){ $lwa['template_color'] = self::$data['template_color']; } }else{ $lwa['template_color'] = self::$data['template_color']; } } $lwa['css_vars']['accent-hue'] = $lwa['template_color']['H']; $lwa['css_vars']['accent-s'] = $lwa['template_color']['S'].'%'; $lwa['css_vars']['accent-l'] = $lwa['template_color']['L'].'%'; } //Deal with specific variables $lwa['profile_link'] = ( !empty($lwa['profile_link']) && $lwa['profile_link'] !== "false" ); $lwa['avatar_size'] = !empty($lwa['avatar_size']) && is_numeric($lwa['avatar_size']) ? absint($lwa['avatar_size']) : 60; // hook here $lwa = apply_filters('lwa_output_data', $lwa, $instance); //Add template logic $templates = static::load_templates(); $template = ( !empty($lwa['template']) && array_key_exists($lwa['template'], $templates) ) ? $lwa['template']:self::$data['template']; $lwa['template'] = static::$template = $template; // convert CSS styles to inline if( empty($lwa['css_vars']['avatar-size']) ) $lwa['css_vars']['avatar-size'] = $lwa['avatar_size'].'px'; foreach( $lwa['css_vars'] as $k => $v ){ $lwa['css_style'] .= '--'.$k.':'. $v.'; '; } //Choose the widget content to display. $show_preview = isset($lwa['v']) && $lwa['v'] && isset($lwa['force_login_display']) && $lwa['force_login_display']; if( is_user_logged_in() && !$show_preview ){ // one more thing... if( !empty($lwa['title_loggedin']) ) { $lwa['title_loggedin'] = str_replace(array('%username%', '%USERNAME%'), \LoginWithAjax::$current_user->display_name, $lwa['title_loggedin']); } //Then check for custom templates or theme template default $lwa_data = $lwa; // backwards compatibility if( !empty($lwa['legacy']) ){ $template_loc = $templates[$template].'/widget_in.php'; include ( $template_loc != '' && file_exists($template_loc) ) ? $template_loc : 'templates/legacy-default/widget_in.php'; }else{ $template_loc = $templates[$template].'/logged-in.php'; include ( $template_loc != '' && file_exists($template_loc) ) ? $template_loc : 'templates/default/logged-in.php'; } }else{ //quick/easy WPML fix, should eventually go into a seperate file if( defined('ICL_LANGUAGE_CODE') ){ if( !function_exists('lwa_wpml_input_var') ){ function lwa_wpml_input_var(){ echo '<input type="hidden" name="lang" id="lang" value="'.esc_attr(ICL_LANGUAGE_CODE).'" />'; } } foreach( array('login_form','lwa_register_form', 'lostpassword_form') as $action ) add_action($action, 'lwa_wpml_input_var'); } //First check for custom templates or theme template default $lwa_data = $lwa; // backwards compatibility if( !empty($lwa['legacy']) ){ $template_loc = $templates[$template].'/widget_out.php'; include ( $template_loc != '' && file_exists($template_loc) ) ? $template_loc : 'templates/legacy-default/widget_out.php'; }else{ $template_loc = $templates[$template].'/login.php'; include ( $template_loc != '' && file_exists($template_loc) ) ? $template_loc : 'templates/default/login.php'; } //quick/easy WPML fix, should eventually go into a seperate file if( defined('ICL_LANGUAGE_CODE') ){ foreach( array('login_form','lwa_register_form', 'lostpassword_form') as $action ) remove_action($action, 'lwa_wpml_input_var'); } } if( !empty(self::$data['template']) ) static::$template = self::$data['template']; } public static function get_output( $instance = array() ){ ob_start(); static::output($instance); return ob_get_clean(); } public static function widget( $instance = array() ){ static::output( $instance ); } public static function shortcode($atts){ $defaults = array( 'profile_link' => true, 'template' => 'default', 'registration' => true, 'redirect' => false, 'redirect_logout' => false, 'remember' => true, 'rememberme' => 1, 'refresh' => true, ); $atts = shortcode_atts($defaults, $atts); unset($atts['modal_button_html']); // security precaution unset($atts['v']); unset($atts['force_login_display']); return static::get_output( $atts ); } public static function new_user_notification($user_login, $login_link, $user_email, $blogname){ //Copied out of /wp-includes/pluggable.php $message = self::$data['notification_message']; $message = str_replace('%USERNAME%', $user_login, $message); $message = str_replace('%PASSWORDURL%', $login_link, $message); $message = str_replace('%BLOGNAME%', $blogname, $message); $message = str_replace('%BLOGURL%', get_bloginfo('wpurl'), $message); $subject = self::$data['notification_subject']; $subject = str_replace('%BLOGNAME%', $blogname, $subject); $subject = str_replace('%BLOGURL%', get_bloginfo('wpurl'), $subject); wp_mail($user_email, $subject, $message); } /* * Auxillary Functions */ /** * Gets name of currently loaded template. * @return string */ public static function get_template(){ return self::$template; } /** * Returns the URL for a relative filepath which would be located in either a child, parent or plugin folder in order of priority. * * This would search for $template_path within: * /wp-content/themes/your-child-theme/plugins/login-with-ajax/... * /wp-content/themes/your-parent-theme/plugins/login-with-ajax/... * /wp-content/plugin-templates/login-with-ajax/... * /wp-content/plugins/login-with-ajax/templates/... * * It is assumed that the file always exists within the core plugin folder if the others aren't found. * * @param string $template_path * * @return string */ public static function locate_template_url( $template_path ){ if( file_exists(get_stylesheet_directory().'/plugins/login-with-ajax/'.$template_path) ){ //Child Theme (or just theme) return trailingslashit(get_stylesheet_directory_uri())."plugins/login-with-ajax/$template_path"; }elseif( file_exists(get_template_directory().'/plugins/login-with-ajax/'.$template_path) ){ //Parent Theme (if parent exists) return trailingslashit(get_template_directory_uri())."plugins/login-with-ajax/$template_path"; }elseif( file_exists(WP_CONTENT_DIR.'/plugin-templates/login-with-ajax/'.$template_path) ){ //login-with-ajax folder in wp-contents return trailingslashit(WP_CONTENT_DIR)."plugin-templates/login-with-ajax/$template_path"; } //Default file in plugin folder return trailingslashit(plugin_dir_url(__FILE__))."templates/$template_path"; } /** * Returns the directory path for a relative filepath which would be located in either a child, parent or plugin folder in order of priority. * * This would search for $template_path within: * /wp-content/themes/your-child-theme/plugins/login-with-ajax/... * /wp-content/themes/your-parent-theme/plugins/login-with-ajax/... * /wp-content/plugin-templates/login-with-ajax/... * * It is assumed that the file always exists within the core plugin folder if the others aren't found. * * @param string $template_path * * @return string */ public static function locate_template( $template_path ){ if( file_exists(get_stylesheet_directory().'/plugins/login-with-ajax/'.$template_path) ){ //Child Theme (or just theme) return get_stylesheet_directory()."/plugins/login-with-ajax/$template_path"; }elseif( file_exists(get_template_directory().'/plugins/login-with-ajax/'.$template_path) ){ //Parent Theme (if parent exists) return get_stylesheet_directory()."/plugins/login-with-ajax/$template_path"; }elseif( file_exists(WP_CONTENT_DIR.'/plugin-templates/login-with-ajax/'.$template_path) ){ //login-with-ajax folder in wp-contents return WP_CONTENT_DIR."plugin-templates/login-with-ajax/$template_path"; } //Default file in plugin folder return LOGIN_WITH_AJAX_PATH."/templates/$template_path"; } /** * Detects whether template file exists in a child or parent theme, false if not. This is used to check if legacy files are still being used. * @param $template_path * @return bool */ public static function locate_legacy_template( $template_path ){ $path = '/plugins/login-with-ajax/'.$template_path; return file_exists(get_stylesheet_directory().$path) || file_exists(get_template_directory().$path); } public static function get_template_path( $template ){ static::load_templates(); if( !empty(static::$templates[$template]) ){ return static::$templates[$template]; } return false; } public static function get_template_data( $template ){ if( empty(static::$templates[$template]) ) $template = 'default'; // get data about a template, we use filters here to provide $settings = self::$data; if( !empty($settings['legacy']) ){ $legacy_templates = array('default' => 'Default', 'divs-only' => 'Divs Only', 'modal' => 'Modal'); $name = !empty($legacy_templates[$template]) ? $legacy_templates[$template] : $template; $data = (object) array('label' => sprintf(esc_html__('%s (Legacy)', 'login-with-ajax'), $name), 'path' => static::get_template_path($template) ); }else{ $templates = array('default' => 'Default', 'modal' => 'Modal', 'minimalistic' => 'Minimalistic', 'modal-minimalistic' => 'Modal Minimalistic', 'classic' => 'Classic', 'classic-vanilla' => 'Classic Vanilla'); $name = !empty($templates[$template]) ? $templates[$template] : $template; $data = (object) array('label' => $name, 'path' => static::get_template_path($template) ); } $template_data = apply_filters('lwa_get_template_data_'.$template, $data); if( $data === $template_data ) $template_data->legacy = true; return $template_data; } /** * Searches for templates within the specified directories and loads their data. * This function will first load known templates within the plugin directory, then it will search for templates within the wp-content/plugin-templates/login-with-ajax folder, * and finally in the parent/child theme folders in the plugins/login-with-ajax (if it exists). The last found directory would override the first from plugin > child theme in precedence. * @param boolean $reload If set templates will be reloaded * @return array */ public static function load_templates($reload = null ){ if( !empty(static::$templates) && !$reload ) return static::$templates; static::$templates = array(); // we will pre-load a functions.php file to allow pre-loading $wp_content_folder = path_join( WP_CONTENT_DIR , "plugin-templates/login-with-ajax/"); if( is_dir($wp_content_folder) && file_exists($wp_content_folder.'functions.php') ){ include($wp_content_folder.'functions.php'); } // allow for short-circuiting template search, maybe desirable for a minor performance boost to avoid unecessary template searching do_action('lwa_before_get_templates'); if( !empty(static::$templates) ) return static::$templates; //Get Templates from theme and default by checking for folders - we assume a template works if a folder exists! //Note that duplicate template names are overwritten in this order of precedence (highest to lowest) - Child Theme > Parent Theme > wp-content folder > Plugin Defaults //First are the defaults in the plugin directory, we know these so hard-code found data self::find_templates( path_join( WP_PLUGIN_DIR , basename( dirname( __FILE__ ) ). "/templates/") ); $plugin_templates_folder = path_join( WP_PLUGIN_DIR , basename( dirname( __FILE__ ) ). "/templates/"); if( !empty(static::$data['legacy']) ) { self::$templates = array('default' => $plugin_templates_folder . 'legacy-default', 'modal' => $plugin_templates_folder . 'legacy-modal', 'divs-only' => $plugin_templates_folder . 'legacy-divs-only',); }else{ self::$templates = array('default' => $plugin_templates_folder . 'default', 'modal' => $plugin_templates_folder . 'modal', 'minimalistic' => $plugin_templates_folder . 'minimalistic', 'modal-minimalistic' => $plugin_templates_folder . 'modal-minimalistic', 'classic' => $plugin_templates_folder . 'classic', 'classic-vanilla' => $plugin_templates_folder . 'classic-vanilla'); } // then, add a search for custom folder in wp-contents/plugin-templates/login-with-ajax/ - The new and preferred way if you have themes that get updated and may overwrite custom lwa themes self::find_templates($wp_content_folder); //Now, the parent theme (if exists) if( get_stylesheet_directory() != get_template_directory() ){ self::find_templates( get_template_directory().'/plugins/login-with-ajax/' ); } //Finally, the child theme self::find_templates( get_stylesheet_directory().'/plugins/login-with-ajax/' ); do_action('lwa_after_get_templates'); return static::$templates; } //Checks a directory for folders and populates the template file public static function find_templates($dir){ if (is_dir($dir)) { if ($dh = opendir($dir)) { $ignore_files = array('.', '..', '.svn', '.git', '2FA'); while (($file = readdir($dh)) !== false) { if ( is_dir($dir . $file) && !in_array($file, $ignore_files) ) { //Template dir found, add it to the template array self::$templates[$file] = path_join($dir, $file); } } closedir($dh); } } } public static function get_templates_data(){ $templates_data = array(); foreach( static::load_templates() as $template => $path ){ $templates_data[$template] = static::get_template_data( $template ); } return apply_filters('lwa_get_templates_data', $templates_data); } public static function get_color_hsl( $css = false, $default = false ){ $hsl = array('H' => 220, 'S' => 86, 'L' => 57); // #3372f0 if( !empty(static::$data['template_color']) && !$default ){ $hsl = static::$data['template_color']; } if( $css ){ return "hsl(".$hsl['H'].", ".$hsl['S']."%, ".$hsl['L']."%)"; } return $hsl; } /** * @param false $default * @return string */ public static function get_color_hex( $default = false ){ $hsl = static::get_color_hsl( false, $default ); try { require_once('assets/php/color.php'); return Login_With_AJAX\Color::hslToHex( array( 'H' => $hsl['H'], 'S' => $hsl['S']/100, 'L' => $hsl['L']/100) ); } catch ( Exception $e ){ return '3372f0'; // return the default color } } /** * @param $color * @param bool $default * @return Login_With_AJAX\Color */ public static function get_color( $color = false, $default = false ){ require_once('assets/php/color.php'); try { return new Login_With_AJAX\Color(static::get_color_hex($default)); } catch( Exception $ex ){ return new Login_With_AJAX\Color('3372f0'); } } /** * Adds a template query param to the provided link and escapes the link. If $template is not provided, then the currently loaded (or default) template is used. If false is provided then query variable will be removed if present in the url. * @param string $url The url to add template link * @param string $template * @return string */ public static function template_link( $url, $template = null ){ if( $template === null ){ $template = self::$template; }elseif( $template === false ){ $template = null; } return esc_url(add_query_arg(array('template'=>$template), $url)); } /** * Returns a sanitized JSONP response from an array * @param array $array * @return string */ public static function json_encode($array){ $return = json_encode($array); if( isset($_REQUEST['callback']) && preg_match("/^jQuery[_a-zA-Z0-9]+$/", $_REQUEST['callback']) ){ $return = $_REQUEST['callback']."($return)"; } return $return; } /** * Triggered by WP's authenticate hook which retriggers an lwa_authenticate filter, allowing LWA add-ons to hook into this and * the possibility to deactivate all authentication triggers in one go (e.g. if a 2FA is successful). * * @param $result * @return mixed|void */ public static function authenticate( $result ){ return apply_filters('lwa_authenticate', $result); } /** * Gets the usermeta table row 'lwa' and returns the specific meta key in that array, for easy retrieval. * @param $user_id * @param $meta_key * * @return array|mixed */ public static function get_user_meta( $user_id, $meta_key, $default = null ) { $meta = get_user_meta( $user_id, 'lwa', true ); if( is_array($meta) && !empty($meta[$meta_key]) ){ return $meta[$meta_key]; } elseif( preg_match('/^([a-z_A-Z0-9-]+)\[([a-z_A-Z0-9-]+)\]/', $meta_key, $matches) ) { // check for array key if( !empty($meta[$matches[1]]) && is_array($meta[$matches[1]]) && isset($meta[$matches[1]][$matches[2]]) ){ return $meta[$matches[1]][$matches[2]]; } } return $default; } /** * Updates the usermeta table row 'lwa' and sets the specific meta key in that array, for easy updating. * * @param $user_id * @param $meta_key * @param $meta_value * * @return bool|int */ public static function update_user_meta( $user_id, $meta_key, $meta_value ) { $meta = get_user_meta( $user_id, 'lwa', true ); if( !is_array($meta) ) $meta = array(); if( preg_match('/^([a-z_A-Z0-9-]+)\[([a-z_A-Z0-9-]+)\]/', $meta_key, $matches) ) { // check for array key if( $meta_value !== null ) { if( empty($meta[$matches[1]]) ) { $meta[$matches[1]] = array(); } $meta[$matches[1]][$matches[2]] = $meta_value; } else { unset( $meta[$matches[1]][$matches[2]] ); } } elseif( $meta_value !== null ) { $meta[$meta_key] = $meta_value; }else { unset( $meta[$meta_key] ); } return update_user_meta( $user_id, 'lwa', $meta ); } /** * Alters the usermeta table row 'lwa' and deletes the specific meta key in that array, for easy deletion. * * @param $user_id * @param $meta_key * * @return bool|int */ public static function delete_user_meta( $user_id, $meta_key ) { // run update with null, which deletes the key return static::update_user_meta( $user_id, $meta_key, null ); } } //Set when to init this class add_action( 'init', '\LoginWithAjax::init' ); add_action( 'widgets_init', '\LoginWithAjax::widgets_init' ); //Installation and Updates $lwa_data = get_option('lwa_data'); if( version_compare( get_option('lwa_version',0), LOGIN_WITH_AJAX_VERSION, '<' ) ){ include_once('lwa-install.php'); } //Include admin file if needed if(is_admin()){ include_once('admin/admin.php'); } //Include pluggable functions file if user specifies in settings if( !empty($lwa_data['notification_override']) ){ include_once('pluggable.php'); } //Template Tag function login_with_ajax($atts = ''){ if( !array($atts) ) $atts = shortcode_parse_atts($atts); echo \LoginWithAjax::shortcode($atts); }
Save
Cancel