Composer依赖冲突是约束无交集的明确信号,应优先运行composer why-not定位阻塞链,如myapp/core requires guzzlehttp/guzzle (^6.5)与laravel/sanctum (^7.2)冲突,而非删vendor或改composer.json。

Composer 依赖冲突不是“运气不好”,而是约束无解的明确信号——它报 Conclusion: don’t install 就是真装不了,不是卡住、不是慢、不是网络问题。
为什么 composer why-not 是第一反应,而不是删 vendor 或改 composer.json
报错只说 don’t install laravel/sanctum:^3.0,但没告诉你谁在拦。删 vendor 和 composer.lock 只是重跑一遍失败逻辑,问题照旧。
-
composer why-not laravel/sanctum:^3.0会逐行输出阻塞链,例如:myapp/core dev-main requires guzzlehttp/guzzle (^6.5) laravel/sanctum ^3.0 requires guzzlehttp/guzzle (^7.2)
——立刻锁定guzzlehttp/guzzle是交集断点 - 注意最后一行才是你
composer.json的根声明,往上每行末尾的(required by ...)是向上追溯起点 - 别用
composer depends替代——它查的是“谁依赖我”,不体现版本限制,对冲突排查无效
composer show --tree 看什么、怎么看才不被误导
composer show --tree 显示的是当前 vendor/ 和 composer.lock 的真实快照,不是你 composer.json 里写的“理想状态”。它不解释原因,只呈现结果。
工作流任务拆解与模型编排技能。使用场景:(1) 收到复杂工作任务需要拆解为可执行步骤,(2) 需要为不同步骤选择最合适的模型,(3) 需要跟踪工作流进度和模型使用情况,(4) 长时间任务卡住需要问题诊断和解决方案。
- 如果树里显示
guzzlehttp/guzzle v6.5.8,但你写了"^7.0",说明已有其他包强制拉低了版本——此时树是“妥协结果”,不是“原因” - 聚焦可疑包:用
composer show --tree guzzlehttp/guzzle | grep -A5 -B5 "monolog"查它和关键依赖的关联层级 - 终端缩进错位?加管道:
composer show --tree | less -S -
--tree在 Composer 2.5+ 已被移除,若命令不存在,改用composer show --format=tree
升级或降级时,--with-dependencies 为什么不能省
不加这个参数,composer update vendor/package 很可能直接失败,报 Your requirements could not be resolved。因为 Composer 默认拒绝更新任何“非必要”的子依赖,哪怕它们是新版本必需的。
- 想升
monolog/monolog到3.0.0,同时保持phpunit/phpunit不动:运行composer update monolog/monolog --with-dependencies - 降级跨主版本(如
guzzlehttp/guzzle从^8.0切回7.4.5)时,必须显式写死版本:"guzzlehttp/guzzle": "7.4.5",而非"^7.0"——避免 Composer 自行选到7.9.0这类不兼容小版本 - 执行后立刻
git diff composer.lock,确认只有预期包及其直系依赖被改动,防止隐性连锁变更
conflict 字段是硬开关,不是提示
你在某个包里写了 "conflict": {"laravel/framework": ">=11.0"},那只要任何间接依赖(比如 orchestra/testbench)拉进了 laravel/framework:11.x,Composer 就会在解析阶段直接拒绝整棵树——哪怕你的项目根本没 require Laravel。
-
conflict全局生效,不看是否实际使用,只看是否出现在依赖图中 - 私有 SDK 或
require-dev里的测试工具最常偷偷引入冲突包,优先用composer why查它们 - 别指望靠
--ignore-platform-reqs绕过——它跳过 PHP 版本或扩展检查,但对conflict无效
真正卡住人的,往往不是哪个命令不会用,而是把 why-not 当成辅助、把 conflict 当成建议、把 show --tree 当成原因分析——其实它们各自只负责一件事,且边界非常清楚。

















