不能直接共用 vendor 目录,因不同项目依赖同一包的不同版本会导致类冲突;符号链接需依赖树完全一致(含 composer.lock、platform 配置),并禁用脚本与插件,且 autoload.php 的硬编码路径需特殊处理。
接共用 vendor 目录Composer 默认为每个项目生成独立的 vendor 目录,因为不同项目可能依赖同一包的不同版本(比如 monolog/monolog v2.9 和 v3.5),强行共享会触发 Class not found 或 Cannot declare class 错误。符号链接方案本质是“欺骗” Composer 让它以为 vendor 在本地,实际指向统一位置——但前提是所有项目使用完全一致的 composer.json 依赖树(包括版本约束、平台配置、插件启用状态)。
composer install --no-scripts --no-plugins 避免执行钩子冲突多个项目共用 vendor 时,post-install-cmd 等脚本可能互相干扰(例如重复生成 autoload 文件、修改缓存路径)。必须禁用自动执行:
--no-scripts:跳过所有 scripts 定义的命令--no-plugins:防止插件(如 hirak/prestissimo)在不同项目间污染全局行为composer install --no-scripts --no-plugins
composer.lock
符号链接生效的前提是所有项目最终解析出完全相同的依赖树。这意味着它们的 composer.lock 必须一致(不只是 composer.json):
composer update --lock 生成标准 composer.lock
composer.lock
composer.json 中的 platform 配置(如 "php": "8.1.0")完全相同,否则 composer install 会重新计算依赖composer show --tree 输出是否一致,不一致说明平台或约束有隐性差异ln -sf 创建跨项目 vendor 链接(Linux/macOS)假设你选定 /opt/composer-shared/vendor 为共享目录,各项目位于 /var/www/project-a、/var/www/project-b:
cd /var/www/project-a rm -rf vendor ln -sf /opt/composer-shared/vendor vendor cd /var/www/project-b rm -rf vendor ln -sf /opt/composer-shared/vendor vendor
Windows 用户需改用 mklink /D,且必须以管理员权限运行命令提示符;注意 PHP 进程需有读取目标目录的权限,Apache/Nginx 用户组要能访问 /opt/composer-shared。
真正麻烦的是 autoload 机制:Composer 自动生成的 vendor/autoload.php 里硬编码了 __DIR__ 路径,链接后会导致 require 加载错位。解决方案是——不要让项目直接 require 链接后的 autoload.php,而是统一用共享目录下的入口,或改用 composer dump-autoload --optimize --classmap-authoritative 减少路径依赖。