Поделиться через


Использование JAR-файла в задании Azure Databricks

Архив Java или JAR-файл основан на популярном формате ZIP-файла и используется для агрегирования множества файлов Java или Scala в один. С помощью задачи JAR можно обеспечить быструю и надежную установку кода Java или Scala в заданиях Azure Databricks. В этой статье приведен пример создания JAR-файла и задания, запускающего приложение, упаковаемое в JAR-файл. В этом примере вы будете:

  • Создайте проект JAR, определяющий пример приложения.
  • Упаковайте примеры файлов в JAR-файл.
  • Создайте задание для запуска JAR-файла.
  • Запустите задание и ознакомьтесь с результатами.

Перед началом работы

Для выполнения этого примера вам потребуется следующее:

  • Для java JARs пакет средств разработки Java (JDK).
  • Для Scala JARs, JDK и sbt.

Шаг 1. Создание локального каталога для примера

Создайте локальный каталог для хранения примера кода и созданных артефактов, например databricks_jar_test.

Шаг 2. Создание JAR-файла

Выполните следующие инструкции, чтобы создать JAR-файл с помощью Java или Scala.

Создание JAR-файла Java

  1. В папке databricks_jar_test создайте файл с именем PrintArgs.java со следующим содержимым:

    import java.util.Arrays;
    
    public class PrintArgs {
      public static void main(String[] args) {
        System.out.println(Arrays.toString(args));
      }
    }
    
  2. PrintArgs.java Скомпилируйте файл, создающий файлPrintArgs.class:

    javac PrintArgs.java
    
  3. (Необязательно) Запустите скомпилированную программу:

    java PrintArgs Hello World!
    
    # [Hello, World!]
    
  4. В той же папке, что PrintArgs.java и PrintArgs.class файлы, создайте папку с именем META-INF.

  5. В папке META-INF создайте файл с именем MANIFEST.MF со следующим содержимым. Обязательно добавьте новую строку в конце этого файла:

    Main-Class: PrintArgs
    
  6. В корне databricks_jar_test папки создайте JAR-файл с именем PrintArgs.jar:

    jar cvfm PrintArgs.jar META-INF/MANIFEST.MF *.class
    
  7. (Необязательно) Чтобы проверить его, запустите JAR-файл из корневого databricks_jar_test каталога:

    java -jar PrintArgs.jar Hello World!
    
    # [Hello, World!]
    

    Примечание.

    Если вы get ошибку no main manifest attribute, in PrintArgs.jar, обязательно добавьте новую строку в конец файла MANIFEST.MF, а затем попробуйте создать и запустить JAR-файл еще раз.

  8. Отправка PrintArgs.jar в том. См. загрузку файлов в томе Unity Catalog.

Создание JAR-файла Scala

  1. databricks_jar_test Создайте пустой файл build.sbt из папки со следующим содержимым:

    ThisBuild / scalaVersion := "2.12.14"
    ThisBuild / organization := "com.example"
    
    lazy val PrintArgs = (project in file("."))
      .settings(
        name := "PrintArgs"
      )
    
  2. databricks_jar_test Создайте структуру src/main/scala/exampleпапок из папки.

  3. В папке example создайте файл с именем PrintArgs.scala со следующим содержимым:

    package example
    
    object PrintArgs {
      def main(args: Array[String]): Unit = {
        println(args.mkString(", "))
      }
    }
    
  4. Скомпилируйте программу:

    sbt compile
    
  5. (Необязательно) Запустите скомпилированную программу:

    sbt "run Hello World\!"
    
    # Hello, World!
    
  6. В папке databricks_jar_test/project создайте файл с именем assembly.sbt со следующим содержимым:

    addSbtPlugin("com.eed3si9n" % "sbt-assembly" % "2.0.0")
    
  7. В корневой databricks_jar_test папке выполните assembly команду, которая создает JAR-файл в папке target :

    sbt assembly
    
  8. (Необязательно) Чтобы проверить его, запустите JAR-файл из корневого databricks_jar_test каталога:

    java -jar target/scala-2.12/PrintArgs-assembly-0.1.0-SNAPSHOT.jar Hello World!
    
    # Hello, World!
    
  9. Отправка PrintArgs-assembly-0.1.0-SNAPSHOT.jar в том. См. загрузку файлов на том Catalog Unity.

Шаг 3. Создание задания Azure Databricks для запуска JAR-файла

  1. Перейдите на целевую страницу Azure Databricks и выполните одно из следующих действий:
    • На боковой панели щелкните "Рабочие процессыCreate Job Button" и щелкните .Кнопка
    • На боковой панели щелкните Новый значокСоздать и selectСоздать задание из меню.
  2. В диалоговом окне задачи, которое отображается на вкладке "Задачи ", замените имя задания... например JAR example.
  3. В поле "Имя задачи" введите имя задачи, например java_jar_task Java или scala_jar_task Scala.
  4. Для типа , selectJAR.
  5. Для основного класса в этом примере введите PrintArgs для Java или example.PrintArgs Scala.
  6. Для кластера кластера, совместимый кластер select. Ознакомьтесь с поддержкой библиотеки Java и Scala.
  7. Для зависимых библиотек нажмите кнопку +Добавить.
  8. В диалоговом окне Добавление зависимой библиотеки с выбранным Volumes введите расположение, where отправленное JAR-файл (PrintArgs.jar или PrintArgs-assembly-0.1.0-SNAPSHOT.jar) на предыдущем шаге в Volumes путь к файлуили отфильтруйте или найдите JAR-файл. Select.
  9. Нажмите кнопку Добавить.
  10. Для Parameters, в этом примере, введите ["Hello", "World!"].
  11. Нажмите кнопку Добавить.

Шаг 4. Запуск задания и просмотр сведений о выполнении задания

Щелкните Кнопка , чтобы запустить рабочий процесс. Чтобы просмотреть подробные сведения о выполнении, щелкните Просмотреть выполнение во всплывающем окне выполненного запуска или щелкните ссылку во времени начала column для выполнения в представлении выполнения заданий.

По завершении выполнения выходные данные отображаются на панели вывода , включая аргументы, переданные задаче.

Ограничения размера выходных данных для заданий JAR

Выходные данные задания, такие как выходные данные журнала, созданные в stdout, подвергаются limitразмером 20 МБ. Если общий объем выходных данных имеет больший размер, выполнение отменяется и помечается как завершенное с ошибкой.

Чтобы избежать возникновения этой limit, можно предотвратить возврат stdout из драйвера в Azure Databricks, настроив конфигурацию Spark spark.databricks.driver.disableScalaOutput на true. По умолчанию флаг имеет значение false. Флаг контролирует выходные данные ячейки для заданий JAR Scala и записных книжек Scala. Если флаг включен, Spark не возвращает клиенту результаты выполнения задания. Флаг не влияет на данные, записываемые в файлы журналов кластера. Databricks рекомендует задать этот флаг только для кластеров заданий JAR, так как он отключает результаты записной книжки.

Рекомендация. Использование общего доступа SparkContext

Так как Azure Databricks — это управляемая служба, некоторые изменения кода могут потребоваться для правильного выполнения заданий Apache Spark. Программы задания JAR должны использовать общий API SparkContext для getSparkContext. Поскольку Azure Databricks инициализирует SparkContext, программы, которые вызывают ошибку new SparkContext(), завершаются с ошибкой. Чтобы getSparkContext, используйте только общие SparkContext, созданные Azure Databricks:

val goodSparkContext = SparkContext.getOrCreate()
val goodSparkSession = SparkSession.builder().getOrCreate()

Некоторых методов при использовании общего SparkContext следует избегать.

  • Не вызывайте SparkContext.stop().
  • Не вызывайте System.exit(0) или sc.stop() в конце программы Main. Это может привести к неопределенному поведению.

Рекомендация. Использование try-finally блоков для очистки задания

Возьмем для примера JAR, состоящий из двух частей:

  • jobBody() — содержит основную часть задания;
  • jobCleanup() который должен выполняться после jobBody()того, успешно ли эта функция выполнена или возвращена исключение.

Например, jobBody() создает tables и jobCleanup() удаляет эти tables.

Безопасный способ убедиться, что метод очистки вызывается, заключается в том, чтобы поместить try-finally блок в код:

try {
  jobBody()
} finally {
  jobCleanup()
}

Не пытайтесь использовать для очистки sys.addShutdownHook(jobCleanup) или следующий код:

val cleanupThread = new Thread { override def run = jobCleanup() }
Runtime.getRuntime.addShutdownHook(cleanupThread)

Так как время существования контейнеров Spark управляется в Azure Databricks, перехватчики завершения работы не выполняются надежно.

Настройка JAR-задания parameters

Вы передаете parameters заданиям JAR в виде массива JSON строк. См. объект spark_jar_task в тексте запроса, передаваемый в операцию Создать задачу (POST /jobs/create) в API заданий. Чтобы получить доступ к этим parameters, сначала проверьте массив String, который передается в вашу функцию main.

Управление зависимостями библиотек

Драйвер Spark имеет определенные зависимости библиотек, которые не могут быть переопределены. Если задание добавляет конфликтующие библиотеки, зависимости библиотеки драйверов Spark имеют приоритет.

Чтобы get полную list зависимостей библиотеки драйверов, выполните следующую команду в записной книжке, подключенной к кластеру, настроенному с той же версией Spark (или к кластеру с драйвером, который требуется проверить):

%sh
ls /databricks/jars

При определении зависимостей библиотеки для JAR Databricks рекомендует перечислять Spark и Hadoop в качестве provided зависимостей. В Maven добавьте Spark и Hadoop в качестве указанных зависимостей:

<dependency>
  <groupId>org.apache.spark</groupId>
  <artifactId>spark-core_2.11</artifactId>
  <version>2.3.0</version>
  <scope>provided</scope>
</dependency>
<dependency>
  <groupId>org.apache.hadoop</groupId>
  <artifactId>hadoop-core</artifactId>
  <version>1.2.1</version>
  <scope>provided</scope>
</dependency>

Добавьте sbtSpark и Hadoop в качестве указанных зависимостей:

libraryDependencies += "org.apache.spark" %% "spark-core" % "2.3.0" % "provided"
libraryDependencies += "org.apache.hadoop" %% "hadoop-core" % "1.2.1" % "provided"

Совет

Укажите правильную версию Scala для ваших зависимостей, исходя из используемой вами версии.

Дальнейшие действия

Дополнительные сведения о создании и запуске заданий Azure Databricks см. в статье "Планирование и оркестрация рабочих процессов".