Composer怎么查看依赖关系树 Composer怎么分析包引用逻辑【结构】

1次阅读

composer show –tree 是查看已安装依赖树的唯一可靠命令,它基于 vendor/ 和 composer.lock 输出真实快照,非 composer.json 的理想状态;查未安装包用 –remote,反向依赖用 composer show –who,溯源需 –tree,且依赖树不等同代码调用关系。

Composer怎么查看依赖关系树 Composer怎么分析包引用逻辑【结构】

composer show –tree 是查看依赖树的唯一可靠命令

别再搜 composer tree——它根本不是 Composer 内置命令,是早年插件遗留的混淆概念。真正能用、稳定、无需额外安装的,只有 composer show --tree

这个命令读的是当前 vendor/ 目录下**已实际安装**的包结构,反映的是 composer.lock 解析后的真实依赖快照,不是 composer.json 里写的“理想状态”。

  • 必须在项目根目录运行,且目标包得已安装;否则报错:Package not found
  • 想查未安装包的依赖?加 --remote:例如 composer show --remote --tree monolog/monolog
  • 不支持 --depth 参数限制层级,真要截断只能靠 head -n 50 或重定向到文件后人工看

查“谁用了这个包”用 composer show –who,不是 depends

composer depends 是个陷阱:2.4+ 才有,且默认关闭,需先执行 composer config experimental.show-depends true 才能用——但没必要。

官方早已把反向依赖能力收进 composer show --who(≥2.2),它直接列出所有**直接声明依赖**该包的已安装包,结果干净、无歧义。

  • 示例:composer show --who psr/log 输出所有 requirepsr/log 的包(如 monolog/monologlaravel/framework
  • 它不递归展开下游链路(比如 A → B → C,只显示 B 依赖 C),这是设计使然,不是 bug
  • 不区分 requirerequire-dev,若只想看生产环境依赖谁用了它,得配合 --no-dev 过滤

定位“为什么装了这个包”必须加 –tree

composer why vendor/package 默认只返回一级来源,比如查 monolog/monolog 可能只显示 laravel/framework,但你真正想知道的是:“我自己的 composer.json 里哪行写了它?”

这时候不加 --tree 就等于白查——它不会自动向上追溯到项目顶层。

  • 正确姿势:composer why --tree monolog/monolog,输出会像:
    monolog/monolog<br>└── laravel/framework<br>    └── your-project-name dev-main
  • 末尾的 your-project-name dev-main 表示源头是你自己项目的 composer.json 中的 require
  • 若某行结尾带 [dev],说明来自 require-dev;若中断在某个包名后没继续,可能是那个包用了 provide 声明虚拟包

依赖树 ≠ 代码调用图,别拿它当静态分析用

composer show --tree 展示的是“Composer 安装时决定拉哪些包”,和“PHP 代码里实际 new/use 了谁”是两回事。

比如一个包声明依赖 symfony/console,但你的代码一行都没用过它——--tree 依然会把它画进去;反过来,如果某处 require_once 手动加载了未声明的类,--tree 根本看不见。

  • 真要分析跨包调用或排查“幽灵依赖”,得用 deptracphpstan/dependency-analyser 这类基于 AST 的工具
  • deptrac 默认不读 composer.lock,它扫描的是 usenew,所以首次运行慢、报告里一 uncovered 不代表有问题,只是规则没覆盖到
  • 大型项目里,把 --tree 当成“安全审查依据”容易误判——它只管声明与安装,不管运行时是否真用

依赖树看起来是棵树,其实是个快照、一张快照、一次求解结果。版本冲突、replaceprovide、平台约束……这些都会让同一份 composer.json 在不同环境下生成完全不同的树。别信一次输出,要查就带着上下文一起看。

text=ZqhQzanResources