【问题标题】:Spring Boot application runs fine via Maven but not via IDE Intellij IDEASpring Boot 应用程序通过 Maven 运行良好,但不能通过 IDE Intellij IDEA
【发布时间】:2018-01-25 23:45:44
【问题描述】:

我有一个 Spring Boot 应用程序,它通过 Maven 的 mvn spring-boot:run 命令运行良好。但是,当我尝试通过 IDE(在我的情况下为 Intellij IDEA 2017.2.1)运行它时,它会失败,因为它无法 @Autowire 数据源。

***************************
APPLICATION FAILED TO START
***************************

Description:

Parameter 0 of constructor in com.myApp.Application required a bean of type 'javax.sql.DataSource' that could not be found.


Action:

Consider defining a bean of type 'javax.sql.DataSource' in your configuration.

这个代码库的原始作者有一个主类,它启动应用程序,接受数据源的构造函数参数,这是我不熟悉的一种方法,因为我习惯于通过application.properties 文件来完成它并让Spring Boot 连接它自己的 DataSource。

@EnableTransactionManagement
@SpringBootApplication
@EnableCaching
public class Application extends JpaBaseConfiguration {


    protected Application(DataSource dataSource, JpaProperties properties,
            ObjectProvider<JtaTransactionManager> jtaTransactionManagerProvider,
            ObjectProvider<TransactionManagerCustomizers> transactionManagerCustomizers) {
        super(dataSource, properties, jtaTransactionManagerProvider, transactionManagerCustomizers);
    }

在 IDEA 中,我注意到此构造函数的 datasourceproperties 参数带有红色下划线。对于datasource,IDE 抱怨存在两个bean,它不知道在XADataSourceAutoConfiguration.classDataSourceConfiguration.class 之间自动装配哪个。至于用红色下划线的构造的另一个参数properties,它找不到任何bean,IDE 抱怨没有找到JpaProperties 类型的bean。以下是在主应用程序启动类中覆盖的其他一些方法,

        @Override
        protected AbstractJpaVendorAdapter createJpaVendorAdapter() {
            return new HibernateJpaVendorAdapter();
        }


        @Override
        protected Map<String, Object> getVendorProperties() {
            Map<String, Object> vendorProperties = new LinkedHashMap<>();
            vendorProperties.putAll(getProperties().getHibernateProperties(getDataSource()));
            return vendorProperties;
        }


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


}

不幸的是,因为我不熟悉这种在 Spring Boot 中使用构造函数来配置/自动配置应用程序的方法,所以我不确定一些事情,但我的确切问题是为什么应用程序在 Maven 中运行良好但不在 Intellij IDEA 中?此外,由于我无法访问该专有代码库的原始作者,我很想知道为什么,如果有人甚至可以给我提示,他们已经配置了构造函数,而不是默认的自动配置。我也有一个集成测试,我写了我正在尝试运行,但是这个测试,无论是通过 IDE 还是通过 Maven 的故障安全插件运行,也会导致同样的错误,DataSource 不是@Autowired。所以这是另一个问题,为什么这个测试不会在主应用程序运行时通过 Maven 运行。这是我的集成测试,

@RunWith(SpringJUnit4ClassRunner.class)
@WebMvcTest(value = TransactionController.class, secure = false)
public class TransactionControllerIT {

    @Autowired
    MockMvc mockMvc;

    @Test
    public void shouldInitiateTransfer() {

        String transferTransaction =
              "some json string I can't show here on stack overflow";

        RequestBuilder requestBuilder = MockMvcRequestBuilders
                .post("/begin-transfer")
                .accept(MediaType.APPLICATION_JSON).content(transferTransaction)
                .contentType(MediaType.APPLICATION_JSON);

        MvcResult result = null;

        try {
            result = mockMvc.perform(requestBuilder).andReturn();
        } catch (Exception e) {
            fail("Exception in integration test!");
        }

        MockHttpServletResponse response = result.getResponse();

        assertEquals(HttpStatus.CREATED.value(), response.getStatus());

    }
}

感谢您阅读我的问题。

【问题讨论】:

    标签: spring maven spring-boot intellij-idea


    【解决方案1】:

    您可以通过以下操作轻松运行 IDEA 中的任何 Spring Boot 应用程序:

    在 Maven 面板中,转到插件,展开 spring-boot 并右键单击“spring-boot:run”。然后点击“创建您的项目...”,如图所示。

    这样您就可以从主工具栏中的 IDEA 以舒适的方式启动应用程序:

    这种方式你仍然使用maven方式,但集成在IDEA中。我真的不知道你为什么会遇到这些问题。我在尝试直接执行 spring boot 应用程序时也遇到了一些问题。

    【讨论】:

    • 我实际上已经这样做了,我在 IDEA 中创建了一个 Maven 运行配置,因为 IDEA 不会原生运行应用程序。我仍然很想知道为什么它不能在 IDEA 中运行。
    【解决方案2】:

    您的测试失败是因为它使用了切片测试,@WebMvcTest 这些测试(@DataJpaTestJsonTest)仅加载整个应用程序上下文的一小部分,而不是应用程序在启动时执行的所有操作或 ( @SpringBootTest) 会。

    当使用切片测试时,它将使用任何注释,并且需要在 @SpringBootApplication 类中定义的任何 bean。

    例如因为您已经定义了自动装配的 bean,并且将启用任何切片测试缓存和事务管理的两个附加注释,并且它始终需要传递这些依赖项。

    我不会让您的主应用程序类以这种方式扩展配置类,它过于复杂并且闻起来像 XY 问题。您应该将配置(和启用注释)外部化到它们自己的 @Configuration 类,并将 @SpringBootApplication 保留为 vanilla 可能避免此类错误。

    【讨论】:

    • 感谢您提供信息丰富的回复。你能告诉我哪些注释可以使我的集成​​测试工作吗?我试过 SpringBootTest 但现在自动装配的 MockMvc 为空。另外,鉴于当前的配置,您能否建议我可以做些什么来让项目在 IDE 中运行?
    • 不确定 IDE 问题。您应该能够使用@SpringBootTest(webEnvironment=MOCK)@AutoConfigureMockMvc 的组合。还有一个备用方案,您可以使用MockMvcBuilder 并通过传递控制器或 Web 应用程序上下文自己创建它。 docs.spring.io/spring/docs/current/javadoc-api/org/…
    猜你喜欢
    • 2021-12-11
    • 1970-01-01
    • 1970-01-01
    • 2017-01-18
    • 2016-03-15
    • 1970-01-01
    • 1970-01-01
    • 2017-02-26
    • 1970-01-01
    相关资源
    最近更新 更多