Files
shopify-ai-backup/chat/templates/Change Login URL/pc-auto-login/plugin-name.php
2026-02-09 18:09:12 +00:00

721 lines
26 KiB
PHP

<?php
/**
* Plugin Name: Plugin Compass Appointment manager
* Plugin URI: https://plugincompass.com/plugins/plugin-name
* Description: Allows users to change the URL of their wp-login page with a custom slug via an admin settings panel.
* Version: 1.0.0
* Author: Plugin Compass
* Author URI: https://plugincompass.com
* License: GPL v2 or later
* License URI: https://www.gnu.org/licenses/gpl-2.0.html
* Text Domain: plugin-name
* Domain Path: /languages
* Update URI: false
*/
// Prevent direct access
if (!defined('ABSPATH')) {
exit;
}
// Define plugin constants
define('PLUGIN_NAME_VERSION', '1.0.0');
define('PLUGIN_NAME_PLUGIN_DIR', plugin_dir_path(__FILE__));
define('PLUGIN_NAME_PLUGIN_URL', plugin_dir_url(__FILE__));
define('PLUGIN_NAME_PLUGIN_BASENAME', plugin_basename(__FILE__));
// Prevent WordPress.org update checks
add_filter('site_transient_update_plugins', function($value) {
$plugin_file = plugin_basename(__FILE__);
if (isset($value->response[$plugin_file])) {
unset($value->response[$plugin_file]);
}
return $value;
});
/**
* Main Plugin Class
*/
class Plugin_Name_Login_URL_Changer {
/**
* Option name for storing custom login URL
*/
const OPTION_NAME = 'plugin_name_custom_login_url';
/**
* Default login slug
*/
const DEFAULT_SLUG = 'wp-login.php';
/**
* Instance of this class
*/
private static $instance = null;
/**
* Get instance of this class
*/
public static function get_instance() {
if (null === self::$instance) {
self::$instance = new self();
}
return self::$instance;
}
/**
* Constructor
*/
private function __construct() {
$this->init();
}
/**
* Initialize plugin
*/
private function init() {
// Admin hooks
add_action('admin_menu', array($this, 'add_admin_menu'));
add_action('admin_init', array($this, 'register_settings'));
add_action('admin_enqueue_scripts', array($this, 'enqueue_admin_assets'));
add_action('admin_notices', array($this, 'display_admin_notices'));
// Frontend hooks - URL rewriting and blocking
add_action('init', array($this, 'handle_custom_login_url'), 1);
add_action('login_init', array($this, 'block_default_login'), 1);
add_filter('site_url', array($this, 'filter_login_url'), 10, 4);
add_filter('network_site_url', array($this, 'filter_login_url'), 10, 3);
add_filter('wp_redirect', array($this, 'filter_wp_redirect'), 10, 2);
add_filter('lostpassword_url', array($this, 'filter_lostpassword_url'), 10, 2);
add_filter('register_url', array($this, 'filter_register_url'), 10, 2);
// Rewrite rules
add_action('init', array($this, 'add_rewrite_rules'), 2);
add_filter('query_vars', array($this, 'add_query_vars'));
}
/**
* Get custom login slug
*/
public function get_custom_slug() {
$slug = get_option(self::OPTION_NAME, '');
return sanitize_text_field($slug);
}
/**
* Check if custom URL is enabled
*/
public function is_custom_url_enabled() {
$slug = $this->get_custom_slug();
return !empty($slug) && $slug !== self::DEFAULT_SLUG;
}
/**
* Get full custom login URL
*/
public function get_custom_login_url() {
if (!$this->is_custom_url_enabled()) {
return wp_login_url();
}
$slug = $this->get_custom_slug();
return home_url('/' . $slug);
}
/**
* Add admin menu page
*/
public function add_admin_menu() {
add_options_page(
__('Login URL Settings', 'plugin-name'),
__('Login URL', 'plugin-name'),
'manage_options',
'plugin-name-login-url',
array($this, 'render_settings_page')
);
}
/**
* Register settings
*/
public function register_settings() {
register_setting(
'plugin_name_login_url_settings',
self::OPTION_NAME,
array(
'type' => 'string',
'sanitize_callback' => array($this, 'sanitize_login_slug'),
'default' => ''
)
);
}
/**
* Sanitize login slug
*/
public function sanitize_login_slug($slug) {
// Check nonce
if (!isset($_POST['plugin_name_login_url_nonce']) || !wp_verify_nonce($_POST['plugin_name_login_url_nonce'], 'plugin_name_save_login_url')) {
add_settings_error(
'plugin_name_login_url',
'invalid_nonce',
__('Security check failed. Please try again.', 'plugin-name'),
'error'
);
return get_option(self::OPTION_NAME, '');
}
// Check capabilities
if (!current_user_can('manage_options')) {
add_settings_error(
'plugin_name_login_url',
'insufficient_permissions',
__('You do not have permission to change this setting.', 'plugin-name'),
'error'
);
return get_option(self::OPTION_NAME, '');
}
$slug = sanitize_text_field($slug);
$slug = trim($slug, '/');
// If empty or default, clear the custom URL
if (empty($slug) || $slug === 'wp-login.php' || $slug === 'wp-login') {
add_settings_error(
'plugin_name_login_url',
'settings_updated',
__('Login URL has been reset to default.', 'plugin-name'),
'success'
);
return '';
}
// Validate slug format
if (!preg_match('/^[a-z0-9-]+$/', $slug)) {
add_settings_error(
'plugin_name_login_url',
'invalid_slug',
__('The login URL can only contain lowercase letters, numbers, and hyphens.', 'plugin-name'),
'error'
);
return get_option(self::OPTION_NAME, '');
}
// Check for reserved slugs
$reserved_slugs = array(
'wp-admin', 'wp-content', 'wp-includes',
'admin', 'login', 'logout', 'register',
'wp-json', 'feed', 'comments', 'trackback',
'xmlrpc', 'wp-login', 'wp-signup', 'wp-activate'
);
if (in_array($slug, $reserved_slugs, true)) {
add_settings_error(
'plugin_name_login_url',
'reserved_slug',
__('This URL is reserved and cannot be used.', 'plugin-name'),
'error'
);
return get_option(self::OPTION_NAME, '');
}
// Check for conflicts with existing pages/posts
$existing = get_page_by_path($slug, OBJECT, array('page', 'post'));
if ($existing) {
add_settings_error(
'plugin_name_login_url',
'slug_conflict',
__('This URL conflicts with an existing page or post.', 'plugin-name'),
'error'
);
return get_option(self::OPTION_NAME, '');
}
// Success message
add_settings_error(
'plugin_name_login_url',
'settings_updated',
sprintf(
__('Login URL has been changed to: %s', 'plugin-name'),
'<code>' . esc_url(home_url('/' . $slug)) . '</code>'
),
'success'
);
return $slug;
}
/**
* Render settings page
*/
public function render_settings_page() {
if (!current_user_can('manage_options')) {
return;
}
$current_slug = $this->get_custom_slug();
$custom_url = $this->get_custom_login_url();
$is_custom = $this->is_custom_url_enabled();
?>
<div class="wrap plugin-name-wrap">
<h1><?php echo esc_html(get_admin_page_title()); ?></h1>
<?php settings_errors('plugin_name_login_url'); ?>
<div class="plugin-name-card">
<h2><?php _e('Custom Login URL', 'plugin-name'); ?></h2>
<p><?php _e('Change the URL of your WordPress login page to improve security and prevent automated attacks.', 'plugin-name'); ?></p>
<?php if ($is_custom) : ?>
<div class="plugin-name-notice plugin-name-notice-warning">
<span class="dashicons dashicons-warning"></span>
<p>
<strong><?php _e('Important:', 'plugin-name'); ?></strong>
<?php _e('Your login URL has been changed. Make sure to bookmark the new URL:', 'plugin-name'); ?>
<br>
<code class="plugin-name-url"><?php echo esc_url($custom_url); ?></code>
</p>
</div>
<?php endif; ?>
<form method="post" action="options.php">
<?php wp_nonce_field('plugin_name_save_login_url', 'plugin_name_login_url_nonce'); ?>
<?php settings_fields('plugin_name_login_url_settings'); ?>
<table class="form-table">
<tr>
<th scope="row">
<label for="<?php echo esc_attr(self::OPTION_NAME); ?>">
<?php _e('Custom Login Slug', 'plugin-name'); ?>
</label>
</th>
<td>
<div class="plugin-name-input-group">
<span class="plugin-name-input-prefix"><?php echo esc_url(home_url('/')); ?></span>
<input type="text"
id="<?php echo esc_attr(self::OPTION_NAME); ?>"
name="<?php echo esc_attr(self::OPTION_NAME); ?>"
value="<?php echo esc_attr($current_slug); ?>"
class="regular-text"
placeholder="my-secret-login"
pattern="[a-z0-9-]+"
title="<?php esc_attr_e('Only lowercase letters, numbers, and hyphens allowed', 'plugin-name'); ?>">
</div>
<p class="description">
<?php _e('Enter a custom slug for your login page (e.g., my-secret-login). Use only lowercase letters, numbers, and hyphens.', 'plugin-name'); ?>
</p>
<?php if ($is_custom) : ?>
<p class="description">
<?php _e('Leave empty and save to reset to default wp-login.php', 'plugin-name'); ?>
</p>
<?php endif; ?>
</td>
</tr>
</table>
<?php submit_button($is_custom ? __('Update Login URL', 'plugin-name') : __('Save Login URL', 'plugin-name')); ?>
</form>
</div>
<div class="plugin-name-card plugin-name-card-info">
<h3><?php _e('Current Login URLs', 'plugin-name'); ?></h3>
<table class="widefat plugin-name-table">
<tbody>
<tr>
<td><strong><?php _e('Custom Login URL:', 'plugin-name'); ?></strong></td>
<td>
<?php if ($is_custom) : ?>
<code><?php echo esc_url($custom_url); ?></code>
<a href="<?php echo esc_url($custom_url); ?>" class="button button-small" target="_blank">
<?php _e('Visit', 'plugin-name'); ?>
</a>
<?php else : ?>
<em><?php _e('Not set (using default)', 'plugin-name'); ?></em>
<?php endif; ?>
</td>
</tr>
<tr>
<td><strong><?php _e('Default Login URL:', 'plugin-name'); ?></strong></td>
<td>
<code><?php echo esc_url(wp_login_url()); ?></code>
<?php if ($is_custom) : ?>
<span class="plugin-name-badge plugin-name-badge-blocked"><?php _e('Blocked', 'plugin-name'); ?></span>
<?php else : ?>
<span class="plugin-name-badge plugin-name-badge-active"><?php _e('Active', 'plugin-name'); ?></span>
<?php endif; ?>
</td>
</tr>
</tbody>
</table>
</div>
<div class="plugin-name-card plugin-name-card-help">
<h3><?php _e('Help & Information', 'plugin-name'); ?></h3>
<ul>
<li><?php _e('The custom login URL will replace the default wp-login.php', 'plugin-name'); ?></li>
<li><?php _e('The old wp-login.php URL will be blocked when a custom URL is set', 'plugin-name'); ?></li>
<li><?php _e('Make sure to bookmark your new login URL before logging out', 'plugin-name'); ?></li>
<li><?php _e('If you forget your custom URL, you can disable this plugin via FTP or database to restore default access', 'plugin-name'); ?></li>
</ul>
</div>
</div>
<?php
}
/**
* Enqueue admin assets
*/
public function enqueue_admin_assets($hook) {
if ('settings_page_plugin-name-login-url' !== $hook) {
return;
}
wp_enqueue_style(
'plugin-name-admin-css',
PLUGIN_NAME_PLUGIN_URL . 'admin/css/admin-style.css',
array(),
PLUGIN_NAME_VERSION
);
}
/**
* Display admin notices
*/
public function display_admin_notices() {
$screen = get_current_screen();
if (!$screen || $screen->id !== 'settings_page_plugin-name-login-url') {
return;
}
// Only show on the settings page if settings_errors hasn't already shown
}
/**
* Add rewrite rules for custom login URL
*/
public function add_rewrite_rules() {
$slug = $this->get_custom_slug();
if (empty($slug)) {
return;
}
add_rewrite_rule(
'^' . $slug . '/?$',
'index.php?plugin_name_login=1',
'top'
);
add_rewrite_rule(
'^' . $slug . '/([^/]+)/?$',
'index.php?plugin_name_login=1&action=$matches[1]',
'top'
);
}
/**
* Add custom query vars
*/
public function add_query_vars($vars) {
$vars[] = 'plugin_name_login';
return $vars;
}
/**
* Handle custom login URL
*/
public function handle_custom_login_url() {
// Check query var (for when rewrite rules work)
$has_query_var = get_query_var('plugin_name_login');
// Fallback: check REQUEST_URI directly (for when rewrite rules don't work)
$request_uri = isset($_SERVER['REQUEST_URI']) ? sanitize_text_field($_SERVER['REQUEST_URI']) : '';
$custom_slug = $this->get_custom_slug();
// Remove query string for comparison
$request_path = strtok($request_uri, '?');
$request_path = trim($request_path, '/');
// Check if we're accessing the custom slug directly
$is_custom_url = !empty($custom_slug) && ($request_path === $custom_slug || preg_match('#^' . preg_quote($custom_slug, '#') . '(/.*)?$#', $request_path));
if (!$has_query_var && !$is_custom_url) {
return;
}
// Set the query var for compatibility
if ($is_custom_url && !$has_query_var) {
set_query_var('plugin_name_login', 1);
// Extract action from URL if present
$action = 'login';
if (preg_match('#^' . preg_quote($custom_slug, '#') . '/([^/]+)#', $request_path, $matches)) {
$action = $matches[1];
}
set_query_var('action', $action);
}
// Prevent caching
nocache_headers();
$action = get_query_var('action') ? get_query_var('action') : 'login';
// Set up login globals that wp-login.php expects
global $error, $interim_login, $action;
// Parse any login errors from query string
$error = '';
if (!empty($_GET['login'])) {
$login = sanitize_text_field($_GET['login']);
switch ($login) {
case 'failed':
$error = __('<strong>Error:</strong> Invalid username or password.', 'plugin-name');
break;
case 'empty':
$error = __('<strong>Error:</strong> Username and password are required.', 'plugin-name');
break;
case 'loggedout':
$error = __('You are now logged out.', 'plugin-name');
break;
case 'expired':
$error = __('Your session has expired. Please log in again.', 'plugin-name');
break;
}
}
// Re-login for interim login
$interim_login = isset($_REQUEST['interim-login']);
// Handle POST requests (form submissions)
if ($_SERVER['REQUEST_METHOD'] === 'POST' && isset($_POST['log'])) {
$this->handle_login_post();
return;
}
// Display the login form
$this->render_login_form($action, $error);
exit;
}
/**
* Handle login form POST submission
*/
private function handle_login_post() {
$user_login = isset($_POST['log']) ? sanitize_user($_POST['log']) : '';
$user_pass = isset($_POST['pwd']) ? $_POST['pwd'] : '';
$remember = isset($_POST['rememberme']) ? true : false;
$credentials = array(
'user_login' => $user_login,
'user_password' => $user_pass,
'remember' => $remember
);
$user = wp_signon($credentials, is_ssl());
if (is_wp_error($user)) {
// Redirect back to custom login with error
$redirect_to = $this->get_custom_login_url();
wp_redirect(add_query_arg('login', 'failed', $redirect_to));
exit;
}
// Successful login - redirect to admin or requested location
$redirect_to = isset($_POST['redirect_to']) ? esc_url_raw($_POST['redirect_to']) : admin_url();
wp_redirect($redirect_to);
exit;
}
/**
* Render the login form
*/
private function render_login_form($action, $error) {
$custom_slug = $this->get_custom_slug();
$login_url = $this->get_custom_login_url();
$redirect_to = isset($_REQUEST['redirect_to']) ? esc_url_raw($_REQUEST['redirect_to']) : admin_url();
// Output login form
?>
<!DOCTYPE html>
<html xmlns="http://www.w3.org/1999/xhtml" <?php language_attributes(); ?>>
<head>
<meta http-equiv="Content-Type" content="<?php bloginfo('html_type'); ?>; charset=<?php bloginfo('charset'); ?>" />
<title><?php bloginfo('name'); ?> &rsaquo; Log In</title>
<?php
wp_enqueue_style('login');
wp_enqueue_script('user-profile');
do_action('login_enqueue_scripts');
do_action('login_head');
?>
</head>
<body class="login wp-core-ui">
<div id="login">
<h1><a href="<?php echo esc_url(apply_filters('login_headerurl', home_url())); ?>"><?php echo get_bloginfo('name', 'display'); ?></a></h1>
<?php if (!empty($error)) : ?>
<div id="login_error"><?php echo $error; ?></div>
<?php endif; ?>
<form name="loginform" id="loginform" action="<?php echo esc_url($login_url); ?>" method="post">
<p>
<label for="user_login">Username or Email Address<br />
<input type="text" name="log" id="user_login" class="input" value="<?php echo esc_attr(isset($_POST['log']) ? $_POST['log'] : ''); ?>" size="20" autocapitalize="off" /></label>
</p>
<p>
<label for="user_pass">Password<br />
<input type="password" name="pwd" id="user_pass" class="input" value="" size="20" /></label>
</p>
<?php do_action('login_form'); ?>
<p class="forgetmenot">
<label for="rememberme"><input name="rememberme" type="checkbox" id="rememberme" value="forever" <?php checked(isset($_POST['rememberme'])); ?> /> Remember Me</label>
</p>
<p class="submit">
<input type="submit" name="wp-submit" id="wp-submit" class="button button-primary button-large" value="Log In" />
<input type="hidden" name="redirect_to" value="<?php echo esc_url($redirect_to); ?>" />
</p>
</form>
<p id="nav">
<a href="<?php echo esc_url(wp_lostpassword_url()); ?>">Lost your password?</a>
</p>
<p id="backtoblog">
<a href="<?php echo esc_url(home_url('/')); ?>">&larr; Back to <?php echo get_bloginfo('name', 'display'); ?></a>
</p>
</div>
<?php do_action('login_footer'); ?>
<?php wp_footer(); ?>
</body>
</html>
<?php
}
/**
* Block default login when custom URL is set
*/
public function block_default_login() {
if (!$this->is_custom_url_enabled()) {
return;
}
// Allow access for certain actions that need wp-login.php
$allowed_actions = array('logout', 'postpass', 'rp', 'resetpass');
$action = isset($_REQUEST['action']) ? sanitize_text_field($_REQUEST['action']) : 'login';
if (in_array($action, $allowed_actions, true)) {
return;
}
// Check if this is the real wp-login.php file (not our custom URL)
$request_uri = isset($_SERVER['REQUEST_URI']) ? sanitize_text_field($_SERVER['REQUEST_URI']) : '';
$custom_slug = $this->get_custom_slug();
if (strpos($request_uri, 'wp-login.php') !== false && strpos($request_uri, $custom_slug) === false) {
// Return 404 or redirect to custom URL
wp_redirect(home_url('/404'), 404);
exit;
}
}
/**
* Filter login URL
*/
public function filter_login_url($url, $path, $scheme = null, $blog_id = null) {
if (!$this->is_custom_url_enabled()) {
return $url;
}
// Only filter wp-login.php URLs
if (strpos($url, 'wp-login.php') === false) {
return $url;
}
$custom_slug = $this->get_custom_slug();
$custom_url = str_replace('wp-login.php', $custom_slug, $url);
return $custom_url;
}
/**
* Filter wp_redirect
*/
public function filter_wp_redirect($location, $status) {
if (!$this->is_custom_url_enabled()) {
return $location;
}
// Replace wp-login.php with custom slug in redirects
if (strpos($location, 'wp-login.php') !== false) {
$custom_slug = $this->get_custom_slug();
$location = str_replace('wp-login.php', $custom_slug, $location);
}
return $location;
}
/**
* Filter lostpassword URL
*/
public function filter_lostpassword_url($url, $redirect) {
if (!$this->is_custom_url_enabled()) {
return $url;
}
$custom_slug = $this->get_custom_slug();
return str_replace('wp-login.php', $custom_slug, $url);
}
/**
* Filter register URL
*/
public function filter_register_url($url) {
if (!$this->is_custom_url_enabled()) {
return $url;
}
$custom_slug = $this->get_custom_slug();
return str_replace('wp-login.php', $custom_slug, $url);
}
}
// Initialize plugin
add_action('plugins_loaded', array('Plugin_Name_Login_URL_Changer', 'get_instance'));
// Activation hook - must be outside class
register_activation_hook(__FILE__, 'plugin_name_activate');
function plugin_name_activate() {
// Make sure rewrite rules are regenerated
global $wp_rewrite;
if ($wp_rewrite) {
$wp_rewrite->flush_rules(true);
} else {
flush_rewrite_rules(true);
}
}
// Deactivation hook - must be outside class
register_deactivation_hook(__FILE__, 'plugin_name_deactivate');
function plugin_name_deactivate() {
// Flush rewrite rules to remove custom rules
flush_rewrite_rules();
}
// Flush rewrite rules after option is updated
add_action('update_option_plugin_name_custom_login_url', 'plugin_name_flush_after_update', 10, 2);
function plugin_name_flush_after_update($old_value, $new_value) {
// Only flush if value actually changed
if ($old_value !== $new_value) {
// Use a transient to delay the flush until after the page loads
set_transient('plugin_name_needs_flush', true, 60);
}
}
// Perform the actual flush on the next admin load
add_action('admin_init', 'plugin_name_perform_flush');
function plugin_name_perform_flush() {
if (get_transient('plugin_name_needs_flush')) {
delete_transient('plugin_name_needs_flush');
flush_rewrite_rules(true);
}
}