0

ios_os フィールドや android_os などのスパース フィールドを含む S3 の JSON ファイルから EMR ジョブを使用してデータをインポートしようとしていますが、データが含まれているのは 1 つだけです。データが null の場合もあれば、空の文字列の場合もあります。DynamoDB に挿入しようとすると、エラーが発生します (ただし、まばらに入力されたレコードを挿入することはできます)。

"AttributeValue に空の文字列を含めることはできません" {"created_at_timestamp":1358122714,...,"data":null,"type":"e","android_network_carrier":""}

空の文字列 "" を含む列を除外しましたが、まだそのエラーが発生しています。これを引き起こしているのは "property":null 値 (またはその両方) だと思います。DynamoDB に移動するときに、適切に機能するためには、これらの値が存在しないはずだと思いますか?

JSONSerde または Hive と DynamoDB テーブルとの対話を通じて、空の文字列属性値を無視するように Hive に指示する方法はありますか。

Hive SQL スキーマと挿入コマンドの例を次に示します。

CREATE EXTERNAL TABLE IF NOT EXISTS json_events (
  -- Common
  created_at BIGINT,
  data STRING,
  type STRING,
  android_network_carrier STRING
)
PARTITIONED BY (created_at BIGINT, type STRING)
ROW FORMAT SERDE "org.apache.hadoop.hive.contrib.serde2.JsonSerde"
WITH SERDEPROPERTIES (
  -- Common
  "created_at"="$.created_at",
  "data"="$.data",
  "android_network_carrier"="$.anw",
  "type"="$.dt"
)
LOCATION s3://test.data/json_events;

CREATE EXTERNAL TABLE IF NOT EXISTS dynamo_events (
  -- Common
  created_at BIGINT,
  data STRING,
  type STRING,
  android_network_carrier STRING
)
STORED BY 'org.apache.hadoop.hive.dynamodb.DynamoDBStorageHandler' 
TBLPROPERTIES ("dynamodb.table.name" = "test-events", 
"dynamodb.column.mapping" = "created_at:created_at,data:data,type:type,android_network_carrier:android_network_carrier"); 
ALTER TABLE json_events RECOVER PARTITIONS;

INSERT OVERWRITE TABLE dynamo_events
SELECT created_at,
  data,
  android_network_carrier,
  type
FROM json_events 
WHERE created_at = 20130114 AND type = 'e';
4

1 に答える 1

1

nullキーでない限り、 s は問題になりません。

ただし、DynamoDB では、データ モデルで説明されているように、空の文字列も空のセットも許可されません。

これを回避するには、いくつかのオプションがあると思います。

  1. "n/a" などの空の文字列の定数を定義し、データ抽出プロセスが欠損値をそのように扱うようにします。
  2. これらのレコードをフィルター処理することもできますが、それはデータを失うことを意味します。これは次のように実行できます。

    INSERT OVERWRITE TABLE dynamo_events
    SELECT created_at,
      data,
      android_network_carrier,
      type
    FROM json_events 
    WHERE created_at = 20130114 AND type = 'e' AND android_network_carrier != "";
    
于 2013-01-16T19:58:42.977 に答える