趣解 ceph rgw multisite data sync 机制
multisite是ceph rgw对象数据异地容灾备份的一个有效方案,笔者希望深入理解该技术,并应用于生产环境中,然而rgw的这部分代码晦涩难懂,笔者多次尝试阅读,仍云里雾里不解其意,最终流着泪咬着牙坚持多看了几遍,总结出了data sync的流程,这里以通俗易懂的形式呈现出来,希望对大家有所帮助~
数据同步流程图
https://www.cnblogs.com/wangmingshuai/articles/11040979.html

首先,认识下 data sync机制 的三个角色Data、DataLogShard、BucketShard
rgw的multisite同步分为两部分:metadata数据同步 和 data数据同步。metadata数据包括bucket信息、bucket instance信息、user信息等;data数据指的是存储的对象的实际数据,即Data。本文仅涉及data数据的同步。
rgw使用datalog来记录Data的变化,为防止datalog成为瓶颈,将datalog分成了${rgw_data_log_num_shards}个shard,即DataLogShard。所有的 DataLogShard 的数据变化就反应了Data的变化。
rgw使用bucket index来提升list对象的效率。为防止bucket index成为瓶颈,将bucket分成了${rgw_override_bucket_index_max_shards}个shard,即BucketShard。每个BucketShard的bucket index log记录了该BucketShard对象的变化。
rgw的每个BucketShard都会通过hash映射到某个DataLogShard上,形成了如下形式的映射关系。理解映射关系是理解data sync的重要前提。
DataLogShard ... : ...
DataLogShard 12 : bucket_a:0、bucket_b:3
DataLogShard 13 : bucket_a:4、bucket_b:7、bucket_c:5 ...
DataLogShard ... : ...
当某个BucketShard的数据发生变化时,对应的DataLogShard的datalog会记录哪个BucketShard发送了数据表更。
咳咳,讲完data sync的三个角色,下面切入主题讲讲data sync的故事
data sync的目标是将 源头rgw Data 都同步到 目标rgw 中。话不多说,系好安全带,老司机直接带你走一遭data sync流程。
故事是这样的,北京rgw想要开拓上海的市场,于是派DataSync去上海创建rgw并负责把北京rgw的数据资源同步到上海rgw,即data sync(北京rgw -> 上海rgw)。
老大DataSync到达上海,来掌控整个data sync流程的进度。前面说了,所有的DataLogShard的变化即反应了rgw Data的变化。老大DataSync决定招聘${rgw_data_log_num_shards}个 小弟DataLogShardSync 来负责将北京rgw中的数据同步到上海rgw,每个小弟负责北京rgw的一个DataLogShard。老大DataSync懂得,数据同步不是一蹴而就的,他只有记录下同步的进度来,才能防止意外的同步失败而导致需要从头开始数据同步。
于是老大DataSync用名为rgw_data_sync_info的记录来规划了他第一阶段工作为StateInit,并记录了他有${rgw_data_log_num_shards}个小弟DataLogShardSync要进行数据同步。
struct rgw_data_sync_info { uint16_t state; uint32_t num_shards;}
① 老大DataSync::StateInit:
老大DataSync需要给他num_shards个小弟DataLogShardSync设定KPI,毫无疑问,小弟DataLogShardSync的目标是赶上北京rgw的数据更新进度,老大DataSync打电话问北京rgw各个DataLogShard数据的最新marker记录成小弟的next_step_marker,并记录各个小弟DataLogShardSync的同步状态为FullSync,整理到rgw_data_sync_marker中 。
struct rgw_data_sync_marker {uint16_t state; string next_step_marker;}
老大DataSync将自己的工作进度(rgw_data_sync_info )和直属小弟的工作进度(rgw_data_sync_marker)都记录了下来到了rgw_data_sync_status中。
struct rgw_data_sync_status {
rgw_data_sync_info sync_info; // 记录data sync的整体同步进度
map sync_markers; // 记录每个DataLogShard的同步进度
}
这样,老大DataSync做完了第一阶段StateInit的工作,规划做下一阶段StateBuildingFullSyncMaps的工作。
② 老大DataSync::StateBuildingFullSyncMaps:
老大DataSync说,北京rgw的datalog会进行截断,如果通过datalog来同步数据到上海rgw,会导致一些数据同步不过来,所以需要进行下FullSync。而进行FullSync就是将小弟DataLogShardSync都管辖着的各个小喽啰BucketShard中的对象逐一list出来,然后从北京rgw传输到上海rgw。因为需要知道小弟DataLogShardSync分别管辖着哪些小喽啰BucketShard。老大打电话问了北京rgw,并将这些信息(每个DataLogShard下有哪些BucketShard)记录下来。
这样,老大DataSync做完了第二阶段StateBuildingFullSyncMaps的工作,规划下一阶段StateSync的工作。
③ 老大DataSync::StateSync:
老大在这个阶段的主要工作是,监督小弟工作,老大前面已经规划了小弟的第一阶段工作是FullSync,小弟DataLogShardSync于是开始按部就班的工作。
④ 小弟DataLogShardSync::FullSync:
小弟DataLogShardSync作为中层干部,需要管理下属的各个小喽啰BucketShardSync,使用rgw_bucket_shard_sync_info来记录下属的每个小喽啰的工作情况。
struct rgw_bucket_shard_sync_info {
uint16_t state;
rgw_bucket_shard_full_sync_marker full_marker;
rgw_bucket_shard_inc_sync_marker inc_marker;
}
同样地,小弟DataLogShardSync需要给下属的各个小喽啰BucketShardSync安排工作。小弟将小喽啰BucketShardSync的第一个阶段工作设定为StateInit。嗯,小弟的工作完成了,真简单,轮到小喽啰干活了。
⑤ 小喽啰BucketShardSync::StateInit:
虽然小弟没有给下属小喽啰设定KPI,但小喽啰BucketShardSync很自觉,自己打电话给北京rgw问到了其对应的BucketShard的最新marker,然后记录到自己的rgw_bucket_shard_sync_info的inc_marker中。意思是,要先full sync(全量同步)到这个marker,然后从这个marker开始inc sync(增量同步)。
这样,小喽啰的第一阶段工作完成了,准备进入下一阶段StateFullSync。
⑥ 小喽啰BucketShardSync::StateFullSync:
在这个阶段,小喽啰会批量从北京rgw查询其对应的BucketShard中的对象,同步到上海rgw,并持续更新full_marker,直到自己的rgw_bucket_shard_sync_info的inc_marker。结束后,小喽啰规划进行下一阶段工作为StateIncrementalSync。
嗯哼,full sync(全量同步)结束,进入inc sync(增量同步阶段)。
⑦ 小弟DataLogShardSync::IncrementalSync:
进行完full sync,终于可以根据datalog的变化来inc sync了。打电话问问北京rgw自从上次同步点,有哪些下属小喽啰BucketShardSync对应的BucketShard发生数据变更。然后,安排这些小喽啰单独进行工作。
⑧ 小喽啰BucketShardSync::StateIncrementalSync:
小喽啰打电话到北京rgw,问从自己的inc_marker开始,有什么新的数据变更,然后根据数据变更来同步数据。
至此,data sync的故事讲完了...
故事太长都忘了?来个简易版:
老大DataSync::StateInit:
更新各个DataLogShard的同步目标为北京rgw的各个DataLogShard的最新marker
老大DataSync::StateBuildingFullSyncMaps:
记录各个DataLogShard下有哪些BucketShard
老大DataSync::StateSync:
安排小弟干活
小弟DataLogShardSync::FullSync:
安排小喽啰干活
小喽啰BucketShardSync::StateInit:
更新自己的同步目标为北京rgw对应BucketShard的最新marker
小喽啰BucketShardSync::StateFullSync :
干活干到自己的目标
小弟DataLogShardSync::IncrementalSync:
根据北京rgw的DataLogShard的更新情况,继续安排小喽啰干活
小喽啰BucketShardSync::StateIncrementalSync:
根据北京rgw的对应BucketShard的更新情况,继续干活
友情出演:
老大DataSync:
控制着整个data sync流程的同步进度。标识进度的状态有三个:StateInit、StateBuildingFullSyncMaps、StateSync。
小弟DataLogShardSync:
控制着一个DataLogShard的同步进度。标识进度的状态有两个:FullSync、IncrementalSync。
小喽啰BucketShardSync:
控制着一个BucketShard的同步进度。标识进度的状态有三个:StateInit、StateFullSync 、StateIncrementalSync。
番外篇:
上海rgw的所有工作人员集体出走了,上海rgw新招了一堆新人,如果保持数据同步呢?新人根据rgw_data_sync_info获知rgw data sync的进度为StateSync,然后根据rgw_data_sync_marker获知各个DataLogShard的同步状态为IncrementalSync,然后根据rgw_bucket_shard_sync_info的获知各个BucketShard的同步进度为StateIncrementalSync。于是,轻松交接工作,继续干活同步数据,即
DataSync::StateSync -> DataLogShardSync::IncrementalSync -> BucketShardSync::StateIncrementalSync
同步流程图
https://www.cnblogs.com/wangmingshuai/articles/11040979.html
关注笔者
专注笔者公众号,阅读更多干货文章:)

趣解 ceph rgw multisite data sync 机制的更多相关文章
- ceph rgw multisite基本用法
Realm: Zonegroup: 理解为数据中心,由一个或多个Zone组成,每个Realm有且仅有 一个Master Zonegroup,用于处理系统变更,其他的称为Slave Zonegroup, ...
- Ceph RGW Multisite 数据同步流程图
- Ceph RGW 创建默认的pool
使用Ceph-deploy完成RGW服务部署后(最好是在部署RGW服务前建立如下这些pool),使用sudo ceph osd lspools 命令,会发现RGW自动以默认参数创建了N个rgw相关的p ...
- 图文详解 Android Binder跨进程通信机制 原理
图文详解 Android Binder跨进程通信机制 原理 目录 目录 1. Binder到底是什么? 中文即 粘合剂,意思为粘合了两个不同的进程 网上有很多对Binder的定义,但都说不清楚:Bin ...
- Java集合详解3:Iterator,fail-fast机制与比较器
Java集合详解3:Iterator,fail-fast机制与比较器 今天我们来探索一下LIterator,fail-fast机制与比较器的源码. 具体代码在我的GitHub中可以找到 https:/ ...
- 010 Ceph RGW对象存储
一.对象存储 1.1 介绍 通过对象存储,将数据存储为对象,每个对象除了包含数据,还包含数据自身的元数据 对象通过Object ID来检索,无法通过普通文件系统操作来直接访问对象,只能通过API来访问 ...
- Download SymmetricDS Data Sync Software for Free
Download SymmetricDS Data Sync Software for Free Download SymmetricDS
- CEPH RGW 设置 user default_placement为ssd-placement,优化100KB-200KB小文件性能,使用户创建的bucket对象放置到 SSD设备的Pool上。
sudo radosgw-admin metadata get user:tuanzi > user.md.json vi user.md.json #to add ssd-placement ...
- [Windows Azure] Getting Started with Windows Azure SQL Data Sync
Getting Started with Windows Azure SQL Data Sync In this tutorial, you learn the fundamentals of Win ...
随机推荐
- AABB边框、OBB边框、通过比较球包围
1) AABB 包围盒: AABB 包围盒是与坐标轴对齐的包围盒, 简单性好, 紧密性较差(尤其对斜对角方向放置的瘦长形对象, 採用AABB, 将留下非常大的边角空隙, 导致大量不是必需的包围盒相交測 ...
- 张汝京:CIDM模式进可攻、退可守,建议尝试
飞象网讯(路金娣/文)大约30多年前一些美国.日本和欧洲的IDM半导体工厂把多余的产能出来做代工服务,因为代工的公司不会与客户竞争,所以专业代工的模式成为半导体市场的新宠.那么,究竟国内半导体行业更加 ...
- Matlab随笔之插值与拟合(下)
原文:Matlab随笔之插值与拟合(下) 1.二维插值之插值节点为网格节点 已知m x n个节点:(xi,yj,zij)(i=1…m,j=1…n),且xi,yi递增.求(x,y)处的插值z. Matl ...
- [转]TensorFlow如何进行时序预测
TensorFlow 是一个采用数据流图(data flow graphs),用于数值计算的开源软件库.节点(Nodes)在图中表示数学操作,图中的线(edges)则表示在节点间相互联系的多维数据数组 ...
- 数据绑定(四)使用DataContext作为Binding的Source
原文:数据绑定(四)使用DataContext作为Binding的Source DataContext属性被定义在FrameworkElement类里,这个类是WPF控件的基类,这意味着所有WPF控件 ...
- 【转】python Counter模块
>>> c = Counter() # 创建一个新的空counter >>> c = Counter('abcasdf') # 一个迭代对象生成的counter & ...
- 管道通信实例(A程序作为服务器,不断从B程序接收数据,并发送到C程序中)
A程序作为服务器,不断从B程序接收数据,并发送到C程序中:#include <stdio.h>#include <conio.h> #include <tchar.h&g ...
- HOLLOW_BRUSH等价于NULL_BRUSH,都代表透明化刷
NULL_BRUSH 或HOLLOW_BRUSH和GetStockObject函数 备注:HOLLOW_BRUSH等价于NULL_BRUSH,都代表透明化刷 HGDIOBJ GetStockObjec ...
- Windows Mount NFS Share from e.g. Linux
Note: Not Stable, so steps below are for reference only ************ Linux Configuration NFS Share 1 ...
- Qt4.85静态编译配置VS动态编译(非常详细的图文教程)
http://www.qter.org/forum.php?mod=viewthread&tid=1409&extra=page%3D1&page=1