用 .env 作本地入口,git 忽略 .env 仅保留 .env.example;部署时通过环境变量或脚本生成 .env,禁用硬编码;laravel 只读 .env,配置缓存需手动更新,app_env 与 app_debug 必须分别显式设置。

如何让 .env 文件不被 Git 提交又支持多环境
直接结论:用 .env 作为本地开发配置入口,不同环境(测试/预发/生产)不靠改文件名切换,而是靠部署时注入真实值。Git 只保留 .env.example,.env 必须在 .gitignore 里。
常见错误是把 .env.production 这类文件提交进仓库,或在 CI/CD 里用 cp .env.production .env —— 这会让敏感信息硬编码进镜像或发布包,也违背 Laravel 的加载逻辑(Laravel 只读 .env,不认其他名字)。
-
.env是 Laravel 启动时唯一自动加载的环境文件,名称不可配置 - 所有环境共用同一套
.env.example,它只定义键名和示例值,不包含真实密钥 - 部署时通过环境变量覆盖(如 Docker 的
-e APP_KEY=xxx)或脚本生成.env,而不是复制预置文件
Laravel 启动时怎么读取 .env?为什么改了不生效
关键点:php artisan config:clear 不会删掉 .env 缓存,真正起作用的是 php artisan config:cache 生成的 bootstrap/cache/config.php —— 它把 .env 解析后的值“固化”进 PHP 数组,后续请求完全绕过 .env 文件。
所以改了 .env 但 config('app.name') 没变,大概率是因为缓存没清干净,或者你正在用 php artisan serve(它不自动重载 .env,必须重启命令)。
- 开发环境建议禁用配置缓存:
APP_ENV=local php artisan config:clear - 生产环境必须跑
php artisan config:cache,但前提是.env已就位且权限正确(Web 用户可读) -
php artisan tinker里测env('APP_NAME')和config('app.name')值不同?说明缓存未更新或.env格式有误(比如漏了引号、用了中文等号)
Docker 部署时怎么安全传入 .env 变量
别把 .env 文件 COPY 进镜像,这是最常踩的坑。Dockerfile 里写 COPY .env . 会导致密钥泄露到镜像层,哪怕后面 RUN rm .env 也删不干净。
正确做法是运行时注入:用 docker run -e APP_KEY=xxx 或挂载临时文件 --env-file .env.prod(注意该文件不能在 Git 里)。Laravel 5.7+ 支持从系统环境变量直接读取,优先级高于 .env 文件。
- 如果用
--env-file,确保文件路径对容器内有效,且 Web 服务器用户(如 www-data)有读权限 - 在
docker-compose.yml中,用environment:块显式列出关键变量,避免整文件暴露 - 密钥类变量(
APP_KEY、DB_PASSWORD)绝不硬编码在 YAML 里,应通过 secrets 或 CI 变量注入
为什么 APP_ENV=production 设了但 debug=true 还报错堆栈
因为 APP_ENV 只控制框架行为开关(比如是否显示详细错误),但真正决定是否显示错误页面的是 APP_DEBUG。这两个变量完全独立,APP_ENV=production 不会自动设 APP_DEBUG=false。
典型现象:线上环境 .env 写着 APP_ENV=production,但忘了关 APP_DEBUG=true,结果 500 错误直接把数据库密码打在 HTML 里。
-
APP_ENV影响日志通道、缓存驱动、优化器行为;APP_DEBUG仅控制错误展示方式 - 生产环境必须显式设
APP_DEBUG=false,且上线前用php -r "echo env('APP_DEBUG') ? 'on' : 'off';"实测 - 某些托管平台(如 Forge、Envoyer)会自动覆盖
APP_DEBUG,但自建环境务必自己确认
最麻烦的其实是权限和时机:Web 服务器用户读不到 .env,或 config:cache 在部署脚本里跑早了(.env 还没生成),这类问题不会报明确错误,只会静默 fallback 到默认值。











