标准 composer.json 是项目依赖契约而非配置清单,name 字段必须为全小写、斜杠分隔的 vendor/name 格式(如 "acme/logger"),否则 install 直接失败;psr-4 命名空间须以 结尾、路径须以 / 结尾;classmap 优先级高于 psr-4;require-dev 包不参与生产 autoload 但会污染 lock 文件;config.platform 和 vendor-dir 修改后须重装 vendor。

标准 composer.json 不是配置清单,而是项目依赖契约——字段写错一个,composer install 就可能装出运行时完全不可用的依赖树,甚至卡在 autoload 阶段报 Class not found。
name 字段必须是 vendor/name 格式,否则 install 直接失败
Composer 用 name 唯一标识包,不是随便起个名字。它必须满足:两段式、全小写、只含字母/数字/短横线/斜杠,中间用 / 分隔。比如 "acme/logger" 合法,"Logger"、"acme_logger"、"acmelogger" 全部非法。
常见错误现象:
Invalid package name "MyApp": package names must be lowercase...- 本地
composer validate过不去,CI 构建直接中断 - 私有 GitLab 仓库中误把目录名当包名,导致其他项目
require时解析失败
注意:即使只是本地开发不发包,也得先按规则填上,否则连 composer dump-autoload 都可能跳过 autoload 配置。
autoload 的 psr-4 路径末尾必须带 /,classmap 优先级高于 psr-4
psr-4 映射的命名空间后缀必须以 结尾,路径必须以 / 结尾。例如:"App\": "src/App/" 正确;"App\": "src/App" 会导致 AppFoo 去加载 src/AppFoo.php,显然找不到。
classmap 和 psr-4 混用时,classmap 优先匹配——哪怕同名类同时存在于两个位置,也会加载 classmap 指向的那个文件。
使用场景:
-
psr-4:现代标准结构,推荐用于主体业务代码 -
classmap:加载旧代码、函数文件、无命名空间的类,或第三方未规范打包的脚本
注意:classmap 扫描后不感知文件变更,改了类名或加了新文件,必须手动执行 composer dump-autoload。
require-dev 里的包不参与生产 autoload,但会污染 lock 文件
require-dev 中的包(如 phpunit/phpunit、phpstan/phpstan)只在开发环境安装,不会被 vendor/autoload.php 加载进生产环境。但它们的版本约束会写进 composer.lock,影响 composer install --no-dev 的解析结果。
容易踩的坑:
- CI 环境执行
composer install --no-dev失败,报 “could not resolve packages”,其实是require-dev里某个包间接拉入了和require冲突的依赖版本 - 本地装了
laravel/framework在require-dev,结果测试通过,但生产部署时因版本不兼容直接报Class not found - 插件类 dev 包(如
phpstan/extension-installer)没在config.allow-plugins中显式放行,composer require --dev看似成功,实际插件未激活
验证方式:CI 中务必用 composer install --no-dev --prefer-dist,并配合 composer why-not vendor/package:version 快速定位冲突源。
config.platform 和 config.vendor-dir 改动后必须重装 vendor
config.platform 是伪报 PHP/扩展版本,仅影响依赖解析,不改变真实环境;config.vendor-dir 可把 vendor/ 改成 libs/,config.bin-dir 可把 vendor/bin/ 改成 bin/。
但这两个配置修改后,composer install 不会自动迁移已有包——旧 vendor/ 还在,新目录为空,autoload 仍指向旧路径,IDE 索引、CI 脚本全失效。
正确做法:
- 删掉旧
vendor/目录(或整个composer.lock) - 运行
composer install --no-dev重新生成 - 同步更新所有引用
vendor/autoload.php的入口文件、Dockerfile、CI 脚本、IDE 自动加载设置
特别注意:config.platform.php 设为 "8.1" 但服务器是 8.3,不会报错,但可能让某些包降级到不支持高版本语法的旧版——这种问题往往上线后才暴露。


















