设置连接保持

在RDS MySQL实例进行切换类的运维操作时,应用程序与代理的连接会有短暂的断开,会对业务造成一定影响,您可以参考本文使用连接保持功能,保证连接不断开,提升产品可用性,降低运维成本。

功能简介

RDS MySQL代理的连接保持功能,即在发生实例切换类的操作时,能保持应用程序与代理的连接不断开,用户通过代理地址访问数据库的应用程序不会收到连接断开的报错,如下图所示。

image.png

image.png

实现原理

数据库代理连接分为前端连接(代理与客户端的连接)和后端连接(代理与数据库的连接),在执行实例切换类操作时,能够在后端连接断开的情况下,保留前端连接,代理在此基础上实现了连接保持能力。

对于后端数据库是RDS MySQL的连接,连接保持的关键在于后端连接(代理与后端RDS MySQL连接)的连接状态恢复。

RDS MySQL的连接状态通常包括系统变量、用户变量、临时表、字符集编码、事务状态和Prepare语句状态信息等。本文将以set names utf8mb4作为连接状态为例介绍RDS MySQL连接保持的实现原理。

主动切换:

主动切换场景下,RDS MySQL数据库代理实现连接保持分为三个步骤:

说明

包含主动切换的运维操作:

  • 主动主备切换

  • 升级小版本

  • 修改重启类参数(修改参数时需重启实例)

  • 变更主实例配置

  1. 开始切换:阻塞新的连接和新的请求

    由于代理不具备事务保持能力,因此,对于不同状态的会话,采取不同的处理方式:

    • 阻塞期间事务活跃的会话:代理将放行请求到后端数据库主节点执行。

    • 阻塞期间新开启的事务的会话:代理将阻塞请求,客户端的现象是阻塞等待服务端回包。

    • 阻塞结束事务仍活跃的会话:客户端与代理的连接将会断开,后端数据库会对未提交的事务进行回滚。

    image.png

  2. 切换中:切换存量连接

    切换过程中会修改存量连接的切换状态:

    • 无法保持的连接:代理会将整个连接断开。

    • 能够保持的连接:连接将会切换至新的数据库节点。

    • 连接池中原数据库主节点的连接:会被清理。

    image.png

  3. 切换完成:恢复连接

    对于能成功保留的连接,代理与后端新的数据库主节点建立连接,并且恢复连接状态。

    image.png

故障切换:

当系统出现故障时,RDS实例会自动进行主备切换,提升一个备节点为主节点,这种切换是非预期的,称为故障切换(Failover)。

代理会缓存当前正在数据库上执行或将要转发的SQL语句。当数据库发生故障时,代理与后端数据库的连接将会断开。代理感知到数据库Failover后,不会立刻断开与客户端的连接,代理会将失败的读请求重新转发到可用的数据库节点,并且恢复连接状态。

重要

对于失败的写请求,代理不能确定数据库是否写成功,因此故障切换时的会话保持不支持写请求。

开启连接保持

说明

2024年01月09日起,符合开启连接保持功能条件的RDS MySQL实例在开通数据库代理时,会默认开启连接保持功能。开启连接保持功能后,您可以随时关闭该功能。

前提条件

主动切换的连接保持

RDS实例满足以下条件:

  • 版本:MySQL 5.6或5.7或8.0

  • 系列:高可用系列、集群系列

  • 存储类型:云盘、本地盘

  • 代理类型:通用型、独享型

  • 已开通数据库代理,且代理的内核版本不低于1.14.5_20231207。

故障切换的连接保持

RDS实例满足以下条件:

  • 版本:MySQL 5.6或5.7或8.0

  • 系列:高可用系列、集群系列

  • 存储类型:云盘、本地盘

  • 代理类型:独享型

    说明

    通用型数据库代理仅支持主动切换场景下的连接保持,独享型数据库代理支持主动切换和故障切换场景下的连接保持。

  • 已开通数据库代理,且代理的内核版本不低于2.9.1。

开启步骤

  1. 访问RDS实例列表,在上方选择地域,然后单击目标实例ID。

  2. 在左侧导航栏,单击数据库代理

  3. 基本信息区域,单击连接保持右侧的开启

    说明

    若无连接保持字样,说明您的实例不符合连接保持的开通条件。

使用连接保持

前提条件

  • 已开通数据库代理。

  • 数据库代理已开启连接保持。

操作步骤

  1. 访问RDS实例列表,在上方选择地域,然后单击目标实例ID。

  2. 在左侧导航栏,单击数据库代理

  3. 根据业务需要配置目标代理连接地址的访问策略,详情请参见配置数据库代理连接地址访问策略。其中读写类型设置为读写(读写分离)

  4. 根据业务需要申请目标代理连接地址的内网/外网地址,详情请参见设置数据库代理连接地址

  5. 在应用程序中,使用目标代理连接地址的内网/外网地址与端口号进行数据库的连接。

  6. 数据库实例进行切换的运维类操作时,数据库代理会自动实现连接保持功能,使用代理连接地址的应用程序与代理的连接不会断开。

使用限制

在切换过程中,连接保持功能无法保持如下场景中的连接:

  • MySQL服务端还没有完全返回包的连接。例如,100 MB的结果集,只返回了50 MB的结果集,剩余的结果集还在返回中。

  • 存在未提交的事务。

  • 连接上使用过change user语句。

  • 连接上使用过LOAD DATA语句。

  • 存在临时表。

  • 通过代理地址进行Binlog订阅的连接。

  • 不支持FOUND_ROWS、ROW_COUNT和LAST_INSERT_ID函数的调用,这些函数可以调用成功,但是无法保证调用结果的正确性。其中SELECT FOUND_ROWS()的用法MySQL官方已不推荐,建议您将SELECT FOUND_ROWS()替换为SELECT COUNT(*) FROM tb1进行查询,详情请参见FOUND_ROWS()

注意事项

  • 由于连接会重连,所以使用select connection_id()查询当前连接的thread id可能会变化。

  • 由于连接会重连,所以show processlist或者SQL洞察中显示的IP地址和端口,可能会与客户端实际的IP地址和端口不一致。

  • 如果连接上存在用户自定义的变量,连接能保持,但用户变量会失效。

关闭连接保持

前提条件

实例已开启连接保持功能。

操作步骤

  1. 访问RDS实例列表,在上方选择地域,然后单击目标实例ID。

  2. 在左侧导航栏,单击数据库代理

  3. 基本信息区域,在连接保持右侧单击关闭

功能测试

本文仅对主动切换场景进行测试。

测试环境

  • 测试用RDS MySQL实例如下:

    • MySQL 8.0版本、高可用系列。

    • 实例规格为8核16 GB独享型规格(mysql.x2.xlarge.2c)。

  • 测试工具:Sysbench

  • 测试数据如下:

    • 100张表,其中每张表包含40000行记录数。

    • 并发度为128。

测试方法

在不同运维场景下,测试RDS MySQL实例的连接保活率(即执行运维操作前后的连接保持比例)。

执行测试语句如下:

sysbench --db-driver=mysql --mysql-host=127.X.X.1 --mysql-port=3306 --mysql-user=username --mysql-password='' --tables=100 --table-size=40000 --threads=128 --mysql-db=sbtest --report-interval=5  --time=600 oltp_read_write run
说明

上述测试语句中的关键参数含义如下:

  • db-driver:数据库引擎

  • mysql-host:数据库代理地址

  • tables:数据库中的表数量

  • table-size:每张表包含的记录条数

  • threads:并发度

  • time:测试时间,单位: 秒

测试结果

在如下测试的运维场景中,RDS MySQL实例均能保持100%的连接保活率。

主动切换场景

保活率

升级小版本

100%

主动主备切换

100%

变更主实例配置

100%

修改重启类参数

100%

相关API

API

描述

ModifyDBProxy

修改RDS实例的数据库代理功能。

DescribeDBProxy

查询RDS实例的数据库代理详情。

相关文档

开通数据库代理