在纱线

时间:2018-04-10 16:01:23

标签: amazon-web-services apache-spark yarn amazon-emr

我有多个spark提交作业,需要作为AWS EMR集群上的Step提交,我的步骤的数据输入对于所有步骤都是相同的,这些步骤当前位于S3存储桶中,输出也在s3上,并且所有步骤都需要并行执行。

目前AWS EMR不支持spark-submit的并行执行,但有一种方法是通过将EMR的YARN调度程序更改为FAIR Scheduler,但这种方法的问题是我们需要为执行程序手动定义Cores / Memory是一个开销。

在AWS EMR中搜索处理此方案的最佳方法,任何建议????

谢谢, -Jack

1 个答案:

答案 0 :(得分:7)

  

目前,AWS EMR不支持并行执行spark-submit

实际上它受到支持但有点棘手。这有两个主要问题,每个Spark作业使用的执行程序数和主节点上驱动程序进程的内存量。

如果你事先知道同时执行spark-submits的最大数量(N),你可以使用--driver-memory, - num-executors, - executor-cores和--executor-memory参数来确保每个作业只占用可用资源的1 / N(如果可以等到提交的作业完成,则可以更多)。如果在实践中很少发生这种并行执行,那么效率非常低。

更好的方法是使用动态分配: https://spark.apache.org/docs/latest/configuration.html#dynamic-allocation

可以使用的参数很少,但是当没有其他作业正在运行时,它将允许单个作业利用几乎所有可用资源(如果maxExecutors是spark.dynamicAllocation.maxExecutors是给定集合的最大可用执行程序数)参数)并且如果多个正在运行,则回退到在作业之间均匀地共享执行者。虽然正在运行的任务不会中断,但这种重新平衡不会立即发生。此外,为此,所有spark-submit调用都必须使用动态分配。如果其中一个spark-submit调用不使用动态分配,它仍然可以获取所有资源并使剩余的Spark作业挨饿。

以下是动态分配参数的示例:

spark-submit \
    --deploy-mode client \
    --master yarn \
    --conf spark.dynamicAllocation.enabled=true \
    --conf spark.shuffle.service.enabled=true \
    --conf spark.dynamicAllocation.executorIdleTimeout=60s \
    --conf spark.dynamicAllocation.cachedExecutorIdleTimeout=60s \
    --conf spark.dynamicAllocation.minExecutors=1 \
    --conf spark.dynamicAllocation.maxExecutors=4 \
    --conf spark.dynamicAllocation.initialExecutors=1 \
    <other Spark options>

对于具有8个节点的群集:

  • 1个工作 - 4个遗嘱执行人
  • 2个工作 - 每个
  • 4个执行者
  • 3个工作 - 每个
  • 2-3个执行者
  • 4个作业 - 每个
  • 执行2个作业
  • 5-8个工作 - 每个
  • 1-2个执行者
  • 超过8个工作 - 一些工作要等待,其余工作将分别获得1个执行者。

FAIR调度也可以工作,它允许比动态分配更好地利用集群资源(因为它不会等到executorIdleTimeout或cachedExecutorIdleTimeout到期)但它只适用于同一Spark App中不同线程发起的多个并行作业(在同一个SparkContext中):https://spark.apache.org/docs/latest/job-scheduling.html

启用此功能可能需要进行一些应用程序架构更改。例如。该应用程序可以从队列中读取处理请求或公开Web服务以接收它们。