WordPress网站迁移
本文最后更新于72 天前,其中的信息可能已经过时,如有错误请发送邮件到184874483@qq.com

本篇教程主要是解决wordpress网站暴力迁移的问题,特别是迁移到国内的服务器,解决了重定向,cdn,路径配置的问题。特别是在创建网站的时候参照:Hacker_Lawking的零基础绝美个人博客搭建+argon主题美化+嘉然看板娘搭建站点

仅能访问首页,但不能进一步查看

在大家都成功的将自己的域名解析到自己的IP地址,并且解析到站点名称,可以通过域名去访问自己网站的时候,我想各位都遇到一个问题:由于国内对于域名网站80或8080端口的严格限制,导致我可以通过我的域名去正确的访问我的服务器的首页,但是如果我接下来想要进行任何跳转的话,比方说跳转到我的管理后台或者是跳转到我首页中的某一篇文章,它都会返回给我这个域名没有备案,所以我猜测在跳转的时候中可能网站里面发生了一个就是重定向。

但实际上问题可能出现在网站程序在生成跳转链接时使用了IP地址或内部域名,而不是你备案的域名。这导致在跳转时,浏览器访问的是未备案的域名(或IP)从而被拦截。解决方案通常是将网站配置为所有访问都通过你备案的域名进行。具体方法取决于你使用的Web服务器(如Nginx、Apache等)和网站程序

1. 网站程序配置

WordPress 站点:在 wp-config.php 文件中添加:

// 强制使用您的域名
define('WP_HOME', 'http://你的域名.com');
define('WP_SITEURL', 'http://你的域名.com');

// 禁用任何自动重定向
define('WP_SITEURL', 'http://你的域名.com');
define('RELOCATE', false);

2. Web 服务器配置

Nginx 配置

server {
    listen 80;
    server_name 你的域名.com www.你的域名.com;
    # 强制跳转到HTTPS(如果使用)
    return 301 https://你的域名.com$request_uri;
}

server {
    listen 443 ssl;
    server_name 你的域名.com www.你的域名.com;
    
    # 如果不是主域名访问,重定向到主域名
    if ($host != '你的域名.com') {
        return 301 https://你的域名.com$request_uri;
    }
    
    # 其他配置...
    root /var/www/你的网站;
    index index.html index.php;
    
    # 处理重定向
    location / {
        try_files $uri $uri/ /index.php?$args;
    }
}

Apache 配置 (.htaccess)

RewriteEngine On

# 强制使用HTTPS
RewriteCond %{HTTPS} off
RewriteRule ^(.*)$ https://你的域名.com/$1 [L,R=301]

# 强制使用主域名(去掉www或添加www)
RewriteCond %{HTTP_HOST} !^你的域名\.com$ [NC]
RewriteRule ^(.*)$ https://你的域名.com/$1 [L,R=301]

# 或者如果要保留www
# RewriteCond %{HTTP_HOST} !^www\.你的域名\.com$ [NC]
# RewriteRule ^(.*)$ https://www.你的域名.com/$1 [L,R=301]

3. 检查主题文件中的重定向

检查当前使用的主题的 functions.php 文件,移除任何可能导致重定向的代码:

// 在主题的functions.php中查找并删除类似代码
remove_action('template_redirect', 'any_redirect_function');

4. 应用程序层重定向处理

在你的网站代码中(如PHP),确保所有重定向都使用绝对URL:

// 错误的做法
header("Location: /admin");

// 正确的做法
header("Location: https://你的域名.com/admin");

// 或者使用基础URL变量
$base_url = "https://你的域名.com";
header("Location: " . $base_url . "/admin");

5. 数据库检查(如有动态内容)

如果你的网站有数据库,检查数据库中是否存储了绝对URL

sql
-- 查找可能包含IP地址或错误域名的记录
SELECT * FROM posts WHERE post_content LIKE '%http://旧域名%';
SELECT * FROM options WHERE option_value LIKE '%http://旧域名%';

6.通过数据库修复(如果上述方法无效)

如果前面5个方法仍不奏效,可能需要直接修改数据库。创建一个临时的PHP文件来修复:

创建一个名为 fix_redirects.php 的文件,放在WordPress根目录:

<?php
require_once('wp-load.php');

// 更新站点URL
update_option('siteurl', 'http://你的域名.com');
update_option('home', 'http://你的域名.com');

// 检查并修复任何可能的重定向设置
$options_to_check = array(
    'wpurl',
    'siteurl', 
    'home',
    'redirect_url',
    'custom_redirect'
);

foreach ($options_to_check as $option) {
    if (get_option($option)) {
        update_option($option, 'http://你的域名.com');
    }
}

echo "重定向设置已修复!请立即删除此文件。";
?>

重要:访问 http://你的域名.com/fix_redirects.php 执行修复,然后立即删除这个文件

7. 检查插件引起的重定向

如果怀疑是插件问题,可以通过重命名插件文件夹临时禁用所有插件:

bash:
# 通过SSH或文件管理器
cd wp-content/plugins
mv plugins plugins_disabled

8. 测试方法

配置完成后,使用以下命令测试重定向:

bash:
curl -I http://你的域名.com/admin
curl -I https://你的域名.com/admin

检查返回的Location头是否都指向你的备案域名。

配置顺序:

  1. 首先检查网站程序设置
  2. 然后配置Web服务器重定向
  3. 最后检查代码中的硬编码重定向

登录后系统地修复

在成功登录后之台,接下来我们可以系统地修复设置,确保网站长期稳定运行。

1. 检查并修复 WordPress 核心设置

在 WordPress 后台进行以下设置:

常规设置

  • 进入 设置 > 常规
  • 检查以下两个字段:
    • WordPress 地址 (URL)http://你的域名.com
    • 站点地址 (URL)http://你的域名.com
  • 确保两个地址完全一致且正确
  • 点击 保存更改

2. 更新永久链接结构

  • 进入 设置 > 永久链接
  • 直接点击 保存更改(无需修改任何设置)
  • 这会刷新 WordPress 的重写规则,修复内部链接

3. 清理 wp-config.php 中的临时修复

现在可以移除或注释掉之前添加的强制重定向代码:

php
// 可以安全地删除或注释掉这两行,因为已在后台正确设置
// define('WP_HOME', 'http://你的域名.com');
// define('WP_SITEURL', 'http://你的域名.com');

多次定义

Warning: Constant WP_SITEURL already defined in /www/wwwroot/114.66.59.86/wp-config.php on line 23,在 wp-config.php 文件中重复定义了 WP_SITEURL 常量。通常有两种情况会导致这个问题:

  1. 在文件中多次定义同一个常量
  2. WordPress 核心文件或插件也尝试定义相同的常量

删除重复定义

在 wp-config.php 文件中:

// 找到这行(大约第23行):
define('WP_SITEURL', 'http://你的域名.com');

// 将其删除或注释掉:
// define('WP_SITEURL', 'http://你的域名.com');

多次重定向

如果我尝试去访问网站的话,它会显示我这个网站试图将你进行多次从重定向,这个”多次重定向”错误是典型的重定向循环问题。通常发生在以下情况:

  1. .htaccess 规则冲突
  2. WordPress 设置与服务器配置冲突
  3. 插件或主题中的重定向代码冲突
  4. 缓存问题

第一步:立即检查并修复 .htaccess 文件

请检查你的 .htaccess 文件,确保没有重复的重定向规则。暂时清空 .htaccess 文件内容,只保留最基础的WordPress规则:

apache
# BEGIN WordPress
RewriteEngine On
RewriteRule .* - [E=HTTP_AUTHORIZATION:%{HTTP:Authorization}]
RewriteBase /
RewriteRule ^index\.php$ - [L]
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule . /index.php [L]
# END WordPress

第二步:临时禁用所有插件

通过文件管理器或FTP,将 wp-content/plugins 文件夹重命名:

bash
mv plugins plugins_disabled

然后测试网站是否正常。

第三步:检查 WordPress 设置

在后台确认以下设置:

  • 设置 > 常规:两个URL地址相同
  • 不要在任何地方设置强制重定向

第四步:逐步排查问题

如果清空 .htaccess 后问题解决,说明是重定向规则问题。逐步添加规则来找出问题所在

附:常见的重定向循环原因

1. 多个重定向规则冲突

apache
# 错误示例 - 多个规则冲突
RewriteCond %{HTTP_HOST} ^旧域名.com [NC]
RewriteRule ^(.*)$ http://新域名.com/$1 [L,R=301]

RewriteCond %{HTTP_HOST} !^新域名.com$ [NC]
RewriteRule ^(.*)$ http://新域名.com/$1 [L,R=301]

2. WordPress 与服务器配置冲突

如果同时在 WordPress 插件和 .htaccess 中设置重定向。

3. 缓存导致的循环

浏览器或服务器缓存了旧的重定向规则。

重定向循环

我目前为止确定我的请求URL是我的那个域名,它后面的301重定向跳转到也是我那个域名。也就是说我的URL和我的location是地址是一样的。

刚才我所描述的情况非常典型 ,这是一个标准的重定向循环:请求发送到你的域名,服务器返回301重定向,但重定向目标还是同一个域名,导致无限循环。

问题根源分析

  1.  WordPress 地址设置问题:即使在后台设置了正确的地址,可能还有其他地方在强制重定向。
  2. 插件冲突:某些插件(特别是安全、缓存、重定向插件)可能添加了额外的重定向逻辑。
  3. 主题函数中的重定向代码主题的 functions.php 文件中可能包含强制重定向的代码。
  4. 服务器配置中的重复重定向可能有多个地方都在设置相同的重定向

第一步:立即诊断 – 创建测试文件

在WordPress根目录创建一个 test-redirect.php 文件:

<?php
// 临时测试文件 - 诊断重定向问题
echo "<h2>重定向诊断</h2>";

// 检查当前URL
echo "<p>当前请求: " . $_SERVER['REQUEST_URI'] . "</p>";

// 检查WordPress设置
require_once('wp-load.php');
echo "<p>WordPress地址: " . get_option('home') . "</p>";
echo "<p>站点地址: " . get_option('siteurl') . "</p>";

// 检查是否有任何重定向头
if (headers_sent()) {
    echo "<p style='color:red'>检测到HTTP头已发送(可能有重定向)</p>";
} else {
    echo "<p style='color:green'>HTTP头未发送</p>";
}

echo "<p>测试完成 - 如果能看到此消息,说明这个页面没有重定向</p>";
?>

访问 http://你的域名.com/test-redirect.php,如果能看到输出,说明问题不在服务器层面。

第二步:搜索所有重定向代码

通过SSH或文件管理器,在WordPress目录中搜索所有可能的重定向代码:

bash
# 搜索PHP文件中的重定向函数
cd /www/wwwroot/您的网站路径

# 搜索header重定向
grep -r "header.*Location" ./

# 搜索WordPress重定向函数
grep -r "wp_redirect" ./

# 搜索站点URL重定向
grep -r "site_url.*http" ./

# 搜索home_url重定向
grep -r "home_url.*http" ./

# 搜索模板重定向
grep -r "template_redirect" ./

# 特别检查主题和插件目录
grep -r "Location:" ./wp-content/themes/
grep -r "Location:" ./wp-content/plugins/

创建一个诊断脚本来确定重定向条件:

<?php
// 创建 diagnose-redirect.php 在WordPress根目录
echo "<h2>wp-load.php 重定向诊断</h2>";

// 包含 wp-load.php 但捕获可能的输出
ob_start();
require_once('wp-load.php');
$output = ob_get_clean();

if (!empty($output)) {
    echo "<p>wp-load.php 有输出: " . htmlspecialchars($output) . "</p>";
}

// 检查 WordPress 常量
echo "<p>ABSPATH: " . (defined('ABSPATH') ? ABSPATH : '未定义') . "</p>";
echo "<p>WPINC: " . (defined('WPINC') ? WPINC : '未定义') . "</p>";

// 检查安装状态
require_once(ABSPATH . 'wp-includes/load.php');
require_once(ABSPATH . 'wp-includes/functions.php');

global $wpdb;
if (isset($wpdb)) {
    echo "<p>数据库连接: 正常</p>";
    
    // 检查 wp_options 表
    $siteurl = $wpdb->get_var("SELECT option_value FROM {$wpdb->options} WHERE option_name = 'siteurl'");
    $home = $wpdb->get_var("SELECT option_value FROM {$wpdb->options} WHERE option_name = 'home'");
    
    echo "<p>数据库 siteurl: " . $siteurl . "</p>";
    echo "<p>数据库 home: " . $home . "</p>";
} else {
    echo "<p>数据库连接: 失败</p>";
}

echo "<p>诊断完成</p>";
?>

WordPress 认为它还没有完成安装

root@instance-KPAJWEdQ:/www/wwwroot/114.66.59.86# grep -n -A 10 -B 10 “header( ‘Location: ‘ . \$path )” ./wp-load.php 69- // Standardize $_SERVER variables across setups. 70- wp_fix_server_vars(); 71- 72- define( ‘WP_CONTENT_DIR’, ABSPATH . ‘wp-content’ ); 73- require_once ABSPATH . WPINC . ‘/functions.php’; 74- 75- $path = wp_guess_url() . ‘/wp-admin/setup-config.php’; 76- 77- // Redirect to setup-config.php. 78- if ( ! str_contains( $_SERVER[‘REQUEST_URI’], ‘setup-config’ ) ) { 79: header( ‘Location: ‘ . $path ); 80- exit; 81- } 82- 83- wp_load_translations_early(); 84- 85- // Die with an error message. 86- $die = ‘<p>’ . sprintf( 87- /* translators: %s: wp-config.php */ 88- __( “There doesn’t seem to be a %s file. It is needed before the installation can continue.” ), 89- ‘<code>wp-config.php</code>’ root@instance-KPAJWEdQ:/www/wwwroot/114.66.59.86#

根据输出的上下文,这个重定向是在WordPress没有找到wp-config.php文件时触发的。它会将用户重定向到安装脚本(setup-config.php

  • 第75行:$path = wp_guess_url() . '/wp-admin/setup-config.php';
  • 第78-81行:如果当前请求的URI不包含’setup-config’,则重定向到$path,即安装页面。

这意味着WordPress认为它还没有安装,因为找不到wp-config.php文件。但是,之前已经能够访问后台,这说明wp-config.php文件是存在的。可能的原因是:

  1. wp-config.php文件不在WordPress根目录中。
  2. 文件权限问题,导致WordPress无法读取。
  3. 文件内容有错误,导致无法正确加载。

检查 wp-config.php 文件状态

bash:
# 检查文件是否存在和权限
ls -la wp-config.php

# 检查文件内容(前几行)
head -20 wp-config.php

验证数据库连接

<?php
// 创建 test-db.php 文件
echo "<h2>数据库连接测试</h2>";

// 包含 wp-config.php 来获取配置
require_once('wp-config.php');

// 尝试连接数据库
try {
    $conn = new mysqli(DB_HOST, DB_USER, DB_PASSWORD, DB_NAME);
    
    if ($conn->connect_error) {
        echo "<p style='color:red'>数据库连接失败: " . $conn->connect_error . "</p>";
    } else {
        echo "<p style='color:green'>数据库连接成功!</p>";
        
        // 检查WordPress表是否存在
        $result = $conn->query("SHOW TABLES LIKE '{$table_prefix}%'");
        echo "<p>找到的WordPress表数量: " . $result->num_rows . "</p>";
        
        $conn->close();
    }
} catch (Exception $e) {
    echo "<p style='color:red'>错误: " . $e->getMessage() . "</p>";
}

echo "<p>测试完成</p>";
?>

检查文件权限

bash:
# 确保 wp-config.php 有正确权限
chmod 644 wp-config.php

# 检查文件所有者
ls -la wp-config.php

检查文件内容,确保包含基本的数据库配置:

<?php
// 基本数据库配置
define( 'DB_NAME', '你的数据库名' );
define( 'DB_USER', '你的数据库用户' );
define( 'DB_PASSWORD', '你的数据库密码' );
define( 'DB_HOST', 'localhost' );
define( 'DB_CHARSET', 'utf8' );
define( 'DB_COLLATE', '' );

// WordPress密钥(可以从 https://api.wordpress.org/secret-key/1.1/salt/ 生成)
define( 'AUTH_KEY',         'put your unique phrase here' );
define( 'SECURE_AUTH_KEY',  'put your unique phrase here' );
define( 'LOGGED_IN_KEY',    'put your unique phrase here' );
define( 'NONCE_KEY',        'put your unique phrase here' );
define( 'AUTH_SALT',        'put your unique phrase here' );
define( 'SECURE_AUTH_SALT', 'put your unique phrase here' );
define( 'LOGGED_IN_SALT',   'put your unique phrase here' );
define( 'NONCE_SALT',       'put your unique phrase here' );

$table_prefix = 'wp_';

define( 'WP_DEBUG', false );

if ( ! defined( 'ABSPATH' ) ) {
    define( 'ABSPATH', __DIR__ . '/' );
}

require_once ABSPATH . 'wp-settings.php';

修复方案

方案1:统一使用带 www 的域名

<?php
// 数据库配置
define( 'DB_NAME', '你的数据库名' );
define( 'DB_USER', '你的数据库用户' );
define( 'DB_PASSWORD', '你的数据库密码' );
define( 'DB_HOST', 'localhost' );

// 统一域名设置 - 都使用带www的版本
define('WP_HOME', 'http://www.preluna.xyz');
define('WP_SITEURL', 'http://www.preluna.xyz');

// 移除这行强制修改
// $_SERVER['HTTP_HOST'] = 'preluna.xyz';

// 其他配置...
define('RELOCATE', false);

// WordPress密钥
define( 'AUTH_KEY',         '你的密钥' );
// ... 其他密钥

$table_prefix = 'wp_';
define( 'WP_DEBUG', false );

if ( ! defined( 'ABSPATH' ) ) {
    define( 'ABSPATH', __DIR__ . '/' );
}

require_once ABSPATH . 'wp-settings.php';

方案2:统一使用不带 www 的域名

<?php
// 数据库配置...

// 统一域名设置 - 都使用不带www的版本
define('WP_HOME', 'http://preluna.xyz');
define('WP_SITEURL', 'http://preluna.xyz');

// 移除强制修改
// $_SERVER['HTTP_HOST'] = 'preluna.xyz';

// 其他配置...
?>

方案3:使用动态检测

<?php
// 数据库配置...

// 动态检测协议和域名
$protocol = (!empty($_SERVER['HTTPS']) && $_SERVER['HTTPS'] !== 'off') ? 'https' : 'http';
$domain = $_SERVER['HTTP_HOST'];

define('WP_HOME', $protocol . '://' . $domain);
define('WP_SITEURL', $protocol . '://' . $domain);

// 移除强制修改
// $_SERVER['HTTP_HOST'] = 'preluna.xyz';

// 其他配置...
?>

额外步骤:配置 .htaccess 统一域名

为了确保所有访问都统一到一种域名格式,在 .htaccess 中添加:

如果选择带 www 的版本:

apache
# 强制使用www版本
RewriteCond %{HTTP_HOST} ^preluna\.xyz [NC]
RewriteRule ^(.*)$ http://www.preluna.xyz/$1 [L,R=301]

如果选择不带 www 的版本:

apache
# 强制去掉www
RewriteCond %{HTTP_HOST} ^www\.preluna\.xyz [NC]
RewriteRule ^(.*)$ http://preluna.xyz/$1 [L,R=301]

检查数据库中的设置

sql
UPDATE wp_options SET option_value = 'http://www.preluna.xyz' WHERE option_name IN ('home', 'siteurl');

推荐方案1(统一使用带 www 的版本),至少我就是这么干的。

网页加载缓慢

按照之前的方法,进行了抓包测验,这时候并没有提取到关于300的请求包了,但是网站加载速度普遍在1000毫秒以上,这到底是什么原因呢?

当你网站从国外服务器迁移到国内的时候,这个原因很可能是采用了cdn服务,你迁移完成之后,但是你的cdn并没有改变,用的还是国外的cdn

创建性能测试脚本

在WordPress根目录创建 performance-test.php

<?php
// performance-test.php - 性能诊断脚本
echo "<h2>WordPress 性能诊断</h2>";

// 记录开始时间
$start_time = microtime(true);

// 1. 测试基础PHP性能
$php_start = microtime(true);
for ($i = 0; $i < 100000; $i++) { }
$php_time = microtime(true) - $php_start;

// 2. 测试数据库连接性能
$db_start = microtime(true);
require_once('wp-load.php');
global $wpdb;
$db_time = microtime(true) - $db_start;

// 3. 测试简单查询性能
$query_start = microtime(true);
$result = $wpdb->get_var("SELECT option_value FROM {$wpdb->options} WHERE option_name = 'home'");
$query_time = microtime(true) - $query_start;

// 4. 测试主题加载性能
$theme_start = microtime(true);
get_template_directory();
$theme_time = microtime(true) - $theme_start;

// 输出结果
echo "<h3>性能指标:</h3>";
echo "<p>PHP基础运算: " . round($php_time * 1000, 2) . " ms</p>";
echo "<p>数据库连接: " . round($db_time * 1000, 2) . " ms</p>";
echo "<p>简单查询: " . round($query_time * 1000, 2) . " ms</p>";
echo "<p>主题加载: " . round($theme_time * 1000, 2) . " ms</p>";
echo "<p>总脚本执行: " . round((microtime(true) - $start_time) * 1000, 2) . " ms</p>";

// 服务器信息
echo "<h3>服务器信息:</h3>";
echo "<p>PHP版本: " . phpversion() . "</p>";
echo "<p>内存限制: " . ini_get('memory_limit') . "</p>";
echo "<p>最大执行时间: " . ini_get('max_execution_time') . "s</p>";
echo "<p>已用内存: " . round(memory_get_usage() / 1024 / 1024, 2) . "MB</p>";

// 检查OPcache状态
if (function_exists('opcache_get_status')) {
    $opcache = opcache_get_status();
    echo "<p>OPcache启用: " . ($opcache['opcache_enabled'] ? '是' : '否') . "</p>";
}
?>

访问这个文件查看基础性能指标。

服务器资源检查

创建WordPress性能分析文件:

<?php
// wp-performance-debug.php
define('SAVEQUERIES', true); // 启用查询记录
define('WP_DEBUG', true);

require_once('wp-load.php');

echo "<h2>WordPress 详细性能分析</h2>";

// 记录查询信息
global $wpdb;
echo "<h3>数据库查询 (" . count($wpdb->queries) . " 次):</h3>";
$total_query_time = 0;
foreach ($wpdb->queries as $q) {
    $total_query_time += $q[1];
    echo "<p>" . round($q[1] * 1000, 2) . "ms: " . substr($q[0], 0, 100) . "...</p>";
}
echo "<p><strong>总查询时间: " . round($total_query_time * 1000, 2) . "ms</strong></p>";

// 检查活动插件
echo "<h3>活动插件:</h3>";
$active_plugins = get_option('active_plugins');
foreach ($active_plugins as $plugin) {
    echo "<p>" . $plugin . "</p>";
}

// 内存使用情况
echo "<h3>内存使用:</h3>";
echo "<p>峰值内存使用: " . round(memory_get_peak_usage() / 1024 / 1024, 2) . "MB</p>";
?>

常见的WordPress性能瓶颈

1. 插件过多或低效插件

bash:
# 检查插件数量
wp plugin list --status=active --format=count

2. 主题性能问题

  • 检查是否使用轻量级主题
  • 禁用不必要的主题功能

3. 数据库优化

sql
-- 优化WordPress表
OPTIMIZE TABLE wp_options, wp_posts, wp_postmeta;

4. PHP配置优化

检查 php.ini 配置:

ini:
memory_limit = 256M
max_execution_time = 300
opcache.enable=1
opcache.memory_consumption=256

立即优化措施

1. 启用缓存

在 wp-config.php 中添加:

php:
// 启用对象缓存(如果支持)
define('WP_CACHE', true);

// 增加内存限制
define('WP_MEMORY_LIMIT', '256M');

2. 禁用不必要的插件

通过文件管理器暂时禁用性能消耗大的插件:

bash
cd wp-content/plugins
mv problematic-plugin problematic-plugin-disabled

3. 检查并优化 .htaccess

确保有适当的缓存头:

apache:
# 启用压缩
<IfModule mod_deflate.c>
    AddOutputFilterByType DEFLATE text/html text/plain text/xml text/css text/javascript application/javascript
</IfModule>

# 设置过期头
<IfModule mod_expires.c>
    ExpiresActive On
    ExpiresByType image/jpg "access plus 1 year"
    ExpiresByType image/jpeg "access plus 1 year"
    ExpiresByType image/gif "access plus 1 year"
    ExpiresByType image/png "access plus 1 year"
    ExpiresByType text/css "access plus 1 month"
    ExpiresByType application/pdf "access plus 1 month"
    ExpiresByType text/javascript "access plus 1 month"
    ExpiresByType text/html "access plus 600 seconds"
</IfModule>

数据库连接性能问题

根据performance-test.php和wp-performance-debug.php的返回结果(见前图)

数据库连接如此慢的可能原因:

  1. 数据库服务器位置问题
    • 数据库服务器与Web服务器不在同一台机器
    • 数据库服务器在远程,网络延迟高
  2. 数据库配置问题
    • MySQL配置不当
    • 连接池配置问题
    • 最大连接数限制
  3. 网络问题
    • DNS解析慢
    • 网络路由问题

第一步:检查数据库连接详情

创建 db-connection-test.php

<?php
echo "<h2>数据库连接详细诊断</h2>";

// 测试直接MySQL连接
$start = microtime(true);

// 从wp-config.php获取数据库配置
require_once('wp-config.php');

echo "<p>数据库主机: " . DB_HOST . "</p>";
echo "<p>数据库名称: " . DB_NAME . "</p>";

// 测试连接
$conn_start = microtime(true);
$mysqli = new mysqli(DB_HOST, DB_USER, DB_PASSWORD, DB_NAME);
$conn_time = microtime(true) - $conn_start;

if ($mysqli->connect_error) {
    echo "<p style='color:red'>连接失败: " . $mysqli->connect_error . "</p>";
} else {
    echo "<p style='color:green'>MySQLi连接成功: " . round($conn_time * 1000, 2) . " ms</p>";
    $mysqli->close();
}

// 测试PDO连接
$pdo_start = microtime(true);
try {
    $pdo = new PDO("mysql:host=" . DB_HOST . ";dbname=" . DB_NAME, DB_USER, DB_PASSWORD);
    $pdo->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
    $pdo_time = microtime(true) - $pdo_start;
    echo "<p style='color:green'>PDO连接成功: " . round($pdo_time * 1000, 2) . " ms</p>";
    $pdo = null;
} catch (PDOException $e) {
    echo "<p style='color:red'>PDO连接失败: " . $e->getMessage() . "</p>";
}

// 测试DNS解析
$dns_start = microtime(true);
$ip = gethostbyname(DB_HOST);
$dns_time = microtime(true) - $dns_start;
echo "<p>数据库主机IP: " . $ip . " (解析耗时: " . round($dns_time * 1000, 2) . " ms)</p>";

echo "<p><strong>总诊断时间: " . round((microtime(true) - $start) * 1000, 2) . " ms</strong></p>";
?>

第二步:检查MySQL配置和状态

通过SSH连接到服务器,运行:

bash:
# 检查MySQL运行状态
systemctl status mysql

# 检查MySQL错误日志
tail -f /var/log/mysql/error.log

# 检查MySQL连接状态
mysql -u root -p -e "SHOW STATUS LIKE 'Threads_connected'; SHOW PROCESSLIST; SHOW VARIABLES LIKE 'max_connections';"

# 检查MySQL性能状态
mysql -u root -p -e "SHOW STATUS LIKE 'Aborted_connects'; SHOW STATUS LIKE 'Connection_errors%';"

第三步:优化数据库连接

第三步:优化数据库连接

在 wp-config.php 中添加持久连接:

// 在 wp-config.php 中添加
define('WP_DEBUG', false);

// 启用持久数据库连接
$mysql_connect = mysqli_connect(DB_HOST, DB_USER, DB_PASSWORD, DB_NAME, null, null, MYSQLI_CLIENT_COMPRESS | MYSQLI_CLIENT_PERSISTENT);

// 或者使用数据库连接优化
define('WP_USE_EXT_MYSQL', false);

方案B:优化MySQL配置

检查并优化MySQL配置 (/etc/mysql/my.cnf 或 /etc/my.cnf):

ini:
[mysqld]
# 连接相关优化
max_connections = 100
connect_timeout = 10
wait_timeout = 600
interactive_timeout = 600

# 性能优化
query_cache_type = 1
query_cache_size = 64M
query_cache_limit = 2M

# 内存优化
key_buffer_size = 256M
innodb_buffer_pool_size = 512M

方案C:使用对象缓存

安装Redis或Memcached来缓存数据库查询:

1.安装Redis:

bash:
apt-get install redis-server php-redis

2.在WordPress中配置:

安装Redis Object Cache插件,或在 wp-config.php 中添加:

// Redis缓存配置
define('WP_REDIS_HOST', '127.0.0.1');
define('WP_REDIS_PORT', 6379);
define('WP_REDIS_TIMEOUT', 1);
define('WP_REDIS_READ_TIMEOUT', 1);

第四步:立即缓解措施

1. 增加PHP内存限制

在 wp-config.php 中:

define('WP_MEMORY_LIMIT', '256M');
define('WP_MAX_MEMORY_LIMIT', '512M');

2. 使用数据库连接优化插件

安装查询优化插件如:

  • Query Monitor
  • WP Optimize
  • Database Cleaner

3. 检查并修复数据库

bash
# 优化所有WordPress表
mysqlcheck -u root -p --auto-repair --optimize --all-databases

真正的瓶颈所在

从dp-connnection-test.php的返回结果中(见前图),关键发现:数据库连接本身很快,但 WordPress 在 wp-load.php 中执行的其他操作非常耗时。所以问题不在数据库连接,而在 WordPress 初始化过程中执行的其他操作:

  1. 插件加载和初始化
  2. 主题函数加载
  3. WordPress 核心文件解析
  4. 钩子和过滤器执行

让我们创建一个更详细的诊断脚本来找出具体瓶颈:

创建 monitor-performance.php

<?php
// 实时监控WordPress加载性能
define('SAVEQUERIES', true);
define('WP_DEBUG', true);

require_once('wp-load.php');

echo "<h2>实时性能监控</h2>";

// 记录查询性能
global $wpdb, $timestart;
$total_time = microtime(true) - $timestart;

echo "<p><strong>总加载时间: " . round($total_time * 1000, 2) . "ms</strong></p>";

// 查询分析
if (!empty($wpdb->queries)) {
    $query_time = 0;
    foreach ($wpdb->queries as $q) {
        $query_time += $q[1];
    }
    echo "<p>数据库查询时间: " . round($query_time * 1000, 2) . "ms</p>";
    echo "<p>查询次数: " . count($wpdb->queries) . "</p>";
}

// 内存使用
echo "<p>内存使用: " . round(memory_get_usage() / 1024 / 1024, 2) . "MB</p>";
echo "<p>峰值内存: " . round(memory_get_peak_usage() / 1024 / 1024, 2) . "MB</p>";

// 活动插件
$active_plugins = get_option('active_plugins');
echo "<p>活动插件数量: " . count($active_plugins) . "</p>";

// 输出最慢的5个查询
if (!empty($wpdb->queries)) {
    echo "<h3>最慢的查询:</h3>";
    usort($wpdb->queries, function($a, $b) {
        return $b[1] <=> $a[1];
    });
    
    for ($i = 0; $i < min(5, count($wpdb->queries)); $i++) {
        echo "<p>" . round($wpdb->queries[$i][1] * 1000, 2) . "ms: " . 
             substr($wpdb->queries[$i][0], 0, 100) . "...</p>";
    }
}
?>

在 wp-config.php 文件中添加以下优化配置:

// 性能优化配置 - 新增部分
define('WP_DEBUG', false);
define('WP_DEBUG_DISPLAY', false);
define('WP_DEBUG_LOG', false);

// 内存优化
define('WP_MEMORY_LIMIT', '256M');
define('WP_MAX_MEMORY_LIMIT', '512M');

// 禁用文章修订和自动保存
define('WP_POST_REVISIONS', 5); // 限制修订版本数量
define('AUTOSAVE_INTERVAL', 160); // 增加自动保存间隔到160秒

// 禁用垃圾站内信
define('EMPTY_TRASH_DAYS', 7);

// 启用对象缓存(如果有Redis/Memcached)
// define('WP_CACHE', true);

// 强制禁用文件编辑(安全+性能)
define('DISALLOW_FILE_EDIT', true);

// 压缩CSS和JS
define('COMPRESS_CSS', true);
define('COMPRESS_SCRIPTS', true);
define('CONCATENATE_SCRIPTS', true);
define('ENFORCE_GZIP', true);

系统化插件性能排查

创建自动化的插件性能测试脚本

PHP:
<?php
// plugin-performance-test.php
echo "<h2>插件性能测试</h2>";

// 获取所有活动插件
require_once('wp-config.php');
require_once(ABSPATH . 'wp-includes/load.php');
require_once(ABSPATH . 'wp-includes/plugin.php');

$active_plugins = get_option('active_plugins', array());
$plugin_performance = [];

// 测试每个插件的加载时间
foreach ($active_plugins as $plugin) {
    $start_time = microtime(true);
    
    // 模拟插件加载
    $plugin_path = WP_PLUGIN_DIR . '/' . $plugin;
    if (file_exists($plugin_path)) {
        include_once($plugin_path);
    }
    
    $load_time = microtime(true) - $start_time;
    $plugin_performance[$plugin] = $load_time;
}

// 排序并显示结果
arsort($plugin_performance);
echo "<h3>插件加载时间排序:</h3>";
foreach ($plugin_performance as $plugin => $time) {
    echo "<p>" . round($time * 1000, 2) . "ms - " . $plugin . "</p>";
}

// 建议禁用最慢的插件
echo "<h3>优化建议:</h3>";
$slow_plugins = array_slice($plugin_performance, 0, 3, true);
foreach ($slow_plugins as $plugin => $time) {
    if ($time > 0.01) { // 超过10ms的插件
        echo "<p style='color:red'>建议检查: " . $plugin . " (" . round($time * 1000, 2) . "ms)</p>";
    }
}
?>

Font Awesome字体文件

在进行数据包分析的时候,发现有几个文件,其中有几个请求标题:https://fastly.jsdelivr.net/gh/solstice23/argon-theme@1.3.5/assets/vendor/font-awesome/fonts/fontawesome-webfont.woff2?v=4.7.0 这几个数据包加载的时间非常长,我该如何去找到这个是哪一个部件导致它产生了这个请求标题。

Request URL https://fastly.jsdelivr.net/gh/solstice23/argon-theme@1.3.5/assets/vendor/font-awesome/fonts/fontawesome-webfont.woff2?v=4.7.0 Request Method GET Status Code 200 OK Remote Address 127.0.0.1:8080 Referrer Policy strict-origin-when-cross-origin accept-ranges bytes access-control-allow-origin * access-control-expose-headers * age 2314223 alt-svc h3=”:443″;ma=86400,h3-29=”:443″;ma=86400,h3-27=”:443″;ma=86400 cache-control public, max-age=31536000, s-maxage=31536000, immutable content-length 77160 content-type font/woff2 cross-origin-resource-policy cross-origin date Wed, 19 Nov 2025 14:46:40 GMT etag W/”12d68-1vSMun0Hb7by/Wupk6dbncHsvww” strict-transport-security max-age=31536000; includeSubDomains; preload timing-allow-origin * vary Accept-Encoding x-cache HIT, HIT x-content-type-options nosniff x-jsd-version 1.3.5 x-jsd-version-type version x-served-by cache-fra-etou8220036-FRA, cache-sin-wsss1830094-SIN origin http://www.preluna.xyz referer https://fastly.jsdelivr.net/gh/solstice23/argon-theme@1.3.5/assets/argon_css_merged.css?ver=1.注意到这个请求是来自Argon主题的Font Awesome字体文件。从报头信息来看,这个请求是通过jsDelivr CDN服务的,并且状态为200,缓存控制设置了一年的有效期,且已经命中了缓存(x-cache: HIT)。但是,由于这个资源是通过CDN加载的,如果CDN在国内访问速度不佳,可能会导致加载缓慢。

根据报头,我们可以获取以下信息:

  • 请求的字体文件来自:https://fastly.jsdelivr.net/gh/solstice23/argon-theme@1.3.5/assets/vendor/font-awesome/fonts/fontawesome-webfont.woff2
  • 引用者(referer)是:https://fastly.jsdelivr.net/gh/solstice23/argon-theme@1.3.5/assets/argon_css_merged.css?ver=1.3.5

这意味着,这个字体文件是通过Argon主题的合并CSS文件(argon_css_merged.css)中引用的。

解决方案:

  1. 将字体文件本地化(下载到你的服务器,并修改CSS中的引用路径)。
  2. 或者,更换CDN源,使用国内更快的CDN,例如将fastly.jsdelivr.net替换为cdn.jsdelivr.net(但注意,jsDelivr在中国大陆的访问有时不稳定)或使用国内CDN

报头信息分析

Remote Address: 127.0.0.1:8080

  • 这表示请求被代理到了本地端口 8080
  • 可能是网络环境有代理设置,或者是某些加速/安全软件导致的

age: 2314223

  • 这个资源在CDN上已经缓存了 2,314,223 秒(约26.8天)
  • 时间过长,可能CDN节点有问题

x-cache: HIT, HIT

  • 资源命中了CDN缓存(这是好的)

缓存控制看起来正常

  • cache-control: public, max-age=31536000 – 缓存1年
  • 但实际加载慢可能是网络问题

问题根源排查

1. 检查代理设置

这个请求被指向了 127.0.0.1:8080,说明存在代理。请检查:

bash
# 检查系统代理设置
echo $http_proxy
echo $https_proxy

# 检查浏览器代理设置
# 在浏览器设置中搜索"代理"

2. 直接测试CDN速度

创建测试脚本来检查真实的CDN响应速度:

<?php
// cdn-speed-test.php
echo "<h2>CDN速度测试</h2>";

$urls = [
    'https://fastly.jsdelivr.net/gh/solstice23/argon-theme@1.3.5/assets/vendor/font-awesome/fonts/fontawesome-webfont.woff2?v=4.7.0',
    'https://cdn.jsdelivr.net/gh/solstice23/argon-theme@1.3.5/assets/vendor/font-awesome/fonts/fontawesome-webfont.woff2?v=4.7.0',
    'https://gcore.jsdelivr.net/gh/solstice23/argon-theme@1.3.5/assets/vendor/font-awesome/fonts/fontawesome-webfont.woff2?v=4.7.0'
];

foreach ($urls as $url) {
    $start = microtime(true);
    
    $ch = curl_init();
    curl_setopt($ch, CURLOPT_URL, $url);
    curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
    curl_setopt($ch, CURLOPT_HEADER, true);
    curl_setopt($ch, CURLOPT_NOBODY, true);
    curl_setopt($ch, CURLOPT_TIMEOUT, 10);
    
    $response = curl_exec($ch);
    $time = round((microtime(true) - $start) * 1000, 2);
    
    if (curl_errno($ch)) {
        echo "<p style='color:red'>❌ {$url} - 错误: " . curl_error($ch) . " ({$time}ms)</p>";
    } else {
        $http_code = curl_getinfo($ch, CURLINFO_HTTP_CODE);
        echo "<p>✅ {$url} - 状态: {$http_code} ({$time}ms)</p>";
    }
    
    curl_close($ch);
}
?>

3. 找到具体调用位置

这个字体文件是通过Argon主题的CSS文件调用的。让我们找到具体位置:

检查主题的CSS文件

bash
# 在主题目录中搜索font-awesome相关文件
cd /www/wwwroot/114.66.59.86/wp-content/themes
find . -name "*.css" -exec grep -l "fontawesome-webfont" {} \;
find . -name "*.css" -exec grep -l "fastly.jsdelivr" {} \;

4. 立即解决方案

方案A:替换CDN域名

在主题的CSS文件中,将 fastly.jsdelivr.net 替换为其他CDN:

bash
# 备份原文件
cd /www/wwwroot/114.66.59.86/wp-content/themes/argon

# 查找并替换(先确认文件位置)
find . -name "*.css" -exec sed -i 's|fastly\.jsdelivr\.net|gcore.jsdelivr.net|g' {} \;

方案B:本地化字体文件(推荐,我就是这么干的)

1.下载字体文件到本地:

bash:
cd /www/wwwroot/114.66.59.86/wp-content/themes/argon/assets/vendor/font-awesome/fonts/

# 下载字体文件
wget https://fastly.jsdelivr.net/gh/solstice23/argon-theme@1.3.5/assets/vendor/font-awesome/fonts/fontawesome-webfont.woff2

2.修改CSS引用:

找到调用这个字体的CSS文件,将URL改为相对路径

css
/* 将原来的 */
src: url('https://fastly.jsdelivr.net/gh/solstice23/argon-theme@1.3.5/assets/vendor/font-awesome/fonts/fontawesome-webfont.woff2?v=4.7.0')

/* 改为 */
src: url('./vendor/font-awesome/fonts/fontawesome-webfont.woff2?v=4.7.0')

5. 检查网络环境

创建网络诊断脚本:

<?php
// network-diagnose.php
echo "<h2>网络环境诊断</h2>";

// 测试DNS解析
$hosts = ['fastly.jsdelivr.net', 'cdn.jsdelivr.net', 'gcore.jsdelivr.net'];
foreach ($hosts as $host) {
    $start = microtime(true);
    $ip = gethostbyname($host);
    $time = round((microtime(true) - $start) * 1000, 2);
    echo "<p>DNS解析 {$host} -> {$ip} ({$time}ms)</p>";
}

// 检查是否有代理
echo "<p>HTTP_PROXY: " . (isset($_SERVER['HTTP_PROXY']) ? $_SERVER['HTTP_PROXY'] : '未设置') . "</p>";
echo "<p>HTTPS_PROXY: " . (isset($_SERVER['HTTPS_PROXY']) ? $_SERVER['HTTPS_PROXY'] : '未设置') . "</p>";
?>

字体文件本地化操作指南

第一步:定位CSS文件

首先找到Argon主题中引用这个字体文件的CSS文件:

bash:
# 进入主题目录
cd /www/wwwroot/114.66.59.86/wp-content/themes

# 搜索包含fontawesome-webfont的CSS文件
find . -name "*.css" -exec grep -l "fontawesome-webfont" {} \;

# 或者搜索包含fastly.jsdelivr的CSS文件
find . -name "*.css" -exec grep -l "fastly.jsdelivr" {} \;

执行后会显示类似这样的结果:

text:
./argon/assets/css/argon.css
./argon/assets/vendor/font-awesome/css/font-awesome.css

第二步:下载字体文件到本地

创建本地字体目录并下载文件:

bash:
# 进入主题的字体目录(如果不存在就创建)
cd /www/wwwroot/114.66.59.86/wp-content/themes/argon/argon/assets/vendor/font-awesome/fonts/
# 这边把路径改成你自己的文件实际路径。
# 如果fonts目录不存在,先创建
mkdir -p fonts
cd fonts

# 下载字体文件
wget https://fastly.jsdelivr.net/gh/solstice23/argon-theme@1.3.5/assets/vendor/font-awesome/fonts/fontawesome-webfont.woff2

# 如果需要,下载其他格式的字体文件(确保完整)
wget https://fastly.jsdelivr.net/gh/solstice23/argon-theme@1.3.5/assets/vendor/font-awesome/fonts/fontawesome-webfont.woff
wget https://fastly.jsdelivr.net/gh/solstice23/argon-theme@1.3.5/assets/vendor/font-awesome/fonts/fontawesome-webfont.ttf
wget https://fastly.jsdelivr.net/gh/solstice23/argon-theme@1.3.5/assets/vendor/font-awesome/fonts/fontawesome-webfont.eot

# 验证文件是否下载成功
ls -la

应该看到类似这样的文件列表:

fontawesome-webfont.woff2
fontawesome-webfont.woff  
fontawesome-webfont.ttf
fontawesome-webfont.eot

如果你创建网站的时候是参照:Hacker_Lawking的零基础绝美个人博客搭建+argon主题美化+嘉然看板娘搭建站点的话,我建议你看一下你当前应用主题是哪一个主题,毕竟你会注意到他的主题文件夹下是有一个多层嵌套的。

第三步:修改CSS文件中的引用路径

找到具体的CSS文件并修改URL引用:

bash:
# 回到主题目录
cd /www/wwwroot/114.66.59.86/wp-content/themes/argon

# 备份原CSS文件(重要!)
cp assets/css/argon.css assets/css/argon.css.backup
cp assets/vendor/font-awesome/css/font-awesome.css assets/vendor/font-awesome/css/font-awesome.css.backup

现在编辑包含字体引用的CSS文件。使用你熟悉的编辑器,比如:

使用nano编辑:

bash:
nano assets/vendor/font-awesome/css/font-awesome.css

或者使用vim:

bash:
vim assets/vendor/font-awesome/css/font-awesome.css

在文件中查找类似这样的代码块:

css:
@font-face {
  font-family: 'FontAwesome';
  src: url('https://fastly.jsdelivr.net/gh/solstice23/argon-theme@1.3.5/assets/vendor/font-awesome/fonts/fontawesome-webfont.eot?v=4.7.0');
  src: url('https://fastly.jsdelivr.net/gh/solstice23/argon-theme@1.3.5/assets/vendor/font-awesome/fonts/fontawesome-webfont.eot?#iefix&v=4.7.0') format('embedded-opentype'),
       url('https://fastly.jsdelivr.net/gh/solstice23/argon-theme@1.3.5/assets/vendor/font-awesome/fonts/fontawesome-webfont.woff2?v=4.7.0') format('woff2'),
       url('https://fastly.jsdelivr.net/gh/solstice23/argon-theme@1.3.5/assets/vendor/font-awesome/fonts/fontawesome-webfont.woff?v=4.7.0') format('woff'),
       url('https://fastly.jsdelivr.net/gh/solstice23/argon-theme@1.3.5/assets/vendor/font-awesome/fonts/fontawesome-webfont.ttf?v=4.7.0') format('truetype'),
       url('https://fastly.jsdelivr.net/gh/solstice23/argon-theme@1.3.5/assets/vendor/font-awesome/fonts/fontawesome-webfont.svg?v=4.7.0#fontawesomeregular') format('svg');
}

修改为相对路径:

css:
@font-face {
  font-family: 'FontAwesome';
  src: url('../fonts/fontawesome-webfont.eot?v=4.7.0');
  src: url('../fonts/fontawesome-webfont.eot?#iefix&v=4.7.0') format('embedded-opentype'),
       url('../fonts/fontawesome-webfont.woff2?v=4.7.0') format('woff2'),
       url('../fonts/fontawesome-webfont.woff?v=4.7.0') format('woff'),
       url('../fonts/fontawesome-webfont.ttf?v=4.7.0') format('truetype'),
       url('../fonts/fontawesome-webfont.svg?v=4.7.0#fontawesomeregular') format('svg');
}

同理,如果你是用Hacker_LawKing提供了文件的话,而且又不会进行修改,那你就按照我图片提供的代码来吧。

第四步:验证修改

创建一个验证脚本来测试字体加载:

<?php
// font-test.php - 放在WordPress根目录
echo "<h2>字体本地化测试</h2>";

// 测试本地字体文件是否存在
$font_files = [
    '/wp-content/themes/argon/argon/assets/vendor/font-awesome/fonts/fontawesome-webfont.woff2',
    '/wp-content/themes/argon/argon/assets/vendor/font-awesome/fonts/fontawesome-webfont.woff',
    '/wp-content/themes/argon/argon/assets/vendor/font-awesome/fonts/fontawesome-webfont.ttf'
];

foreach ($font_files as $font) {
    $full_path = $_SERVER['DOCUMENT_ROOT'] . $font;
    if (file_exists($full_path)) {
        $size = round(filesize($full_path) / 1024, 2);
        echo "<p style='color:green'>✅ {$font} - 存在 ({$size}KB)</p>";
    } else {
        echo "<p style='color:red'>❌ {$font} - 不存在</p>";
    }
}

// 测试CSS文件修改
$css_path = $_SERVER['DOCUMENT_ROOT'] . '/wp-content/themes/argon/argon/assets/vendor/font-awesome/css/font-awesome.css';
if (file_exists($css_path)) {
    $content = file_get_contents($css_path);
    if (strpos($content, 'fastly.jsdelivr.net') === false) {
        echo "<p style='color:green'>✅ CSS文件已成功修改,没有CDN引用</p>";
    } else {
        echo "<p style='color:red'>❌ CSS文件中仍存在CDN引用</p>";
    }
    
    if (strpos($content, '../fonts/') !== false) {
        echo "<p style='color:green'>✅ CSS文件已使用本地字体路径</p>";
    } else {
        echo "<p style='color:red'>❌ CSS文件中没有本地字体路径</p>";
    }
}
?>

第五步:清除缓存并测试

# 清除WordPress缓存(如果有)
cd /www/wwwroot/114.66.59.86
rm -rf wp-content/cache/*

# 重启Web服务器(可选)
systemctl restart apache2
# 或者
systemctl restart nginx

如果你运行了刚才的脚本,并且产生了如下的报错:

警告:file_get_contents():open_basedir限制生效。File(/wp-content/themes/argon/assets/vendor/font-awesome/css/font-awesome.css) 不在允许路径内:(/www/wwwroot/114.66.59.86/:/tmp/) 在 /www/wwwroot/114.66.59.86/verify-fonts.php 第6 行 警告:file_get_contents(/wp-content/themes/argon/assets/vendor/font-awesome/css/font-awesome.css):未能打开流:在线/www/wwwroot/114.66.59.86/verify-fonts.php作不被允许6

这个错误是因为 open_basedir 限制,导致无法使用相对路径直接读取文件。我们需要使用绝对路径,并且确保路径在允许的目录内,根据错误信息,允许的路径是:/www/wwwroot/114.66.59.86/ 和 /tmp/,所以,我们应该使用绝对路径来读取文件。修改验证脚本,使用绝对路径,并且确保路径正确。另外,注意错误中提到的文件路径是:/wp-content/themes/argon/assets/vendor/font-awesome/css/font-awesome.css
这实际上是一个相对路径,我们需要将其转换为绝对路径。已知网站根目录是: /www/wwwroot/114.66.59.86/所以,绝对路径应该是:/www/wwwroot/114.66.59.86/wp-content/themes/argon/assets/vendor/font-awesome/css/font-awesome.css

修复后的验证脚本

<?php
// verify-fonts-fixed.php - 修复版的本地字体文件验证
echo "<h2>本地字体文件验证(修复版)</h2>";

// 使用绝对路径
$base_path = '/www/wwwroot/114.66.59.86';
$css_file = $base_path . '/wp-content/themes/argon/argon/assets/vendor/font-awesome/css/font-awesome.css';

echo "<p>检查CSS文件: {$css_file}</p>";

if (file_exists($css_file)) {
    $css_content = file_get_contents($css_file);
    echo "<p style='color:green'>✅ CSS文件读取成功</p>";
    
    // 提取所有字体路径
    preg_match_all('/url\(\'([^\']+)\'\)/', $css_content, $matches);
    
    $found_fonts = 0;
    $missing_fonts = 0;
    
    foreach ($matches[1] as $font_path) {
        // 构建完整路径 - 基于CSS文件所在目录
        $font_dir = dirname($css_file); // CSS文件所在目录
        $relative_path = $font_path;
        
        // 处理 ../fonts/ 这样的相对路径
        if (strpos($relative_path, '../') === 0) {
            $full_font_path = dirname($font_dir) . '/' . substr($relative_path, 3);
        } else {
            $full_font_path = $font_dir . '/' . $relative_path;
        }
        
        // 清理查询参数
        $clean_path = preg_replace('/\?.*$/', '', $full_font_path);
        
        if (file_exists($clean_path)) {
            $size = round(filesize($clean_path) / 1024, 2);
            echo "<p style='color:green'>✅ {$font_path} - 存在 ({$size}KB)</p>";
            echo "<p style='font-size:12px; color:gray'>实际路径: {$clean_path}</p>";
            $found_fonts++;
        } else {
            echo "<p style='color:red'>❌ {$font_path} - 文件缺失</p>";
            echo "<p style='font-size:12px; color:gray'>查找路径: {$clean_path}</p>";
            $missing_fonts++;
        }
    }
    
    echo "<h3>统计结果:</h3>";
    echo "<p>找到字体文件: {$found_fonts} 个</p>";
    echo "<p>缺失字体文件: {$missing_fonts} 个</p>";
    
    if ($missing_fonts > 0) {
        echo "<h3>解决方案:</h3>";
        echo "<p>请手动检查字体文件是否存在于正确位置,或重新下载字体文件。</p>";
    }
    
} else {
    echo "<p style='color:red'>❌ CSS文件不存在: {$css_file}</p>";
}

// 额外检查:直接列出字体目录
echo "<h3>字体目录内容:</h3>";
$fonts_dir = $base_path . '/wp-content/themes/argon/argon/assets/vendor/font-awesome/fonts/';
if (is_dir($fonts_dir)) {
    $files = scandir($fonts_dir);
    foreach ($files as $file) {
        if ($file != '.' && $file != '..') {
            $file_path = $fonts_dir . $file;
            $size = round(filesize($file_path) / 1024, 2);
            echo "<p>{$file} - {$size}KB</p>";
        }
    }
} else {
    echo "<p style='color:red'>字体目录不存在: {$fonts_dir}</p>";
}
?>

替代方案:使用命令行验证

如果PHP脚本仍有问题,可以直接使用命令行验证:

# 进入字体目录
cd /www/wwwroot/114.66.59.86/wp-content/themes/agon/argon/assets/vendor/font-awesome/fonts/

# 检查文件是否存在
echo "=== 检查字体文件 ==="
ls -la *.woff2 *.woff *.ttf *.eot *.svg 2>/dev/null

echo "=== 文件大小 ==="
for file in *.woff2 *.woff *.ttf *.eot *.svg 2>/dev/null; do
    if [ -f "$file" ]; then
        size=$(du -h "$file" | cut -f1)
        echo "$file - $size"
    fi
done

echo "=== 检查CSS引用 ==="
cd ../css/
grep -n "url.*fontawesome-webfont" font-awesome.css

当你完成了上述的步骤之后,可能还会发现还会有一个比较占用较长的时间请求。ttps://fastly.jsdelivr.net/gh/huangwb8/bloghelper@latest/fonts/13.woff2 请求方法 GET 状态代码 200 OK 远程地址 127.0.0.1:7897 引用站点策略 strict-origin-when-cross-origin accept-ranges bytes access-control-allow-origin * access-control-expose-headers * age 37669 alt-svc h3=”:443″;ma=86400,h3-29=”:443″;ma=86400,h3-27=”:443″;ma=86400 cache-control public, max-age=604800, s-maxage=43200 content-length 3621316 content-type font/woff2 cross-origin-resource-policy cross-origin date Wed, 19 Nov 2025 16:05:00 GMT etag W/”3741c4-dVJ/KrCJs4wIM94sDq+X6lci2A4″ strict-transport-security max-age=31536000; includeSubDomains; preload timing-allow-origin * vary Accept-Encoding x-cache HIT, HIT x-content-type-options nosniff x-jsd-version 1.3.31 x-jsd-version-type version x-served-by cache-fra-eddf8230021-FRA, cache-hkg17927-HKG

注意到这个请求的远程地址是127.0.0.1:7897,这说明你的系统配置了代理(可能是科学上网工具)。这个代理可能导致了请求的延迟。分析一下响应头:

  • age: 37669(表示这个资源在CDN上已经缓存了37669秒,约10.5小时)
  • cache-control: public, max-age=604800, s-maxage=43200(缓存设置,最大年龄604800秒,共享缓存最大年龄43200秒)
    • max-age=604800 = 7天缓存
    • s-maxage=43200 = 12小时共享缓存
      对于不常变化的字体文件来说,这个缓存时间偏短。
  • content-length: 3621316(这个字体文件很大,约3.6MB),3.62 MB 的字体文件!这是导致加载慢的主要原因。正常的图标字体通常在 50-200KB 左右。
  • x-cache: HIT, HIT(表示命中了CDN缓存

可能的原因:

  1. 代理延迟:由于请求经过了本地代理(127.0.0.1:7897),代理服务器的处理速度可能较慢,或者代理服务器到CDN的网络连接不佳。
  2. 字体文件过大:3.6MB的字体文件在慢速网络下会需要较长时间下载。
  3. CDN节点问题:虽然命中了缓存,但是CDN节点到代理服务器之间的网络可能较慢。

定位调用来源

这个字体来自 huangwb8/bloghelper,可能是一个WordPress插件。让我们找到它:

# 在整个WordPress目录中搜索这个字体URL
cd /www/wwwroot/114.66.59.86
grep -r "huangwb8/bloghelper" . --include="*.php" --include="*.css" --include="*.js"

# 或者搜索13.woff2
grep -r "13.woff2" . --include="*.php" --include="*.css" --include="*.js"

创建诊断脚本

<?php
// diagnose-large-font.php
echo "<h2>大字体文件诊断</h2>";

$font_url = "https://fastly.jsdelivr.net/gh/huangwb8/bloghelper@latest/fonts/13.woff2";
$local_path = "/www/wwwroot/114.66.59.86/wp-content/fonts/13.woff2";

// 测试远程下载速度
$start = microtime(true);
$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, $font_url);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_setopt($ch, CURLOPT_FOLLOWLOCATION, true);
curl_setopt($ch, CURLOPT_TIMEOUT, 30);
$font_data = curl_exec($ch);
$download_time = microtime(true) - $start;
$file_size = strlen($font_data);

curl_close($ch);

echo "<p>远程字体下载: " . round($download_time, 2) . "秒</p>";
echo "<p>文件大小: " . round($file_size / 1024 / 1024, 2) . "MB</p>";

// 检查是否可以本地化
if (file_exists($local_path)) {
    $local_size = filesize($local_path);
    echo "<p style='color:green'>✅ 本地字体文件存在: " . round($local_size / 1024 / 1024, 2) . "MB</p>";
} else {
    echo "<p style='color:orange'>⚠️ 本地字体文件不存在,建议下载到本地</p>";
}

// 检查网络环境
echo "<h3>网络环境检查:</h3>";
echo "<p>是否有代理: " . (isset($_SERVER['HTTP_PROXY']) ? '是' : '否') . "</p>";

// 测试直接连接速度(绕过代理)
$test_urls = [
    'https://fastly.jsdelivr.net/gh/huangwb8/bloghelper@latest/fonts/13.woff2',
    'https://gcore.jsdelivr.net/gh/huangwb8/bloghelper@latest/fonts/13.woff2',
    'https://cdn.jsdelivr.net/gh/huangwb8/bloghelper@latest/fonts/13.woff2'
];

foreach ($test_urls as $test_url) {
    $start = microtime(true);
    $headers = get_headers($test_url, 1);
    $time = round((microtime(true) - $start) * 1000, 2);
    
    if ($headers && strpos($headers[0], '200') !== false) {
        echo "<p>✅ {$test_url} - 可访问 ({$time}ms)</p>";
    } else {
        echo "<p>❌ {$test_url} - 不可访问 ({$time}ms)</p>";
    }
}
?>

这个PHP代码并没有将下载的文件保存到本地。让我详细解释一下代码的执行流程:

  1. 下载文件到内存:$font_data = curl_exec($ch); // 文件内容存储在内存变量 $font_data 中
  2. 计算文件大小:$file_size = strlen($font_data); // 只是计算内存中数据的大小
  3. 脚本结束后:变量”$font_data” 被销毁,下载的内容就从内存中清除了

文件存储位置:

  • 不在硬盘上 – 没有使用”file_put_contents()” 或类似函数保存
  • 只在内存中 – 临时存储在变量中
  • 临时存在 – 脚本执行完毕后自动释放

如果想要保存文件,需要在 curl_exec 之后添加:

file_put_contents($local_path, $font_data);
echo "<p>文件已保存到: " . $local_path . "</p >";

创建脚本

<?php
// verify-css-path.php
echo "<h2>CSS路径修改验证</h2>";

$css_file = '/www/wwwroot/114.66.59.86/wp-content/themes/argon/assets/vendor/font-awesome/css/font-awesome.css';
$css_content = file_get_contents($css_file);

// 检查修改后的路径
if (strpos($css_content, '../../agron/assets/vendor/font-awesome/fonts/') !== false) {
    echo "<p style='color:green'>✅ CSS文件已成功修改</p>";
} else {
    echo "<p style='color:red'>❌ CSS文件修改失败</p>";
}

// 提取并测试所有字体路径
preg_match_all('/url\(\'([^\']+)\'\)/', $css_content, $matches);

echo "<h3>字体路径验证:</h3>";
foreach ($matches[1] as $font_path) {
    // 基于CSS文件位置构建完整路径
    $css_dir = '/www/wwwroot/114.66.59.86/wp-content/themes/argon/assets/vendor/font-awesome/css/';
    $full_path = dirname(dirname($css_dir)) . '/' . $font_path;
    $clean_path = preg_replace('/\?.*$/', '', $full_path);
    
    if (file_exists($clean_path)) {
        $size = round(filesize($clean_path) / 1024, 2);
        echo "<p style='color:green'>✅ {$font_path} - 文件存在 ({$size}KB)</p>";
    } else {
        echo "<p style='color:red'>❌ {$font_path} - 文件不存在</p>";
        echo "<p>查找路径: {$clean_path}</p>";
    }
}
?>

编码格式不对

在后面你进行了测试,经过我的脚本发现,那个路径下并没有这个文件,但是在后续查看的过程中,你发现你的服务器下是存在这个文件的,但是当你尝试去点击打开看的时候,它提示编码格式不对。编码格式不对的错误提示通常意味着文件损坏、文件格式错误或者服务器MIME类型配置问题。让咱们系统地解决这个问题。

1. 检查文件完整性和类型

创建文件诊断脚本:

<?php
// file-diagnose.php
echo "<h2>字体文件完整性诊断</h2>";

$font_files = [
    '/www/wwwroot/114.66.59.86/wp-content/themes/argon/agron/assets/vendor/font-awesome/fonts/fontawesome-webfont.woff2',
    '/www/wwwroot/114.66.59.86/wp-content/themes/argon/agron/assets/vendor/font-awesome/fonts/fontawesome-webfont.woff',
    '/www/wwwroot/114.66.59.86/wp-content/themes/argon/agron/assets/vendor/font-awesome/fonts/fontawesome-webfont.ttf',
    '/www/wwwroot/114.66.59.86/wp-content/themes/argon/agron/assets/vendor/font-awesome/fonts/fontawesome-webfont.eot',
    '/www/wwwroot/114.66.59.86/wp-content/themes/argon/agron/assets/vendor/font-awesome/fonts/fontawesome-webfont.svg'
];

foreach ($font_files as $file_path) {
    if (!file_exists($file_path)) {
        echo "<p style='color:red'>❌ 文件不存在: {$file_path}</p>";
        continue;
    }
    
    $size = filesize($file_path);
    $file_info = finfo_file(finfo_open(FILEINFO_MIME_TYPE), $file_path);
    
    echo "<h3>分析: " . basename($file_path) . "</h3>";
    echo "<p>文件大小: " . round($size / 1024, 2) . "KB</p>";
    echo "<p>MIME类型: {$file_info}</p>";
    
    // 检查文件头签名
    $handle = fopen($file_path, 'rb');
    $header = fread($handle, 8);
    fclose($handle);
    
    $hex_header = bin2hex($header);
    echo "<p>文件头: {$hex_header}</p>";
    
    // 验证文件类型
    $expected_types = [
        'woff2' => 'font/woff2',
        'woff' => 'font/woff',
        'ttf' => 'font/ttf',
        'eot' => 'application/vnd.ms-fontobject',
        'svg' => 'image/svg+xml'
    ];
    
    $ext = pathinfo($file_path, PATHINFO_EXTENSION);
    $expected_type = $expected_types[$ext] ?? 'unknown';
    
    if ($file_info === $expected_type) {
        echo "<p style='color:green'>✅ MIME类型正确</p>";
    } else {
        echo "<p style='color:orange'>⚠️ MIME类型可能不正确,期望: {$expected_type}</p>";
    }
    
    // 检查文件是否可读
    if (is_readable($file_path)) {
        echo "<p style='color:green'>✅ 文件可读</p>";
    } else {
        echo "<p style='color:red'>❌ 文件不可读</p>";
    }
}
?>

2. 重新下载字体文件

文件可能已损坏,让我们重新下载:

# 进入字体目录
cd /www/wwwroot/114.66.59.86/wp-content/themes/argon/agron/assets/vendor/font-awesome/fonts/

# 备份原文件(如果存在)
mkdir -p backup
cp * backup/ 2>/dev/null || true

# 从官方源重新下载Font Awesome 4.7.0字体文件
wget -O fontawesome-webfont.woff2 "https://cdnjs.cloudflare.com/ajax/libs/font-awesome/4.7.0/fonts/fontawesome-webfont.woff2?v=4.7.0"
wget -O fontawesome-webfont.woff "https://cdnjs.cloudflare.com/ajax/libs/font-awesome/4.7.0/fonts/fontawesome-webfont.woff?v=4.7.0"
wget -O fontawesome-webfont.ttf "https://cdnjs.cloudflare.com/ajax/libs/font-awesome/4.7.0/fonts/fontawesome-webfont.ttf?v=4.7.0"
wget -O fontawesome-webfont.eot "https://cdnjs.cloudflare.com/ajax/libs/font-awesome/4.7.0/fonts/fontawesome-webfont.eot?v=4.7.0"
wget -O fontawesome-webfont.svg "https://cdnjs.cloudflare.com/ajax/libs/font-awesome/4.7.0/fonts/fontawesome-webfont.svg?v=4.7.0"

# 验证下载的文件大小
echo "下载的文件大小:"
ls -la *.woff2 *.woff *.ttf *.eot *.svg

# 设置正确权限
chmod 644 *.woff2 *.woff *.ttf *.eot *.svg

3. 检查服务器MIME类型配置

“编码格式不对”可能是服务器没有正确配置字体文件的MIME类型:

检查Apache配置

# 检查Apache MIME类型
grep -r "font/woff2" /etc/apache2/ /etc/httpd/ 2>/dev/null

# 或者检查mime.types文件
grep -E "woff2|woff|ttf|eot|svg" /etc/mime.types

对于Nginx(在server配置中添加):

location ~* \.(woff2|woff|ttf|eot|svg)$ {
    types {
        font/woff2 woff2;
        font/woff woff;
        font/ttf ttf;
        application/vnd.ms-fontobject eot;
        image/svg+xml svg;
    }
    expires 1y;
    add_header Cache-Control "public, immutable";
}

5. 创建测试页面验证字体加载

<?php
// test-font-loading.php
echo "<h2>字体加载测试</h2>";

// 测试直接访问字体文件
$font_urls = [
    '/wp-content/themes/argon/agron/assets/vendor/font-awesome/fonts/fontawesome-webfont.woff2',
    '/wp-content/themes/argon/agron/assets/vendor/font-awesome/fonts/fontawesome-webfont.woff'
];

foreach ($font_urls as $font_url) {
    $full_url = 'http://' . $_SERVER['HTTP_HOST'] . $font_url;
    
    echo "<h3>测试: {$font_url}</h3>";
    
    // 使用cURL测试
    $ch = curl_init();
    curl_setopt($ch, CURLOPT_URL, $full_url);
    curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
    curl_setopt($ch, CURLOPT_HEADER, true);
    curl_setopt($ch, CURLOPT_NOBODY, false);
    curl_setopt($ch, CURLOPT_TIMEOUT, 10);
    
    $response = curl_exec($ch);
    $http_code = curl_getinfo($ch, CURLINFO_HTTP_CODE);
    $content_type = curl_getinfo($ch, CURLINFO_CONTENT_TYPE);
    
    echo "<p>HTTP状态码: {$http_code}</p>";
    echo "<p>Content-Type: {$content_type}</p>";
    
    if (strpos($response, 'Content-Type: font/woff2') !== false || 
        strpos($response, 'Content-Type: font/woff') !== false) {
        echo "<p style='color:green'>✅ MIME类型正确</p>";
    } else {
        echo "<p style='color:orange'>⚠️ MIME类型可能不正确</p>";
    }
    
    curl_close($ch);
}

// 测试CSS字体声明
echo "<h3>CSS字体声明测试</h3>";
echo "<style>
@font-face {
  font-family: 'TestFontAwesome';
  src: url('/wp-content/themes/argon/agron/assets/vendor/font-awesome/fonts/fontawesome-webfont.woff2?v=4.7.0') format('woff2'),
       url('/wp-content/themes/argon/agron/assets/vendor/font-awesome/fonts/fontawesome-webfont.woff?v=4.7.0') format('woff');
  font-weight: normal;
  font-style: normal;
}
.test-icon {
  font-family: 'TestFontAwesome';
  font-size: 24px;
}
</style>";

echo "<p class='test-icon'>如果这显示为一个图标,则字体加载成功</p>";
echo "<p>普通文本(对比用)</p>";
?>

6. 检查文件编码和BOM

有时候文件可能包含BOM头导致问题:

# 检查文件是否有BOM头
cd /www/wwwroot/114.66.59.86/wp-content/themes/argon/agron/assets/vendor/font-awesome/fonts/

for file in *.woff2 *.woff *.ttf *.eot *.svg; do
    if [ -f "$file" ]; then
        # 检查前几个字节
        hexdump -n 3 -C "$file" | head -1
    fi
done

# 如果是文本文件(如SVG),检查编码
file -i fontawesome-webfont.svg

CDN服务

如果本地字体文件持续有问题,可以暂时回退到CDN

@font-face {
  font-family: 'FontAwesome';
  src: url('https://cdnjs.cloudflare.com/ajax/libs/font-awesome/4.7.0/fonts/fontawesome-webfont.eot?v=4.7.0');
  src: url('https://cdnjs.cloudflare.com/ajax/libs/font-awesome/4.7.0/fonts/fontawesome-webfont.eot?#iefix&v=4.7.0') format('embedded-opentype'),
       url('https://cdnjs.cloudflare.com/ajax/libs/font-awesome/4.7.0/fonts/fontawesome-webfont.woff2?v=4.7.0') format('woff2'),
       url('https://cdnjs.cloudflare.com/ajax/libs/font-awesome/4.7.0/fonts/fontawesome-webfont.woff?v=4.7.0') format('woff'),
       url('https://cdnjs.cloudflare.com/ajax/libs/font-awesome/4.7.0/fonts/fontawesome-webfont.ttf?v=4.7.0') format('truetype'),
       url('https://cdnjs.cloudflare.com/ajax/libs/font-awesome/4.7.0/fonts/fontawesome-webfont.svg?v=4.7.0#fontawesomeregular') format('svg');
}

如果实在看不懂的话

WordPress数据库中的旧URL引用

在网站测试中,通过F12打开它的控制台,发现源代码里面多了一个不属于现在这个服务器里面的文件夹,而这个文件夹名字是你之前暴力移植过来的IP地址,由WordPress数据库中的旧URL引用 导致

当在源代码中看到不属于当前服务器的文件夹(特别是旧IP地址相关的路径),通常是由于:

问题原因分析

1. 数据库中的硬编码URL

WordPress在数据库中存储了大量绝对URL,包括:

  • 文章内容中的图片链接
  • 主题设置中的路径
  • 插件配置中的URL
  • 附件元数据

2. 序列化数据问题

WordPress使用序列化数组存储数据,直接替换会导致数据损坏。

3. 缓存残留

浏览器、服务器或CDN缓存了旧的内容。

第一步:识别具体问题

首先,让我们找出所有包含旧IP地址的数据库记录:

<?php
// find-old-urls.php - 查找数据库中的旧URL
echo "<h2>查找数据库中的旧URL引用</h2>";

require_once('wp-config.php');
global $wpdb;

// 搜索包含旧IP地址的记录
$old_ip = '114.66.59.86'; // 替换为您的旧IP
$tables = [
    $wpdb->posts,
    $wpdb->postmeta,
    $wpdb->options,
    $wpdb->comments,
    $wpdb->commentmeta
];

foreach ($tables as $table) {
    echo "<h3>检查表: {$table}</h3>";
    
    // 检查posts表的内容
    if ($table == $wpdb->posts) {
        $results = $wpdb->get_results($wpdb->prepare("
            SELECT ID, post_title, post_type 
            FROM {$table} 
            WHERE post_content LIKE %s 
            OR guid LIKE %s
        ", "%{$old_ip}%", "%{$old_ip}%"));
    } 
    // 检查其他表
    else {
        $results = $wpdb->get_results($wpdb->prepare("
            SELECT * FROM {$table} 
            WHERE option_value LIKE %s 
            OR meta_value LIKE %s
        ", "%{$old_ip}%", "%{$old_ip}%"));
    }
    
    if ($results) {
        foreach ($results as $row) {
            echo "<p>找到引用: ";
            if (isset($row->post_title)) {
                echo "文章 '{$row->post_title}' (ID: {$row->ID})";
            } elseif (isset($row->option_name)) {
                echo "选项 '{$row->option_name}'";
            }
            echo "</p>";
        }
    } else {
        echo "<p>未找到相关引用</p>";
    }
}
?>

第二步:安全地替换数据库中的URL

手动SQL替换(谨慎操作)

cd /www/wwwroot/114.66.59.86
wp search-replace 'http://114.66.59.86' 'http://www.preluna.xyz' --all-tables --dry-run
# 如果预览结果正确,去掉 --dry-run 执行实际替换
wp search-replace 'http://114.66.59.86' 'http://www.preluna.xyz' --all-tables

第三步:检查并修复序列化数据

序列化数据需要特殊处理,否则会损坏数据:

<?php
// fix-serialized-data.php - 修复序列化数据
echo "<h2>修复序列化数据中的URL</h2>";

require_once('wp-config.php');
global $wpdb;

// 主要检查选项表
$options = $wpdb->get_results("
    SELECT option_id, option_name, option_value 
    FROM {$wpdb->options} 
    WHERE option_value LIKE '%114.66.59.86%'
");

foreach ($options as $option) {
    echo "<p>处理选项: {$option->option_name}</p>";
    
    // 检查是否是序列化数据
    $value = $option->option_value;
    if (is_serialized($value)) {
        $unserialized = unserialize($value);
        
        // 递归替换
        array_walk_recursive($unserialized, function(&$item, $key) {
            if (is_string($item)) {
                $item = str_replace('http://114.66.59.86', 'http://www.preluna.xyz', $item);
            }
        });
        
        // 重新序列化并更新
        $new_value = serialize($unserialized);
        $wpdb->update(
            $wpdb->options,
            ['option_value' => $new_value],
            ['option_id' => $option->option_id]
        );
        
        echo "<p style='color:green'>✅ 已修复序列化数据</p>";
    } else {
        // 直接替换
        $new_value = str_replace('http://114.66.59.86', 'http://www.preluna.xyz', $value);
        $wpdb->update(
            $wpdb->options,
            ['option_value' => $new_value],
            ['option_id' => $option->option_id]
        );
        echo "<p style='color:green'>✅ 已修复普通数据</p>";
    }
}

// WordPress的序列化检查函数
function is_serialized($data) {
    if (!is_string($data)) return false;
    $data = trim($data);
    if ('N;' == $data) return true;
    if (!preg_match('/^([adObis]):/', $data, $badions)) return false;
    switch ($badions[1]) {
        case 'a':
        case 'O':
        case 's':
            if (preg_match("/^{$badions[1]}:[0-9]+:.*[;}]\$/s", $data)) return true;
            break;
        case 'b':
        case 'i':
        case 'd':
            if (preg_match("/^{$badions[1]}:[0-9.E-]+;\$/", $data)) return true;
            break;
    }
    return false;
}
?>

第四步:清理所有缓存

# 清除WordPress缓存
cd /www/wwwroot/114.66.59.86
rm -rf wp-content/cache/*

# 清除浏览器缓存
# 按 Ctrl+Shift+Delete (Windows) 或 Cmd+Shift+Delete (Mac)

# 重启Web服务器
systemctl restart apache2
# 或
systemctl restart nginx

# 清除OPcache(如果有)
systemctl restart php8.0-fpm
# 或找到php-fpm进程并重启

第五步:验证修复

创建验证脚本检查是否还有旧URL:

<?php
// verify-fix.php - 验证修复结果
echo "<h2>验证URL修复结果</h2>";

$home_url = get_home_url();
$site_url = get_site_url();

echo "<p>当前主页URL: {$home_url}</p>";
echo "<p>当前站点URL: {$site_url}</p>";

// 检查是否有旧IP的残留
$check_urls = [
    get_home_url(),
    get_site_url(),
    get_template_directory_uri(),
    get_stylesheet_directory_uri()
];

foreach ($check_urls as $url) {
    if (strpos($url, '114.66.59.86') !== false) {
        echo "<p style='color:red'>❌ 发现旧IP: {$url}</p>";
    } else {
        echo "<p style='color:green'>✅ URL正常: {$url}</p>";
    }
}

// 检查数据库中的关键选项
global $wpdb;
$critical_options = [
    'home',
    'siteurl',
    'upload_url_path',
    'fileupload_url'
];

foreach ($critical_options as $option) {
    $value = get_option($option);
    if ($value && strpos($value, '114.66.59.86') !== false) {
        echo "<p style='color:red'>❌ 选项 {$option} 包含旧IP: {$value}</p>";
    } else {
        echo "<p style='color:green'>✅ 选项 {$option} 正常</p>";
    }
}
?>

WordPress网站迁移与性能优化完整解决方案总结

在WordPress网站迁移和优化过程中,我们遇到并解决了以下核心问题:

  1. 重定向循环 – 网站无限重定向到自身
    • WordPress设置与服务器配置冲突
    • 数据库中的URL设置与当前域名不匹配
    • 插件或主题中的强制重定向代码
  2. 资源加载缓慢 – 字体和静态文件加载时间过长
    • 字体文件从外部CDN加载,网络延迟高
    • 本地文件路径配置错误
    • 文件权限或MIME类型配置问题
  3. 路径配置错误 – CSS引用与实际文件路径不匹配
    • 字体文件从外部CDN加载,网络延迟高
    • 本地文件路径配置错误
    • 文件权限或MIME类型配置问题
  4. 数据库残留URL – 旧服务器IP地址在源代码中残留
    • 文章内容中的硬编码URL
    • 主题选项中的绝对路径
    • 序列化数据中的旧域名
  5. CDN配置需求 –
文末附加内容
暂无评论

发送评论 编辑评论


				
|´・ω・)ノ
ヾ(≧∇≦*)ゝ
(☆ω☆)
(╯‵□′)╯︵┴─┴
 ̄﹃ ̄
(/ω\)
∠( ᐛ 」∠)_
(๑•̀ㅁ•́ฅ)
→_→
୧(๑•̀⌄•́๑)૭
٩(ˊᗜˋ*)و
(ノ°ο°)ノ
(´இ皿இ`)
⌇●﹏●⌇
(ฅ´ω`ฅ)
(╯°A°)╯︵○○○
φ( ̄∇ ̄o)
ヾ(´・ ・`。)ノ"
( ง ᵒ̌皿ᵒ̌)ง⁼³₌₃
(ó﹏ò。)
Σ(っ °Д °;)っ
( ,,´・ω・)ノ"(´っω・`。)
╮(╯▽╰)╭
o(*////▽////*)q
>﹏<
( ๑´•ω•) "(ㆆᴗㆆ)
😂
😀
😅
😊
🙂
🙃
😌
😍
😘
😜
😝
😏
😒
🙄
😳
😡
😔
😫
😱
😭
💩
👻
🙌
🖕
👍
👫
👬
👭
🌚
🌝
🙈
💊
😶
🙏
🍦
🍉
😣
Source: github.com/k4yt3x/flowerhd
颜文字
Emoji
小恐龙
花!
上一篇
下一篇