作为MySQL DBA或者后端开发,你是否遇到过这些问题:
应用连接MySQL偶尔卡顿,排查日志却没慢 SQL?
服务器带宽不高,但 DNS 解析请求却占了不少?
明明配置了用户权限,客户端却提示 “Access denied”?
这些问题,大概率和MySQL的skip_name_resolve参数有关。我也经常遇到很多人部署数据库时没有对这个参数进行调整。今天就带大家来了解一下这个参数,踩过坑的小伙伴们也可以留言补充相关经验。
一、什么是skip_name_resolve?
skip_name_resolve是MySQL的核心系统参数之一,直译是“跳过名称解析”,它的核心作用是:禁用MySQL对客户端连接的DNS反向解析。
此参数的核心工作逻辑是当客户端(比如Java应用、Navicat)连接MySQL服务器时:
默认情况下(参数关闭,skip_name_resolve=OFF):MySQL会先获取客户端的IP地址,然后向DNS服务器发起请求,将IP解析为对应的主机名,最后用“主机名”去匹配mysql.user权限表中的授权规则。
开启后(skip_name_resolve=ON):MySQL直接跳过DNS解析步骤,只用客户端的IP地址匹配权限表,完成授权验证。
二、为什么要开启这个参数?
1. 解决连接卡顿问题
DNS解析需要网络请求,哪怕是毫秒级的延迟,高并发场景下(比如每秒上千次连接)会被无限放大,表现为:
应用连接MySQL时偶尔超时
show processlist能看到大量“Login”状态的连接
服务器网卡抓包能看到频繁的DNS查询请求
2. 避免DNS依赖风险
如果出现DNS服务器故障、网络抖动,或者解析规则配置错误,会直接导致:
客户端连接被拒绝(Accessdenied)
MySQL连接线程阻塞,甚至拖垮整个实例
3. 轻微提升性能
跳过DNS解析步骤,减少MySQL的CPU和网络开销,虽然单连接提升微乎其微,但长期运行能降低实例负载。
三、案例演示
接下来用真实案例演示,对比开启 / 关闭参数的差异,以及如何正确配置。
1. 环境准备
MySQL版本:8.4.7(5.7/8.0 版本操作完全一致)
测试工具:mysql客户端
测试服务器:CentOS7.x
创建一个测试用的数据库账号
mysql> create user test@'c7' identified by '123456';Query OK, 0 rows affected (0.05 sec)
mysql> grant all on *.* to test;Query OK, 0 rows affected (0.02 sec)2. 测试默认值情况(skip_name_resolve=OFF)
写了个脚本,测试连接100次的耗时最小值、最大值和平均值(如有需要测试的可以联系我获取参考测试)

测试结果:
测试总次数:100 次,有效次数:100 次
最小连接耗时:22 毫秒
最大连接耗时:185 毫秒
平均连接耗时:32.65 毫秒
3. 测试skip_name_resolve=ON的情况


测试结果如下:
测试总次数:100 次,有效次数:100 次
最小连接耗时:20 毫秒
最大连接耗时:40 毫秒
平均连接耗时:26.63 毫秒
4. 结果对比
从上面的测试结果可以看出,虽然平均连接耗时差距不大(相差约6毫秒),但是最大连接耗时差距就非常大了: 默认值185毫秒 、开启后40毫秒。这样也简单验证了在跳过 DNS 解析步骤时,减少开销,虽然单连接提升微乎其微,但长期运行能降低实例负载。
四、最容易踩的坑:权限授权问题
开启skip_name_resolve后,90%的报错都来自权限配置。 因为MySQL不再解析主机名,所以mysql.user表中用主机名授权的用户会失效!
1. 反面案例
假设你之前创建了这样的用户:
-- 用主机名授权(开启参数后会失效)create user 'app_user'@'db01' identified by '123456';grant all on test.* to 'app_user'@'db-client-01';开启skip_name_resolve=ON后,当db01主机(IP:192.168.1.100)连接时,MySQL会直接用IP192.168.1.100匹配权限表,但表中只有app_user@db01,没有app_user@192.168.1.100,因此会报错:
Access denied for user 'app_user'@'192.168.1.100' (using password: YES)2. 建议做法
开启参数后,用户授权必须用IP 地址或通配符:
-- 1. 授权指定IPcreate user 'app_user'@'192.168.1.100' identified by '123456';-- 2. 授权整个网段(推荐)create user 'app_user'@'192.168.1.%' identified by '123456';-- 3. 授权所有IP(测试环境可用,生产不推荐)create user 'app_user'@'%' identified by '123456';3. 修复已有授权用户
查看当前用户的授权主机:
select user, host from mysql.user where user = 'app_user';删除主机名授权的用户:
drop user 'app_user'@'db01';重新用 IP 授权:
create user 'app_user'@'192.168.1.100' identified by '123456';grant all on test.* to 'app_user'@'192.168.1.100';flush privileges;4. 哪些场景不适合开启
虽然skip_name_resolve好处多,但以下场景建议保持关闭(如有其他场景,欢迎留言补充):
MySQL环境依赖 “主机名” 做权限管理(比如动态DNS、主机名、IP频繁变更)
客户端IP是动态分配的,无法提前配置IP授权
测试环境,对连接性能要求不高,且需要灵活的主机名授权
六、总结
skip_name_resolve的核心作用是禁用DNS反向解析,解决连接卡顿、DNS依赖问题。因此建议生产环境开启,但是开启后必须用IP地址或网段授权用户,不能用主机名,否则会可能报权限错误;测试环境可根据需求选择。
最后提醒:任何参数调整都要先在测试环境验证,再灰度上线!如果你的MySQL也有连接卡顿问题,不妨试试开启这个参数,效果立竿见影~
你在使用MySQL时遇到过哪些连接相关的问题?欢迎留言沟通。
关注微信公众号「数据库干货铺」,获取更多数据库运维干货。
2162

被折叠的 条评论
为什么被折叠?



