Hibernate写入XML数据库

时间:2011-11-24 11:05:57

标签: xml database hibernate

我们目前面临着以下任务,我正在努力寻找我认为应该在那里的任何地方。

数据模型通过Hibernate存储在MySQL中。一切正常,产品已发货。

对于计划的未来版本,但需要更改数据模型。我们还不知道有哪些变化和变化,但我们知道客户数据库必须相应更新。

这很可能会在未来版本的未来版本上再次发生,这让我想到了问题的第一部分:

  • 通过将现有数据库内容导出到XML文件,基于它们创建的Hibernate版本,然后在重写之前更新内容(f.ex. with XSLT)来解决此问题是否合理数据库内容与更新的Hibernate版本?

我可以看到这种方法的以下优点:

  • 我们必须为新版本编写一次XSLT。
  • 我们可以轻松地将此应用于所有客户 - 甚至是自动化的。
  • 通过链接相应的XSLT,我们可以轻松地将数据库内容从版本X转换为版本Y,即使中间有多个版本。

然而,假设采用这种方法,实际问题是我们不想编写额外的代码来生成相应的XML文件。最理想的情况是,我想使用一个数据库将其内容存储在XML文件中并提供JDBC接口。有没有人知道如何以最小的努力实现这一目标?

我想到的工作流程如下:

  • 使用版本X中的Hibernate datamodel。创建两个数据库连接,一个连接到MySQL DB,一个连接到XML DB。从第一个读出所有内容,将其转储到后面(这可能需要一些自定义代码)
  • 编写XSLT,在XML DB的XML文件上执行它。
  • 使用版本Y的Hibernate datamodel。创建两个数据库连接,一个连接到MySQL DB,一个连接到XML DB。从XML读出所有内容并将其转储回MySQL。

可行否?有没有更好的方法来解决这个问题?我在哪里可以找到支持JDBC的XML数据库?

3 个答案:

答案 0 :(得分:1)

我认为XML数据库(如eXist)实现JDBC没有任何意义,因为JDBC直接基于处理SQL和关系模型。此外,我不确定我看到XML的计划好处是什么; XSLT是XML内容的正确转换语言。但在这种情况下,你最多拥有的是关系数据的XML包装,而不是树形的深层嵌套文本数据。 因此,您可能最好只编写Java代码来逐行进行更改。 这是一种相当普遍的做法。

您当然可以使用XML或JSON作为中间存储/缓冲格式,即处理导入和导出。但是,中间处理不一定会受益于XSLT或临时数据库。

答案 1 :(得分:1)

一个简单的解决方案可以是mysqldump --xml(http://dev.mysql.com/doc/refman/5.1/en/mysqldump.html#option_mysqldump_xml),它可以生成如下数据:

<mysqldump xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
<database name="world">
  <table_data name="City">
    <row>
      <field name="ID">1</field>
      <field name="Name">Kabul</field>
      <field name="CountryCode">AFG</field>
      <field name="District">Kabol</field>
      <field name="Population">1780000</field>
    </row>

然后,您可以使用“LOAD XML INFILE”http://dev.mysql.com/doc/refman/5.5/en/load-xml.html转换此数据并在表中再次加载它。

作为替代方案,我听到一些同事使用 Liquibase 获得了不错的结果:数据库重构工具。这允许您使用http://www.liquibase.org/manual/refactoring_commands中列出的重构命令以描述性方式编写数据库迁移脚本。

例如:

  <databaseChangeLog>
  <changeSet id="1" author="greyfairer>  
  <addLookupTable
        existingTableName="address" existingColumnName="state"
        newTableName="state" newColumnName="abbreviation"
        constraintName="fk_address_state"
    />

Liquibase还会跟踪在专用变更集表中应用的所有变更集。因此,如果您在产品的第2版中应用了变更集2a和2b,而在版本3中使用了3a和3b,则Liquibase可以检测到如果从版本1升级,那么它们都需要应用4,而版本2只需要3a和3b,因为2a和2b已经在变更集表中。

当然,这些解决方案并不反映您的域模型,但有时在进行此类迁移时,更容易使用数据库术语而不是域术语。

答案 2 :(得分:0)

更好的方法是不使用Hibernate IMO。

我们有一个使用nHibernate和SqlServer的解决方案,因此您的解决方案将有所不同,但我确信可以应用相关工具来实现相同的目标。

要从R1升级到R1.1,我们使用nHibernate映射文件(比如db1.1)将新模式生成到空的'build'数据库中。然后我们获取当前版本(db1.0)的副本并使用db模式工具(我们使用DbGhost)然后将db1.0升级到db1.1。

DbGhost(以及其他类似工具)将自动添加非null添加项和新表,并为每组批量更改提供自定义sql的注入点。

它实现了一个梦想,并且在我们的多开发人员,多种环境中工作得很好。一个真正的好处是,对于最终版本,可以更改DbGhost调用以生成一个总结所有chnages的升级版本。

希望它有所帮助。