TL;DR
- RDBベンチマークTPC-HをAmazon EMRのクエリエンジン Hiveで実行する手順を紹介します
実験概要
- デフォルト設定のAmazon EMRで,TPC-Hベンチマークを一部修正して実行します
- Hive HPL/SQLに合わせて,データの格納手順などが若干変わります
- EMRのセットアップ方法は,Amazon EMRでHiveのセットアップを参照してください
TPC-Hベンチマークの実行手順
- ベンチマークの実行は,以下の手続きで実施します.
- データベースベンチマークTPC-HをMySQLで実行する(TPC-H v2.18.0)と同様の手順ですが,Hive用に
- TPC-Hのデータとクエリを生成するツールのダウンロード
- Hive向けの修正
- テーブルの作成
- データの生成
- データの登録
- インデックスの作成
- 実行クエリの生成
- クエリを実行して性能計測
1. ベンチマークツールのダウンロード
- デフォルト設定のままでEMRクラスタを作ると,
/
パーティションが10GBくらいしかないので,/mnt
パーティションに,データを置くようにします
# hadoop ユーザで実行
$ sudo mkdir /mnt/hadoop
$ sudo chown -R hadoop:hadoop /mnt/hadoop
$ cd /home/hadoop
$ ln -s /mnt/hadoop .
- TPC-H_Toolsの[Download]から,TPC-Toolsを入手します
- 入力するメールアドレスにダウンロードキー付きのURLが送付されるので,それをクリックしてダウンロードします
- TPC-H_Tools_v2.18.0を入手しました
- scpコマンドなどで,EMRのマスターノード(SSHでログインするノード)に,tpc-h-tools.zipにリネームしてコピーします
2. Hive向けにツールを修正
- データベースベンチマークTPC-HをMySQLで実行する(TPC-H v2.18.0)に加えて,いくつかの修正をする必要があります.
- この記事では,パッチのダウンロードからの手順を紹介します.
tpch-patchesのダウンロードと修正(MySQL版と同じ)
- hadoopユーザでEMRマスターノードにsshした後,下記のコマンドでディレクトリを作成し,tpch-patchesを
git clone
します - 前項でダウンロードしたtpc-h-tool.zipを配置します
$ mkdir -p ~/{src,bin,share}
$ cd ~/src
$ git clone https://github.com/itiut/tpch-patches
$ cp ~/tpc-h-tool.zip ~/src/
- src/tpch-patches/install.shを以下のように修正します(MySQL版と同じ)
diff --git a/install.sh b/install.sh
index 9d81955..bb0b6f5 100755
--- a/install.sh
+++ b/install.sh
@@ -22,7 +22,8 @@ esac
BASE_DIR=$PWD
DATABASE=$1
-TPCH_PROG=tpch_2_17_0
+TPCH_PROG=tpc-h-tool
+TPCH_VER=2.18.0_rc2
: ${PREFIX:=$HOME}
PREFIX=$(readlink -f $PREFIX)
BIN_DIR=$PREFIX/bin
@@ -40,14 +41,11 @@ ensure_directories() {
download_and_extract_dbgen() {
pushd $SRC_DIR
- if [ ! -f $TPCH_PROG.zip ]; then
- echo "Download $TPCH_PROG.zip ..."
- curl -LO http://www.tpc.org/tpch/spec/$TPCH_PROG.zip
- fi
if [ ! -d $TPCH_PROG ]; then
echo "Extract $TPCH_PROG.zip ..."
- unzip $TPCH_PROG
+ unzip $TPCH_PROG.zip
rm -rf __MACOSX
+ mv $TPCH_VER $SRC_DIR/$TPCH_PROG
fi
popd
}
- tpch-patches/install.shを実行して,{データ,クエリ}生成プログラムを生成する
$ ./install.sh mysql
3. テーブルの作成(スキーマの登録)
- スキーマ設定
~/share/dbgen/dss.ddl
を,Hive用に修正します- 各テーブルの作成コマンド
CREATE TABLE
について,最後の閉じカッコとセミコロンの間に,下記の例のように3行追加します.- ロードするファイルの区切り文字に関する設定です
- MySQLではロード時に区切り文字を設定しますが,Hiveではスキーマ設定のときに設定します
- 8つのテーブルがあるので,それぞれ記載します
- 各テーブルの作成コマンド
CREATE TABLE nation ( N_NATIONKEY INTEGER ,
N_NAME CHAR(25) ,
N_REGIONKEY INTEGER ,
N_COMMENT VARCHAR(152))
ROW FORMAT DELIMITED
FIELDS TERMINATED BY '|'
LINES TERMINATED BY '\n';
- EMRのHiveに,
sf1
などのデータベースを作成します - その後,
dss.ddl
をクエリとして実行します
$ cd ~/share/dbgen
$ hive -e "create database sf1;"
$ hive --database sf1 -f dss.ddl
4. データの生成(MySQLと同じ)
-
dbgen
コマンドで,データテーブルを作成します- テーブルデータは大きくなるので,
/mnt
パーティションに置くとよいです
- テーブルデータは大きくなるので,
$ mkdir ~/hadoop/sf1 && cd ~/hadoop/sf1
$ ~/bin/dbgen -s 1
$ ls
-rw-rw-r-- 1 hadoop hadoop 24346144 4月 12 01:40 customer.tbl
-rw-rw-r-- 1 hadoop hadoop 759863287 4月 12 01:40 lineitem.tbl
-rw-rw-r-- 1 hadoop hadoop 2224 4月 12 01:40 nation.tbl
-rw-rw-r-- 1 hadoop hadoop 171952161 4月 12 01:40 orders.tbl
-rw-rw-r-- 1 hadoop hadoop 24135125 4月 12 01:40 part.tbl
-rw-rw-r-- 1 hadoop hadoop 118984616 4月 12 01:40 partsupp.tbl
-rw-rw-r-- 1 hadoop hadoop 389 4月 12 01:40 region.tbl
-rw-rw-r-- 1 hadoop hadoop 1409184 4月 12 01:40 supplier.tbl
5. テーブルへデータの登録
- テーブルファイルを,Hiveに登録するコマンドを実行します
- MySQL版と似ていますが,若干異なるので注意が必要です
$ cd ~/hadoop/sf1
# データベースsf1に,各テーブルの内容を登録する
$ for tbl_file in *.tbl;
do
hive --database sf1 -e \
"LOAD DATA LOCAL INPATH '$tbl_file' OVERWRITE INTO TABLE $(basename $tbl_file .tbl);"
done
6. インデックスの作成
- インデックス指定ファイルを作成し,テーブルのインデックスを登録します
- gistのdss.ri.tpchをダウンロードします
- tpch-patchesで生成されたdss.riと基本的には同じですが,Hive用の修正をしています
- 主キー,外部キーの指定で,
disable novalidate
(データ検証しない)の指定をしています - 主キー,外部キーの制約名を,データベース名ごとに別にするように修正しています
- 主キー,外部キーの指定で,
- 以下のコマンドで,データベース名ごとのインデックス指定ファイルを生成して,テーブルのインデックスを作成します
sed -e 's/tpch/sf1/g' dss.ri.tpch > dss.ri.sf1
hive --database sf1 -f dss.ri.sf1
7. クエリファイルの作成(MySQLと同じ)
-
qgen
コマンドで,TPC-Hのクエリファイルを生成します.-
-s
オプションで,実行するScale Factorを指定してください
-
$ cd ~/bin
$ mkdir -p ~/bin/sf1query && cd ~/bin/sf1query
$ for i in $(seq 1 22); do ~/bin/qgen -s 1 $i > $i.sql; done
8. クエリを実行して性能計測
- 下記コマンドで,Hive上のデータベースに対してクエリ(1.sql)を実行できます.
- 実行時間をファイル(sf1_1.log)に書き出しています
$ (time hive --database sf1 -f ~/sf1query/1.sql) >& sf1_1.log
Logging initialized using configuration in file:/etc/hive/conf.dist/hive-log4j2.properties Async: false
OK
Time taken: 0.93 seconds
Query ID = hadoop_XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
Total jobs = 1
Launching Job 1 out of 1
Status: Running (Executing on YARN cluster with App id application_XXXXX_XXXXXX)
----------------------------------------------------------------------------------------------
VERTICES MODE STATUS TOTAL COMPLETED RUNNING PENDING FAILED KILLED
----------------------------------------------------------------------------------------------
Map 1 .......... container SUCCEEDED 15 15 0 0 0 0
Reducer 2 ...... container SUCCEEDED 1 1 0 0 0 0
Reducer 3 ...... container SUCCEEDED 1 1 0 0 0 0
----------------------------------------------------------------------------------------------
VERTICES: 03/03 [==========================>>] 100% ELAPSED TIME: 46.16 s
----------------------------------------------------------------------------------------------
OK
A F 37734107.00 56586554400.73 53758257134.8700 55909065222.827692 25.522006 38273.129735 0.049985 1478493
N F 991417.00 1487504710.38 1413082168.0541 1469649223.194375 25.516472 38284.467761 0.050093 38854
N O 73589282.00 110371877742.86 104854991266.2109 109053028629.140947 25.502061 38248.916868 0.049995 2885621
R F 37719753.00 56568041380.90 53741292684.6040 55889619119.831932 25.505794 38250.854626 0.050009 1478870
Time taken: 56.439 seconds, Fetched: 4 row(s)
$ hive -e "RESET QUERY CACHE;"
- ScaleFactor=1 (1GB)のデータでは,Query1の実行に約56.4秒要しました.
- AuroraとEC2の比較の結果と比べると,だいぶ遅い(3倍程度の計算時間)です.