先用mysql -h 127.0.0.1 -p 3306 -u user -p db命令行直连验证;能通则非服务问题,需查symfony的database_url配置(如localhost应改127.0.0.1、密码需url编码、serverversion须显式指定);不通则说明mysql服务未运行、端口未监听或网络不通。

Connection refused 或 SQLSTATE[HY000] [2002] 怎么快速定位
这不是 Symfony 配置写错了,而是根本没连上 MySQL 服务。先别翻 doctrine.yaml,直接用命令行验证底层通路:
- 运行
mysql -h 127.0.0.1 -P 3306 -u your_user -p your_dbname—— 能连上,说明服务和密码没问题;连不上,就不是框架的事 - 检查
DATABASE_URL是否用了localhost:本地开发务必换127.0.0.1,否则 PHP 会尝试 Unix socket,而 Docker 或某些 MySQL 配置下 socket 路径不一致 - 查端口是否被占:
sudo lsof -i :3306或netstat -tuln | grep :3306,确认 mysqld 真正在监听
DATABASE_URL 里密码含 @ / : 怎么避免解析失败
URL 中的特殊字符不编码,parse_url() 会提前截断用户或主机名,导致连接凭据错乱。比如 mysql://user:pa@ss/word@127.0.0.1:3306/db 实际被解析成 user=“user”,pass=“pa”,host=“ss”,完全错误。
- 必须对密码做 URL 编码:用
rawurlencode('pa@ss/word')得到pa%40ss%2Fword -
DATABASE_URL应写成:mysql://user:pa%40ss%2Fword@127.0.0.1:3306/db?serverVersion=8.0 - 别依赖 IDE 自动编码——有些编辑器会双编码,手动用 PHP 函数或在线工具校验一次
doctrine:database:create 报 Access denied 怎么办
这个命令不是用 root 登录建库,而是用 DATABASE_URL 里的用户执行 CREATE DATABASE。报权限错,95% 是该用户没被授予建库权限,不是密码或 host 写错了。
- 登录 MySQL(用 root)执行:
GRANT CREATE ON *.* TO 'your_user'@'%' IDENTIFIED BY 'your_pass'; FLUSH PRIVILEGES; - 如果只允许建指定库,改用:
GRANT CREATE ON `your_dbname`.* TO 'your_user'@'%'; - Docker 环境注意:MySQL 8.0 默认用
caching_sha2_password插件,老项目可能不兼容,需执行ALTER USER 'your_user'@'%' IDENTIFIED WITH mysql_native_password BY 'your_pass';
查不到数据但 SQL 日志显示查询已发出去
说明请求到了数据库,但结果为空或被过滤。别急着改 DQL,先确认是否触发了隐式 WHERE 条件或实体映射偏差。
- 启用 SQL 日志:
doctrine.dbal.logging: true+doctrine.dbal.profiling: true,在config/packages/dev/doctrine.yaml里加 - 看日志里实际执行的 SQL —— 注意参数绑定是否生效,比如
:status绑定值是null还是'active' - 检查实体字段是否加了
@ORM\Column(nullable=false)却没设默认值,导致 INSERT 失败后后续 SELECT 返回空 - 关联查询漏写
leftJoin或没addSelect,Doctrine 不会自动加载关联对象,模板里$product->getCategory()返回 null 不报错,但你以为数据丢了
真正卡住的地方,往往不在 Doctrine 层,而在 MySQL 用户权限粒度、Docker 网络 DNS 解析、或 PHP 连接复用时 wait_timeout 被云服务商强制缩短——这些点不列在错误堆栈里,得靠 mysql 命令和 tcpdump 验证。











