根本原因是docker容器内环境变量未正确注入database_url,导致symfony无法连接数据库;需在docker-compose.yml中显式配置environment或env_file,使用服务名而非localhost,并验证变量是否生效。

容器启动后 php bin/console 报错 “No database connection”
根本原因不是数据库没连上,而是 Symfony 默认在 .env 里读取 DATABASE_URL,而 Docker 容器内环境变量没生效或被覆盖。本地 .env 文件不会自动进容器,硬编码的 localhost:5432 在容器里指向自己,不是数据库服务。
- 确保
docker-compose.yml中 PHP 服务通过environment或env_file显式注入DATABASE_URL=postgresql://db_user:db_pass@db:5432/db_name(注意主机名用服务名db,不是localhost) - 删掉容器内
.env里的DATABASE_URL行,避免它覆盖环境变量;或者设为DATABASE_URL=${DATABASE_URL}并确认docker-compose.yml确实传入了该变量 - 运行
docker-compose exec php bash -c 'printenv | grep DATABASE'验证变量是否真实存在且拼写正确
composer install 在容器里慢得像卡住
不是网络问题,是 Docker for Mac/Windows 的文件挂载性能缺陷 —— vendor/ 目录映射到宿主机时,大量小文件 IO 极其拖慢 Composer。
- 开发阶段把
vendor/排除在volumes外:只挂载./src:/var/www/html/src,不挂./:/var/www/html - 改用多阶段构建:Dockerfile 里先
composer install --no-dev到临时镜像,再复制vendor/到最终镜像,完全避开挂载问题 - 如果必须热重载依赖(极少见),加
cache: true和COMPOSER_CACHE_DIR=/tmp/composer-cache避免反复下载
路由正常但 assets:install 后 CSS/JS 404
Symfony 的 Webpack Encore 或传统 asset 拷贝,生成路径依赖 public/ 目录结构,但 Nginx/Apache 容器没把 public/ 设为根目录,或没启用 try_files 回退规则。
- 检查 Nginx 配置是否含
root /var/www/html/public;(不是/var/www/html) - 确认
location /块有try_files $uri /index.php?$query_string;,否则静态资源请求直接 404,不会 fallback 到 front controller - 运行
docker-compose exec nginx cat /etc/nginx/conf.d/default.conf看实际加载的配置是否生效,别信本地编辑完就完事
本地改代码没反应,缓存像清不掉
不是 OPcache 没关,是 Docker 卷挂载 + Symfony 的 cache:clear 在容器里执行,但宿主机改的代码被卷实时同步后,PHP-FPM 进程还拿着旧 opcode 缓存,且 var/cache 目录若也挂载了宿主机,容器内清除操作可能被覆盖或权限锁死。
- 开发时强制关闭 OPcache:在 PHP 容器的
php.ini加opcache.enable=0,别只靠OPCACHE_ENABLE=0环境变量(某些基础镜像不读) -
var/cache绝对不要挂载到宿主机 —— 改成命名卷或完全不挂载,让容器自己管理缓存生命周期 - 每次改代码后,手动
docker-compose exec php rm -rf var/cache/*,比依赖cache:clear命令更可靠










