腾讯游戏数据自愈服务方案

腾讯游戏数据自愈服务方案简介

1. 引言

在正式介绍项目背景之前,让我们先看一组数据:

这是2个灰度的业务,都是Z3服务器,我们先只从时间成本的收益角度来看:

⑴  左一业务数据量是330G,数据不一致时通过重做slave需要150分钟左右,而借助pt-table-sync只需要5分钟,速度提升30 倍。

⑵  右一业务的量是93G,通过sync工具花费3分钟,而如果重做slave要35分钟,速度提升12倍。

引入这组数据意在指明,整个过程不仅解放了DBA的双手,也符合”零运维”的趋势,数据自愈将是互娱DBA团队在未来提供的服务之一。

2. 背景

MySQL数据库基于binlog的数据同步方案,绝大部分情况下能保证主备数据完全一致,但某些异常情况下,例如开发使用了unsafe statement的SQL(如带limit)及硬件故障等,都可能导致主备数据不一致。DBA通过checksum工具可以发现这些不一致的情况,但往往需要重新做一个热备来恢复主备数据一致性,并且此过程可能需要10小时以上,而实际情况上主备数据通常仅有少量不一致,在线修复这些数据差异可以更高效地完成一个数据一致的热备。

3. 收益

重做热备是我们目前首选的修复方案,但有时候没有备用的新机子却让修复步伐戛然而止,而如果没有修复,倘若master故障,由于数据不一致,切换到slave是存在数据丢失的风险,那么又不得不执行修复,DBA就需要评估以前slave上的连接切换到master是否会影响master的性能......这样DBA的工作量就无形中翻倍了。

我们在引言中也道出了sync工具相比传统的热备在时间上的收益,但除了这个,数据自愈服务的收益包括但不限于:

▼ 业务数据更安全,恢复热备时间变短

▼ 减少服务器资源,避免重做热备的机器申请

▼ 提升DBA做热备的处理效率

▼ 降低沟通成本,保证业务持续稳定运行

4. 数据自愈解决方案

我们从开源社区引入了Percona公司的pt-table-sync,该项目从2007年启动。

下面我们对该工具的实现细节以及互娱DBA团队在此基础上进行定制开发的部分内容进行讨论。

⑴  流程图

Pt-table-sync有2种修复模式:replicate模式和非replicate模式,上图是replicate的,这也是我们所推荐,原因会在下文说明。

这里,我们先对上图作下简要介绍

① 对每一个chunk,再校验时加上for update锁,一旦获得锁,就记录下当前主库的show master status值。以我测试机的案例:


SELECT /*water2.t:1/1*/ 0 AS chunk_num, COUNT(*) AS cnt, COALESCE(LOWER(CONV(BIT_XOR(CAST(CRC32(CONCAT_WS(‘#‘, `id`, `name`, CONCAT(ISNULL(`name`)))) AS UNSIGNED)), 10, 16)), 0) AS crc FROM `water2`.`t` FORCE INDEX (`PRIMARY`) WHERE (1=1) AND ((1=1)) FOR UPDATE


SHOW MASTER STATUS

② 在从库上执行select master_pos_wait()函数,等待从库SQL线程执行到show master status得到的位置,以此保证,主从上关于这个chunk的内容均不再改变。


SELECT MASTER_POS_WAIT(‘binlog3306.000014‘, 139672350, 60)

③ 对这个chunk执行checksum,然后与主库的checksum进行比较


DR:

SELECT /*water2.t:1/1*/ 0 AS chunk_num, COUNT(*) AS cnt, COALESCE(LOWER(CONV(BIT_XOR(CAST(CRC32(CONCAT_WS(‘#‘, `id`, `name`, CONCAT(ISNULL(`name`)))) AS UNSIGNED)), 10, 16)), 0) AS crc FROM `water2`.`t` FORCE INDEX (`PRIMARY`) WHERE (1=1) AND ((1=1)) LOCK IN SHARE MODE

DB:

SELECT /*water2.t:1/1*/ 0 AS chunk_num, COUNT(*) AS cnt, COALESCE(LOWER(CONV(BIT_XOR(CAST(CRC32(CONCAT_WS(‘#‘, `id`, `name`, CONCAT(ISNULL(`name`)))) AS UNSIGNED)), 10, 16)), 0) AS crc FROM `water2`.`t` FORCE INDEX (`PRIMARY`) WHERE (1=1) AND ((1=1)) FOR UPDATE

④ 如果checksum相同,说明主从数据一致,就继续下一个chunk

⑤ 如果checksum不同,说明该chunk有不一致,深入chunk内部,逐行计算checksum并比较,如果发现某行不一致,则标记下来,继续检测剩余行,直到这个chunk结束。

⑥ 直到修复该chunk所有不一致的行,继续检查和修复下一个chunk

⑵ checksum算法

有2个层次的校验算法,一是块级,一是行级。

① 单行数据checksum值计算

检查表结构并获取每一列的数据类型,把所有数据类型都转化为字符串,然后用concat_ws()函数进行拼接,由此计算出该行的checksum值,checksum默认采用crc32计算。下面是一个例子:


SELECT /*rows in chunk*/ `id`, `name`, CRC32(CONCAT_WS(‘#‘, `id`, `name`, CONCAT(ISNULL(`name`)))) AS __crc FROM `water2`.`t` FORCE INDEX (`PRIMARY`) WHERE (1=1) AND (1=1) ORDER BY `id` FOR UPDATE;

② 数据块checksum值的计算

智能分析表上的索引,然后把表的数据split成若干个chunk,计算的时候以chunk为单位,可以理解为把chunk内的所有行的数据拼接起来,再计算crc32的值,即得到该chunk的checksum值。下面是一个例子:


SELECT /*water2.t:1/1*/ 0 AS chunk_num, COUNT(*) AS cnt, COALESCE(LOWER(CONV(BIT_XOR(CAST(CRC32(CONCAT_WS(‘#‘, `id`, `name`, CONCAT(ISNULL(`name`)))) AS UNSIGNED)), 10, 16)), 0) AS crc FROM `water2`.`t` FORCE INDEX (`PRIMARY`) WHERE (1=1) AND ((1=1)) FOR UPDATE;

⑶ 数据精确切分

锁生命周期是我们一直很注重的问题。

2010年底和2011年初,彼时我们刚刚引入了数据在线校验方案不久,在企鹅gamedb每天日常checksum时,DB有锁数据情况,导致TTC大量数据无法写入的告警,mk-table-checksum 1.2.8 版本数据分片方法不合理,当表数据分布非常不均匀时,数据切片会导致某些块包含的数据行过大,其中innodb行锁实现为索引间隙锁,checksum过程会锁住chunk的数据。

felixliang修改mk-table-checksum的源代码,增加自定义recursive_dynamic_calculate_chunks函数,实现了精确数据切片控制,该函数内部调用explain查看每个chunk包含的rows,确保每个chunk中的行数不多于chunk-size参数设置的大小。当每个chunk切分均匀后,chunk数据校验在1秒左右完成,锁数据情况几乎很难感知得到。

这个方案已经在腾讯游戏日常数据校验稳定运行3年多,我们相信该切分算法比官方默认的切分而言更加健壮、同时也更加安全。而pt-table-sync同样会对不一致的表切分,由此我们迁移了该切分算法到pt-table-sync里面,这也是”前人栽树,后人乘凉”的好处。

⑷ 延迟控制

这是为什么我们要采用replicate模式的必要性。

非replicate模式只是普通的线程请求行为,跳过MySQL的Replication机制,本身不做延迟控制,然而,pt-table-sync在修复过程中是不能容忍从库延迟,如果延迟太多,pt-table-sync会长期持有对chunk的for update锁,然后等待从库的master_pos_wait执行完毕或超时,从库延迟越大,等待过程就越长,主库加锁的时间就越长,对线上影响就越大。但是如果不等待,这个工具是无法验证主从数据是否一致。

但是,replicate模式下,补偿SQL是通过master上执行,生成binlog,然后全量同步到slave,再在slave上回放,从而达到数据修复的效果。而数据安全是生命线,改错了master就得回档,就不是闹着玩的。改错了slave不会对玩家有影响,对DBA是个保护。

那么,我们既想要replicate模式带来的好处,又想避免补偿SQL在master执行带来的风险不可控因素,该如何做?

互娱DBA团队通过修改get_change_dbh函数让最后一步生成的补偿SQL不走binlog,直接在slave上跑,从而避免在master上修复带来的数据安全问题。

⑸ 普通索引

pt-table-sync采用replace into来修复主从不一致,必须保证被replace的表有主键或唯一键,否则replace into退化成insert into,而insert是不能在master上执行,因为那样只会使不一致扩散。

对发现主从不一致的行,采用replace into 语句,在主库上执行一遍以生成该行的全量binlog,并同步到从库,这会以主库数据为基础修复从库:

① 对于主库有的行而从库没有的行,采用replace在主库上插入(必须不能是insert)

② 对于从库有的行而主库没有的行,通过在主库执行delete来删除

因为现网环境比较复杂,我们不能保证腾讯全球游戏每个表上都有主键或唯一键。因此,互娱DBA团队通过源码修改,当发现主库上的表没有唯一键时不会致命退出,而是继续执行,但采用了另外一种算法,即在slave上采用delete + replace 方式修补。

⑹ 平台兼容

我们先看mk-table-checksum与pt-table-checksum表结构。

⒈ mk-table-checksum

Ⅱ. Pt-table-checksum

是的,这2个表结构是不一样的,而pt-table-sync的replicate模式是直接读取pt-table-checksum的表,但是我们:
① mk-table-checksum修复版已经集成到我们的GCS平台

② 保留pt-table-sync最新版本的功能,避免引入mk-table-sync老版本bug

基于上述2个理由,我们修改了find_replication_differences函数,让pt-table-sync兼容了mk-table-checksum,这样既能兼容现有平台的功能,又可以用得上pt-table-sync最新版本的新特性。

⑺ 超时控制

在我们测试过程中,发现官方提供的超时控制--wait参数有”bug”

① 对于非replicate模式,wait参数无效

② 对于replicate模式,wait只能是0和非0,当非0时,任何值都是一样的

下面是我们的测试现象

所以,无论哪种模式,wait参数都是没有用的。

我们修改源码来通过外部参数的动态控制超时行为:

5. 小结

数据自愈是数据校验的一种延续与补充,是随着后续业务全量铺开而互娱DBA团队不断定制开发演变的数据修复服务方案。在数据自愈的服务化之路上,相信我们会越来越好。

时间: 2024-10-28 03:38:19

腾讯游戏数据自愈服务方案的相关文章

一个轻客户端,多语言支持,去中心化,自动负载,可扩展的实时数据写服务的实现方案讨论

背景 背景是设计一个实时数据接入的模块,负责接收客户端的实时数据写入(如日志流,点击流),数据支持直接下沉到HBase上(后续提供HBase上的查询),或先持久化到Kafka里,方便后续进行一些计算和处理,再下沉到文件系统或做别的输出. 在设计中,对于客户端和服务端有这么些目标. 客户端需要支持多语言(Java,C++),做得尽量轻量级,只要连上服务端的ip:port,以RPC的形式调用简单的write就可以把数据写出去.客户端不承担任何逻辑的处理,服务端的负载均衡对客户端是透明的. 服务端想要

揭秘腾讯大数据平台与推荐应用架构

内容简介: 腾讯的月活跃用户8.3亿 微信月活跃用户4.4亿 QQ空间月活跃用户6.5亿 游戏月活跃用户过亿 如今腾讯的数据分析已经能做到始终“不落地”,即全部的实时处理.腾讯大数据平台有如下核心模块:TDW.TRC.TDBank.TPR和 Gaia.简单来说,TDW用来做批量的离线计算,TRC负责做流式的实时计算,TPR负责精准推荐,TDBank则作为统一的数据采集入口,而底层的 Gaia则负责整个集群的资源调度和管理.李勇还特别强调了数据平台体系化是应用基础,数据应用商业化是价值导向. 数据

R语言数据清理:视频游戏数据案例研究

Wesnoth之战是一款开源的回合制策略游戏.游戏世界很丰富,有几个派系,地图和数百个可用单位.在本教程中,您将学习如何将中等大小的数据集(如游戏元数据)转换为有用的格式,以便使用R进行进一步分析. 您将了解整洁数据集遵循的关键原则,为什么跟踪它们有用,以及如何清理您给出的数据.整理也是了解新数据集的好方法. 最后,在本教程中,您将学习如何编写一个函数,使您的分析看起来更清晰,并允许您以非常可重复的方式在分析中执行重复元素.该功能允许您将最新版本的数据动态加载到灵活的数据方案中,这意味着在添加新

论游戏数据网站dotamax的盈利方式

由于我很早在内测时期就开始上手dota2这款游戏,作为一个资深玩家,在最初的两年是没有用到过游戏数据网站的,后来出现了dotabuff网站,但是由于是纯英文且部分功能不全,使用并不方便,后来出现了dotamax网站,从刚开始的建站直至现如今的基本功能完善,许许多多和我一样的玩家在使用,因此,该网站的流量是十分可观的.后来,由于游戏博彩的流行,dotamax又专门开设了博彩服务,以及和各大直播网站的合作链接.目前来看,这是一个颇为成功的网站,但是该网站的盈利点在何处呢?  dotamax现在靠do

腾讯游戏是如何使用Docker的

转自:http://www.infoq.com/cn/articles/how-tencent-game-use-docker 干货 | 腾讯游戏是如何使用Docker的? 作者 郭蕾 发布于 2015年8月15日 | 讨论 分享到: 微博 微信 Facebook Twitter 有道云笔记 邮件分享 稍后阅读 我的阅读清单 腾讯第一季度的财报显示, 腾讯游戏的收入占腾讯总营收的59.4%,很显然,腾讯游戏已经是腾讯最赚钱的部门,当然,腾讯也是国内最大的游戏发行商.游戏行业相对于其他行业来说特

华云数据:云服务5分钟快速响应

从云计算的技术标准到服务标准,标准的建立将有利于规范处于初级阶段的中国云计算产业的健康发展.华云数据开行业先河,以"5分钟快速响应服务新标准"实现了差异化竞争,进一步确立了自己的优势. 在云计算的概念刚刚出现时,人们已经在热议,围绕云计算应该建立一系列标准.只不过当时,大家更关注的是云计算的技术标准.但是现在,随着云计算应用逐步落地,以及提供各类云服务的厂商不断涌现,业界又在谈论,云计算服务也应该进一步规范,做到有章可循.作为专业的云服务提供商,无锡华云数据技术服务有限公司(以下简称华

网易游戏还能否撼动腾讯游戏霸主地位?

今年9月,网易发布了由<阴阳师>改版的<决战!平安京>,正式面向腾讯的<王者荣耀>发起挑战.如今,网易游戏和腾讯游戏为了能成为游戏行业的老大展开了一系列的激烈竞争. 根据国外权威移动游戏产业媒体PocketGamer的最新报告我们了解到,在"全球50大手游发行商"中,腾讯游戏排第三,而网易游戏排第四. 网易游戏如何一步步成为腾讯游戏的劲敌? 网易游戏虽说不是游戏行业的龙头老大,但其地位也不低,而网易之所以能在众多游戏中突出重围成为行业"二把

局域网如何禁止腾讯游戏,网关(不是路由)怎样屏蔽DNF、穿越火线等游戏。

腾讯游戏是腾讯四大网络平台之一,是全球领先的游戏开发和运营机构,也是国内最大的网络游戏社区.但是,很多青少年沉迷游戏,不但影响工作和学习,还会伤害身体.滋生犯罪. 本文中,我将演示如何用WSG上网行为管理网关来屏蔽腾讯游戏的登录.根据腾讯游戏登录协议介绍,腾讯游戏的登录主要是http方式,需要连接网站"(dlied|msdk|mdt).*\.qq\.com"(正则表达式).如果你的路由器或者防火墙能够支持正则表达式域名过滤,你可以直接把该正则表达式添加到黑名单中以禁止腾讯游戏的登录.

搭建企业级全网数据定时备份方案【cron + rsync】

1.1.1. 服务端的配置[192.168.25.141] Rsync的端口是:873 man rsyncd.conf 查看帮助 1.vim /etc/rsyncd.conf vi /etc/rsyncd.conf -->man rsyncd.conf 查看帮助 ######rsyncd.conf####### uid = rsync ----->非系统虚拟用户 gid = rsync use chroot =no -->防止出现安全问题 maxconnections = 200 ---