【问题标题】:Unable to get spring boot to automatically create database schema无法让spring boot自动创建数据库模式
【发布时间】:2015-01-08 23:54:37
【问题描述】:

当我启动它时,我无法让 spring boot 自动加载我的数据库架构。

这是我的 application.properties:

spring.datasource.url=jdbc:mysql://localhost:3306/test
spring.datasource.username=test
spring.datasource.password=
spring.datasource.driverClassName = com.mysql.jdbc.Driver

spring.jpa.database = MYSQL

spring.jpa.show-sql = true

spring.jpa.hibernate.ddl-auto = create
spring.jpa.hibernate.dialect = org.hibernate.dialect.MySQL5Dialect
spring.jpa.hibernate.naming_strategy = org.hibernate.cfg.ImprovedNamingStrategy

这是我的 Application.java:

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

这是一个示例实体:

@Entity
@Table(name = "survey")
public class Survey implements Serializable {

    private Long _id;

    private String _name;

    private List<Question> _questions;

    /**
     * @return survey's id.
     */
    @Id
    @GeneratedValue(strategy = IDENTITY)
    @Column(name = "survey_id", unique = true, nullable = false)
    public Long getId() {
        return _id;
    }

    /**
     * @return the survey name.
     */
    @Column(name = "name")
    public String getName() {
        return _name;
    }


    /**
     * @return a list of survey questions.
     */
    @OneToMany(mappedBy = "survey")
    @OrderBy("id")
    public List<Question> getQuestions() {
        return _questions;
    }

    /**
     * @param id the id to set to.
     */
    public void setId(Long id) {
        _id = id;
    }

    /**
     * @param name the name for the question.
     */
    public void setName(final String name) {
        _name = name;
    }

    /**
     * @param questions list of questions to set.
     */
    public void setQuestions(List<Question> questions) {
        _questions = questions;
    }
}

任何想法我做错了什么?

【问题讨论】:

  • 它会抛出什么异常/错误?
  • 没有异常,它启动然后运行完美,直到它尝试与数据库交互,然后它抛出一个关于没有表的异常。日志中也没有相关警告。

标签: java mysql spring hibernate spring-boot


【解决方案1】:

有几种可能的原因:

  1. 您的实体类在相同或相对于子包中,您使用@EnableAutoConfiguration. 进行类如果没有,那么您的 spring 应用程序看不到它们,因此不会在 db 中创建任何东西

  2. 检查您的配置,您似乎正在使用一些特定于休眠的选项,请尝试将它们替换为:

    spring.jpa.database-platform=org.hibernate.dialect.MySQL5InnoDBDialect
    spring.jpa.hibernate.ddl-auto=update
    spring.datasource.driverClassName=com.mysql.cj.jdbc.Driver
    spring.datasource.url=jdbc:mysql://localhost:3306/test
    spring.datasource.username=test
    spring.datasource.password=
    

**请注意,驱动类的手动加载是不必要的,因为它是自动注册的,所以不要打扰它

  1. 您的application.properties 必须在src/main/resources 文件夹中。

如果您没有正确指定方言,它可能会尝试默认与启动内存数据库捆绑在一起,并且(就像我一样)我可以看到它尝试连接到本地 HSQL(请参阅控制台输出)实例并在更新架构时失败。

【讨论】:

  • 将方言更改为org.hibernate.dialect.MySQL5InnoDBDialect 成功了。感谢您的帮助!
  • 数字 1 对我有用。如果我不想让我的模型与我的主类在同一个项目中,我该怎么办。我在模型包中添加了componentscan,但我没有帮助我。
  • @O.Badr,有效的评论。我很可能一次粘贴了许多配置文件中的行。方言和驱动程序应与目标数据库匹配。
  • @borys86,所以在你的解决方案中我们应该使用org.hibernate.dialect.MySQL5InnoDBDialect,因为问题是关于 MySQL 的!
  • #2 为我工作,但 spring.datasource.driverClassName=com.mysql.jdbc.Driver 不需要并给出警告:Loading class com.mysql.jdbc.Driver'. This is deprecated. The new driver class is com.mysql.cj.jdbc.Driver '。驱动通过SPI自动注册,一般不需要手动加载驱动类。
【解决方案2】:

您是否尝试过运行它:

spring.jpa.generate-ddl=true

然后

spring.jpa.hibernate.ddl-auto = create

默认情况下,DDL 执行(或验证)会延迟到 ApplicationContext 启动。还有一个 spring.jpa.generate-ddl 标志,但如果 Hibernate autoconfig 处于活动状态,则不会使用它,因为 ddl-auto 设置更细粒度。

spring-boot-features

【讨论】:

  • 是的,使用这些属性运行它也不起作用。奇怪的是它甚至没有在 jconsole 中显示属性值:spring.jpa.CONFIGURATION_PROPERTIES={prefix=spring.jpa, properties={databasePlatform=null, database=MYSQL, generateDdl=false, showSql=false}}
  • 很可能是运行查询的用户没有创建表的权限?你有什么错误吗?
  • 用户与创建架构的用户相同:/。在我点击访问数据库的 Rest Controller 之前没有错误。
  • 这个对我有用 创建
【解决方案3】:
@SpringBootApplication
@EnableConfigurationProperties
@EntityScan(basePackages = {"com.project.ppaa.model"})  // scan JPA entities
public class Application {

  private static ConfigurableApplicationContext applicationContext;

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

它应该会自动工作,如果没有,你可以进入基础包

@EntityScan(basePackages = {"com.project.ppaa.model"})  // scan JPA entities manually

【讨论】:

  • 它适用于我,spring boot 版本:1.5.9.RELEASE。但是,我发现根本原因是我应该将 ApplicationConfig 放在我的实体包的父包中。因此,它可以自动扫描层次结构中的实体。
  • 这对我有用。非常感谢。我花了几个小时来解决这个问题。问题是,没有抛出任何错误,甚至只是一个信息。什么都没有,我一直在盲目地尝试搜索这个问题的每个关键字。但是我仍然不知道为什么它不会自动扫描我的实体。 ://
  • 当我的 dao 和存储库、实体类位于不同的 maven 模块中时,这对我有帮助
【解决方案4】:

使用以下两个设置确实有效。

spring.jpa.generate-ddl=true
spring.jpa.hibernate.ddl-auto=create

【讨论】:

  • 这属于application.properties文件吗?
  • 是的,您将这些添加到 applications.properties。或者,您可以在主 SpringBootApplication 类中配置属性。
【解决方案5】:

你只需像这样添加createDatabaseIfNotExist=true

spring.datasource.url=jdbc:mysql://localhost:3306/test?createDatabaseIfNotExist=true&amp;amp;useUnicode=true&amp;amp;characterEncoding=utf-8&amp;amp;autoReconnect=true

到您的 application.properties 文件

【讨论】:

  • 这是我找了很久的东西。谢谢,它有效
【解决方案6】:

如果你的实体类和你的主类不在同一个包中,你可以在主类中使用@EntityScan注解,指定你想要保存或打包的实体。喜欢你的模型包。

关于:

spring.jpa.hibernate.ddl-auto = create

您可以使用选项update。它不会删除任何数据,并且会以相同的方式创建表。

【讨论】:

    【解决方案7】:

    我用这个解决方案解决了我的问题。 只是在 application.properties 文件的 spring.datasource.url 属性上插入了一个新参数 createDatabaseIfNotExist=true,如下所示: p>

    spring.datasource.url=jdbc:mysql://localhost:3306/minhasenha?autoReconnect=true&useSSL=false&createDatabaseIfNotExist=true
    

    我有带有 DDL 的 src/main/resources/Schema.sql 来创建数据库架构。我确实使用 flyaway 来创建和维护表格。

    我在这里创建了这个解决方案: original answer

    【讨论】:

      【解决方案8】:
      spring.jpa.properties.hibernate.dialect = org.hibernate.dialect.MySQL5Dialect
      spring.jpa.generate-ddl=true
      spring.jpa.hibernate.ddl-auto=update
      

      MySQL5Dialect 成功了,之前我使用的是 'MySQLDialect'

      【讨论】:

      • 添加 ``` spring.jpa.generate-ddl=true ``` 就成功了。仅使用 ``` spring.jpa.hibernate.ddl-auto=update ```。默认接缝为假。
      【解决方案9】:

      您需要根据您的 Spring Boot 版本和它下载的库版本来提供配置。

      我的设置:Spring Boot 1.5.x(在我的例子中是 1.5.10)下载 Hibernate v5.x

      仅当您的 Spring Boot 设置已下载 Hibernate v4 时才使用下面的内容。

      spring.jpa.hibernate.naming_strategy=org.hibernate.cfg.ImprovedNamingStrategy

      Hibernate 5 不支持上述。

      如果你的 Spring Boot Setup 已经下载了 Hibernate v5.x,那么更喜欢下面的定义:

      spring.jpa.hibernate.naming.physical-strategy=org.hibernate.boot.model.naming.PhysicalNamingStrategyStandardImpl

      重要提示: 在您的 Spring Boot 应用程序开发中,您应该更喜欢使用注解:@SpringBootApplication,它已被超级注解为:@SpringBootConfiguration and @EnableAutoConfiguration

      现在 如果您的实体类与主类所在的包位于不同的包中,则 Spring Boot 不会扫描这些包。

      因此您需要显式定义 Annotation:@EntityScan(basePackages = { "com.springboot.entities" })
      此注释扫描基于 JPA 的注释实体类(以及其他,如 MongoDB、Cassandra 等)

      注意: “com.springboot.entities”是自定义包名。

      以下是我在 application.properties 中定义基于 Hibernate 和 JPA 的属性以创建表的方式:-

      spring.datasource.driver-class-name=com.mysql.jdbc.Driver
      spring.datasource.url=jdbc:mysql://localhost:3333/development?useSSL=true spring.datasource.username=admin
      spring.datasource.password=

      spring.jpa.open-in-view=false
      spring.jpa.hibernate.ddl-auto=创建
      spring.jpa.generate-ddl=true
      spring.jpa.hibernate.use-new-id-generator-mappings=true
      spring.jpa.hibernate.naming.physical-strategy=org.hibernate.boot.model.naming.PhysicalNamingStrategyStandardImpl
      spring.jpa.hibernate.naming.strategy=org.hibernate.cfg.ImprovedNamingStrategy
      spring.jpa.show-sql=true
      spring.jpa.properties.hibernate.dialect=org.hibernate.dialect.MySQL5Dialect
      spring.jpa.properties.hibernate.format_sql=true

      我可以使用上述配置创建表。

      参考它并在适用的地方更改您的代码。

      【讨论】:

        【解决方案10】:

        这是我在阅读了上述所有答案后所做的。

        1. 将带有其他简单属性的spring.jpa.hibernate.ddl-auto=update 添加到application.properties
        2. 运行
        3. 在控制台中,您可以看到错误。在错误中的一处,您可以找到该软件生成的用于创建实体表的 SQL 代码。
        4. 复制该 SQL 代码并将其单独粘贴到您的 DBMS 以创建表。
        5. 之后,再次运行应用程序。

        【讨论】:

          【解决方案11】:

          遗憾的是,上面给出的答案都不起作用,因为我后来发现问题来自我的 pom 文件。我使用了 spring boot 启动项目,并添加了另一种不起作用的 spring jpa。 最初我有这个,

              <dependency>
                  <groupId>org.springframework.data</groupId>
                  <artifactId>spring-data-jpa</artifactId>
              </dependency> 
          

          我用这个替换它:

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

          注意 spring-boot-starter-data-jpa。希望这可以帮助某人。检查您的 pom 文件并确保您的依赖项匹配。

          【讨论】:

            【解决方案12】:

            Abderrahmane 响应正确:在 url 属性中添加 ?createDatabaseIfNotExist=true。 看来ddl-auto 什么都不会做。

            【讨论】:

            • 问题不在于创建数据库,而在于 Spring JPA 没有在数据库中创建表。数据库可能已创建但未播种表
            【解决方案13】:

            在我的情况下,即使我使用的是 JPArepository,表也不会自动创建。 在我的 springboot 应用程序 application.properties 文件中添加以下属性后,现在将自动创建表。 spring.jpa.hibernate.ddl-auto=update

            【讨论】:

              【解决方案14】:

              我也有同样的问题。结果我在主应用程序类上设置了@PropertySource 注释来读取不同的基本属性文件,因此不再使用普通的“application.properties”。

              【讨论】:

                【解决方案15】:

                只需在spring数据源url中添加createDatabaseIfNotExist=true参数

                示例: spring.datasource.url= jdbc:mysql://localhost:3306/test?createDatabaseIfNotExist=true

                【讨论】:

                  【解决方案16】:
                  Use this Sample code
                  
                  application.properties
                  # DataSource settings: set here your own configurations for the database 
                  # connection. In this example we have "dojsb" as database name and 
                  # "root" as username and password.
                  spring.datasource.url =jdbc:postgresql://localhost:5432/usman
                  spring.datasource.username = postgres
                  spring.datasource.password = 12345
                  
                  # Keep the connection alive if idle for a long time (needed in production)
                  spring.datasource.testWhileIdle = true
                  spring.datasource.validationQuery = SELECT 1
                  
                  # Show or not log for each sql query
                  spring.jpa.show-sql = true
                  
                  # Hibernate ddl auto (create, create-drop, update)
                  spring.jpa.hibernate.ddl-auto = create
                  
                  # Naming strategy
                  spring.jpa.hibernate.naming-strategy = org.hibernate.cfg.ImprovedNamingStrategy
                  
                  # Use spring.jpa.properties.* for Hibernate native properties (the prefix is
                  # stripped before adding them to the entity manager)
                  
                  # The SQL dialect makes Hibernate generate better SQL for the chosen database
                  spring.jpa.properties.hibernate.dialect = org.hibernate.dialect.PostgreSQLDialect
                  
                  server.port = 8963
                  
                  
                  
                  Entity Class:
                  
                  
                  
                  import java.sql.Timestamp;
                  import java.util.UUID;
                  
                  import javax.persistence.Column;
                  import javax.persistence.Entity;
                  import javax.persistence.Id;
                  import javax.persistence.Table;
                  
                  import org.hibernate.annotations.Type;
                  
                  
                  @Entity
                  @Table(name = "QUEUERECORDS")
                  public class QueuesRecords {
                      @Id
                      private UUID id;
                  
                      @Column(name="payload", nullable = true)
                      @Type(type="text")
                      private String payload;
                  
                  
                      @Column(name="status", nullable = true)
                      @Type(type="text")
                      private String status;
                  
                      private Timestamp starttime;
                  
                      private Timestamp endtime;
                  
                      @Column(name="queueid",nullable= true)
                      @Type(type="text")
                      private String queueid;
                  
                      public UUID getId() {
                          return id;
                      }
                  
                      public void setId(UUID id) {
                          this.id = id;
                      }
                  
                      public String getPayload() {
                          return payload;
                      }
                  
                      public void setPayload(String payload) {
                          this.payload = payload;
                      }
                  
                      public String getStatus() {
                          return status;
                      }
                  
                      public void setStatus(String status) {
                          this.status = status;
                      }
                  
                      public Timestamp getStarttime() {
                          return starttime;
                      }
                  
                      public void setStarttime(Timestamp starttime) {
                          this.starttime = starttime;
                      }
                  
                      public Timestamp getEndtime() {
                          return endtime;
                      }
                  
                      public void setEndtime(Timestamp endtime) {
                          this.endtime = endtime;
                      }
                  
                      public String getQueueid() {
                          return queueid;
                      }
                  
                      public void setQueueid(String queueid) {
                          this.queueid = queueid;
                      }
                  
                  
                  
                  }
                  
                  
                  
                  Main class
                  
                  
                  
                  import org.springframework.beans.factory.annotation.Autowired;
                  import org.springframework.boot.SpringApplication;
                  import org.springframework.boot.autoconfigure.SpringBootApplication;
                  
                  
                  @SpringBootApplication
                  public class Test{
                  
                      public static void main(String[] args) {
                  
                          SpringApplication.run(Test.class, args);
                  
                  
                      }
                  }
                  

                  【讨论】:

                    【解决方案17】:

                    我之前也遇到过同样的问题。我的问题是我试图通过使用“列表”建立实体关系。我知道这是原因,因为程序在没有 list 变量的情况下运行良好。在你的情况下,我认为问题是:

                    private List<Question> _questions;
                    

                    我假设您已经有一个名为 Question 的类。所以,尝试拥有:

                    @OneToMany
                    private Question _questions;
                    

                    但问题是,在您的方法中,您将处理它,以便它返回一个列表。我将 Spring Data JPA 与 CrudRepository 一起使用。所以,如果你决定使用它,你的可能看起来像这样:

                    public List<Question> findById( Long _id );
                    

                    您需要进行更多更改,但这些更改非常简单明了。参考this Java Brains video更好地掌握,看看还有什么需要修改的。

                    【讨论】:

                      【解决方案18】:

                      我遇到了类似的问题。我正在使用 spring boot 2.x,但我错过了在 spring 初始化程序中添加 Postgres 依赖项。 我手动添加了依赖

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

                      这就是我得到的- INFO org.hibernate.dialect.Dialect - HHH000400:使用方言: org.hibernate.dialect.PostgreSQL方言 而不是

                      **INFO  org.hibernate.dialect.Dialect - HHH000400: Using 
                      dialect:org.hibernate.dialect.PostgreSQL10Dialect**
                      

                      这将我连接到数据库

                      这并不奇怪,因为Springboot自己做了版本依赖,减少了开发工作。另一方面,如果 Springboot 选择了错误的依赖,会浪费很多时间。

                      【讨论】:

                        【解决方案19】:

                        很简单,我们在
                        spring.jpa.hibernate.ddl-auto = create;
                        之后添加分号 这是错误的
                        spring.jpa.hibernate.ddl-auto = create
                        够了

                        【讨论】:

                          【解决方案20】:

                          如果您的数据库是 MySQL:

                          spring.jpa.hibernate.ddl-auto=update
                          spring.datasource.driverClassName=com.mysql.jdbc.Driver
                          spring.datasource.url=jdbc:mysql://localhost:3306/your_database
                          spring.datasource.username=root
                          spring.datasource.password=root
                          

                          如果您的数据库是 PostgreSQL:

                          spring.jpa.properties.hibernate.jdbc.lob.non_contextual_creation=true
                          spring.jpa.hibernate.ddl-auto=update
                          spring.datasource.url=jdbc:postgresql://localhost:3306/your_database
                          spring.datasource.username=root
                          spring.datasource.password=root
                          

                          【讨论】:

                            【解决方案21】:

                            以下配置对我有用:

                            spring.jpa.properties.javax.persistence.schema-generation.database.action=create
                            spring.jpa.properties.javax.persistence.schema-generation.create-database-schemas=true
                            spring.jpa.properties.javax.persistence.schema-generation.create-source=metadata
                            spring.jpa.properties.javax.persistence.schema-generation.drop-source=metadata
                            spring.jpa.properties.javax.persistence.schema-generation.connection=jdbc:mysql://localhost:3306/your_database
                            

                            【讨论】:

                              【解决方案22】:

                              如果您在 Spring Boot 上遇到此问题,请仔细检查您的包名称,该名称应与以下内容完全相同:

                              com.example.YOURPROJECTNAME - consists main application class
                              com.example.YOURPROJECTNAME.entity - consists entities
                              

                              【讨论】:

                              • 您能否提供一些说明这是一项要求的参考资料?这将为您的答案增加更多价值。
                              【解决方案23】:

                              使用 springboot 连接 mysql 以及自动创建表到数据库: spring.datasource.url=jdbc:mysql://localhost:3306/solace spring.datasource.username=root spring.datasource.password=root spring.jpa.generate-ddl=true spring.jpa.hibernate.ddl-auto=update

                              【讨论】:

                              • 请更详细地描述您为获得此结果所做的工作以及您如何知道它是正确的:)
                              【解决方案24】:

                              在我的情况下,我不得不用名称 user 重命名表。例如,我将其重命名为 users 并且它起作用了。

                              【讨论】:

                                【解决方案25】:

                                我有同样的问题,但我补充说

                                spring.jpa.hibernate.ddl-auto = create
                                

                                现在一切正常

                                【讨论】:

                                  【解决方案26】:

                                  这个帮了我

                                  我假设你有 INNODB 引擎:

                                  spring.jpa.properties.hibernate.dialect = org.hibernate.dialect.MySQL8Dialect
                                  
                                  spring.jpa.properties.hibernate.dialect.storage_engine=innodb
                                  

                                  【讨论】:

                                    【解决方案27】:

                                    我遇到了同样的问题,只用这个添加解决了它:

                                    spring.jpa.database-platform=org.hibernate.dialect.PostgreSQLDialect
                                    

                                    【讨论】:

                                    • Postgres 对 MySQL 数据库没有帮助。
                                    【解决方案28】:

                                    只需添加

                                    spring.jpa.databaseplatform=org.hibernate.dialect.PostgreSQLDialect  
                                    

                                    最后。这将解决您的问题。 只是缺少了这个

                                    【讨论】:

                                    • Postgres 对 MySQL 数据库没有帮助。
                                    猜你喜欢
                                    • 2017-10-08
                                    • 2021-04-21
                                    • 2018-12-30
                                    • 1970-01-01
                                    • 1970-01-01
                                    • 2017-11-11
                                    • 2016-10-11
                                    • 1970-01-01
                                    • 2019-01-12
                                    相关资源
                                    最近更新 更多