composer-unused 是唯一能落地的冗余依赖扫描方案,它通过扫描 PHP 源码识别真实使用情况,而 composer show 和 composer why 仅查依赖图谱、不分析代码调用,无法准确识别未使用包。

composer-unused 是目前唯一能落地的冗余依赖扫描方案,其他命令(如 composer show、composer outdated)根本不看代码调用,纯属无效尝试。
为什么 composer show 和 composer why 都不能用来找未使用包
它们只查依赖图谱和锁文件状态,完全不扫描 PHP 源码:
-
composer show只输出已安装包列表,不管你的src/里有没有use过它 -
composer why vendor/package只回答“谁声明了它”,不回答“你有没有真用它”——哪怕你删光所有use,只要它还在composer.json里,why就会说“root requires it” - 框架配置驱动的包(如
symfony/dotenv、doctrine/migrations)在 PHP 文件里没use,但删了就启动失败;这些会被composer-unused标为 unused,必须人工白名单过滤
composer-unused 扫描前必须确认的三件事
否则大概率报一堆误报,或直接漏掉关键路径:
- 确保
vendor/已完整生成:composer install必须跑过,否则 autoload 映射缺失,composer-unused会找不到类引用 - 检查
composer.json的autoload和autoload-dev是否覆盖了你的真实代码路径;如果主逻辑在app/或lib/,但没配进 autoload,就得加--path=app --path=lib - 测试类、命令行类、事件监听器等若在
tests/或bin/下,且没被 autoload-dev 覆盖,需显式加--include-tests或--additional-files=bin/console
运行时容易踩的坑和对应参数
默认行为对多数项目太保守,得靠参数调准:
工作流任务拆解与模型编排技能。使用场景:(1) 收到复杂工作任务需要拆解为可执行步骤,(2) 需要为不同步骤选择最合适的模型,(3) 需要跟踪工作流进度和模型使用情况,(4) 长时间任务卡住需要问题诊断和解决方案。
立即学习“PHP免费学习笔记(深入)”;
- PHP 7.4 项目必须用
v0.9.11:新版v0.12.x含readonly语法,直接 fatal error - CI 中建议加
--no-progress --min-confidence=high --fail-on-unused:避免进度条干扰日志,也防止 medium 置信度导致误失败 - 想跳过
require-dev包(如phpunit/phpunit),加--no-dev;但注意:这会让工具忽略所有 dev-only 包的引用,包括你在*Test.php里用的guzzlehttp/guzzle - 误报常见于扩展名包(如
ext-redis)——它不是 Composer 包,删了毫无意义,应在composer-unused.php中用whitelist()或addNamedFilter()排除
删包不是扫完就 composer remove 了事
扫描结果只是线索,删之前必须交叉验证:
- 对每个疑似冗余包,先跑
composer why vendor/package:如果返回空,说明它既不是顶层依赖,也没被其他包传递依赖——这时才可考虑删 - 批量删更安全:
composer remove spatie/laravel-permission laravel/sanctum是原子操作,失败全回退;别写 for 循环逐个删 - 删完后
vendor/目录仍有残留是正常现象,必须再跑一次composer install或composer update --with-dependencies才真正清理磁盘文件 - 检查
vendor/composer/autoload_psr4.php是否还含已删包路径,若有,说明 autoloader 没刷新,补一句composer dump-autoload --classmap-authoritative
最麻烦的从来不是工具不会跑,而是你得判断:那个被标为 unused 的包,到底是真没用,还是它藏在 YAML 配置里、注解里、或字符串反射里——composer-unused 不分析这些,你得自己翻。


















