HBase之写入数据流程

目录

1.HBase写入数据流程

2.疑问

2.1上述(8)中,数据写入到HLog时,实际上在这个时刻只是写入文件系统的缓存中,并没有真正的落地到磁盘中,那什么时候落地到磁盘中呢?


1.HBase写入数据流程

(1)Client向服务端发起Put请求。默认情况下,autoflush=true,所以每发送一个Put请求,就会直接发送到服务端。当autoflush=false时,则会将Put缓存到本地buffer中,达到一定阈值之后再一起发送到服务端,提高效率。

(2)当本地buffer size >2M(默认配置下,可以修改)时,开始批量提交Put。此时首先会查看HBase元数据,根据要插入的RowKey寻找对应的RegionServer。通过HConnection的locateRegion方法获得HRegionLocation,并按照RowKey对其进行分组

(3)为每一个HRegionLocation构造一个远程RPC请求,封装成MultiServerCallable

(4)通过rpcCallerFactory. newCaller()发送RPC请求到相应的服务端RegionServer

(5)此时RegionServer接收到请求后,会将Put对象反序列化

(6)对Put执行各种检查操作,例如判断region是否为只读、MemStore大小是否超过设定值等

(7)获取行锁、Region共享锁,开始写事务(实现MVCC)

(8)将数据封装成WALEdit对象,然后顺序写入到HLog中(其实此时只是写入到文件系统的缓存中,还没有真正落地到磁盘),然后释放行锁、共享锁

(9)写入数据到MemStore中

(10)当MemStore size 大于64M之后,会启动flush线程,将数据落地到硬盘中

2.疑问

2.1上述(8)中,数据写入到HLog时,实际上在这个时刻只是写入文件系统的缓存中,并没有真正的落地到磁盘中,那什么时候落地到磁盘中呢?

实际上数据从写入HLog到最终落地到HDFS上经过了如下几步:

(1)当WALEdit对象写入到本地系统的缓存后,会产生一个自增变量txid。且当WALEdit对象全部写入之后,会释放行锁、共享锁。

(2)待WALEdit对象全部写完在之后,负责将WALEdit对象写入到HLog的线程会阻塞在syncedTillHere里面。

(3)待行锁和共享锁释放之后,会携带自增变量txid去唤醒AsyncWriter线程

(4)AsyncWriter线程会将所有在本地buffer中缓存的WALEdit对象写入到HDFS文件系统缓存中(在写入的过程中,AsyncWriter先会对比之前写入的旧的txid,比较传进来的txid是否大于,若小于,则表示已经写入过了,直接跳过)

(5)当AsyncWriter线程将所有的WALEdit对象写入到HDFS文件系统缓存中后,会携带maxTxid去唤醒AsyncFlusher线程

(6)此时AsyncFlusher线程会将所有写入到HDFS文件系统缓存的WALEdit对象全部Sync落地到HDFS上(HFile中)

(7)待WALEdit对象全部落地到HDFS上后,会调用setFlushTxid方法唤醒AsyncNotifier线程

(8)AsyncNotifier线程会唤醒所有阻塞在syncedTillHere的工作线程。所有工作线程被唤醒之后,则表示WAL写入完成

(9)执行MVCC结束写事务

 

你可能感兴趣的:(Hbase)