Amazon Redshiftのパフォーマンスチューニング #1 アーキテクチャ概要

     - データベース ,  


ご挨拶

こんにちは。システム開発部の中村です。
現在新卒入社2年目で、普段は受託開発の要件定義等の業務が主担当だったりします。
このブログの発起人というか、まあ言い出しっぺという事で初稿を上げさせて頂きます。

今回はAmazon Web ServiceのDWHサービス、Redshiftのパフォーマンスチューニングと題しまして、
内実アーキテクチャから、システムテーブルを利用し現状のクエリパフォーマンスを分析する方法を説明させて頂ければと思います。
ちなみに実家がAmazonの倉庫に近いです。

アーキテクチャ概要

パフォーマンスチューニングの前に、explainを見るにしてもシステムテーブルを漁るにしても、
まずは基本的なアーキテクチャに関する知識が必要かと思いますので、簡単におさらいします。
この辺りはスタートガイド的な記事に書いてありますので、もう知っているという方は本記事は読み飛ばして頂いて構いません。
詳しくは技評さんの記事などご参照頂ければと思います。
Amazon Redshiftではじめるビッグデータ処理入門

Redshiftは、ざっくり言いますとカラムナー型の分散RDBで、CPUコア毎に独立したディスク領域を持つシェアードナッシング型アーキテクチャです。
このCPUコアと紐付いたディスクパーティションのセットが分散の最小単位であり、公式ドキュメントで「ノードスライス」と呼んでいるものです。
購入単位の「ノード」より細かい単位なのでご注意下さい。

分散スタイル

さて、Redshiftのアーキテクチャを理解するにあたり、キモになるのがこの分散スタイルです。
当然ここでのテーブル設計が、パフォーマンスに大きく関わります。

Redshift上の各テーブルは、ノードスライスに対して3つのスタイルで分散されます。
ノードスライス1,2にはテーブルA,ノードスライス3,4にはテーブルB…という、データ格納先の明示的な指定は出来ません。
よってデータ並列によるスループット向上を狙うことになります。

  1. 均等な分散(ラウンドロビン
  2. キー分散(ハッシュ関数)
  3. ALL分散

均等分散は、ラウンドロビンで、全てのノードスライスのデータ数がほぼ均等になる様に分散します。
非正規化した、結合が想定されないテーブルが多いと思います。
create tableでdiststyle EVENを指定する。もしくは、指定しない場合デフォルトがこのスタイルが採択されます。

キー分散は、カラムのデータにハッシュ関数を掛けて対応するノードスライスに分散するスタイルです。
Redshiftは、結合は対象が同じノードスライスにいないと結合出来ません。
必然的に、キー分散は結合キーに対して指定する事になります。
create table文でdistkey(col)と指定すればok。

ALL分散はテーブル全体が全てのノードスライスにコピーされるスタイルです。
create tableでdiststyle ALLを指定します。

イメージとしては下記のようになります。
大文字のアルファベットを値とするCapitalフィールドを持つリレーションがあったとして、各分散スタイルを適用すると下図のような具合になります。
dw1.xlarge, dw2.largeノードが2VCPU、dw1.8xlargeノードが16VCPU、dw2.8xlargeノードが32VCPUであるため、
厳密には3ノードスライスという事はありませんが、便宜上という事で目を瞑って頂ければと思います。

分散スタイル図解

redshift

CREATE文はこういった形式になります。

/* 均等な分散 */
create table evenlyDistributed (
    id int,
    name varchar(255),
    date timestamp
)
diststyle EVEN;

/* キー分散 */
create table keyBasedDistributed (
    id int,
    ...
)
distkey(id);

/* ALL分散 */
create table distributedToAllNodeSlice (
    id int,
    ...
)
diststyle ALL;

より詳細なcreate文の書式については公式ガイドをご参照下さい。
Amazon Redshift データベース開発者ガイド/CREATE TABLE の例

ALL分散は導入にあたり少々注意が必要です。
Redshiftは上記の通り、joinするレコード同士が同じノードスライスになければ結合出来ません。
では、それでもjoinしたい場合はどうなるかというと、再分散(redistribution)と言って、結合条件に合致するように各ノードスライスへのレコード分散のやり直しが起こります。
例えば分散キー≠結合キーとなる場合にjoinしたとしても、explainを取ると、DS_BCAST_INNER属性が付いている思います。
これは内部表となるテーブル全体のコピーを全ノードスライスに転送する操作であり、結果だけ見るとALL分散と同じではあるのですが、
テーブル設計の段階でALL分散を指定しておけばクエリ実行の度、再分散が毎回発生する事を避けられるためパフォーマンスの向上が期待出来ます。

ただOLAP分析のディメンションになるような小サイズのマスタテーブルならこれで良いのですが、
当然ALL分散では特性上必要となるディスク領域も増加しますし、更新時等々のオーバーヘッドが懸念されますので、
それなりのサイズのテーブルに対して指定したい場合は慎重を期すべきです。というより避けるべきと思います。
RedshiftはカラムナーDBなので、テーブル定義上列が増えた所でselectするカラムを絞ればI/Oに影響はほぼないため、
単純計算ですが結合対象の
トランザクションテーブル行数÷ノードスライス数 < マスタテーブル行数
となる場合は、パフォーマンス上は勿論データサイズ的にも
非正規化させてトランザクションテーブルのカラムを増やすのが得策かと思います。

アーキテクチャの解説で大分長くなってしまいましたので、
後半のクエリ分析編へ続きます。


DACエンジニア採用情報

  関連記事

6914441342_605f947885
Treasure Dataの新機能(Data Tank)をAudienceOneのレポート機能で利用した話

Data Tankとは? Treasure Dataの新機能でTreasure Dataのプラットフォーム上に構築されたデータマートです。 Tableau等のBIツールとの接続を想定されており、AWSでいうところのRedshift的なものだと考えるとわかりやすいかと。 Data TankはPostg …

heatmap
巨大データベースのスケールアップと引越作業

はじめに ビッグデータ解析部でオーディエンスデータ解析基盤の開発、運用を担当している Mike です。 弊社ではインターネット広告配信ログをはじめとする「ビッグデータ」と呼ぶにふさわしいデータボリュームを扱うオーディエンスデータ解析基盤を構築しています。今秋、そのうちの1構成要素である、データサイズ …

image1
トレジャーデータの新機能「Data Connector」でクライアントレスなビッグデータ連携を実現する

トレジャーデータは、スキーマレスな大量のデータ(ビッグデータ)をパブリッククラウド上に保管して集計や抽出をするためのサービスなのですが、他システムからの連携データをトレジャーデータのテーブルに格納するまでが一苦労でした。 他システムとの外部連携を行う場合、一般的にローカルサーバー内のストレージを外部 …

logomono-tableau-software-mono
Tableauを利用してMySQLとRedshiftのクロスDBジョインを実現する

はじめに RedshiftやTreasureDataなどのデータマート用のDBにはID単位の解析結果が格納され、ローカルのMySQLにはIDに紐づいた名称マスタが管理されている構成の場合、データマートのクロス集計結果に対してIDに紐づいた名称を付与したいことがあります。 データマート用に用意したDB …

11396380473_26f323b1e4_z
Google BigQuery / Tableauを使ってみた

TableauからGoogle BigQueryへ接続してみました。 弊社で利用しているTreasureDataからデータ出力してBigQueryへロード、Tableauから接続まで実際に行った手順について記載します。 TreasureDataからAmazonS3へデータ出力 まず、データが蓄積され …

PPG_anteli-kunatokei_TP_V
Treasure Dataで大規模なマスタデータを扱う際にはtimeカラムインデックスを活用しよう

DACではTreasure Dataを利用して各種データの蓄積や集計を行っています。Treasure Dataは時系列のデータを扱うのに特にすぐれたアーキテクチャなのですが、セグメントIDとユーザーIDの組み合わせといった大量のマスタデータを利用した計算にも利用することもできます。そのような場合にt …