2017-11-28 18 views
2

私は、このような複数のファイルを持っていると私はそれぞれ{}テーブル内の1つの列を形成するようにしたいハイブテーブルにハイブテーブル内のデータの配列を別々の行にインポートするにはどうすればよいですか?

[ 
    { 
     "identifier" : "id#1", 
     "dataA" : "dataA#1" 
    }, 
    { 
     "identifier" : "id#2", 
     "dataA" : "dataA#2" 
    } 
] 

を次の形式でデータをインポートしようとしています。これは私が試したものです:

CREATE EXTERNAL TABLE final_table(
    identifier STRING, 
    dataA STRING 
) ROW FORMAT SERDE 'org.openx.data.jsonserde.JsonSerDe' 
LOCATION "s3://bucket/path_in_bucket/" 

これは{}ごとに1つの行を作成していません。私も試したことがあります

CREATE EXTERNAL TABLE final_table(
    rows ARRAY< STRUCT< 
    identifier: STRING, 
    dataA: STRING 
    >> 
) ROW FORMAT SERDE 'org.openx.data.jsonserde.JsonSerDe' 
LOCATION "s3://bucket/path_in_bucket/" 

しかし、これはどちらでもありません。各レコードがハイブクエリの配列内の項目である配列としての入力を指定する方法はありますか?何をすべきかに関する提案はありますか?

答えて

1

データファイル内のJSONレコードは、1行に1つずつ表示する必要があります。空の行はNULLレコードを生成します。

このJSONは動作するはず

{ "識別子": "ID#1"、 "DATAA": "DATAA#1"}、 { "識別子": "ID#2"、 "DATAA": "DATAA#2"}ここで

+0

私が我慢するJSONは読みやすくするためにフォーマットされます。あなたが[]を取り除くことを意味するならば、私は11672のファイルを持っています、各ファイルが配列であることを指定するいくつかのオプションがありますか – shrewquest

+0

より良い理解のためにサンプル出力を提供できますか? –

+0

期待される出力はハイブテーブルです配列内の各項目をテーブル内の1つの行として表示します – shrewquest

0

は何が必要です

方法1:配列に名前を追加する

データ

{"data":[{"identifier" : "id#1","dataA" : "dataA#1"},{"identifier" : "id#2","dataA" : "dataA#2"}]} 

SQL

SET hive.support.sql11.reserved.keywords=false; 

CREATE EXTERNAL TABLE IF NOT EXISTS ramesh_test (
    data array< 
    struct< 
     identifier:STRING, 
     dataA:STRING 
    > 
    > 
) 
ROW FORMAT SERDE 'org.openx.data.jsonserde.JsonSerDe' 
LOCATION 'my_location'; 

SELECT rows.identifier, 
     rows.dataA 
    FROM ramesh_test d 
LATERAL VIEW EXPLODE(d.data) d1 AS rows ; 

出力

enter image description here

方法2 - データへの変更なし

データ

[{"identifier":"id#1","dataA":"dataA#1"},{"identifier":"id#2","dataA":"dataA#2"}] 

SQL

CREATE EXTERNAL TABLE IF NOT EXISTS ramesh_raw_json (
    json STRING 
) 
LOCATION 'my_location'; 

SELECT get_json_object (exp.json_object, '$.identifier') AS Identifier, 
     get_json_object (exp.json_object, '$.dataA') AS Identifier 
    FROM (SELECT json_object 
      FROM ramesh_raw_json a 
      LATERAL VIEW EXPLODE (split(regexp_replace(regexp_replace(a.json,'\\}\\,\\{','\\}\\;\\{'),'\\[|\\]',''), '\\;')) json_exploded AS json_object) exp; 

出力は

enter image description here

+0

これは{"data":<現在持っているデータ>}に変更する必要があります。とにかく既存のデータを変更することなくこれを行うことができるかどうかを知りたい。 – shrewquest

+0

@shrewquest - 配列オブジェクトに名前をつけたくない場合は、配列を爆発させてget_json_objectを使って値を取得する必要があると思います。私の経験では、それは厄介でパフォーマンスの面では遅いです。私の提案は、配列オブジェクトに名前を連結する一時テーブルを作成することです。あなたはUNIXのスクリプトでそれを行うことも、Hive自体を一時テーブルを使って行うこともできます。 – Ramesh

+0

@shrewquest - データを変更する必要のない方法2の回答を更新しました。お役に立てれば! – Ramesh

関連する問題