Spark 2.1.1和Typesafe Config的配合使用

3

我正在尝试使用typesafeconfig支持我的Spark应用程序的一些外部配置文件。

我正在像这样在我的应用程序代码(driver)中加载application.conf文件:

val config = ConfigFactory.load()
val myProp = config.getString("app.property")
val df = spark.read.avro(myProp)

application.conf的格式如下:

app.propety="some value"

spark-submit的执行方式如下:

spark-submit 
        --class com.myapp.Main \
        --conf spark.shuffle.service.enabled=true \
        --conf spark.dynamicAllocation.enabled=true \
        --conf spark.dynamicAllocation.minExecutors=56 \
        --conf spark.dynamicAllocation.maxExecutors=1000 \
        --driver-class-path $HOME/conf/*.conf \
        --files $HOME/conf/application.conf \
        my-app-0.0.1-SNAPSHOT.jar

看起来它不起作用,我得到了以下结果:

Exception in thread "main" com.typesafe.config.ConfigException$Missing: No configuration setting found for key 'app'
    at com.typesafe.config.impl.SimpleConfig.findKey(SimpleConfig.java:124)
    at com.typesafe.config.impl.SimpleConfig.find(SimpleConfig.java:147)
    at com.typesafe.config.impl.SimpleConfig.find(SimpleConfig.java:159)
    at com.typesafe.config.impl.SimpleConfig.find(SimpleConfig.java:164)
    at com.typesafe.config.impl.SimpleConfig.getString(SimpleConfig.java:206)
    at com.paypal.cfs.fpti.Main$.main(Main.scala:42)
    at com.paypal.cfs.fpti.Main.main(Main.scala)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at java.lang.reflect.Method.invoke(Method.java:498)
    at org.apache.spark.deploy.SparkSubmit$.org$apache$spark$deploy$SparkSubmit$$runMain(SparkSubmit.scala:750)
    at org.apache.spark.deploy.SparkSubmit$.doRunMain$1(SparkSubmit.scala:187)
    at org.apache.spark.deploy.SparkSubmit$.submit(SparkSubmit.scala:212)
    at org.apache.spark.deploy.SparkSubmit$.main(SparkSubmit.scala:126)
    at org.apache.spark.deploy.SparkSubmit.main(SparkSubmit.scala)

查看日志,我发现"--files"有效,似乎是类路径问题...

18/03/13 01:08:30 INFO SparkContext: Added file file:/home/user/conf/application.conf at file:/home/user/conf/application.conf with timestamp 1520928510820
18/03/13 01:08:30 INFO Utils: Copying /home/user/conf/application.conf to /tmp/spark-2938fde1-fa4a-47af-8dc6-1c54b5e89d48/userFiles-c2cec57f-18c8-491d-8679-df7e7da45e05/application.conf

当我使用--conf spark.driver.extraJavaOptions="-Dapp.property=/some/path"时,它可以工作。只是不确定如何让它从我的文件中读取。 - Maayan
2个回答

2
原来我离答案很近...以下是我的解决方法:
spark-submit \
    --class com.myapp.Main \
    --conf spark.shuffle.service.enabled=true \
    --conf spark.dynamicAllocation.enabled=true \
    --conf spark.dynamicAllocation.minExecutors=56 \
    --conf spark.dynamicAllocation.maxExecutors=1000 \
    --driver-class-path $APP_HOME/conf \
    --files $APP_HOME/conf/application.conf \
    $APP_HOME/my-app-0.0.1-SNAPSHOT.jar

那么$APP_HOME将包含以下内容:

conf/application.conf
my-app-0.0.1-SNAPSHOT.jar

我猜你需要确保application.conf文件放在一个文件夹中,这就是诀窍。


0
为了指定配置文件路径,您可以将其作为应用程序参数传递,然后从主类的args变量中读取。
这是您执行spark-submit命令的方式。请注意,我已在应用程序jar之后指定了配置文件。
spark-submit 
        --class com.myapp.Main \
        --conf spark.shuffle.service.enabled=true \
        --conf spark.dynamicAllocation.enabled=true \
        --conf spark.dynamicAllocation.minExecutors=56 \
        --conf spark.dynamicAllocation.maxExecutors=1000 \
        my-app-0.0.1-SNAPSHOT.jar $HOME/conf/application.conf

然后,从指定在args(0)中的路径加载配置文件:

import com.typesafe.config.ConfigFactory
[...]
val dbconfig = ConfigFactory.parseFile(new File(args(0))

现在您可以访问您的 application.conf 文件的属性。
val myProp = config.getString("app.property")

希望能有所帮助。


谢谢,但这个解决方案不太好。感觉像是一个权宜之计。 - Maayan

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接