当前位置: 首页 > 知识库问答 >
问题:

如何在运行时创建数据源bean而不会在Spring中崩溃?

田瀚
2023-03-14

我正在连接多个数据源,但有时某些数据源可能处于脱机状态,此时我在应用程序上遇到错误,应用程序在启动时失败。

我想在启动时跳过数据源配置...我已经尝试了几种方法

spring.autoconfigure.exclude=org.springframework.boot.autoconfigure.jdbc.DataSourceAutoConfiguration 

application.properties,我也试着添加

@SpringBootApplication(exclude={DataSourceAutoConfiguration.class})

到主类,但它仍然试图配置数据源。

我还尝试在所有方法和构造函数上使用@Lazy注释,如下所示,但在创建efEntityManagerFactory时仍然出错

@Lazy
@Configuration
@EnableJpaRepositories(basePackages = "com.heyo.tayo.repository.foo", entityManagerFactoryRef = "fooEntityManagerFactory", transactionManagerRef = "fooTransactionManager")
public class PersistencefooConfiguration {

    @Autowired
    private DbContextHolder dbContextHolder;

    @Lazy
    @Bean
    @ConfigurationProperties("tay.datasource.foo")
    public DataSourceProperties fooDataSourceProperties() {
        return new DataSourceProperties();
    }

    @Lazy
    @Bean
    @ConfigurationProperties("tay.datasource.foo.configuration")
    public DataSource fooDataSource() {
        DataSource dataSource = fooDataSourceProperties().initializeDataSourceBuilder()
                    .type(BasicDataSource.class).build();
        dbContextHolder.addNewAvailableDbType(DbTypeEnum.foo);

        return dataSource;
    }

    @Lazy
    @Bean(name = "fooEntityManagerFactory")
    public LocalContainerEntityManagerFactoryBean fooEntityManagerFactory(
            EntityManagerFactoryBuilder builder) {

//THE CODE IS FAILING AT BELOW RETURN CASE

        return builder
                .dataSource(fooDataSource())
                .packages("com.heyo.tayo.model.foo")
                .build();
    }

    @Lazy
    @Bean
    public PlatformTransactionManager fooTransactionManager(
            final @Qualifier("fooEntityManagerFactory") LocalContainerEntityManagerFactoryBean fooEntityManagerFactory) {
        return new JpaTransactionManager(fooEntityManagerFactory.getObject());
    }

}

对于不同数据源的不同配置,我有多个类似于上面的类,我正在将它们添加到DataSourceBean的可用dbs静态列表中。

这是我的db适配器工厂类。

这是我的dbAdaptor工厂,它创建了相应的db适配器

@Service
public class DbAdapterFactory {

    @Autowired
    private BeanFactory beanFactory;

    @Autowired
    private DbContextHolder dbContextHolder;

    public DBAdapter dbAdapter(){

        DbTypeEnum currentDb = dbContextHolder.getCurrentDb();
        DBAdapter dbAdapter = null;

        if(currentDb == DbTypeEnum.FOODB) {
            dbAdapter = beanFactory.getBean(foodbadaptor.class);
        } else {
            dbAdapter = beanFactory.getBean(koodbadaptor.class);
        }

        return dbAdapter;
    }

这里是db上下文持有人,可以进行设置默认db或获取当前db等操作:

@Component
public class DbContextHolder {

    private DbTypeEnum dbType = DbTypeEnum.FOODB;
    private Set<DbTypeEnum> availableDbTypes = new HashSet<>();

    public void setCurrentDb(DbTypeEnum dbType) {
        this.dbType = dbType;
    }

    public DbTypeEnum getCurrentDb() {
        return this.dbType;
    }

    public List<DbTypeEnum> getAvailableDbTypes() {
        return new ArrayList<>(availableDbTypes);
    }

    public void addNewAvailableDbType(DbTypeEnum dbTypeEnum) {
        availableDbTypes.add(dbTypeEnum);
    }
}

我做了所有@Lazy或尝试@SpringBootApplication(排除={DataSourceAutoConfiguration.class}),但仍然有东西在调用创建bean并获得错误和应用程序正在关闭。我想使用该配置和数据源在一个尝试捕捉块,不要停止应用程序在运行时。我如何实现这一点,或者我在配置或注释中缺少什么?

共有1个答案

谷涵容
2023-03-14

我相信您可以简单地添加应用程序属性

spring.sql.init.continue-on-error=true

根据Spring护套2.5。5用户指南:

https://docs.spring.io/spring-boot/docs/2.5.5/reference/htmlsingle/#howto-initialize-a-database-using-spring-jdbc

SpringBoot支持其基于脚本的数据库初始值设定项的快速失败功能。如果脚本导致异常,则应用程序无法启动。您可以通过设置spring来调整该行为。sql。初始化。错误时继续。

根据您的spring启动版本,该属性将被命名为

spring.sql.init.continue-on-error

或者在Spring Boot 2.5之前

spring.datasource.continue-on-error
 类似资料:
  • 我正在用Spring Data JPA做一个项目。 我已经设法用BeanFactoryPostProcessor动态创建了datasource,并在使用AbstracTroutingDataSource登录时切换到所需的datasource。 现在我想在运行时做的是: 使用BeanFactoryPostProcessor获取动态数据源映射 创建新的数据源 将最近创建的数据源与其他数据源一起放在映射

  • 问题内容: 我正在使用Hibernate租约,并且每次用户登录时,我都将数据库更改为其用户名(SQLite)。可悲的是,有时数据库不存在,我需要创建它。 问题是我不知道如何在运行时在数据库中创建所有表。 通常,Hibernete为此创建数据库: 问题答案: 创建数据库之后,可以为此使用SchemaExport导出要在新创建的数据库中创建的实体。基本步骤如下。如何获取配置的属性并不重要。 Javad

  • 我正在创建JavaMailSender的bean类,并自动拥有javamailsender,但我得到错误 我不能为bean id="mail Sender"创建bean类。我在过去的两天里一直在努力,请让我离开它。 和错误页 组织。springframework。豆。工厂BeanCreationException:创建名为“employeeController”的bean时出错:自动连线依赖项的注

  • 请帮我解决这个问题。抱歉,我无法格式化StackTrace。

  • 我的目标是使用Spring创建一个Webserver。它必须实现Multitenancy,如果您不使其动态(添加、删除、更改),它会很好地工作。是否可以在Spring中更新数据源bean? 我的代码: 我试过的: 它更新bean(?)但不更新Spring的数据源,如果使用此方法添加,数据库连接仍然缺失。

  • Spring Boot:如何在运行时添加新数据源 我的项目想要连接两个数据源。 第一个数据源我可以在application.properties配置,但第二个数据源不能配置,因为此配置位于第一个数据源的DB的表配置中。 所以, 配置第一个数据源 现在,我从application.properties配置两个数据源,它的工作。 但需求需要更改第一个数据源表中的第二个数据源。T、 T型 请给我一些建议