0. 시작 전 Gradle 설정 내용 확인

https://minaminaworld.tistory.com/218

 

[SpringBoot] 멀티 데이터베이스 설정하기 - 설정편

1. Gradle 설정 dependencies { implementation 'org.springframework.boot:spring-boot-starter-data-jpa' implementation 'org.springframework.boot:spring-boot-starter-web' testImplementation 'junit:junit..

minaminaworld.tistory.com


1. 테스트 DB, 스키마, 테이블 정보

 - 테스트 DB명: db1

 - 테스트 스키마: jpa

 - 테스트 테이블: userjpa (Jpa Option: create를 통한 자동 생성함)

 

 


2. application.yml 과 application-local.yml

 - application.yml

spring:
  profiles:
    active: local

- application-local.yml

spring:
  config:
    activate:
      on-profile: local
  datasource:
    jpa:
      #     jdbc-url: jdbc:postgresql://localhost:5432/db1
      url: jdbc:postgresql://localhost:5432/db1
      username: postgres
      password: postgres
      driver-class-name: org.postgresql.Driver
    mybatis:
      #      jdbcUrl: jdbc:postgresql://localhost:5432/db1
      url: jdbc:postgresql://localhost:5432/db1
      username: postgres
      password: postgres
      driver-class-name: org.postgresql.Driver
server:
  port: 8090 # 서버 포트 변경

3. JpaDbProperties.java : 데이터베이스 설정 정보 세팅(yml 참고)

package com.example.multidb.database.config;

import lombok.Getter;
import lombok.Setter;
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.stereotype.Component;

@Component
@ConfigurationProperties(prefix = "spring.datasource.jpa") // application-local.yml 참고
@Getter
@Setter
public class JpaDbProperties {
    String url;
    String username;
    String password;
    String driverClassName;
}

4. UserJpa.java와 UserJpaRepository.java

- UserJpa.java

package com.example.multidb.domain.jpa;

import lombok.*;
import javax.persistence.*;

@Entity
@SequenceGenerator(
        name = "USER_SEQ_GEN", // 시퀀스 제너레이터 이름
        sequenceName = "USER_SEQ", // 시퀀스 이름
        initialValue = 1,
        allocationSize = 1 // 메모리를 통해 할당할 범위 사이즈
)
@Getter
@Setter
@NoArgsConstructor(access = AccessLevel.PROTECTED)
@Table(schema = "jpa")
public class UserJpa {

    @Id
    @GeneratedValue(
            strategy = GenerationType.SEQUENCE,
            generator = "USER_SEQ_GEN"
    )
    private Long id;

    private String name;

    @Column(unique = true, nullable = false)
    private String email;

    private int age;

    public UserJpa(String name, String email, int age) {
        this.name = name;
        this.email = email;
        this.age = age;
    }

}

- UserJpaRepository.java

package com.example.multidb.persistence.jpa.repository;

import com.example.multidb.domain.jpa.UserJpa;
import org.springframework.data.jpa.repository.JpaRepository;
import org.springframework.stereotype.Repository;

@Repository
public interface UserJpaRepository extends JpaRepository<UserJpa, Long> {

}

4. JpaDb.java: DB 설정하기

 - 1번과 2번 방식 동일하게 DataSouce를 생성할 수 있음으로 참고하시길 바랍니다.

 

package com.example.multidb.database.config;

import com.google.common.collect.ImmutableMap;
import lombok.RequiredArgsConstructor;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.boot.jdbc.DataSourceBuilder;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.Primary;
import org.springframework.data.jpa.repository.config.EnableJpaRepositories;
import org.springframework.orm.jpa.JpaTransactionManager;
import org.springframework.orm.jpa.JpaVendorAdapter;
import org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean;
import org.springframework.orm.jpa.vendor.HibernateJpaVendorAdapter;
import org.springframework.transaction.PlatformTransactionManager;

import javax.persistence.EntityManagerFactory;
import javax.sql.DataSource;

@Configuration
@EnableJpaRepositories(
        entityManagerFactoryRef = "jpaEntityManagerFactory",
        transactionManagerRef = "jpaTransactionManager",
        basePackages = {"com.example.multidb.persistence.jpa.repository"} // Repository 위치
)
@RequiredArgsConstructor
public class JpaDb {
//// 1번 방식 ----------------------------------------------------------------------------
//    @Bean
//    @ConfigurationProperties(prefix = "spring.datasource.jpa")
//    public DataSourceProperties jpaDataSourceProperties() {
//        DataSourceProperties dataSourceProperties = new DataSourceProperties();
//        return dataSourceProperties;
//    }
//
//    @Bean(name = "jpaDataSource")
//    public DataSource dataSource(@Qualifier("jpaDataSourceProperties") DataSourceProperties dataSourceProperties) {
//        // 프로퍼티 정보
//        String url = dataSourceProperties.getUrl();
//        String username = dataSourceProperties.getUsername();
//        String password = dataSourceProperties.getPassword();
//        String driverClassName = dataSourceProperties.getDriverClassName();
//
//        System.out.println("------------------------------------------");
//        System.out.println("url = " + url);
//        System.out.println("username = " + username);
//        System.out.println("password = " + password);
//        System.out.println("driverClassName = " + driverClassName);
//        System.out.println("------------------------------------------");
//
//        return dataSourceProperties.initializeDataSourceBuilder().type(HikariDataSource.class).build();
//    }
//// ---------------------------------------------------------------------------- 1번 방식

    // 2번 방식 ----------------------------------------------------------------------------
    private final JpaDbProperties jpaDbProperties;

    @Primary
    @Bean(name = "jpaDataSource")
    public DataSource dataSource() {
        // 빌더 dataSource 생성

        // 프로퍼티 정보
        System.out.println("------------------------------------------");
        String url = jpaDbProperties.getUrl();
        String username = jpaDbProperties.getUsername();
        String password = jpaDbProperties.getPassword();
        String driverClassName = jpaDbProperties.getDriverClassName();

        System.out.println("url = " + url);
        System.out.println("username = " + username);
        System.out.println("password = " + password);
        System.out.println("driverClassName = " + driverClassName);
        System.out.println("------------------------------------------");

        return  DataSourceBuilder.create()
                .url(jpaDbProperties.getUrl())
                .username(jpaDbProperties.getUsername())
                .password(jpaDbProperties.getPassword())
                .driverClassName(jpaDbProperties.getDriverClassName())
                .build();
    }
    // ---------------------------------------------------------------------------- 2번 방식

    @Bean(name = "jpaEntityManagerFactory")
    @Primary
    public EntityManagerFactory entityManagerFactory(
            @Qualifier("jpaDataSource") DataSource dataSource
    ) {
        LocalContainerEntityManagerFactoryBean factory = new LocalContainerEntityManagerFactoryBean();
        factory.setDataSource(dataSource);
        factory.setPackagesToScan(new String[]{"com.example.multidb.domain.jpa"}); //Entity 위치
        factory.setPersistenceUnitName("jpa");

        JpaVendorAdapter vendorAdapter = new HibernateJpaVendorAdapter();
        factory.setJpaVendorAdapter(vendorAdapter);
        factory.setJpaPropertyMap(ImmutableMap.of(
                "hibernate.hbm2ddl.auto", "create",
//                "hibernate.hbm2ddl.auto", "create-drop",
                "hibernate.dialect", "org.hibernate.dialect.PostgreSQL10Dialect",
                "hibernate.show_sql", "true",
                "hibernate.format_sql", "true",
                "hibernate.open-in-view", "false"
        ));
        factory.afterPropertiesSet();
        return factory.getObject();
    }

    @Bean(name = "jpaTransactionManager")
    @Primary
    public PlatformTransactionManager transactionManager(@Qualifier("jpaEntityManagerFactory") EntityManagerFactory entityManagerFactory) {
        JpaTransactionManager tm = new JpaTransactionManager();
        tm.setEntityManagerFactory(entityManagerFactory);
        return tm;
    }

}

5. JpaService.java와 JpaServiceTest.java: UserJpa 생성 서비스 코드와 테스트 작성

- JpaService.java

package com.example.multidb.service;

import com.example.multidb.domain.jpa.UserJpa;
import com.example.multidb.persistence.jpa.repository.UserJpaRepository;
import lombok.RequiredArgsConstructor;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

@Service
@RequiredArgsConstructor
public class JpaService {

    private final UserJpaRepository userJpaRepository;

    @Transactional
    public void createUser(String name, String email, int age) {
//        UserJpa userJpa = new UserJpa("A", "a@email.com", 20);
        userJpaRepository.save(new UserJpa(name, email, age));
    }
}

- JpaServiceTest.java

package com.example.multidb.service;

import org.junit.jupiter.api.DisplayName;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;

import static org.junit.jupiter.api.Assertions.*;

@SpringBootTest
class JpaServiceTest {

    @Autowired
    private JpaService jpaService;

    @Test
    @DisplayName("JPA 유저 생성")
    void createUser() {
        //        UserJpa userJpa = new UserJpa("A", "a@email.com", 20);
        for (int i = 0; i < 10; i++) {
            jpaService.createUser("A" + i, "a" + i + "@email.com", 20 + i);
        }
    }
}

6. 테스트 결과


 

블로그 이미지

미나미나미

,