Impala 表使用 Avro 文件格式(翻譯)

Impala 表使用 Avro 文件格式

Cloudera Impala 支持數據文件使用 Avro 文件格式的表。Impala 能夠查詢 Avro 表,但目前不支持建立和插入數據。對於這些操做,使用 Hive 處理,而後切換回 Impala 執行查詢。 html

繼續閱讀: node

建立 Avro 表

請在 Hive 中使用包含 STORED AS AVRO 子句的 CREATE TABLE 語句來建立使用 Avro 文件格式的新表。關於經過 Hive 向 Avro 表加載數據的信息,參見 Avro page on the Hive wikishell

當在 Hive 中建立了表以後,切換回 impala-shell 並執行 INVALIDATE METADATA 語句。而後你能夠經過 impala-shell 查詢這個表。 數據庫

下面的例子演示瞭如何在 Hive 中建立 Avro 表:
hive> CREATE TABLE new_table
    > ROW FORMAT SERDE 'org.apache.hadoop.hive.serde2.avro.AvroSerDe'
    > STORED AS INPUTFORMAT 'org.apache.hadoop.hive.ql.io.avro.AvroContainerInputFormat'
    > OUTPUTFORMAT 'org.apache.hadoop.hive.ql.io.avro.AvroContainerOutputFormat'
    > TBLPROPERTIES ('avro.schema.literal'='{
    >    "name": "my_record",
    >    "type": "record",
    >    "fields": [
    >       {"name":"bool_col", "type":"boolean"},
    >       {"name":"int_col", "type":"int"},
    >       {"name":"long_col", "type":"long"},
    >       {"name":"float_col", "type":"float"},
    >       {"name":"double_col", "type":"double"},
    >       {"name":"string_col", "type":"string"},
    >       {"name": "nullable_int", "type": ["null", "int"]]}');
OK
Time taken: 6.372 seconds

Record 的每個字段成爲標準的列。注意任何其餘的信息,如 record 名,都被忽略。 apache

  Note: 對於容許爲空的列,請確保在實際類型名以前加上 "null" 條目。


在 Impala 中使用 Hive 建立的 Avro 表


當你經過 Hive 建立了 Avro 表以後,只要它只使用 Impala 兼容的數據類型,你就能夠在 Impala 中使用它(例如,它不能包含嵌套類型如 array, map, struct)。由於 Impala 和 Hive 共用相同的元數據數據庫,Impala 能夠直接訪問 Hive 中建立的表的定義和表的數據。 json

當你在 Hive 中建立了 Avro 表以後,經過 impala-shell 在下次鏈接到 Impala 後執行 INVALIDATE METADATA。這是一次性操做,讓 Impala 發現新表。假如你經過多個節點執行查詢,在 Hive 建立新表以後,第一次鏈接到各個節點上時,在每個節點上執行 INVALIDATE METADATA 語句。 app

當你經過 Hive LOAD DATA 或 INSERT 語句,或者經過手工複製或移動文件到表對應的數據目錄,這樣加載新數據文件到 Avro 表以後,經過 impala-shell 在下次鏈接到 Impala 後執行 REFRESH table_name 語句。假如你經過多個節點執行查詢,在 Impala 以外加載新數據以後,第一次鏈接到各個節點上時,在每個節點上執行 REFRESH 語句。 oop

Impala 僅支持 boolean, int, long, float, double, string 類型, 或這些類型與 null 值的聯合; 例如,["string", "null"]。與 null 的聯合本質上是建立一個可爲 null 的類型。 fetch




經過 JSON 設置 Avro 模式


如上所示,你能夠直接在你的 CREATE TABLE 語句中嵌入模式(schema),在 Hive metastore 中列寬的約束限制了你能夠設置的模式的長度(column width restrictions in the Hive metastore limit the length of schema you can specify)。假如你遇到長模式文字的問題,請嘗試存儲你的模式爲一個 HDFS 中的 JSON 文件。使用相似下面的屬性,設置你的 HDFS 中的模式 url

tblproperties ('avro.schema.url'='hdfs//your-name-node:port/path/to/schema.json');



Avro 表啓用壓縮

爲了給 Avro 表啓用壓縮,請在 Hive shell 中指定設置啓用壓縮,並設置編解碼器,而後像以前的例子那樣執行 CREATE TABLE 語句。Impala Avro 表支持 snappy 和 deflate 編解碼器。

例如:

hive> set hive.exec.compress.output=true;
hive> set avro.output.codec=snappy;

How Impala Handles Avro Schema Evolution


自 Impala 1.1 開始, Impala 能夠處理採用模式演變(schema evolution) 的 Avro 數據文件,這些不一樣的數據文件在同一個表中,並使用略微不一樣的類型定義(你能夠經過在 Hive shell中運行 ALTER TABLE 語句執行 schema evolution 操做)。所修改的列的舊的和新的類型必須是兼容的,例如一個列開始多是 int 而後修改成 bigint/float。

當任意表的定義被修改,或在當前 impalad 節點以外添加數據,假如 Avro 模式經過 Hive 修改,請確保 Impala 加載了表的最新的元數據。執行 REFRESH table_name 或 INVALIDATE METADATA table_name 語句來加載。REFRESH 當即加載元數據,而 INVALIDATE METADATA 在下次表訪問時加載元數據。

當查詢不涉及到 Avro 數據文件或列時,Impala 不會檢查它們的一致性。所以,假如你執行 SELECT c1, c2 FROM t1, 若是列 c3 以兼容的方式進行了修改,Impala 不會返回任何錯誤。假如查詢只返回部分分區的數據,Impala 不會檢查未使用分區的數據文件。

在 Hive DDL 語句中,你能夠設置 avro.schema.literal 表屬性(若是模式定義爲short) or an avro.schema.url 屬性(若是模式定義爲 long,或容許方便的編輯定義)。

例如,在 Hive shell 中運行如下 SQL 代碼建立一個使用 Avro 文件格式的表,並放入一些例子數據:

CREATE TABLE avro_table (a string, b string)
ROW FORMAT SERDE 'org.apache.hadoop.hive.serde2.avro.AvroSerDe'
STORED AS INPUTFORMAT 'org.apache.hadoop.hive.ql.io.avro.AvroContainerInputFormat'
OUTPUTFORMAT 'org.apache.hadoop.hive.ql.io.avro.AvroContainerOutputFormat'
TBLPROPERTIES (
  'avro.schema.literal'='{
    "type": "record",
    "name": "my_record",
    "fields": [
      {"name": "a", "type": "int"},
      {"name": "b", "type": "string"}
    ]}');

INSERT OVERWRITE TABLE avro_table SELECT 1, "avro" FROM functional.alltypes LIMIT 1;

一當 Avro 表被建立幷包含數據以後,你就能夠經過 impala-shell 命令查詢:

-- [localhost:21000] > select * from avro_table;
-- Query: select * from avro_table
-- Query finished, fetching results ...
-- +---+------+
-- | a | b    |
-- +---+------+
-- | 1 | avro |
-- +---+------+

如今在 Hive shell 中,你修改了一個列的類型,並添加一個包含默認值的新列:

-- Promote column "a" from INT to FLOAT (no need to update Avro schema)
ALTER TABLE avro_table CHANGE A A FLOAT;

-- Add column "c" with default
ALTER TABLE avro_table ADD COLUMNS (c int);
ALTER TABLE avro_table SET TBLPROPERTIES (
  'avro.schema.literal'='{
    "type": "record",
    "name": "my_record",
    "fields": [
      {"name": "a", "type": "int"},
      {"name": "b", "type": "string"},
      {"name": "c", "type": "int", "default": 10}
    ]}');

再次回到 impala-shell,你能夠基於該表最新的模式定義查詢這個表。由於表的元數據是在 Impala 以外修改的,應首先執行 REFRESH 語句一邊 Impala 更新該表的元數據到最新。

-- [localhost:21000] > refresh avro_table;
-- Query: refresh avro_table
-- Query finished, fetching results ...

-- Returned 0 row(s) in 0.23s
-- [localhost:21000] > select * from avro_table;
-- Query: select * from avro_table
-- Query finished, fetching results ...
-- +---+------+----+
-- | a | b    | c  |
-- +---+------+----+
-- | 1 | avro | 10 |
-- +---+------+----+
-- Returned 1 row(s) in 0.14s
相關文章
相關標籤/搜索