I need to perform an initial upload of roughly 130 million items (5+ Gb total) into a single DynamoDB table. After I faced problems with uploading them using the API from my application, I decided to try EMR instead.
Long story short, the import of that very average (for EMR) amount of data takes ages even on the most powerful cluster, consuming hundreds of hours with very little progress (about 20 minutes to process test 2Mb data bit, and didn't manage to finish with the test 700Mb file in 12 hours).
I have already contacted Amazon Premium Support, but so far they only told that "for some reason DynamoDB import is slow".
I have tried the following instructions in my interactive hive session:
CREATE EXTERNAL TABLE test_medium (
hash_key string,
range_key bigint,
field_1 string,
field_2 string,
field_3 string,
field_4 bigint,
field_5 bigint,
field_6 string,
field_7 bigint
)
ROW FORMAT DELIMITED
FIELDS TERMINATED BY '|'
LOCATION 's3://my-bucket/s3_import/'
;
CREATE EXTERNAL TABLE ddb_target (
hash_key string,
range_key bigint,
field_1 bigint,
field_2 bigint,
field_3 bigint,
field_4 bigint,
field_5 bigint,
field_6 string,
field_7 bigint
)
STORED BY 'org.apache.hadoop.hive.dynamodb.DynamoDBStorageHandler'
TBLPROPERTIES (
"dynamodb.table.name" = "my_ddb_table",
"dynamodb.column.mapping" = "hash_key:hash_key,range_key:range_key,field_1:field_1,field_2:field_2,field_3:field_3,field_4:field_4,field_5:field_5,field_6:field_6,field_7:field_7"
)
;
INSERT OVERWRITE TABLE ddb_target SELECT * FROM test_medium;
Various flags doesn't seem to have any visible effect. Have tried the following settings instead of default ones:
SET dynamodb.throughput.write.percent = 1.0;
SET dynamodb.throughput.read.percent = 1.0;
SET dynamodb.endpoint=dynamodb.eu-west-1.amazonaws.com;
SET hive.base.inputformat=org.apache.hadoop.hive.ql.io.HiveInputFormat;
SET mapred.map.tasks = 100;
SET mapred.reduce.tasks=20;
SET hive.exec.reducers.max = 100;
SET hive.exec.reducers.min = 50;
The same commands run for HDFS instead of DynamoDB target were completed in seconds.
That seems to be a simple task, a very basic use case, and I really wonder what can I be doing wrong here.
Here is the answer I finally got from AWS support recently. Hope that helps someone in a similar situation: