composer.json 不支持环境变量替换,需通过 scripts 钩子+dotenv 脚本生成配置文件,或使用 auth.json(仅限该文件,支持 ${var} 语法)管理认证信息。

composer.json 里不能直接写 ${ENV_VAR}
Composer 解析 composer.json 是静态的,不执行 shell 展开,也不读取环境变量。你写 "url": "${API_BASE_URL}",它就真当字面量存进去,不会替换——部署时要么报错,要么配错。
真正能起作用的是 composer install 阶段的插件机制或外部脚本干预:
- 用
composer/installers或自定义脚本(scripts段)在安装后读取环境变量,生成实际配置文件 - 把敏感/可变配置抽离到独立文件(如
.env),由应用层(不是 Composer)加载 - 若必须让 Composer “感知”环境,得靠
composer config动态设仓库地址等全局项,但仅限少数字段(如github-oauth、process-timeout)
用 scripts + dotenv 在安装后注入变量
这是最常用也最可控的做法:利用 Composer 的 post-install-cmd 或 post-update-cmd 钩子,调用 PHP 脚本读取 .env 并写入配置目录。
示例流程:
- 项目根目录放
.env(含DB_HOST=127.0.0.1),不提交到 Git -
composer.json中声明脚本:"scripts": { "post-install-cmd": [ "php scripts/write-config.php" ] } -
scripts/write-config.php用Dotenv\Dotenv::createImmutable(__DIR__)->load()读变量,再file_put_contents('config/database.php', ...)
注意:这个脚本必须能被 Composer 执行到,且依赖 vlucas/phpdotenv 已通过 require-dev 安装。
别把数据库密码塞进 repositories 的 URL 里
有人想绕过配置文件,直接在 composer.json 的 repositories 里写 "url": "https://${USER}:${PASS}@git.example.com/repo.git"——这极其危险:
- 密码会明文留在
composer.json或composer.lock中,极易泄露 - Git 提交历史、CI 日志、团队成员本地副本都可能暴露凭证
- Composer 不支持运行时解析 URL 中的变量,
${PASS}就是字面字符串
正确做法是用 auth.json(支持环境变量扩展)或 Git 凭据助手,让 Composer 自动注入认证信息。
auth.json 支持有限的环境变量展开
Composer 从 2.2 开始允许在 auth.json 中使用 ${VAR_NAME} 语法(仅限该文件,且只在安装/更新时生效)。
例如:
{
"http-basic": {
"your-company.com": {
"username": "${COMPOSER_USER}",
"password": "${COMPOSER_TOKEN}"
}
}
}
只要部署机上设置了 COMPOSER_USER 和 COMPOSER_TOKEN,Composer 就能自动替换。但注意:
- 变量名必须全大写,且只能是字母、数字、下划线 没有嵌套或默认值语法(比如
-
auth.json文件本身不能被 Git 跟踪,应放在COMPOSER_HOME下或通过--auth参数传入
${VAR:-default} 不支持)
复杂逻辑(比如多环境路由、条件开关)依然得靠外部脚本驱动,Composer 本身不是配置管理工具。










