更新时间:2024-07-19 GMT+08:00

单表并发控制

默认情况下Hudi不支持单表并发写和Compaction操作,在使用Flink、Spark引擎进行数据写入以及使用Spark引擎进行Compaction操作时,会先尝试获取锁对应的锁(集群内Zookeeper提供分布式锁服务,并自动配置生效),如果获取失败则任务直接退出,以防止所任务并发操作表时导致表损坏。如果开启Hudi单表并发写功能,则上述功能自动失效。

Hudi单表并发写实现方案

  1. 使用外部服务(Zookeeper/Hive MetaStore)作为分布式互斥锁服务。
  2. 允许并发写入文件,但是不允许并发提交commit,提交commit操作封装到事务中。
  3. 提交commit时,执行冲突检查:若本次提交的commit中,修改的文件列表,与本次instanceTime之后的commit存在重叠文件,则提交失败,本次写入无效。

使用并发机制需要注意问题

  1. Hudi当前并发机制无法保证写入后表主键唯一, 这个需要用户自己来保证。
  2. 增量查询问题:数据消费以及Checkpoint可能会乱序,多个并发写操作在不同的时间点完成。
  3. 并发写需要在启用并发写特性后支持并发,未开启时不支持并发写入。

如何使用并发机制

  1. 启用并发写入机制。

    hoodie.write.concurrency.mode=optimistic_concurrency_control

    hoodie.cleaner.policy.failed.writes=LAZY

  2. 设置并发锁方式。

    Hive MetaStore:

    hoodie.write.lock.provider=org.apache.hudi.hive.HiveMetastoreBasedLockProvider

    hoodie.write.lock.hivemetastore.database=<database_name>

    hoodie.write.lock.hivemetastore.table=<table_name>

    Zookeeper:

    hoodie.write.lock.provider=org.apache.hudi.client.transaction.lock.ZookeeperBasedLockProvider

    hoodie.write.lock.zookeeper.url=<zookeeper_url>

    hoodie.write.lock.zookeeper.port=<zookeeper_port>

    hoodie.write.lock.zookeeper.lock_key=<table_name>

    hoodie.write.lock.zookeeper.base_path=<table_path>

更多配置参数请参考配置参考

当设置cleaner policy为Lazy时,本次写入仅能关注到自己写入的文件是否过期,不能检查并清理历史写入产生的垃圾文件,即在并发场景下,无法自动清理垃圾文件。