重复类定义错误主因是多个自动加载器或PSR-4映射重叠导致同一类文件被重复加载;需检查spl_autoload_register调用、Composer映射前缀冲突、vendor共用及COMPOSER_VENDOR_DIR环境变量。

重复类定义(Fatal error: Cannot declare class XXX)基本可以确定是多个自动加载器同时加载了同一个类文件,或同一命名空间下存在两个同名类文件被不同路径映射进来。
检查是否注册了多个 autoloader
PHP 允许用 spl_autoload_register() 注册多个加载器,一旦两个加载器都匹配到 UserService,就会尝试两次 require_once 同一文件——而 PHP 对 class 定义不支持重复声明。
- 搜索项目中所有
spl_autoload_register调用,尤其注意手动写的加载逻辑(如require_once 'src/' . $class . '.php') - 检查是否在 ThinkPHP 或 CodeIgniter 的入口或配置中启用了
composer_autoload,同时又在index.php里手动require vendor/autoload.php - 确认没有第三方 SDK 自带
__autoload或spl_autoload_register,和 Composer 加载器形成竞争
验证 PSR-4 映射是否重叠
Composer 的 autoload.psr-4 配置若前缀长度相近或路径交叉,会导致同一个类被两个映射规则同时命中。例如:
围绕关键发现、作用机制、临床相关性及研究局限性展开讨论。适用于撰写或优化任何生物医学论文的“讨论(Discussion)”部分——包括结果解读、与既往文献关联、阐释意外发现、界定研究局限性,以及撰写结论。当用户输入以下任一指令时也会自动触发该功能: - “write my discussion” - “help me discuss my findings” - “how do I compare to prior studies” - “write the limitations par
"autoload": {
"psr-4": {
"App\": "app/",
"App\Http\": "src/http/"
}
}
此时 AppHttpControllersIndexController 既匹配 App\(→ app/Http/Controllers/IndexController.php),也匹配 AppHttp\(→ src/http/Controllers/IndexController.php),结果可能加载两遍。
- 运行
composer dump-autoload后,打开vendor/composer/autoload_psr4.php,人工检查键名是否嵌套或前缀重叠 - PSR-4 映射按前缀长度**降序匹配**,但前提是路径真实存在;若
app/Http/Controllers/和src/http/Controllers/都有IndexController.php,就必然触发重复定义 - 删掉冗余的子命名空间映射,只保留最宽泛且路径唯一的根映射,如只留
"App\": "app/"
排查 vendor 共用或缓存残留
多个 ThinkPHP 项目共用 vendor/ 目录时,vendor/autoload.php 中硬编码的 __DIR__ 会指向错误路径,导致 PSR-4 映射错乱,类文件被从非预期位置加载两次。
- 执行
php -r "echo __DIR__;"对比vendor/autoload.php输出路径与当前项目根目录是否一致 - 删除
vendor/composer/autoload_*.php全部文件(保留installed.json),再运行composer dump-autoload -o - 确认系统环境变量中没有
COMPOSER_VENDOR_DIR,该变量会强制所有项目写入同一vendor
真正麻烦的不是报错本身,而是重复类可能只在某些请求路径下触发——比如某个中间件手动 require 了类,而 Composer 又在控制器里自动加载了一次。这种隐式叠加很难靠日志复现,必须逐个关掉自定义加载逻辑、清空 autoload 缓存、验证每个映射路径的真实文件存在性。

















