Как создать EXTERNAL Spark таблицу из данных в HDFS - PullRequest
0 голосов
/ 26 апреля 2018

Я загрузил паркетный стол из HDFS в DataFrame:

val df = spark.read.parquet("hdfs://user/zeppelin/my_table")

Теперь я хочу предоставить эту таблицу Spark SQL, но это должна быть таблица с постоянным доступом, поскольку я хочу получить к ней доступ через соединение JDBC или другие сеансы Spark.

Быстрым способом может быть вызов метода df.write.saveAsTable, но в этом случае он материализует содержимое DataFrame и создаст указатель на данные в мета-хранилище Hive, создав другую копию данных в HDFS.

Я не хочу иметь две копии одних и тех же данных, поэтому я хотел бы создать внешнюю таблицу, которая будет указывать на существующие данные.

1 Ответ

0 голосов
/ 26 апреля 2018

Для создания внешней таблицы Spark необходимо указать параметр «путь» DataFrameWriter. Примерно так:

df.write.
  option("path","hdfs://user/zeppelin/my_mytable").
  saveAsTable("my_table")

Проблема, однако, в том, что он очистит ваш путь hdfs hdfs://user/zeppelin/my_mytable, удалив существующие файлы, и вызовет org.apache.spark.SparkException: Job aborted.. Это похоже на ошибку в Spark API ...

В любом случае, обходной путь к этому (протестирован в Spark 2.3) - создать внешнюю таблицу, но из Spark DDL. Если в вашей таблице много столбцов, создание DDL может быть проблематичным. К счастью, начиная с Spark 2.0, вы можете вызвать DDL SHOW CREATE TABLE, чтобы позволить spark выполнять тяжелую работу. Проблема в том, что вы действительно можете запустить SHOW CREATE TABLE в постоянной таблице.

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

// Create a sample of the table 
val df = spark.read.parquet("hdfs://user/zeppelin/my_table")
df.limit(1).write.
    option("path", "/user/zeppelin/my_table_tmp").
    saveAsTable("my_table_tmp")

// Now get the DDL, do not truncate output
spark.sql("SHOW CREATE TABLE my_table_tmp").show(1, false)

Вы получите DDL вроде:

CREATE TABLE `my_table_tmp` (`ID` INT, `Descr` STRING)
USING parquet
OPTIONS (
  `serialization.format` '1',
  path 'hdfs:///user/zeppelin/my_table_tmp')

Что вы хотели бы изменить , чтобы иметь исходное имя таблицы и путь к исходным данным . Теперь вы можете запустить следующее, чтобы создать таблицу Spark External, указывающую на ваши существующие данные HDFS:

spark.sql("""
  CREATE TABLE `my_table` (`ID` INT, `Descr` STRING)
  USING parquet
  OPTIONS (
    `serialization.format` '1',
    path 'hdfs:///user/zeppelin/my_table')""")
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...