Documentation Home
MySQL 8.4 Reference Manual
Related Documentation Download this Manual
PDF (US Ltr) - 39.8Mb
PDF (A4) - 39.9Mb
Man Pages (TGZ) - 257.9Kb
Man Pages (Zip) - 364.9Kb
Info (Gzip) - 4.0Mb
Info (Zip) - 4.0Mb


MySQL 8.4 Reference Manual  /  ...  /  DNS Lookups and the Host Cache

7.1.12.3 DNS 查找和主机缓存

MySQL 服务器维护一个内存中的主机缓存,包含客户端信息:IP 地址、主机名和错误信息。性能chema host_cache 表公开了主机缓存的内容,以便使用 SELECT 语句来检查。这样可以帮助您诊断连接问题的原因。请参阅第29.12.22.3节,“host_cache 表”

以下部分讨论主机缓存的工作原理,以及其他主题,如如何配置和监控缓存。

服务器仅在非localhost TCP连接中使用主机缓存,不会对使用loopback接口地址(例如127.0.0.1::1)或 Unix socket 文件、命名管道或共享内存建立的TCP连接使用缓存。

服务器对主机缓存有多种用途:

  • 通过缓存IP地址到主机名称的结果,服务器避免了对每个客户端连接进行域名系统(DNS)查询。相反,对于给定的主机,它只需要在该主机的第一个连接时执行一次查找。

  • 缓存中包含客户端连接过程中发生的错误信息。一些错误被认为是“阻塞”错误。如果从同一主机连续出现太多这些错误而没有成功连接,服务器将阻止来自该主机的进一步连接。max_connect_errors系统变量确定了在阻止连接前允许出现的连续错误次数。

对于每个适用的新客户端连接,服务器使用客户端IP地址检查是否将客户端主机名称存储在主机缓存中。如果是,则服务器拒绝或继续处理连接请求,取决于该主机是否被阻止。如果主机不在缓存中,服务器尝试解析主机名称。首先,它将IP地址解析为主机名称,然后将主机名称解析回IP地址。然后,它将结果与原始IP地址进行比较,以确保它们相同。服务器将该操作的结果存储在主机缓存中。如果缓存已满,则最近最少使用的条目将被丢弃。

服务器使用getaddrinfo()系统调用进行主机名称解析。

服务器处理主机缓存中的条目如下:

  1. 当来自给定IP地址的第一个TCP客户端连接到达服务器时,创建新的缓存条目,以记录客户端IP、主机名称和客户端查找验证标志。初始情况下,主机名称设置为NULL,标志为false。这一条目也用于来自同一个源IP的后续客户端TCP连接。

  2. 如果客户端IP条目的验证标志为false,服务器尝试IP-to-主机名称-to-IP DNS解析。如果成功,则更新主机名称并将验证标志设置为true。否则,如果失败是永久的,主机名称保持NULL,验证标志设置为true。如果失败是暂时的,主机名称和验证标志保持不变。在这种情况下,下一次客户端从同一个IP连接时将再次尝试DNS解析。

  3. 如果在处理来自给定IP地址的客户端连接时发生错误,服务器更新对应的错误计数器条目。有关记录的错误描述,请见第29.12.22.3节,“host_cache表”

要解除阻塞的主机,刷新主机缓存;见处理阻塞主机

即使没有刷新主机缓存,一些阻塞的主机也可能在其他主机活动的情况下变得解除阻塞:

  • 当客户端IP地址不在缓存中时,连接到服务器的连接,如果缓存已满,服务器将丢弃最近最少使用的缓存条目,以便为新的条目腾出空间。

  • 如果丢弃的条目是阻塞主机的条目,那么该主机将被解锁。

有一些连接错误不是与TCP连接相关的,也是在连接过程中的早期阶段(甚至在IP地址未知之前),或不是特定IP地址相关的(例如内存不足情况)。关于这些错误,请查看Connection_errors_xxx状态变量(见第7.1.10节,“服务器状态变量”)。

主机缓存默认启用。系统变量host_cache_size控制其大小,以及性能chema中的host_cache表的大小,该表公开了缓存内容。缓存大小可以在服务器启动时设置,并且可以在运行时更改。例如,在服务器启动时将其设置为100,请将以下行添加到服务器文件my.cnf中:

[mysqld]
host_cache_size=200

要在运行时将其设置为300,请执行以下操作:

SET GLOBAL host_cache_size=300;

host_cache_size设置为0,或者在服务器启动时或运行时,可以禁用主机缓存。禁用缓存后,服务器每次连接到客户端都会进行DNS查找。

在运行时更改缓存大小将导致隐式主机缓存刷新操作,清除主机缓存、截断host_cache表,并解锁任何被阻塞的主机;请参阅Flush the Host Cache.

要禁用DNS主机名称查找,启动服务器时启用skip_name_resolve系统变量。在这种情况下,服务器将使用IP地址,而不是主机名称来匹配连接的主机到MySQL授权表中的行。只有在那些表中使用IP地址指定的帐户才能被使用。(客户端可能无法连接,如果没有存在指定客户端IP地址的帐户。)

如果您有一个非常慢的DNS和许多主机,您可能可以通过启用skip_name_resolve来禁用DNS查找,或者增加host_cache_size的值以使主机缓存更大。

要完全禁止TCP/IP连接,请在启动服务器时启用skip_networking系统变量。

要调整连续连接错误的允许数量,以便在主机阻塞发生前,请设置max_connect_errors系统变量。例如,在启动时将值设置到服务器my.cnf文件中:

[mysqld]
max_connect_errors=10000

在运行时更改值,可以这样做:

SET GLOBAL max_connect_errors=10000;

性能_schema中的host_cache表公开了主机缓存的内容。使用SELECT语句可以检查该表,可能有助于诊断连接问题的原因。关于该表的信息,请见第29.12.22.3节,“The host_cache Table”

在以下情况下,清空主机缓存可能是有益或可取的:

  • 一些客户端主机更改了IP地址。

  • 出现错误消息Host 'host_name' is blocked,该错误消息对来自合法主机的连接进行阻止。 (请见Dealing with Blocked Hosts.)

清空主机缓存将产生以下效果:

  • 它清除内存中的主机缓存。

  • 它从性能_schema中的host_cache表中删除所有行,该表公开了缓存内容。

  • 它解除任何被阻止的主机。这使得来自这些主机的进一步连接尝试变得可能。

要清空主机缓存,可以使用以下方法:

服务器使用主机缓存来跟踪客户端连接过程中发生的错误。如果出现以下错误,它意味着mysqld从给定的主机接收了许多中断的连接请求:

Host 'host_name' is blocked because of many connection errors.
Unblock with 'mysqladmin flush-hosts'

系统变量max_connect_errors确定服务器在阻止主机之前允许的中断连接请求次数。超过max_connect_errors次失败的连接请求没有成功连接,服务器假设某些事情出错(例如,someone is trying to break in),并阻止主机进一步的连接请求。

要解除阻塞的主机,请刷新主机缓存;请参阅刷新主机缓存

另外,可以通过将max_connect_errors设置为描述在Configuring the Host Cache中的值来避免出现错误信息。max_connect_errors的默认值是100。将max_connect_errors设置为一个大值使得主机更不容易达到阈值并被阻止。但是,如果出现Host 'host_name' is blocked错误信息,首先验证被阻止的主机是否存在TCP/IP连接问题。如果存在网络问题,那么增加max_connect_errors的值将无效。