GC的疑问

《分布式数据库TiDB》书中29页最后有段话:为了确保持续时间较长的事务在超过GC过期时间后仍能正常运行,safe point不会超过正在执行中事务的开始时间(start_ts)。
这句话是指长事务会导致所有表延迟进行垃圾数据清理吗?
另外生产环境如果设置清理间隔为1天的话,假如有10张表有很多的垃圾数据,清理时是并行还是串行?有没有机制控制对IO的影响?

这句话的意思是不影响正在执行的事务,其他没有事务的表会正常GC
GC默认是并发进行的,由 tidb_gc_concurrency参数控制

TiDB的GC清理过程是并行的,不会导致所有表延迟垃圾数据清理; TiDB支持GC流控,通过配置gc.max-write-bytes-per-sec限制GC worker每秒数据写入量,值设置为0时,关闭该功能。

1 个赞

会导致整个集群的 GC 延迟,而不是单表。

原因是 TiDB 使用 全局 Safe Point。

GC 的逻辑是:

PD 会维护一个 GC safe point(全局时间戳)

TiKV 只能清理 commit_ts < safe point 的旧版本

如果存在一个长事务:

start_ts = T1

那么:

safe point <= T1

1 个赞

TiDB GC 是分布式并行执行的,不是串行。

TiDB 3.0 以后默认使用 Distributed GC。

GC流程:

:one: PD / GC Leader

只负责:

计算 safe point
更新到 PD

:two: 每个 TiKV 节点

自主执行 GC:

扫描本节点 Region Leader
删除旧版本

所以并行度是:

TiKV节点数 × Region数量

假设:

3 TiKV
每个 TiKV 1000 Region

GC时:

3000 Region 并行处理

不是:

表1 → 表2 → 表3

也不是:

Region1 → Region2 → Region3

而是:

Region 并行 GC

所以即使:

10张表都有很多垃圾

也会:

多节点并行 GC

1 个赞

清理默认是并行的,TiDB 提供多层机制限制 GC 的 IO 与 CPU 开销

如果允许gc删除当前正在执行的事务运行的快照,那么就违反了事务隔离性了啊

TiDB 的 GC safe point 是一个时间戳门槛,早于这个时间戳的所有数据版本都会被清理。

是的,另外gc是并行的

GC应该是可以多个节点执行gc的

在 TiDB 6.1.0 之前的版本中,TiDB 内部事务不会影响 GC safe point 推进。从 TiDB 6.1.0 版本起,计算 safe point 时会考虑内部事务的 startTS,从而解决内部事务因访问的数据被清理掉而导致失败的问题。带来的负面影响是如果内部事务运行时间过长,会导致 safe point 长时间不推进,进而会影响业务性能。

TiDB v6.1.0 引入了系统变量 tidb_gc_max_wait_time 控制活跃事务阻塞 GC safe point 推进的最长时间,超过该值后 GC safe point 会强制向后推进。

实际生产环境如果有长事务这个机制会导致MVCC失败吗?

只是会导致gc回收不了历史版本数据吧

这里说的强制向后推进没明白什么意思?我理解要么就是MVCC版本被清理,要么就是历史数据不会被清理了。

学习了

就是正常的推进,回收已经提交的事务的历史版本

如果活跃事务的时间没有超过 [tidb_gc_max_wait_time]的时间,那gc就会一直等,如果超过了,gc safe point就会正常推进,大概就是这么个意思

因为gc safe point也不可能一直等下去,历史版本数据长时间不回收,会带来很多其他问题

gc不影响mvcc

mvcc应该是事务特征里必须具备的,否则就不满足事务隔离性了啊