如何在不丢失Hibernate数据的情况下更新数据库模式?

时间:2009-04-10 15:29:58

标签: database hibernate schema migrate

想象一下,您正在使用Hibernate和JBoss开发Java EE应用程序。您有一个正在运行的服务器,其中包含一些重要数据。您偶尔会发布下一版本的应用程序(1-2周),并且它们在持久层中有一堆更改:

  • 新实体
  • 已移除的实体
  • 属性类型更改
  • 属性名称更改
  • 关系变更

如何有效地设置更新数据库架构并保留数据的系统?据我所知(我可能会误解),Hibernate不执行alter column,drop / alter constraint。

谢谢你, Artem B。

8 个答案:

答案 0 :(得分:17)

LiquiBase是您最好的选择。它有一个hibernate integration模式,它使用Hibernate的hbm2ddl来比较你的数据库和你的hibernate映射,但它不是自动更新数据库,而是输出一个liquibase changelog文件,可以在实际运行之前进行检查。

虽然更方便,但任何比较数据库和hibernate映射的工具都会出错。有关示例,请参阅http://www.liquibase.org/2007/06/the-problem-with-database-diffs.html。使用liquibase,您可以构建一个数据库更改列表,因为您可以使用可以在具有分支和合并的代码中生存的格式进行开发。

答案 1 :(得分:4)

您可以使用提供Maven和Gradle插件的https://github.com/Devskiller/jpa2ddl工具,并且能够基于JPA实体为Flyway生成自动架构迁移。它还包括所有属性,方言,用户类型,命名策略等。

答案 2 :(得分:3)

我个人跟踪迁移SQL脚本中的所有更改。

答案 3 :(得分:3)

答案 4 :(得分:2)

对于一个应用程序,我使用SchemaUpdate,它是内置于Hibernate的,直接来自引导类,因此每次应用程序启动时都会检查架构。这需要添加新的列或表,这主要是成熟的应用程序发生的事情。为了处理特殊情况,比如删除列,引导程序只需在try / catch中手动运行ddl,这样如果它已被删除一次,它就会默默地抛出错误。我不确定我是否会在生产应用程序中使用关键任务数据执行此操作,但在几年和数百次部署中,我从未遇到过问题。

答案 5 :(得分:2)

作为Nathan Voxland关于LiquiBase的说法的进一步回答,这是一个在Windows下为mySql数据库执行迁移的示例:

例如,在liquibase发行版中的 lib 文件夹下放置mysql 连接器

在liquibase发行版的根目录中创建文件属性 liquibase.properties 并插入此循环行:

driver: com.mysql.jdbc.Driver
classpath: lib\\mysql-connector-java-5.1.30.jar
url: jdbc:mysql://localhost:3306/OLDdatabase
username: root
password: pwd

以其他名称生成或检索更新的数据库,例如 NEWdatabase

现在,您将使用以下命令行在 Migration.xml 文件中区分差异:

liquibase diffChangeLog --referenceUrl="jdbc:mysql://localhost:3306/NEWdatabase" 
--referenceUsername=root --referencePassword=pwd > C:\Users\ME\Desktop\Migration.xml

最后,使用刚刚生成的 Migration.xml 文件执行更新:

java -jar liquibase.jar --changeLogFile="C:\Users\ME\Desktop\Migration.xml" update

注意:所有这些命令行都应该从liquibase主目录执行,其中存在liquibase.bat / .sh和liquibase.jar。

答案 6 :(得分:1)

我使用hbm2ddl ant任务生成我的ddl。有一个选项可以在数据库中执行alter tables / columns。

请参阅hbm2ddl ant任务的“update”属性:

http://www.hibernate.org/hib_docs/tools/reference/en/html/ant.html#d0e1137

  

更新(默认值:false):尝试并创建   表示的更新脚本   在什么之间的“三角洲”   数据库和映射是什么   指定。忽略创建/更新   属性。 (使用   生产数据库,无保证   所有正确的三角洲都可以   生成也不是底层的   数据库实际上可以执行   需要的操作)

答案 7 :(得分:0)

您还可以使用 DBMigrate 。它与Liquibase类似:

  

类似于Ruby on的'rake migrate'   Rails这个库让你管理   Java的数据库升级   应用