Передача аргументов командной строки Spark-shell
У меня есть искра, написанная в scala. Я использую
spark-shell -i <file-name>
чтобы выполнить задание. Мне нужно передать аргумент командной строки для задания. Прямо сейчас я вызываю script через задачу linux, где я делаю
export INPUT_DATE=2015/04/27
и используйте параметр переменной среды для доступа к значению с помощью:
System.getenv("INPUT_DATE")
Есть ли лучший способ обработать аргументы командной строки в Spark-shell?
Ответы
Ответ 1
Краткий ответ:
spark-shell -i <(echo val theDate = $INPUT_DATE ; cat <file-name>)
Длинный ответ:
Это решение вызывает добавление следующей строки в начале файла перед передачей spark-submit
:
val theDate = ...
,
тем самым определяя новую переменную. То, как это делается (синтаксис <( ... )
), называется заменой процесса. Он доступен в Bash. Подробнее см. этот вопрос и для альтернатив (например, mkFifo
) для сред Bash.
Сделать это более систематическим:
Поместите код ниже в script (например, spark-script.sh
), а затем вы можете просто использовать:
./spark-script.sh your_file.scala first_arg second_arg third_arg
,
и args
с вашими аргументами.
Файл spark-script.sh
:
scala_file=$1
shift 1
[email protected]
#set +o posix # to enable process substitution when not running on bash
spark-shell --master yarn --deploy-mode client \
--queue default \
--driver-memory 2G --executor-memory 4G \
--num-executors 10 \
-i <(echo 'val args = "'$arguments'".split("\\s+")' ; cat $scala_file)
Ответ 2
Мое решение использует настраиваемый ключ для определения аргументов вместо spark.driver.extraJavaOptions
, если когда-нибудь вы передадите значение, которое может повлиять на поведение JVM.
spark-shell -i your_script.scala --conf spark.driver.args="arg1 arg2 arg3"
Вы можете получить доступ к аргументам из вашего кода scala следующим образом:
val args = sc.getConf.get("spark.driver.args").split("\\s+")
args: Array[String] = Array(arg1, arg2, arg3)
Ответ 3
Я использую extraJavaOptions
, когда у меня есть scala script, который слишком прост для прохождения процесса сборки, но мне все равно нужно передать ему аргументы. Это не красиво, но оно работает, и вы можете быстро передать несколько аргументов:
spark-shell -i your_script.scala --conf spark.driver.extraJavaOptions="-Darg1,arg2,arg3"
Обратите внимание, что -D
не принадлежит аргументам, которые являются arg1
, arg2
и arg3
. Затем вы можете получить доступ к аргументам из вашего кода scala следующим образом:
val sconf = new SparkConf()
val paramsString = sconf.get("spark.driver.extraJavaOptions")
val paramsSlice = paramsString.slice(2,paramsString.length)
val paramsArray = paramsSlice.split(",")
val arg1 = paramsArray(0)
Во второй строке вы загружаете строку, в третьей строке вы обрезаете -D
, а в четвертой строке вы разделите строку с помощью ,
как разделитель и сохраните результат в массиве. Затем вы можете получить доступ к параметрам, как в пятой строке.