Generate DDL with spring boot using a custom delimiter

前端 未结 5 1862
臣服心动
臣服心动 2020-12-31 20:27

I want generate create and drop ddl scripts using spring boot v1.4.3 with JPA - Hibernate 5.0.11.

Most answers I found use the javax.persistence.schema-generati

5条回答
  •  盖世英雄少女心
    2020-12-31 21:18

    Finally after a lot of investigation I think I found an easy solution that uses public APIs. The solution I found uses hibernate 5.2 (more concrete 5.2.6.Final). But I think it can also be adapted to 5.0

    Here is my spring java configuration

    @Configuration
    @AutoConfigureAfter({ HibernateJpaAutoConfiguration.class })
    public class HibernateJavaConfig {
    
        @ConditionalOnMissingBean({ Metadata.class })
        @Bean
        public Metadata getMetadata(StandardServiceRegistry standardServiceRegistry,
                PersistenceUnitInfo persistenceUnitInfo) {
            MetadataSources metadataSources = new MetadataSources(standardServiceRegistry);
    
            List managedClassNames = persistenceUnitInfo.getManagedClassNames();
            for (String managedClassName : managedClassNames) {
                metadataSources.addAnnotatedClassName(managedClassName);
            }
    
            Metadata metadata = metadataSources.buildMetadata();
            return metadata;
        }
    
        @ConditionalOnMissingBean({ StandardServiceRegistry.class })
        @Bean
        public StandardServiceRegistry getStandardServiceRegistry(JpaProperties jpaProperties) {
            StandardServiceRegistryBuilder ssrb = new StandardServiceRegistryBuilder();
    
            Map properties = jpaProperties.getProperties();
            ssrb.applySettings(properties);
    
            StandardServiceRegistry ssr = ssrb.build();
            return ssr;
        }
    
        @ConditionalOnMissingBean({ PersistenceUnitInfo.class })
        @Bean
        public PersistenceUnitInfo getPersistenceUnitInfo(EntityScanPackages entityScanPackages) {
            List packagesToScan = entityScanPackages.getPackageNames();
    
            DefaultPersistenceUnitManager persistenceUnitManager = new DefaultPersistenceUnitManager();
    
            String[] packagesToScanArr = (String[]) packagesToScan.toArray(new String[packagesToScan.size()]);
            persistenceUnitManager.setPackagesToScan(packagesToScanArr);
            persistenceUnitManager.afterPropertiesSet();
    
            PersistenceUnitInfo persistenceUnitInfo = persistenceUnitManager.obtainDefaultPersistenceUnitInfo();
            return persistenceUnitInfo;
        }
    
    }
    

    The java configuration creates a Metadata bean. This bean can be used in hibernate 5.2 to execute a schema generation. E.g.

    @Component
    public class GenerateDDLApplicationRunner implements ApplicationRunner {
    
        private Metadata metadata;
    
        public GenerateDDLApplicationRunner(Metadata metadata) {
            this.metadata = metadata;
        }
    
        public void run(ApplicationArguments args) throws Exception {
            File dropAndCreateDdlFile = new File("drop-and-create.ddl");
            deleteFileIfExists(dropAndCreateDdlFile);
    
            SchemaExport schemaExport = new SchemaExport();
            schemaExport.setDelimiter(";");
            schemaExport.setFormat(false);
            schemaExport.setOutputFile(dropAndCreateDdlFile.getAbsolutePath());
    
            schemaExport.execute(EnumSet.of(TargetType.SCRIPT), Action.BOTH, metadata);
        }
    
        private void deleteFileIfExists(File dropAndCreateDdlFile) {
            if (dropAndCreateDdlFile.exists()) {
                if (!dropAndCreateDdlFile.isFile()) {
                    String msg = MessageFormat.format("File is not a normal file {0}", dropAndCreateDdlFile);
                    throw new IllegalStateException(msg);
                }
    
                if (!dropAndCreateDdlFile.delete()) {
                    String msg = MessageFormat.format("Unable to delete file {0}", dropAndCreateDdlFile);
                    throw new IllegalStateException(msg);
                }
            }
        }
    
    }
    

    The hibernate dialect is configured using the spring boot application.properties. In my case:

    spring.jpa.properties.hibernate.dialect = org.hibernate.dialect.MySQL57InnoDBDialect
    

提交回复
热议问题