最佳实践—如何支持热点更新场景

简介: 背景介绍 数据库中更新的模式为lock -> update -> unlock,当对数据库中的同一条记录有大量修改请求时,会造成大量的锁争抢与锁等待。请求量增加会导致TPS下降,延迟飙升。例如,秒杀场景中对于商品库存的扣减。 您可以选择在数据库内核中进行批处理,即对该条记录进行的更新操作使用组提交,更新的模式更改为lock-> group update -> unlock,从而减少锁争抢。结合流水线处理等优化,可以大大提高该场景的TPS,详情可见测试结果。

使用方法

  1. 开启hotspot相关功能。在控制台的参数设置页面打开以下两个开关项,或者使用set global命令(非必须情况不建议使用set global指令)。
set global hotspot=on;
set global hotspot_lock_type=on
  1. 切换事务类型为XA,并在业务的update语句中添加inventory hint。
begin;

set drds_transaction_policy=xa; // 若默认事务策略是XA,则无须重复设置,否则每次均需设置事务策略为XA以使用热点更新hint
UPDATE /+ commit_on_success rollback_on_fail target_affect_row(number)/ table_reference
SET assignment_list
[WHERE where_condition];

注意事项

  • where条件应为主键更新或唯一键更新,且不支持带有全局索引的表(可包含本地索引)。
  • 若已开启共享read_view,则应当先将共享read_view进行关闭,而后使用热点更新的能力。
  • 热点更新hint的使用场景为单分片事务,无法在跨库场景中使用。

Inventory Hint各参数含义

  • commit_on_success(必选)如果该语句成功,则进行提交,连同该语句之前的未提交语句一并提交。
  • rollback_on_fail如果该语句失败,则进行回滚,连同该语句之前的未提交语句一并回滚。
  • target_affect_row(number)校验更新的行数是否符合预期,若不符合则更新失败。

示例

  • 添加commit_on_success以使用组提交等针对热点更新场景的优化(id为主键,使用如下语句对id=1的记录进行更新时,若更新成功则自动提交)
begin;
set drds_transaction_policy=xa;
UPDATE /+ commit_on_success/ table_test SET c = c - 1 WHERE id = 1;
  • 使用rollback_on_fail,可使得更新失败时自动进行回滚
begin;
set drds_transaction_policy=xa;
UPDATE /+ commit_on_success rollback_on_fail/ table_test SET c = c - 1 WHERE id = 1;
  • 使用target_affect_row(number),使得该update语句的预期更新行数为number,若不为number,则更新失败
begin;
set drds_transaction_policy=xa;
UPDATE /+ commit_on_success rollback_on_fail target_affect_row(1)/ table_test SET c = c - 1 WHERE id = 1;
  • 在带有热点更新hint的update语句前,可对同一个物理库中的表进行DML操作
begin;
set drds_transaction_policy=xa;
INSERT into table_test_2 values (1,1);
UPDATE /+ commit_on_success rollback_on_fail target_affect_row(1)/ table_test SET c = c - 1 WHERE id = 1;
  • 在带有热点更新hint的update语句后继续进行DML操作,原因是其后的语句会重新开启新的事务(非必须情况下不推荐)
begin;
set drds_transaction_policy=xa;
UPDATE /+ commit_on_success rollback_on_fail target_affect_row(1)/ table_test SET c = c - 1 WHERE id = 1;
INSERT into table_test_2 values (1,1); // 不推荐,因为该条sql会重新开启一个新的事务

查看inventory hint是否生效

  • 使用命令show global status like "%Group_update%"查看组提交状态,Group_update_leader_count一直增加则说明触发了热点组提交的优化逻辑。
mysql> show global status like "%Group_update%";
+---------------------------------------+--------+
| Variable_name | Value |
+---------------------------------------+--------+
| Group_update_fail_count | 54 |
| Group_update_follower_count | 962869 |
| Group_update_free_count | 2 |
| Group_update_group_same_count | 0 |
| Group_update_gu_leak_count | 0 |
| Group_update_ignore_count | 0 |
| Group_update_insert_dup | 0 |
| Group_update_leader_count | 168292 |
| Group_update_lock_fail_count | 0 |
| Group_update_mgr_recycle_queue_length | 0 |
| Group_update_recycle_queue_length | 0 |
| Group_update_reuse_count | 23329 |
| Group_update_total_count | 2 |
+---------------------------------------+--------+
13 rows in set (0.01 sec)
  • 使用show physical full processlist查看update的状态,是否出现hotspot字样
mysql> show physical full processlist where command != 'Sleep';
+-------+------+-----+---------+-------------+---------+------+-------------------------+----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
| Group | Atom | Id | User | db | Command | Time | State | Info |
+-------+------+-----+---------+-------------+---------+------+-------------------------+----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
| 0 | 0 | 56 | diamond | test_000001 | Query | 0 | hotspot wait for commit | /DRDS /127.0.0.1/12e774cab8800000-128/0// /UPDATE /+COMMIT_ON_SUCCESS ROLLBACK_ON_FAIL TARGET_AFFECT_ROW(1) / `test_hotline_lZTr` AS `test_hotline` SET `b` = (`b` + 1) WHERE (`a` = 1) |
| 0 | 0 | 822 | diamond | test_000001 | Query | 0 | query end | /DRDS /127.0.0.1/12e774c4e9400000-563/0// /UPDATE /+COMMIT_ON_SUCCESS ROLLBACK_ON_FAIL TARGET_AFFECT_ROW(1) / `test_hotline_lZTr` AS `test_hotline` SET `b` = (`b` + 1) WHERE (`a` = 1) |
| 0 | 0 | 831 | diamond | test_000001 | Query | 0 | hotspot wait for commit | /DRDS /127.0.0.1/12e774c551000000-509/0// /UPDATE /+COMMIT_ON_SUCCESS ROLLBACK_ON_FAIL TARGET_AFFECT_ROW(1) / `test_hotline_lZTr` AS `test_hotline` SET `b` = (`b` + 1) WHERE (`a` = 1) |
| 0 | 0 | 838 | diamond | test_000000 | Query | 0 | starting | show full processlist |
+-------+------+-----+---------+-------------+---------+------+-------------------------+----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
4 rows in set (0.33 sec)

热点更新测试

测试表定义


CREATE TABLE sbtest(id INT UNSIGNED NOT NULL PRIMARY KEY, c BIGINT UNSIGNED NOT NULL);

测试语句


UPDATE /+ COMMIT_ON_SUCCESS ROLLBACK_ON_FAIL TARGET_AFFECT_ROW(1) / sbtest SET c=c+1 WHERE id = 1;

测试工具

sysbench

机器规格

4C8G×2 (两节点)

测试结果

场景 1线程 4线程 8线程 16线程 32线程 64线程 128线程 256线程 512线程
热点更新 298 986 1872 3472 6315 10138 13714 15803 23262
普通更新 318 423 409 409 412 428 448 497 615
  • 以上结果的单位为TPS,即每秒处理的交易数(Transaction per second)
  • 热点更新的TPS与机器规格、并发请求数、更新语句有关,测试结果仅供参考
相关文章
|
对象存储 容器
Typora配置阿里云OSS作为图床上传图片
Typora配置阿里云OSS作为图床上传图片
1113 0
|
前端开发 Java 开发者
深入理解Spring Boot中的@Service注解
【4月更文挑战第22天】在 Spring Boot 应用开发中,@Service 注解扮演着特定的角色,主要用于标识服务层组件。本篇技术博客将全面探讨 @Service 注解的概念,并提供实际的应用示例,帮助开发者理解如何有效地使用这一注解来优化应用的服务层架构
3029 1
|
缓存 Java 编译器
JAVA并发编程synchronized全能王的原理
本文详细介绍了Java并发编程中的三大特性:原子性、可见性和有序性,并探讨了多线程环境下可能出现的安全问题。文章通过示例解释了指令重排、可见性及原子性问题,并介绍了`synchronized`如何全面解决这些问题。最后,通过一个多窗口售票示例展示了`synchronized`的具体应用。
|
人工智能 架构师 IDE
阿里云通义灵码重磅升级,能自主修BUG、开发应用的AI程序员来了
通义灵码AI编程能力再进化,说几句话就能开发网页
23632 9
|
C# Windows IDE
WPF入门实战:零基础快速搭建第一个应用程序,让你的开发之旅更上一层楼!
【8月更文挑战第31天】在软件开发领域,WPF(Windows Presentation Foundation)是一种流行的图形界面技术,用于创建桌面应用程序。本文详细介绍如何快速搭建首个WPF应用,包括安装.NET Framework和Visual Studio、理解基础概念、创建新项目、设计界面、添加逻辑及运行调试等关键步骤,帮助初学者顺利入门并完成简单应用的开发。
766 0
|
机器学习/深度学习 算法 计算机视觉
5.1 目标检测基本概念和YOLOv3设计思想
这篇文章详细介绍了目标检测的基本概念、发展历程、设计思想以及YOLOv3算法,解释了如何通过不同的方法生成候选区域并对这些区域进行分类以实现目标检测任务。
|
存储 弹性计算 运维
基于Kibana Discover筛选数据,自由搜索航班信息并导出CSV报告
通过本教程,您将体验Kibana的Discover功能,包括筛选数据(查询栏下添加筛选或在查询栏中使用KQL语法筛选)、保存搜索和导出搜索结果为CSV报告。
8355 3
【每日一道智力题】之猴子搬香蕉
【每日一道智力题】之猴子搬香蕉
1688 0
|
Shell Linux
解决脚本文件无法执行conda命令的问题:CommandNotFoundError: Your shell has not been properly configured to use
使用Linux系统时,有时候希望利用一个脚本执行多条命令来节省时间,其中如果安装有anaconda,需要切换环境或者关闭conda环境,按道理说,在终端里可以通过命令
2217 0
|
前端开发 容器
一篇文章带你掌握Flex布局的所有用法(下)
一篇文章带你掌握Flex布局的所有用法(下)
264 0
一篇文章带你掌握Flex布局的所有用法(下)