Spring 引导 - 创建名称为 'dataSource' 的 bean 在 class 路径资源中定义时出错

Spring Boot - Error creating bean with name 'dataSource' defined in class path resource

我有 Spring 引导 Web 应用程序。它以 RESTful 方法为中心。所有配置似乎都已到位,但由于某种原因 MainController 无法处理请求。它会导致 404 错误。如何解决?

@Controller
public class MainController {

    @Autowired
    ParserService parserService;

    @RequestMapping(value="/", method= RequestMethod.GET)
    public @ResponseBody String displayStartPage(){
        return "{hello}";
    }
}

申请

@Configuration
@ComponentScan(basePackages = "")
@EnableAutoConfiguration
public class Application extends SpringBootServletInitializer{
        public static void main(final String[] args) {
            SpringApplication.run(Application.class, args);
        }

        @Override
        protected final SpringApplicationBuilder configure(final SpringApplicationBuilder application) {
            return application.sources(Application.class);
        }
}

解析器控制器

@RestController
public class ParserController {

    @Autowired
    private ParserService parserService;

    @Autowired
    private RecordDao recordDao;

 private static final Logger LOG = Logger.getLogger(ParserController.class);

    @RequestMapping(value="/upload", method= RequestMethod.POST)
    public @ResponseBody String fileUploadPage(
   }
}

更新

好像MySQL不能被Spring初始化....

    Caused by: org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'org.springframework.boot.autoconfigure.orm.jpa.HibernateJpaAutoConfiguration': Injection of autowired dependencies failed; 

nested exception is org.springframework.beans.factory.BeanCreationException: Could not autowire field: private javax.sql.DataSource org.springframework.boot.autoconfigure.orm.jpa.JpaBaseConfiguration.dataSource; 

nested exception is org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'dataSource' defined in class path resource [org/springframework/boot/autoconfigure/jdbc/DataSourceAutoConfiguration$NonEmbeddedConfiguration.class]: Instantiation of bean failed; 

nested exception is org.springframework.beans.factory.BeanDefinitionStoreException: Factory method [public javax.sql.DataSource org.springframework.boot.autoconfigure.jdbc.DataSourceAutoConfiguration$NonEmbeddedConfiguration.dataSource()] threw exception; 

nested exception is org.springframework.beans.factory.BeanCreationException: Cannot determine embedded database driver class for database type NONE. If you want an embedded database please put a supported one on the classpath.

更新2

application.properties

    # Database 
    spring.datasource.driverClassName = com.mysql.jdbc.Driver
    spring.datasource.url = jdbc:mysql://localhost:3306/logparser
    spring.datasource.username = root
    spring.datasource.password = root
    
    spring.jpa.database = MYSQL
    spring.jpa.show-sql = true
    
    # Hibernate
    hibernate.dialect: org.hibernate.dialect.MySQL5Dialect
    hibernate.show_sql: true
    hibernate.hbm2ddl.auto: update
    entitymanager.packagesToScan: /

更新4

尽管已设置 @RequestMapping,但精简版控制器似乎没有响应。为什么会这样?

PS. It occurs when I run Maven's lifecycle test. When running in degub mode in IntelliJ there is no error outputted.

更新5

我也按照教程中的说明使用这个 DAO....

public interface RecordDao extends CrudRepository<Record, Long> {
}

http://blog.netgloo.com/2014/10/27/using-mysql-in-spring-boot-via-spring-data-jpa-and-hibernate/

更新6

我确实更改了我的应用程序属性。并尝试了每一个组合,但它拒绝工作。 ;(

Maven 输出:

-------------------------------------------------------
 T E S T S
-------------------------------------------------------
Running IntegrationTest
Tests run: 1, Failures: 0, Errors: 1, Skipped: 0, Time elapsed: 2.365 sec <<< FAILURE! - in IntegrationTest
saveParsedRecordsToDatabase(IntegrationTest)  Time elapsed: 2.01 sec  <<< ERROR!
java.lang.IllegalStateException: Failed to load ApplicationContext
    at org.springframework.test.context.CacheAwareContextLoaderDelegate.loadContext(CacheAwareContextLoaderDelegate.java:99)
    at org.springframework.test.context.DefaultTestContext.getApplicationContext(DefaultTestContext.java:101)
    at org.springframework.test.context.support.DependencyInjectionTestExecutionListener.injectDependencies(DependencyInjectionTestExecutionListener.java:109)
    at org.springframework.test.context.support.DependencyInjectionTestExecutionListener.prepareTestInstance(DependencyInjectionTestExecutionListener.java:75)
    at org.springframework.test.context.TestContextManager.prepareTestInstance(TestContextManager.java:331)
    at org.springframework.test.context.junit4.SpringJUnit4ClassRunner.createTest(SpringJUnit4ClassRunner.java:213)
    at org.springframework.test.context.junit4.SpringJUnit4ClassRunner.runReflectiveCall(SpringJUnit4ClassRunner.java:290)
    at org.junit.internal.runners.model.ReflectiveCallable.run(ReflectiveCallable.java:12)
    at org.springframework.test.context.junit4.SpringJUnit4ClassRunner.methodBlock(SpringJUnit4ClassRunner.java:292)
    at org.springframework.test.context.junit4.SpringJUnit4ClassRunner.runChild(SpringJUnit4ClassRunner.java:233)
    at org.springframework.test.context.junit4.SpringJUnit4ClassRunner.runChild(SpringJUnit4ClassRunner.java:87)
    at org.junit.runners.ParentRunner.run(ParentRunner.java:238)
    at org.junit.runners.ParentRunner.schedule(ParentRunner.java:63)
    at org.junit.runners.ParentRunner.runChildren(ParentRunner.java:236)
    at org.junit.runners.ParentRunner.access[=19=]0(ParentRunner.java:53)
    at org.junit.runners.ParentRunner.evaluate(ParentRunner.java:229)
    at org.springframework.test.context.junit4.statements.RunBeforeTestClassCallbacks.evaluate(RunBeforeTestClassCallbacks.java:61)
    at org.springframework.test.context.junit4.statements.RunAfterTestClassCallbacks.evaluate(RunAfterTestClassCallbacks.java:71)
    at org.junit.runners.ParentRunner.run(ParentRunner.java:309)
    at org.springframework.test.context.junit4.SpringJUnit4ClassRunner.run(SpringJUnit4ClassRunner.java:176)
    at org.apache.maven.surefire.junit4.JUnit4Provider.execute(JUnit4Provider.java:264)
    at org.apache.maven.surefire.junit4.JUnit4Provider.executeTestSet(JUnit4Provider.java:153)
    at org.apache.maven.surefire.junit4.JUnit4Provider.invoke(JUnit4Provider.java:124)
    at org.apache.maven.surefire.booter.ForkedBooter.invokeProviderInSameClassLoader(ForkedBooter.java:200)
    at org.apache.maven.surefire.booter.ForkedBooter.runSuitesInProcess(ForkedBooter.java:153)
    at org.apache.maven.surefire.booter.ForkedBooter.main(ForkedBooter.java:103)
Caused by: org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'org.springframework.boot.autoconfigure.orm.jpa.HibernateJpaAutoConfiguration': Injection of autowired dependencies failed; nested exception is org.springframework.beans.factory.BeanCreationException: Could not autowire field: private javax.sql.DataSource org.springframework.boot.autoconfigure.orm.jpa.JpaBaseConfiguration.dataSource; nested exception is org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'dataSource' defined in class path resource [org/springframework/boot/autoconfigure/jdbc/DataSourceAutoConfiguration$NonEmbeddedConfiguration.class]: Instantiation of bean failed; nested exception is org.springframework.beans.factory.BeanDefinitionStoreException: Factory method [public javax.sql.DataSource org.springframework.boot.autoconfigure.jdbc.DataSourceAutoConfiguration$NonEmbeddedConfiguration.dataSource()] threw exception; nested exception is org.springframework.beans.factory.BeanCreationException: Cannot determine embedded database driver class for database type NONE. If you want an embedded database please put a supported one on the classpath.

看来您还没有向 Spring 传递足够的数据 Spring 引导配置数据源

Create/In 您现有的 application.properties 添加以下内容

spring.datasource.driverClassName=
spring.datasource.url=
spring.datasource.username=
spring.datasource.password=

确保为每个属性附加一个值。

hibernate.*属性没用,应该是spring.jpa.*属性。更不用说您正在尝试使用 spring.jpa.* 属性覆盖已经设置的那些。 (对于每个 属性 的解释,我强烈建议阅读 Spring 引导 reference guide

spring.jpa.database-platform = org.hibernate.dialect.MySQL5Dialect
spring.jpa.show-sql = true

# Hibernate
spring.jpa.hibernate.ddl-auto=update

还会根据您的 Application class 的基础包自动检测要扫描的包。如果您想指定其他内容,请使用 @EntityScan 注释。另外指定最顶层的包并不是真正明智的,因为它会扫描整个 class 路径,这将严重影响性能。

也许您忘记了 MySQL JDBC 驱动程序。

<dependency>
    <groupId>mysql</groupId>
    <artifactId>mysql-connector-java</artifactId>
    <version>5.1.34</version>
</dependency>

看起来最初的问题是自动配置。

如果您不需要数据源,只需将其从自动配置过程中删除即可:

@EnableAutoConfiguration(exclude={DataSourceAutoConfiguration.class})

编辑: 如果在您的主要 class:

中使用 @SpringBootApplication
@SpringBootApplication(exclude={DataSourceAutoConfiguration.class})

您是否运行 将应用程序作为 jar? ( java -jar xxxx.jar)

如果是这样,你有 application.properties 存储在那个罐子里吗?

如果不是,请找出原因:

  • 要自动打包到jar中,文件可以在:src/main/resources/application.properties
  • pom.xml中的maven插件也可以配置

在我的例子中,发生这种情况是因为 org.springframework.boot.autoconfigure.orm.jpa.JpaBaseConfiguration.dataSource 是一个没有限定符的自动装配字段,并且我正在使用具有限定名称的多个数据源。我通过在我的一个数据源 bean 配置上任意使用 @Primary 解决了这个问题

@Primary
@Bean(name="oneOfManyDataSources")
public DataSource dataSource() { ... }

我想他们希望您实现 AbstractRoutingDataSource,然后自动配置将正常工作,因为不需要限定符,您只有一个数据源,允许您的 bean 根据需要解析为适当的 DataSource。然后你根本不需要@Primary 或@Qualifier 注释,因为你只有一个数据源。

在任何情况下,我的解决方案都有效,因为我的 bean 通过限定符指定数据源,并且 JPA 自动配置的东西很高兴,因为它有一个主数据源。我绝不推荐将此作为 "right" 做事的方式,但就我而言,它可以快速解决问题并且不会以任何明显的方式阻止我的应用程序的行为。希望有一天能够实现 AbstractRoutingDataSource 并重构所有需要特定数据源的 bean,然后也许这将是一个更简洁的解决方案。

我遇到了同样的错误,发现这是由于我的 pom.xml 中缺少某些依赖项,例如 Spring JPA、Hibernate、Mysql 或者 Jackson . 因此,请确保您的 pom.xml 中没有缺少依赖项并检查它们的版本兼容性。

<!-- Jpa and hibernate -->
<dependency>
    <groupId>org.springframework</groupId>
    <artifactId>spring-orm</artifactId>
    <version>4.2.2.RELEASE</version>
</dependency>
<dependency>
    <groupId>org.hibernate</groupId>
    <artifactId>hibernate-entitymanager</artifactId>
    <version>5.0.3.Final</version>
</dependency>
<dependency>
    <groupId>mysql</groupId>
    <artifactId>mysql-connector-java</artifactId>
    <version>5.1.6</version>
</dependency>

它对我有用你可以试试你的: 将此添加到 Tomcat

中的 VM 选项
-DdevBaseDir="C:\Your_Project_Dir_Path"

更改以下代码行

spring.datasource.driverClassName

spring.datasource.driver-class-name

即使在 application.properties 中提供了所有必需的数据源属性后,我仍然面临这个问题。然后我意识到属性配置 class 没有被 Spring 引导扫描,因为它与我的 Spring 引导 Application.java 相比处于不同的包层次结构中,因此没有属性被应用于数据源对象。 我更改了属性配置的包名称 class,它开始工作了。

如果您在 spring 启动应用程序中使用 application.properties,那么只需将下面这行代码放入 application.properties 中,它应该可以工作:
spring.datasource.url: jdbc:mysql://google/?cloudSqlInstance=&socketFactory=com.google.cloud.sql.mysql.SocketFactory&user=****&password=****

在我的例子中,我只是忽略了 application.properties 文件中的以下内容:

# 休眠

#spring.jpa.hibernate.ddl-自动=更新

对我有用....

检查您在 runtime 组在 build.gradle

是否有数据库依赖
runtime group: 'com.h2database', name: 'h2', version: '1.4.194'

或者如果您使用 Maven

,则将范围从测试更改为 运行时
<dependency>
    <groupId>com.h2database</groupId>
    <artifactId>h2</artifactId>
    <version>1.4.194</version>
    <scope>runtime</scope>
</dependency>

给你点不一样的,当你遇到这种错误时,无法创建 测试用例中的 bean 数据源。

可能是以下原因造成的:

  1. 没有数据源,您需要创建数据源,h2 内存数据源或其他,或者您可以选择 exclude={datasource··}.
  2. 这样的方式
  3. 您有自己的数据源,例如 MySQL,但它仍然无法正常工作。这是由class AutoConfigureTestDatabase引起的,它会为您选择一个数据源,这可能会导致歧义。

解决方案:添加@AutoConfigureTestDatabase(replace = AutoConfigureTestDatabase.Replace.NONE)以避免替换默认数据源。

与原始问题没有直接关系,但这对某些人有用。这个错误发生在我身上,有一个简单的两个项目结构。一个项目使用 spring JDBC(假设 A)处理一些数据库操作,而另一个项目根本没有任何 JDBC 操作(假设 B)。但是,在我启动服务B时仍然出现了这个错误。说数据源应该正确初始化。

据我所知,我已将此依赖项添加到两个模块的父 pom

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-jdbc</artifactId>
</dependency>

这导致 spring 也为项目 B 初始化 JDBC 依赖项。所以,我把它移到项目A的pom中,一切都很好。

希望这对某人有所帮助

这个问题是在您 运行 测试时出现的。 添加依赖项

testCompile group: 'com.h2database', name: 'h2', version: '1.4.197' 

在测试源添加文件下添加文件夹资源bootstrap.yml 并提供内容。

spring:
  datasource:
    type: com.zaxxer.hikari.HikariDataSource
    url: jdbc:h2:mem:TEST
    driver-class-name: org.h2.Driver
    username: username
    password: password
    hikari:
      idle-timeout: 10000

这将设置您的数据源。

几天都遇到同样的问题,最后不是代码的问题,问题出在maven上,你必须删除他从你的硬盘下载的所有文件"C:\Users\username.m2\repository" ,并为您的项目执行另一个更新 maven,这将解决您的问题。

我通过更改父 Spring 引导依赖关系解决了我的问题。

<parent>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-parent</artifactId>
    <version>2.1.0.RELEASE</version>
</parent>

<parent>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-parent</artifactId>
    <version>2.0.6.RELEASE</version>
</parent>

有关更多信息,请查看发行说明:Spring Boot 2.1.0 Release Notes

在 MySQL

中创建了数据库
create database springboot2;

application.properties

spring.datasource.driver-class-name=com.mysql.cj.jdbc.Driver
spring.datasource.url = jdbc:mysql://localhost:3306/springboot2
spring.datasource.username = root
spring.datasource.password = root
spring.jpa.show-sql = true
spring.jpa.hibernate.ddl-auto = update
spring.jpa.properties.hibernate.dialect = org.hibernate.dialect.MySQL5Dialect
server.port=9192

pom.xml

<dependencies>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-data-jpa</artifactId>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
        </dependency>

        <dependency>
            <groupId>mysql</groupId>
            <artifactId>mysql-connector-java</artifactId>
            <scope>runtime</scope>
        </dependency>
        <dependency>
            <groupId>org.projectlombok</groupId>
            <artifactId>lombok</artifactId>
            <optional>true</optional>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-test</artifactId>
            <scope>test</scope>
            <exclusions>
                <exclusion>
                    <groupId>org.junit.vintage</groupId>
                    <artifactId>junit-vintage-engine</artifactId>
                </exclusion>
            </exclusions>
        </dependency>
    </dependencies>

主要class

import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;

@SpringBootApplication
public class Application {

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

}

型号class

package com.First.Try.springboot.entity;
    
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.Id;
import javax.persistence.Table;

import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
@Data
@AllArgsConstructor 
@NoArgsConstructor
@Entity
@Table(name="PRODUCT_TBL1")
public class Product {
    @Id
    @GeneratedValue
    private int id;
    private String name;
    private int quantity;
    private double price;
    ....
    ....
    ....
 }

默认情况下,使用最新版本的 Spring Boot,data.sql 的加载是在创建表之前完成的。所以使用 - spring.jpa.defer-datasource-initialization=true

例子-

**In application.properties :- **
spring.jpa.show-sql=true
spring.datasource.url=jdbc:h2:mem:testdb
spring.h2.console.enabled=true
spring.jpa.defer-datasource-initialization=true

谢谢 阿塔尔·卡里姆

我正在使用 spring boot 2.6.0 我尝试了几个答案,但还不够。 我找到的一个临时解决方案是这个

@SpringBootApplication(exclude = SqlInitializationAutoConfiguration.class)

虽然它让服务器 运行 和 h2 控制台出现,但我无法连接到我的 data.sql 文件。这是我得到的错误

Database "mem:testdb" not found, either pre-create it or allow remote database creation (not recommended in secure environments) [90149-200] 90149/90149

这是我找到的解决方案 (有些已经)将这些行添加到 application.properties 文件

spring.jpa.show-sql=true
spring.h2.console.enabled=true
spring.datasource.url=jdbc:h2:mem:testdb
spring.jpa.defer-datasource-initialization=true

保存一个重新运行 服务器然后尝试从 h2-console

再次访问浏览器上的数据库

默认情况下,data.sql 个脚本现在 运行 在 Hibernate 初始化之前。这使基于脚本的基本初始化行为与 Flyway 和 Liquibase 的行为保持一致。如果要使用 data.sql 填充 Hibernate 创建的模式,请将 spring.jpa.defer-datasource-initialization 设置为 true。

spring.jpa.defer-datasource-initialization=true 解决问题

我没有在 pom 中使用 h2 配置 file.I 添加了它,这个问题就解决了。

<dependency>
        <groupId>com.h2database</groupId>
        <artifactId>h2</artifactId>
        <scope>runtime</scope>
    </dependency>

您的数据源似乎有问题。 如果您不需要数据源,只需使用

禁用它
spring.autoconfigure.exclude=org.springframework.boot.autoconfigure.jdbc.DataSourceAutoConfiguration
 

只需将此放入您的 application.properties

如果您正在使用 mysql,则需要 2 个依赖项

1

. <dependency>          
<groupId>mysql</groupId>
   <artifactId>mysql-connector-java</artifactId>        </dependency>

    
 <dependency> 
        <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-jdbc</artifactId>   </dependency>

如果您正在使用 potgress,您只需要:

1.

<dependency>        
    <groupId>org.postgresql</groupId>
    <artifactId>postgresql</artifactId>              
      <scope>runtime</scope>
            </dependency>