#1998·typecho

后台目录重命名后,访问默认 /admin/* 路径返回 500 (TypeError)

Author: iugdonCreated Aug 6, 2026Updated Aug 6, 2026

环境

  • Typecho 1.3.0
  • PHP 8.0

复现步骤

  1. config.inc.php 中把后台目录重命名为非默认值:
    php
    define('__TYPECHO_ADMIN_DIR__', '/adm_AbCdEfGhIjKlMnOpQrStUvWxYz/');
  2. 未登录访问默认后台路径:https://example.com/admin/login.php
  3. 返回 500 错误

实际行为

返回 500。开启 __TYPECHO_DEBUG__ 后可见:

TypeError: Cannot assign null to property Typecho\Cookie::$domain of type string
in /app/var/Typecho/Cookie.php:72
#0 /app/var/Widget/Init.php(96): Typecho\Cookie::setPrefix('')

预期行为

  • 重定向到配置的后台目录,或
  • 返回 404(不暴露后台入口存在)

原因分析

Widget\Options::___rootUrl() 在后台上下文(__TYPECHO_ADMIN__ 已定义)下无条件执行:

php
$adminDir = '/' . trim(defined('__TYPECHO_ADMIN_DIR__') ? __TYPECHO_ADMIN_DIR__ : '/admin/', '/');
$rootUrl = substr($rootUrl, 0, -strlen($adminDir));

当请求落在默认 /admin/ 路径、而配置的后台目录是更长的重命名路径时,strlen($adminDir) > strlen($rootUrl)substr() 返回空字符串。空串传入 Cookie::setPrefix('')parse_url('')host → PHP 8 强类型 string $domain 赋值 null → TypeError → 500。

建议修复

  1. Options::___rootUrl():仅当 $rootUrl 确实以 $adminDir 结尾时才裁剪,避免产生空字符串
  2. Cookie::setPrefix():对无 host 的 URL 做防御($parsed['host'] ?? ''