PostgreSQLエンタープライズ・コンソーシアム 技術部会 WG#1

2017年度WG1活動報告書

PostgreSQL Enterprise Consortium

目次
目次
1. 改訂履歴
2. ライセンス3. はじめに3.1. PostgreSQLエンタープライズコンソーシアムとWG1について
3.1.1. 各WGとWG1の活動テーマ
3.2. WG1の活動テーマ
3.3. 本資料の概要と目的
3.3.1. 2017年度の活動テーマ
3.3.2. 定点観測（スケールアップ）
3.3.3. Windows版PostgreSQL性能
3.3.4. パラレルクエリ
3.3.5. 全文検索
3.3.6. レプリケーション
3.3.7. Foreign Data Wrapper
3.4. 成果の公開
3.4.1. 2016年度までの活動テーマの紹介
3.5. 実施体制
3.6. 実施スケジュール
3.7. 謝辞
4. 定点観測(スケールアップ検証)
4.1. 検証概要
4.2. pgbench とは
4.3. 検証構成
4.3.1. ハードウェア構成
4.3.2. ソフトウェア構成
4.3.3. カーネル設定
4.3.4. PostgreSQL 設定
4.3.5. 環境
4.4. 検証方法(参照系)
4.5. 検証結果(参照系)
4.6. 検証方法(更新系)
4.7. 検証結果(更新系)
4.8. 追加検証
4.8.1. システムコール調査
4.9. 考察
5. Windows版PostgreSQL性能検証
5.1. 検証概要
5.2. 検証構成
5.2.1. ハードウェア構成
5.2.2. ソフトウェア構成
5.3. 検証モデル
5.3.1. データベースクラスタ構成
5.3.2. PostgreSQLの設定
5.3.3. 検証用ベンチマーク
5.3.3.1. 初期データ登録
5.3.3.2. 参照系測定
5.3.3.3. 更新系測定
5.4. 検証結果
5.4.1. 参照系
5.4.2. 更新系
5.4.3. Windows版 shared_buffersチューニング
5.4.4. Windows版 wal_sync_methodチューニング
5.5. まとめ
5.6. 参考
6. パラレルクエリ 性能検証
6.1. 検証概要
Page 2 of 86

2
6
7
8
8
8
8
8
8
9
9
9
9
9
9
9
9
10
10
10
11
11
11
12
12
13
13
13
14
14
15
15
16
16
16
21
23
23
23
23
23
24
24
24
25
25
25
26
26
26
26
27
27
28
28
29
29

PostgreSQL Enterprise Consortium

6.1.1. TPC-DSとは
6.2. パラレルクエリとは
6.2.1. パラレルクエリ
6.2.2. PostgreSQLでのパラレルクエリ
6.2.3. パラレルクエリに関連するパラメータ
6.3. 検証構成
6.3.1. 検証ハードウェア構成
6.3.2. 検証ソフトウェア構成
6.4. 検証方法
6.4.1. 検証項目
6.4.1.1. 検証A
6.4.1.2. 検証B
6.4.1.3. 対照群
6.4.2. データモデル
6.4.3. 使用クエリについて
6.4.3.1. No.10
6.4.3.2. No.11
6.4.4. DB設定
6.4.5. 測定手順
6.4.5.1. 検証A測定方法
6.4.5.2. 検証B測定方法
6.5. 検証結果
6.5.1. 検証A(パラレルクエリを有効にしたことによる効果)
6.5.2. 検証B(並列処理数(起動するワーカーの数)の違いによる検証結果)
6.5.2.1. 検証B補足 パラレルで動作した部分の比較(検証サーバ2)
6.5.3. 対照群(パラレルクエリoff)
6.6. 考察6.6.1. 検証A
6.6.1.1. No.10
6.6.1.2. No.11
6.6.2. 検証B
6.6.2.1. No.10
6.6.2.2. No.11
6.6.3. 総括
7. 全文検索7.1. 検証概要
7.2. 検証構成
7.2.1. マシン構成
7.2.2. 全文検索用モジュール
7.2.3. postgresql.confの設定値
7.3. 検証方法
7.3.1. 検証構成
7.3.2. 全文検索対象のデータ
7.3.3. インデックスの作成方法
7.3.4. 背景負荷
7.3.5. 検索方法
7.4. 検証結果
7.4.1. レプリケーション構成なし
7.4.1.1. データ更新性能
7.4.1.2. 全文検索性能
7.4.2. ロジカルレプリケーション構成
7.4.2.1. データ更新性能
7.4.2.2. 全文検索性能
7.4.3. 結果比較
7.4.3.1. データ更新性能
7.4.3.2. 全文検索性能
7.5. 考察8. レプリケーション検証
8.1. 検証概要
Page 3 of 86

29
29
29
29
30
31
31
31
32
32
32
32
32
32
33
33
33
33
34
34
37
37
37
43
47
49
51
51
51
54
57
57
57
58
59
59
59
59
59
59
60
60
60
60
61
61
62
62
62
62
62
62
62
63
63
64
65
67
67

PostgreSQL Enterprise Consortium

8.1.1. レプリケーションとは
8.1.1.1. 同期方式
8.1.1.2. 同期レプリケーション
8.1.1.3. 非同期レプリケーション
8.2. 検証構成
8.2.1. 検証サーバ
8.2.2. データベース設定
8.2.2.1. postgresql.confの設定
8.2.2.2. pg_hba.confの設定
8.3. 検証方法
8.3.1. 検証パターン
8.3.2. 検証A(Slaveの台数を増加させた場合)
8.3.3. 検証B(同期・非同期混在の場合)
8.3.4. 環境
8.3.4.1. データベースの初期設定
8.3.4.2. Master側の設定
8.3.4.3. 同期・非同期の設定
8.3.4.4. 各データベースサーバ再起動
8.3.5. 測定
8.4. 検証結果
8.4.1. 検証A(Slaveの台数を増加させた場合)
8.4.2. 検証B(同期・非同期混在の場合)
8.5. 考察8.5.1. 検証Aについて
8.5.2. 検証Bについて
8.5.3. まとめ
9. FDW検証
9.1. 検証概要
9.2. 検証構成
9.2.1. ハードウェア構成
9.2.2. ソフトウェア構成
9.2.3. データベース構成
9.2.3.1. テーブル構成
9.2.3.2. PostgreSQLの設定
9.3. 検証方法
9.3.1. 測定方法
9.3.2. 参照(SELECT)
9.3.2.1. 検証パターン
9.3.2.2. データベースへのアクセス
9.3.3. 更新(UPDATE)
9.3.3.1. 検証パターン
9.3.3.2. データベースへのアクセス
9.3.4. 挿入(INSERT)
9.3.4.1. 検証パターン
9.3.4.2. データベースへのアクセス
9.4. 検証結果
9.4.1. 参照(SELECT)
9.4.2. 更新(UPDATE)
9.4.3. 挿入(INSERT)
9.5. 考察10. おわりに
11. 著者
12. Appendix 検証環境

67
67
67
68
69
69
70
70
71
71
71
71
71
71
71
71
72
72
72
73
73
74
75
75
75
75
77
77
77
77
77
78
78
78
79
79
79
79
81
81
81
81
81
81
81
82
82
82
83
83
84
85
86

Page 4 of 86

PostgreSQL Enterprise Consortium

Page 5 of 86

PostgreSQL Enterprise Consortium

1. 改訂履歴
版

1.0

改訂日

変更内容

2018/04/12 新規作成

Page 6 of 86

PostgreSQL Enterprise Consortium

2. ライセンス
本作品はCC-B Yライセンスによって許諾されています。 ライセンスの内容を知りたい方は こちら でご確認ください。 文書の内容、表記に関する誤り、ご要望、感想等につきましては、PG ECo n s のサイト を通じてお寄せいただきますようお願いいたします。

Eclip se は、Eclip se Fo u n datio n In c の米国、およびその他の国における商標もしくは登録商標です。
IB M およびDB 2 は、世界の多くの国で登録された In tern atio n al B u sin ess Mach in es Co rp o ratio n の商標です。
In tel 、インテルおよびXeo n は、米国およびその他の国における In tel Co rp o ratio n の商標です。
Java は、O racle Co rp o ratio n 及びその子会社、関連会社の米国及びその他の国における登録商標です。 文中の社名、商品名等は各社の商標または登録商標である場合があります。
Lin u x は、Lin u s To rvalds 氏の日本およびその他の国における登録商標または商標です。
Red Hat およびSh ado w man lo go は、米国およびその他の国におけるRed Hat,In c. の商標または登録商標です。
Micro so ft 、W in do w s Server 、SQ L Server 、米国 Micro so ft Co rp o ratio n の米国及びその他の国における登録商標または商標です。
MySQ L は、O racle Co rp o ratio n 及びその子会社、関連会社の米国及びその他の国における登録商標です。 文中の社名、商品名等は各社の商標または登録商標である場合があります。
O racle は、O racle Co rp o ratio n 及びその子会社、関連会社の米国及びその他の国における登録商標です。 文中の社名、商品名等は各社の商標または登録商標である場合があります。
Po stgreSQ L は、Po stgreSQ L Co mmu n ity Asso ciatio n o f Can ada のカナダにおける登録商標およびその他の国における商標です。
W in do w s は米国 Micro so ft Co rp o ratio n の米国およびその他の国における登録商標です。
TPC, TPC B en ch mark, TPC-B , TPC-C, TPC-E, tp mC, TPC-H, TPC-DS, Q p h H は米国Tran sactio n Pro cessin g Perfo rman ce Co u n cil の商標です。
その他、本資料に記載されている社名及び商品名はそれぞれ各社が 商標または登録商標として使用している場合があります 。

Page 7 of 86

PostgreSQL Enterprise Consortium

3. はじめに3.1. PostgreSQLエンタープライズコンソーシアムとWG1について
Po stgreSQ L エンタープライズコンソーシアム(略称 PG ECo n s) は、Po stgreSQ L 本体および各種ツールの情報収集と提供、整備などの活動を通じて、ミッションクリティカ
ル性の高いエンタープライズ領域へのPo stgreSQ L の普及を推進することを目的として、2012 年4 月に設立された団体です。

3.1.1. 各 WGと WG1の 活動テー マ
PG ECo n s 技術部会ではPo stgreSQ L の普及を促進する技術的な課題の解決をテーマとし、「大規模基幹業務に向けた Po stgreSQ L の適用領域の明確化」を大きな目標に活動しております(2012 年7 月6 日開催のPG ECo n s セミナーより)。
この目標に向けて技術部会では課題を以下の課題領域に分類し、三つのワーキング・グループ(W G )で分担することとしました。

表 3.1 PG ECo n s における課題領域
課題領域

概要

担当 WG

性能

性能評価手法、性能向上手法、チューニングなど

1

互換性

データ、スキーマ、SQ L 、ストアドプロシージャの互換性

2

可用性

高可用クラスタ、B CP

3

保守性

保守サポート、トレーサビリティ

3

運用性

監視運用、バックアップ運用

3

セキュリ
ティ

監査

3

接続性

他ソフトウェアとの連携

3

W G 1 （新技術検証ワーキンググループ）
新しい技術の実検証から有用性や課題を検討
Po stgreSQ L の最新バージョンの性能傾向の調査・検討
W G 2 （移行ワーキンググループ）
ストアドプロシージャの移行技術に対する強化
利用者観点で整備した「移行フレームワーク」に基づき、成果物のユーザビリティ向上、 内容の最新化などを実施
W G 3 （課題検討ワーキンググループ）
データベース管理者やアプリケーション開発者が抱える、現場の課題に向けた課題に対するテーマを設定

3.2. WG1の活動テーマ
W G 1 では、Po stgreSQ L の新技術に対する技術検証、および新バージョンにおける性能検証を進めるにあたり、以下のような観点から個々の検証テーマをたてて、参加企業が集まってチームを作って具体的な検討を進めています。

表 3.2 W G 1 の検証テーマ
検証観点

具体的なテーマの例

新機能の技術検証

文字列データやJSO N などの特定データ型に対する処理性能や利便性、VACU U M に代表される保守コマンドの改善など性能向上機能定点観測

パラレルクエリ、パーティショニング、クエリキャッシュ、高速ロードなど
最新バージョンの Po stgreSQ L に対して、前バージョンとの性能傾向の差異を把握する

スケ ールアップ

マルチコアCPU でのスケールアップ性検証。定点観測で実施する

スケ ールアウト

負荷分散クラスタでのスケールアウト性検証

性能検証手法オンラインやバッチなどの業務別性能モデル、サイジング手法

性能チ ューニング

チューニングノウハウの整備、実行計画の制御手法

3.3. 本資料の概要と目的
本資料は、2017 年10 月にリリースされた Po stgreSQ L 10 のスケール性、新技術・機能向上、W in do w s 版Po stgreSQ L 性能、および近年のPo stgreSQ L に関連する技術について調査と性能検証を実施し、その方法と結果を報告します。

3.3.1. 2017年度の 活動テー マ
Page 8 of 86

PostgreSQL Enterprise Consortium

2017 年度は、2017 年10 月5 日にリリースされた Po stgreSQ L 10 を対象として以下のようなテーマで検証を実施しました。
定点観測（スケールアップ）
W in do w s 版Po stgreSQ L 性能
パラレルクエリ
全文検索
レプリケーション

FDW
以下、各検証テーマごとの概要を紹介します。

3.3.2. 定点観測（ スケー ル アッ プ）
例年通り、Po stgreSQ L 新旧バージョンにおけるスケール性能を比較する検証を行いました。 参照系クエリのスケール性能は 9.6 と 10 で大きな差は見られませんでした。
しかし、更新系クエリのスケール性能は 9.6 に比べ、10 では大きな性能低下が見られました。 この結果を踏まえ。10 における更新系クエリのスケール性能低下の原因を重点的に調査、検証しました。 今回の結論として、原因は10 で変更されたセマフォによるものと見ています。

3.3.3. Windows版 PostgreSQL 性能
Lin u x 上で実施していた定点観測と同様の測定をW in do w s 版Po stgreSQ L でも実施し、Lin u x 版Po stgreSQ L と、W in do w s 版Po stgreSQ L の性能の傾向を評価しました。 同一スペックのサーバ上でLin u x/W in do w s のO S の差異による測定を実施した結果、過負荷状態でなければ、W in do w s 版Po stgreSQ L は性能面では
Lin u x 版と遜色はないと考えられます。 また、特定のPo stgreSQ L パラメータについて、W in do w s 版固有のチューニングが必要か検証しました。 sh ared_b u ffers については、Lin u x 版のチューニング方針とは異なり、参照主体のモデルでは、非常に小さな値を設定しても性能上の問題はないという結果となりました。 w al_syn c_meth o d に
ついては、o p en _datasyn c を設定することが妥当であるという結果となりました。

3.3.4. パラレル クエリ
Po stgreSQ L 9.5 までは、メニーコア環境であっても1 つのクエリでは1 つのコアしか使用されませんでした。 商用ソフトウェアでは以前から実装されていて、Po stgreSQ L でも長年実装が待ち望まれてきたメニーコアを有効活用するパラレルクエリが、バージョン9.6 で実装され、バージョン10 で強化されました。 今回は、B I のようなO LAP において使用される形式のクエリを模したベンチマークテストである TPC-DS で定義されているクエリを題材とし、O LAP においてバージョン9.5 〜10 で、パラレルクエリによりどのように性能が変化するのかを検証しました。 検証の結果、扱うクエリによってパラレルクエリのパフォーマンスは、パラレルクエリの外側にある要因に左右される可能性があることが明らかになりました。 特に、パラレルクエリ実行により、実行計画の取得だけでは判明しない差異が存在しないかの確認、 パラレルクエリ実行の処理時間と、オーバヘッドやパラレ
ルクエリ部分以外の処理時間の割合を算出し、 効果が十分に得られるかどうかの確認が必要であるものと考えます。

3.3.5. 全文検索
近年の全文検索のユースケースでは、静的なデータを検索するだけではなく、データが継続して変更されているなかで検索を行う事が多くなっています。 このユースケースでは、同一のDB に対して更新と検索が同時に発生するため、通常では十分なパフォーマンスが得られないと予想されることから、今回Po stgreSQ L10 から実装されたロジカ
ルレプリケーションを使用した負荷分散を行い、十分なパフォーマンスが得られるかどうか検証しました。 検証の結果、Master とSlave に別々のインデックスを設定できるロジ
カルレプリケーションを利用した負荷分散構成をつくることで、全文検索用のインデックスによるデータ更新性能の劣化を起こさずに、全文検索用のインデックスを利用した
高速な全文検索が可能になることが明らかになりました。

3.3.6. レプリ ケー シ ョ ン
Po stgreSQ L では、9.0 からレプリケーション機能を実装しており、継続的に機能強化が行われています。 9.6 からは、2 台以上の複製先に対してデータを同期しながら更新が行える、複数同期レプリケーションが利用可能となりました。 本テーマでは、Po stgreSQ L におけるレプリケーション機能について、 同期レプリケーション・非同期レプリ
ケーション、またそれらが混在する構成において、どのように性能が変化するのかを検証しました。 本検証結果から、同期のみの構成は非同期のみの構成に比べ約1/2 の性能となること、同期・非同期混在の構成では総台数が同じでも同期の台数を増やすことで性能の低下が見られること、同期・非同期の台数を変化させることである程
度一定の割合で性能値も変化することが確認できました。

3.3.7. Foreign Data Wrapper
Po stgreSQ L から外部のデータへアクセスする為の仕組みであるFDW （ Fo reign Data W rap p er ）機能は点在する様々なデータをPo stgreSQ L から一括して管理する事ができる為、 企業のデータ活用に非常に有望視されていますが、一方で性能的なオーバヘッドに対する懸念もあります。 本検証では、Po stgreSQ L 10 系のFDW 機能に注目して、外部テーブルの有無を条件として参照系、更新系における性能オーバヘッドを明らかにしました。 今回の検証では、FDW を利用しない場合と比較してFDW を利用する場合は参照系では最低で4% 、更新系では最低で66% のスループットとなりました。

3.4. 成果の公開
本資料も含めて、活動成果は報告書の形にまとめて、 PG ECo n s のW eb サイト で公開しています。また、過去の活動成果も含めてテーマ毎に報告書を検索できるように
成果物総索引 も用意しています。

3.4.1. 2016年度まで の 活動テー マの 紹介
2012 年度は、企業システムで使われる機器構成で、 Po stgreSQ L のスケールアップ、スケールアウトによる性能特性、性能限界を検証しました。 企業システムへのPo stgreSQ L 採用や、システム構成を検討するための、 一つの指針として「 2012 年度W G 1 活動報告書」として情報を公開しています。
2013 年度は、2012 年度に引き続き2013 年9 月9 日にリリースされた Po stgreSQ L 9.3 を対象とした スケールアップの定点観測を実施、Po stgreSQ L 9.3 新機能による性能影響も合わせて評価することとしました。 また、更新スケールアウト構成が可能なPo stgres-XC の測定パターンを変えた再測定により、 最適な利用指針を探る評価を
Page 9 of 86

PostgreSQL Enterprise Consortium
実施することとしました。 さらに、2013 年度の新たな取り組みとしてデータベースの性能向上に着目、 データベースのI/O 負荷分散機能であるパーティショニングや、ハード
ウェアを活用した性能向上の検証を実施しました。

2014 年度は、2013 年度に引き続き2014 年12 月7 日にリリースされた Po stgreSQ L 9.4 を対象とした スケールアップの定点観測を実施、そして 9.4 新機能のW AL 改善を評価するために 更新系処理を新たに評価することとしました。 また、新たな取り組みとして物理環境以外の環境におけるデータベースの性能評価に着目、 KVM を使った仮想化環境と、Lin u x コンテナのDo cker 環境の検証を実施しました。
2015 年度は、2016 年1 月7 日にリリースされた Po stgreSQ L 9.5 を対象とした、スケールアップの定点観測を実施しました。 これは昨年度に引き続き、参照系・更新系の双方で性能を調査するものです。 Po stgreSQ L 9.5 での2 つの新機能、B RIN インデックスとParallel Vacu u m について、その利用ノウハウが得られるような検証を行い ました。最後に、基盤となるLin u x O S の主要なディストリビューションの一つである Red Hat En terp rise Lin u x 6 と7 とでPo stgreSQ L の性能を比較しました。
2016 年度は、2017 年9 月にリリースされた Po stgreSQ L 9.6 を対象とした、スケールアップの定点観測を実施しました。 これは例年通り、参照系・更新系の双方で性能を調査するものです Po stgreSQ L 9.6 の新機能のパラレルクエリや改善が行われた VACU U M について効果を検証しました。 また、Pgp o o l-II のスケールアウト性能、
JSO N/JSO NB データ型に関する性能評価を行いました。

3.5. 実施体制
2017 年7 月20 日に開催された 2017 年度第1 回技術部会より、以下の体制で実施しています(企業名順)。
表 3.3 2017 年度W G 1 参加企業

SRA O SS, In c. 日本支社
NEC ソリューションイノベータ株式会社
NTTテクノクロス株式会社
株式会社クリアコード
日本電信電話株式会社
富士通株式会社
この中で、SRA O SS, In c. 日本支社は、「主査」として W G 1 の取りまとめ役を担当することになりました。

3.6. 実施スケジュール
2017 年度は、下記スケジュールで活動しました。
表 3.4 実施スケジュール
活動概要

スケ ジュール

W G 1 スタート

2017 年7 月20 日

実施計画策定2017 年7 月～12 月

検証実施2018 年1 月～2018 年2 月

2017 年度W G 1 活動報告書作成

2018 年2 月～2018 年4 月

総会と成果報告会

2018 年5 月8 日(東京)、2018 年5 月23 日(大阪/報告会のみ実施)

3.7. 謝辞
検証用の機器を日本ヒューレット・パッカード株式会社、日本電気株式会社および富士通株式会社(敬称略)よりご提供いただきました。 この場を借りて厚く御礼を申し上げます。

Page 10 of 86

PostgreSQL Enterprise Consortium

4. 定点観測 (スケールアップ検証 )4.1. 検証概要
W G 1 では、Po stgreSQ L の新バージョン・新リリースにあわせて、新旧バージョンの性能比較やスケールアップ特性の検証を主な目的にした定点観測を2012 年度から実施
してきました。2014 年度からは、それまでの参照処理に加えて更新処理についても検証を実施し、検証結果の公開を行うようになりました。 2017 年度は32 コアのCPU （ Xeo n G o ld 6142 ）、メモリ384G B といったスペックのサーバで、最新のPo stgreSQ L バージョン 10 と前バージョンの 9.6 とのスケールアップ参照性能の比較および更新性能の比較を行いました。

4.2. pgbench とは
本検証では、 p gb en ch というベンチマークツールを使用しました。

p gb en ch はPo stgreSQ L に付属する簡易なベンチマークツールです(バージョン9.5 より前はco n trib に付属)。標準ベンチマーク TPC-B （銀行口座、銀行支店、銀行窓口担当者などの業務をモデル化）を参考にしたシナリオに基づくベンチマークの実行のほか、検索クエリのみを実行するシナリオも搭載されています。また、カスタムスクリプトを用意することで、独自のシナリオでベンチマークを実行することも可能です。

p gb en ch でベンチマークを実行すると、以下のように 1 秒あたりで実行されたトラザクションの数(TPS: Tran sactio n s Per Seco n d)が出力されます。なお、「 in clu din g
co n n ectio n s estab lish in g 」はPo stgreSQ L への接続に要した時間を含んだ TPS を、「 exclu din g co n n ectio n s estab lish in g 」はこれを含まないTPS を示します。

transaction type: TPC-B (sort of)scaling factor: 10
query mode: simple
number of clients: 10
number of threads: 1
number of transactions per client: 1000
number of transactions actually processed: 10000/10000
tps = 85.184871 (including connections establishing)tps = 85.296346 (excluding connections establishing)p gb en ch には「スケールファクタ」という概念があり、データベースの初期化モードでp gb en ch を起動することにより、任意のサイズのテスト用のテーブルを作成できます。デフォルトのスケールファクタは1 で、このとき「銀行口座」に対応する「 p gb en ch _acco u n ts 」というテーブルで10 万件のデータ、約15MB のデータベースが作成されます。
以下に、各スケールファクタに対応するデータベースサイズを示します。
表 4.1 スケールファクタに対するデータベースサイズ
スケ ールファク タ

データ ベースサイ ズ

1

15MB

10

150MB

100

1.5G B

1000

15G B

5000

75G B

初期化モードではp gb en ch _acco u n ts の他にもテーブルが作成されます。作成されるテーブルのリストを以下に示します。
表 4.2 p gb en ch _acco u n ts(口座)
列名

データ 型

コ メ ントaid

in tegerアカウント番号(主キー)b id

in teger

支店番号

ab alan cein teger

口座の金額

fillerch aracter(84)
表 4.3 p gb en ch _b ran ch es(支店)

列名

データ 型

備考

コ メ ントb idin teger

支店番号b b alan cein teger

口座の金額

fillerch aracter(84) 備考

Page 11 of 86

PostgreSQL Enterprise Consortium
表 4.4 p gb en ch _tellers(窓口担当者)
列名

データ 型

コ メ ントtid

in teger

担当者番号

b id

in teger

支店番号

tb alan cein teger

口座の金額

fillerch aracter(84) 備考

スケールファクタが 1 の時、p gb en ch _acco u n ts は 10 万件、p gb en ch _b ran ch es は 1 件、p gb en ch _tellers は 10 件のデータが作成されます。スケールファクタを増やすとこれに比例して各テーブルのデータが増えます。

p gb en ch には、様々なオプションがあります。詳細は Po stgreSQ L 文書 をご覧ください。ここでは、本検証で 使用している主なオプションのみを説明します。
表 4.5 ベンチマークテーブル初期化
オプショ ン

説明-i

ベンチマークテーブルの初期化-sスケールファクタ
作成するテーブルのフィルファクタ-F

表 4.6 ベンチマークの実行
オプショ ン説明-c

同時接続クライアント数-jp gb en ch 内のワーカスレッド数-T

ベンチマークを実行する秒数-n

実行前にバキュームを行わない-P指定した秒数ごとのレポートを表示-r

実行クエリの平均レイテンシを表示

4.3. 検証構成
4.3.1. ハー ドウ ェア構成

Page 12 of 86

PostgreSQL Enterprise Consortium

図 4.1 検証ハードウェア構成
本検証では上図構成のうち「 DB サーバ#2 」と「負荷掛け用」を用いました。

4.3.2. ソフトウ ェア構成
検証環境のソフトウェア構成を示します。
表 4.7 DB サーバ#2

OS

Red Hat En terp rise Lin u x 7.3

Po stgreSQ L

9.6.6, 10.1
表 4.8 負荷掛け用

OS

Red Hat En terp rise Lin u x 7.3

p gb en ch

10.1

4.3.3. カー ネ ル 設定
O S デフォルト
ハイパースレッディングは利用しない

4.3.4. PostgreSQL 設定
Po stgreSQ L 設定ファイル p o stgresql.co n f での設定は以下の通りです。 これらは参照系検証と更新系検証で共通です。
Page 13 of 86

PostgreSQL Enterprise Consortium

listen_addresses = '*' ... 負荷掛け用マシンからの接続用
max_connections = 500 ... 多めに設定
shared_buffers = 40GB
work_mem = 1GB
maitenance_work_mem = 20GB
checkpoint_timeout = 60min
max_wal_size = 160GB

4.3.5. 環境
以下の手順で、データベースクラスタを作成しました。

in itdb でデータディレクトリを作成し、上記に示した設定をp o stgresql.co n f に記述します。

$ initdb --no-locale --encoding=utf-8$ vi $PGDATA/postgresql.conf

Po stgreSQ L を起動してベンチマーク用のデータベースを作成します。

$ pg_ctl start -w$ createdb [dbname]4.4. 検証方法(参照系)
p gb en ch コマンドを用いて、ベンチマーク用データベースをスケールファクタ 2000 で初期化します。

$ pgbench -i -s 2000 [dbname]

本検証では p g_p rew arm モジュールを用います。

p g_p rew arm はバッファキャッシュにテーブルデータを読み込むためのモジュールで、バッファキャッシュがクリア されているデータベース起動直後の性能低下状態を解消するために用いることができます。
まず、測定スクリプト実行前に p g_p rew arm を実行します。これによりテーブルデータはすべてバッファキャッシュに格納されます。

=# SELECT pg_prewarm('pgbench_accounts');

以下のスクリプトを参照系カスタムスクリプトとして作成して、適度な負荷がかかるようにしました。これは、p gb en ch の標準 シナリオ（ p gb en ch -S ）ではCPU に充分な負荷がかからないためです。具体的には、ランダムに 10000 行を取得 しています。

\set naccounts 100000 * :scale\set row_count 10000\set aid_max :naccounts - :row_count\setrandom aid 1 :aid_max
SELECT count(abalance) FROM pgbench_accounts WHERE aid BETWEEN :aid and :aid + :row_count;

これを、クライアント用検証機から

Page 14 of 86

PostgreSQL Enterprise Consortium$ pgbench -n -h [host] -p [port] -c [clients] -j [threads] -f [参照系カスタムスクリプト] -T 300 -s 2000 -P 1
-r [dbname]

として実行しました。SELECTのみであるためVACU U M を実行せず(-n )、p gb en ch クライアント数(-c)とスレッド数(-j)を変動させながら、300 秒ずつ (-T)実行しています。ス
レッド数はクライアント数の半分としています。スケールファクタ (-s)にはデータベース初期化時と同じ2000 を指定します。 また、1 秒毎の進捗レポート取得(-P)と各クエリの平均レイテンシ(-r)も取得する指定にしました。（ただし、-P, -r の指定によって得られた結果は今回の考察に直接用いることはありませんでした）
計測はクライアント数ごとにそれぞれ3 回ずつ実行し、その中央値を結果とします。また、変動させるクライアント数は{1 2 4 8 16 32 48 64 96} です。

4.5. 検証結果(参照系)
検証結果のTPS のグラフを以下に示します。 9.6, 10 はともにクライアント数増加につれて TPS が増加し、 コア数を超えた辺りのクライアント数でTPS は頭打ちとなっています。 10 のTPS はほとんどクライアント数においてわずかに 9.6 を上回る結果となりました。

図 4.2 各クライアント数に対する TPS (参照系)

4.6. 検証方法(更新系)
p gb en ch コマンドを用いて、ベンチマーク用データベースをスケールファクタ 2000 で初期化します。 このとき、フィルファクタは 80 とします。

$ pgbench -i -s 2000 [dbname] -F 80

更新系検証でも、 p g_p rew arm モジュールを用います。 測定スクリプト実行前に p g_p rew arm を実行します。これによりテーブルデータはすべてバッファキャッシュに格納されます。

=# SELECT pg_prewarm('pgbench_accounts');

以下のスクリプトを更新系カスタムスクリプトとして作成して、適度な負荷がかかるようにしました。

Page 15 of 86

PostgreSQL Enterprise Consortium\set naccounts 100000 * :scale\set aid_val random(1, :naccounts)
UPDATE pgbench_accounts SET filler=repeat(md5(current_timestamp::text),2) WHERE aid = :aid_val;

これを、クライアント用検証機から$ pgbench -n -h [host] -p [port] -c [clients] -j [threads] -f [更新系カスタムスクリプト] -T 300 -s 2000 -P 1
-r [dbname]

として実行しました。VACU U M を実行せず(-n )、p gb en ch クライアント数(-c)とスレッド数(-j)を変動させながら、300 秒ずつ (-T)実行しています。スレッド数はクライアント数の半分としています。スケールファクタ (-s)にはデータベース初期化時と同じ2000 を指定します。 また、1 秒毎の進捗レポート取得(-P)と各クエリの平均レイテンシ(-r)も取得す
る指定にしました。（ただし、-P, -r の指定によって得られた結果は今回の考察に直接用いることはありませんでした）
計測はクライアント数ごとにそれぞれ3 回ずつ実行し、その中央値を結果とします。また、変動させるクライアント数は{1 2 4 8 16 32 48 64 96} です。 このとき、更新系検証の場合は実行後のテーブルを使い回さず、毎回初期化しています。

4.7. 検証結果(更新系)
検証結果のTPS のグラフを以下に示します。 9.6, 10 はともにクライアント数増加につれて TPS が増加しますが、 コア数を超えた辺りのクライアント数から差が現れ、最大
TPS は9.6 が10 を大きく上回る結果となりました。

図 4.3 各クライアント数に対する TPS (更新系)

10 の更新性能劣化を解明するために別途、追加の検証を行いました。

4.8. 追加検証
4.8.1. シ ステム コー ル 調査
各バージョンの p o stgres プロセスが実行するシステムコールを調査しました。 strace コマンドを用いることで、実行したシステムコールを取得できます。 strace コマンドはデフォルトでは実行されたシステムコールの詳細を示しますが、 -c オプションを用いることでシステムコールの集計を行うことが可能です。

Page 16 of 86

PostgreSQL Enterprise Consortium
また、-f オプションを用いることで集計の対象に全子プロセスを含めています。 （ただし、バックエンドプロセス以外も拾ってしまっています）

9.6 と 10 で大きく差の出た 80 クライアント接続指定の p gb en ch を対象に、 p gb en ch 実行開始直後にシステムコール情報取得を開始しています。

$ cat ${PGDATA}/postmaster.pid | head -n1 | xargs -I@ strace -p @ -f -c -o 《出力先ファイル》

図 4.4 9.6 の p o stgres プロセスが使用するシステムコール

Page 17 of 86

PostgreSQL Enterprise Consortium

図 4.5 10 の p o stgres プロセスが使用するシステムコール
図ではそれぞれ実行時間割合の大きい10 個のシステムコールを示しています。 利用されているシステムコールはほぼ同じですが、 実行時間割合が一番高いシステムコー
ルが異なっていました。 9.6 は semo p , 10 は fu tex システムコールが最も用いられています。
また、実行されたシステムコールの情報は実行回数とエラー回数も同時に得られます。 9.6 の semo p , 10 の fu tex の実行回数とエラー回数を示したのが次の図です。

Page 18 of 86

PostgreSQL Enterprise Consortium

図 4.6 9.6 の semo p , 10 の fu tex の実行回数とエラー回数

fu tex のシステムコールは semo p に対してエラー回数が多く、 エラー割合の大きさがパフォーマンス低下につながったのではないかと予想されます。
さらに、これらのシステムコールがどの関数から利用されているかを確認しました。 (ここから先は検証期間の関係上、検証者の環境で行っています)
システムコールと呼び出し側のスタックトレース採取は strace の -k オプションを用いました。

(9.6)./strace -ff -o 《出力先》 -p 《 postmaster PID》 -k -e semop(10)./strace -ff -o 《出力先》 -p 《 postmaster PID》 -k -e futex

9.6 で semo p が用いられていたケースは以下の2 通りでした。

Page 19 of 86

PostgreSQL Enterprise Consortium

semop(5472262, [{3, -1, 0}], 1)= 0> /usr/lib64/libc-2.17.so(semop+0x7) [0xf8f37]> /usr/local/pgsql/9.6.6/bin/postgres(PGSemaphoreLock+0x41) [0x24f441]> /usr/local/pgsql/9.6.6/bin/postgres(LWLockAcquireOrWait+0xfc) [0x2ab60c]> /usr/local/pgsql/9.6.6/bin/postgres(XLogFlush+0xcd) [0xdb75d]> /usr/local/pgsql/9.6.6/bin/postgres(CommitTransaction+0x4a7) [0xd2f17]> /usr/local/pgsql/9.6.6/bin/postgres(CommitTransactionCommand+0xc5) [0xd39f5]> /usr/local/pgsql/9.6.6/bin/postgres(finish_xact_command.part.4+0x35) [0x2b5fe5]> /usr/local/pgsql/9.6.6/bin/postgres(PostgresMain+0x1fb2) [0x2b98c2]> /usr/local/pgsql/9.6.6/bin/postgres(ServerLoop+0x964) [0x6b42a]> /usr/local/pgsql/9.6.6/bin/postgres(PostmasterMain+0xe6a) [0x26018a]> /usr/local/pgsql/9.6.6/bin/postgres(main+0x3e0) [0x6bf10]> /usr/lib64/libc-2.17.so(__libc_start_main+0xf5) [0x21b35]> /usr/local/pgsql/9.6.6/bin/postgres(_start+0x29) [0x6bf77]
semop(5505031, [{1, 1, 0}], 1)= 0> /usr/lib64/libc-2.17.so(semop+0x7) [0xf8f37]> /usr/local/pgsql/9.6.6/bin/postgres(PGSemaphoreUnlock+0x41) [0x24f4c1]> /usr/local/pgsql/9.6.6/bin/postgres(LWLockRelease+0x264) [0x2abc84]> /usr/local/pgsql/9.6.6/bin/postgres(XLogFlush+0x138) [0xdb7c8]> /usr/local/pgsql/9.6.6/bin/postgres(CommitTransaction+0x4a7) [0xd2f17]> /usr/local/pgsql/9.6.6/bin/postgres(CommitTransactionCommand+0xc5) [0xd39f5]> /usr/local/pgsql/9.6.6/bin/postgres(finish_xact_command.part.4+0x35) [0x2b5fe5]> /usr/local/pgsql/9.6.6/bin/postgres(PostgresMain+0x1fb2) [0x2b98c2]> /usr/local/pgsql/9.6.6/bin/postgres(ServerLoop+0x964) [0x6b42a]> /usr/local/pgsql/9.6.6/bin/postgres(PostmasterMain+0xe6a) [0x26018a]> /usr/local/pgsql/9.6.6/bin/postgres(main+0x3e0) [0x6bf10]> /usr/lib64/libc-2.17.so(__libc_start_main+0xf5) [0x21b35]> /usr/local/pgsql/9.6.6/bin/postgres(_start+0x29) [0x6bf77]

10 で fu tex が用いられていたケースは以下の2 通りでした。

Page 20 of 86

PostgreSQL Enterprise Consortium

futex(0x7f7f17ddfe58, FUTEX_WAKE, 1)= 1> /usr/lib64/libpthread-2.17.so(sem_post+0x3d) [0xdb7d]> /usr/local/pgsql/10.1/bin/postgres(PGSemaphoreUnlock+0x22) [0x284ef2]> /usr/local/pgsql/10.1/bin/postgres(LWLockRelease+0x324) [0x2ed664]> /usr/local/pgsql/10.1/bin/postgres(XLogFlush+0x138) [0xedac8]> /usr/local/pgsql/10.1/bin/postgres(CommitTransaction+0x4c1) [0xe4ca1]> /usr/local/pgsql/10.1/bin/postgres(CommitTransactionCommand+0xc5) [0xe57b5]> /usr/local/pgsql/10.1/bin/postgres(finish_xact_command.part.4+0x15) [0x2f82d5]> /usr/local/pgsql/10.1/bin/postgres(exec_simple_query+0x392) [0x2fa0a2]> /usr/local/pgsql/10.1/bin/postgres(PostgresMain+0xf5c) [0x2fb28c]> /usr/local/pgsql/10.1/bin/postgres(ServerLoop+0xbd7) [0x75c6d]> /usr/local/pgsql/10.1/bin/postgres(PostmasterMain+0xe89) [0x296609]> /usr/local/pgsql/10.1/bin/postgres(main+0x3f1) [0x76681]> /usr/lib64/libc-2.17.so(__libc_start_main+0xf5) [0x21b35]> /usr/local/pgsql/10.1/bin/postgres(_start+0x29) [0x766e8]
futex(0x7f7f17ddfc98, FUTEX_WAIT, 0, NULL) = 0> /usr/lib64/libpthread-2.17.so(do_futex_wait.constprop.1+0x2b) [0xd79b]> /usr/lib64/libpthread-2.17.so(__new_sem_wait_slow.constprop.0+0x4f) [0xd82f]> /usr/lib64/libpthread-2.17.so(sem_wait+0x2b) [0xd8cb]> /usr/local/pgsql/10.1/bin/postgres(PGSemaphoreLock+0x22) [0x284e92]> /usr/local/pgsql/10.1/bin/postgres(LWLockAcquireOrWait+0xbd) [0x2ece6d]> /usr/local/pgsql/10.1/bin/postgres(XLogFlush+0xcd) [0xeda5d]> /usr/local/pgsql/10.1/bin/postgres(CommitTransaction+0x4c1) [0xe4ca1]> /usr/local/pgsql/10.1/bin/postgres(CommitTransactionCommand+0xc5) [0xe57b5]> /usr/local/pgsql/10.1/bin/postgres(finish_xact_command.part.4+0x15) [0x2f82d5]> /usr/local/pgsql/10.1/bin/postgres(exec_simple_query+0x392) [0x2fa0a2]> /usr/local/pgsql/10.1/bin/postgres(PostgresMain+0xf5c) [0x2fb28c]> /usr/local/pgsql/10.1/bin/postgres(ServerLoop+0xbd7) [0x75c6d]> /usr/local/pgsql/10.1/bin/postgres(PostmasterMain+0xe89) [0x296609]> /usr/local/pgsql/10.1/bin/postgres(main+0x3f1) [0x76681]> /usr/lib64/libc-2.17.so(__libc_start_main+0xf5) [0x21b35]> /usr/local/pgsql/10.1/bin/postgres(_start+0x29) [0x766e8]

semo p も fu tex もいずれも PG Semap h o reLo ck, PG Semap h o reU n lo ck 関数で利用されていました。 つまり、いずれもセマフォを操作する関数から用いられるシステ
ムコールでした。

4.9. 考察
本検証では例年通り、Po stgreSQ L 最新バージョンと旧バージョンとのスケールアップ性能比較検証を行いました。
さて今回、10 のリリースノートにはスケール性能向上を謳った項目が見受けられなかったので、 検証前は参照系更新系いずれも性能は大きく変化しないものと予想していました。
実際、参照系においては新旧バージョンで性能は大きく変わりませんでしたが、 しかし更新系においては多数の同時接続時において新バージョンの明らかな性能低下が確認されました。
更新系について、システムコールの面から追加検証を行いました。 追加検証により、各バージョンで実行時間が一番長いシステムコールが異なること、 それらのシステム
コールはセマフォ操作の関数から呼び出されていること、 10 のシステムコールのエラー率が高いことを確認できました。
また、各バージョンで実行時間が一番長いシステムコールが異なるのは、10 において 「 Lin u x 上で利用されるデフォルトのセマフォが System V セマフォから PO SIX セマフォに変更」 されたことに依るものでした。本変更点はリリースノートからも確認できました。
状況証拠ではありますが、これらの結果より更新性能低下の原因はセマフォが変更されたことが大きいとみられます。 今回、検証期間をオーバーしてしまったため叶いませんでしたが、実際にセマフォがパフォーマンス低下の原因かどうかは10 において System V セマフォの使用を明示的に指定することで確認可能と思われます。
ところで、本検証と同時期（ 2018-01-23 ）に p gsql-h ackers メーリングリストへ9.6 と10 の更新性能比較検証報告(※3)が投稿されています。 こちらの結果も本検証と同様に 10 の性能低下を示す結果でした。その後のコメントでやはりセマフォの変更による性能低下が示唆されておりました。
参考：

1. Po stgreSQ L 10 リリースノート (日本語)h ttp s://w w w .p o stgresql.jp /do cu men t/10/h tml/release-10.h tml
2. Po stgreSQ L 10 リリースノート (英語)h ttp s://w w w .p o stgresql.o rg/do cs/10/static/release-10.h tml

Page 21 of 86

PostgreSQL Enterprise Consortium

3. p gsql-h ackers メーリングリストに投稿された 9.6 と 10 の更新性能比較検証
h ttp s://w w w .p o stgresql.o rg/messageid/CAD__O u gYDM3O %2B dyZn n ZSb Jp rSfsG FJcQ 1R%3De59T3h cLmDu g4_w %40mail.gmail.co m

Page 22 of 86

PostgreSQL Enterprise Consortium

5. Windows版 PostgreSQL性能検証
5.1. 検証概要
本章では、W in do w s 版Po stgreSQ L の性能を測定し、Lin u x 版Po stgreSQ L との性能の傾向を比較した結果を示します。
国内のPo stgrreSQ L ユーザの中にはW in do w s 版Po stgreSQ L を業務に使っているユーザも少なからずいます。 しかし、これまでPG ECo n s では、W in do w s 版
Po stgreSQ L を用いた性能検証は実施していませんでした。 今年度のPG ECo n s では、Lin u x 上で実施していた定点観測と同様の測定をW in do w s 版Po stgreSQ L でも実施し、Lin u x 版Po stgreSQ L と、W in do w s 版Po stgreSQ L の性能の傾向を評価しました。

5.2. 検証構成
本節では、W in do w s 版Po stgreSQ L 検証の環境を説明します。

5.2.1. ハー ドウ ェア構成

図 5.1 検証ハードウェア構成

5.2.2. ソフトウ ェア構成
検証環境のソフトウェア構成を示します。

Page 23 of 86

PostgreSQL Enterprise Consortium
表 5.1 DB サーバ#1

OS
Po stgreSQ L
OSW in do w s Server2016
10.1 (EDB in staller 版)
表 5.2 負荷掛け用
Red Hat En terp rise Lin u x 7.3

Po stgreSQ L

10.1 (ソースビルド版)

5.3. 検証モデル
本節では、W in do w s 版Po stgreSQ L 検証のモデルを説明します。 検証モデルの概要については、「定点観測(スケールアップ検証)」を参考にしてください。

5.3.1. デ ー タベ ー スクラスタ構成
W in do w s 版Po stgreSQ L をインストーラでインストールすると、インストール中にデフォルトのデータベースクラスタを作成します。 このデータベースクラスタは、デフォルトではC:\Program Files\PostgreSQL\10\dataの下に作成されます。 今回の性能検証では、データベースクラスタを外部ストレージには配置せず、またデータベース格納領域とW AL 格納領域の分離は行わない構成で実施しています。

5.3.2. PostgreSQL の 設定
Po stgreSQ L の設定として設定ファイルを以下のように変更して測定を実施しました。

Page 24 of 86

PostgreSQL Enterprise Consortium

pgbench=# SELECT * FROM pg_file_settings ;sourcefile| sourceline | seqno |name|setting| applied | error-----------------------------------------------------+------------+-------+---------------------------+--------------------+---------+------C:/Program Files/PostgreSQL/10/data/postgresql.conf |59 |1 | listen_addresses
| *
| t
|
C:/Program Files/PostgreSQL/10/data/postgresql.conf |63 |2 | port| 5432| t|
C:/Program Files/PostgreSQL/10/data/postgresql.conf |
127 |
3 |
dynamic_shared_memory_type | windows| t|
C:/Program Files/PostgreSQL/10/data/postgresql.conf |344 |4 | log_destination| stderr| t|
C:/Program Files/PostgreSQL/10/data/postgresql.conf |350 |5 | logging_collector
| on
| f
|
C:/Program Files/PostgreSQL/10/data/postgresql.conf |472 |6 | log_timezone| Asia/Tokyo| t|
C:/Program Files/PostgreSQL/10/data/postgresql.conf |566 |7 | datestyle| iso, mdy| t|
C:/Program Files/PostgreSQL/10/data/postgresql.conf |568 |8 | timezone| Asia/Tokyo| t|
C:/Program Files/PostgreSQL/10/data/postgresql.conf |581 |9 | lc_messages
| C
| t
|
C:/Program Files/PostgreSQL/10/data/postgresql.conf |583 |10 | lc_monetary
| C
| t
|
C:/Program Files/PostgreSQL/10/data/postgresql.conf |584 |11 | lc_numeric
| C
| t
|
C:/Program Files/PostgreSQL/10/data/postgresql.conf |585 |12 | lc_time
| C
| t
|
C:/Program Files/PostgreSQL/10/data/postgresql.conf |
588 |
13 |
default_text_search_config | pg_catalog.english | t|
C:/Program Files/PostgreSQL/10/data/postgresql.conf |662 |14 | max_connections
| 510
| t
|
C:/Program Files/PostgreSQL/10/data/postgresql.conf |663 |15 | shared_buffers| 38GB| t|
C:/Program Files/PostgreSQL/10/data/postgresql.conf |664 |16 | work_mem
| 1GB
| t
|
C:/Program Files/PostgreSQL/10/data/postgresql.conf |665 |17 | checkpoint_timeout| 30min| t|
C:/Program Files/PostgreSQL/10/data/postgresql.conf |666 |18 | max_wal_size| 160GB| t|
C:/Program Files/PostgreSQL/10/data/postgresql.conf |667 |19 | logging_collector
| on
| t
|
C:/Program Files/PostgreSQL/10/data/postgresql.conf |668 |20 | log_line_prefix| %t [%p-&l]| t|(20 rows)

5.3.3. 検証用ベ ン チマー ク
検証用のベンチマークとして、Po stgreSQ L 標準のベンチマークツールp gb en ch を使用しました。 （ p gb en ch の詳細については、「定点観測(スケールアップ検証)」を参考にしてください。

5.3.3.1. 初期データ 登録
初期データの登録は、p gb en ch の-i オプションでスケールファクタ = 1000 のサイズを指定しました。 fillfacto r の設定はデフォルト(テーブルのfillfacto r= 100)、u n lo gged
tab le の指定はなしとしました。

5.3.3.2. 参照系測定
走行時間は300 秒を指定しました。 同時実行数として 1, 2, 4, 8, 16, 32, 48, 72, 80, 96 を与えて実行しました。 参照系測定のために、以下のカスタムクエリを
p gb en ch に与えて実行しました。

Page 25 of 86

PostgreSQL Enterprise Consortium\set naccounts 100000 * :scale\set row_count 10000\set aid_max :naccounts - :row_count\set aid random(1, :aid_max)
SELECT count(abalance) FROM pgbench_accounts WHERE aid BETWEEN :aid and :aid + :row_count;

それぞれの同時実行数において、3 回の測定を実施し、その測定結果(tp s)の中間値を測定値としています。

5.3.3.3. 更新系測定
走行時間は300 秒を指定しました。 同時実行数として 1, 2, 4, 8, 16, 32, 48, 72, 80, 96 を与えて実行しました。 更新系測定のために、以下のカスタムクエリを
p gb en ch に与えて実行しました。

\set naccounts 100000 * :scale\set aid_val random(1, :naccounts)
UPDATE pgbench_accounts SET filler=repeat(md5(current_timestamp::text),2) WHERE aid = :aid_val;

それぞれの同時実行数において、3 回の測定を実施し、その測定結果(tp s)の中間値を測定値としています。

5.4. 検証結果
本節では、W in do w s 版Po stgreSQ L 検証結果を示します。

5.4.1. 参照系
参照系ベンチマークの結果を以下に示します。

参照系に関しては、Lin u x 版Po stgreSQ L と同等の傾向かつ性能になっていると判断できます。 また CPU 使用率とtp s/laten cyの関係を見ると、CPU 使用率が100% 近
くになるまでは、同時接続数に対してほぼスケールしており、CPU 使用率が100% 近くになると、tp s は横ばいとなり、laten cyが増加していくという傾向があります。 このモデルでは、CPU ネックになるという結果になりました。 tp s の傾向がLin u x 版とほぼ同等の傾向であることから、CPU 使用率の傾向についてもLin u x 版と大きな差はないと考えられます。

5.4.2. 更新系

Page 26 of 86

PostgreSQL Enterprise Consortium

更新系に関しては、tp s がピーク付近になると、Lin u x 版と比較して tp s が低下するという傾向になりました。 接続数がピークを超えると、W in do w s 版もLin u x 版もtp s が低下するという傾向にありますが、tp s の劣化度合いが、Lin u x 版よりもW in do w s 版のほうが大きくなっています。 CPU 使用率についてはtp s のピークおよび、それ以降になってもそれほど大きくなっておらず、I/O ネックになっていることが推測されます。

5.4.3. Windows版 shared_buffersチュ ー ニ ン グ
sh ared_b u ffers を定点観測用の設定値(実メモリの約10%= 約40G B )と、非常に小さな設定値(64MB )で参照系モデルを測定した結果を示します。

W in do w s 版Po stgreSQ L の場合、sh ared_b u ffers が小さくてもほとんど変わらない結果になっています。接続数が大きくなった場合には小さな設定値のほうが僅かに高い結果となっています。 W in do w s 版Po stgreSQ L の場合、Po stgreSQ L 文書のsh ared_b u ffers の説明に、「 W in do w s システムでのsh ared_b u ffers の範囲は一
般的に 64MB から 512MB です。」という記述がありますが、その記述どおりの結果が出たと考えられます。

5.4.4. Windows版 wal_sync_methodチュ ー ニ ン グ
w al_syn c_meth o d チューニングは、以下の2 ステップで実施しました。
p g_test_fsyn c による測定
p gb en ch による測定
p g_test_fsyc とは、Po stgreSQ L を動作させる場合に、最も高速なw al_syn c_meth o d を決定するためのツールです。 p g_test_fsyn c による測定を実施した結果を以下に示します。

テスト パタ ーン

表 5.3 p g_fsyn c による測定結果
fdatasync
fsync_writethroughopen_datasync

fsync

open_synco n e 8kB w rite(o p s/sec)

105161.390

n /a5288.632

5406.255n /ao n e 8kB w rite(o p s/sec)

105161.390

n /a5288.632

5406.255

n /a

次に更新系ベンチマークで実施した測定を、w al_syn c_meth o d をo p en _datasyn c,fsyn c_w riteth ro u gh ,fsyn c に設定して実施した結果を以下に示します。

Page 27 of 86

PostgreSQL Enterprise Consortiumw al_syn c_meth o d については、p g_test_fsyn c ユーティリティを使った事前検証と、実際に p gb en ch を用いた測定の両方において、o p en _datasyn c を設定すること
で、p gb en ch でも最も高いtp s を出せるという結果となりました。

5.5. まとめ
定点観測モデルを用いて、W in do w s 版Po stgreSQ L とLin u x 版Po stgreSQ L の性能を比較しました。 同一スペックのサーバ上でLin u x/W in do w s のO S の差異による測定を実施した結果、参照のみの場合は、Lin u x 版と同等の性能、更新系の場合には、tp s がピークに到達する前には同等の性能でしたが、ピークを超えた後は、Lin u x よりもtp s が低下する傾向があるのを確認しました。 この結果から、W in do w s 版Po stgreSQ L では、大量の書き込みが発生する場合には、Lin u x 版Po stgreSQ Lと比較すると性能が低い可能性があると推測されます。 しかし、過負荷状態でなければ、Lin u x 版と同等の性能にはなっており、W in do w s 版Po stgreSQ L は性能面ではLin u x 版と遜色はないと考えられます。
特定のPo stgreSQ L パラメータについて、W in do w s 版固有のチューニングが必要か検証しました。 sh ared_b u ffers については、Lin u x 版のチューニング方針とは異なり、参照主体のモデルでは、非常に小さな値を設定しても性能上の問題はないという結果となりました。 w al_syn c_meth o d については、o p en _datasyn c を設定することが妥当であるという結果となりました。

5.6. 参考
1. Po stgreSQ L 文書 p g_test_fsyn c
h ttp s://w w w .p o stgresql.jp /do cu men t/10/h tml/p gtestfsyn c.h tml
2. Po stgreSQ L 文書 資源の消費
h ttp s://w w w .p o stgresql.jp /do cu men t/10/h tml/ru n time-co n fig-reso u rce.h tml#ru n time-co n fig-reso u rce-memo ry

Page 28 of 86

PostgreSQL Enterprise Consortium

6. パラレルクエリ 性能検証
6.1. 検証概要
近年、ビッグデータ活用の流れから、データベースに大量のデータを投入して検索や集計を行い、新たな知見を得ようとする試みが増えています。 例えば、店舗における売上データなど、経営に関わるデータを組み合わせて多面的に解析するB I(B u sin ess In telligen ce)が典型的です。 このような使用方法においては、長大かつ高負荷となるクエリを処理することとなり、 多数の短小なクエリを大量に処理するような使用方法であるO LTP に対して、O LAP と呼ばれています。 一般的に、O LAP ではパラレルクエリ
やパーティショニングの恩恵を受けやすいとされています。

Po stgreSQ L をO LAP 用途で使用したいという要望は、以前から根強くありましたが、 Po stgreSQ L 9.5 まではパラレルクエリが実装されていなかったため、 O LAP 用途で実用的に使用できない状態でした。
そこで、Po stgreSQ L 9.6 で実装され、Po stgreSQ L 10 で強化されたパラレルクエリによって、Po stgreSQ L がO LAP 用途で実用的に使用できるようになったのかを検証します。 本検証では、O LAP において使用される形式のクエリを模したベンチマークテストであるTPC-DS で定義されているクエリを題材として使用します。

6.1.1. TPC-DSとは
TPC-DS は、TPC-H の後継となるベンチマークテストです。B I でよく用いられるスタースキーマをもとに、 TPC-H よりさらにテーブル間の関連を複雑にし、1 回のクエリ発行で多数のテーブルジョインや集約演算が行われるように クエリが工夫されています。
大規模なデータを取り扱うので、I/O 周りはもちろんのこと、多数のジョイン操作や集約演算が行われることから、 通常のO LTP よりもCPU の処理性能と、CPU をどの程度うまく使えているかがベンチマーク結果を大きく左右します。

TPC-DS では、99 種類/103 本のクエリが定義されていますが、本検証では、そのうちのNo .10 とN0.11 の2 種類/2 本のクエリについて検証を行いました。
これら 2 種類/2 本を選定したのは、本検証に先立って行った事前検証の結果、No .10 に関してはパラレルクエリ実行を行うことで劇的な性能改善が見られたこと、 No .11
に関してはPo stgreSQ L 10 でのみパラレルクエリ実行が行われており [1] 、Po stgreSQ L 10 で新規にパラレルクエリ対応したパターンにマッチしたものと判断したことが理由です。

[1] No .11 以外にはNo .4 が該当しますが、事前検証の結果から、No .4 は検証対象としたバージョン9.5 〜10 のすべてで実行時間が長大(6 時間強)となることが見込まれたため、検証期間の関係から採用を見送りました。

6.2. パラレルクエリとは
6.2.1. パラレル クエリ
パラレルクエリとは、一つのクエリを複数のプロセスで分担して並列処理することで、単一プロセスでの処理よりも高速にクエリを実行する処理方式です。
例えばSELECT文で1000 万レコードを全件検索する場合、検索で使用するプロセスが1 個だけだと1 プロセスが1000 万レコードをすべて検索する必要があります。 それに対して、例えば、検索で使用するプロセスが10 プロセスあって、それらで分担することができれば、1 プロセス当たりの検索対象は100 万レコードと10 分の1 に減ります。 複数のプロセスで分担することで高速化を図るため、メニーコア環境での使用で、効果を発揮します。
複数のプロセスで検索処理を分担して実行することで、1 プロセスあたりの検索自体にかかる実行時間は短くなりますが、 ある処理を複数に分割する配分の制御や受け
渡し、そして複数で処理した結果を集めて一つにまとめる処理などの実行時間が長くなります。 複数のプロセスで短縮できる時間があまり少ないと、パラレルクエリに変更す
ることでむしろ余計に実行時間がかかってしまうこともあります。
そのため、プランナは多くの実行プランの中から、パラレルクエリのほうが効率的に処理できると判断した場合のみパラレルクエリの実行プランを選択します。

6.2.2. PostgreSQL で の パラレル クエリ
2017 年現在、Po stgreSQ L で実装されているパラレルクエリに関する処理は、パラレルスキャン、パラレルジョイン、パラレル集約の三種類です。
プランナが処理を分担したほうが効率的だと判断した場合、パラレルクエリのプランを採用します。

exp lain (an alyze , verb o se)で確認したパラレルクエリ プラン例

Page 29 of 86

PostgreSQL Enterprise Consortium

QUERY PLAN--------------------------------------------------------------------------------------------------------------------------------------Gather (cost=1000.00..112816.10 rows=38400 width=52) (actual time=0.198..224.017 rows=99740 loops=1)
Output: log_id, date, "time", product_id, place_id, machine_id, app_id, access_time_second, access_count, err_code
Workers Planned: 4Workers Launched: 4-> Parallel Seq Scan on public.access_log (cost=0.00..107976.10 rows=9600 width=52) (actual time=0.017..209.797 rows=19948 loops=5)
Output: log_id, date, "time", product_id, place_id, machine_id, app_id, access_time_second, access_count, err_code
Filter: ((access_log.log_id % '77'::bigint) = 0)
Rows Removed by Filter: 1516052
Worker 0: actual time=0.016..214.828 rows=20088 loops=1
Worker 1: actual time=0.016..214.518 rows=19967 loops=1
Worker 2: actual time=0.020..218.061 rows=20817 loops=1
Worker 3: actual time=0.015..213.654 rows=20054 loops=1
パラレルクエリでは、親プロセスに加えワーカーがバックグラウンドワーカープロセスとして起動されて処理を実行するため、検索プロセス数は親プロセスとワーカーの合計となります。そして、各プロセスで処理した結果をG ath er ノードで集約します。
また、パラレルクエリで起動されるワーカー数は、テーブルサイズによりデフォルトで起動する数が決まっています。
表 6.1 テーブルサイズによるワーカー数
ブロ ック 数 [2]

サイ ズ（ M B ）起動ワーカ ー数

検索プロ セス数

1,024

8

1

2

3,072

24

2

3

9,216

72

3

4

27,648216

4

582,944648

5

6248,832

1,944

6

7

746,496

5,832

7

8

2,239,488

17,4968

96,718,464

52,4889

1020,155,392

157,464

10

11

・・・

・・・

・・・

・・・

[2] プロック数はブロックサイズがデフォルト(8KB )の場合です。

6.2.3. パラレル クエリ に関連するパラメー タ
パラレルクエリ時に関連する主なパラメータには以下のパラメータがあります。なお、max_p arallel_w o rkers_p er_gath er パラメータのデフォルト値がバージョン9.6 では0 のため、デフォルト設定ではパラレルクエリは実行されません。バージョン10 では同パラメータのデフォルト値は2 であるため、デフォルト設定でもパラレルクエリが実行されます。

Page 30 of 86

PostgreSQL Enterprise Consortium
表 6.2 パラレルクエリに関連する主なパラメータパラ メ ータ

デフォルト 値 (9.6)

デフォルト 値 (10)

説明

8

8

システムがサポートするバックグラウンド
ワーカープロセスの最大数を指定します。

max_p arallel_w o rkers_p er_gath er 0[3]2

一つのG ath er ノードに対して起動できるワーカー数の最大値を指定します。

max_p arallel_w o rkers [3] [4]―8

一度に有効となるパラレルワーカープロ
セスの最大数を指定します。

min _p arallel_relatio n _size

8MB―

パラレル処理を行うテーブルの最小サイズを指定します。

min _p arallel_tab le_scan _size―

8MB

パラレル処理を行うテーブルの最小サイズを指定します。

min _p arallel_in dex_scan _size

―

512KB

パラレル処理を行うインデックスの最小サイズを指定します。

p arallel_setu p _co st

1000

1000

ワーカーを起動するためのコストに対するプランナの推測値を指定します。

p arallel_tu p le_co st

0.1

0.1

あるワーカーから、1 行を他のプロセスに転送するためのコストに対するプランナの推測値を指定します。

max_w o rker_p ro cesses [3][3] (1, 2, 3) max_p arallel_w o rkers_p er_gath er で指定した値がmax_w o rker_p ro cesses で指定した値を超える場合、起動されるワーカー数は
max_w o rker_p ro cesses の値に制限されます。また、複数のパラレルクエリが同時に行われる場合、起動されるワーカー数の合計がmax_w o rker_p ro cesses で指定した値に制限されます。このため、プラン作成時のワーカー数よりも実際に起動されるワーカー数が少ない場合があります。

[4] Po stgreSQ L 10 では、max_p arallel_w o rkers もあり、パラレルクエリの実行に使用されるワーカー数は、基本的にはこちらに指定した値に制限されます。ただし、
この値がmax_w o rker_p ro cesses で指定した値を超える場合は、起動されるワーカー数はmax_w o rker_p ro cesses の値に制限されます。

6.3. 検証構成
6.3.1. 検証ハー ドウ ェア構成
検証環境のハードウェア構成の概略を示します。
本パラレルクエリ検証ではDB サーバ上でSQ L を直接実行する形式としました。
またコア数やメモリサイズの違いによるパラレルクエリの効果の違いを比較するために、 検証ではコア数とメモリサイズの構成が異なる下記のDB サーバを使用しました。
表 6.3 検証用DB サーバ構成
機器
検証サーバ1 (DL380 G en 10)

検証サーバ2

項目

仕様

CPU

インテル Xeo n G o ld 6142@ 2.60G Hz
16 コアx2 合計 32 コア
ハイパースレッディング:o ff

搭載メモリ

384G B

内蔵ストレージ

HDD 1.2TB SAS 10K x 16

CPU

インテル Xeo n E5-2630 v4@ 2.20G Hz
10 コアx2 合計 20 コア
ハイパースレッディング:o ff

搭載メモリ

256G B

内蔵ストレージ

SSD 400G B x 8 (HW -RAID カード, RAID 5 構成)(Exp ress5800/R120f-1E)

6.3.2. 検証ソフトウ ェア構成
検証環境のソフトウェア構成を示します。

Page 31 of 86

PostgreSQL Enterprise Consortium
表 6.4 ソフトウェア構成
種類

OS

ソフト ウェ ア名およびバージョ ン

Red Hat En terp rise Lin u x 7.2

Datab ase Po stgreSQ L 9.5.10
Po stgreSQ L 9.6.6
Po stgreSQ L 10.1

6.4. 検証方法
6.4.1. 検証項目
パラレルクエリ検証では以下の2 点を検証します。

6.4.1.1. 検証 A
検証A では、p o stgresql.co n f で、デフォルトではコメントアウトされているパラレルクエリ関連のパラメータの コメントアウトを単に外した (有効化した )だけの状態で、パラレル
クエリでの処理性能の改善状況を 確認します。
本検証によって、コメントアウトを外すだけという作業のみで、O LAP 用途におけるクエリに対する性能が、 どの程度改善するのか、もしくは悪化するのかを明らかにします。
(特に、Po stgreSQ L 10 においては、デフォルトの設定そのものの性能を検証することになります。)
また、パラレルクエリを有効化した場合に作成される実行計画が、有効化前からどのように変化し、 それが適切なものであるかどうかを検証します。

6.4.1.2. 検証 B
検証B では、パラレルクエリの並列度による処理性能の改善状況を確認します。
検証A におけるパラメータに加えて、 max_w o rker_p ro cesses 、max_p arallel_w o rkers_p er_gath er 、max_p arallel_w o rkers(Po stgreSQ L 10 のみ) の各パラメータの値を変更し、並列度の違いによる処理時間を比較します。
本検証によって、パラレルクエリ関連パラメータ、特に並列度のチューニングによって、 O LAP 用途におけるクエリに対する性能が、検証A との比較でさらに改善する余地があるのかどうかを明らかにします。

6.4.1.3. 対照群
対照群として、バージョン9.6 、バージョン10 において、max_p arallel_w o rkers_p er_gath er= 0 に明示的に設定を行った状態で 処理時間を比較します。
これにより、パラレルクエリ部分によらない性能改善がどの程度あったのかを明らかにします。

6.4.2. デ ー タモデ ル
本検証で使用するデータモデルは、TPC-DS において定義されているデータモデルに準拠します。
なお、Scale Facto r は2G B を採用しました。
各テーブルのサイズは、以下のとおりです。

Page 32 of 86

PostgreSQL Enterprise Consortium

relname| rows | bytes------------------------+----------+-----------call_center
|
8|
8192
catalog_page|
11718 |
2318336
catalog_returns| 288491 | 68222976
catalog_sales| 2880108 | 838221824
customer| 144000 | 39616512
customer_address|
72000 | 13123584
customer_demographics | 1920800 | 224788480
date_dim|
73049 | 16179200
dsdgen_version
|
1|
8192
household_demographics |7200 |
557056
income_band
|
20 |
8192
inventory| 16966362 | 1017929728
item|
26000 | 15671296
promotion
|
322 |
81920
reason|36 |8192
ship_mode
|
20 |
8192
store
|
22 |
8192
store_returns| 575285 | 102301696
store_sales| 5760759 | 1109213184
time_dim|
86400 | 13533184
warehouse|
5|8192
web_page
|
74 |
16384
web_returns| 143629 | 29876224
web_sales| 1439236 | 420954112
web_site
|
30 |
16384

relname| rows | bytes-----------------------------+----------+----------call_center_pkey
|
8|
16384
catalog_page_pkey|
11718 |
286720catalog_returns_pkey| 288491 | 9125888
catalog_sales_pkey| 2880108 | 90865664
customer_address_pkey|
72000 | 1630208
customer_demographics_pkey | 1920800 | 43171840
customer_pkey| 144000 | 3260416
date_dim_pkey|
73049 | 1654784
household_demographics_pkey |7200 |
180224income_band_pkey
|
20 |
16384
inventory_pkey| 16966362 | 689053696
item_pkey|
26000 |
606208promotion_pkey
|
322 |
16384
reason_pkey
|
36 |
16384
ship_mode_pkey
|
20 |
16384
store_pkey
|
22 |
16384
store_returns_pkey| 575285 | 18169856
store_sales_pkey| 5760759 | 181723136
time_dim_pkey|
86400 | 1957888
warehouse_pkey
|
5|
16384
web_page_pkey
|
74 |
16384
web_returns_pkey| 143629 | 4554752
web_sales_pkey| 1439236 | 45424640
web_site_pkey
|
30 |
16384

6.4.3. 使用クエリ につい て
本検証では、TPC-DS で定義されるNo .10 とNo .11 のクエリを使用します。 それぞれのクエリは、データモデルに対し、以下のデータの抽出を指示します。

6.4.3.1. N o.10
(参考訳) ある一定の地方に住み、実店舗と実店舗以外 [5] での流通経路の両方で購入したことのある顧客のうち、 性別・配偶者有無・最終学歴・購入額予測・信用状況・被扶養者数・就業している被扶養者数・大学生の被扶養者数が 同一のものの人数を数えよ。

[5] 実店舗以外には、W eb (EC サイト)通販とカタログ通販の2 種類がある想定。
6.4.3.2. N o.11
(参考訳) 昨年と比較して、今年の実店舗における使用金額よりW eb (EC サイト)通販での使用金額が大きくなった 顧客を抽出せよ。

6.4.4. DB設定
性能測定にあたり、デフォルトから変更したパラメータは以下のとおりです。

Page 33 of 86

PostgreSQL Enterprise Consortium
表 6.5 デフォルトから変更したパラメータパラ メ ータ

検証サーバ 1

listen _addresses*

sh ared_b u ffers

40G B

w o rk_mem

1G B

main ten an ce_w o rk_mem

20G B

au to vacu u mo ff

max_w o rker_p ro cesses [6]8max_p arallel_w o rkers_p er_gath er [6] 2
max_p arallel_w o rkers [6] [7]8lo g_lin e_p refix'%t [%p -%l]: '[6] (1, 2, 3) 測定により値を変更して実施します。
[7] Po stgreSQ L 10 のみ

6.4.5. 測定手順
測定に際しては、SQ L の実行前に p g_p rew arm を利用して、テーブル・インデックスのデータをディスクから一度読み込み、 Po stgreSQ L のバッファ上、もしくはO S のディスク
バッファ上に常駐させた状態にします。

SELECT relname, pg_prewarm(oid)
FROM pg_class
WHERE relnamespace in (SELECT oid
FROM pg_namespace
WHERE nspname='public') AND (
relkind='r' OR relkind='i');
6.4.5.1. 検証 A 測定方法
No .10 とNo .11 のSQ L を、p sql を使用して実行します。
No .10Page 34 of 86

PostgreSQL Enterprise Consortium

selectcd_gender,
cd_marital_status,
cd_education_status,
count(*) cnt1,
cd_purchase_estimate,count(*) cnt2,
cd_credit_rating,count(*) cnt3,
cd_dep_count,
count(*) cnt4,
cd_dep_employed_count,
count(*) cnt5,
cd_dep_college_count,
count(*) cnt6
fromcustomer c,customer_address ca,customer_demographics
where
c.c_current_addr_sk = ca.ca_address_sk andca_county in ('Walker County','Richland County','Gaines County','Douglas County','Dona Ana
County') and
cd_demo_sk = c.c_current_cdemo_sk andexists (select *from store_sales,date_dim
where c.c_customer_sk = ss_customer_sk andss_sold_date_sk = d_date_sk andd_year = 2002 andd_moy between 4 and 4+3) and(exists (select *from web_sales,date_dim
where c.c_customer_sk = ws_bill_customer_sk andws_sold_date_sk = d_date_sk andd_year = 2002 andd_moy between 4 ANd 4+3) orexists (select *from catalog_sales,date_dim
where c.c_customer_sk = cs_ship_customer_sk andcs_sold_date_sk = d_date_sk andd_year = 2002 andd_moy between 4 and 4+3))
group by cd_gender,
cd_marital_status,
cd_education_status,
cd_purchase_estimate,cd_credit_rating,
cd_dep_count,
cd_dep_employed_count,
cd_dep_college_countorder by cd_gender,
cd_marital_status,
cd_education_status,
cd_purchase_estimate,cd_credit_rating,
cd_dep_count,
cd_dep_employed_count,
cd_dep_college_countlimit 100;
No .11

with year_total as (select c_customer_id customer_id,c_first_name customer_first_name,c_last_name customer_last_name,c_preferred_cust_flag customer_preferred_cust_flag

Page 35 of 86

PostgreSQL Enterprise Consortium,c_birth_country customer_birth_country,c_login customer_login,c_email_address customer_email_address,d_year dyear,sum(ss_ext_list_price-ss_ext_discount_amt) year_total,'s' sale_typefrom customer,store_sales,date_dim
where c_customer_sk = ss_customer_sk
and ss_sold_date_sk = d_date_sk
group by c_customer_id,c_first_name,c_last_name,c_preferred_cust_flag,c_birth_country,c_login,c_email_address,d_yearunion allselect c_customer_id customer_id,c_first_name customer_first_name,c_last_name customer_last_name,c_preferred_cust_flag customer_preferred_cust_flag,c_birth_country customer_birth_country,c_login customer_login,c_email_address customer_email_address,d_year dyear,sum(ws_ext_list_price-ws_ext_discount_amt) year_total,'w' sale_typefrom customer,web_sales,date_dim
where c_customer_sk = ws_bill_customer_sk
and ws_sold_date_sk = d_date_sk
group by c_customer_id,c_first_name,c_last_name,c_preferred_cust_flag,c_birth_country,c_login,c_email_address,d_year)selectt_s_secyear.customer_id,t_s_secyear.customer_first_name,t_s_secyear.customer_last_name,t_s_secyear.customer_email_addressfrom year_total t_s_firstyear,year_total t_s_secyear,year_total t_w_firstyear,year_total t_w_secyear
where t_s_secyear.customer_id = t_s_firstyear.customer_id
and t_s_firstyear.customer_id = t_w_secyear.customer_id
and t_s_firstyear.customer_id = t_w_firstyear.customer_id
and t_s_firstyear.sale_type = 's'and t_w_firstyear.sale_type = 'w'
and t_s_secyear.sale_type = 's'and t_w_secyear.sale_type = 'w'
and t_s_firstyear.dyear = 2001
and t_s_secyear.dyear = 2001+1
and t_w_firstyear.dyear = 2001
and t_w_secyear.dyear = 2001+1
and t_s_firstyear.year_total > 0
and t_w_firstyear.year_total > 0
and case when t_w_firstyear.year_total > 0 then t_w_secyear.year_total /Page 36 of 86

PostgreSQL Enterprise Consortium

t_w_firstyear.year_total else 0.0 end> case when t_s_firstyear.year_total > 0 then t_s_secyear.year_total /t_s_firstyear.year_total else 0.0 end
order by t_s_secyear.customer_id,t_s_secyear.customer_first_name,t_s_secyear.customer_last_name,t_s_secyear.customer_email_address
limit 100;
6.4.5.2. 検証 B 測定方法
No .10 とNo .11 のSQ L を、p sql を使用して実行します。
測定に際しては、p o stgresql.co n f に以下の設定を行い、再起動を行うことで設定の反映を行っています。 また、測定を行う前にはp g_p rew arm を用いて、メモリ上にデータを常駐させた状態にしています。
表 6.6 検証時設定
パラ メ ータ

workers = 2

workers = 4

workers = 6

workers = 8

max_p arallel_w o rkers_p er_geth er 2

4

6

8

max_w o rker_p ro cesses

8

16

24

32

max_p arallel_w o rkers

8

16

24

32

6.5. 検証結果
6.5.1. 検証 A(パラレル クエリ を有効にしたことによる効果 )表 6.7 検証条件

DB サーバ
検証サーバ1

スト レージ
内蔵ストレージ

SQL 文
TPC-DS で定義されるNo .10 とNo .11

保持データ 量Scale Facto r = 2G Bの各クエリ
検証サーバ2内蔵ストレージ

TPC-DS で定義されるNo .10 とNo .11の各クエリ

バージョン毎の処理時間のグラフと表を以下に示します。

Page 37 of 86

Scale Facto r = 2G B

PostgreSQL Enterprise Consortium

図 6.1 バージョンと処理時間の比較 (No .10/検証サーバ1)

Page 38 of 86

PostgreSQL Enterprise Consortium

図 6.2 バージョンと処理時間の比較 (No .10/検証サーバ1 9.6 と10 を抜粋)

表 6.8 バージョンと処理時間 (No .10/検証サーバ1)
バージョ ン

処理時間 ( 秒 )性能向上比 ( 倍 ) [8]

パラ レルク エリ選択有無

9.5

10247

1.00

―

9.6

2.70833783.6○10

2.32054415.9○[8] 性能向上比は、バージョン9.5 の結果を、比較対象の各バージョンでの結果で除したものです。以下の性能向上比も、すべてこの方法で計算しています。

Page 39 of 86

PostgreSQL Enterprise Consortium

図 6.3 バージョンと処理時間の比較 (No .10/検証サーバ2)

Page 40 of 86

PostgreSQL Enterprise Consortium

図 6.4 バージョンと処理時間の比較 (No .10/検証サーバ2 9.6 と10 を抜粋)

表 6.9 バージョンと処理時間 (No .10/検証サーバ2)
バージョ ン

処理時間 ( 秒 )性能向上比 ( 倍 )パラ レルク エリ選択有無

9.5

11968

1.00

―

9.6

5.85632043.6○10

5.64912118.6○

Page 41 of 86

PostgreSQL Enterprise Consortium

図 6.5 バージョンと処理時間の比較 (No .11/検証サーバ1)

表 6.10 バージョンと処理時間 (No .11/検証サーバ1)
バージョ ン

処理時間 ( 秒 )性能向上比 ( 倍 )パラ レルク エリ選択有無

9.5

6913.6

1.00

―

9.6

7420.90.93164☓106899.51.0020○Page 42 of 86

PostgreSQL Enterprise Consortium

図 6.6 バージョンと処理時間の比較 (No .11/検証サーバ2)

表 6.11 バージョンと処理時間 (No .11/検証サーバ2)
バージョ ン

処理時間 ( 秒 )性能向上比 ( 倍 )パラ レルク エリ選択有無

9.5

9882.6

1.00

―

9.6

10013

0.98698☓109167.4

1.0780○

検証の結果、No .10 はバージョン9.6 ・バージョン10 ともにパラレルクエリの実行が行われ、バージョン9.5 と比較して、劇的に高速化したことがわかります。 一方、No .11 ではバージョン10 のみパラレルクエリの実行が行われましたが、バージョン9.5 と比較してあまり高速化しませんでした。
なお、No .11 のクエリにおいて、バージョン10 のみパラレルクエリ実行となったのは、 本クエリがバージョン10 のパラレルクエリ機能強化において対応した、 『非相関サブクエリのパラレル実行』に該当したものと考えます。

6.5.2. 検証 B(並列処理数 (起動するワー カー の 数 )の 違い による検証結果 )Page 43 of 86

PostgreSQL Enterprise Consortium

図 6.7 max_p arallel_w o rkers の値と処理時間の比較 (No .10/検証サーバ1)

表 6.12 並列処理数と処理時間 (No .10/
検証サーバ1)
ワーカ ー数

9.6 ( 秒 )10 ( 秒 )2

2.70832.320542.44592.082762.40471.997082.40362.0346

Page 44 of 86

PostgreSQL Enterprise Consortium

図 6.8 max_p arallel_w o rkers の値と処理時間の比較 (No .10/検証サーバ2)

表 6.13 並列処理数と処理時間 (No .10/
検証サーバ2)
ワーカ ー数

9.6 ( 秒 )10 ( 秒 )2

5.85635.649145.84155.381065.69775.44678

5.58885.2956

Page 45 of 86

PostgreSQL Enterprise Consortium

図 6.9 max_p arallel_w o rkers の値と処理時間の比較 (No .11/検証サーバ1)

表 6.14 並列処理数と処理
時間 (No .11/検証サーバ1)
ワーカ ー数

10 ( 秒 )2

6899.546897.466818.186844.0Page 46 of 86

PostgreSQL Enterprise Consortium

図 6.10 max_p arallel_w o rkers の値と処理時間の比較 (No .11/検証サーバ2)

表 6.15 並列処理数と処理
時間 (No .11/検証サーバ2)
ワーカ ー数

10 ( 秒 )2

9167.449354.169396.589389.6

検証の結果、No .10 は、並列処理数の増加にともなって、処理時間が減少する傾向にありました。 一方、No .11 では並列処理数の増加に伴って処理時間が減少せず、特に検証サーバ2 においては処理時間が増加する傾向が見られました。

6.5.2.1. 検証 B 補足 パラ レルで動作し た 部分の比較 ( 検証サーバ 2)
パラレルクエリ実行した部分の処理時間は、理論上、並列処理数に反比例する関係がありますが、 検証B のクエリの処理時間全体での比較データでは反比例の関係にあることを推測できるものとはなりませんでした。
ここでは、クエリ全体の処理に要した時間ではなく、パラレルクエリ実行となった部分のみの時間を抜き出して、 理論と合致する傾向にあるかどうかを検証しました。

Page 47 of 86

PostgreSQL Enterprise Consortium

図 6.11 max_p arallel_w o rkers の値と処理時間の比較 (No .10/検証サーバ2 パラレル実行部分のみ)

表 6.16 並列処理数と処理時間 (No .10/
検証サーバ2)
ワーカ ー数

9.6 ( 秒 )10 ( 秒 )2

0.51170.5546

4

0.38340.363560.34040.34268

0.33480.3469Page 48 of 86

PostgreSQL Enterprise Consortium

図 6.12 max_p arallel_w o rkers の値と処理時間の比較 (No .11/検証サーバ2 パラレル実行部分のみ) [9][9] max_p arallel_w o rkers_p er_gath er= 0 は、パラレル実行o ff を意味します。
表 6.17 並列処理数と処理
時間 (No .11/検証サーバ2)
ワーカ ー数
10 ( 秒 )
0

22.77

2

7.74

4

5.31

6

4.85

8

4.80

No .10 、No .11 のクエリにおいて、パラレルクエリ実行となった部分のみを抜き出して比較したところ、両クエリともに、並列処理数の増加にともなって、処理時間が減少する
傾向にありました。 グラフの形状からは、パラレルクエリ実行された部分の処理時間と並列処理数の間には、反比例に近い関係がありそうであると推測できます。

6.5.3. 対照群 (パラレル クエリ off)

Page 49 of 86

PostgreSQL Enterprise Consortium

図 6.13 バージョンと処理時間の比較 (No .10/検証サーバ2 パラレル実行なし)

表 6.18 バージョンと処理時間 (No .10/検証サーバ2)
バージョ ン

処理時間 ( 秒 )性能向上比 ( 倍 )

9.5

11968

1.00

9.6

14658

0.81648109930.21.2052

Page 50 of 86

PostgreSQL Enterprise Consortium

図 6.14 バージョンと処理時間の比較 (No .11/検証サーバ2 パラレル実行なし)

表 6.19 バージョンと処理時間 (No .11/検証サーバ2)
バージョ ン

処理時間 ( 秒 )性能向上比 ( 倍 )9.5

9882.61.00

9.6

9911.1

0.99712108105.3

1.2193

検証の結果、パラレルクエリo ff の状態で、バージョン9.5 比でバージョン9.6 はNo .10 で20% 、No .11 で1% の性能低下が認められ、 バージョン10 はNo .10 、No .11 ともに概ね20% の性能向上が認められました。
ここから、パラレルクエリ以外の部分でバージョン9.6 とバージョン10 の間において改善が行われ、 高速化したことが伺えます。

6.6. 考察6.6.1. 検証 A

6.6.1.1. N o.10
No .10 では、検証サーバ1 、検証サーバ2 ともに、パラレルクエリのないバージョン9.5 よりも、 パラレルクエリのあるバージョン9.6 、およびバージョン10 で劇的に高速化しました。
また、バージョン9.6 とバージョン10 を比較すると、10 のほうがより高速化しています。
ここで、検証サーバ2 で採取した、バージョン9.5 とバージョン9.6 のEXPLAIN ANALYZE の結果を比較します。
バージョン9.5

Page 51 of 86

PostgreSQL Enterprise Consortium

QUERY PLAN-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------Limit (cost=1920510150.45..1920510152.68 rows=47 width=68) (actual time=11967560.428..11967560.439 rows=19 loops=1)-> GroupAggregate (cost=1920510150.45..1920510152.68 rows=47 width=68) (actual time=11967560.427..11967560.437 rows=19 loops=1)
Group Key: customer_demographics.cd_gender, customer_demographics.cd_marital_status, customer_demographics.cd_education_status, cu
stomer_demographics.cd_purchase_estimate, customer_demographics.cd_credit_rating, customer_demographics.cd_dep_count, customer_demographics.cd_dep_employed_count, customer_demographics.cd_dep_college_count-> Sort (cost=1920510150.45..1920510150.56 rows=47 width=68) (actual time=11967560.409..11967560.410 rows=19 loops=1)
Sort Key: customer_demographics.cd_gender, customer_demographics.cd_marital_status, customer_demographics.cd_education_status, customer_demographics.cd_purchase_estimate, customer_demographics.cd_credit_rating, customer_demographics.cd_dep_count, customer_demogra
phics.cd_dep_employed_count, customer_demographics.cd_dep_college_countSort Method: quicksort Memory: 27kB-> Nested Loop (cost=217984.67..1920510149.14 rows=47 width=68) (actual time=11963323.535..11967560.289 rows=19 loops=1)
Join Filter: (c.c_current_cdemo_sk = customer_demographics.cd_demo_sk)
Rows Removed by Join Filter: 36495181-> Seq Scan on customer_demographics (cost=0.00..46648.00 rows=1920800 width=76) (actual time=0.005..202.805 rows=19
20800 loops=1)-> Materialize (cost=217984.67..1919051713.26 rows=49 width=8) (actual time=0.114..6.229 rows=19 loops=1920800)-> Nested Loop (cost=217984.67..1919051713.02 rows=49 width=8) (actual time=219831.780..11962737.942 rows=19 loops=1)-> Nested Loop (cost=217984.37..1919048998.10 rows=6909 width=16) (actual time=13693.957..11962695.074 r
ows=1912 loops=1)-> HashAggregate (cost=217983.95..218076.07 rows=9212 width=8) (actual time=1408.577..1502.045 row
s=17305 loops=1)
Group Key: store_sales.ss_customer_sk-> Hash Join (cost=3254.88..217960.92 rows=9212 width=8) (actual time=21.141..1376.343 rows=
211451 loops=1)
Hash Cond: (store_sales.ss_sold_date_sk = date_dim.d_date_sk)-> Seq Scan on store_sales (cost=0.00..193010.67 rows=5760867 width=16) (actual time=0.011..830.192 rows=5760749 loops=1)-> Hash (cost=3253.36..3253.36 rows=122 width=8) (actual time=21.083..21.083 rows=122
loops=1)
Buckets: 1024 Batches: 1 Memory Usage: 13kB-> Seq Scan on date_dim (cost=0.00..3253.36 rows=122 width=8) (actual time=10.94
7..21.057 rows=122 loops=1)
Filter: ((d_moy >= 4) AND (d_moy <= 7) AND (d_year = 2002))
Rows Removed by Filter: 72927-> Index Scan using customer_pkey on customer c (cost=0.42..208296.88 rows=1 width=24) (actual tim
e=691.194..691.194 rows=0 loops=17305)
Index Cond: (c_customer_sk = store_sales.ss_customer_sk)
Filter: ((alternatives: SubPlan 1 or hashed SubPlan 2) OR (alternatives: SubPlan 3 or hashed S
ubPlan 4))
Rows Removed by Filter: 1
SubPlan 1-> Nested Loop (cost=0.29..69605.82 rows=1 width=0) (actual time=246.900..246.900 rows=0 loops=17304)-> Seq Scan on web_sales (cost=0.00..69376.65 rows=28 width=8) (actual time=169.745.
.246.871 rows=9 loops=17304)
Filter: (c.c_customer_sk = ws_bill_customer_sk)
Rows Removed by Filter: 1416796-> Index Scan using date_dim_pkey on date_dim date_dim_1 (cost=0.29..8.17 rows=1 width=8) (actual time=0.002..0.002 rows=0 loops=163513)
Index Cond: (d_date_sk = web_sales.ws_sold_date_sk)
Filter: ((d_moy >= 4) AND (d_moy <= 7) AND (d_year = 2002))
Rows Removed by Filter: 1★1 SubPlan 2-> Hash Join (cost=3254.88..74454.63 rows=2403 width=8) (never executed)
Hash Cond: (web_sales_1.ws_sold_date_sk = date_dim_2.d_date_sk)-> Seq Scan on web_sales web_sales_1 (cost=0.00..65778.52 rows=1439252 width=16) (never executed)-> Hash (cost=3253.36..3253.36 rows=122 width=8) (never executed)-> Seq Scan on date_dim date_dim_2 (cost=0.00..3253.36 rows=122 width=8) (never executed)
Filter: ((d_moy >= 4) AND (d_moy <= 7) AND (d_year = 2002))
SubPlan 3-> Nested Loop (cost=0.29..138690.29 rows=1 width=0) (actual time=458.050..458.050 rows=0
loops=16785)-> Seq Scan on catalog_sales (cost=0.00..138323.23 rows=46 width=8) (actual time=196.035..457.985 rows=19 loops=16785)
Filter: (c.c_customer_sk = cs_ship_customer_sk)
Rows Removed by Filter: 2842597-> Index Scan using date_dim_pkey on date_dim date_dim_3 (cost=0.29..7.97 rows=1 width=8) (actual time=0.002..0.002 rows=0 loops=319521)
Index Cond: (d_date_sk = catalog_sales.cs_sold_date_sk)
Filter: ((d_moy >= 4) AND (d_moy <= 7) AND (d_year = 2002))
Rows Removed by Filter: 1★2 SubPlan 4-> Hash Join (cost=3254.88..145226.12 rows=4789 width=8) (never executed)
Hash Cond: (catalog_sales_1.cs_sold_date_sk = date_dim_4.d_date_sk)-> Seq Scan on catalog_sales catalog_sales_1 (cost=0.00..131122.98 rows=2880098 widt

Page 52 of 86

PostgreSQL Enterprise Consortiumh=16) (never executed)-> Hash (cost=3253.36..3253.36 rows=122 width=8) (never executed)-> Seq Scan on date_dim date_dim_4 (cost=0.00..3253.36 rows=122 width=8) (never executed)
Filter: ((d_moy >= 4) AND (d_moy <= 7) AND (d_year = 2002))-> Index Scan using customer_address_pkey on customer_address ca (cost=0.29..0.38 rows=1 width=8) (actual time=0.017..0.017 rows=0 loops=1912)
Index Cond: (ca_address_sk = c.c_current_addr_sk)
Filter: ((ca_county)::text = ANY ('{"Walker County","Richland County","Gaines County","Douglas County","Dona Ana County"}'::text[]))Rows Removed by Filter: 1
Planning time: 2.273 ms
Execution time: 11967560.997 ms(65 rows)
バージョン9.6

QUERY PLAN-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------Limit (cost=1989435197.83..1989435200.20 rows=50 width=116) (actual time=5837.880..5837.890 rows=19 loops=1)-> GroupAggregate (cost=1989435197.83..1989435200.20 rows=50 width=116) (actual time=5837.878..5837.886 rows=19 loops=1)
Group Key: customer_demographics.cd_gender, customer_demographics.cd_marital_status, customer_demographics.cd_education_status, cu
stomer_demographics.cd_purchase_estimate, customer_demographics.cd_credit_rating, customer_demographics.cd_dep_count, customer_demographics.cd_dep_employed_count, customer_demographics.cd_dep_college_count-> Sort (cost=1989435197.83..1989435197.95 rows=50 width=68) (actual time=5837.864..5837.865 rows=19 loops=1)
Sort Key: customer_demographics.cd_gender, customer_demographics.cd_marital_status, customer_demographics.cd_education_status, customer_demographics.cd_purchase_estimate, customer_demographics.cd_credit_rating, customer_demographics.cd_dep_count, customer_demogra
phics.cd_dep_employed_count, customer_demographics.cd_dep_college_countSort Method: quicksort Memory: 27kB-> Nested Loop (cost=173679.20..1989435196.42 rows=50 width=68) (actual time=1725.947..5837.733 rows=19 loops=1)
Join Filter: (c.c_current_cdemo_sk = customer_demographics.cd_demo_sk)
Rows Removed by Join Filter: 36495181-> Seq Scan on customer_demographics (cost=0.00..46648.00 rows=1920800 width=76) (actual time=0.007..243.870 rows=19
20800 loops=1)-> Materialize (cost=173679.20..1987947948.54 rows=50 width=8) (actual time=0.001..0.001 rows=19 loops=1920800)-> Nested Loop (cost=173679.20..1987947948.29 rows=50 width=8) (actual time=1099.634..1160.304 rows=19 loops=1)-> Nested Loop (cost=173678.90..1987945135.92 rows=7157 width=16) (actual time=1097.034..1152.777 rows=1
912 loops=1)-> HashAggregate (cost=173678.48..173773.91 rows=9543 width=8) (actual time=557.000..561.240 rows=
17305 loops=1)
Group Key: store_sales.ss_customer_sk-> Gather (cost=4254.87..173654.63 rows=9543 width=8) (actual time=22.603..525.341 rows=2114
51 loops=1)
Workers Planned: 2Workers Launched: 2-> Hash Join (cost=3254.87..171700.33 rows=3976 width=8) (actual time=20.033..514.916
rows=70484 loops=3)
Hash Cond: (store_sales.ss_sold_date_sk = date_dim.d_date_sk)-> Parallel Seq Scan on store_sales (cost=0.00..159405.96 rows=2400396 width=16)(actual time=0.013..322.422 rows=1920250 loops=3)-> Hash (cost=3253.36..3253.36 rows=121 width=8) (actual time=19.853..19.853 row
s=122 loops=3)
Buckets: 1024 Batches: 1 Memory Usage: 13kB-> Seq Scan on date_dim (cost=0.00..3253.36 rows=121 width=8) (actual time
=9.799..19.836 rows=122 loops=3)
Filter: ((d_moy >= 4) AND (d_moy <= 7) AND (d_year = 2002))
Rows Removed by Filter: 72927-> Index Scan using customer_pkey on customer c (cost=0.42..208296.27 rows=1 width=24) (actual tim
e=0.034..0.034 rows=0 loops=17305)
Index Cond: (c_customer_sk = store_sales.ss_customer_sk)
Filter: ((alternatives: SubPlan 1 or hashed SubPlan 2) OR (alternatives: SubPlan 3 or hashed S
ubPlan 4))
Rows Removed by Filter: 1★3 SubPlan 1-> Nested Loop (cost=0.29..69605.71 rows=1 width=0) (never executed)-> Seq Scan on web_sales (cost=0.00..69376.54 rows=28 width=8) (never executed)
Filter: (c.c_customer_sk = ws_bill_customer_sk)-> Index Scan using date_dim_pkey on date_dim date_dim_1 (cost=0.29..8.17 rows=1 width=8) (never executed)
Index Cond: (d_date_sk = web_sales.ws_sold_date_sk)
Filter: ((d_moy >= 4) AND (d_moy <= 7) AND (d_year = 2002))
SubPlan 2-> Gather (cost=4254.87..64134.86 rows=2384 width=8) (actual time=19.795..181.225 rows=552
59 loops=1)
Workers Planned: 2Workers Launched: 2-> Hash Join (cost=3254.87..62896.46 rows=993 width=8) (actual time=19.257..176.775
rows=18420 loops=3)

Page 53 of 86

PostgreSQL Enterprise Consortium
Hash Cond: (web_sales_1.ws_sold_date_sk = date_dim_2.d_date_sk)-> Parallel Seq Scan on web_sales web_sales_1 (cost=0.00..57382.85 rows=599685
width=16) (actual time=0.009..107.567 rows=479749 loops=3)-> Hash (cost=3253.36..3253.36 rows=121 width=8) (actual time=19.055..19.055 r
ows=122 loops=3)
Buckets: 1024 Batches: 1 Memory Usage: 13kB-> Seq Scan on date_dim date_dim_2 (cost=0.00..3253.36 rows=121 width=8)(actual time=9.966..19.026 rows=122 loops=3)
Filter: ((d_moy >= 4) AND (d_moy <= 7) AND (d_year = 2002))
Rows Removed by Filter: 72927★4 SubPlan 3-> Nested Loop (cost=0.29..138689.82 rows=1 width=0) (never executed)-> Seq Scan on catalog_sales (cost=0.00..138322.75 rows=46 width=8) (never executed)
Filter: (c.c_customer_sk = cs_ship_customer_sk)-> Index Scan using date_dim_pkey on date_dim date_dim_3 (cost=0.29..7.97 rows=1 width=8) (never executed)
Index Cond: (d_date_sk = catalog_sales.cs_sold_date_sk)
Filter: ((d_moy >= 4) AND (d_moy <= 7) AND (d_year = 2002))
SubPlan 4-> Gather (cost=4254.87..123574.10 rows=4771 width=8) (actual time=251.298..330.496 rows=1
10495 loops=1)
Workers Planned: 2Workers Launched: 2-> Hash Join (cost=3254.87..122097.00 rows=1988 width=8) (actual time=248.959..310.3
83 rows=36832 loops=3)
Hash Cond: (catalog_sales_1.cs_sold_date_sk = date_dim_4.d_date_sk)-> Parallel Seq Scan on catalog_sales catalog_sales_1 (cost=0.00..114322.25 ro
ws=1200025 width=16) (actual time=0.009..200.903 rows=960019 loops=3)-> Hash (cost=3253.36..3253.36 rows=121 width=8) (actual time=17.051..17.051 r
ows=122 loops=3)
Buckets: 1024 Batches: 1 Memory Usage: 13kB-> Seq Scan on date_dim date_dim_4 (cost=0.00..3253.36 rows=121 width=8)(actual time=8.867..17.027 rows=122 loops=3)
Filter: ((d_moy >= 4) AND (d_moy <= 7) AND (d_year = 2002))
Rows Removed by Filter: 72927-> Index Scan using customer_address_pkey on customer_address ca (cost=0.29..0.38 rows=1 width=8) (actual time=0.004..0.004 rows=0 loops=1912)
Index Cond: (ca_address_sk = c.c_current_addr_sk)
Filter: ((ca_county)::text = ANY ('{"Walker County","Richland County","Gaines County","Douglas County","Dona Ana County"}'::text[]))Rows Removed by Filter: 1
Planning time: 2.310 ms
Execution time: 5838.753 ms(74 rows)
ここで注目するのは、n ever execu ted となっている部分 [10] です。 バージョン9.5 ではSu b Plan 2 (上記バージョン9.5 のEXPLAIN ANALYZE ★1 印)とSu b Plan 4 (上記バージョン9.5 のEXPLAIN ANALYZE ★2 印)がn ever execu ted となっているのに対し、 バージョン9.6 ではSu b Plan 1 (上記バージョン9.6 のEXPLAIN ANALYZE ★3 印)とSu b Plan 3 (上記バージョン9.6 のEXPLAIN ANALYZE ★4 印)がn ever execu ted となっています。

[10] 実行計画としてはあったが、実際の実行時に何らか(ジョイン対象のテーブル検索の結果が0 件であった、など)の理由で、実行不要と判断され、実行されなかったことを示します。
ここから、実行計画としてはパラレルクエリ実行部分以外での差異はないものの、 実際のテーブルに対する検索・ジョインの操作が行われた内容が異なっていることになります。
特に、バージョン9.5 の場合、ジョイン操作の中では、データ量が多い場合に最も非効率とされているNested Lo o p を Su b Plan 1 では17304 回、Su b Plan 3 では16785
回繰り返しており、 実行時間の長大化に拍車がかかった可能性があります。
対して、バージョン9.6 の場合、ジョイン操作の中では、データ量が多い場合に Nested Lo o p よりも効率的とされているHash Jo in を Su b Plan 2 、Su b Plan 4 ともに 1 回のみ実行しており、 実行時間の数千倍高速化という、劇的な短縮に寄与した可能性があります。
しかし、 対照群(パラレルクエリo ff) の結果から、バージョン9.5 とパラレルクエリo ff のバージョン9.6 、および、バージョン10 の性能差は、 バージョン9.6 がバージョン9.5 比で20% 程度、バージョン10 でも9.5 比で+ 20% 倍程度のスピードであり、 上記の数千倍からは大きく乖離しています。
これは、パラレルクエリを有効にすることで、実行計画上の差異ではわからない差異が実際には発生し、 実行時間がまったく異なる可能性がある、ということを示しています。 No .10 のクエリでは高速化しましたが、実際のクエリでは逆に大幅に実行時間が長くなることもあり得るため、 注意が必要であると考えます。
なお、バージョン9.6 とバージョン10 の間のEXPLAIN ANALYZE の結果も同様でしたが、バージョン9.6 とバージョン10 ではバージョン10 のほうが高速化しています。 これは、 対照群(パラレルクエリo ff) での測定で示されたとおり、パラレルクエリ以外での改善によるものと考えられます。

6.6.1.2. N o.11
No .11 では、検証サーバ1 、検証サーバ2 ともに、パラレルクエリのないバージョン9.5 、パラレルクエリを選択しなかったバージョン9.6 よりも、 パラレルクエリを選択したバージョン
10 で高速化しました。
ここで、検証サーバ2 で採取した、バージョン9.5 とバージョン10 のEXPLAIN ANALYZE の結果を比較します。

Page 54 of 86

PostgreSQL Enterprise Consortium
バージョン9.5

QUERY PLAN-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------Limit (cost=2098571.40..2098571.41 rows=4 width=132) (actual time=9882417.331..9882417.344 rows=100 loops=1)
CTE year_total-> Append (cost=944045.46..1393256.05 rows=6715350 width=220) (actual time=31347.496..39832.048 rows=461362 loops=1)-> GroupAggregate (cost=944045.46..1155118.18 rows=5276818 width=166) (actual time=31347.494..37126.071 rows=350725 loops=1)
Group Key: customer.c_customer_id, customer.c_first_name, customer.c_last_name, customer.c_preferred_cust_flag, customer.c_birth_country, customer.c_login, customer.c_email_address, date_dim.d_year-> Sort (cost=944045.46..957237.51 rows=5276818 width=166) (actual time=31347.437..33488.240 rows=5371601 loops=1)
Sort Key: customer.c_customer_id, customer.c_first_name, customer.c_last_name, customer.c_preferred_cust_flag, custo
mer.c_birth_country, customer.c_login, customer.c_email_address, date_dim.d_year▲ Sort Method: external merge Disk: 883896kB-> Hash Join (cost=11694.60..354856.10 rows=5276818 width=166) (actual time=139.594..4694.187 rows=5371601 loops=1)
Hash Cond: (store_sales.ss_sold_date_sk = date_dim.d_date_sk)-> Hash Join (cost=8076.00..277802.21 rows=5511229 width=166) (actual time=104.472..3431.795 rows=5501511 lo
ops=1)Hash Cond: (store_sales.ss_customer_sk = customer.c_customer_sk)-> Seq Scan on store_sales (cost=0.00..193010.67 rows=5760867 width=26) (actual time=0.013..982.918 ro
ws=5760749 loops=1)-> Hash (cost=6276.00..6276.00 rows=144000 width=156) (actual time=103.472..103.472 rows=144000 loops=
1)
Buckets: 262144 Batches: 1 Memory Usage: 26182kB-> Seq Scan on customer (cost=0.00..6276.00 rows=144000 width=156) (actual time=0.006..59.612 ro
ws=144000 loops=1)-> Hash (cost=2705.49..2705.49 rows=73049 width=16) (actual time=34.605..34.605 rows=73049 loops=1)
Buckets: 131072 Batches: 1 Memory Usage: 4449kB-> Seq Scan on date_dim (cost=0.00..2705.49 rows=73049 width=16) (actual time=0.011..23.222 rows=73049
loops=1)-> HashAggregate (cost=153002.71..170984.36 rows=1438532 width=169) (actual time=2596.201..2677.001 rows=110637 loops=1)
Group Key: customer_1.c_customer_id, customer_1.c_first_name, customer_1.c_last_name, customer_1.c_preferred_cust_flag, cu
stomer_1.c_birth_country, customer_1.c_login, customer_1.c_email_address, date_dim_1.d_year-> Hash Join (cost=11694.60..117039.41 rows=1438532 width=169) (actual time=110.878..1271.497 rows=1438731 loops=1)
Hash Cond: (web_sales.ws_sold_date_sk = date_dim_1.d_date_sk)-> Hash Join (cost=8076.00..93639.92 rows=1438820 width=169) (actual time=85.471..936.814 rows=1438929 loops=1)
Hash Cond: (web_sales.ws_bill_customer_sk = customer_1.c_customer_sk)-> Seq Scan on web_sales (cost=0.00..65778.52 rows=1439252 width=29) (actual time=0.009..249.180 rows=143924
7 loops=1)-> Hash (cost=6276.00..6276.00 rows=144000 width=156) (actual time=84.549..84.549 rows=144000 loops=1)
Buckets: 262144 Batches: 1 Memory Usage: 26182kB-> Seq Scan on customer customer_1 (cost=0.00..6276.00 rows=144000 width=156) (actual time=0.008..42.5
86 rows=144000 loops=1)-> Hash (cost=2705.49..2705.49 rows=73049 width=16) (actual time=24.930..24.930 rows=73049 loops=1)
Buckets: 131072 Batches: 1 Memory Usage: 4449kB-> Seq Scan on date_dim date_dim_1 (cost=0.00..2705.49 rows=73049 width=16) (actual time=0.019..14.193 rows=
73049 loops=1)-> Sort (cost=705315.35..705315.36 rows=4 width=132) (actual time=9882417.328..9882417.334 rows=100 loops=1)
Sort Key: t_s_secyear.customer_id, t_s_secyear.customer_first_name, t_s_secyear.customer_last_name, t_s_secyear.customer_email_add
ress
Sort Method: top-N heapsort Memory: 51kB-> Nested Loop (cost=0.00..705315.31 rows=4 width=132) (actual time=65298.027..9882415.035 rows=382 loops=1)
Join Filter: ((t_s_secyear.customer_id = t_w_secyear.customer_id) AND (CASE WHEN (t_w_firstyear.year_total > '0'::numeric) T
HEN (t_w_secyear.year_total / t_w_firstyear.year_total) ELSE 0.0 END > CASE WHEN (t_s_firstyear.year_total > '0'::numeric) THEN (t_s_secyea
r.year_total / t_s_firstyear.year_total) ELSE 0.0 END))
Rows Removed by Join Filter: 116789448-> Nested Loop (cost=0.00..537356.80 rows=13 width=268) (actual time=51185.761..9440691.635 rows=5287 loops=1)
Join Filter: (t_s_firstyear.customer_id = t_s_secyear.customer_id)
Rows Removed by Join Filter: 757357814-> Nested Loop (cost=0.00..369414.25 rows=16 width=104) (actual time=41605.749..8383949.375 rows=10841 loops=1)
Join Filter: (t_s_firstyear.customer_id = t_w_firstyear.customer_id)
Rows Removed by Join Filter: 1554943027-> CTE Scan on year_total t_s_firstyear (cost=0.00..184672.13 rows=56 width=52) (actual time=31347.529..31679.
091 rows=69732 loops=1)
Filter: ((year_total > '0'::numeric) AND (sale_type = 's'::text) AND (dyear = 2001))
Rows Removed by Filter: 391630-> CTE Scan on year_total t_w_firstyear (cost=0.00..184672.13 rows=56 width=52) (actual time=86.506..117.877 r
ows=22299 loops=69732)
Filter: ((year_total > '0'::numeric) AND (sale_type = 'w'::text) AND (dyear = 2001))
Rows Removed by Filter: 439063-> CTE Scan on year_total t_s_secyear (cost=0.00..167883.75 rows=168 width=164) (actual time=0.002..91.634 rows=6986
1 loops=10841)
Filter: ((sale_type = 's'::text) AND (dyear = 2002))
Rows Removed by Filter: 391501-> CTE Scan on year_total t_w_secyear (cost=0.00..167883.75 rows=168 width=52) (actual time=58.814..81.687 rows=22090 loop
s=5287)Filter: ((sale_type = 'w'::text) AND (dyear = 2002))
Rows Removed by Filter: 439272
Planning time: 1.732 ms
Page 55 of 86

PostgreSQL Enterprise Consortium
Execution time: 9882579.077 ms(58 rows)
バージョン10QUERY PLAN-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------Limit (cost=2325263.07..2325263.08 rows=5 width=132) (actual time=9167300.012..9167300.025 rows=100 loops=1)
CTE year_total-> Append (cost=487078.35..1569013.03 rows=7199995 width=220) (actual time=5368.720..10511.778 rows=461362 loops=1)-> Finalize GroupAggregate (cost=487078.35..1329228.33 rows=5760759 width=220) (actual time=5368.718..7740.506 rows=350725 loo
ps=1)Group Key: customer.c_customer_id, customer.c_first_name, customer.c_last_name, customer.c_preferred_cust_flag, customer.c_birth_country, customer.c_login, customer.c_email_address, date_dim.d_year★ -> Gather Merge (cost=487078.35..1137203.04 rows=4800632 width=188) (actual time=5368.659..7284.982 rows=526909 loops=1)
Workers Planned: 2Workers Launched: 2-> Partial GroupAggregate (cost=486078.33..582090.97 rows=2400316 width=188) (actual time=5297.614..6795.760 rows=
175636 loops=3)
Group Key: customer.c_customer_id, customer.c_first_name, customer.c_last_name, customer.c_preferred_cust_flag, customer.c_birth_country, customer.c_login, customer.c_email_address, date_dim.d_year-> Sort (cost=486078.33..492079.12 rows=2400316 width=166) (actual time=5297.576..5509.034 rows=1790534 loop
s=3)
Sort Key: customer.c_customer_id, customer.c_first_name, customer.c_last_name, customer.c_preferred_cust_flag, customer.c_birth_country, customer.c_login, customer.c_email_address, date_dim.d_year▲ Sort Method: quicksort Memory: 518574kB-> Hash Join (cost=11694.60..231707.33 rows=2400316 width=166) (actual time=129.090..1662.490 rows=179
0534 loops=3)
Hash Cond: (store_sales.ss_sold_date_sk = date_dim.d_date_sk)-> Hash Join (cost=8076.00..197785.01 rows=2400316 width=166) (actual time=97.578..1187.631 rows
=1833837 loops=3)
Hash Cond: (store_sales.ss_customer_sk = customer.c_customer_sk)-> Parallel Seq Scan on store_sales (cost=0.00..159405.16 rows=2400316 width=26) (actual t
ime=0.014..341.113 rows=1920250 loops=3)-> Hash (cost=6276.00..6276.00 rows=144000 width=156) (actual time=96.616..96.616 rows=144000 loops=3)
Buckets: 262144 Batches: 1 Memory Usage: 26182kB-> Seq Scan on customer (cost=0.00..6276.00 rows=144000 width=156) (actual time=0.01
5..52.952 rows=144000 loops=3)-> Hash (cost=2705.49..2705.49 rows=73049 width=16) (actual time=30.976..30.976 rows=73049 loops=3)
Buckets: 131072 Batches: 1 Memory Usage: 4449kB-> Seq Scan on date_dim (cost=0.00..2705.49 rows=73049 width=16) (actual time=0.019..19.52
1 rows=73049 loops=3)-> HashAggregate (cost=149794.31..167784.76 rows=1439236 width=220) (actual time=2659.957..2741.482 rows=110637 loops=1)
Group Key: customer_1.c_customer_id, customer_1.c_first_name, customer_1.c_last_name, customer_1.c_preferred_cust_flag, cu
stomer_1.c_birth_country, customer_1.c_login, customer_1.c_email_address, date_dim_1.d_year-> Hash Join (cost=11694.60..113813.41 rows=1439236 width=169) (actual time=114.108..1395.779 rows=1438731 loops=1)
Hash Cond: (web_sales.ws_sold_date_sk = date_dim_1.d_date_sk)-> Hash Join (cost=8076.00..92024.63 rows=1439236 width=169) (actual time=86.674..1025.239 rows=1438929 loops=1)
Hash Cond: (web_sales.ws_bill_customer_sk = customer_1.c_customer_sk)-> Seq Scan on web_sales (cost=0.00..65778.36 rows=1439236 width=29) (actual time=0.015..287.207 rows=143924
7 loops=1)-> Hash (cost=6276.00..6276.00 rows=144000 width=156) (actual time=85.756..85.756 rows=144000 loops=1)
Buckets: 262144 Batches: 1 Memory Usage: 26182kB-> Seq Scan on customer customer_1 (cost=0.00..6276.00 rows=144000 width=156) (actual time=0.008..43.6
11 rows=144000 loops=1)-> Hash (cost=2705.49..2705.49 rows=73049 width=16) (actual time=26.996..26.996 rows=73049 loops=1)
Buckets: 131072 Batches: 1 Memory Usage: 4449kB-> Seq Scan on date_dim date_dim_1 (cost=0.00..2705.49 rows=73049 width=16) (actual time=0.023..15.640 rows=
73049 loops=1)-> Sort (cost=756250.03..756250.05 rows=5 width=132) (actual time=9167300.007..9167300.013 rows=100 loops=1)
Sort Key: t_s_secyear.customer_id, t_s_secyear.customer_first_name, t_s_secyear.customer_last_name, t_s_secyear.customer_email_add
ress
Sort Method: top-N heapsort Memory: 51kB-> Nested Loop (cost=0.00..756249.97 rows=5 width=132) (actual time=34279.533..9167297.564 rows=382 loops=1)
Join Filter: ((t_s_secyear.customer_id = t_w_secyear.customer_id) AND (CASE WHEN (t_w_firstyear.year_total > '0'::numeric) T
HEN (t_w_secyear.year_total / t_w_firstyear.year_total) ELSE 0.0 END > CASE WHEN (t_s_firstyear.year_total > '0'::numeric) THEN (t_s_secyea
r.year_total / t_s_firstyear.year_total) ELSE 0.0 END))
Rows Removed by Join Filter: 116789448-> Nested Loop (cost=0.00..576151.10 rows=16 width=268) (actual time=21125.197..8715422.593 rows=5287 loops=1)
Join Filter: (t_s_firstyear.customer_id = t_s_secyear.customer_id)
Rows Removed by Join Filter: 757357814-> Nested Loop (cost=0.00..396080.13 rows=18 width=104) (actual time=12131.633..7708400.851 rows=10841 loops=1)
Join Filter: (t_s_firstyear.customer_id = t_w_firstyear.customer_id)
Rows Removed by Join Filter: 1554943027-> CTE Scan on year_total t_s_firstyear (cost=0.00..197999.86 rows=60 width=52) (actual time=5368.741..5627.44
3 rows=69732 loops=1)
Filter: ((year_total > '0'::numeric) AND (sale_type = 's'::text) AND (dyear = 2001))

Page 56 of 86

PostgreSQL Enterprise Consortium
Rows Removed by Filter: 391630-> CTE Scan on year_total t_w_firstyear (cost=0.00..197999.86 rows=60 width=52) (actual time=83.745..108.815 r
ows=22299 loops=69732)
Filter: ((year_total > '0'::numeric) AND (sale_type = 'w'::text) AND (dyear = 2001))
Rows Removed by Filter: 439063-> CTE Scan on year_total t_s_secyear (cost=0.00..179999.88 rows=180 width=164) (actual time=0.002..87.811 rows=6986
1 loops=10841)
Filter: ((sale_type = 's'::text) AND (dyear = 2002))
Rows Removed by Filter: 391501-> CTE Scan on year_total t_w_secyear (cost=0.00..179999.88 rows=180 width=52) (actual time=65.129..83.847 rows=22090 loop
s=5287)Filter: ((sale_type = 'w'::text) AND (dyear = 2002))
Rows Removed by Filter: 439272
Planning time: 2.155 ms
Execution time: 9167346.764 ms(63 rows)
変化した部分は、パラレルクエリ実行を示すG ath er の有無(上記バージョン10 のEXPLAIN ANALYZE ★印の行)と、So rt Meth o d(上記バージョン9.6 のEXPLAINANALYZE ▲ 印 と 上記バージョン10 のEXPLAIN ANALYZE ▲ 印)の違いになります。

So rt Meth o d がバージョン10 では効率が良いインメモリ処理のQ u ick So rt であるのに対し、 バージョン9.5 では若干効率の劣るMerge So rt で、ディスクを作業領域に使用して処理されています。
一般的に、ソートの方式として Q u ick So rt が選択されない原因は、実行計画作成時に予想される作業メモリ量が w o rk_mem パラメータで指定した値を超えてしまうことにあります。パラレルクエリを用いない場合は、 ソート対象となるデータ量が多くなると予想され、メモリの確保を断念したものと考えます。 一方、パラレルクエリを用いる場
合は、ソートもパラレルクエリ実行の対象に含まれるため、 本ケースの場合は、1 ワーカーが担当するソート対象のデータ量が3 分の1 となり、メモリ確保可能と判断したと考えます。
検証サーバ2 はディスクがSSD であるため、ディスクが作業領域として使用されても、 大きな性能劣化は発生しにくいと考えますが、通常のハードディスクが作業領域として使用される場合は、 性能が大きく劣化することが予想され、パラレルクエリ実行によって Q u ick So rt を選択可能となっただけでも性能の改善が見込まれます。
データ量が処理方式を左右する操作(ソート、ジョイン、集約)の場合は、パラレルクエリ実行に伴って、 より効率的な処理方式を選択する可能性があるものと考えます。

6.6.2. 検証 B

6.6.2.1. N o.10
No .10 では、検証サーバ1 、および、検証サーバ2 ともに、並列処理数の増加にともなって、高速化する傾向にありました。
理論上、並列処理数とパラレルクエリで実行された部分の処理時間は反比例の関係にありますが、 並列処理数と処理時間の間において、正確な反比例の関係が認められませんでした。 特に、検証サーバ2 では、グラフの形状からは反比例の関係を推測できる形状になっていませんでした。 また、ワーカー数2 とワーカー数8 の間における、性能の変化はワーカー数2 に対してワーカー数8 が、 検証サーバ1 で12.3% 改善、検証サーバ2 で6.3% 改善と小さく、No .10 における処理時間の大半はパラレルクエリ実行できない部分が 占めていることが示唆されます。
ここで、No .10 において実行計画を確認すると、パラレルクエリ実行を有効にした結果、 パラレルクエリ実行の対象となっていないジョイン操作(考察 検証A No .10 バージョン9.6 のEXPLAIN ANALYZE 9 行目のNested Lo o p )が 全体5.86 秒に対して 4.11 秒強と73% を占めていました。 また、他のワーカー数(4, 6, 8)における実行計画を確認したところ、当該部分はそれぞれ4.33 秒強、4.28 秒弱、4.20 秒弱となり、 4.11 秒から見て、2% 〜5% 程度のばらつきが見られました。 ここからは、No .10 のクエリの実行
時間において、パラレルクエリ実行に要した時間は支配的ではなかったということ、 パラレルクエリ外に要した時間について無視できない大きさのばらつきが含まれていたことが示唆されます。
また、パラレルクエリ実行された部分のみの実行時間で比較すると、 検証B 補足 パラレルで動作した部分の比較(検証サーバ2) より、 検証サーバ2 では、グラフの形状が反比例の関係に近い高速化の傾向にあったことが確認できますが、 反比例の曲線が本来存在するべきであろう位置から、x 軸から y軸の+ の方向に 0.3 秒〜0.4 秒弱移動しているような グラフとなっています。 ここからは、パラレルクエリ実行において、0.3 秒〜0.4 秒弱の固定的な時間を追加で要していることが示唆されます。
以上から、ワーカー数による性能差は、パラレルクエリ実行による改善分とパラレルクエリ実行に伴うオーバヘッド分、 パラレルクエリ外の要因の合成となり、オーバヘッド分よりも、パラレルクエリ外に要した時間が無視できない大きさでばらついたことから、 グラフが複雑な形状となった可能性があると考えます。

6.6.2.2. N o.11
No .11 では、検証サーバ1 では並列処理数の増加に伴って、高速化する傾向を確認できましたが、 ワーカー数2 とワーカー数4 では0.03% 程度の改善とほとんど効果が見られませんでした。 これは、ワーカー数2 とワーカー数4 の間でのパラレルクエリ実行に関するオーバヘッドが増加したが、 その増加分をパラレルクエリ実行で埋められなかったため、と考えます。
また、ワーカー数6 とワーカー数8 との比較では、ワーカー数8 が0.38% の低速化が認められました。 こちらに関しては、実行計画を確認したところ、No .10 と同様にパラレル
クエリ実行における並列処理数は、 今回の条件では5 が最大であったので、ワーカー数6 とワーカー数8 では実行計画が同一となり、 処理時間が0.38% 微増と、ほとんど変化していないことから、概ね妥当と考えます。
検証サーバ2 においては、No .11 では逆に低速化する傾向が認められました。 ただし、 検証B 補足 パラレルで動作した部分の比較(検証サーバ2) に示したとおり、パラレ
ルクエリで実行された部分に関しては、 理論通りの高速化傾向を示している点、クエリ実行全体の処理時間9000 秒強に対して、 パラレルクエリ実行部分の処理時間がPage 57 of 86

PostgreSQL Enterprise Consortium

5 秒弱〜23 秒弱程度(0.06% 〜0.25%)と比率が極めて小さい点から、 低速化した原因は、パラレルクエリ実行におけるオーバヘッド、 もしくはパラレルクエリ実行の部分以外での要因がもととなっているものと考えます。
以上の結果から、パラレルクエリ実行に伴うオーバヘッドの大きさが、パラレルクエリ実行による高速化分を上回る場合がありうると考えます。 また、パラレルクエリでの実行が選択されても、処理時間全体に占めるパラレルクエリ実行部分の比率からは、 大きな改善が見込めない場合も存在することが示されたと考えます。

6.6.3. 総括
Po stgreSQ L 9.6 においてパラレルクエリが実装されたことによって、大規模エンタープライズ用途向けの機能の一つがPo stgreSQ L に新たに加わり、 Po stgreSQ L は新たな時代に突入したと感じていましたが、実際に検証を行った結果、パラレルクエリの使用には細心の注意が必要であることが明らかになりました。
特に、パラレルクエリ実行により、実行計画の取得だけでは判明しない差異が存在しないかの確認、 パラレルクエリ実行の処理時間と、オーバヘッドやパラレルクエリ部分以外の処理時間の割合を算出し、 効果が十分に得られるかどうかの確認が必要であるものと考えます。
以上から、現状のパラレルクエリの実装においては、O LAP 用途での使用には不安が残る結果となりました。
より不安なくパラレルクエリを使用できるよう、次期バージョンでのパラレルクエリのさらなる進化と、これを司るプランナ・エグゼキュータのさらなる深化に期待したいです。

Page 58 of 86

PostgreSQL Enterprise Consortium

7. 全文検索7.1. 検証概要
近年の全文検索のユースケースでは、静的なデータを検索するだけではなく、データが継続して変更されている なかで検索を行う事が多くなっています。 例えば...
口コミサイト(口コミは継続的に更新される、口コミが更新されている最中も口コミは検索される)
動画共有サイト(動画は継続的に投稿され更新されている、動画が更新されている最中も動画は検索される)
上記のようなケースでは、同一のDB に対して更新と検索が同時に発生するため、十分なパフォーマンスが 得られないと予想されます。
そこで、Po stgreSQ L10 から実装されたロジカルレプリケーションを使用した負荷分散を行い、 上記のようなケースで十分なパフォーマンスが得られるかを検証します。
ロジカルレプリケーションを用いた負荷分散は以下のような構成で行います。

Master をデータの更新専用とし、全文検索用のインデックスを設定しません。
Slave をデータ検索専用とし、全文検索用のインデックスを設定します。
全文検索は、Po stgreSQ L に以下の全文検索用のモジュールを使います。

p g_b igm （ピージーバイグラム）
PG ro o n ga （ピージールンガ）

7.2. 検証構成
7.2.1. マシ ン 構成
本検証に用いたハードウェア構成を 表. 7.1 、 ソフトウェア構成を 表. 7.2 に示します。

表 7.1 ハードウェア構成
項目

仕様

機種

Amazo n W eb Service(AW S) m4.2xlarge

CPU

In tel(R) Xeo n (R) CPU E5-2686 v4 @2.30G Hz
(8 コア)

メモリ

32G B

内蔵ストレージ

SSD 256G B
表 7.2 ソフトウェア構成

ソフト ウェ ア

バージョ ンCen tO S

7.4 （ 64b it ）

用途

備考

OS

Po stgreSQ L 10.1

データベース

p g_b igm

1.2

インデックスPG ro o n ga

2.0.3

インデックスG ro o n ga

7.1.0

インデックスPG ro o n ga の動作に必要

7.2.2. 全文検索用モジュ ー ル
本検証で利用した全文検索用モジュールを 表. 7.3 に示します。

表 7.3 検証対象の全文検索用モジュール
名称

説明

ラ イ センス

解析方法

p g_b igm

日本語に対応した全文検索機能を提供するモジュール

Po stgreSQ L Licen se

2-gramPG ro o n ga

日本語に対応した全文検索機能として実績の豊富なG ro o n ga をPo stgreSQ L から利用可能にするモジュール

Po stgreSQ L Licen se

N-gram

7.2.3. postgresql.confの 設定値
p o stgresql.co n f の設定値を 表. 7.4 のように変更しています。 今回は大量のデータに一度にインデックスを作成するため、main ten an ce_w o rk_mem を多めに確保しPage 59 of 86

PostgreSQL Enterprise Consortiumています。

表 7.4 p o stgresql.co n f の設定値
パラ メ ータ

設定値

max_co n n ectio n s

100

sh ared_b u fferes

8G B

max_w al_size

1G B

main ten an ce_w o rk_mem

4G B

考え 方

搭載メモリの1/4 を割り当て

インデックス作成の際に必要となる領域のため、多めに確保

7.3. 検証方法
7.3.1. 検証構成
検証構成を 表. 7.5 に示します。

表 7.5 検証構成と測定項目
検証構成
レプリケーション構成なし

測定項目
データ更新性能* インデックスなしの時のデータ更新性能* p g_b igm のインデックスありの時のデータ更新性能* PG ro o n ga のインデックスありの時のデータ更新性能
全文検索性能* インデックスなしの時の全文検索性能* p g_b igm のインデックスありの時の全文検索性能* PG ro o n ga のインデックスありの時の全文検索性能

ロジカルレプリケーション構成

データ更新性能* インデックスなしの時のデータ更新性能* p g_b igm のインデックスありの時のデータ更新性能* PG ro o n ga のインデックスありの時のデータ更新性能
全文検索性能* インデックスなしの時の全文検索性能* p g_b igm のインデックスありの時の全文検索性能* PG ro o n ga のインデックスありの時の全文検索性能

レプリケーション構成なしと、ロジカルレプリケーション構成時のデータ更新性能、全文検索性能を比較します。
ロジカルレプリケーション構成時は、Master(データ更新用)のDB には全文検索用のインデックスを設定しないため、インデックスを設定するレプリケーション構成なしの時のデータ更新性能と比べることで、どの程度更新性能が向上したかを示すことができます。

7.3.2. 全文検索対象の デ ー タ
本検証の検索対象は、国立情報学研究所のダウンロードサービスにより株式会社ドワンゴから提供を受けた「 ニコニコ動画コメント等データ 」内の動画のメタデータを
Po stgreSQ L へjso n b 型として格納したものです。 表. 7.6 にテーブル構造とデータの例を示します。

表 7.6 テーブル名「 n iko n iko 」
record （ jsonb 型）

tag （ Text型）

備考{"tags": ["料理", "カレー"], "title": "テスト", "len gth ": 578, "catego ry": "料
表中の X には、任意の数値が入ります。
理", "size_lo w ": 29606343, "video _id": "smXXXXXXX", "file_typ e": "flv", "size_h igh ": 31095758, "w atch _n u m": XXXX, "mylist_n u m": 22,"co mmen t_n u m": 290, "descrip tio n ": "テスト", "u p lo ad_time":
XXXXXXXXXX}

1

7.3.3. イン デ ッ クスの 作成方法
作成したテーブルの「 reco rd 」カラムに対し、CREATE INDEXコマンドでインデックスを作成します。 インデックスは、良く検索されるであろう、動画のタイトル(title)と動画の詳細(descrip tio n )に対してインデックスを設定します。 全文検索のインデックスは以下の5 パターンの設定を行います。
インデックスなし

Page 60 of 86

PostgreSQL Enterprise Consortium

p g_b igm のインデックス2 種類

CREATE EXTENSION pg_bigm;
CREATE INDEX pgbigm_title_index ON nikoniko USING gin((record->>'title') gin_bigm_ops);
CREATE EXTENSION pg_bigm;
CREATE INDEX pgbigm_description_index ON nikoniko USING gin((record->>'description') gin_bigm_ops);
PG ro o n ga のインデックス2 種類

CREATE EXTENSION pgroonga;
CREATE INDEX pgroonga_title_index ON nikoniko USING pgroonga((record->>'title'));CREATE EXTENSION pgroonga;
CREATE INDEX pgroonga_description_index ON nikoniko USING pgroonga((record->>'description'));7.3.4. 背景負荷
背景負荷は、断続的に INSERTを行うことで実現します。 背景負荷のスループットは以下の通りです。
背景負荷(約1200[reco rd/s])

INSERTするデータは以下のようなJSO N データです。

{"tags": ["xxx", "xxxx", "xxxx"],"title": "xxxx","length": 208,
"category": "ゲーム","size_low": 9274707,"video_id": "smXXXXX","file_type": "flv","size_high": 10298881,"watch_num": 201902,"mylist_num": 3112,"comment_num": 3788,"description": "xxxxxxxxx","upload_time": XXXXXXXXXX}

7.3.5. 検索方法
動画検索で検索されやすい、動画のタイトル、動画の詳細を対象に検索します。 検索キーワードは、ヒット数が0 にならない一般的な用語とします。
検索に使うクエリーは以下の通りです。

PG ro o n ga のインデックス使用時
動画タイトルでの検索

SELECT COUNT(*) FROM fluentd WHERE (record ->> 'title') &@ 'カレー';
動画詳細での検索

SELECT COUNT(*) FROM fluentd WHERE (record ->> 'description') &@ 'カレー';p g_b igm のインデックス使用時、インデックスなしの時
動画タイトルでの検索

SELECT COUNT(*) FROM fluentd WHERE (record->>'title') LIKE '%カレー%';
動画詳細での検索

Page 61 of 86

PostgreSQL Enterprise Consortium

SELECT COUNT(*) FROM fluentd WHERE (record->>'description') LIKE '%カレー%';7.4. 検証結果
7.4.1. レプリ ケー シ ョ ン 構成なし
7.4.1.1. データ 更新性能
表. 7.7 にデータ更新性能を記載します。 データ更新性能は、1 秒間あたりに INSERTしたレコード数を測定しており、 表. 7.7 に記載されている数値が大きいほど 高速にデータを更新していることを表しています。
以下の通り、インデックスなしのときが最もデータ更新が速く、PG ro o n ga とp g_b igm はインデックスを設定する キーによって、更新性能が異なります。

descrip tio n キーのように、長いテキストが多いカラムにインデックスを設定した場合：更新性能（良） インデックスなし ＞ PG ronnga ＞ pg_bigm 更新性能（悪）title キーのように、短いテキストが多いカラムにインデックスを設定した場合：更新性能（良） インデックスなし ＞ pg_bigm ＞ PG ronnga 更新性能（悪）表 7.7 データ更新性能
イ ンデック スなし

pg_bigm のイ ン

PGroonga のイ ン

デック スありデック スあり

データ更新性能[in sert/s](descrip tio n キーにインデックスを設定)

1305[in sert/s]

944[in sert/s]

998[in sert/s]

データ更新性能[in sert/s](title キーにインデックスを設定)

1305[in sert/s]

1202[in sert/s]

1152[in sert/s]

7.4.1.2. 全文検索性能表. 7.8 、表. 7.9 に 全文検索性能を記載します。 全文検索性能は、平均レイテンシを測定しており、表. 7.8 、表. 7.9 に記載されている数値が小さいほど、高速に検索出来ることを表します。 検索に 1 件もヒットしない状態にならないように、事前に 203317 レコードを登録済みの状態で計測します。 背景負荷がある場合は、INSERTとSELECTを別々のインスタンスから実行し、全文検索性能を測定します。

表 7.8 全文検索性能 動画タイトルでの検索
背景負荷

イ ンデック スなし

pg_bigm イ ンデック スあり

PGroonga イ ンデック スありなし

62.48[ms]0.46[ms]

0.88[ms]あり

121.44[ms]1.63[ms]

0.95[ms]

表 7.9 全文検索性能 動画の詳細での検索
背景負荷

イ ンデック スなし

pg_bigm イ ンデック スあり

PGroonga イ ンデック スありなし

138.66[ms]1.62[ms]

1.12[ms]あり

330.07[ms]2.09[ms]

1.30[ms]

7.4.2. ロジカル レプリ ケー シ ョ ン 構成
7.4.2.1. データ 更新性能
表. 7.10 にデータ更新性能を記載します。 データ更新性能は、1 秒間あたりに INSERTしたレコード数を測定しており、 表. 7.10 に記載されている数値が大きいほど 高
速にデータを更新していることを表しています。
ロジカルレプリケーション構成の場合は、データ更新専用にデータベースを用意するので、 全文検索用のインデックスを設定しません。 そのため、結果はインデックスなしの時のデータ更新性能のみとなります。

表 7.10 データ更新性能
イ ンデック スなし
データ更新性能[in sert/s]

1292[in sert/s]

7.4.2.2. 全文検索性能表. 7.11 、表. 7.12 に 全文検索性能を記載します。 全文検索性能は、平均レイテンシを測定しており、表. 7.11 、表. 7.12 に記載されている数値が小さいほど、高速

Page 62 of 86

PostgreSQL Enterprise Consortiumに検索出来ることを表します。
検索に 1 件もヒットしない状態にならないように、事前に 203317 レコードを登録済みの状態で計測します。 背景負荷がある場合は、INSERTとSELECTを別々のインスタン
スから実行し、全文検索性能を測定します。

表 7.11 全文検索性能 動画タイトルでの検索
背景負荷

イ ンデック スなし

pg_bigm イ ンデック スあり

PGroonga イ ンデック スありなし

60.26[ms]1.93[ms]

0.88[ms]あり

118.94[ms]2.15[ms]

0.92[ms]

表 7.12 全文検索性能 動画の詳細での検索
背景負荷

イ ンデック スなし

pg_bigm イ ンデック スあり

PGroonga イ ンデック スありなし

138.44[ms]1.92[ms]

1.11[ms]あり

262.53[ms]2.11[ms]

1.16[ms]

7.4.3. 結果比較
7.4.3.1. データ 更新性能
図. 7.1 に、レプリケーション構成なしとロジカルレプリケーション 構成のデータ更新性能の比較結果を示します。 以下のグラフは左から、レプリケーション構成なしでインデック
スなし、p g_b igm のインデックスあり、 PG ro o n ga のインデックスあり、ロジカルレプリケーション構成のMaster のデータ更新性能を示しています。

Page 63 of 86

PostgreSQL Enterprise Consortium

図 7.1 データ更新性能比較
上記グラフから、レプリケーション構成なしでインデックスなしの時のデータ更新性能と ロジカルレプリケーション構成のデータ更新性能は、ほぼ同じ性能であることがわかります。 これは、ロジカルレプリケーション構成のMaster データベースはデータ更新専用に運用されるため、 全文検索用のインデックスを設定していないためです。
レプリケーション構成のない、単一のデータベースで全文検索のインデックスを設定する場合は、 上記グラフの左から 2,3 番目の値が示すとおり、インデックスなしよりデータ更新性能が落ちますが、 ロジカルレプリケーション構成の場合は、Slave に全文検索のインデックスを設定するため、 データ更新性能を落とさず、全文検索の高速化が可能です。

7.4.3.2. 全文検索性能
図. 7.2 に、レプリケーション構成なしの時の全文検索性能と ロジカルレプリケーション構成時の全文検索性能の比較結果を示します。 背景負荷がある状態での全文検索性能を比較しています。

Page 64 of 86

PostgreSQL Enterprise Consortium

図 7.2 全文検索性能
インデックスなしの場合は、ロジカルレプリケーション構成の方がデータ更新の影響を受けないため、 全文検索性能が向上しています。 p g_b igm とPG ro o n ga のインデックスが設定されている場合は、 レプリケーション構成なしの時の全文検索性能とあまり変化はありません。
上記2 つの比較結果から、ロジカルレプリケーション構成にすることで、データの更新性能を落とさずに、 全文検索性能を向上させることができます。

7.5. 考察
全文検索用のインデックスを設定すると、全文検索性能が大幅に向上しますが、単一のデータベースで 更新も全文検索も実施する場合は、全文検索用のインデックスが設定されているとデータ更新性能 が落ちてしまいます。
今回の検証では、ロジカルレプリケーションを用いて、データ更新を行うデータベースには全文検索用の インデックスを設定せず、検索用のデータベースを用意し、検索用のPage 65 of 86

PostgreSQL Enterprise Consortium
データベースにのみインデックスを 設定する構成でのパフォーマンスを検証しました。 また、ロジカルレプリケーションを非同期で実施することによって、データ更新用のデータベースへの 性能影響を抑えています。 ロジカルレプリケーションが非同期で実施されることにより、最新の更新がSlave へ反映されませんが、 今回のモデルのような検索シス
テムでは、最新状態であることは必須ではないため、現実の運用としては、 問題ないと判断しました。
データ更新専用のデータベースを用意することで、データ更新用のデータベースには全文検索用のインデックス を設定しなくても良くなります。検証の結果から、このような負荷分散を行うことで、全文検索用のインデックス が設定されていることによるデータ更新の劣化を防ぐことができる事がわかりました。
また、ロジカルレプリケーション構成時の全文検索性能の結果から、この検索専用のデータベースに全文検索用の インデックスを設定した場合の検索性能とレプリケーショ
ン構成なしでの全文検索性能がほぼ変わらないことから 今回の検証のような負荷分散を行った構成でも、通常の構成と同様の全文検索性能が発揮できることがわかりました。
上記から、Master とSlave に別々のインデックスを設定できるロジカルレプリケーションを利用した負荷分散 構成をつくることで、全文検索用のインデックスによるデータ更新
性能の劣化を起こさずに、全文検索用の インデックスを利用した高速な全文検索が可能になります。

Page 66 of 86

PostgreSQL Enterprise Consortium

8. レプリケーション検証
8.1. 検証概要
Po stgreSQ L では、9.0 からレプリケーション機能を実装しており、継続的に機能強化が行われています。 9.6 からは、2 台以上の複製先に対してデータを同期しながら更新が行える、複数同期レプリケーションが利用可能となりました。 これにより、負荷分散構成でのデータの信頼性向上などが期待されます。
しかしながら、従来まで可能であった非同期での複数台レプリケーションに比べ、同期処理にかかるオーバヘッドによってスループットが低下することが予想されます。 また、同期の台数を増加させることによる性能的なオーバヘッドや、同期・非同期を混在させた環境での動作については懸念も存在します。
本章では、Po stgreSQ L におけるレプリケーション機能について、 同期レプリケーション・非同期レプリケーション、またそれらが混在する構成において、どのように性能が変化するのかを検証しました。

8.1.1. レプリ ケー シ ョ ン とは
データベースにおいて、レプリケーションとは複数のデータべースサーバの間で、データの一貫性を保ちながら、その内容を複製する手法を指します。 複製を作成することで、障害発生時のバックアップや、負荷分散等の冗長化構成を取ることが可能となることから、 データベースの可用性や性能向上を目的として利用される機能です。

Po stgreSQ L においては、Master 側のデータベースに対する操作が記録された W AL(W rite Ah ead Lo ggin g)ファイルを Slave 側に転送し、反映することでレプリケーションが実現されます。転送時の処理方法を設定することにより、同期方式を選択することが可能となっています。
また、転送された W AL ファイルのSlave 側の処理の違いにより、Po stgreSQ L におけるレプリケーションには ｢同期レプリケーション｣と｢非同期レプリケーション｣の2 種類の形態が存在します。

8.1.1.1. 同期方式
Po stgreSQ L では、同期中のW AL ファイルの処理を設定することにより、同期のレベルを設定することが出来ます。 同期のレベルを高くすると、Slave 側への同期が保証されるデータが増えますが、その分の処理によるオーバヘッドがかかるため、パフォーマンスが低下することになります。
同期方式は、p o stgresql.co n f のパラメータ 'syn ch ro n o u s_co mmit' により設定可能であり、以下の5 つから選択することが可能です。本検証では、デフォルトの設定である'o n ' に設定し、測定を行っています。

表 8.1 同期方式の比較
設定

内容

remo te_ap p ly

完全同期。W AL 適用まで保証。Slave から Master への昇格時の時間短縮と参照負荷分散の拡充が目的。

on

同期。W AL 転送（ディスク書き込み）まで保証。データ保護が目的。

remo te_w rite

準同期。W AL 転送（メモリ書き込み）まで保証。データ保護とパフォーマンスのバランスが目的。

lo cal非同期。ローカルのW AL 書き込みまで保証。パフォーマンス優先が目的。

o ff

完全非同期。ローカルのW AL 書き込みも保証しない。最も高パフォーマンスだが、非現実的。

8.1.1.2. 同期レプリケ ーショ ン
同期レプリケーションとは、Master から Slave へW AL ファイルを転送した際に、Master がSlave への反映完了を待つレプリケーション方式です。 Master はW AL ファイルを転送後、Slave の応答を待ってから次の処理に移ります。
処理の流れは以下のようになり、①から順に処理が実行されます。Clien t が⑥O K を受け取るためには、Slave での④W AL 書き込みの処理が完了し、⑤応答を受け取る必要があります。

Page 67 of 86

PostgreSQL Enterprise Consortium

このため、Master でコミットが成功した場合、Slave にもデータが反映されていることが保証されます。 ただし、コミットの完了にはSlave からの応答を待つ必要があるため、
単位時間当たりの処理性能は低くなります。

8.1.1.3. 非同期レプリケ ーショ ン
非同期レプリケーションは、同期レプリケーションと異なり、Master がSlave の反映完了を待たないレプリケーション方式です。 Master はW AL ファイルをSlave へ転送した後、すぐに次の処理に移ります。
処理の流れは以下のようになり、①から順に処理が実行されます。同期の場合と異なり、Slave での⑤W AL 書き込みの処理の前に、Clien t には③O K が返されています。

このため、Master とSlave のデータは必ずしも一致するとは言えません。 一方で、コミットの完了にはSlave からの応答を待つ必要がないため、単位時間の処理性能は高くなります。
表. 8.2 に、それぞれの方式の特長をまとめます。

Page 68 of 86

PostgreSQL Enterprise Consortium
表 8.2 レプリケーション方式の比較
同期レプリケ ーショ ン

非同期レプリケ ーショ ン

Master のコミット時

Slave の反映完了を待つ

Slave の反映完了を待たない

コミットされているデータの内容

Master とSlave で一致する

Master とSlave で一致するとは限らない

処理性能

比較的低い

比較的高い

8.2. 検証構成
8.2.1. 検証サ ー バ
本検証を実施するにあたり、各検証サーバには仮想マシン(KVM)を用いました。 負荷かけ用のClien t マシン1 台、レプリケーション元となるMaster マシン1 台、レプリケーショ
ン先となるSlave マシン3 台、計5 台の構成です。
表. 8.3 にホストマシン、 表. 8.4 にゲストマシンの構成を示します。

表 8.3 ホストマシン構成
ホスト マシン ×2
機種

PRIMERG Y CX 2550 M2

CPU

インテル Xeo n プロセッサ E5-2650 v4 48 コア 2.2G Hz

メモリ

256G B

ストレージ

内蔵 2.5 インチ SSD–400G B × 24

OS

Cen tO S 7.3

表 8.4 ゲストマシン構成

Slave*3 台

ClientM asterOS

Cen tO S 7.3

Cen tO S 7.3

Cen tO S 7.3

vCPU

4

4

4

メモリ

48G B

48G B

48G B

ディスク

200G B

200G B

200G BDB MS

Po stgreSQ L 10.1 Po stgreSQ L 10.1 Po stgreSQ L 10.1

また、それぞれの仮想マシンは以下の様にネットワークを設定しました。

Page 69 of 86

PostgreSQL Enterprise Consortium

8.2.2. デ ー タベ ー ス設定
レプリケーション検証を行うための、Po stgreSQ L の各種設定を以下に示します。

8.2.2.1. postgresql.confの設定
Master のp o stgresql.co n f の設定を 表. 8.5 に、 Slave のp o stgresql.co n f の設定を 表. 8.6 に示します。これらはデフォルトから変更した値のみとなります。
表 8.5 Master のp o stgresql.co n f 設定
パラ メ ータ

設定値

sh ared_b u ffres

16G B

w al_level

rep lica

syn ch ro n o u s_co mmiton

max_w al_size

8G B

max_w al_sen ders4w al_keep _segmen t

16#syn ch ro n o u s_stan db y_n ames "X(< 同期とするSlave サーバのap p licatio n _n ame> )"#X= 同期とするサーバ数
au to vacu u mo ff

表 8.6 Slave のp o stgresql.co n f の設定
パラ メ ータ

設定値

sh ared_b u ffres

16G B

w al_level

rep lica

syn ch ro n o u s_co mmit o n
max_w al_size

8G B

max_w al_sen ders4w al_keep _segmen t

16

au to vacu u mo ff

h o t_stan db yonPage 70 of 86

PostgreSQL Enterprise Consortium

8.2.2.2. pg_hba.confの設定
Master 側での認証のために、p g_h b a.co n f の設定を以下の様にします。

host
host
host
host

all
replication
replication
replication(負荷掛けマシンのIP)/24(Slaveマシン1のIP)/24(Slaveマシン2のIP)/24(Slaveマシン3のIP)/24

all
repl_user
repl_user
repl_user

trust
trust
trust
trust

8.3. 検証方法
8.3.1. 検証パター ン
本検証では、以下の2 パターンで性能を比較します。

8.3.2. 検証 A(Slaveの 台数を増加させた場合 )検証A では、Slave 台数を1 台～3 台に変更し、Slave 台数の増加による 性能影響を同期レプリケーション、非同期レプリケーションそれぞれで明らかにします。

8.3.3. 検証 B(同期・ 非同期混在の 場合 )検証B では、同期・非同期が混在する構成での検証を行います。 Slave の合計台数が3 台となるように、以下の4 パターンで性能を比較します。

表 8.7 検証B のパターン
パタ ーン

同期

非同期

非同期のみ

0台

3台

同期・非同期混在①

1台

2台

同期・非同期混在②

2台

1台

同期のみ

3台

0台

8.3.4. 環境
8.3.4.1. データ ベースの初期設定
in itdb コマンドにてデータベースクラスタを作成します。

initdb --no-locale -E UTF8
先述した通りに、p g_h b a.co n f を編集します。

vi pg_hba.conf
p o stgresql.co n f を先に述べた設定に編集し、データベースを起動します。

vi postgresql.conf
pg_ctl -w start
8.3.4.2. M aster側の設定検証用のデータベースを作成します。 p gb en ch の初期化オプションを用いて、スケールファクタ = 1000 のおおよそ15G B のデータベースを作成します。

createdb pgbench
pgbench -i -s 1000 pgbench
レプリケーション用のユーザを作成します。

psql -c "CREATE ROLE repl_user LOGIN REPLICATION PASSWORD 'password'"
CREATE ROLE

Page 71 of 86

PostgreSQL Enterprise Consortium

8.3.4.3. 同期・ 非同期の設定
同期・非同期で共通の設定

Slave にて、Master のデータベースのバックアップ(複製)を取ります。

pg_basebackup -h <MasterサーバのIPアドレス> -D $PGDATA -R --progress -U repl_user
p o stgresql.co n f を設定し、データベースサーバを起動します。

vi postgresql.conf
pg_ctl -w start
Slave のreco very.co n f へap p licatio n _n ame の記述を追加します。 下記ではSlave2 を例としています。

vi recovery.conf~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~# primary_conninfoの末尾に application_name=slave2を追加
同期の場合の設定同期とする場合には、Master のp o stgres.co n f 内、syn ch ro n o u s_stan db y_n ames を下記のように、適した値に設定する必要があります。 下記では一例として、同
期台数2 台(slave1 とslave2)としています。

vi postgresql.conf~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
synchronous_standby_names='2(slave1,slave2)'
8.3.4.4. 各データ ベースサーバ再起動
同期・非同期の設定後、Master とSlave それぞれのPo stgreSQ L を再起動します。

pg_ctl -w restart

8.3.5. 測定
性能測定には、Po stgreSQ L に標準で同梱されているp gb en ch を使用しました。 p gb en ch では、ベンチマーク用のスクリプトをユーザにてカスタマイズすることが可能です。 本検証では、以下に示す簡単な更新処理を行うカスタムスクリプトで測定を行いました。

\set naccounts 100000 * :scale\set aid random(1, :naccounts)
UPDATE pgbench_accounts
SET filler = repeat(md5(clock_timestamp()::text),2)
WHERE aid = :aid;
また、キャッシュによる測定値の影響を排除するため、以下の処理の順で測定を行ないました。

1. VACU U M 処理の実施
2. CHECKPO INT処理の実施
3. 各マシンのキャッシュクリア
4. p g_p rew arm によるデータのロード
5. p gb en ch によるTPS 値の測定
これらを1 パターンにつき3 回実施し、各パターンの平均値を結果としました。 以下にその処理を行ったスクリプトを示します。

Page 72 of 86

PostgreSQL Enterprise Consortium#!/bin/bash
mkdir /data/$1
for i in `seq 1 3`; do#VACUUM処理の実施
vacuumdb -h <MasterのIP> -a -z#CHECKPOINT処理の実施
psql -h <MasterのIP> pgbench -c "CHECKPOINT;"#各マシンのキャッシュクリア
echo "password" | sudo -S ssh <MasterのIP> "sync"
echo "password" | sudo -S ssh <MasterのIP> "echo 3 > /proc/sys/vm/drop_caches"echo "password" | sudo -S ssh <Slave1のIP> "sync"
echo "password" | sudo -S ssh <Slave1のIP> "echo 3 > /proc/sys/vm/drop_caches"echo "password" | sudo -S ssh <Slave2のIP> "sync"
echo "password" | sudo -S ssh <Slave2のIP> "echo 3 > /proc/sys/vm/drop_caches"echo "password" | sudo -S ssh <Slave3のIP> "sync"
echo "password" | sudo -S ssh <Slave3のIP> "echo 3 > /proc/sys/vm/drop_caches"#pg_prewarmによるデータのロード
psql -h <MasterのIP> pgbench -c "SELECT * FROM pg_prewarm('pgbench_accounts')"#pgbenchによるTPS値の測定
pgbench -n -c 64 -T 300 -f script.sh -s 1000 -h <MasterのIP> pgbench >/data/$1/bench_data_${i}.txt
done8.4. 検証結果
8.4.1. 検証 A(Slaveの 台数を増加させた場合 )検証A での結果は下記となります。

表 8.8 同期レプリケーションの結果
同期台数

TPS 値

レプリケ ーショ ンなし の TPS 値を 100% と し た と きの割合（参考）レプリケーションなし

9254.0（ 100.0% ）1台

4668.650.4%

2台

4014.443.4%

3台3686.339.8%
表 8.9 非同期レプリケーションの結果

非同期台数

TPS 値

レプリケ ーショ ンなし の TPS 値を 100% と し た と きの割合（参考）レプリケーションなし

9254.0（ 100.0% ）1台

8495.991.8%

2台

7786.984.1%

3台

7205.377.9%

Page 73 of 86

PostgreSQL Enterprise Consortium

8.4.2. 検証 B(同期・ 非同期混在の 場合 )検証B での結果は以下となります。

表 8.10 検証B 結果
パタ ーン

同期

非同期

TPS 値

レプリケ ーショ ンなし の TPS 値
を 100% と し た と きの割合（参考）レプリケーションなし

0台

0台

9254.0（ 100.0% ）

非同期のみ

0台

3台

7205.377.9%

同期・非同期混在①1台

2台

4043.6

43.7% [1]同期・非同期混在②2台

1台

3822.9

41.3% [2]

同期のみ

3台

0台

3686.339.8%[1] 同期1 台のみは50.4% 、非同期2 台のみは84.1% のため、単純に掛け合わせると42.4% となるが、上回っている。
[2] 同期2 台のみは43.4% 、非同期1 台のみは91.8% のため、単純に掛け合わせると39.8% となるが、上回っている。

Page 74 of 86

PostgreSQL Enterprise Consortium

8.5. 考察
今回の構成では、Master とSlave は同じホストマシン上で稼働しており、ネットワークとストレージは物理的には同一のものを使用しています。 そのため、Slave のノード数が多くなるほど、物理的なリソースの競合により性能に影響が出てきたのではないかと考えられます。 今回の検証では詳細な原因の特定には至りませんでしたが、2012 年度に PG ECo n s で実施した「更新系・複数台レプリケーション検証」 [3] でも 同様の傾向が見られており、非同期レプリケーションであっても必ずしもMaster の更新性能への影響が少ないわけではなく、 スケールアウトによるボトルネックが出てきてしまうケースがあると言えます。

[3] PG ECo n s 2012 年度W G 1 活動報告 p .41 「 (4) ネットワークやストレージ構成について」

8.5.1. 検証 Aについ て
同期のみの構成の場合は、非同期のみの構成の場合に比べ約1/2 の性能値となりました。 同期の場合、一つの処理の完了にはMaster とSlave 双方の処理の完了を待つ必要があります。 一方で非同期の場合は、Master だけの処理が完了すれば次の処理が開始されます。 このことから、同期の場合は非同期に比べ、処理の完了を待つ対象が2 倍になるため、 TPS 値が約1/2 になったものと考えられます。
また、同期・非同期ともに、サーバ台数を増やすとTPS 値が下がっていく傾向が見られました。 特に、Slave 側の処理を待たない非同期の場合でも、サーバ台数を増やすことでTPS 値の低下が見られる結果となりました。 TPS 値の低下の度合いを見てみると、サーバ台数を増やすごとに TPS 値が約10% ずつ減少していることが分かり、 複製先が4 台以上となっても同じように性能は一定の割合で逓減していくことが考えられます。

8.5.2. 検証 Bについ て
表. 8.10 で見たように、同じ台数の構成であっても、同期の台数を増やすほど性能値が低下していく傾向を見ることが出来ました。 また、非同期を同期に 1 台変更するごとに約5% ずつ TPS 値が減少しており、 検証A と同様、台数を変化させる毎に性能は一定の割合で逓減していくことが考えられます。
非同期のみの構成と比較すると、同期を1 台でも追加すると性能値が急落するということも確認できました。 これは検証A と同様に、同期ではSlave 側の処理を待つ時間が増えるためと考えらえます。 また、同期ではSlave 側の処理の完了時に Master 側への応答が返ってくるため、ネットワークの使用量が増加します。 そのため、検証A の場
合と同様に、ネットワークのリソース競合により性能が低下することが考えらえます。

8.5.3. まとめ
本章では、Po stgreSQ L 9.6 より利用可能となった複数同期レプリケーションを利用した構成での性能測定を行い、 非同期のみの構成、同期・非同期が混在する構成との比較検証を行いました。
検証結果から、今回の検証環境下では以下のような傾向を見ることができました。

1. 同期のみの構成は、非同期のみの構成に比べ約1/2 の性能となる。
2. 同期・非同期混在の構成では、総台数が同じでも同期の台数を増やすことで性能の低下が見られる。
3. 同期・非同期の台数を変化させることで、ある程度一定の割合で性能値も変化している。

Page 75 of 86

PostgreSQL Enterprise Consortium
特に 3 ．に関しては、今回検証を行った環境よりSlave 数の多い構成でも サイジングの基礎値として利用可能な値が取れたのではないかと考えられます。
また、今回の検証では原因の特定までには至りませんでしたが、性能に影響を与える要因として、 ネットワークやストレージのリソースを共有していることによるオーバーヘッドが考えられます。 レプリケーション構成を考える際は、Po stgreSQ L の設定だけではなく、サーバの配置やマシンの構成も 考慮する必要があると言えそうです。

Page 76 of 86

PostgreSQL Enterprise Consortium

9. FDW検証
9.1. 検証概要
Po stgreSQ L から外部のデータへアクセスするための仕組みであるFDW (Fo reign Data W rap p er)は近年Po stgreSQ L が最も力を入れて強化している機能の一つです。この機能を用いることで、点在する様々な外部データをPo stgreSQ L から一括して管理する事ができるため、企業のデータ活用に非常に有望視されています。しかしながら、性能的なオーバヘッドに対する懸念も存在します。 そこで本検証では、Po stgreSQ L 10 系のFDW 機能に注目して、参照系、更新系における性能オーバヘッドを明らかにします。
検証用データベースに Po stgreSQ L に標準で同梱されているp gb en ch から生成したものに加え、CREATE TAB LE によりカスタムに作成したテーブルを組み合わせ使用しています。 詳細は後述します。 また、FDW モジュールにはPo stgreSQ L9.3 より実装されているp o stgres_fdw を使用しました。このモジュールを用いることで、外部に存在するPo stgreSQ L のテーブルを内部に存在するテーブルと同様に扱うことができます。 なお、FDW モジュールとしてはPo stgreSQ L だけでなく、MySQ L 、O racleDB 、CSV
ファイル、Mo n go DB 等、様々なデータソースへアクセス可能なものが提供されています。 詳細は公式w iki に記載されています（ h ttp s://w iki.p o stgresql.o rg/w iki/Fo reign _data_w rap p ers ）。

9.2. 検証構成
本検証では、負荷クライアント(以降「 Clien t 」 )からデータベースサーバ(以降、「 In tern al 」 )のいくつかのテーブルにアクセスします。「 In tern al 」のテーブルに格納されるデー
タの実体は、「 In tern al 」の中に存在する場合もあるし、FDW 機能によって接続された 2 つの外部データベースサーバ(以降、「 Extern al-1 」「 Extern al-2 」 )に存在する場
合もあります。

9.2.1. ハー ドウ ェア構成
ハードウェア構成を 表. 9.1 に示します。なお、今回、データベースサーバはすべて仮想環境としています。本検証は、FDW 機能を利用する場合と利用しない場合でのオー
バヘッドを測定する事が目的であるため、仮想環境である点は性能面で考慮不要と考えました。

表 9.1 ハードウェア構成
種別

メ モリ

CPU

ディスク

In tern al

仮想

2.40G Hz 2co res

4 GB

20 G B

Extern al-1

仮想

2.40G Hz 2co res

4 GB

20 G B

Extern al-2仮想

2.40G Hz 2co res

4 GB

20 G B

Clien t

物理

In tel(R) Xeo n (R) E5620 24 G B
2.40G Hz 16co res

9.2.2. ソフトウ ェア構成
ソフトウェア構成を 表. 9.2 に示します。

Page 77 of 86

PostgreSQL Enterprise Consortium
表 9.2 ソフトウェア構成
ソフト ウェ アOS
In tern al

Cen tO S 7.4(1708)

Po stgreSQ L 10.3

Extern al-1

Cen tO S 7.4(1708)

Po stgreSQ L 10.3

Extern al-2

Cen tO S 7.4(1708)

Po stgreSQ L 10.3

Clien tCen tO S 7.4(1708)

JDB C Ru n n er 1.2
O p en JDK 1.8.0_161
p o stgresql-jdb c 42.2.2-1

9.2.3. デ ー タベ ー ス構成
9.2.3.1. テーブル構成
本検証では、簡単な銀行の口座処理を模擬しています。この銀行のデータベースは、顧客情報(addrb o o k)、口座情報 (p gb en ch _acco u n ts)、取引履歴(p gb en ch _h isto ry)の3 つのテーブルを持っています。なお、今回は1 人の顧客が1 つの口座を持つ (顧客のPRIMARY KEYであるID と口座のPRIMARY KEYであるID が1 対
1 に紐付く )ことを想定としています。 なお、口座情報(p gb en ch _acco u n ts)、取引履歴(p gb en ch _h isto ry)については、Po stgreSQ L の標準ベンチマークツールである
p gb en ch を利用して作成し、顧客情報(addrb o o k)テーブルについては下記のCREATE TAB LE により個別なテーブルを作成しました。
顧客情報(addrb o o k)
氏名、メールアドレス、性別、年齢などの情報を持つ顧客テーブルを以下の様に作成しました。 なお、顧客情報テーブルには、「なんちゃって個人情報(h ttp ://kazin a.co m/du mmy/in dex.h tml)」を利用して作成した 10 万件のデータを格納しています。

CREATE SEQUENCE addrbook_id_seq;
CREATE TABLE addrbook (idbigint PRIMARY KEY DEFAULT nextval('addrbook_id_seq'::regclass),
namecharacter varying(32),kanacharacter varying(32),emailcharacter varying(64),gendercharacter(1),ageinteger,birthdaydate,marriagecharacter(2),blood_type character(3),divisioncharacter varying(4),phone_nocharacter varying(12),mobile_no character varying(13),carriercharacter varying(10),
note
text
);
講座情報(p gb en ch _acco u n ts)、取引履歴(p gb en ch _h isto ry)
講座情報(p gb en ch _acco u n ts)、取引履歴(p gb en ch _h isto ry)テーブルは、p gb en ch にて Scalin g Facto r = 1 で生成しました。 下記にテーブル生成時のコマンドを示します。

$ /usr/pgsql-10/bin/pgbench -i -s 1 fdwdb
9.2.3.2. PostgreSQL の設定
今回の検証環境においてデフォルトより変更した設定について以下に示します。

p o stgresql.co n f の設定

listen_addresses = '*'shared_buffers = 1024MB
work_mem = 8MB
effective_cache_size = 1GB
max_connections = 110
p g_h b a.co n f の設定

Page 78 of 86

PostgreSQL Enterprise Consortium

host

all

all

(Client’s IP Address)/24

trust

9.3. 検証方法
検証は参照・更新・挿入のそれぞれの処理を外部データの有無のパターンで測定し、 内部テーブルのみの場合を基準値とした場合において、外部テーブルの変化/増加に伴いどの程度の性能オーバーヘッドが発生するかを検証していきます。

9.3.1. 測定方法
以下の方法で測定を行いました。なお、測定には｢JDB C Ru n n er ｣を用いています。
共通設定
・走行開始後10 秒は計測を行わず、10 秒経過後に 60 秒間のスループットを計測します。
・ 各パターン3 回測定して、中央値を採用します。
参照(SELECT)での設定
・ 同時接続数は1 、10 、20 、30 、40 、50 、60 、70 、80 、90 、100 の11 パターン。
更新(U PDATE)、挿入(INSERT)での設定
・ 同時接続数は1 のみ(注)(注)FDW を使用した場合、外部データベース側のPo stgreSQ L では、トランザクション隔離レベルが、SERIALIZAB LE かREPEATAB LE READ しか使用できず、多重度が増すとU PDATE 時に｢co u ld n o t serialize access du e to co n cu rren t u p date ｣エラーが頻発するため、更新、挿入では、同時接続数１のみ実施しています。

9.3.2. 参照 (SELECT)
9.3.2.1. 検証パタ ーン
パターン１
顧客情報(addrb o o k)、口座情報(p gb en ch _acco u n ts)共に内部テーブルである場合。

パターン２
顧客情報(addrb o o k)が内部テーブル、口座情報(p gb en ch _acco u n ts)が外部テーブルである場合。

Page 79 of 86

PostgreSQL Enterprise Consortium

パターン３
顧客情報(addrb o o k)が外部テーブル、口座情報(p gb en ch _acco u n ts)が内部テーブルである場合。

パターン４
顧客情報(addrb o o k)、口座情報(p gb en ch _acco u n ts)共に外部テーブルである場合。

Page 80 of 86

PostgreSQL Enterprise Consortium

9.3.2.2. データ ベースへのアク セス
ある顧客に対して、顧客情報(addrb o o k)から氏名(n ame)、年齢(age)、口座情報(p gb en ch _acco u n t)から残高(ab alan ce)を抽出します。

SELECT ad.name, ad.age, ac.abalance
FROM addrbook ad, pgbench_accounts ac
WHERE ad.id = $int AND ad.id = ac.aid

9.3.3. 更新 (UPDATE)
9.3.3.1. 検証パタ ーン
更新対象のテーブル(今回は口座情報である、p gb en ch _accn o u n ts)が内部データの場合と外部データの場合で測定します。

9.3.3.2. データ ベースへのアク セス
ある口座(p gb en ch _acco u n ts)の残高(ab alan ce)を増加させます。

UPDATE pgbench_accounts
SET abalance = abalance + $int_a WHERE aid = $int_b$in t_a = -999999 ～ 999999 の整数(乱数)$in t_b = 1 ～ 100000 の整数(乱数)9.3.4. 挿入 (INSERT)
9.3.4.1. 検証パタ ーン
データの挿入対象のテーブル(今回は取引履歴であるp gb en ch _h isto ry)が内部データの場合と外部データの場合で測定します。

9.3.4.2. データ ベースへのアク セス
取引履歴(p gb en ch _h isto ry)に適当な履歴を挿入します。

INSERT INTO pgbench_history (tid, bid, aid, delta)
VALUES ($int_a, 1, $int_b, $int_c)$in t_a = 1 ～ 10 の整数(乱数)$in t_b = 1 ～ 100000 の整数(乱数)$in t_c = -999999 ～ 999999 の整数(乱数)Page 81 of 86

PostgreSQL Enterprise Consortium

9.4. 検証結果
9.4.1. 参照 (SELECT)
外部テーブル参照のあり/無しで大きく性能が異なりました。 下記図と 表. 9.3 にその結果を示します。
またパターン2 、3 、4 にはパターン1 を基準とした時の性能(Th ro u gh p u t)劣化率を記載しています。

表 9.3 結果一覧

1

10

20

30

40

50

60

70

80

90

100

パターン1

3869.215675.2

15593.4

15561.3

15517.1

15350.5

15164.8

14872.3

14492.1

14016.6

13605.8

パターン2

296.4
▲92.3%

2852.0▲81.8%

3347.2▲78.5%

3379.8▲78.23%3353.4▲78.4%

3340.5▲78.2%

3350.8▲77.9%

3350.1▲77.5%

3222.5▲77.8%

3269.2▲76.7%

3222.8▲76.3%

パターン3

276.6
▲92.9%

2916.8▲81.4%

3181.6▲79.6%

3240.4▲79.2%

3253.6▲79.0%

3229.8▲79.0%

3199.2▲78.9%

3222.1▲78.3%

3145.7▲78.3%

3119.1▲77.7%

3108.5▲77.2%

161.7
1905.52204.52214.02231.12184.22208.6▲95.8%▲87.8%▲85.9%▲85.8%▲85.6%▲85.8%▲85.4%
パターン1 ：顧客情報(addrb o o k)、口座情報(p gb en ch _acco u n ts)共に内部テーブル
パターン2 ：顧客情報(addrb o o k)が内部テーブル、口座情報(p gb en ch _acco u n ts)が外部テーブル
パターン3 ：顧客情報(addrb o o k)が外部テーブル、口座情報(p gb en ch _acco u n ts)が内部テーブル
パターン4 ：顧客情報(addrb o o k)、口座情報(p gb en ch _acco u n ts)共に外部テーブル

2166.6▲85.4%

2125.3▲85.3%

2118.9▲84.9%

2112.7▲84.5%

パターン4

同時接続数1 の場合では、片方が外部テーブルとなるパターン2/パターン3 において ▲92 ～93% 、両方が外部テーブルとなるパターン4 において ▲96% の性能(Th ro u gh p u t)劣化となりました。 同時接続数10 ～100 において大きく傾向は変わりませんが、パターン2/パターン3 において ▲76 ～81% 、パターン4 において ▲84 ～87%
劣化していました。

9.4.2. 更新 (UPDATE)
今回の環境で外部テーブルを更新した場合(FDW 機能あり)、内部テーブルの更新(FDW 機能なし)に比べて、約31% 性能(Th ro u gh p u t)が劣化しています。

Page 82 of 86

PostgreSQL Enterprise Consortium

9.4.3. 挿入 (INSERT)
今回の環境で外部テーブルにデータを挿入した場合(FDW 機能あり)、内部テーブルへの挿入(FDW 機能なし)に比べて、約34% 性能(Th ro u gh p u t)が劣化しました。

9.5. 考察
参照においては、測定条件によって異なりますが▲76% ～▲91% 、更新・挿入においては▲35% 前後の性能低下が見られました。
個々のアクセスのレスポンス時間を比較すると、同時接続数100 の場合、内部テーブルのみで平均14ms 、すべて外部テーブルの場合でも平均70ms となっています。今回、非常に単純なアクセスパターンであったため、内部テーブルのみのレスポンス時間が非常に短く、外部テーブルアクセスのオーバヘッドの影響が大きく出る結果となったと想定されます。
更新・挿入においてもレスポンス時間は全パターンで10ms 前後であり、外部テーブルアクセスによるオーバヘッドの大きさは同様の傾向であると考えられます。
来年度以降の測定においては、複数のテーブルの結合など、内部テーブルのみであったとしても時間のかかる処理を対象として測定することで、外部テーブル処理のオーバ
ヘッドをより明らかにできるのではないかと考えます。

Page 83 of 86

PostgreSQL Enterprise Consortium

10. おわりに今年度(2017 年度)は、Po stgreSQ L エンタープライズ・コンソーシアム(PG ECo n s)の発足から数えて 6 年目となり、わたくしども技術部会ワーキンググループ 1(以下、本W G )も、今回で 6 期目となりました。本 W G では昨年度に PG ECo n s のワーキンググループの位置づけを見直してから、性能に加えて新技術の検証も行う「新技術検証
ワーキンググループ」として活動しました。本報告書では、以下の 6 つのテーマの検証結果を報告しました。

1. Po stgreSQ L 10 および前バージョン9.6 と比較したスケール性の検証
2. W in do w s 版Po stgreSQ L とLin u x 版Po stgreSQ L の性能比較検証
3. Po stgreSQ L 10 で強化されたパラレルクエリ検証
4. Po stgreSQ L 10 で実装されたロジカルレプリケーションを利用した全文検索検証
5. Po stgreSQ L 9.6 で実装された複数同期レプリケーション検証
6. Fo reign Data W rap p er 検証
以下では、今年度の検証活動を振り返って、具体的な進め方をご紹介することで、報告書のあとがきとしたいと思います。まず、テーマの選定にあたっては、参加メンバからテーマを募るとともに、PG ECo n s の成果報告会や、オープンソースカンファレンスなどに参加されたお客様に記入いただくアンケートを参考に進めました。
例年通りの定点観測を行うことはもちろんのことながら、さらに今年度は定点観測と同様の検証モデルを用いて今までW G 1 で触れてこなかった W in do w s 版
Po stgreSQ L の性能検証を行うこととなりました。以前から、W in do w s でもPo stgreSQ L サーバを立てるケースが増えるに従い、W in do w s 版Po stgreSQ L の実際の性能、特に Lin u x 版Po stgreSQ L と比較した際の性能を知りたいという要望が多くなってきました。今回のW in do w s 版Po stgreSQ L 検証ではLin u x 版との性能比較に加えて W in do w s 版固有のチューニング要素も検証対象となっており、W in do w s 版Po stgreSQ L 利用者にとって有用な情報を提供できることが期待されます。 また、検証
テーマを考慮する上でPo stgreSQ L 最新バージョンの新機能は外せません。バージョンが10 となった今回は強化されたパラレルクエリ、ロジカルレプリケーションが検証対象となりました。 さらに、複数同期レプリケーション検証やFo reign Data W rap p er の検証といったテーマは過去に検証しきれなかったテーマを改めて今回選定しています。
各テーマごとの検証活動は担当する企業が主体となって進めます。各担当企業が作成した検証計画は、定例の会合で議論しました。提出された検証計画に対して「どのような観点で・何を計測することで、検証の目的が満たされるのか」検討します。その中で不足している観点や冗長な測定パターンが明らかになることもあります。こうして検証計画が固まると、約2 週間から 1 ヶ月程度、実機上で測定作業をします。得られたデータは整理されて会合に提出されます。「検証の目的に適ったデータが得られているか」確認し、「そのデータの意味するところは何か」考察して、少しでも質の高い結果が得られるように議論を重ねます。
こうした作業を積み重ねることで、単にベンチマークプログラムの測定値に留まらない、有用な結果が得られます。これらは、日常の業務で Po stgreSQ L に深く係わり、その挙動やソースコードを熟知したメンバが集まって初めて達成できた成果です。PG ECo n s の会合は、異なる企業に属するメンバが集まって、専門的な意見を交わす貴重な場となっており、メンバの技術力の向上にも寄与しているものと思います。さらに今年度から議論のためにチャットツールを導入したところ、以前よりも圧倒的に意見のやりとりの回数が増えました。これはメンバー間の連帯感向上、ひいては各検証における考察の質向上に寄与しました。
今回の報告書が皆様の Po stgreSQ L の活用のご参考になれば幸いです。報告書へのご意見がございましたら、PG ECo n s までお寄せください。また、PG ECo n s の活動にご関心をお持ちの方は、是非、参加をご検討ください( ご連絡にはこちらのW eb サイト をご利用ください)。

(終わり)

Page 84 of 86

PostgreSQL Enterprise Consortium

11. 著者（企業・団体名順）
版
第1.0 版(2017 年度W G 1)

所属企業・ 団体名

部署名

氏名

SRA O SS, In c. 日本支社

O SS 事業本部

近藤 雄太

NEC ソリューションイノベータ株式会社

サポートサービス事業部

近藤 太樹

NTTテクノクロス株式会社

Io Tイノベーション事業部

原田 登志

NTTテクノクロス株式会社

Io Tイノベーション事業部

勝俣 智成

株式会社クリアコード

須藤 功平

株式会社クリアコード

堀本 泰弘

日本電信電話株式会社

オープンソースソフトウェアセンタ

坂田 哲夫

富士通株式会社

共通ソフトウェア開発技術本部
ソフトウェア開発技術統括部
O SS 技術センター

野山 孝太郎

富士通株式会社

共通ソフトウェア開発技術本部
ソフトウェア開発技術統括部
O SS 技術センター

白石 明大

富士通株式会社

共通ソフトウェア開発技術本部
ソフトウェア開発技術統括部
O SS 技術センター

高澤 亮平

Page 85 of 86

PostgreSQL Enterprise Consortium

12. Appendix 検証環境
提供：日本ヒューレット・パッカード株式会社
定点観測（スケールアップ)/W in do w s 検証/パラレルクエリ検証での使用機器/設備

提供：日本電気株式会社
パラレルクエリ検証での使用機器/設備
型番

Exp ress5800/R120f-1E

CPU

インテル Xeo n E5-2630 v4@ 2.20G Hz

メモリ

256G B

内蔵ストレージ

SSD 400G B x 8 (RAID 5 構成)

OS

Red Hat En terp rise Lin u x 7.2
提供：富士通株式会社
複数同期レプリケーション検証/FDW 検証での使用機器/設備

Amazo n W eb Service
全文検索検証での使用機器/設備
項目

仕様

機種

Amazo n W eb Service(AW S) m4.2xlarge

CPU

In tel(R) Xeo n (R) CPU E5-2686 v4 @2.30G Hz
(8 コア)

メモリ

32G B

内蔵ストレージ

SSD 256G B

Page 86 of 86