Hibernate 使用hbm2ddl为数据库架构更新生成SQL DDL(不丢失数据)

Hibernate 使用hbm2ddl为数据库架构更新生成SQL DDL(不丢失数据),hibernate,orm,code-generation,Hibernate,Orm,Code Generation,我一直在使用hbm2ddl和hbm2java为基于XML映射文件(hbm.XML)的项目构建数据库和POJO。我现在开始在系统中获取一些真实的数据,因此重新运行我的ant脚本(删除数据库并重新创建所有内容)不再是可行的选择,因为我希望保留数据。我听说有一个hbm2ddl.auto功能,可以用来修改数据库结构而不删除数据,但我从s/o的一些答案中得出结论,这不是一个最佳做法 我的理解是,您应该根据映射文件中的更改编写SQLDDL,并针对DB运行它。我想知道是否可以使用hbm2ddl根据映射文件生成

我一直在使用
hbm2ddl
hbm2java
为基于XML映射文件(hbm.XML)的项目构建数据库和POJO。我现在开始在系统中获取一些真实的数据,因此重新运行我的ant脚本(删除数据库并重新创建所有内容)不再是可行的选择,因为我希望保留数据。我听说有一个hbm2ddl.auto功能,可以用来修改数据库结构而不删除数据,但我从s/o的一些答案中得出结论,这不是一个最佳做法

我的理解是,您应该根据映射文件中的更改编写SQLDDL,并针对DB运行它。我想知道是否可以使用hbm2ddl根据映射文件生成此DDL。我也开始讨论LiquiBase,但不确定这些是否适合我的情况,因为我希望继续使用hbm.xml文件作为关键数据定义源


欢迎提出意见和建议-提前感谢

这可能不是在生产环境中实现这一点的最佳方式,但如果您不是“与成千上万的用户生活在一起”,下面介绍如何做到这一点:

  • 设置为
    update
    (这是一个hibernate属性,请在
    hibernate.cfg.xml
    中或在spring配置中设置,如果您使用它)
  • 每次(重新)启动应用程序时,数据库模式都将使用新字段和约束进行更新
  • 旧字段可能无法删除,因此您可以手动清理它们
  • 非空
    列相对应的原语应指定
    默认值
    ,或者您应该手动执行
    更新
    查询。否则会出现运行时异常

    • 上周我问了我同样的问题,我决定使用LiquiBase。这里有许多关于“堆栈溢出”的说法,它们不鼓励您在生产环境中使用hbm2ddl。我也是


      当我尝试添加独特的约束时,我遇到了hbm2ddl的能力限制,我意识到是时候选择更复杂的方法了。

      如果我使用ant脚本的
      hbm2ddl
      任务和
      export=false
      update=true
      生成脚本,我会得到同样的结果吗,对我的数据库进行测试?当人们评论说不应在生产环境中使用更新时,我不清楚他们的意思是:“不要在启动应用程序时将其放入配置中自动更新数据库,因为这些更改可能未通过数据测试”,或者“根本不要使用此功能,即使只是生成SQL;您应该手工编写SQL。“@slau我绝对不同意第二种说法。这些人希望通过跟踪数据库的变化使他们的生活变得不必要的复杂。因为您的对象模型是原始数据,所以如果可能,您应该从中生成所有内容。我的回答中的第四个要点涵盖了第一个陈述——可能与已经输入的数据不一致。但是,如果在投入生产之前使用生产中的数据对其进行测试,仍然可以。我同意只维护一个工件(映射),而不是保留增量。但我认为,在这种情况下,人们普遍认为生成的增量不够完整,再加上变化的不可预测性——我认为这仍然是数据模型转换/重构中的一个公开问题。在任何情况下,我尝试使用更新生成SQL,并看到了您提到的许多要点。我认为这是一个可管理的解决方案,我需要在这一点上。谢谢我对LiquiBase的理解是,您必须手动维护
      变更集
      ,以反映您对映射文件所做的任何更改。我认为这可能会很麻烦,特别是因为我不担心分布式更改,您需要包括LiquiBase库来进行部署。当您提到
      hbm2ddl
      在唯一约束方面存在问题时,您的意思是当您尝试向现有列添加唯一约束时?是的,
      hbm2ddl
      在向现有列添加约束方面存在问题。IIRC,当你尝试添加索引时,它也会失败。你是对的。我不喜欢在现有列中添加索引,但在新字段中似乎可以。看起来一个新的LiquiBase构建正在进行中-可能很快就会检查出来。谢谢你的建议!