https://sanghye.tistory.com/26


회사에서 한 애플리케이션에 멀티 디비를 연결해야 하는 업무를 맞게 되었다. 기존 서비스를 운영하는 디비와 별개로 사용하면서 디비 관리를 하자는 의견이 나와 작업을 진행하였다. 처음에 우선 도커를 통해 로컬 디비에 접속해 디비 설치 > 연결을 해주었고, 그 이후에 많은 시행 착오 끝에 멀티 디비와 연결할 수가 있었다. 그 과정에서 어렵고 헤맸던 과정을 기록해보고자 한다.
먼저 한 애플리케이션에 프로젝트 다시 생성 및 설정까지 다시 해줘야했기 때문에 꽤나 어려움을 겪고 고생을 했는데 이 애플리케이션에 멀티 디비까지 연결해야한다니… 산넘어 산이었다. 먼저 첫 번째 만난 에러는 바로 스프링 순환 참조 문제였다.
디비가 2개이다 보니 DBConfig에서 생성해주는 빈 또한 2개일 수 밖에 없다. 서로 다른 빈들이 서로 참조를 맞물리게 주입되면서 생기는 현상인데 beanA에서 beanB를 참조하는 과정에서 beanB에서도 beanA를 참조해야하는 경우 이 문제가 발생하고 만다. 그래서 각각 메인으로 사용할 빈에게 @primary 어노테이션을 추가해주었고, 그래도 해결이 되지 않았다. 하지만 문제는 그게 아니었고, DBConfig에서 sqlSessionFactory를 설정해주었어야 했는데 나는 하나의 DBConfig 안에서 각각 다른 sqlSessionFactory를 변수로 선언해주었고 문제는 그거였다. SqlSessionFactory는 이 이름 외에 다른 어떠한 것도 올 수가 없었다. 그렇다면 멀티 디비에 대한 각각 sqlSessionFactory는 어떻게 설정해주어야할까? 이 문제를 해결하기 위해서는 DBConfig패키지를 2개로 나눈 후 각각 해당되는 DBConfig 안에서 sqlSessionFactory를 설정해주면 순환참조 문제는 해결이 되었다.
두 개의 데이터 소스가 선언 되었을 때 자동 injection을 하고자 한다면 어떻게 지정해줘야하는지 문제였다. 방법은 @Autowired 어노테이션을 사용하는 것.
이 어노테이션은 Spring framwork에서 지원하는 dependency 정의 용도의 어노테이션으로, 스프링 프레임워크에 종속적이긴 하지만 정밀한 dependency Injection이 필요한 경우에 유용하다. 이 어노테이션을 사용하거나 아니면 @Resource 어노테이션을 사용해도 된다. 하지만 나는 Autowired를 사용하기로 결정했다.
그렇다면 두 어노테이션의 차이점은 무엇일까?
@Autowired: 필드, 생성자, 입력 파라미터가 여러 개인 메소드(@Qualifier는 메소드의 파라미터)에 적용이 가능하다이고,
@Resource는 필드, 입력 파라미터가 한 개인 빈 프로퍼티 setter메소드에 적용이 가능하다는 것이다.
하지만 중요한 것은 메인 데이터소스에는 무조건 @Primary를 써줘야한다는 것!
그리고 경로 문제도 있었다. application.properties에서 아래와 같이 디비에 대한 명명을 제대로 해주지 않아서 디비가 연결되지 않았던 문제도 있었다.
나에게는 꽤나 어려운 작업이었는데 조금 더 시간은 단축했으면 좋지 않았을까 하는 회고를 해본다.