programing

Spring-Boot 실행 데이터.하나의 프로파일에서만 sql

topblog 2023. 7. 2. 18:58
반응형

Spring-Boot 실행 데이터.하나의 프로파일에서만 sql

나는 프로필 "기본"을 사용하여 Postgre에 연결하는 이 응용 프로그램을 가지고 있습니다.SQL 데이터베이스 및 Flyway를 사용한 마이그레이션을 수행합니다.

"devEmbeddedCreate"라는 다른 프로파일을 만들고 싶습니다. 여기서 내장형 데이터베이스 서버(h2)를 사용하고 다음을 사용하여 데이터베이스를 만듭니다.spring.jpa.hibernate.ddl-auto=create-drop에서application.properties파일을 작성하고 "data.sql" 스크립트를 실행하여 일부 테이블을 초기화합니다.

스크립트를 "data.sql" 파일 이름으로 남겨두면 응용 프로그램이 시작될 때마다 실행됩니다.그건 제가 원하지 않는 일입니다. 특정 프로필에서만 실행해야 합니다.

제가 시도해 본 것들:

  1. 문서에는 다음이 있을 수 있다고 나와 있습니다.schema-${platform}.sql파일을 사용하여 플랫폼을 정의할 수 있습니다.spring.datasource.platform구성에서.그것이 작동하지 않는 문제는data-${platform}.sql파일. (여기)

  2. 생성됨EmbeddedDatabaseBuilder문제는 내가 그것을 사용할 때, 그것은 자동으로 데이터베이스를 만들지 않고 지정된 스크립트만 적용한다는 것입니다.다음과 같이 데이터베이스를 자동으로 작성할 수 없습니다.spring.jpa.hibernate.ddl-auto=create-drop합니다. (여기와 여기)

  3. XML 구성을 Java 기반 구성으로 변환하는 방법을 찾고 있던 중 데이터베이스와 모든 구성을 생성하는 방법을 찾았습니다.메모리에서 작동하도록 여러 번 조정하고 변경한 후 유망해 보였지만 시작하는 동안(여기서는) 데이터베이스가 닫히는 이유(그리고 모든 구조가 지워짐)를 찾지 못했습니다.

그냥 "헤이 스프링"이라고 말할 수 있는 더 간단한 방법이 있을 거예요이것을 시작으로 실행합니다.data-devEmbeddedCreate.sql내 프로필이 다음일 때 스크립트devEmbeddedCreate,그렇죠?

1) 접근 방식은 올바른 방향으로 진행되었지만 다음을 통해 데이터 소스 플랫폼을 설정해야 합니다.spring.datasource.platform,것은 아니다.spring.jpa.database-platform스크립트 실행 기능은 JPA별 기능이 아닙니다.

또한 다음을 설정하여 실행할 SQL 스크립트 파일을 수동으로 지정할 수 있습니다.spring.datasource.schema소유물.org.springframework.boot.autoconfigure.jdbc에서 발췌한 내용입니다.1.0.2의 DataSourceAutoConfiguration 파일입니다.릴리스:

String schema = this.datasourceProperties.getProperty("schema");
if (schema == null) {
    schema = "classpath*:schema-"
            + this.datasourceProperties.getProperty("platform", "all")
            + ".sql,classpath*:schema.sql,classpath*:data.sql";
}

문서에 지정된 파일 집합은 사용자 자신의 목록을 지정하지 않은 경우에만 사용됩니다.

미래의 독자들을 위해.

저는 이것을 조금 다른 방법으로 해결했습니다..."vmx config"를 사용합니다.

다음 중 가장 중요한 부분은 다음과 같습니다.

@Bean @Profile(SPRING_PROFILE_DEFAULT) public DataSourceInitializer getDataSourceInitializer(최종 데이터 소스 데이터 소스) {

프로파일이 활성화된 경우에만 "data.sql"이라는 이름이 아닌 .sql 파일이 로드됩니다.

import org.springframework.beans.factory.annotation.Value;
import org.springframework.boot.jdbc.DataSourceBuilder;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.Profile;
import org.springframework.core.env.Environment;
import org.springframework.core.io.Resource;
import org.springframework.dao.annotation.PersistenceExceptionTranslationPostProcessor;
import org.springframework.jdbc.datasource.init.DataSourceInitializer;
import org.springframework.jdbc.datasource.init.DatabasePopulator;
import org.springframework.jdbc.datasource.init.ResourceDatabasePopulator;
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 org.springframework.transaction.annotation.EnableTransactionManagement;

import javax.sql.DataSource;
import java.util.Optional;
import java.util.Properties;

@Configuration
@EnableTransactionManagement
/* below @CS is not needed with setPackagesToScan */
//@ComponentScan(basePackageClasses = {SomeJpaEntityOne.class, SomeJpaEntityTwo.class})
public class PersistenceJpaConfig {

    public static final String SPRING_PROFILE_DEFAULT = "default";

    /* the below file-name is purposely not "data.sql" (or data-spring.sql) to avoid/bypass "auto-find" spring-data logic.  the file/resource is referred to later in a specific spring profile */
    @Value("classpath:developer.local.seed.data.dml.sql")
    private Resource seedDataLocalDeveloperResource;

    /**
     * @param env
     * @return
     */
    /* bean must be named entityManagerFactory to satisfy spring-jpa magic */
    @Bean(name = "entityManagerFactory")
    public LocalContainerEntityManagerFactoryBean entityManagerFactory(Environment env) {
        final LocalContainerEntityManagerFactoryBean em = new LocalContainerEntityManagerFactoryBean();
        em.setDataSource(this.getDataSourceOne());

        final String entityManagerFactoryPackagesToScanCsv = "com.myentitiespackageone,com.myentitiespackagetwo";
        String[] packagesArray = entityManagerFactoryPackagesToScanCsv.split(",");
        em.setPackagesToScan(packagesArray);

        final JpaVendorAdapter vendorAdapter = new HibernateJpaVendorAdapter();
        em.setJpaVendorAdapter(vendorAdapter);
        em.setJpaProperties(getCustomHibernateProperties(env, configMapRetriever));

        return em;
    }

    @Bean
    public DataSource getDataSourceOne() {

        DataSourceBuilder dataSourceBuilder = DataSourceBuilder.create();
        dataSourceBuilder.driverClassName("myDataSourceDriverClassName");
        dataSourceBuilder.url("mydataSourceUrl");
        dataSourceBuilder.username("mydataSourceUserName");
        dataSourceBuilder.password("myPassword");

        DataSource returnItem = dataSourceBuilder.build();
        return returnItem;
    }

    /**
     * @param env
     * @param secretRetriever
     * @param configMapRetriever
     * @return JPA PlatformTransactionManager
     */
    /* This bean must be named 'transactionManager' to satisfy jpa string-magic */
    @Bean(name = "transactionManager")
    public PlatformTransactionManager getAPlatformTransactionManager(Environment env) {
        final JpaTransactionManager transactionManager = new JpaTransactionManager();
        transactionManager.setEntityManagerFactory(entityManagerFactory(env).getObject());
        return transactionManager;
    }

    /**
     * @return JPA PersistenceExceptionTranslationPostProcessor
     */
    @Bean
    public PersistenceExceptionTranslationPostProcessor getAPersistenceExceptionTranslationPostProcessor() {
        return new PersistenceExceptionTranslationPostProcessor();
    }

    final Properties getCustomHibernateProperties(Environment env, IConfigMapRetriever configMapRetriever) {

        Properties hibernateProperties = new Properties();
        /* not shown */
        /* but stuff like

                "hibernate.dialect"
                "hibernate.hbm2ddl.auto"
                "hibernate.jdbc.batch_size"
                "hibernate.jdbc.fetch_size"
                "hibernate.order_inserts"
                "hibernate.order_updates"
                "hibernate.jdbc.batch_versioned_data"
                "hibernate.generate_statistics"
                "hibernate.show_sql"
                "hibernate.format_sql"

        */

        return hibernateProperties;
    }

    /**
     * @param dataSource
     * @return
     */
    @Bean
    @Profile(SPRING_PROFILE_DEFAULT)
    public DataSourceInitializer getDataSourceInitializer(final DataSource dataSource) {
        final DataSourceInitializer initializer = new DataSourceInitializer();
        initializer.setDataSource(dataSource);
        initializer.setDatabasePopulator(getDatabasePopulator());
        return initializer;
    }

    private DatabasePopulator getDatabasePopulator() {
        final ResourceDatabasePopulator populator = new ResourceDatabasePopulator();
        populator.addScript(seedDataLocalDeveloperResource);
        return populator;
    }
}

언급URL : https://stackoverflow.com/questions/23790743/spring-boot-execute-data-sql-in-one-profile-only

반응형