wp-domain-mapping/admin/pages.php
2025-05-26 22:47:52 +08:00

1435 lines
69 KiB
PHP
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

<?php
/**
* Admin page templates for WP Domain Mapping plugin
*
* @package WP Domain Mapping
*/
// Prevent direct access
if ( ! defined( 'ABSPATH' ) ) {
exit;
}
/**
* Render main admin page with tabs
*/
function dm_render_admin_page() {
?>
<div class="wrap">
<h1><?php echo esc_html( get_admin_page_title() ); ?>
<span style="font-size: 13px; padding-left: 10px;">
<?php printf( esc_html__( 'Version: %s', 'wp-domain-mapping' ), esc_html( WP_DOMAIN_MAPPING_VERSION ) ); ?>
</span>
<a href="https://wpmultisite.com/document/wp-domain-mapping" target="_blank" class="button button-secondary" style="margin-left: 10px;">
<?php esc_html_e( 'Document', 'wp-domain-mapping' ); ?>
</a>
<a href="https://wpmultisite.com/forums/" target="_blank" class="button button-secondary">
<?php esc_html_e( 'Support', 'wp-domain-mapping' ); ?>
</a>
</h1>
<?php
// Display settings errors
settings_errors( 'dm_settings' );
// Get current tab
$current_tab = isset( $_GET['tab'] ) ? sanitize_text_field( $_GET['tab'] ) : 'settings';
$tabs = array(
'settings' => __( 'Settings', 'wp-domain-mapping' ),
'dns-setup' => __( 'DNS Setup', 'wp-domain-mapping' ),
'health' => __( 'Domain Health', 'wp-domain-mapping' ),
'import-export' => __( 'Import/Export', 'wp-domain-mapping' )
);
// Display success messages for tabs
if ( isset( $_GET['checked'] ) && $_GET['checked'] && $current_tab === 'health' ) {
echo '<div class="notice notice-success is-dismissible"><p>' .
__( 'Domain health check completed.', 'wp-domain-mapping' ) .
'</p></div>';
}
if ( isset( $_GET['checking'] ) && $_GET['checking'] && $current_tab === 'health' ) {
echo '<div class="notice notice-info"><p>' .
__( 'Domain health check started. The check is running in the background.', 'wp-domain-mapping' ) .
'</p></div>';
}
if ( isset( $_GET['settings-updated'] ) && $_GET['settings-updated'] && $current_tab === 'health' ) {
echo '<div class="notice notice-success is-dismissible"><p>' .
__( 'Settings saved.', 'wp-domain-mapping' ) .
'</p></div>';
}
if ( isset( $_GET['imported'] ) && $_GET['imported'] && $current_tab === 'import-export' ) {
$count = intval( $_GET['imported'] );
echo '<div class="notice notice-success is-dismissible"><p>' .
sprintf(
_n(
'%d domain mapping imported successfully.',
'%d domain mappings imported successfully.',
$count,
'wp-domain-mapping'
),
$count
) .
'</p></div>';
}
if ( isset( $_GET['export'] ) && $_GET['export'] == 'success' && $current_tab === 'import-export' ) {
echo '<div class="notice notice-success is-dismissible"><p>' .
__( 'Domain mappings exported successfully.', 'wp-domain-mapping' ) .
'</p></div>';
}
?>
<!-- Main Configuration Card -->
<div class="card domain-mapping-card">
<!-- Tab Navigation inside card -->
<div class="domain-mapping-tabs">
<?php foreach ( $tabs as $tab_key => $tab_label ) : ?>
<button type="button" class="domain-mapping-tab <?php echo $current_tab === $tab_key ? 'active' : ''; ?>"
data-tab="<?php echo esc_attr( $tab_key ); ?>"
onclick="switchTab('<?php echo esc_js( $tab_key ); ?>')">
<?php echo esc_html( $tab_label ); ?>
</button>
<?php endforeach; ?>
</div>
<!-- Tab Content -->
<div class="domain-mapping-content">
<!-- Settings Tab -->
<div class="domain-mapping-section" data-section="settings" <?php echo $current_tab !== 'settings' ? 'style="display:none;"' : ''; ?>>
<?php dm_render_settings_content(); ?>
</div>
<!-- DNS Setup Tab -->
<div class="domain-mapping-section" data-section="dns-setup" <?php echo $current_tab !== 'dns-setup' ? 'style="display:none;"' : ''; ?>>
<?php
$dm_ipaddress = get_site_option( 'dm_ipaddress', '' );
$dm_cname = get_site_option( 'dm_cname', '' );
dm_render_dns_content( $dm_ipaddress, $dm_cname );
?>
</div>
<!-- Domain Health Tab -->
<div class="domain-mapping-section" data-section="health" <?php echo $current_tab !== 'health' ? 'style="display:none;"' : ''; ?>>
<?php dm_render_health_content(); ?>
</div>
<!-- Import/Export Tab -->
<div class="domain-mapping-section" data-section="import-export" <?php echo $current_tab !== 'import-export' ? 'style="display:none;"' : ''; ?>>
<?php dm_render_import_export_content(); ?>
</div>
</div>
</div>
<!-- Installation Check Card (independent) -->
<?php dm_render_installation_check(); ?>
</div>
<script>
function switchTab(tab) {
// Update URL without reloading
const url = new URL(window.location);
url.searchParams.set('tab', tab);
window.history.pushState({}, '', url);
// Update active tab
document.querySelectorAll('.domain-mapping-tab').forEach(t => t.classList.remove('active'));
document.querySelector(`[data-tab="${tab}"]`).classList.add('active');
// Update visible section
document.querySelectorAll('.domain-mapping-section').forEach(s => s.style.display = 'none');
document.querySelector(`[data-section="${tab}"]`).style.display = 'block';
}
</script>
<?php
}
/**
* Render settings tab content (without card wrapper)
*/
function dm_render_settings_content() {
// Get current options
$dm_ipaddress = get_site_option( 'dm_ipaddress', '' );
$dm_cname = get_site_option( 'dm_cname', '' );
$dm_remote_login = get_site_option( 'dm_remote_login', 1 );
$dm_301_redirect = get_site_option( 'dm_301_redirect', 0 );
$dm_redirect_admin = get_site_option( 'dm_redirect_admin', 1 );
$dm_user_settings = get_site_option( 'dm_user_settings', 1 );
$dm_no_primary_domain = get_site_option( 'dm_no_primary_domain', 0 );
// Get server IP address if not set
if ( empty( $dm_ipaddress ) ) {
$server_ip = isset( $_SERVER['SERVER_ADDR'] ) ? $_SERVER['SERVER_ADDR'] : '';
if ( empty( $server_ip ) && function_exists( 'gethostbyname' ) ) {
$server_ip = gethostbyname( $_SERVER['SERVER_NAME'] );
}
if ( $server_ip && filter_var( $server_ip, FILTER_VALIDATE_IP ) ) {
$dm_ipaddress = $server_ip;
}
}
?>
<form method="POST">
<input type="hidden" name="action" value="update" />
<?php wp_nonce_field( 'domain_mapping' ); ?>
<h2><?php esc_html_e( 'Server Configuration', 'wp-domain-mapping' ); ?></h2>
<p><?php esc_html_e( 'Configure the IP address or CNAME for domain mapping.', 'wp-domain-mapping' ); ?></p>
<table class="form-table" role="presentation">
<tr>
<th scope="row"><label for="ipaddress"><?php esc_html_e( 'Server IP Address:', 'wp-domain-mapping' ); ?></label></th>
<td>
<input type="text" id="ipaddress" name="ipaddress" value="<?php echo esc_attr( $dm_ipaddress ); ?>" class="regular-text" />
<p class="description">
<?php esc_html_e( 'Enter the IP address(es) users should point their DNS A records to. Use commas to separate multiple IPs.', 'wp-domain-mapping' ); ?>
</p>
</td>
</tr>
<tr>
<th scope="row"><label for="cname"><?php esc_html_e( 'Server CNAME Domain:', 'wp-domain-mapping' ); ?></label></th>
<td>
<input type="text" id="cname" name="cname" value="<?php echo esc_attr( $dm_cname ); ?>" class="regular-text" placeholder="server.example.com" />
<p class="description">
<?php
printf(
/* translators: %s: IDN warning message */
esc_html__( 'Use a CNAME instead of an IP (overrides IP settings). %s', 'wp-domain-mapping' ),
dm_idn_warning()
);
?>
</p>
</td>
</tr>
</table>
<h3><?php esc_html_e( 'Domain Options', 'wp-domain-mapping' ); ?></h3>
<table class="form-table" role="presentation">
<tr>
<th scope="row"></th>
<td>
<fieldset>
<legend class="screen-reader-text"><?php esc_html_e( 'Domain Options', 'wp-domain-mapping' ); ?></legend>
<label for="dm_remote_login">
<input type="checkbox" name="dm_remote_login" id="dm_remote_login" value="1" <?php checked( $dm_remote_login, 1 ); ?> />
<?php esc_html_e( 'Enable Remote Login', 'wp-domain-mapping' ); ?>
</label>
<p class="description">
<?php esc_html_e( 'Allows users to log in from mapped domains and be redirected to the original domain for authentication.', 'wp-domain-mapping' ); ?>
</p>
</fieldset>
</td>
</tr>
<tr>
<th scope="row"></th>
<td>
<fieldset>
<legend class="screen-reader-text"><?php esc_html_e( 'Permanent Redirect', 'wp-domain-mapping' ); ?></legend>
<label for="permanent_redirect">
<input type="checkbox" name="permanent_redirect" id="permanent_redirect" value="1" <?php checked( $dm_301_redirect, 1 ); ?> />
<?php esc_html_e( 'Use Permanent Redirect (301)', 'wp-domain-mapping' ); ?>
</label>
<p class="description">
<?php esc_html_e( 'Use 301 redirects instead of 302 redirects. This is better for SEO but may cause caching issues.', 'wp-domain-mapping' ); ?>
</p>
</fieldset>
</td>
</tr>
<tr>
<th scope="row"></th>
<td>
<fieldset>
<legend class="screen-reader-text"><?php esc_html_e( 'User Settings', 'wp-domain-mapping' ); ?></legend>
<label for="dm_user_settings">
<input type="checkbox" name="dm_user_settings" id="dm_user_settings" value="1" <?php checked( $dm_user_settings, 1 ); ?> />
<?php esc_html_e( 'Enable User Domain Mapping Page', 'wp-domain-mapping' ); ?>
</label>
<p class="description">
<?php esc_html_e( 'Allow site administrators to manage their domain mappings from the Tools menu.', 'wp-domain-mapping' ); ?>
</p>
</fieldset>
</td>
</tr>
<tr>
<th scope="row"></th>
<td>
<fieldset>
<legend class="screen-reader-text"><?php esc_html_e( 'Redirect Admin', 'wp-domain-mapping' ); ?></legend>
<label for="always_redirect_admin">
<input type="checkbox" name="always_redirect_admin" id="always_redirect_admin" value="1" <?php checked( $dm_redirect_admin, 1 ); ?> />
<?php esc_html_e( 'Redirect Admin Pages to Original Domain', 'wp-domain-mapping' ); ?>
</label>
<p class="description">
<?php esc_html_e( 'Force admin pages to use the original WordPress domain instead of the mapped domain.', 'wp-domain-mapping' ); ?>
</p>
</fieldset>
</td>
</tr>
<tr>
<th scope="row"></th>
<td>
<fieldset>
<legend class="screen-reader-text"><?php esc_html_e( 'Disable Primary Domain', 'wp-domain-mapping' ); ?></legend>
<label for="dm_no_primary_domain">
<input type="checkbox" name="dm_no_primary_domain" id="dm_no_primary_domain" value="1" <?php checked( $dm_no_primary_domain, 1 ); ?> />
<?php esc_html_e( 'Disable Primary Domain Check', 'wp-domain-mapping' ); ?>
</label>
<p class="description">
<?php esc_html_e( 'Do not redirect to the primary domain, but allow access through any mapped domain.', 'wp-domain-mapping' ); ?>
</p>
</fieldset>
</td>
</tr>
</table>
<p class="submit">
<input type="submit" class="button button-primary" value="<?php esc_attr_e( 'Save Configuration', 'wp-domain-mapping' ); ?>" />
<a href="<?php echo esc_url( admin_url( 'network/sites.php?page=domains' ) ); ?>" class="button button-secondary">
<?php esc_html_e( 'Manage Domains', 'wp-domain-mapping' ); ?>
</a>
</p>
</form>
<?php
}
/**
* Render DNS setup tab content (without card wrapper)
*/
function dm_render_dns_content( $dm_ipaddress, $dm_cname ) {
?>
<h2><?php esc_html_e( 'DNS Setup Instructions', 'wp-domain-mapping' ); ?></h2>
<div class="dns-instructions">
<?php if ( ! empty( $dm_cname ) ) : ?>
<h3><?php esc_html_e( 'CNAME Method (Recommended)', 'wp-domain-mapping' ); ?></h3>
<p>
<?php
printf(
/* translators: %s: CNAME value */
esc_html__( 'Tell your users to add a DNS "CNAME" record for their domain pointing to: %s', 'wp-domain-mapping' ),
'<code>' . esc_html( $dm_cname ) . '</code>'
);
?>
</p>
<div class="dns-example">
<h4><?php esc_html_e( 'Example DNS Record', 'wp-domain-mapping' ); ?></h4>
<table class="widefat striped">
<thead>
<tr>
<th><?php esc_html_e( 'Type', 'wp-domain-mapping' ); ?></th>
<th><?php esc_html_e( 'Name', 'wp-domain-mapping' ); ?></th>
<th><?php esc_html_e( 'Value', 'wp-domain-mapping' ); ?></th>
<th><?php esc_html_e( 'TTL', 'wp-domain-mapping' ); ?></th>
</tr>
</thead>
<tbody>
<tr>
<td><code>CNAME</code></td>
<td><code>@</code> <?php esc_html_e( '(or empty)', 'wp-domain-mapping' ); ?></td>
<td><code><?php echo esc_html( $dm_cname ); ?></code></td>
<td><code>3600</code></td>
</tr>
<tr>
<td><code>CNAME</code></td>
<td><code>www</code></td>
<td><code><?php echo esc_html( $dm_cname ); ?></code></td>
<td><code>3600</code></td>
</tr>
</tbody>
</table>
</div>
<?php endif; ?>
<?php if ( ! empty( $dm_ipaddress ) ) : ?>
<h3><?php esc_html_e( 'A Record Method', 'wp-domain-mapping' ); ?></h3>
<p>
<?php
printf(
/* translators: %s: IP address(es) */
esc_html__( 'Tell your users to add a DNS "A" record for their domain pointing to: %s', 'wp-domain-mapping' ),
'<code>' . esc_html( $dm_ipaddress ) . '</code>'
);
?>
</p>
<div class="dns-example">
<h4><?php esc_html_e( 'Example DNS Record', 'wp-domain-mapping' ); ?></h4>
<table class="widefat striped">
<thead>
<tr>
<th><?php esc_html_e( 'Type', 'wp-domain-mapping' ); ?></th>
<th><?php esc_html_e( 'Name', 'wp-domain-mapping' ); ?></th>
<th><?php esc_html_e( 'Value', 'wp-domain-mapping' ); ?></th>
<th><?php esc_html_e( 'TTL', 'wp-domain-mapping' ); ?></th>
</tr>
</thead>
<tbody>
<?php
$ips = array_map( 'trim', explode( ',', $dm_ipaddress ) );
foreach ( $ips as $index => $ip ) :
?>
<tr>
<td><code>A</code></td>
<td><code>@</code> <?php esc_html_e( '(or empty)', 'wp-domain-mapping' ); ?></td>
<td><code><?php echo esc_html( $ip ); ?></code></td>
<td><code>3600</code></td>
</tr>
<?php endforeach; ?>
<tr>
<td><code>A</code></td>
<td><code>www</code></td>
<td><code><?php echo esc_html( $ips[0] ); ?></code></td>
<td><code>3600</code></td>
</tr>
</tbody>
</table>
</div>
<?php endif; ?>
<?php if ( empty( $dm_ipaddress ) && empty( $dm_cname ) ) : ?>
<div class="notice notice-warning">
<p>
<?php esc_html_e( 'Please configure either a Server IP Address or CNAME in the Settings tab to provide DNS setup instructions.', 'wp-domain-mapping' ); ?>
</p>
</div>
<?php endif; ?>
<h3><?php esc_html_e( 'Additional DNS Tips', 'wp-domain-mapping' ); ?></h3>
<ul class="dns-tips">
<li><?php esc_html_e( 'Most DNS changes take 24-48 hours to fully propagate worldwide.', 'wp-domain-mapping' ); ?></li>
<li><?php esc_html_e( 'For "www" subdomain, create a separate CNAME record with "www" as the name pointing to the same value.', 'wp-domain-mapping' ); ?></li>
<li><?php esc_html_e( 'If you\'re using Cloudflare or similar services, you may need to adjust proxy settings.', 'wp-domain-mapping' ); ?></li>
<li><?php esc_html_e( 'For SSL to work properly, make sure your web server is configured with the appropriate SSL certificates for mapped domains.', 'wp-domain-mapping' ); ?></li>
</ul>
</div>
<?php
}
/**
* Render DNS instructions (independent card) - kept for backward compatibility
*/
function dm_render_dns_instructions( $dm_ipaddress, $dm_cname ) {
?>
<div class="card domain-mapping-card">
<h2><?php esc_html_e( 'DNS Setup Instructions', 'wp-domain-mapping' ); ?></h2>
<div class="dns-instructions">
<?php if ( ! empty( $dm_cname ) ) : ?>
<h3><?php esc_html_e( 'CNAME Method (Recommended)', 'wp-domain-mapping' ); ?></h3>
<p>
<?php
printf(
/* translators: %s: CNAME value */
esc_html__( 'Tell your users to add a DNS "CNAME" record for their domain pointing to: %s', 'wp-domain-mapping' ),
'<code>' . esc_html( $dm_cname ) . '</code>'
);
?>
</p>
<div class="dns-example">
<h4><?php esc_html_e( 'Example DNS Record', 'wp-domain-mapping' ); ?></h4>
<table class="widefat striped">
<thead>
<tr>
<th><?php esc_html_e( 'Type', 'wp-domain-mapping' ); ?></th>
<th><?php esc_html_e( 'Name', 'wp-domain-mapping' ); ?></th>
<th><?php esc_html_e( 'Value', 'wp-domain-mapping' ); ?></th>
<th><?php esc_html_e( 'TTL', 'wp-domain-mapping' ); ?></th>
</tr>
</thead>
<tbody>
<tr>
<td><code>CNAME</code></td>
<td><code>@</code> <?php esc_html_e( '(or empty)', 'wp-domain-mapping' ); ?></td>
<td><code><?php echo esc_html( $dm_cname ); ?></code></td>
<td><code>3600</code></td>
</tr>
<tr>
<td><code>CNAME</code></td>
<td><code>www</code></td>
<td><code><?php echo esc_html( $dm_cname ); ?></code></td>
<td><code>3600</code></td>
</tr>
</tbody>
</table>
</div>
<?php endif; ?>
<?php if ( ! empty( $dm_ipaddress ) ) : ?>
<h3><?php esc_html_e( 'A Record Method', 'wp-domain-mapping' ); ?></h3>
<p>
<?php
printf(
/* translators: %s: IP address(es) */
esc_html__( 'Tell your users to add a DNS "A" record for their domain pointing to: %s', 'wp-domain-mapping' ),
'<code>' . esc_html( $dm_ipaddress ) . '</code>'
);
?>
</p>
<div class="dns-example">
<h4><?php esc_html_e( 'Example DNS Record', 'wp-domain-mapping' ); ?></h4>
<table class="widefat striped">
<thead>
<tr>
<th><?php esc_html_e( 'Type', 'wp-domain-mapping' ); ?></th>
<th><?php esc_html_e( 'Name', 'wp-domain-mapping' ); ?></th>
<th><?php esc_html_e( 'Value', 'wp-domain-mapping' ); ?></th>
<th><?php esc_html_e( 'TTL', 'wp-domain-mapping' ); ?></th>
</tr>
</thead>
<tbody>
<?php
$ips = array_map( 'trim', explode( ',', $dm_ipaddress ) );
foreach ( $ips as $index => $ip ) :
?>
<tr>
<td><code>A</code></td>
<td><code>@</code> <?php esc_html_e( '(or empty)', 'wp-domain-mapping' ); ?></td>
<td><code><?php echo esc_html( $ip ); ?></code></td>
<td><code>3600</code></td>
</tr>
<?php endforeach; ?>
<tr>
<td><code>A</code></td>
<td><code>www</code></td>
<td><code><?php echo esc_html( $ips[0] ); ?></code></td>
<td><code>3600</code></td>
</tr>
</tbody>
</table>
</div>
<?php endif; ?>
<?php if ( empty( $dm_ipaddress ) && empty( $dm_cname ) ) : ?>
<div class="notice notice-warning">
<p>
<?php esc_html_e( 'Please configure either a Server IP Address or CNAME to provide DNS setup instructions.', 'wp-domain-mapping' ); ?>
</p>
</div>
<?php endif; ?>
<h3><?php esc_html_e( 'Additional DNS Tips', 'wp-domain-mapping' ); ?></h3>
<ul class="dns-tips">
<li><?php esc_html_e( 'Most DNS changes take 24-48 hours to fully propagate worldwide.', 'wp-domain-mapping' ); ?></li>
<li><?php esc_html_e( 'For "www" subdomain, create a separate CNAME record with "www" as the name pointing to the same value.', 'wp-domain-mapping' ); ?></li>
<li><?php esc_html_e( 'If you\'re using Cloudflare or similar services, you may need to adjust proxy settings.', 'wp-domain-mapping' ); ?></li>
<li><?php esc_html_e( 'For SSL to work properly, make sure your web server is configured with the appropriate SSL certificates for mapped domains.', 'wp-domain-mapping' ); ?></li>
</ul>
</div>
</div>
<?php
}
/**
* Render installation check (independent card)
*/
function dm_render_installation_check() {
?>
<div class="card domain-mapping-card">
<h2><?php esc_html_e( 'Installation Check', 'wp-domain-mapping' ); ?></h2>
<table class="widefat striped">
<tbody>
<tr>
<th><?php esc_html_e( 'Status', 'wp-domain-mapping' ); ?></th>
<th><?php esc_html_e( 'Check', 'wp-domain-mapping' ); ?></th>
<th><?php esc_html_e( 'Value', 'wp-domain-mapping' ); ?></th>
</tr>
<tr>
<td>
<?php if ( file_exists( WP_CONTENT_DIR . '/sunrise.php' ) ) : ?>
<span class="dashicons dashicons-yes-alt" style="color: #46b450;"></span>
<?php else : ?>
<span class="dashicons dashicons-no-alt" style="color: #dc3232;"></span>
<?php endif; ?>
</td>
<td><?php esc_html_e( 'sunrise.php file', 'wp-domain-mapping' ); ?></td>
<td>
<?php if ( file_exists( WP_CONTENT_DIR . '/sunrise.php' ) ) : ?>
<?php esc_html_e( 'Found', 'wp-domain-mapping' ); ?>
<?php else : ?>
<?php
printf(
/* translators: %s: WordPress content directory */
esc_html__( 'Not found - copy sunrise.php to %s', 'wp-domain-mapping' ),
'<code>' . esc_html( WP_CONTENT_DIR ) . '</code>'
);
?>
<?php endif; ?>
</td>
</tr>
<tr>
<td>
<?php if ( defined( 'SUNRISE' ) ) : ?>
<span class="dashicons dashicons-yes-alt" style="color: #46b450;"></span>
<?php else : ?>
<span class="dashicons dashicons-no-alt" style="color: #dc3232;"></span>
<?php endif; ?>
</td>
<td><?php esc_html_e( 'SUNRISE constant', 'wp-domain-mapping' ); ?></td>
<td>
<?php if ( defined( 'SUNRISE' ) ) : ?>
<?php
printf(
/* translators: %s: SUNRISE constant value */
esc_html__( 'Defined as: %s', 'wp-domain-mapping' ),
'<code>' . esc_html( SUNRISE ) . '</code>'
);
?>
<?php else : ?>
<?php esc_html_e( 'Not defined - add to wp-config.php: ', 'wp-domain-mapping' ); ?>
<code>define( 'SUNRISE', 'on' );</code>
<?php endif; ?>
</td>
</tr>
<tr>
<td>
<?php if ( defined( 'SUNRISE_LOADED' ) ) : ?>
<span class="dashicons dashicons-yes-alt" style="color: #46b450;"></span>
<?php else : ?>
<span class="dashicons dashicons-no-alt" style="color: #dc3232;"></span>
<?php endif; ?>
</td>
<td><?php esc_html_e( 'SUNRISE_LOADED', 'wp-domain-mapping' ); ?></td>
<td>
<?php if ( defined( 'SUNRISE_LOADED' ) ) : ?>
<?php esc_html_e( 'Loaded successfully', 'wp-domain-mapping' ); ?>
<?php else : ?>
<?php
if ( defined( 'SUNRISE' ) ) {
esc_html_e( 'Not loaded - make sure SUNRISE is defined before the require_once() in wp-config.php', 'wp-domain-mapping' );
} else {
esc_html_e( 'Not loaded - SUNRISE constant not defined', 'wp-domain-mapping' );
}
?>
<?php endif; ?>
</td>
</tr>
<tr>
<td>
<?php
// Check COOKIE_DOMAIN configuration in a performance-friendly way
$cookie_domain_status = dm_check_cookie_domain_status();
if ($cookie_domain_status['is_optimal']): ?>
<span class="dashicons dashicons-yes-alt" style="color: #46b450;"></span>
<?php elseif ($cookie_domain_status['has_warning']): ?>
<span class="dashicons dashicons-warning" style="color: #f56e28;"></span>
<?php else: ?>
<span class="dashicons dashicons-no-alt" style="color: #dc3232;"></span>
<?php endif; ?>
</td>
<td><?php esc_html_e('COOKIE_DOMAIN', 'wp-domain-mapping'); ?></td>
<td>
<?php if ($cookie_domain_status['is_optimal']): ?>
<span style="color: #46b450;">
<?php echo esc_html($cookie_domain_status['message']); ?>
</span>
<?php elseif ($cookie_domain_status['has_warning']): ?>
<span style="color: #f56e28;">
<?php echo esc_html($cookie_domain_status['message']); ?>
</span>
<br><small style="color: #666;">
<?php esc_html_e('This may cause login issues on mapped domains. Consider removing the COOKIE_DOMAIN definition from wp-config.php.', 'wp-domain-mapping'); ?>
</small>
<?php else: ?>
<span style="color: #dc3232;">
<?php echo esc_html($cookie_domain_status['message']); ?>
</span>
<br><small style="color: #666;">
<?php esc_html_e('Remove the define(\'COOKIE_DOMAIN\', ...) line from wp-config.php to enable dynamic cookie domain handling.', 'wp-domain-mapping'); ?>
</small>
<?php endif; ?>
<?php if (defined('WP_DEBUG') && WP_DEBUG && !empty($cookie_domain_status['debug_info'])): ?>
<br><small style="color: #999; font-style: italic;">
<?php echo esc_html($cookie_domain_status['debug_info']); ?>
</small>
<?php endif; ?>
</td>
</tr>
<tr>
<td>
<?php
global $wpdb;
$tables = dm_get_table_names();
$tables_exist = true;
foreach ( $tables as $table ) {
if ( $wpdb->get_var( "SHOW TABLES LIKE '$table'" ) != $table ) {
$tables_exist = false;
break;
}
}
?>
<?php if ( $tables_exist ) : ?>
<span class="dashicons dashicons-yes-alt" style="color: #46b450;"></span>
<?php else : ?>
<span class="dashicons dashicons-no-alt" style="color: #dc3232;"></span>
<?php endif; ?>
</td>
<td><?php esc_html_e( 'Database tables', 'wp-domain-mapping' ); ?></td>
<td>
<?php if ( $tables_exist ) : ?>
<?php esc_html_e( 'All tables exist', 'wp-domain-mapping' ); ?>
<?php else : ?>
<?php esc_html_e( 'Some tables are missing - deactivate and reactivate the plugin', 'wp-domain-mapping' ); ?>
<?php endif; ?>
</td>
</tr>
<tr>
<td>
<?php if ( is_multisite() ) : ?>
<span class="dashicons dashicons-yes-alt" style="color: #46b450;"></span>
<?php else : ?>
<span class="dashicons dashicons-no-alt" style="color: #dc3232;"></span>
<?php endif; ?>
</td>
<td><?php esc_html_e( 'Multisite', 'wp-domain-mapping' ); ?></td>
<td>
<?php if ( is_multisite() ) : ?>
<?php esc_html_e( 'Enabled', 'wp-domain-mapping' ); ?>
<?php else : ?>
<?php esc_html_e( 'Not enabled - this plugin requires WordPress Multisite', 'wp-domain-mapping' ); ?>
<?php endif; ?>
</td>
</tr>
</tbody>
</table>
</div>
<?php
}
/**
* Render health tab content
*/
function dm_render_health_content() {
// Get all domains
global $wpdb;
$tables = dm_get_table_names();
$domains = $wpdb->get_results("
SELECT d.*, b.domain as original_domain, b.path
FROM {$tables['domains']} d
JOIN {$wpdb->blogs} b ON d.blog_id = b.blog_id
ORDER BY d.blog_id ASC, d.active DESC
");
// Get health check results
$health_results = get_site_option( 'dm_domain_health_results', array() );
// Check if batch processing is in progress
$health_check_progress = get_site_option( 'dm_health_check_progress', false );
?>
<h2><?php _e( 'Domain Health Status', 'wp-domain-mapping' ); ?></h2>
<?php if ( $health_check_progress !== false ) : ?>
<div class="notice notice-info">
<p>
<?php _e( 'Health check in progress...', 'wp-domain-mapping' ); ?>
<span id="health-check-progress-text">
<?php
printf(
__( 'Processed %d of %d domains (%d%%)', 'wp-domain-mapping' ),
$health_check_progress['processed'],
$health_check_progress['total'],
round( ( $health_check_progress['processed'] / $health_check_progress['total'] ) * 100 )
);
?>
</span>
</p>
<div class="progress-bar-outer" style="background-color: #f0f0f1; border-radius: 4px; height: 20px; width: 100%; overflow: hidden; margin-top: 10px;">
<div id="health-check-progress-bar" class="progress-bar-inner" style="background-color: #2271b1; height: 100%; width: <?php echo round( ( $health_check_progress['processed'] / $health_check_progress['total'] ) * 100 ); ?>%; transition: width 0.5s;"></div>
</div>
</div>
<script>
jQuery(document).ready(function($) {
var healthCheckInterval = setInterval(function() {
$.ajax({
url: ajaxurl,
type: 'POST',
data: {
action: 'dm_check_domain_health_batch',
nonce: '<?php echo wp_create_nonce( 'dm_check_domain_health_batch' ); ?>'
},
success: function(response) {
if (response.success) {
if (response.data.complete) {
clearInterval(healthCheckInterval);
location.reload();
} else {
$('#health-check-progress-text').text(
'<?php _e( 'Processed ', 'wp-domain-mapping' ); ?>' +
response.data.processed + ' <?php _e( 'of', 'wp-domain-mapping' ); ?> ' +
response.data.total + ' <?php _e( 'domains', 'wp-domain-mapping' ); ?> (' +
response.data.percentage + '%)'
);
$('#health-check-progress-bar').css('width', response.data.percentage + '%');
}
}
}
});
}, 2000);
});
</script>
<?php else : ?>
<p>
<form method="post" action="">
<?php wp_nonce_field( 'dm_manual_health_check', 'dm_manual_health_check_nonce' ); ?>
<input type="hidden" name="dm_manual_health_check" value="1">
<input type="submit" class="button button-primary" value="<?php esc_attr_e( 'Check All Domains Now', 'wp-domain-mapping' ); ?>">
</form>
</p>
<?php endif; ?>
<div class="tablenav top">
<div class="tablenav-pages">
<span class="displaying-num">
<?php
if ( ! empty( $domains ) ) {
printf(
_n( '%s domain', '%s domains', count( $domains ), 'wp-domain-mapping' ),
number_format_i18n( count( $domains ) )
);
} else {
_e( 'No domains found', 'wp-domain-mapping' );
}
?>
</span>
</div>
<br class="clear">
</div>
<table class="wp-list-table widefat fixed striped domains-health-table">
<thead>
<tr>
<th class="column-domain"><?php _e( 'Domain', 'wp-domain-mapping' ); ?></th>
<th class="column-site"><?php _e( 'Site', 'wp-domain-mapping' ); ?></th>
<th class="column-dns"><?php _e( 'DNS Status', 'wp-domain-mapping' ); ?></th>
<th class="column-ssl"><?php _e( 'SSL Status', 'wp-domain-mapping' ); ?></th>
<th class="column-status"><?php _e( 'Reachable', 'wp-domain-mapping' ); ?></th>
<th class="column-last-check"><?php _e( 'Last Check', 'wp-domain-mapping' ); ?></th>
<th class="column-actions"><?php _e( 'Actions', 'wp-domain-mapping' ); ?></th>
</tr>
</thead>
<tbody>
<?php if ( ! empty( $domains ) ) : ?>
<?php foreach ( $domains as $domain ) :
$domain_key = md5( $domain->domain );
$health_data = isset( $health_results[$domain_key] ) ? $health_results[$domain_key] : null;
$site_name = get_blog_option( $domain->blog_id, 'blogname', __( 'Unknown', 'wp-domain-mapping' ) );
?>
<tr data-domain="<?php echo esc_attr( $domain->domain ); ?>" data-blog-id="<?php echo esc_attr( $domain->blog_id ); ?>">
<td class="column-domain">
<?php echo esc_html( $domain->domain ); ?>
<?php if ( $domain->active ) : ?>
<span class="dashicons dashicons-star-filled" style="color: #f0b849;" title="<?php esc_attr_e( 'Primary Domain', 'wp-domain-mapping' ); ?>"></span>
<?php endif; ?>
</td>
<td class="column-site">
<a href="<?php echo esc_url( network_admin_url( 'site-info.php?id=' . $domain->blog_id ) ); ?>">
<?php echo esc_html( $site_name ); ?>
<div class="row-actions">
<span class="original-domain"><?php echo esc_html( $domain->original_domain . $domain->path ); ?></span>
</div>
</a>
</td>
<td class="column-dns">
<?php if ( $health_data && isset( $health_data['dns_status'] ) ) : ?>
<?php if ( $health_data['dns_status'] === 'success' ) : ?>
<span class="dashicons dashicons-yes-alt" style="color: #46b450;" title="<?php esc_attr_e( 'DNS correctly configured', 'wp-domain-mapping' ); ?>"></span>
<?php else : ?>
<span class="dashicons dashicons-warning" style="color: #dc3232;" title="<?php echo esc_attr( $health_data['dns_message'] ); ?>"></span>
<?php endif; ?>
<?php else : ?>
<span class="dashicons dashicons-minus" style="color: #999;" title="<?php esc_attr_e( 'Not checked yet', 'wp-domain-mapping' ); ?>"></span>
<?php endif; ?>
</td>
<td class="column-ssl">
<?php if ( $health_data && isset( $health_data['ssl_valid'] ) ) : ?>
<?php if ( $health_data['ssl_valid'] ) : ?>
<span class="dashicons dashicons-yes-alt" style="color: #46b450;" title="<?php esc_attr_e( 'SSL certificate valid', 'wp-domain-mapping' ); ?>"></span>
<div class="row-actions">
<span><?php echo esc_html( sprintf( __( 'Expires: %s', 'wp-domain-mapping' ), isset( $health_data['ssl_expiry'] ) ? date( 'Y-m-d', strtotime( $health_data['ssl_expiry'] ) ) : '-' ) ); ?></span>
</div>
<?php else : ?>
<span class="dashicons dashicons-warning" style="color: #dc3232;" title="<?php esc_attr_e( 'SSL certificate issue', 'wp-domain-mapping' ); ?>"></span>
<?php endif; ?>
<?php else : ?>
<span class="dashicons dashicons-minus" style="color: #999;" title="<?php esc_attr_e( 'Not checked yet', 'wp-domain-mapping' ); ?>"></span>
<?php endif; ?>
</td>
<td class="column-status">
<?php if ( $health_data && isset( $health_data['accessible'] ) ) : ?>
<?php if ( $health_data['accessible'] ) : ?>
<span class="dashicons dashicons-yes-alt" style="color: #46b450;" title="<?php esc_attr_e( 'Site is accessible', 'wp-domain-mapping' ); ?>"></span>
<?php else : ?>
<span class="dashicons dashicons-warning" style="color: #dc3232;" title="<?php esc_attr_e( 'Site is not accessible', 'wp-domain-mapping' ); ?>"></span>
<?php endif; ?>
<?php else : ?>
<span class="dashicons dashicons-minus" style="color: #999;" title="<?php esc_attr_e( 'Not checked yet', 'wp-domain-mapping' ); ?>"></span>
<?php endif; ?>
</td>
<td class="column-last-check">
<?php
if ( $health_data && isset( $health_data['last_check'] ) ) {
echo esc_html( human_time_diff( strtotime( $health_data['last_check'] ), current_time( 'timestamp' ) ) ) . ' ' . __( 'ago', 'wp-domain-mapping' );
} else {
_e( 'Never', 'wp-domain-mapping' );
}
?>
</td>
<td class="column-actions">
<button type="button" class="button button-small check-domain-health" data-domain="<?php echo esc_attr( $domain->domain ); ?>">
<?php _e( 'Check Now', 'wp-domain-mapping' ); ?>
</button>
</td>
</tr>
<?php endforeach; ?>
<?php else : ?>
<tr>
<td colspan="7"><?php _e( 'No domains found.', 'wp-domain-mapping' ); ?></td>
</tr>
<?php endif; ?>
</tbody>
</table>
<h3><?php _e( 'Health Check Settings', 'wp-domain-mapping' ); ?></h3>
<form method="post" action="">
<?php wp_nonce_field( 'dm_health_settings', 'dm_health_settings_nonce' ); ?>
<input type="hidden" name="dm_health_settings" value="1">
<table class="form-table" role="presentation">
<tr>
<th scope="row"><?php _e( 'Automatic Health Checks', 'wp-domain-mapping' ); ?></th>
<td>
<fieldset>
<legend class="screen-reader-text"><span><?php _e( 'Automatic Health Checks', 'wp-domain-mapping' ); ?></span></legend>
<label for="health_check_enabled">
<input name="health_check_enabled" type="checkbox" id="health_check_enabled" value="1" <?php checked( get_site_option( 'dm_health_check_enabled', true ) ); ?>>
<?php _e( 'Enable automatic daily health checks', 'wp-domain-mapping' ); ?>
</label>
</fieldset>
</td>
</tr>
<tr>
<th scope="row"><?php _e( 'Email Notifications', 'wp-domain-mapping' ); ?></th>
<td>
<fieldset>
<legend class="screen-reader-text"><span><?php _e( 'Email Notifications', 'wp-domain-mapping' ); ?></span></legend>
<label for="health_notifications_enabled">
<input name="health_notifications_enabled" type="checkbox" id="health_notifications_enabled" value="1" <?php checked( get_site_option( 'dm_health_notifications_enabled', true ) ); ?>>
<?php _e( 'Send email notifications when domain health issues are detected', 'wp-domain-mapping' ); ?>
</label>
</fieldset>
</td>
</tr>
<tr>
<th scope="row"><label for="notification_email"><?php _e( 'Notification Email', 'wp-domain-mapping' ); ?></label></th>
<td>
<input name="notification_email" type="email" id="notification_email" class="regular-text" value="<?php echo esc_attr( get_site_option( 'dm_notification_email', get_option( 'admin_email' ) ) ); ?>">
<p class="description"><?php _e( 'Email address for domain health notifications.', 'wp-domain-mapping' ); ?></p>
</td>
</tr>
<tr>
<th scope="row"><label for="ssl_expiry_threshold"><?php _e( 'SSL Expiry Warning', 'wp-domain-mapping' ); ?></label></th>
<td>
<input name="ssl_expiry_threshold" type="number" id="ssl_expiry_threshold" min="1" max="90" class="small-text" value="<?php echo esc_attr( get_site_option( 'dm_ssl_expiry_threshold', 14 ) ); ?>">
<span><?php _e( 'days', 'wp-domain-mapping' ); ?></span>
<p class="description"><?php _e( 'Send notifications when SSL certificates are expiring within this many days.', 'wp-domain-mapping' ); ?></p>
</td>
</tr>
<tr>
<th scope="row"><label for="health_check_batch_size"><?php _e( 'Batch Size', 'wp-domain-mapping' ); ?></label></th>
<td>
<input name="health_check_batch_size" type="number" id="health_check_batch_size" min="5" max="50" class="small-text" value="<?php echo esc_attr( get_site_option( 'dm_health_check_batch_size', 10 ) ); ?>">
<span><?php _e( 'domains per batch', 'wp-domain-mapping' ); ?></span>
<p class="description"><?php _e( 'Number of domains to check in each batch. Lower values prevent timeouts but take longer.', 'wp-domain-mapping' ); ?></p>
</td>
</tr>
</table>
<p class="submit">
<input type="submit" name="submit" id="submit" class="button button-primary" value="<?php esc_attr_e( 'Save Changes', 'wp-domain-mapping' ); ?>">
</p>
</form>
<script type="text/javascript">
jQuery(document).ready(function($) {
// Single domain health check
$('.check-domain-health').on('click', function() {
var $button = $(this);
var domain = $button.data('domain');
var $row = $button.closest('tr');
$button.prop('disabled', true).text('<?php esc_html_e( 'Checking...', 'wp-domain-mapping' ); ?>');
$.ajax({
url: ajaxurl,
type: 'POST',
data: {
action: 'dm_check_domain_health',
domain: domain,
nonce: '<?php echo wp_create_nonce( 'dm_check_domain_health' ); ?>'
},
dataType: 'json',
success: function(response) {
if (response.success) {
// Refresh page to show updated results
location.reload();
} else {
alert(response.data || '<?php esc_html_e( 'An error occurred during the health check.', 'wp-domain-mapping' ); ?>');
$button.prop('disabled', false).text('<?php esc_html_e( 'Check Now', 'wp-domain-mapping' ); ?>');
}
},
error: function() {
alert('<?php esc_html_e( 'An error occurred during the health check.', 'wp-domain-mapping' ); ?>');
$button.prop('disabled', false).text('<?php esc_html_e( 'Check Now', 'wp-domain-mapping' ); ?>');
}
});
});
});
</script>
<?php
}
/**
* Check if WP China Yes plugin is active
*/
function dm_is_wp_china_yes_active() {
if ( ! function_exists( 'is_plugin_active' ) ) {
include_once( ABSPATH . 'wp-admin/includes/plugin.php' );
}
// Check for common WP China Yes plugin paths
$possible_plugins = array(
'wp-china-yes/wp-china-yes.php',
'wp-china-yes/index.php',
'wp-china-yes/main.php'
);
foreach ( $possible_plugins as $plugin ) {
if ( is_plugin_active( $plugin ) ) {
return true;
}
}
// Also check if the WP_CHINA_YES constant is defined
return defined( 'WP_CHINA_YES' );
}
/**
* Render import/export tab content
*/
function dm_render_import_export_content() {
$wp_china_yes_active = dm_is_wp_china_yes_active();
?>
<?php if ( ! $wp_china_yes_active ) : ?>
<div class="notice notice-info inline">
<p>
<?php
$wpcy_installed = class_exists('WP_China_Yes'); // 检查是否安装了文派叶子插件
$wpcy_link = $wpcy_installed
? admin_url('admin.php?page=wp-china-yes')
: 'https://wpcy.com';
printf(
__('Install the %s high-performance component to use batch domain import/export.', 'wp-domain-mapping'),
sprintf(
'<a href="%s" target="_blank" rel="noopener noreferrer">%s</a>',
esc_url($wpcy_link),
__('文派叶子 🍃WPCY.COM', 'wp-domain-mapping')
)
);
?>
</p>
</div>
<?php endif; ?>
<h2><?php _e( 'Export Domain Mappings', 'wp-domain-mapping' ); ?></h2>
<div class="export-section" <?php echo ! $wp_china_yes_active ? 'style="opacity: 0.5; pointer-events: none;"' : ''; ?>>
<p><?php _e( 'Export all domain mappings to a CSV file.', 'wp-domain-mapping' ); ?></p>
<form method="post" action="">
<?php wp_nonce_field( 'domain_mapping_export', 'domain_mapping_export_nonce' ); ?>
<input type="hidden" name="domain_mapping_export" value="1">
<div style="margin-bottom: 15px;">
<label>
<input type="checkbox" name="include_header" value="1" checked <?php echo ! $wp_china_yes_active ? 'disabled' : ''; ?>>
<?php _e( 'Include column headers', 'wp-domain-mapping' ); ?>
</label>
</div>
<div style="margin-bottom: 15px;">
<label for="blog_id_filter"><?php _e( 'Export for specific site ID (optional):', 'wp-domain-mapping' ); ?></label>
<input type="number" id="blog_id_filter" name="blog_id_filter" min="1" class="regular-text" <?php echo ! $wp_china_yes_active ? 'disabled' : ''; ?>>
<p class="description"><?php _e( 'Leave empty to export all domains.', 'wp-domain-mapping' ); ?></p>
</div>
<p>
<input type="submit" class="button button-primary" value="<?php esc_attr_e( 'Export to CSV', 'wp-domain-mapping' ); ?>" <?php echo ! $wp_china_yes_active ? 'disabled' : ''; ?>>
</p>
</form>
</div>
<h2><?php _e( 'Import Domain Mappings', 'wp-domain-mapping' ); ?></h2>
<div class="import-section" <?php echo ! $wp_china_yes_active ? 'style="opacity: 0.5; pointer-events: none;"' : ''; ?>>
<p><?php _e( 'Import domain mappings from a CSV file.', 'wp-domain-mapping' ); ?></p>
<form method="post" enctype="multipart/form-data" id="domain-mapping-import-form">
<?php wp_nonce_field( 'domain_mapping_import', 'domain_mapping_import_nonce' ); ?>
<input type="hidden" name="domain_mapping_import" value="1">
<div style="margin-bottom: 15px;">
<label for="csv_file"><?php _e( 'CSV File:', 'wp-domain-mapping' ); ?></label><br>
<input type="file" id="csv_file" name="csv_file" accept=".csv" required <?php echo ! $wp_china_yes_active ? 'disabled' : ''; ?>>
<p class="description">
<?php _e( 'The CSV file should have the columns: blog_id, domain, active (1 or 0).', 'wp-domain-mapping' ); ?><br>
<?php _e( 'Example: 1,example.com,1', 'wp-domain-mapping' ); ?>
</p>
</div>
<div style="margin-bottom: 15px;">
<label>
<input type="checkbox" name="has_header" value="1" checked <?php echo ! $wp_china_yes_active ? 'disabled' : ''; ?>>
<?php _e( 'First row contains column headers', 'wp-domain-mapping' ); ?>
</label>
</div>
<div style="margin-bottom: 15px;">
<label>
<input type="checkbox" name="update_existing" value="1" checked <?php echo ! $wp_china_yes_active ? 'disabled' : ''; ?>>
<?php _e( 'Update existing mappings', 'wp-domain-mapping' ); ?>
</label>
<p class="description"><?php _e( 'If unchecked, will skip domains that already exist.', 'wp-domain-mapping' ); ?></p>
</div>
<div style="margin-bottom: 15px;">
<label>
<input type="checkbox" name="validate_sites" value="1" checked <?php echo ! $wp_china_yes_active ? 'disabled' : ''; ?>>
<?php _e( 'Validate site IDs', 'wp-domain-mapping' ); ?>
</label>
<p class="description"><?php _e( 'If checked, will only import domains for existing sites.', 'wp-domain-mapping' ); ?></p>
</div>
<p>
<input type="submit" class="button button-primary" value="<?php esc_attr_e( 'Import from CSV', 'wp-domain-mapping' ); ?>" <?php echo ! $wp_china_yes_active ? 'disabled' : ''; ?>>
</p>
</form>
<div id="import-progress" style="display: none; margin-top: 20px;">
<p><?php _e( 'Processing import...', 'wp-domain-mapping' ); ?></p>
<div class="progress-bar-outer" style="background-color: #f0f0f1; border-radius: 4px; height: 20px; width: 100%; overflow: hidden;">
<div class="progress-bar-inner" style="background-color: #2271b1; height: 100%; width: 0%;"></div>
</div>
<p class="progress-text">0%</p>
</div>
<div id="import-results" style="display: none; margin-top: 20px;">
<h3><?php _e( 'Import Results', 'wp-domain-mapping' ); ?></h3>
<div class="import-summary"></div>
<div class="import-details"></div>
</div>
</div>
<h2><?php _e( 'CSV Format', 'wp-domain-mapping' ); ?></h2>
<p><?php _e( 'The CSV file should follow this format:', 'wp-domain-mapping' ); ?></p>
<table class="widefat" style="margin-top: 10px;">
<thead>
<tr>
<th>blog_id</th>
<th>domain</th>
<th>active</th>
</tr>
</thead>
<tbody>
<tr>
<td>1</td>
<td>example.com</td>
<td>1</td>
</tr>
<tr>
<td>2</td>
<td>example.org</td>
<td>0</td>
</tr>
</tbody>
</table>
<ul style="margin-top: 15px;">
<li><strong>blog_id</strong>: <?php _e( 'The ID of the WordPress site (required)', 'wp-domain-mapping' ); ?></li>
<li><strong>domain</strong>: <?php _e( 'The domain name without http:// or https:// (required)', 'wp-domain-mapping' ); ?></li>
<li><strong>active</strong>: <?php _e( 'Set to 1 to make this the primary domain, 0 otherwise (required)', 'wp-domain-mapping' ); ?></li>
</ul>
<?php if ( $wp_china_yes_active ) : ?>
<script type="text/javascript">
jQuery(document).ready(function($) {
$('#domain-mapping-import-form').on('submit', function(e) {
e.preventDefault();
var formData = new FormData(this);
formData.append('action', 'dm_import_csv');
// Show progress bar
$('#import-progress').show();
$.ajax({
url: ajaxurl,
type: 'POST',
data: formData,
dataType: 'json',
contentType: false,
processData: false,
success: function(response) {
$('#import-progress').hide();
$('#import-results').show();
if (response.success) {
$('.import-summary').html(
'<div class="notice notice-success"><p>' +
response.data.message +
'</p></div>'
);
var details = '<table class="widefat">' +
'<thead><tr>' +
'<th>Status</th>' +
'<th>Details</th>' +
'</tr></thead><tbody>';
$.each(response.data.details, function(i, item) {
var statusClass = 'notice-success';
if (item.status === 'error') {
statusClass = 'notice-error';
} else if (item.status === 'warning') {
statusClass = 'notice-warning';
}
details += '<tr class="' + statusClass + '">' +
'<td>' + item.status + '</td>' +
'<td>' + item.message + '</td>' +
'</tr>';
});
details += '</tbody></table>';
$('.import-details').html(details);
} else {
$('.import-summary').html(
'<div class="notice notice-error"><p>' +
response.data +
'</p></div>'
);
}
},
error: function() {
$('#import-progress').hide();
$('#import-results').show();
$('.import-summary').html(
'<div class="notice notice-error"><p>' +
'<?php _e( 'An error occurred during import.', 'wp-domain-mapping' ); ?>' +
'</p></div>'
);
},
xhr: function() {
var xhr = new window.XMLHttpRequest();
xhr.upload.addEventListener('progress', function(evt) {
if (evt.lengthComputable) {
var percentComplete = evt.loaded / evt.total * 100;
$('.progress-bar-inner').css('width', percentComplete + '%');
$('.progress-text').text(Math.round(percentComplete) + '%');
}
}, false);
return xhr;
}
});
});
});
</script>
<?php endif; ?>
<?php
}
/**
* Render domains admin page
*/
function dm_render_domains_page() {
global $wpdb, $current_site;
WP_Domain_Mapping_Core::get_instance()->create_tables();
if ( isset($current_site->path) && $current_site->path != "/" ) {
wp_die( sprintf(
esc_html__( "<strong>Warning!</strong> This plugin will only work if WordPress is installed in the root directory of your webserver. It is currently installed in '%s'.", "wp-domain-mapping" ),
esc_html( $current_site->path )
));
}
$tables = dm_get_table_names();
$total_domains = $wpdb->get_var( "SELECT COUNT(*) FROM {$tables['domains']}" );
$primary_domains = $wpdb->get_var( "SELECT COUNT(*) FROM {$tables['domains']} WHERE active = 1" );
$edit_row = false;
if ( isset( $_GET['edit_domain'] ) ) {
$edit_domain = sanitize_text_field( $_GET['edit_domain'] );
$edit_row = $wpdb->get_row( $wpdb->prepare(
"SELECT * FROM {$tables['domains']} WHERE domain = %s",
$edit_domain
));
}
// Include the admin page template
require_once WP_DOMAIN_MAPPING_DIR_PATH . 'admin/domains-page.php';
}
/**
* Render user domain mapping page
*/
function dm_render_user_page( $protocol = null, $domains = null ) {
global $wpdb;
if ( null === $protocol ) {
$protocol = is_ssl() ? 'https://' : 'http://';
}
if ( null === $domains ) {
$domains = dm_get_domains_by_blog_id( $wpdb->blogid );
}
// Include original user page content
require_once WP_DOMAIN_MAPPING_DIR_PATH . 'admin/user-page.php';
}
/**
* Check COOKIE_DOMAIN configuration status in a performance-friendly way
* Uses caching to avoid reading wp-config.php on every page load
*
* @return array Status information about COOKIE_DOMAIN configuration
*/
function dm_check_cookie_domain_status() {
// Cache key for storing the check result
$cache_key = 'dm_cookie_domain_check_' . md5(ABSPATH);
$cached_result = get_transient($cache_key);
// Return cached result if still valid (cached for 1 hour)
if ($cached_result !== false) {
// Always check runtime values as they can change
$cached_result['runtime_defined'] = defined('COOKIE_DOMAIN');
$cached_result['is_mapped_request'] = defined('MAPPED_DOMAIN') && MAPPED_DOMAIN;
// Update debug info
if (defined('WP_DEBUG') && WP_DEBUG) {
$debug_parts = array();
$debug_parts[] = 'Runtime defined: ' . ($cached_result['runtime_defined'] ? 'Yes' : 'No');
if ($cached_result['runtime_defined']) {
$debug_parts[] = 'Value: ' . COOKIE_DOMAIN;
}
$debug_parts[] = 'Mapped request: ' . ($cached_result['is_mapped_request'] ? 'Yes' : 'No');
$cached_result['debug_info'] = 'Debug: ' . implode(', ', $debug_parts);
}
return $cached_result;
}
// Initialize result array
$result = array(
'is_optimal' => false,
'has_warning' => false,
'message' => '',
'debug_info' => '',
'wp_config_has_definition' => false,
'runtime_defined' => defined('COOKIE_DOMAIN'),
'is_mapped_request' => defined('MAPPED_DOMAIN') && MAPPED_DOMAIN
);
// Check if COOKIE_DOMAIN is defined in wp-config.php
$wp_config_path = ABSPATH . 'wp-config.php';
if (file_exists($wp_config_path)) {
// Use a more efficient approach - only read first part of file
$file_handle = fopen($wp_config_path, 'r');
if ($file_handle) {
$line_count = 0;
$max_lines = 200; // Only check first 200 lines for performance
while (($line = fgets($file_handle)) !== false && $line_count < $max_lines) {
$line = trim($line);
$line_count++;
// Skip empty lines and comments
if (empty($line) || substr($line, 0, 2) === '//' || substr($line, 0, 1) === '#' || substr($line, 0, 2) === '/*') {
continue;
}
// Stop at the end of configuration section
if (strpos($line, "require_once") !== false && strpos($line, "wp-settings.php") !== false) {
break;
}
// Check for COOKIE_DOMAIN definition
if (preg_match('/define\s*\(\s*[\'"]COOKIE_DOMAIN[\'"]/', $line)) {
$result['wp_config_has_definition'] = true;
break;
}
}
fclose($file_handle);
}
}
// Determine status and message - Always allow access, just show warnings
if (!$result['wp_config_has_definition']) {
$result['is_optimal'] = true;
if ($result['runtime_defined'] && $result['is_mapped_request']) {
$result['message'] = __('Not defined in wp-config.php (optimal). Currently managed by domain mapping.', 'wp-domain-mapping');
} else {
$result['message'] = __('Not defined in wp-config.php (optimal for domain mapping)', 'wp-domain-mapping');
}
} else {
// Even if defined in wp-config.php, don't block access - just show warning
if ($result['runtime_defined']) {
$result['has_warning'] = true;
$result['message'] = __('Defined in wp-config.php but currently working', 'wp-domain-mapping');
} else {
$result['has_warning'] = true;
$result['message'] = __('Defined in wp-config.php (may affect some domain mapping features)', 'wp-domain-mapping');
}
}
// Add debug information if WP_DEBUG is enabled
if (defined('WP_DEBUG') && WP_DEBUG) {
$debug_parts = array();
$debug_parts[] = 'Runtime defined: ' . ($result['runtime_defined'] ? 'Yes' : 'No');
if ($result['runtime_defined']) {
$debug_parts[] = 'Value: ' . COOKIE_DOMAIN;
}
$debug_parts[] = 'Mapped request: ' . ($result['is_mapped_request'] ? 'Yes' : 'No');
$debug_parts[] = 'Config file check: ' . ($result['wp_config_has_definition'] ? 'Found' : 'Not found');
$result['debug_info'] = 'Debug: ' . implode(', ', $debug_parts);
}
// Cache the result for 1 hour (exclude runtime values from cache)
$cache_data = $result;
unset($cache_data['runtime_defined'], $cache_data['is_mapped_request'], $cache_data['debug_info']);
set_transient($cache_key, $cache_data, HOUR_IN_SECONDS);
return $result;
}
/**
* Legacy function to prevent blocking access - always returns false
* This ensures backward compatibility with any existing checks
*/
function dm_cookie_domain_is_blocking() {
return false;
}
/**
* Safe check for COOKIE_DOMAIN without blocking access
* This can be used throughout the plugin without causing access issues
*/
function dm_is_cookie_domain_safe() {
$status = dm_check_cookie_domain_status();
return $status['is_optimal'] || $status['has_warning'];
}