MySQL DNS查找和主机缓存解读

2024年 7月 29日 34.4k 0

MySQL服务默认维护一个内存中的主机缓存,其中包含有关客户端的信息:IP地址、主机名,计数信息。当然,这里不包括本地主机TCP连接,环回接口地址(例如127.0.0.1或::1)建立的TCP连接,或者使用Unix套接字文件sock、命名管道或共享内存建立的连接,它不使用缓存。

MySQL服务将主机缓存用于以下2个目的:

  • 通过缓存IP到主机名称查找的结果,可以避免对每个客户端连接进行域名系统(DNS)查找。相反,对于给定的主机,它只需要对来自该主机的第一个连接执行查找。
  • 缓存包含有关客户端连接过程中发生的错误的信息。有些错误被认为是“阻塞”。如果给定主机连续发生太多错误而没有成功连接,MySQL服务会阻止该主机的进一步连接。这里max_connect_errors参数起到作用

当主机缓存达到错误次数(max_connect_errors)之后,连接请求被中断而没有成功连接后,MySQL服务会阻止该主机进行进一步的连接。如果在前一个连接中断后,在少于max_connect_errors的尝试次数内成功建立了来自主机的连接,则主机的错误计数将清除为零。

这些信息保存在Performance Schema 的host_cache表公开主机缓存的内容,以便可以使用SELECT语句对其进行检查。

mysql> SELECT * FROM performance_schema.host_cache\G;
*************************** 1. row ***************************
IP: 114.84.88.43
HOST: NULL
HOST_VALIDATED: YES
SUM_CONNECT_ERRORS: 0
COUNT_HOST_BLOCKED_ERRORS: 0
COUNT_NAMEINFO_TRANSIENT_ERRORS: 0
COUNT_NAMEINFO_PERMANENT_ERRORS: 1
COUNT_FORMAT_ERRORS: 0
COUNT_ADDRINFO_TRANSIENT_ERRORS: 0
COUNT_ADDRINFO_PERMANENT_ERRORS: 0
COUNT_FCRDNS_ERRORS: 0
COUNT_HOST_ACL_ERRORS: 0
COUNT_NO_AUTH_PLUGIN_ERRORS: 0
COUNT_AUTH_PLUGIN_ERRORS: 0
COUNT_HANDSHAKE_ERRORS: 0
COUNT_PROXY_USER_ERRORS: 0
COUNT_PROXY_USER_ACL_ERRORS: 0
COUNT_AUTHENTICATION_ERRORS: 1
COUNT_SSL_ERRORS: 0
COUNT_MAX_USER_CONNECTIONS_ERRORS: 0
COUNT_MAX_USER_CONNECTIONS_PER_HOUR_ERRORS: 0
COUNT_DEFAULT_DATABASE_ERRORS: 0
COUNT_INIT_CONNECT_ERRORS: 0
COUNT_LOCAL_ERRORS: 0
COUNT_UNKNOWN_ERRORS: 0
FIRST_SEEN: 2024-07-24 10:28:49
LAST_SEEN: 2024-07-24 10:30:41
FIRST_ERROR_SEEN: 2024-07-24 10:28:49
LAST_ERROR_SEEN: 2024-07-24 10:30:41
1 row in set (0.00 sec)

字段 说明
IP 连接到服务器的客户端的IP地址。
HOST 该客户端IP的解析DNS主机名,如果名称未知,则为NULL。
HOST_VALIDATED 客户端IP的IP到主机名到IP DNS解析是否成功执行。
SUM_CONNECT_ERRORS 为“阻塞”的连接错误数(根据max_connect_errors系统变量进行评估)。
COUNT_HOST_BLOCKED_ERRORS 被阻止的连接数。
COUNT_NAMEINFO_TRANSIENT_ERRORS IP到主机名DNS解析期间的瞬态错误数。
COUNT_NAMEINFO_PERMANENT_ERRORS IP到主机名DNS解析期间的永久错误数。
COUNT_FCRDNS_ERRORS 主机名格式错误数。
COUNT_ADDRINFO_PERMANENT_ERRORS 主机名到IP反向DNS解析期间的瞬态错误数。
COUNT_ADDRINFO_PERMANENT_ERRORS 主机名到IP反向DNS解析期间的永久错误数。
COUNT_FCRDNS_ERRORS 正向确认的反向DNS错误数。
COUNT_HOST_ACL_ERRORS 使用ACL连接的错误数。
COUNT_NO_AUTH_PLUGIN_ERRORS 由于请求不可用的身份验证插件而导致的错误数。
COUNT_AUTH_PLUGIN_ERRORS 身份验证插件报告的错误数。
COUNT_HANDSHAKE_ERRORS 握手错误次数。
COUNT_PROXY_USER_ERRORS 代理用户错误数。
COUNT_PROXY_USER_ACL_ERRORS 代理用户ACL错误数。
COUNT_AUTHENTICATION_ERRORS 身份验证失败导致的错误数。
COUNT_SSL_ERRORS SSL问题导致的错误数。
COUNT_MAX_USER_CONNECTIONS_ERRORS 超出用户的连接配额所导致的错误数。
COUNT_MAX_USER_CONNECTIONS_PER_HOUR_ERRORS 超过每小时连接配额所导致的错误数。
COUNT_DEFAULT_DATABASE_ERRORS 默认数据库相关的错误数。
COUNT_INIT_CONNECT_ERRORS init_connect语句执行失败导致的错误数。
COUNT_LOCAL_ERRORS 本地连接的错误数,与网络、身份验证或授权无关。
COUNT_UNKNOWN_ERRORS 其他未知错误的数量。
FIRST_SEEN 第一次连接尝试的时间戳。
LAST_SEEN 最近一次连接尝试的时间戳。
FIRST_ERROR_SEEN 第一次错误的时间戳。
LAST_ERROR_SEEN 最新错误的时间戳。

如果碰到堵塞,需要解除阻止被阻止的主机,需要刷新主机缓存。如 命令行FLUSH HOSTS 或 TRUNCATE:

mysql> FLUSH HOSTS;
Query OK, 0 rows affected, 1 warning (0.00 sec)

mysql> SHOW WARNINGS;
+---------+------+--------------------------------------------------------------------------------+
| Level | Code | Message | +---------+------+--------------------------------------------------------------------------------+
| Warning | 1287 | 'FLUSH HOSTS' is deprecated and will be removed in a future release. Please use TRUNCATE TABLE performance_schema.host_cache instead |
+---------+------+--------------------------------------------------------------------------------+
1 row in set (0.00 sec)

#也是使用host_cache_size,不记录主机缓存信息
mysql>SET GLOBAL host_cache_size=0;

主机缓存参数

到MySQL8.0版本主机缓存,有两个参数。

1. host_cache_size

该参数控制缓存数量,以及Performance Schema host_cache表的记录大小。默认是-1。无限制。

[mysqld]
host_cache_size=10

SET GLOBAL host_cache_size=20;

将大小设置为0将禁用主机缓存。禁用缓存后,服务器每次连接客户端时都会执行DNS查找。

2.skip_name_resolve

该参数用于控制MySQL服务在连接时是否进行主机名解析。主机名解析是将主机名转换为IP地址的过程,它涉及到网络通信和DNS查询。如果此变量为OFF,将在检查客户端连接时解析主机名。如果它是ON,只使用IP号码。然而,在某些情况下,主机名解析可能会导致查询的延迟,性能,无法连接等问题。通过设置该参数为ON,可以告诉MySQL服务跳过主机名解析步骤,直接使用IP地址进行查询,从而避免上述问题。

主机缓存影响参数

验证1:密码错误

首先先把max_connect_errors设置5,之后使用密码错误连续登录6次,最后一次正确登录。

#设置登录错误次数:
mysql> set global max_connect_errors=5;

#查看cache表:
mysql> SELECT * FROM performance_schema.host_cache\G;

MySQL DNS查找和主机缓存解读-1
备注:输入正确的密码仍可登录,说明max_connect_errors设置的值与输入密码错误次数无关。

验证2:网络延迟

使用tc qdisc模拟网络丢包延。延迟设置15000ms。因为connect_timeout默认是10s,所以延迟要大于这个值。
正确输入连接MySQL服务信息,当网络延迟导致连接丢失时(网络异常,网络超时等因素出现,就会导致这个握手协议无法完成)SUM_CONNECT_ERRORS,COUNT_HANDSHAKE_ERRORS 加1。

#设置延迟15s:
shell> tc qdisc add dev eth0 root netem delay 15000ms

#删除延迟:
shell> tc qdisc del dev eth0 root

MySQL DNS查找和主机缓存解读-2

达到max_connect_errors=5次之后,提示信息如下:
MySQL DNS查找和主机缓存解读-3
备注:从上述验证中,可以看出max_connection_errors设置值与密码输入错误的次数无关。跟网络通讯握手协议失败有关系。

3.系统设置

在Linux操作系统下的/etc/resolv.conf是DNS客户机配置文件,用于设置DNS服务器的IP地址及DNS域名,还包含了主机的域名搜索顺序。
resolv.conf的关键字主要有四个,分别是:

nameserver #定义DNS服务器的IP地址。
domain #定义本地域名。
search #定义域名的搜索列表。
sortlist #对返回的域名进行排序。

shell# cat /etc/resolv.conf
# Generated by NetworkManager
domain example.com
search example.com mysql.com
nameserver 192.168.1.10
nameserver 192.168.1.20

如开启MySQL的DNS解析,那这个文件需要关注下。还有/etc/hosts文件强制配置ip地址和其对应主机名。

总结

在日常的MySQL使用中,普遍关闭MySQL的DNS解析,较少影响数据库的稳定性和可用性。。因为日常维护中难免不会有IP变更,域名变更等维护工作,导致DNS解析失败,(如DNS服务器故障、网络问题或配置错误)。

相关文章

Oracle如何使用授予和撤销权限的语法和示例
Awesome Project: 探索 MatrixOrigin 云原生分布式数据库
下载丨66页PDF,云和恩墨技术通讯(2024年7月刊)
社区版oceanbase安装
Oracle 导出CSV工具-sqluldr2
ETL数据集成丨快速将MySQL数据迁移至Doris数据库

发布评论