batch 서비스에서 DB connection 을 계속 잡고 가는 경우
- 작성자 :
- 송*경
- 작성일 :
- 2018-12-18 20:51:52
- 조회수 :
- 1,700
- 구분 :
- 실행환경
- 진행상태 :
- 완료
Q
egovframe에서 transaction manager 를 이용하는 배치 서비스를 구성하였습니다.
테스트하면서 보니 몇몇 transaction 이 계속 유지가 됩니다. 길게는 몇 시간까지 유지가 됩니다.
서버 구동 시간이 길면 쌓여가기도 합니다.
logger에서는 DB connection open 후에 transaction이 잘 이용되고
정상적으로 DB connection closed 메시지가 보여집니다.
그런데 배치서비스에서 이용하는 아래의 몇몇 Query 는 DB session을 모니터링하다보면
여전히 connection을 붙잡고 있습니다. 이 connection을 다시 이용하는 것도 아니고 inactive 상태로 유지됩니다.
배치서비스의 jobRepository는 bean으로 등록해 이용하고 있습니다.
<bean id="jobRepository" class="org.springframework.batch.core.repository.support.JobRepositoryFactoryBean"
p:dataSource-ref="dataSource" p:transactionManager-ref="transactionManager"
p:isolation-level-for-create="ISOLATION_DEFAULT"/>
context-transaction에서는 아래와 같이 설정했습니다.
<bean id="txManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
<property name="dataSource" ref="dataSource"/>
</bean>
<aop:config>
<aop:pointcut id="requiredTx" expression="execution(* egovframework.sample..impl.*Impl.*(..))"/>
<aop:advisor advice-ref="txAdvice" pointcut-ref="requiredTx" />
</aop:config>
<tx:advice id="txAdvice" transaction-manager="transactionManager">
<tx:attributes>
<tx:method name="*" rollback-for="Exception"/>
</tx:attributes>
</tx:advice>
isolation을 READ_COMMITED 설정해봤지만 큰 변화는 없었습니다.
필요한 설정이 있는지 혹은 잘못된 설정이 있는지 궁금합니다.
혹은 다른 부분에서 확인해야 할 사항이나 배치 서비스의 내부 table 간에 고려해야 하는 사항이 있는지 알고 싶습니다.
문제를 일으키는 Query는 아래와 같습니다.
SELECT JOB_INSTANCE_ID,
KEY_NAME,
TYPE_CD,
STRING_VAL,
DATE_VAL,
LONG_VAL,
DOUBLE_VAL
FROM BATCH_JOB_PARAMS
WHERE JOB_INSTANCE_ID = :1
UPDATE BATCH_JOB_EXECUTION
SET START_TIME = :1 ,
END_TIME = :2 ,
STATUS = :3 ,
EXIT_CODE = :4 ,
EXIT_MESSAGE = :5 ,
VERSION = :6 ,
CREATE_TIME = :7 ,
LAST_UPDATED = :8
WHERE JOB_EXECUTION_ID = :9
AND VERSION = :10
SELECT VERSION
FROM BATCH_JOB_EXECUTION
WHERE JOB_EXECUTION_ID=:1
테스트하면서 보니 몇몇 transaction 이 계속 유지가 됩니다. 길게는 몇 시간까지 유지가 됩니다.
서버 구동 시간이 길면 쌓여가기도 합니다.
logger에서는 DB connection open 후에 transaction이 잘 이용되고
정상적으로 DB connection closed 메시지가 보여집니다.
그런데 배치서비스에서 이용하는 아래의 몇몇 Query 는 DB session을 모니터링하다보면
여전히 connection을 붙잡고 있습니다. 이 connection을 다시 이용하는 것도 아니고 inactive 상태로 유지됩니다.
배치서비스의 jobRepository는 bean으로 등록해 이용하고 있습니다.
<bean id="jobRepository" class="org.springframework.batch.core.repository.support.JobRepositoryFactoryBean"
p:dataSource-ref="dataSource" p:transactionManager-ref="transactionManager"
p:isolation-level-for-create="ISOLATION_DEFAULT"/>
context-transaction에서는 아래와 같이 설정했습니다.
<bean id="txManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
<property name="dataSource" ref="dataSource"/>
</bean>
<aop:config>
<aop:pointcut id="requiredTx" expression="execution(* egovframework.sample..impl.*Impl.*(..))"/>
<aop:advisor advice-ref="txAdvice" pointcut-ref="requiredTx" />
</aop:config>
<tx:advice id="txAdvice" transaction-manager="transactionManager">
<tx:attributes>
<tx:method name="*" rollback-for="Exception"/>
</tx:attributes>
</tx:advice>
isolation을 READ_COMMITED 설정해봤지만 큰 변화는 없었습니다.
필요한 설정이 있는지 혹은 잘못된 설정이 있는지 궁금합니다.
혹은 다른 부분에서 확인해야 할 사항이나 배치 서비스의 내부 table 간에 고려해야 하는 사항이 있는지 알고 싶습니다.
문제를 일으키는 Query는 아래와 같습니다.
SELECT JOB_INSTANCE_ID,
KEY_NAME,
TYPE_CD,
STRING_VAL,
DATE_VAL,
LONG_VAL,
DOUBLE_VAL
FROM BATCH_JOB_PARAMS
WHERE JOB_INSTANCE_ID = :1
UPDATE BATCH_JOB_EXECUTION
SET START_TIME = :1 ,
END_TIME = :2 ,
STATUS = :3 ,
EXIT_CODE = :4 ,
EXIT_MESSAGE = :5 ,
VERSION = :6 ,
CREATE_TIME = :7 ,
LAST_UPDATED = :8
WHERE JOB_EXECUTION_ID = :9
AND VERSION = :10
SELECT VERSION
FROM BATCH_JOB_EXECUTION
WHERE JOB_EXECUTION_ID=:1
A
안녕하세요.
표준프레임워크센터 입니다.
일반 MVC에서 하나의 호출이 오면
DB가 호출이 되서 사용이 되고 종료된 되는것은
한 사이클로 한 쓰레드에서 처리될 것입니다,
이경우 아무래도 모니터링이 수월할듯 합니다.
하지만 대용량의 배치의 경우에는
대용량의 데이타를 처리하다보니
내부적으로 단일이 아닌 멀티 쓰레드를 사용하게되고
DB Pool이나 자원을 최대한 효율적으로 사용하기 위해서
병렬처리하는 로직을 수행하다보니
모니터링시 순간순간 확인하는 경우
앞과 뒤의 상태가 이어지지 않아
해석하기 어려운 상황이 많이 발생할것으로 생각이 됩니다.
동시다발적으로 변경되는 상황이기 때문에
굉장히 모니터링이 어려울수도 있고
동시성 관련한 전문적인 지식이 필요할수도 있을듯 합니다.
감사합니다.
표준프레임워크센터 입니다.
일반 MVC에서 하나의 호출이 오면
DB가 호출이 되서 사용이 되고 종료된 되는것은
한 사이클로 한 쓰레드에서 처리될 것입니다,
이경우 아무래도 모니터링이 수월할듯 합니다.
하지만 대용량의 배치의 경우에는
대용량의 데이타를 처리하다보니
내부적으로 단일이 아닌 멀티 쓰레드를 사용하게되고
DB Pool이나 자원을 최대한 효율적으로 사용하기 위해서
병렬처리하는 로직을 수행하다보니
모니터링시 순간순간 확인하는 경우
앞과 뒤의 상태가 이어지지 않아
해석하기 어려운 상황이 많이 발생할것으로 생각이 됩니다.
동시다발적으로 변경되는 상황이기 때문에
굉장히 모니터링이 어려울수도 있고
동시성 관련한 전문적인 지식이 필요할수도 있을듯 합니다.
감사합니다.