集群部署模式下的 spark-submit 将应用程序 ID 获取到控制台

spark-submit in cluster deploy mode get application id to console

我遇到了一个需要快速解决的问题。我浏览了很多关于 spark 集群部署模式的帖子和教程,但我对这种方法一无所知,因为我被困了几天。

我的用例:- 我有很多使用 'spark2-submit' 命令提交的 spark 作业,一旦提交,我需要在控制台中打印应用程序 ID。 spark 作业是使用集群部署模式提交的。 (在普通客户端模式下,它被打印出来)

创建解决方案时我需要考虑的要点:- 我不应该更改代码(因为这会花费很长时间,因为有很多应用程序 运行),我只能提供 log4j 属性或一些自定义编码。

我的做法:-

1) 我已经尝试更改 log4j 级别和各种 log4j 参数,但日志记录仍然转到集中日志目录。

我的log4j.properties部分:-

log4j.logger.org.apache.spark.scheduler.cluster.YarnClusterSchedulerBackend=ALL,console
log4j.appender.org.apache.spark.scheduler.cluster.YarnClusterSchedulerBackend.Target=System.out

log4j.logger.org.apache.spark.deploy.SparkSubmit=ALL
log4j.appender.org.apache.spark.deploy.SparkSubmit=console

log4j.logger.org.apache.spark.deploy.SparkSubmit=TRACE,console
log4j.additivity.org.apache.spark.deploy.SparkSubmit=false

log4j.logger.org.apache.spark.deploy.yarn.Client=ALL
log4j.appender.org.apache.spark.deploy.yarn.Client=console


log4j.logger.org.apache.spark.SparkContext=WARN
log4j.logger.org.apache.spark.scheduler.DAGScheduler=INFO,console

log4j.logger.org.apache.hadoop.ipc.Client=ALL

2) 我还尝试添加自定义侦听器,并且我能够在应用程序完成后获取 spark 应用程序 ID,但无法获取控制台。

代码逻辑:-

public void onApplicationEnd(SparkListenerApplicationEnd arg0) 
    {
         for (Thread t : Thread.getAllStackTraces().keySet()) 
         {
            if (t.getName().equals("main"))
            {
                System.out.println("The current state : "+t.getState());

                Configuration config = new Configuration();

                ApplicationId appId = ConverterUtils.toApplicationId(getjobUId);

                // some logic to write to communicate with the main thread to print the app id to console.
            }
         }
    }

3) 我已启用 spark.eventLog 为 true 并在 HDFS 中指定了一个目录以从 spark-submit 命令写入事件日志。

如果有人能帮助我找到解决方法,那将非常有帮助。或者,如果我做错了什么,任何见解都会对我有所帮助。

谢谢。

澄清一下:

  1. client mode 表示 Spark 驱动程序 运行ning 在您 运行 从
  2. 提交 spark 的同一台机器上
  3. cluster mode 表示 Spark 驱动程序 运行 在集群的某个地方

您提到当您在 客户端 模式下 运行 应用程序时,它会被记录下来,您可以在控制台中看到它。当您在 集群 模式下 运行 时,您的输出也会被记录,您 只是看不到它 因为它是 运行在 不同的 机器上。

一些想法:

  • 将来自工作节点的日志聚合到一个地方,您可以在其中解析它们以获取应用程序 ID。
  • 将 appID 写入一些共享位置,如 HDFS 或数据库。如果您想保留 log4j,您可以使用 Log4j appender

在同一个地方卡了几天后,我终于找到了解决问题的方法。

在浏览了集群部署模式的 Spark 代码和一些博客之后,几乎没有什么事情弄清楚了。它可能会帮助其他寻求相同结果的人。

在集群部署模式下,作业是通过用户提交计算机的客户端线程提交的。实际上我正在将 log4j 配置传递给驱动程序和执行程序,但错过了 "Client" 的 log4j 配置丢失的部分。

所以我们需要使用:-

SPARK_SUBMIT_OPTS="-Dlog4j.debug=true -Dlog4j.configuration=<location>/log4j.properties" 火花提交 <rest of the parameters>