ThinkPHP 5.0 伪静态生效需框架路由开启、URL模式配置正确、服务器重写规则匹配三者协同;Apache下.htaccess必须置于public目录,标准规则为RewriteRule ^(.*)$ index.php/$1 [QSA,PT,L],确保PATH_INFO正常解析。

ThinkPHP 5.0 伪静态要生效,必须同时满足三件事:框架路由开启、URL 模式配置正确、Web 服务器重写规则匹配请求路径。缺一不可,光改 route.php 或只配 .htaccess 都会失败。
Apache 下 .htaccess 规则怎么写才不 404
绝大多数 404 是因为 RewriteRule 没把请求真正交给 index.php 处理,或 PATH_INFO 解析失败。
- 确保
mod_rewrite已启用(Linux 下执行sudo a2enmod rewrite,Windows 检查httpd.conf中LoadModule rewrite_module modules/mod_rewrite.so是否取消注释) -
.htaccess必须放在public/目录(即index.php所在目录),不是项目根目录 - 标准可用规则(兼容大多数 TP5.0 版本):
<IfModule mod_rewrite.c>
Options +FollowSymlinks -Multiviews
RewriteEngine On
RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{REQUEST_FILENAME} !-f
RewriteRule ^(.*)$ index.php/$1 [QSA,PT,L]
</IfModule>
注意:index.php/$1 是关键,不是 index.php?s=$1 —— 后者是兼容模式,TP5.0 默认走 PATH_INFO,用 /$1 才能触发框架的路由解析;如果部署在子目录(如 /blog/),必须加 RewriteBase /blog/
Nginx 的 try_files 规则为什么比 if 更可靠
Nginx 官方明确不推荐在 location 块里用 if 判断文件是否存在,容易因执行顺序导致跳过 PHP 处理,返回 404 或直接下载 index.php 源码。
立即学习“PHP免费学习笔记(深入)”;
- 正确做法:用
try_files逐级 fallback,最后兜底到/index.php?s=兼容入口 - 在
server块的location /内写:
location / {
try_files $uri $uri/ /index.php?s=$uri&$args;
}
这个写法不依赖 PATH_INFO,对老版本 Nginx(如 1.8)也稳定;若你确认 Nginx ≥1.10 且启用了 fastcgi_split_path_info,也可用更干净的 fastcgi_param PATH_INFO $fastcgi_path_info 方式,但绝大多数 TP5.0 部署场景下,/index.php?s= 最省心。
url_html_suffix 和路由规则怎么配合才不冲突
后缀只是“伪装”,不是真实文件扩展名,它和服务器重写规则是两层逻辑:后缀由框架解析,重写由 Web 服务器完成。
- 在
config/app.php中设置:'url_html_suffix' => 'html|shtml|xml',支持多个后缀用|分隔 - 对应路由规则(
route/route.php)要显式包含后缀,例如:Route::rule('article/:id', 'index/article/read')->ext('html'); - 如果不设
->ext(),框架会尝试匹配所有允许的后缀,但一旦 URL 中带了.html,而路由没声明支持,就会 404 —— 这是新手最常踩的坑 - 想彻底去掉后缀?设
'url_html_suffix' => ''即可,此时http://site.com/index/index和http://site.com/index/index.html都能访问,但后者不会被当作参数值处理
为什么本地开发正常,上线就 404
根本原因通常是服务器环境差异被忽略:
- Apache:检查虚拟主机配置中
AllowOverride是否为FileInfo Options,设成All或None都会失效 - Nginx:确认
location ~ \.php$块里fastcgi_param SCRIPT_FILENAME指向的是$document_root$fastcgi_script_name,而不是硬编码路径 - TP5.0 自带的
public/.htaccess文件权限是否为 644?有些共享主机禁止读取隐藏文件,需改名或换用web.config - 最隐蔽的一点:某些 Linux 发行版(如 CentOS)默认 SELinux 开启,会拦截 Apache 读取
.htaccess,临时关闭验证:setenforce 0
伪静态不是开关一开就完事,它是框架、配置、服务器三方咬合的结果;PATH_INFO 解析失败、Rewrite 条件漏判、后缀未注册进路由——任何一个环节松动,URL 就断在半路。



















