땃쥐네

[Spring DB] 커넥션, DB 세션, 트랜잭션의 관계 본문

Spring

[Spring DB] 커넥션, DB 세션, 트랜잭션의 관계

ttasjwi 2022. 10. 23. 17:16

이전 글들에서 커넥션이란 무엇이고 커넥션을 어떻게 획득하는 지(datasource), 트랜잭션이란 무엇이고 왜 필요한 지 등을 한번씩 살펴봤습니다.

 

- [Spring DB] 커넥션과 DataSource

- [Spring DB] 순수 JDBC 기술로 CRUD

- [Spring DB] 커넥션 풀을 통한 커넥션 획득

- [DataBase] 트랜잭션 및 트랜잭션의 4대 특성(ACID)

 

이전 글까지는 WAS 측에서의 커넥션을 살펴봤다면 이제 반대쪽 DB 입장에서의 커넥션을 살펴보고, 커넥션과 트랜잭션의 관계를 확인해봅시다.


커넥션, DB 세션, 트랜잭션

WAS와 DB가 커넥션을 맺으면 DB측에서는 '데이터베이스 세션'이란 것을 생성하게 됩니다. 이제 모든 커넥션을 통한 데이터베이스 조작 요청, 조회 요청, 트랜잭션 시작, 커밋, 롤백, 종료 등은 이 DB 세션을 통해서 실행하게 됩니다.

 

기본적으로는 세션을 통해 트랜잭션이 시작되지 않은 상황이면 SQL을 바로 실행할 수 있습니다. 하지만 애플리케이션 로직은 보통 여러가지 SQL들의 연속으로 구성되어 있으며, 이들의 원자성을 보장하기 위해서는 트랜잭션에서 SQL을 실행해야합니다. DB 세션을 통해 트랜잭션을 시작하여 1개 이상의 SQL들을 실행하다가 일괄적으로 커밋하거나 롤백하면 됩니다. 트랜잭션을 통해 데이터 변경을 커밋, 롤백하면 그 후에는 트랜잭션을 다시 종료하면 됩니다.


커넥션마다 세션, 세션마다 트랜잭션

이제 여러 커넥션이 있는 상황을 살펴봅시다.

 

커넥션 풀을 사용할 때 기준으로 예를 들어 살펴보면, 애플리케이션 로딩 시점에 지정된 숫자만큼 커넥션을 맺고 커넥션 풀에서 관리합니다. 그러면 반대쪽 DB 입장에서는 커넥션 각각마다 세션을 생성하게 됩니다. 애플리케이션 로딩 중에는 계속 커넥션이 유지되므로 DB 세션도 유지됩니다.

 

여기서 핵심은, 각 커넥션마다 다른 세션을 사용하고 각각의 세션에서 트랜잭션이 시작되므로, 커넥션마다 트랜잭션이 서로 다르다는 것입니다! 서로 다른 두 물리적 커넥션이 같은 트랜잭션을 사용하지 않습니다.


같은 트랜잭션에서 여러 SQL을 실행할 때, 같은 커넥션을 공유해야한다.

 

보통 웹 요청 하나가 올 때마다, 의미 있는 하나의 비즈니스 로직을 수행하게 됩니다. 비즈니스 로직은 그 복잡성이 각각 다르겠지만 공통적으로 부분만 성공하고, 부분만 실패해서는 안 됩니다. 이 비즈니스 로직 각각의 원자성을 보장하기 위해서는 트랜잭션을 적용해야합니다.

 

애플리케이션 로직은 SQL 하나만 실행하기보다 여러 SQL을 연속적으로 수행해야하는 경우가 많은데, 이 SQL을 실행할 때마다 각각 같은 커넥션을 사용하여, 같은 DB 세션을 통해 같은 트랜잭션 위에서 실행되어야합니다.

 

그런데 우리가 기존에 작성한 코드들을 봅시다. 리포지토리단에서 계속해서 dataSource를 통해, 매번 다른 커넥션을 획득해오는 것을 알 수 있습니다. SQL들을 실행할 때 리포지토리의 메서드들을 호출할텐데, 각각의 메서드는 다른 커넥션을 사용하므로 이들은 같은 트랜잭션 위에서 동작하지 않는다는 것을 알 수 있습니다.

 

앞으로 실제로 트랜잭션 관련 코드를 작성할 때, 커넥션을 공유해야함을 염두해둬야합니다.


마치며

 

이번 글에서는 커넥션-DB 세션-트랜잭션의 관계를 살펴보았습니다. 이론적으로 각각의 요소가 어떤 관계가 있는 지를 살펴봤고, 이제 이 지식을 기반으로 트랜잭션 코드를 하나 하나 작성해볼 것입니다.

 

다음 글에서는 커넥션을 통해 트랜잭션 코드를 작성해보고, 같은 트랜잭션 위에서 SQL을 실행할 수 있도록 커넥션을 공유할 수 있도록 하는 방법을 알아보도록 하겠습니다.


Comments