资讯动态

WordPress换域名后永久链接404的完整修复指南:从数据库替换到伪静态配置

发布时间:2026/9/20 9:19:31 来源:尧图企业网站定制
接手过很多次“站点换域名”的活儿每次最头疼的不是换域名本身而是换完以后整站文章页、分类页集体404。首页明明能打开后台有时候能进有时候进不去进去了发文章、改固定链接又提示一堆错。这篇文章就把我处理这类问题的完整思路写出来从永久链接失效的根源到数据库替换、序列化数据避坑、Web服务器配置、最终清理缓存和旧域名跳转一次讲透。1. 换域名后永久链接失效先定位坏在哪一层1.1 问题现象不是所有页面都打不开很多朋友遇到的情况是换完域名新域名能打开首页但点进任何一篇文章或者分类页直接给出404。更迷惑的是有时候后台能登录有时候登录后又被弹回去或者页面CSS样式全丢图片全部不显示。这些现象背后的原因其实各不相同首页能打开文章页404说明Web服务器运行正常WordPress程序文件也没问题但 URL 重写规则没有正确工作。要么是.htaccessApache环境里的规则不对要么是 Nginx 的try_files配置缺失要么是固定链接规则根本没生效。后台登录后反复跳回登录页这通常是siteurl和home这两个选项不一致或者数据库里存的还是旧域名导致 WordPress 生成的 Cookie 作用域、重定向地址全部基于旧域名。图片、样式全丢页面HTML能加载但里面所有静态资源的URL还是旧域名这100%是数据库里存的是旧地址浏览器去请求旧域名当然全部失败。1.2 永久的根因WordPress的URL都来自数据库不是自动识别的很多人误以为“我把域名解析到服务器WordPress就会自动用新域名生成链接”这是最大的误区。WordPress 里所有链接的生成都依赖于两个选项siteurl和home它们存放在wp_options表中。你后台上传图片、发文章、生成文章链接时WordPress 会拿这两个值去拼绝对地址。我把站点迁移理解为三层结构排查时必须按层走不能一上来就乱改数据库层存着siteurl、home、文章内容里的旧域名、插件选项里的旧域名。配置文件层wp-config.php、.htaccess或 Nginx 配置决定请求如何被转发到index.php。服务器层域名解析、SSL证书、Web服务器监听指向。永久链接固定链接失效本质上是第三层没接到第一层。.htaccess里的规则原本是“把所有请求转发给index.php”如果路径有问题请求根本没到 WordPress 手里自然无法根据文章的 URL 别名slug去数据库里匹配文章。1.3 和“固定链接”设置有什么关系WordPress 后台“设置 → 固定链接”里选择的那种结构比如/archives/%post_id%.html或/%postname%/只是告诉 WordPress“用这种格式造URL”。它会不会生效还要看 PHP 进程是否具备写.htaccess的权限。换域名后如果你没去后台保存过固定链接WordPress 的重写规则还是旧的。而且很多人换了域名以后根本进不去后台规则就一直没刷新于是404一直持续。所以解决思路应该是先把数据库里的旧域名统一改成新域名再确保 Web 服务器规则正确最后进后台手动保存一次固定链接让规则重新生成。2. 动手之前备份、表结构和“序列化数据”的坑2.1 先备份再动刀这不是废话我见过不少人在 phpMyAdmin 里直接执行“替换域名”的SQL结果整站数据库损坏最后只能恢复备份。如果你不想在凌晨翻车开工前一定要做两件事用主机面板的数据库备份功能或者命令mysqldump -u用户名 -p 数据库名 backup.sql导出一份完整数据库。把整个wp-content目录打包下载。主题、插件丢了可以重下但uploads目录里的图片、附件丢了基本找不回。这里多说一句备份出来的 SQL 文件建议先下载到本地不要只在服务器上存一份。因为某些“批量替换”操作会把数据改得半死不活你需要在本地留一份完好的原始文件随时恢复。2.2 wp_options 和永久链接相关的关键行wp_options表里和永久链接、站点域名直接相关的选项主要有这几个option_name作用siteurlWordPress 程序文件所在的完整地址后台登录、接口请求都依赖它home站点对外访问的完整地址文章链接、前端页面URL都基于它permalink_structure固定链接结构如/%postname%/rewrite_rules已经生成的重写规则缓存保存固定链接设置时重新生成手动处理时很多人只改了前两个以为就完事了。实际上文章内容、自定义菜单、小工具、插件配置里可能存着大量旧地址这些同样会造成图片失效、跳转异常等问题。2.3 序列化数据的坑为什么直接写SQL替换会白屏这是换域名时最容易踩的雷。WordPress 里的很多字段特别是wp_options里的小工具配置、主题选项以及wp_postmeta里的页面构建器数据都是用 PHP 的serialize()函数序列化后存储的。序列化字符串长这样a:2:{s:8:siteurl;s:22:https://old-domain.com/;}其中s:22表示后面字符串的长度是22个字符。如果你用一行简单的 SQL 去做全局替换UPDATE wp_options SET option_value REPLACE(option_value, https://old-domain.com, https://new-domain.com);假设旧域名是https://old-domain.com20个字符新域名是https://new-domain-long.com26个字符替换完之后字符串里的s:20还是原来的数字但实际内容已经变成26个字符。PHP 反序列化的时候发现长度对不上直接返回falseWordPress 加载这个选项就会报错严重时整站白屏。所以这里必须明确一件事只要涉及批量替换URL优先使用带反序列化处理能力的工具而不是 phpMyAdmin 里裸奔 SQL。2.4 什么工具能安全处理序列化数据我个人常用的方案有三种按推荐程度排序WP-CLI命令行wp search-replace命令会自动处理序列化数据还支持--precise精确匹配速度非常快。Better Search Replace 插件后台可视化操作不需要命令行权限执行前还能开 Dry Run 预览适合新手。自己写 PHP 脚本调用 WordPress 的$wpdb遍历表对每个字段尝试unserialize()再serialize()但脚本必须处理好各种边界情况工作量较大。如果是几十篇文章的小站用插件就够了。如果是日更的大型站点或者数据库里有几十万条记录建议直接用 WP-CLI。我一般会在替换前先跑一遍--dry-run看清楚会替换多少处再真正执行。3. 正确更新数据库从 URL 替换到固定链接刷新3.1 用 WP-CLI 完成核心替换推荐如果你的服务器能通过 SSH 访问这是最高效的方式。进入 WordPress 根目录后wp search-replace https://old-domain.com https://new-domain.com --all-tables --precise --recurse-objects --dry-run参数说明--all-tables处理数据库中所有表而不是只处理 WordPress 核心表。--precise要求精确匹配避免old-domain.com.evil.com这种模糊值被误替换。--recurse-objects递归处理序列化数组和对象内部的值解决前面提到的序列化长度问题。--dry-run只统计会替换多少处不实际修改。确认结果符合预期后去掉--dry-run再执行一遍wp search-replace https://old-domain.com https://new-domain.com --all-tables --precise --recurse-objects这条命令会把wp_options、wp_posts、wp_postmeta、wp_comments等所有表里的旧域名统一替换掉同时调整序列化字符串里的长度数字不会再出现白屏问题。执行完之后再确认一下站点地址和首页地址wp option get siteurl wp option get home如果还是旧域名手动更新wp option update siteurl https://new-domain.com wp option update home https://new-domain.com3.2 用 Better Search Replace 插件适合虚拟主机没有 SSH 权限时可以在旧域名还打得开后台的情况下先安装一个 Better Search Replace 插件或者把旧站点做成维护模式通过插件临时访问然后按以下步骤操作后台进入“工具 → Better Search Replace”。“Search for”填旧域名如https://old-domain.com。“Replace with”填新域名如https://new-domain.com。选择所有数据表。勾选“Dry run”先跑一次查看需要替换的数量。确认无误后取消勾选“Dry run”执行替换。这个插件的核心逻辑就是安全处理序列化数据它会先尝试反序列化再进行字符串替换并重新序列化。整个过程比手写SQL稳得多。3.3 文章内容和上传文件里残留的旧URLwp search-replace已经覆盖了wp_posts.post_content和wp_postmeta所以文章正文里的链接、媒体库附件路径都会一起被替换。不过有一个细节经常被忽略旧的文章缩略图、特色图片的_wp_attached_file元数据以及图集里引用的附件ID通常也都被替换干净了但如果当初是通过外部URL插入的图片那就不会被处理。这时候需要去“媒体库”里重新上传或修改链接。另外如果你用了 Elementor、WPBakery 这类页面构建器它们很多配置会存成 JSON 或序列化数据也会被 WP-CLI 的--recurse-objects一并处理。我遇到过一次 Elementor CSS 文件迟迟不更新的情况是因为 Elementor 在wp-content/uploads/elementor/css下生成了带哈希的 CSS 文件但页面引用的还是新域名下的旧哈希路径。做完数据库替换后去“Elementor → 工具 → Regenerate CSS”点一次重建就好。3.4 刷新永久链接规则数据库替换完成后需要让 WordPress 重新生成重写规则。这一步可以在后台操作也可以用命令行后台方式登录后进入“设置 → 固定链接”不修改任何选项直接点“保存更改”。这会让 WordPress 调用flush_rewrite_rules()重新生成规则并尝试写入.htaccess。命令行方式wp rewrite flush --hard之所以要保存固定链接是因为rewrite_rules这个选项里缓存了旧域名生成的重写规则。如果不刷新即使数据库里其他值都改好了部分配置了缓存的站点依然会404。4. 服务器这一层.htaccess 与 Nginx 规则不能漏4.1 Apache 环境的 .htaccess 默认规则如果网站运行在 Apache 下WordPress 根目录的.htaccess里至少要有下面这段# BEGIN WordPress IfModule mod_rewrite.c RewriteEngine On RewriteBase / RewriteRule ^index\.php$ - [L] RewriteCond %{REQUEST_FILENAME} !-f RewriteCond %{REQUEST_FILENAME} !-d RewriteRule . /index.php [L] /IfModule # END WordPress这段规则的意思是如果一个请求对应的文件或目录在磁盘上不存在就把它统一交给根目录下的index.php去处理。WordPress 拿到这个请求后再按照你的固定链接结构去匹配具体的文章、分类、标签页。如果你更换域名时还把网站从一个子目录搬到了根目录比如原来在https://old.com/blog/下现在要放到https://new.com那.htaccess里的RewriteBase /必须跟着调整。否者请求会被错误地转发到/blog/index.php而那个目录其实已经不存在了404自然就来了。换完域名后如果.htaccess被系统重建过但权限没给够WordPress 无法自动写入文件固定链接也会失效。遇到这种情况手动把上面那段规则放进去并确认文件可写即可。4.2 Nginx 环境的伪静态配置Nginx 下没有.htaccess所有规则写在站点配置里。核心是location块里的try_filesserver { listen 80; server_name new-domain.com www.new-domain.com; root /var/www/wordpress; index index.php index.html; location / { try_files $uri $uri/ /index.php?$query_string; } location ~ \.php$ { include snippets/fastcgi-php.conf; fastcgi_pass unix:/var/run/php/php8.1-fpm.sock; } }try_files $uri $uri/ /index.php?$query_string;是 Nginx 实现 WordPress 伪静态的关键。它的意思是先尝试用当前请求路径找真实文件找不到就找目录再找不到就把请求转给index.php并把原来的查询字符串带上。很多人在 Nginx 下换完域名后404检查点通常就这么几个新域名的 server 块是否真的存在且server_name写的是新域名。root指向的目录有没有放 WordPress 文件。PHP 的fastcgi_pass路径是否和当前 PHP 版本匹配。配置改动后有没有执行nginx -t检查语法并systemctl reload nginx重载。4.3 旧域名做301跳转别让权重和流量流失换新域名旧域名不要直接废弃。正确的做法是把旧域名所有请求301到新域名对应路径既能保住搜索引擎积累的权重也能让老访客通过旧链接自动落到新站。Apache 环境可以在旧域名站点根目录的.htaccess最前面放IfModule mod_rewrite.c RewriteEngine On RewriteCond %{HTTP_HOST} ^old-domain\.com$ [NC,OR] RewriteCond %{HTTP_HOST} ^www\.old-domain\.com$ [NC] RewriteRule ^(.*)$ https://new-domain.com/$1 [R301,L] /IfModuleNginx 环境给旧域名单独建一个 server 块server { listen 80; server_name old-domain.com www.old-domain.com; return 301 https://new-domain.com$request_uri; } server { listen 443 ssl; server_name old-domain.com www.old-domain.com; # 这里配置旧域名的 SSL 证书如果没有证书可以只做 80 跳转 return 301 https://new-domain.com$request_uri; }很多人忽略了一点旧域名如果启用了HTTPS但没有为旧域名续期SSL证书https://old-domain.com会直接证书报错根本到不了跳转逻辑。所以稳妥的做法是如果旧域名没有证书只保留80端口跳转如果有证书再配置443跳转。4.4 域名解析和CDN回源的问题更换域名后首先要确认新域名已经解析到服务器IP解析生效后再去动搜索引擎收录的事。如果你还用了CDN比如Cloudflare记得把新域名添加到CDN并更新回源地址否则用户访问新域名时CDN回源到旧域名会出现无限跳转或证书不匹配。CDN域名之间还有一层冷门坑如果原先图片是由CDN域名提供的比如cdn.old-domain.com数据库替换时如果直接用old-domain.com→new-domain.com会把cdn.old-domain.com也变成cdn.new-domain.com。如果你的CDN已经配置了对应的新域名CNAME那没问题如果没有所有图片都会404。处理这种场景我建议数据库里只替换主站域名CDN访问地址的切换放到CDN管理后台去做不要把CDN域名一起SQL替换掉。5. 换完域名后常见的“玄学”问题排查5.1 后台登录一直循环进不去怎么办换完域名后最抓狂的就是后台根本进不去。你输入新域名/wp-admin页面跳转到https://new-domain.com/wp-login.php登录后又被弹回wp-login.php?redirect_to...始终进不去。这通常有几个原因siteurl和home没有改干净或者一个改了另一个没改。解决方法是先确保这两个值都是新域名并清理浏览器Cookie和站点缓存。服务器或CDN层有强制HTTPS跳转但新域名的SSL证书还没生效。访问时页面一直在HTTP和HTTPS之间来回跳。先确认浏览器地址栏的小锁是否正常。插件缓存了旧的重定向规则。到wp-content/plugins里暂时把缓存类插件WP Rocket、W3 Total Cache 等改名禁用登录成功后再启用。反向代理配置问题比如 Cloudflare 的 SSL 模式是“灵活”但源站没有部署证书导致无限跳转。这时候把 Cloudflare SSL 改成“完全”或“完全严格”并确保源站也有证书。如果确实进不去后台最快的救急方式是在wp-config.php里加两行强制覆盖define(WP_HOME, https://new-domain.com); define(WP_SITEURL, https://new-domain.com);加在/* Thats all, stop editing! Happy blogging. */这一行之前。这会强制 WordPress 使用新地址数据库里的值暂时被忽略。登录后台后再去“设置 → 常规”里确认地址正确然后可以把这两行删掉或者保留作为固定配置实际很多人选择保留。5.2 页面能打开但图片不显示页面HTML正常但图片全是裂图打开新标签页访问图片URL又跳回旧域名或者404。这种情况基本可以断定媒体库中的URL没有替换干净或者浏览器/CDN缓存了旧资源。处理方式确认数据库里的_wp_attached_file、_wp_attachment_metadata中的路径没有旧域名残留。用 Better Search Replace 或 WP-CLI 再全库搜一次。如果图片上传用的是相对路径/wp-content/uploads/...那一般不受域名影响如果存的是绝对路径https://old-domain.com/wp-content/uploads/...就必须要替换。检查是否有对象缓存、页面缓存插件。比如 WP Rocket 的预生成缓存文件里还写着旧URL需要在设置里清空缓存并重新预加载。如果有CDN还要去CDN控制台“刷新缓存”或“提交URL刷新”。替换完成以后还可以在后台“媒体库”里看图片是否正常显示预览。如果还是不显示用浏览器的开发者工具F12查看具体资源的请求地址是旧域名还是新域名能直接判断是缓存问题还是数据库没改干净。5.3 HTTPS 换域名后混合内容如果旧站本来就是HTTPS通常问题不大。如果旧站是HTTP新域名部署了HTTPS就要小心“混合内容”问题页面主体通过HTTPS加载资源却还是HTTP地址浏览器会默认阻止部分HTTP请求。解决方案是在数据库替换时直接把URL从http://old-domain.com替换成https://new-domain.com一步到位。如果已经换完了才发现历史数据里还有HTTP就再跑一遍wp search-replace http://new-domain.com https://new-domain.com --all-tables --precise --recurse-objects --dry-run确认替换数量合理后去掉--dry-run执行。注意如果数据库里已经存在https://new-domain.com这样的新地址这步替换不会动它们因为搜索的是http://而不是https://。另外也要检查主题、插件里有写死HTTP资源的情况比如某些主题的Customizer里保存了Google Fonts地址。5.4 文章里旧链接全部要跳转有更细的规则吗如果旧站仍然在线数据库替换后文章里的链接已经变成新域名所以文章内的旧跳转需求通常已经不存在。但如果是“新域名刚启用、旧域名还得继续跑一段时间”的过渡期比如还在等用户更新收藏夹那么除了旧域名301之外还可以对某个特定的旧文章路径做跳转例如旧地址https://old.domain.com/?p123应该跳到新地址对应的文章。WordPress 原生就支持?p123这种查询只要你配置了“文章ID”样式的固定链接结构旧查询就能自动匹配到新文章。这个原理适用于新旧固定链接结构一致的情况。如果旧站用的是/index.php/2024/10/hello-world/这种路径新站用的是/%postname%/数据库替换后页面URL已经变化旧站301跳转也只能跳到新站首页具体到每篇文章的跳转映射关系就要额外写重定向规则了。这种情况建议旧站先不要直接停把文章逐一迁移后再通过爬虫数据或日志统计去做定向跳转。6. 迁移操作清单我每次换域名都按这个顺序来最后整理一份我自己的标准操作顺序按这个顺序来翻车概率会低很多。强烈建议把它保存成自己的迁移SOP备份数据库和wp-content目录下载到本地。新域名完成DNS解析确认解析生效ping new-domain.com或使用在线工具。在新域名对应的服务器目录放好 WordPress 文件导入数据库。修改wp-config.php里的数据库连接信息如果数据库名、用户名变了。用 WP-CLI 或 Better Search Replace 做一次全库 URL 替换先 Dry Run 再执行。确认siteurl和home已经是新域名。检查.htaccess或 Nginx 伪静态规则需要的话在wp-config.php里临时加上WP_HOME和WP_SITEURL强制覆盖。访问新域名首页看是否正常能进后台的话去“设置 → 固定链接”保存一次。检查文章页、分类页、标签页、搜索结果页是否能正常打开。检查媒体库图片是否显示必要时在 Elementor 或主题设置里重建CSS缓存。清空所有缓存WordPress缓存插件、CDN缓存、浏览器缓存。旧域名配置301跳转到新域名。在百度站长平台、谷歌Search Console提交新域名和站点地图必要时做改版工具里的“站点换地址”操作。我在实际操作中还总结了几条额外经验数据库替换前先把全站首页的HTML源码保存一份。替换后对比源码里的URL哪里没改一目了然。如果wp search-replace替换后出现了页面风格全丢的问题先别慌去后台点一下“保存固定链接”再把主题缓存插件清掉八成能恢复。这是最容易忽略的一步。多站点网络Multisite换域名除了siteurl和home还要修改wp_blogs表里的domain字段、wp_site表里的domain字段同时更新wp-config.php里的DOMAIN_CURRENT_SITE。每张子站的表里也可能存着旧的子站路径。这块比单站点麻烦很多建议单独规划迁移窗口。换域名这事看着是个小操作实际牵涉数据库、重写规则、缓存、CDN、SSL好几个层面。只要把数据库里的绝对地址处理干净服务器伪静态规则没问题再让固定链接重新生成一次大部分问题都能迎刃而解。希望这份清单能帮你少折腾几个小时。

读完文章,也想定制专属网站?

尧图设计师 24 小时内与您沟通定制方案

免费获取报价