My Books

My Slides

rss 아이콘 이미지

이번 시간에는 톰캣 서버 + UCP + JSP + Jmeter를 이용해서 RLB 동작 방식을 파악해보도록 하겠습니다.



 

 

준비 사항


다음 사항을 준비합니다.


1. Jmeter 설치


Jmeter 설치는 여기를 참고하세요.
 
2. UCP 구성
지난 포스팅을 참고하세요.


3. 샘플 JSP 작성 (load.jsp)


load.jsp의 핵심은 노드에 따라서 쿼리 성능의 편차를 크게 하는 것입니다. 이를 위해, 인스턴스 명을 기준으로 쿼리를 분기해서 처리했습니다.

LOAD.JSP 보기


4. 성능 정보를 수집할 스크립트 생성 (save_load.sql)


save_table을 생성한 후, save_load.sql을 이용해서 서비스의 로드 및 시스템 상황을 저장합니다.

SAVE_LOAD.SQL 보기


이제 모든 준비가 끝났습니다. 그럼 테스트를 시작합니다.




12-1. UCP + CLB_GOAL=SHORT / RLB_GOAL=SERVICE_TIME 인 서비스 (ONLINE_UCP)를 이용한 부하 테스트


아래 순서대로 테스트를 진행합니다.


1. 톰캣 서버 기동


[root@ap1 ~]# service tomcat start
Using CATALINA_BASE:   /usr/local/tomcat
Using CATALINA_HOME:   /usr/local/tomcat
Using CATALINA_TMPDIR: /usr/local/tomcat/temp
Using JRE_HOME:        /usr/local/java
Using CLASSPATH:       /usr/local/tomcat/bin/bootstrap.jar:/usr/local/tomcat/bin/tomcat-juli.jar


2. 커넥션 풀 연결 확인


UCP는 톰캣 기동 시에 커넥션을 연결하지 않고, 첫 번째 요청이 들어오는 시점에 커넥션을 연결합니다. 따라서, 현재 시점에는 ONLINE_UCP 서비스로 연결된 세션은 없습니다.
select 'INST_1' as inst_id, count(*) total_cnt,
       sum(decode(service_name,'ONLINE_DBCP',1)) online_dbcp,
       sum(decode(service_name,'ONLINE_UCP' ,1)) online_ucp,
       sum(decode(service_name,'SHORT_SRV'  ,1)) short_srv,
       sum(decode(service_name,'LONG_SRV'   ,1)) long_srv
from gv$session where inst_id=1
union all
select 'INST_2' as inst_id, count(*) total_cnt,
       sum(decode(service_name,'ONLINE_DBCP',1)),
       sum(decode(service_name,'ONLINE_UCP' ,1)),
       sum(decode(service_name,'SHORT_SRV'  ,1)),
       sum(decode(service_name,'LONG_SRV'   ,1))
from gv$session where inst_id=2;


INST_I  TOTAL_CNT ONLINE_DBCP ONLINE_UCP  SHORT_SRV   LONG_SRV
------ ---------- ----------- ---------- ---------- ----------
INST_1         74           6                     6          6
INST_2         67           4                     4          4


3. UCP 연결


UCP는 최초 요청 직후에 커넥션을 연결합니다. 이전 포스팅에서 작성한 test.jsp를 수행한 후, 커넥션 연결 여부를 확인합니다.

INST_I  TOTAL_CNT ONLINE_DBCP ONLINE_UCP  SHORT_SRV   LONG_SRV
------ ---------- ----------- ---------- ---------- ----------
INST_1         87           6         13          6          6
INST_2         74           4          7          4          4


4. 로드 저장용 스크립트 수행


save_load.sql을 이용해서 5초에 1번씩 부하 상황을 저장합니다.

[oracle@rac1 ~]$ while true
> do
> sqlplus apps/apps @save_load.sql
> sleep 5
> done


5. Jmeter로 Run 테스트


다음과 같이 Jmeter를 설정한 후 실행합니다.





12-2. 결과 분석


테스트가 끝난 후에, 다음 쿼리를 이용해서 수행 결과를 분석합니다.


결과 분석용 쿼리 보기


결과-1. 아래 그래프와 같이, DBTIMEPERCALL 시간이 짧은 2번 노드로 커넥션 풀 세션이 이전하는 것을 알 수 있습니다. 즉, RLB가 정상적으로 이루어졌습니다. (그림-1, 그림-2. 참조)


그림-1. 노드 별 DBTIMEPERSEC 트렌드


그림-2. 노드 별 커넥션 풀 세션 수 트랜드



결과-2. RLB가 정상적으로 이루어짐에 따라서, 1번 노드의 active 세션 개수가 점차적으로 줄어드는 것을 확인할 수 있습니다. (그림-3. 참조)


그림-3. 노드 별 Active 세션 수 트랜드



결과-3. CPU 런-큐 및 CPU(%)은 RLB와는 무관한것으로 확인됩니다. (그림-4, 그림-5. 참조) 즉, 해당 값들 커넥션 시점의 로드 밸런싱(CLB)를 위해서만 사용됩니다. 그리고 커넥션 풀 세션들이 2번 노드로 이전함에 따라, 1번 노드의 CPU(%)이 점차적으로 감소하는 것을 확인할 수 있습니다.


그림-4. 노드 별 CPU Run-Queue 트렌드


그림-5. 노드 별 CPU(%) 트렌드



12-3 결과 요약


상기 예제를 통해 UCP 환경에서의 RLB 동작 방식을 확인했습니다. 나머지 3개의 서비스에 대한 테스트 겱는 지면 관계상 요약 정리만 하도록 하겠습니다. (표-1. 참조)


표-1. 서비스 유형 별 테스트 결과 요약

 서비스 명

 구성

 영향받는 항목

 RLB

여부

 GOODNESS

 DELTA

 LONG_SRV

CLB_GOAL=LONG
DBCP

 커넥션 시,

"해당 서비스의 세션 수"

 X

 세션 수

 1

 SHORT_SRV

 CLB_GOAL=SHORT
 RLB_GOAL=NONE

 DBCP

 커넥션 시,

"CPU 사용률(%)"

 X

 낮을수록 좋음
최대값

(CPU수*5000)

 가변적

 ONLINE_DBCP

 CLB_GOAL=SHORT

RLB_GOAL=SERVICE_TIME
DBCP

 커넥션 시,

"CPU 사용률(%)"

 X

 상동

 가변적

 ONLINE_UCP

 CLB_GOAL=SHORT
RLB_GOAL=SERVICE_TIME
UDP

 커넥션 시,

"CPU 사용률(%)"
런타임 시,

"콜당 수행 시간"

 O

 상동

 가변적


글을 마치며


4회의 연재를 통해 로드 밸런싱의 기본 개념 및 동작 원리를 살펴보았습니다. 테스트를 통해 원리를 검증 또는 역 추적한다는 것은 사실 굉장히 시간 소모적이고 위험할 수도 있는 (즉, 엉뚱한 결론에 이르는) 일입니다. 예를 들어, ONS.JAR 없이 UCP를 테스트했다면 지금과는 아주 상이한 결과가 나왔을 겁니다. 하지만, 다양한 역 추적 기법 (쿼리, 트레이스, OS 명령어 등)을 통해 원리를 이해해 나가는 과정은 재미있는 일임에 분명합니다. 다음 시간의 주제는 Failover 입니다. 다음 시간에 뵙겠습니다.

 


저작자 표시 비영리 변경 금지
신고
크리에이티브 커먼즈 라이선스
Creative Commons License

[10] CLB, RLB를 위한 서비스 매트릭스 정보의 흐름

RAC 2016.07.08 20:28 Posted by 시연아카데미

똘똘님! 이전 포스팅을 통해 CLB와 RLB의 기본 개념은 쉽게 이해했습니다. 이번 시간에는 로드 밸런싱을 위한 "서비스 매트릭스" 정보의 흐름에 대해서 알고 싶습니다. 




네 궁금님. 말씀하신 것처럼 오라클은 로드 밸런싱을 위해 "서비스 매트릭스" 정보를 이용합니다. 테스트를 통해서 살펴보겠습니다.




10-1. 리스너 설정


로드 밸런싱을 위해서는 로컬 리스너와 리모트 리스너를 설정해야 합니다. 리스너는 대부분 설치 시에 자동으로 설정되므로 설정 내용만 확인하면 될 것입니다. 제 경우에는 SCAN IP를 사용하므로 remote_listener 설정 값이 rac-scan:1521로 나타납니다. SCAN을 사용하지 않는 환경에서는 상대 노드(들)의 리스너 주소가 출력되면 됩니다.
1번 노드> show parameter _listener
NAME                 VALUE
-------------------- --------------------------------------------
local_listener       (ADDRESS=(PROTOCOL=TCP)(HOST=192.168.56.81)(PORT=1521))
remote_listener      rac-scan:1521

2번 노드> show parameter _listener
NAME                 VALUE
-------------------- --------------------------------------------
local_listener       (ADDRESS=(PROTOCOL=TCP)(HOST=192.168.56.82)(PORT=1521))
remote_listener      rac-scan:1521



10-2. 서비스 생성


CLB 옵션 (LONG, SHORT)의 차이를 확인하기 위해 2개의 서비스 (LONG_SRV, SHORT_SRV)를 생성합니다. 또한, UCP (Universal Connection Pool) 환경에서만 RLB가 동작하는 것을 검증하기 위해 2개의 서비스 (ONLINE_DBCP, ONLINE_UCP)를 생성합니다. (표-1. 참조)


표-1. 동작 차이 확인을 위한 4개의 서비스 목록

 서비스 명

 CLB_GOAL

 RLB_GOAL

 사용할 커넥션 풀

 LONG_SRV

 LONG

 n/a

 DBCP

 SHORT_SRV

 SHORT

 NONE

 DBCP

 ONLINE_DBCP

 SHORT

 SERVICE_TIME

 DBCP

 ONLINE_UCP

 SHORT

 SERVICE_TIME

 UCP


서비스 생성

srvctl add service -db ORA12C -service LONG_SRV -preferred ORA12C1,ORA12C2 \
-clbgoal LONG -notification true
srvctl add service -db ORA12C -service SHORT_SRV -preferred ORA12C1,ORA12C2 \
-clbgoal SHORT -rlbgoal NONE
srvctl add service -db ORA12C -service ONLINE_DBCP -preferred ORA12C1,ORA12C2 \
-clbgoal SHORT -rlbgoal SERVICE_TIME
srvctl add service -db ORA12C -service ONLINE_UCP -preferred ORA12C1,ORA12C2 \
-clbgoal SHORT -rlbgoal SERVICE_TIME



Note
RLB_GOAL이 THROUGHPUT인 경우는 테스트 대상에서 제외했습니다. 제 테스트 환경에서는 RLB_GOAL이 SERVICE_TIME인 경우와 THROUGHPUT인 경우의 차이점을 발견하지 못했기 때문입니다. 약간의 차이는 있지만, 두 개의 옵션 모두 "Call당 처리 시간" 기준으로 커넥션이 이전되었습니다.


서비스 시작

srvctl start service -db ORA12C -service LONG_SRV
srvctl start service -db ORA12C -service SHORT_SRV
srvctl start service -db ORA12C -service ONLINE_DBCP
srvctl start service -db ORA12C -service ONLINE_UCP


서비스 확인

srvctl status service -db ORA12C

Service LONG_SRV is running on instance(s) ORA12C1,ORA12C2
Service ONLINE_DBCP is running on instance(s) ORA12C1,ORA12C2
Service ONLINE_UCP is running on instance(s) ORA12C1,ORA12C2
Service SHORT_SRV is running on instance(s) ORA12C1,ORA12C2



10-3. 로드 밸런싱과 관련된 MMON, MMNL, LREG, 리스너 동작 방식


몇 가지 테스트를 통해 분석한 MMON, MMNL, LREG, 리스너의 동작 방식은 다음과 같습니다. (그림-1. 참조)

  1. MMON은 30초에 1번씩 RLB로 설정된 서비스들의 서비스 매트릭스 정보를 SYS.SYS$SERVICE_METRICS_TAB에 저장합니다.
  2. 각 노드의 MMNL은 5초에 1번씩 모든 서비스들의 서비스 매트릭스 정보를 V$SERVICEMETRIC에 저장합니다.
  3. LREG (11g까지는 PMON)는 서비스 매트릭스 정보를 리스너들에게 전달합니다.
  4. 리스너들은 LREG로부터 서비스 메트릭스 정보를 전달 받습니다.


그림-1. 서비스 매트릭스 전달 방식



10-4. 검증 방법 상세


사실, 이 부분은 엔지니어 적인 호기심으로 트레이싱을 해본 내용들입니다. 그냥 스킵해도 무방하며, 트레이스 방법에 대해서만 가볍게 리뷰하셔도 좋을 것 같습니다.



10-3의 1번 항목 검증


select to_char(ENQ_TIME, 'YYYY-MM-DD: HH:MI:SS') Enq_time, user_data
from   SYS.SYS$SERVICE_METRICS_TAB
order  by 1;

2016-07-08: 09:45:11  SYS$RLBTYP('ONLINE_UCP', 'VERSION=1.0 database=ORA12C servic
                      e=ONLINE_UCP { {instance=ORA12C1 percent=100 flag=UNKNOWN af
                      f=FALSE} } timestamp=2016-07-08 18:45:11')
2016-07-08: 09:45:11  SYS$RLBTYP('ONLINE_DBCP', 'VERSION=1.0 database=ORA12C servi
                      ce=ONLINE_DBCP { {instance=ORA12C1 percent=100 flag=UNKNOWN
                      aff=FALSE} } timestamp=2016-07-08 18:45:11')
2016-07-08: 09:45:41  SYS$RLBTYP('ONLINE_UCP', 'VERSION=1.0 database=ORA12C servic
                      e=ONLINE_UCP { {instance=ORA12C1 percent=100 flag=UNKNOWN af
                      f=FALSE} } timestamp=2016-07-08 18:45:41')
2016-07-08: 09:45:41  SYS$RLBTYP('ONLINE_DBCP', 'VERSION=1.0 database=ORA12C servi
                      ce=ONLINE_DBCP { {instance=ORA12C1 percent=100 flag=UNKNOWN
                      aff=FALSE} } timestamp=2016-07-08 18:45:41')


Note
SYS$SERVICE_METRICS_TAB 테이블에는 RLB와 관련된 서비스의 서비스 메트릭스 정보만 30초마다 저장됩니다. 해당 테이블에는 CLB 관련 서비스의 정보는 저장되지 않습니다.


다음과 같이, kill -stop 명령어로 MMON 프로세스를 STOP 시킨 후에는 SYS$SERVICE_METRICS_TAB 테이블에 서비스 매트릭스 정보가 입력되지 않는 것을 알 수 있습니다.

[oracle@rac2 SS]$ ps -ef | grep mmon
oracle    8474     1  0 18:43 ?        00:00:01 ora_mmon_ORA12C2
[oracle@rac2 SS]$ kill -stop 8474
[oracle@rac2 SS]$ su root
[root@rac2 SS]# strace -p 8474
Process 8474 attached
--- stopped by SIGSTOP ---



10-3의 2번 항목 검증


1번과 동일한 방법으로 MMNL 프로세스를 STOP 시키면 V$SERVICEMETRIC 테이블에 서비스 매트릭스 정보가 입력되지 않는 것을 알 수 있습니다. 
 

10-3의 3번 항목 검증


10257 트레이스를 이용하면 됩니다. 해당 트레이스를 활성화시키면 PMON 및 LREG의 수행 내용을 확인할 수 있습니다. SQL> alter system set events '10257 trace name context forever, level 16'; --트레이스 on
SQL> alter system set events '10257 trace name context off'; -- 트레이스 off


예시-1. LREG 프로세스 트레이스 결과

*** 2016-07-08 19:13:34.357
kmlwait: status: succ=4, wait=0, fail=0
kmmlrl: update for process drop delta: 107 106 72 74 299
kmmlrl: 72 processes
kmmlrl: node load 445
kmmlrl: instance load 4
kmmgdnu: LONG_SRV
         goodness=0, delta=1, pdb=1,
         flags=0x104:unblocked/not overloaded, update=0x6:G/D/-
kmmgdnu: ONLINE_DBCP
         goodness=100, delta=100, pdb=1,
         flags=0x104:unblocked/not overloaded, update=0x6:G/D/-
kmmgdnu: ONLINE_UCP
         goodness=100, delta=100, pdb=1,
         flags=0x104:unblocked/not overloaded, update=0x6:G/D/-
kmmgdnu: SHORT_SRV
         goodness=0, delta=100, pdb=1,
         flags=0x104:unblocked/not overloaded, update=0x6:G/D/-
kmmgdnu: ORA12CXDB
         goodness=0, delta=1, pdb=0,
         flags=0x105:unblocked/not overloaded, update=0x6:G/D/-
kmmgdnu: ORA12C
         goodness=0, delta=1, pdb=0,
         flags=0x104:unblocked/not overloaded, update=0x6:G/D/-



10-3의 4번 항목 검증


리스너 트레이스를 이용하면 됩니다.
  • 로컬 리스너 트레이스 방법: lsnrctl trace user
  • 스캔 리스너 트레이스 방법: lsnrctl trace user LISTENER_SCAN1

예시-2. 리스너 프로세스 트레이스 결과 
2016-07-08 19:13:34.358201 : nsglgrDoRegister:service:ONLINE_UCP what:4 value:100
2016-07-08 19:13:34.358209 : nsglgrDoRegister:service:ONLINE_UCP what:2 value:100
2016-07-08 19:13:34.358216 : nsglgrDoRegister:service:ONLINE_DBCP what:4 value:100
2016-07-08 19:13:34.358223 : nsglgrDoRegister:service:ONLINE_DBCP what:2 value:100
2016-07-08 19:13:34.358230 : nsglgrDoRegister:service:SHORT_SRV what:4 value:100
2016-07-08 19:13:34.358237 : nsglgrDoRegister:service:SHORT_SRV what:2 value:0
2016-07-08 19:13:34.358245 : nsglgrDoRegister:service:LONG_SRV what:4 value:1
2016-07-08 19:13:34.358253 : nsglgrDoRegister:service:LONG_SRV what:2 value:0
2016-07-08 19:13:34.358261 : nsglgrDoRegister:service:ORA12C what:4 value:1
2016-07-08 19:13:34.358269 : nsglgrDoRegister:service:ORA12C what:2 value:0


Note
두 개의 트레이스 파일을 비교함으로써 리스너 프로세스의 what:4=delta, what:2=goodness 임을 알 수 있습니다. 해당 값들은 V$SERVICEMETRIC의 DELTA 및 GOODNESS 칼럼 값과 동일합니다.



참고 문헌


http://www.slideshare.net/fullscreen/alexgorbachev/demistifying-oracle-rac-workload-management-by-alex-gorbachev-nocoug-2010-spring-conference/1


글을 마치며


이번 시간에는 RLB, CLB 서비스 생성 방법 및 로드 밸런싱을 위한 "서비스 매트릭스" 정보들이 흐름을 살펴보았습니다.


[11] 톰캣 서버에 UCP (Universal Connection Pool) 구성 및 JSP 샘플 코드 작성 바로가기


저작자 표시 비영리 변경 금지
신고
크리에이티브 커먼즈 라이선스
Creative Commons License

똘똘님. 자동으로 로드를 분산시킨다는 개념은 위험성이 내포되어 있긴 하지만, 원리를 잘 이해하고 적용한다면 관리 측면에서는 상당히 매력적인 기능인 것 같습니다. 공부를 하다 보니 CLB, RLB, CLB_GOAL, RLB_GOAL 등의 용어가 등장합니다. CLB의 개념은 그다지 어렵지 않은데, RLB 개념이 명확하지 않습니다. CLB와 RLB의 개념을 정립해주실 수 있을까요?




네. 간단한 질문이지만 상당히 어려운 질문입니다. 설명드릴 것이 많지만, 한번에 너무 많은 지식은 소화하기 힘드니 이번 시간에는 CLB와 RLB의 차이를 명확히 아는 것만을 목표로 진행해 보겠습니다.



들어가기에 앞서


로드 밸런싱 관련 내용은 설명할 내용이 많은 관계로 다음과 같이 4개의 연재로 진행할 예정입니다.


1) [09] Connection Load Balancing (CLB)과 Runtime Connection Load Balancing (RLB) 설명

2) [10] CLB, RLB를 위한 서비스 매트릭스 정보의 흐름

3) [11] 톰캣 서버에 UCP (Universal Connection Pool) 구성 및 JSP 샘플 코드 작성

4) [12] Jmeter + 톰캣 + UCP를 이용한 RLB (Runtime Load Balancing) 동작 방식 검증



9-1. 로드 밸런싱 개요


클러스터 환경에서 동시에 다수의 노드가 동일한 서비스를 수행하는 경우, 바꿔 말해 하나의 서비스가 여러 개의 노드에서 동시에 수행되는 환경이 있다고 가정해보겠습니다. 이때, 서비스 성능 수준을 높이기 위해서 로드 밸런싱은 반드시 필요한 요소입니다. 일반적으로 로드 밸런싱은 2가지로 구분할 수 있습니다.

  • 커넥션 로드 밸런싱
  • 런-타임 로드 밸런싱
Note
커넥션 로드 밸런싱은 "세션 수" 또는 "CPU 사용률(%)"을 기준으로 동작하고, 런-타임 로드 밸런싱은 "서비스 처리 시간"을 기준으로 동작합니다.



커넥션 로드 밸런싱의 한계점

  • 커넥션 시점에는 CPU 사용률(%)이 비슷했으나, 접속한 노드의 CPU(%)이 갑자기 높아지는 경우
  • 세션 수나 CPU 사용률(%)은 비슷하나, 노드 간의 서비스 처리 성능이 차이가 나는 경우  
이러한 문제를 해결하기 위해 "런-타임 로드 밸런싱"이 필요하다고 할 수 있습니다.



9-2. 오라클의 로드 밸런싱 방법


오라클은 커넥션 로드 밸런싱과 런-타임 로드 밸런싱을 모두 제공합니다. (표-1 및 그림-1 참조)
  • 커넥션 로드 밸런싱: Connection Load Balancing (CLB)이라고 하며, CLB_GOAL로 설정
  • 런-타임 밸런싱: Runtime Load Balancing (RLB)이라고 하며, RLB_GOAL로 설정 


그림-1. 로드 밸런싱 옵션


Note
RLB_GOAL을 설정하기 위해서는 CLB_GOAL을 SHORT로 지정해야 합니다.


표-1. CLB, RLB 비교 설명

 구분

 CLB (커넥션 로드 밸런싱)

 RLB (런-타임 로드 밸런싱)

 설정 방법

 서비스 생성 시, CLB_GOAL 설정

 서비스 생성 시, RLB_GOAL 설정

 옵션

 LONG
 "세션 수"가 적은 노드로 접속

 SERVICE_TIME
 UCP 사용 시, 서비스 처리 시간이 우수한 노드로 접속

 (OLTP 환경에 적합)

 SHORT
 "CPU(%)"이 낮은 노드로 접속

 THROUPUT
 UCP 사용 시, 서비스 처리 능력이 우수한 노드로 접속
 (BATCH 환경에 적합)


Note
LONG 옵션에서 말하는 "세션 수"는 "해당 서비스로 접속한 세션 수"를 의미합니다. 전체 세션 수가 아닌 점을 주의해야 합니다. 



9-3. RLB는 모든 환경에서 적용될까요?


"표-1"에서 언급한 것처럼 "RLB는 UCP (Unified Connection Pool) 환경에서만 동작"합니다. 간단하지만 가장 중요한 내용이라고 할 수 있겠습니다. DBCP, JDBC Connection Pool 및 SQL*Plus와 같은 클라이언트의 접속은 RLB가 적용되지 않습니다. 테스트 시, 모니터링을 해보면 DBCP나 SQL*Plus 접속에 대해서도 RBL가 적용되는 것 같은 착각을 할 수 있지만, 해당 접속들은 CLB로만 처리됩니다.

 

 



참고 문헌


http://oracleinaction.com/rac-load-balancing/



[10] CLB, RLB 동작을 위한 서비스 매트릭스 정보의 흐름 바로가기

저작자 표시 비영리 변경 금지
신고
크리에이티브 커먼즈 라이선스
Creative Commons License


 

티스토리 툴바