Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/spring/12.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
如何在XML配置文件中使用SpringBoot自动配置bean?_Spring_Spring Integration_Spring Boot - Fatal编程技术网

如何在XML配置文件中使用SpringBoot自动配置bean?

如何在XML配置文件中使用SpringBoot自动配置bean?,spring,spring-integration,spring-boot,Spring,Spring Integration,Spring Boot,我想利用XML配置文件中的一些Spring Boot自动配置bean,但在尝试这样做时,我总是遇到异常和错误 例如,如果我的类路径上有与数据相关的库,Spring Boot将自动配置一个DataSource对象,我可以将该对象自动连接到我自己的bean和类中,如下所示: @Configuration @ImportResource("classpath:xmlconfig.xml") public class Config { // This works!! @Autowire

我想利用XML配置文件中的一些Spring Boot自动配置bean,但在尝试这样做时,我总是遇到异常和错误

例如,如果我的类路径上有与数据相关的库,Spring Boot将自动配置一个
DataSource
对象,我可以将该对象自动连接到我自己的bean和类中,如下所示:

@Configuration
@ImportResource("classpath:xmlconfig.xml")
public class Config {

    // This works!!
    @Autowired
    private DataSource dataSource;

    @Bean
    public ClassThatRequiresADataSource() {
        ClassThatRequiresADataSource foo = new ClassThatRequiresADataSource();
        foo.setDataSource(dataSource);
        return foo;
    }
}
但是,如果我尝试在XML配置文件中执行同样的操作,我将得到一个异常。我已经通过在我的主配置类中添加一个
@ImportResource(“classpath:xmlconfig.XML”)
来引导XML配置文件。这是我所说的一个例子。。。内部
xmlconfig.xml

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd">

    <!-- THIS DOES NOT WORK! -->
    <bean id="anotherClassThatRequiresADataSource" class="my.package.AnotherClassThatRequiresADataSource">
        <property name="dataSource" ref="dataSource"/>
    </bean>

</beans>
我主要在Spring集成应用程序中使用它,Java配置还没有得到很好的支持,框架的核心是基于XML配置的,但是我想在一些集成元素中使用Spring Boot自动配置的
DataSource
ConnectionFactory
bean

编辑:@AdilF提供的答案适用于
dataSource
bean,但类似的配置不适用于
connectionFactory
bean。请参阅下面的GitHub项目,以获取演示代码:

如果有人能想出如何正确连接
connectionFactory
bean,我将不胜感激

下面是说明这一点的大部分代码:

Application.java

@Configuration
@ComponentScan
@EnableAutoConfiguration
public class Application {

    public static void main(String[] args) {
        SpringApplication.run(Application.class, args);
    }
}
Config.java

@Configuration
@ImportResource("classpath:/resources/config.xml")
public class Config { }
FooService.java

@Service
public class FooService {

    final private Logger logger = LoggerFactory.getLogger(FooService.class);

    @Autowired
    private DataSource dataSource;

    @Autowired
    private ConnectionFactory connectionFactory;

    @Autowired
    private EntityManagerFactory entityManagerFactory;

    @PostConstruct
    public void init() {
        Assert.notNull(dataSource, "dataSource is null!");
        logger.info("dataSource not null");

        Assert.notNull(connectionFactory, "connectionFactory is null!");
        logger.info("connectionFactory not null");

        Assert.notNull(entityManagerFactory, "entityManagerFactory is null!");
        logger.info("entityManagerFactory is not null");
    }
}
public class BarService {

    final private Logger logger = LoggerFactory.getLogger(BarService.class);

    private DataSource dataSource;

    private ConnectionFactory connectionFactory;

    private EntityManagerFactory entityManagerFactory;

    public void setDataSource(DataSource dataSource) {
        this.dataSource = dataSource;
    }

    public void setConnectionFactory(ConnectionFactory connectionFactory) {
        this.connectionFactory = connectionFactory;
    }

    public void setEntityManagerFactory(final EntityManagerFactory entityManagerFactory) {
        this.entityManagerFactory = entityManagerFactory;
    }

    @PostConstruct
    public void init() {
        Assert.notNull(dataSource, "dataSource is null!");
        logger.info("dataSource not null");

        Assert.notNull(connectionFactory, "connectionFactory is null!");
        logger.info("connectionFactory not null");

        Assert.notNull(entityManagerFactory, "entityManagerFactory is null!");
        logger.info("entityManagerFactory is not null");
    }
}
BarService.java

@Service
public class FooService {

    final private Logger logger = LoggerFactory.getLogger(FooService.class);

    @Autowired
    private DataSource dataSource;

    @Autowired
    private ConnectionFactory connectionFactory;

    @Autowired
    private EntityManagerFactory entityManagerFactory;

    @PostConstruct
    public void init() {
        Assert.notNull(dataSource, "dataSource is null!");
        logger.info("dataSource not null");

        Assert.notNull(connectionFactory, "connectionFactory is null!");
        logger.info("connectionFactory not null");

        Assert.notNull(entityManagerFactory, "entityManagerFactory is null!");
        logger.info("entityManagerFactory is not null");
    }
}
public class BarService {

    final private Logger logger = LoggerFactory.getLogger(BarService.class);

    private DataSource dataSource;

    private ConnectionFactory connectionFactory;

    private EntityManagerFactory entityManagerFactory;

    public void setDataSource(DataSource dataSource) {
        this.dataSource = dataSource;
    }

    public void setConnectionFactory(ConnectionFactory connectionFactory) {
        this.connectionFactory = connectionFactory;
    }

    public void setEntityManagerFactory(final EntityManagerFactory entityManagerFactory) {
        this.entityManagerFactory = entityManagerFactory;
    }

    @PostConstruct
    public void init() {
        Assert.notNull(dataSource, "dataSource is null!");
        logger.info("dataSource not null");

        Assert.notNull(connectionFactory, "connectionFactory is null!");
        logger.info("connectionFactory not null");

        Assert.notNull(entityManagerFactory, "entityManagerFactory is null!");
        logger.info("entityManagerFactory is not null");
    }
}
config.xml

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd">

    <bean id="barService" class="app.service.BarService">
        <!-- THIS WORKS! -->
        <property name="dataSource" ref="dataSource"/>

        <!-- THIS DOESN'T WORK! -->
        <property name="connectionFactory" ref="connectionFactory"/>
        <property name="entityManagerFactory" ref="entityManagerFactory"/>
    </bean>

</beans>
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd">

    <bean id="barService" class="app.service.BarService">
        <property name="dataSource" ref="dataSource"/>
    </bean>

</beans>

下面的示例代码适用于我

主要应用

package app;

import org.springframework.boot.SpringApplication;
import org.springframework.context.ConfigurableApplicationContext;
import org.springframework.util.Assert;

import javax.sql.DataSource;

public class Application {

    public static void main(String[] args) {
        ConfigurableApplicationContext context = SpringApplication.run(Config.class);
        DataSource dataSource = context.getBean("dataSource", DataSource.class);
        Assert.notNull(dataSource);
    }

}
Spring Java配置

package app;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.autoconfigure.EnableAutoConfiguration;
import org.springframework.context.annotation.*;
import org.springframework.data.jpa.repository.config.EnableJpaRepositories;

import javax.sql.DataSource;

@Configuration
@EnableAutoConfiguration
@EnableJpaRepositories
@ComponentScan
@ImportResource("classpath:config.xml")
public class Config {

    @Autowired
    private DataSource dataSource;

}
酒吧服务

package app.service;

import org.springframework.util.Assert;
import javax.annotation.PostConstruct;
import javax.sql.DataSource;

public class BarService {

    private DataSource dataSource;

    public void setDataSource(DataSource dataSource) {
        this.dataSource = dataSource;
    }

    @PostConstruct
    public void init() {
        Assert.notNull(dataSource);
    }
}
餐饮服务

package app.service;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.util.Assert;

import javax.annotation.PostConstruct;
import javax.sql.DataSource;

@Service
public class FooService {

    @Autowired
    DataSource dataSource;

    @PostConstruct
    public void init() {
        Assert.notNull(dataSource);
    }

}
config.xml

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd">

    <bean id="barService" class="app.service.BarService">
        <!-- THIS WORKS! -->
        <property name="dataSource" ref="dataSource"/>

        <!-- THIS DOESN'T WORK! -->
        <property name="connectionFactory" ref="connectionFactory"/>
        <property name="entityManagerFactory" ref="entityManagerFactory"/>
    </bean>

</beans>
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd">

    <bean id="barService" class="app.service.BarService">
        <property name="dataSource" ref="dataSource"/>
    </bean>

</beans>

我使用了您的自动配置测试示例项目,并能够使其正常工作。我发现您的xml的唯一问题如下

@PersistenceContext
private EntityManager entityManager
我假设您想使用嵌入式代理。当我运行你的项目时,这是自动配置的

@Bean
public ConnectionFactory jmsConnectionFactory() {
    return this.properties.createConnectionFactory();
}
这将创建一个名为jmsConnectionFactory的bean,但是您的xml正在尝试连接一个名为connectionFactory的bean。将bean名称更改为jmsConnectionFactory修复了

<bean id="barService" class="app.service.BarService">
    <property name="dataSource" ref="dataSource"/>
    <property name="connectionFactory" ref="jmsConnectionFactory"/>
    <property name="entityManagerFactory" ref="entityManagerFactory"/>
</bean>

我知道这超出了这个问题的范围,但我想我应该补充一点

您在哪里创建数据源?java配置和xml配置都没有创建数据源。如果启用了
@EnableAutoConfiguration
功能,Spring Boot会自动创建
数据源。然后,您可以将其自动连接到JavaConfig bean中。对于初学者来说,
应用程序
类需要在已经存在的内容旁边添加
@Configuration
注释。基于Java的配置和XML配置的主要区别在于,Java配置基于类型注入,而XML配置基于名称注入。我建议不要创建
Config
类,而是将
@Configuration
@ImportResource
中的内容移动到应用程序类中(或者将
应用程序
类中的内容移动到
配置
类中)。应用程序类用
@Configuration
注释。我一定是在邮件里漏掉了。在任何一种情况下,如果我将所有内容都移动到应用程序类,我仍然会遇到相同的问题。
@ComponentScan
注释的目的是,我不必将所有bean定义都放在主类中,因此它不应该更改任何内容。您所需要做的就是从
应用程序.java
文件中删除
@Configuration@ComponentScan@EnableAutoConfiguration
,并将其放在
配置.java
上。这对我来说很有效。我的主类启动Spring Boot时已经有了注释集。。。所以这里没有骰子。在我最初的帖子中我应该更清楚,我会继续更新它。在这种情况下,将
--debug
选项添加到命令行参数中,并检查spring boot是否拾取了所有配置。如果你可以发布一个github项目来描述这个问题,我可以看一看。当使用
--debug
运行时,Boot甚至还不足以抛出autoconfig报告。它似乎是先解析XML文件,然后再做其他任何事情。您是否在thr类路径上有
spring boot starter数据jpa
?是的。你有一个简单的项目,在这个工作?我想看看。