忘れかけのIT備忘録

今まで学んできた知識や小技、なるほど!と思ったことをメモするブログです。

サービスのロード・バランシング検証

サービスのロード・バランシングについて、机上の知識はあるものの、実務経験が無いため、実際の動きを検証しました。

■検証環境
OS:Oracle Linux 6.5
GI:Oracle Grid Infrastructure 12c Release 1 (12.1.0.2.0) Enterprise Edition
DB:Oracle Database 12c Release 1 (12.1.0.2.0) Enterprise Edition
※2ノードRAC(管理者管理型DB)

■前提
・SCANを使用しているため、サーバ側ロード・バランシングの検証になります
DNSサーバはdnsmasqを使用しています
・ノード1を疑似クライアントとしています (※1)
・接続時ロード・バランシングのみの検証です (※2)
(※1) 本来ならクライアント用のアプリケーションサーバを建てて、JDBCやOCI等のドライバを入れるべきですが割愛しました
(※2) コネクションプールを使用していないため、実行時ロード・バランシング(ランタイム・ロード・バランシング)は検証していません(ロード・バランシング・アドバイザ未使用)

■設定情報

 クラスタリソース情報
[root@node1 ~]# /u01/app/12.1.0/grid/bin/crsctl stat res -t
--------------------------------------------------------------------------------
Name           Target  State        Server                   State details      
--------------------------------------------------------------------------------
Local Resources
--------------------------------------------------------------------------------
ora.DATA.dg
               ONLINE  ONLINE       node1                    STABLE
               ONLINE  ONLINE       node2                    STABLE
ora.FRA.dg
               ONLINE  ONLINE       node1                    STABLE
               ONLINE  ONLINE       node2                    STABLE
ora.LISTENER.lsnr
               ONLINE  ONLINE       node1                    STABLE
               ONLINE  ONLINE       node2                    STABLE
ora.asm
               ONLINE  ONLINE       node1                    Started,STABLE
               ONLINE  ONLINE       node2                    Started,STABLE
ora.net1.network
               ONLINE  ONLINE       node1                    STABLE
               ONLINE  ONLINE       node2                    STABLE
ora.ons
               ONLINE  ONLINE       node1                    STABLE
               ONLINE  ONLINE       node2                    STABLE
--------------------------------------------------------------------------------
Cluster Resources
--------------------------------------------------------------------------------
ora.LISTENER_SCAN1.lsnr
      1        ONLINE  ONLINE       node1                    STABLE
ora.LISTENER_SCAN2.lsnr
      1        ONLINE  ONLINE       node1                    STABLE
ora.LISTENER_SCAN3.lsnr
      1        ONLINE  ONLINE       node1                    STABLE
ora.MGMTLSNR
      1        ONLINE  ONLINE       node1                    169.254.105.185 192.
                                                                                 168.100.101,STABLE
ora.cvu
      1        ONLINE  ONLINE       node2                    STABLE
ora.mgmtdb
      1        ONLINE  ONLINE       node1                    Open,STABLE
ora.node1.vip
      1        ONLINE  ONLINE       node1                    STABLE
ora.node2.vip
      1        ONLINE  ONLINE       node2                    STABLE
ora.oc4j
      1        ONLINE  ONLINE       node2                    STABLE
ora.orcl.db
      1        ONLINE  ONLINE       node1                    Open,STABLE
      2        ONLINE  ONLINE       node2                    Open,STABLE
ora.orcl.hoge.svc ★検証用のサービス
      1        ONLINE  ONLINE       node1                    STABLE
      2        ONLINE  ONLINE       node2                    STABLE
ora.scan1.vip
      1        ONLINE  ONLINE       node1                    STABLE
ora.scan2.vip
      1        ONLINE  ONLINE       node1                    STABLE
ora.scan3.vip
      1        ONLINE  ONLINE       node1                    STABLE
--------------------------------------------------------------------------------

リスナーの登録情報
#ノード1
[grid@node1 ~]$ lsnrctl status LISTENER
サービスのサマリー...
サービス"+ASM"には、1件のインスタンスがあります。
  インスタンス"+ASM1"、状態READYには、このサービスに対する1件のハンドラがあります...
サービス"-MGMTDBXDB"には、1件のインスタンスがあります。
  インスタンス"-MGMTDB"、状態READYには、このサービスに対する1件のハンドラがあります...
サービス"_mgmtdb"には、1件のインスタンスがあります。
  インスタンス"-MGMTDB"、状態READYには、このサービスに対する1件のハンドラがあります...
サービス"hoge"には、1件のインスタンスがあります。
  インスタンス"orcl1"、状態READYには、このサービスに対する1件のハンドラがあります...
サービス"node_cluster"には、1件のインスタンスがあります。
  インスタンス"-MGMTDB"、状態READYには、このサービスに対する1件のハンドラがあります...
サービス"orcl"には、1件のインスタンスがあります。
  インスタンス"orcl1"、状態READYには、このサービスに対する1件のハンドラがあります...
サービス"orclXDB"には、1件のインスタンスがあります。
  インスタンス"orcl1"、状態READYには、このサービスに対する1件のハンドラがあります...

#ノード2
[grid@node2 ~]$ lsnrctl status LISTENER
サービスのサマリー...
サービス"+ASM"には、1件のインスタンスがあります。
  インスタンス"+ASM2"、状態READYには、このサービスに対する1件のハンドラがあります...
サービス"hoge"には、1件のインスタンスがあります。
  インスタンス"orcl2"、状態READYには、このサービスに対する1件のハンドラがあります...
サービス"orcl"には、1件のインスタンスがあります。
  インスタンス"orcl2"、状態READYには、このサービスに対する1件のハンドラがあります...
サービス"orclXDB"には、1件のインスタンスがあります。
  インスタンス"orcl2"、状態READYには、このサービスに対する1件のハンドラがあります...

疑似クライアントのネットサービス名情報
#ノード1、ノード2
[oracle@node1 ~]$ cat /u01/app/oracle/product/12.1.0/dbhome_1/network/admin/tnsnames.ora
ORCL =
  (DESCRIPTION =
    (ADDRESS = (PROTOCOL = TCP)(HOST = scan.oracle12c.jp)(PORT = 1521))
    (CONNECT_DATA =
      (SERVER = DEDICATED)
      (SERVICE_NAME = orcl)
    )
  )

HOGE =
  (DESCRIPTION =
    (ADDRESS = (PROTOCOL = TCP)(HOST = scan.oracle12c.jp)(PORT = 1521))
    (CONNECT_DATA =
      (SERVER = DEDICATED)
      (SERVICE_NAME = hoge)
    )
  )

 

■検証パターン
①セッション数均等化の検証
②CPU負荷分散の検証(全ノード:CPU負荷なし)
③CPU負荷分散の検証(ノード1:CPU負荷あり、ノード2:CPU負荷なし)

■検証
①セッション数均等化の検証
1秒単位で疑似クライアントからhogeサービス(clbgoal:LONG)に接続するのを1分間実行し、セッションが各インスタンスに振り分けられる割合を検証します

サービスの情報
[oracle@node1 ~]$ srvctl config service -db orcl -service hoge
サービス名: hoge
サーバー・プール: 
カーディナリティ: 2
切断: false
サービス・ロール: PRIMARY
管理ポリシー: AUTOMATIC
DTPトランザクション: false
AQのHA通知: false
グローバル: false
コミット結果: false
フェイルオーバー・タイプ: 
フェイルオーバー・メソッド: 
TAFフェイルオーバー再試行: 
TAFフェイルオーバー遅延: 
接続ロード・バランシングの目標: LONG
ランタイム・ロード・バランシングの目標: NONE
TAFポリシー仕様: NONE
エディション: 
プラガブル・データベース名: 
最大タイム・ラグ: ANY
SQL翻訳プロファイル: 
保存時間: 86400秒
リプレイ開始時間: 300秒
セッション状態一貫性: 
GSMフラグ: 0
サービスは有効です
優先インスタンス: orcl1,orcl2
使用可能なインスタンス:

【検証手順】
1. 疑似クライアントで「sqlplus system/XXXXX@HOGE」を1秒単位で1分間実行する
2. gv$sessionから全インスタンスのセッション情報を取得する (※1)
(※1) セッション情報取得SQL
select inst_id, count(inst_id) as curr_sessions
from gv$session
where username = 'SYSTEM' and program like '%sqlplus%'
group by inst_id
order by inst_id;

【想定】
セッションは各インスタンスにほぼ均等に振り分けられるはず

【検証結果】
   INST_ID CURR_SESSIONS
---------- -------------
         1            30
         2            30
★セッションが各インスタンスに綺麗に均等に振り分けられました

②CPU負荷分散の検証(全ノード:CPU負荷なし)
全ノードでCPU負荷が発生していない状態で、1秒単位で疑似クライアントからhogeサービス(clbgoal:SHORT、rlbgoal:NONE)に接続するのを1分間実行し、セッションが各インスタンスに振り分けられる割合を検証します

サービスの情報
[oracle@node1 ~]$ srvctl config service -db orcl -service hoge
サービス名: hoge
サーバー・プール: 
カーディナリティ: 2
切断: false
サービス・ロール: PRIMARY
管理ポリシー: AUTOMATIC
DTPトランザクション: false
AQのHA通知: false
グローバル: false
コミット結果: false
フェイルオーバー・タイプ: 
フェイルオーバー・メソッド: 
TAFフェイルオーバー再試行: 
TAFフェイルオーバー遅延: 
接続ロード・バランシングの目標: SHORT
ランタイム・ロード・バランシングの目標: NONE
TAFポリシー仕様: NONE
エディション: 
プラガブル・データベース名: 
最大タイム・ラグ: ANY
SQL翻訳プロファイル: 
保存時間: 86400秒
リプレイ開始時間: 300秒
セッション状態一貫性: 
GSMフラグ: 0
サービスは有効です
優先インスタンス: orcl1,orcl2
使用可能なインスタンス:

【検証手順】
1. 疑似クライアントで「sqlplus system/XXXXX@HOGE」を1秒単位で1分間実行する
2. gv$sessionから全インスタンスのセッション情報を取得する (※1)
(※1) セッション情報取得SQLは、検証パターン①と同じです

【想定】
セッションは各インスタンスにほぼ均等に振り分けられるはず

【検証結果】
   INST_ID CURR_SESSIONS
---------- -------------
         1            29
         2            31
★セッションが各インスタンスにほぼ均等に振り分けられました

③CPU負荷分散の検証(ノード1:CPU負荷あり、ノード2:CPU負荷なし)
ノード1でCPU負荷が発生している状態で、1秒単位で疑似クライアントからhogeサービス(clbgoal:SHORT、rlbgoal:NONE)に接続するのを1分間実行して、セッションが各インスタンスに振り分けられる割合を検証します

サービスの情報
検証パターン②と同じ

【検証手順】
1. ノード1で疑似的にCPU負荷を発生させる (※1)
2. 疑似クライアントで「sqlplus system/XXXXX@HOGE」を1秒単位で1分間実行する
3. gv$sessionから全インスタンスのセッション情報を取得する (※2)
(※1) ノード1で「yes > /dev/null &」を複数回実行し、CPU使用率が90%前後の状態を作っています
(※2) セッション情報取得SQLは、検証パターン①と同じです

【想定】
セッションはノード2(インスタンス2)に振り分けられるはず

【検証結果】
   INST_ID CURR_SESSIONS
---------- -------------
         1             1
         2            59
★ほとんどのセッションはノード2(インスタンス2)に振り分けられました

■おわりに
今回はSCANを使用したサービスのロード・バランシングの具体的な動きを確認することができました。
なお、サービスのロード・バランシングはSCANを使用しなくても可能です。
SCANを使用しない場合、各ノードのtnsnames.oraに各ノードVIPを指定して、local_listenerにローカルリスナー、remote_listenerに相手ノードのリスナーを指定します。
11gR2以降ならlistener_networksでネットワークセグメントを制御することも可能です。(前提としてクラスタリソースにネットワークリソースを追加する必要があります)