MySQL DDL--ghost工具学习

Johnny21
• 阅读 1504

GHOST工作流程图:

MySQL DDL--ghost工具学习

GHOST工作原理:

1、首先新建一张ghost表,结构与源表相同 2、使用alter命令修改ghost表 3.1、模拟从库命令获取主库上该表的binlog(基于全镜像的行模式的binlog包含更改前和更改后的所有数据),并解析成语句到ghost表上执行。 3.2、获取源表的数据范围(如按照主键获取到最大值和最小值),然后将数据拆分为多个批次拷贝插入到ghost表中 4、锁住源表,防止用户修改源表数据 5、将源表重命名,将ghost表改名为源表 6、释放表锁,清理gh-ost工具产生的表。

GHOST有工作模式:

1.连接主库直接修改
    直连主库
    主库上创建ghost表
    新表(ghost表)上直接alter修改表结构
    迁移原表数据到新表
    拉取解析binlog事件,应用到新表
    cut\-over阶段,用新表替换掉原表 2.连接从库间接应用到主库
    连接从库
    校验完后,在主库创建新表
    迁移原表数据到新表
    模拟从库的从库,拉取解析增量binlog应用到主库
    cut\-over阶段,用新表替换掉原表  

两者不同的点就在于,通过连接从库来进行变更,对主库的性能影响最小,但使用主库能够减少网络影响,操作速度更快。

如何保证源表和新表数据一致:

由于使用binlog获得的数据总是新于或者等于从源表拷贝的数据: 1、在应用binlog导出的数据时,将UPDATE和DELETE直接应用ghost表,将INSERT修改为REPLACE INTO再应用到ghost表。 2、在copy源表数据到ghost表时,使用INSERT IGNORE来忽略掉ghost表已存在的记录 3、对于在gh-ost工作期间发生的DELETE操作:
    A:如果记录在从源表删除前被复制到ghost表, 则ghost表中记录会在应用binlog导出的DELETE命令时删除。
    B:使用记录在从源表复制到ghost表之前被删除,则记录不会被复制到ghost表,应用binlog导出的DELETE命令也不会报错。

GHOST支持跨服务器操作

假设有一套主从复制A1-->A2,A1为主库,A2为从库,另有一台服务器B1装有gh-ost,可以在B1上执行对A1上表的修改: 1、对于数据拷贝操作,B1发送查询到A1上先获取最大值和最小值,然后在B1上进行拆分成不同批次,再从B1上发送命令给A1执行小范围数据拷贝 2、对于Binlog解析,先模拟B1到A1的搭建复制,从A1上拉取binlog到B1,在B1上解析成SQL命令,再发送到A1上执行。

对于跨服务器执行gh\-ost命令,会导致大量数据在数据库服务器到命令服务器之间传输,需要考虑网络带宽和网络稳定

重命名原理

在pt-osc或者online ddl中,最后的rename操作一般是耗时比较短,但如果表结构变更过程中,有大查询进来,那么在rename操作的时候,会触发MDL锁的等待,如果在高峰期,这就是个严重的问题。所以gh-ost是怎么做的呢?

gh\-ost利用了MySQL的一个特性,就是原子性的rename请求,在所有被blocked的请求中,优先级永远是最高的。gh-ost基于此设计了该方案:一个连接对原表加锁,另启一个连接尝试rename操作,此时会被阻塞住,当释放lock的时候,rename会首先被执行,其他被阻塞的请求会继续应用到新表。

唯一索引问题

如果通过gh-ost来新增唯一索引,由于REPLACE INTO和INSERT IGNORE会受到ghost表上唯一索引的影响,当在唯一索引上存在数据重复时,会导致数据丢失。

相关资源:GHOST文件提取_工具_最新版

本文转自 https://blog.csdn.net/weixin_33806300/article/details/85993965,如有侵权,请联系删除。

点赞
收藏
评论区
推荐文章
blmius blmius
3年前
MySQL:[Err] 1292 - Incorrect datetime value: ‘0000-00-00 00:00:00‘ for column ‘CREATE_TIME‘ at row 1
文章目录问题用navicat导入数据时,报错:原因这是因为当前的MySQL不支持datetime为0的情况。解决修改sql\mode:sql\mode:SQLMode定义了MySQL应支持的SQL语法、数据校验等,这样可以更容易地在不同的环境中使用MySQL。全局s
皕杰报表之UUID
​在我们用皕杰报表工具设计填报报表时,如何在新增行里自动增加id呢?能新增整数排序id吗?目前可以在新增行里自动增加id,但只能用uuid函数增加UUID编码,不能新增整数排序id。uuid函数说明:获取一个UUID,可以在填报表中用来创建数据ID语法:uuid()或uuid(sep)参数说明:sep布尔值,生成的uuid中是否包含分隔符'',缺省为
待兔 待兔
5个月前
手写Java HashMap源码
HashMap的使用教程HashMap的使用教程HashMap的使用教程HashMap的使用教程HashMap的使用教程22
Jacquelyn38 Jacquelyn38
3年前
2020年前端实用代码段,为你的工作保驾护航
有空的时候,自己总结了几个代码段,在开发中也经常使用,谢谢。1、使用解构获取json数据let jsonData  id: 1,status: "OK",data: 'a', 'b';let  id, status, data: number   jsonData;console.log(id, status, number )
Easter79 Easter79
3年前
sql注入
反引号是个比较特别的字符,下面记录下怎么利用0x00SQL注入反引号可利用在分隔符及注释作用,不过使用范围只于表名、数据库名、字段名、起别名这些场景,下面具体说下1)表名payload:select\from\users\whereuser\_id1limit0,1;!(https://o
Stella981 Stella981
3年前
Hive 删除行, 表 ,清空表
删除行A表数据如下id(String)       name(String)\1                       aaa2                      bbb3                      ccc\
Wesley13 Wesley13
3年前
gh
ghost简单使用(站在巨人的肩膀上)ghost介绍与原理性的东西这里就不多做介绍,因为好雨云发布一篇文章,针对ghost原理写的已经非常详细,括号里之所以写(站在巨人的肩膀上),也是对好雨云的感谢与崇拜。1\.ghost工作模式ghost有三种工作模式:a:连接到从库,在主库做迁移
Stella981 Stella981
3年前
Android蓝牙连接汽车OBD设备
//设备连接public class BluetoothConnect implements Runnable {    private static final UUID CONNECT_UUID  UUID.fromString("0000110100001000800000805F9B34FB");
为什么mysql不推荐使用雪花ID作为主键
作者:毛辰飞背景在mysql中设计表的时候,mysql官方推荐不要使用uuid或者不连续不重复的雪花id(long形且唯一),而是推荐连续自增的主键id,官方的推荐是auto_increment,那么为什么不建议采用uuid,使用uuid究
Python进阶者 Python进阶者
11个月前
Excel中这日期老是出来00:00:00,怎么用Pandas把这个去除
大家好,我是皮皮。一、前言前几天在Python白银交流群【上海新年人】问了一个Pandas数据筛选的问题。问题如下:这日期老是出来00:00:00,怎么把这个去除。二、实现过程后来【论草莓如何成为冻干莓】给了一个思路和代码如下:pd.toexcel之前把这