Jor*_*men 6 python amazon-web-services amazon-rds aws-lambda amazon-aurora
我正在运行 Amazon Web Services RDS Aurora 5.6 数据库集群。有几个 lambda 与这些数据库实例对话,它们都是用 python 编写的。现在一切运行良好,但突然之间,从几天前开始,python 代码有时会开始抛出以下错误:
[ERROR] InterfaceError: 2003: Can't connect to MySQL server on 'CLUSTER-DOMAIN:3306' (-3 Temporary failure in name resolution)
这种情况每 1000 个左右的新连接就会发生 1 个。有趣的是,最近几天我没有接触过整个服务(自从它开始发生以来)。所有 lambda 都使用官方 MySQL 连接器客户端,并使用以下代码段在每次初始化时进行连接:
import mysql.connector as mysql
import os
connection = mysql.connect(user=os.environ['DATABASE_USER'],
password=os.environ['DATABASE_PASSWORD'],
database=os.environ['DATABASE_NAME'],
host=os.environ['DATABASE_HOST'],
autocommit=True)
Run Code Online (Sandbox Code Playgroud)
为了排除这是 Python MySQL 客户端中的问题,我添加了以下内容来解析主机:
import os
import socket
host = socket.gethostbyname(os.environ['DATABASE_HOST'])
Run Code Online (Sandbox Code Playgroud)
同样在这里,我有时会收到以下错误:
[ERROR] gaierror: [Errno -2] 名称或服务未知
现在我怀疑这与 DNS 有关,但由于我只是使用集群端点,因此我无能为力。有趣的是,我最近在不同地区也遇到了完全相同的问题,使用相同的设置(Aurora 5.6 集群,python 中的 lambda 连接到它)并且在那里发生了同样的情况。
我已经尝试重新启动集群中的所有机器,但问题似乎仍然存在。这真的是DNS问题吗?我能做些什么来阻止这种情况发生?
AWS Support 告诉我这个错误很可能是由 AWS 的 VPC 中的流量配额引起的。
根据他们关于DNS 配额的文档:
每个 Amazon EC2 实例将可以发送到 Amazon 提供的 DNS 服务器的数据包数量限制为每个网络接口每秒最多 1024 个数据包。此配额无法增加。Amazon 提供的 DNS 服务器支持的每秒 DNS 查询数量因查询类型、响应大小和使用的协议而异。有关可扩展 DNS 架构的更多信息和建议,请参阅适用于 Amazon VPC的混合云 DNS 解决方案白皮书。
需要注意的是,我们在这里查看的指标是每个 ENI 的每秒数据包数。这有什么重要的?好吧,虽然每个查询的实际数据包数量各不相同,但每个 DNS 查询通常有多个数据包,这可能不是很明显。
虽然在 VPC 流日志中看不到这些数据包,但在查看我自己的数据包捕获时,我可以看到一些包含大约 4 个数据包的解析。
不幸的是,我不能对白皮书说太多。在这个阶段,我并没有真正考虑将混合 DNS 服务的实施视为“好的”解决方案。
我正在寻找方法来减轻发生此错误的风险,并在它确实发生时限制其影响。在我看来,有多种选择可以实现这一目标:
INFORMATION_SCHEMA.REPLICA_HOST_STATUS表,其中 MySQL 会“近实时”公开有关数据库实例的元数据。请注意,该表“包含集群范围的元数据”。如果您是 cbf,请查看选项 4。是一个数据库驱动程序或连接器,能够从元数据表中读取数据库集群拓扑。它可以将新连接路由到单个实例端点,而无需依赖高级集群端点。智能驱动程序通常还能够以循环方式对可用 Aurora 副本之间的只读连接进行负载平衡。
最初,我认为创建一个指向集群的 CNAME 可能是个好主意,但现在我不太确定缓存 Aurora DNS 查询结果是否明智。这有几个原因,在Aurora 连接管理手册中以不同级别的详细信息进行了讨论:
除非您使用智能数据库驱动程序,否则您将依赖 DNS 记录更新和 DNS 传播来实现跨 Aurora 副本的故障转移、实例扩展和负载平衡。目前,Aurora DNS 区域使用 5 秒的短生存时间 (TTL)。确保您的网络和客户端配置不会进一步增加 DNS 缓存 TTL
Aurora 的集群和读取器端点抽象了数据库集群中发生的角色变化(主实例提升/降级)和拓扑变化(实例的添加和删除)
我希望这有帮助!