推荐方法 - 通过 app.php 配置文件(最简单)

这是 ThinkPHP 官方推荐且最简单的方法,通过在应用的全局配置文件中指定 404 页面的路径即可。

thinkphp 404页面模板
(图片来源网络,侵删)

适用场景

  • 当你的 404 页面是一个静态的 HTML 文件时,这是最佳选择。
  • 当你希望所有类型的 404 错误(如控制器不存在、方法不存在、路由不存在)都指向同一个页面时。

操作步骤

  1. 创建 404 模板文件 在你的项目 public 目录下(或其他 Web 服务器可访问的目录),创建一个 HTML 文件作为你的 404 页面。

    public 目录下创建 html 文件:

    <!-- 文件路径: /public/404.html -->
    <!DOCTYPE html>
    <html lang="zh-CN">
    <head>
        <meta charset="UTF-8">
        <meta name="viewport" content="width=device-width, initial-scale=1.0">
        <title>404 - 页面未找到</title>
        <style>
            body { font-family: 'Arial', sans-serif; background-color: #f4f4f4; color: #333; text-align: center; padding-top: 50px; }
            .container { max-width: 600px; margin: 0 auto; background: #fff; padding: 30px; border-radius: 8px; box-shadow: 0 0 10px rgba(0,0,0,0.1); }
            h1 { color: #e74c3c; }
            p { font-size: 18px; line-height: 1.6; }
            a { color: #3498db; text-decoration: none; font-weight: bold; }
            a:hover { text-decoration: underline; }
        </style>
    </head>
    <body>
        <div class="container">
            <h1>哎呀!404 了</h1>
            <p>抱歉,您访问的页面不存在或已被移除。</p>
            <p>请检查您输入的网址是否正确,或者 <a href="/">点击这里返回首页</a>。</p>
        </div>
    </body>
    </html>
  2. 修改应用配置文件 打开你的应用配置文件 app.php,它通常位于 app/应用名/config/app.php 路径下。

    在该文件中,找到 http_exception_template 配置项,并将其值设置为你刚刚创建的 404 模板的路径。

    thinkphp 404页面模板
    (图片来源网络,侵删)
    // 文件路径: app/应用名/config/app.php
    return [
        // ... 其他配置项 ...
        // 将这个配置项修改为你的 404 模板路径
        'http_exception_template' => [
            // 404 错误对应的模板
            404 => app()->getRootPath() . 'public/404.html',
            // 你也可以自定义其他状态码的模板
            // 500 => app()->getRootPath() . 'public/500.html',
            // 403 => app()->getRootPath() . 'public/403.html',
        ],
        // ... 其他配置项 ...
    ];

    说明:

    • app()->getRootPath() 会获取到项目的根目录(即 public 目录的上一级),所以拼接 public/404.html 就能准确定位到文件。
    • 这个配置项是一个数组,你可以为不同的 HTTP 状态码(如 403, 500)指定不同的模板。
  3. 测试 重启你的 PHP 服务器(如果需要),然后访问一个不存在的 URL(http://你的域名/一个不存在的页面),你就会看到自定义的 404 页面了。


备用方法 - 通过路由捕获

这种方法更灵活,可以让你在控制器中处理 404 逻辑,例如记录日志、动态渲染模板等。

适用场景

  • 当你的 404 页面需要动态数据时(从数据库获取内容)。
  • 当你需要在 404 页面中执行一些额外的逻辑(如记录错误日志)。
  • 当你想区分不同原因导致的 404(如路由不存在 vs 控制器不存在)。

操作步骤

  1. 在路由文件中定义 404 路由 在你的 app/应用名/route/ 目录下,打开 app.php(或根据你的 route.php 配置)路由文件,添加一个通配符路由来捕获所有未匹配的请求。

    thinkphp 404页面模板
    (图片来源网络,侵删)
    // 文件路径: app/应用名/route/app.php
    use think\facade\Route;
    // ... 其他路由定义 ...
    // 定义一个 404 页面路由
    // '*' 会匹配所有未定义的路由
    Route::any('*', 'Error/notFound');
  2. 创建错误控制器 创建一个名为 Error 的控制器,并编写 notFound 方法来处理 404 逻辑。

    // 文件路径: app/应用名/controller/Error.php
    <?php
    declare (strict_types = 1);
    namespace app\controller;
    use think\Request;
    use think\Response;
    use think\facade\View;
    class Error
    {
        /**
         * 处理 404 错误
         * @param Request $request
         * @return Response
         */
        public function notFound(Request $request): Response
        {
            // 1. 记录日志(可选)
            // trace('404 Not Found: ' . $request->url(), 'error');
            // 2. 渲染模板
            // 可以直接返回一个字符串,或者使用视图引擎
            // 方法 A: 直接返回字符串
            // return response('<h1>页面不存在</h1><p>请检查您的URL。</p>', 404);
            // 方法 B: 使用视图引擎渲染模板(推荐)
            // 假设你的模板在 view/error/404.html
            View::assign([
                'message' => '您访问的页面不存在哦!',
                'url'    => $request->url(),
            ]);
            return response(View::fetch('error/404'), 404);
        }
    }
  3. 创建视图模板app/应用名/view/ 目录下创建 error 目录,并在其中创建 html 文件。

    <!-- 文件路径: app/应用名/view/error/404.html -->
    <!DOCTYPE html>
    <html lang="zh-CN">
    <head>
        <meta charset="UTF-8">
        <title>动态 404 页面</title>
        <style>
            body { font-family: 'Microsoft YaHei', sans-serif; background-color: #fafafa; text-align: center; padding-top: 100px; }
            h1 { color: #ff6b6b; }
            p { color: #666; }
        </style>
    </head>
    <body>
        <h1>404 - 页面未找到</h1>
        <p>您请求的路径是: <strong>{$url}</strong></p>
        <p>{$message}</p>
        <p><a href="/">返回首页</a></p>
    </body>
    </html>
  4. 测试 访问一个不存在的 URL,系统会自动跳转到 Error/notFound 方法,并渲染你自定义的动态 404 模板。


总结与对比

特性 方法一(配置文件) 方法二(路由)
实现难度 非常简单,只需配置一个路径。 稍微复杂,需要创建控制器和视图。
灵活性 较低,只能指向静态文件。 非常高,可以处理动态数据、执行业务逻辑。
性能 性能更好,直接返回静态文件,不经过 PHP 框架解析。 性能稍差,因为请求需要经过路由和控制器。
适用场景 简单的、静态的 404 页面。 需要动态内容或复杂逻辑的 404 页面。

推荐建议:

  • 对于绝大多数项目,使用方法一(配置文件) 是最佳选择,它简单、高效、且官方支持良好。
  • 只有当你确实需要在 404 页面中展示动态内容或执行额外操作时,才考虑使用方法二(路由)