Аутентификация JavaKerberos для SQL Server на платформе Spark

Я пытаюсь заставить искровой кластер писать на SQL-сервер с помощью JavaKerberos с драйвером JDBC от Microsoft (v7.0.0) (т. е. я указываю integratedSecurity=true;authenticationScheme=JavaKerberos в строке подключения) с учетными данными, указанными в файле keyTab, и у меня нет большого успеха ( проблема такая же, если я указываю учетные данные в строке подключения).

Я отправляю задание в кластер (4-узловой режим YARN v 2.3.0) с помощью:

spark-submit --driver-class-path mssql-jdbc-7.0.0.jre8.jar \
--jars /path/to/mssql-jdbc-7.0.0.jre8.jar \
--conf spark.executor.extraClassPath=/path/to/mssql-jdbc-7.0.0.jre8.jar \
--conf "spark.driver.extraJavaOptions=-Djava.security.auth.login.config=/path/to/SQLJDBCDriver.conf" \
--conf "spark.executor.extraJavaOptions=-Djava.security.auth.login.config=/path/to/SQLJDBCDriver.conf" \
application.jar

Все работает частично: драйвер spark правильно аутентифицируется и создает таблицу, однако, когда любой из исполнителей приходит для записи в таблицу, они терпят неудачу с исключением:

java.security.PrivilegedActionException: GSSException: No valid credentials provided (Mechanism level: Failed to find any Kerberos tgt)

Наблюдения:

  • Я могу заставить все работать, если укажу учетные данные SQL-сервера (однако мне нужно использовать встроенную безопасность в моем приложении)
  • Keytab и файл модуля входа в систему «SQLJDBCDriver.conf», похоже, указаны правильно, поскольку они работают для драйвера.
  • Я вижу в пользовательском интерфейсе искры, что исполнители выбирают правильные параметры командной строки: -Djava.security.auth.login.config=/path/to/SQLJDBCDriver.conf

После большого количества протоколирования/отладки разницы в поведении искрового драйвера и исполнителя, кажется, что исполнитель пытается использовать неправильные учетные данные, даже если указанные параметры должны заставить его использовать те, которые указаны в keytab, как он успешно работает с драйвером spark. (Вот почему он генерирует это конкретное исключение, которое он делает, если я пытаюсь намеренно ввести неправильные учетные данные.)

Как ни странно, я вижу в выводе отладки, что драйвер JDBC находит и читает файл SQLJDBCDriver.conf, и должен быть представлен keytab (в противном случае я получаю, что файл не найден), но затем он сразу же игнорирует их и пытается использовать поведение по умолчанию/локальный пользователь реквизиты для входа.

Может ли кто-нибудь помочь мне понять, как я могу заставить исполнителей использовать учетные данные, указанные в keytab, или иным образом получить аутентификацию JavaKerberos/SQL Server для работы со Spark?


person quarkonium    schedule 05.10.2018    source источник


Ответы (3)


Просто чтобы сообщить об этом, я только что закрыл https://issues.apache.org/jira/browse/SPARK-12312, и теперь можно выполнять аутентификацию Kerberos с помощью встроенных поставщиков соединений JDBC. Добавлено много провайдеров, и один из них — MS SQL. Пожалуйста, прочтите документацию по его использованию: https://spark.apache.org/docs/latest/sql-data-sources-jdbc.html

Имейте в виду, что Spark 3.1 еще не выпущен, поэтому пройдет некоторое время, прежде чем на странице появятся два недавно добавленных параметра конфигурации (keytab и principal). Я думаю, что обновление документа произойдет в течение 1-2 недель.

person Gabor Somogyi    schedule 10.02.2021

Таким образом, очевидно, что аутентификация JDBC Kerberos в настоящее время просто невозможна для исполнителей в соответствии со старой JIRA здесь https://issues.apache.org/jira/browse/SPARK-12312. Поведение такое же, как и в версии 2.3.2 в соответствии со списком пользователей искры и моим тестированием.

Временные решения

  1. Используйте kinit, а затем распределите кешированный TGT исполнителям, как описано здесь: https://github.com/LucaCanali/Miscellaneous/blob/master/Spark_Notes/Spark_Executors_Kerberos_HowTo.md. Я думаю, что этот метод работает только для пользователя, под которым работают искровые исполнители. По крайней мере, я не мог заставить его работать для моего варианта использования.
  2. Оберните драйвер jdbc пользовательской версией, которая занимается аутентификацией, а затем вызывает и возвращает соединение из реального драйвера MS JDBC. Подробности здесь: https://datamountaineer.com/2016/01/15/spark-jdbc-sql-server-kerberos/ и соответствующий репозиторий здесь: https://github.com/nabacg/krb5sqljdb. Я заставил эту технику работать, хотя мне пришлось изменить код аутентификации для моего случая.
person quarkonium    schedule 18.10.2018

Встроенная проверка подлинности не работает с драйвером JDBC MS SQLServer в защищенном кластере с интеграцией AD, поскольку контейнеры не будут иметь контекста, поскольку токены Kerberos теряются при появлении модулей сопоставления (поскольку YARN передает задание своей внутренней подсистеме безопасности).

Вот мой репозиторий, который использовался для обхода аутентификации Kerberos/AD https://github.com/chandanbalu/mssql-jdbc-krb5 реализует драйвер, который переопределяет метод подключения последнего драйвера MS SQL JDBC (mssql-jdbc-9.2.1.jre8.jar) и получает билет для файла keytab. /principal и возвращает это соединение.

Вы можете получить последнюю сборку этого пользовательского драйвера из папки выпуска здесь

Запустите spark-shell с JARS

spark-shell --jars /efs/home/c795701/.ivy2/jars/mssql-jdbc-9.2.1.jre8.jar,/efs/home/c795701/mssql-jdbc-krb5/target/scala-2.10/mssql-jdbc-krb5_2.10-1.0.jar

Скала

scala>val jdbcDF = spark.read.format("jdbc").option("url", "jdbc:krb5ss://<SERVER_NAME>:1433;databasename=<DATABASE_NAME>;integratedSecurity=true;authenticationScheme=JavaKerberos;[email protected];krb5Keytab=/efs/home/c795701/c795701.keytab").option("driver","hadoop.sqlserver.jdbc.krb5.SQLServ, "dbo.table_name").load()

scala>jdbcDF.count()
scala>jdbcDF.show(10)

Команда spark-submit

com.spark.SparkJDBCIngestion — операции фрейма данных Spark JDBC

ingestionframework-1.0-SNAPSHOT.jar — JAR сборки вашего проекта

spark-submit \
--master yarn \
--deploy-mode cluster \
--jars "/efs/home/c795701/mssql-jdbc-krb5/target/scala-2.10/mssql-jdbc-krb5_2.10-1.0.jar,/efs/home/c795701/.ivy2/jars/scala-library-2.11.1.jar"
--files /efs/home/c795701/c795701.keytab
--class com.spark.SparkJDBCIngestion \
/efs/home/c795701/ingestionframework/target/ingestionframework-1.0-SNAPSHOT.jar
person Chandan Balu    schedule 04.06.2021