使用Apache Spark多次插入表中

时间:2017-10-26 13:57:02

标签: hadoop apache-spark bigdata phoenix

我正在开展一个项目,我仍然坚持以下方案。

我有一张桌子:superMerge(id,name,salary)

我还有另外两个表:table1和table2

所有表(table1,table2和superMerge)具有相同的结构。

现在,我的挑战是从table1和table2插入/更新superMerge表。 table1每10分钟更新一次,table2每20分钟更新一次,因此在时间t = 20分钟我有2个工作试图更新同一个表(在这种情况下是superMerge。)

我想了解如何使用Spark或任何其他hadoop应用程序将此并行插入/更新/合并到superMerge表中。

4 个答案:

答案 0 :(得分:5)

这里的问题是这两个工作无法相互沟通,不知道对方在做什么。一个相对简单的解决方案是实现基于文件的基本“锁定”系统:

  • 每个作业在HDFS上的特定文件夹中创建一个(空)文件,指示更新/插入正在进行中并在作业完成时删除该文件

  • 现在,每个作业必须在开始更新/插入之前检查是否存在此类文件。如果存在,作业必须等到文件消失。

答案 1 :(得分:1)

你能控制job1&的代码吗?作业2?你如何安排这些?

通常,您可以将这两个作业转换为每10分钟运行一次的作业。一旦在20分钟内,这个统一的作业以不同的模式运行(从2个表合并),而默认模式将仅从1个表合并。 因此,当您拥有相同的驱动程序时 - 您不需要在两个作业之间进行任何同步(例如锁定)。该解决方案假设工作在10分钟内完成。

答案 2 :(得分:1)

您的数据集有多大?您打算在批处理(Spark)中执行此操作,还是可以流式插入/更新(Spark Streaming)?

让我们假设您想要批量执行此操作:

  • 每10分钟只启动一个可处理两个表的作业。如果你有表1和表2做一个联盟并加入superMerge。正如伊戈尔伯曼所说的那样。
  • 小心你的superMerge表会变大,你的加入时间会更长。

答案 3 :(得分:0)

我遇到了这种情况,将tb1 DF1写入location1,将tb2 DF2写入位置2,最后只需将路径切换到超级合并表,也可以将表格插入表格插入,但这会占用很多特别是在蜂巢中运行时间。

覆盖到登台位置location1和位置2:

df1.write.mode("overwrite").partitionBy("partition").parquet(location1)

df2.write.mode("overwrite").partitionBy("partition").parquet(location2)

切换到超级合并表的路径:

hiveContext.sql(alter table super_merge_table add if not exists partition(partition=x); LOAD DATA INPATH 'location1/partition=x/' INTO TABLE super_merge_table  partition(partition=x))"

hiveContext.sql(alter table super_merge_table add if not exists partition(partition=x); LOAD DATA INPATH 'location2/partition=x/' INTO TABLE super_merge_table  partition(partition=x))"

您可以执行并行合并而不会覆盖其他合并。