Java Hibernate vs JPA vs JDO - 各自的优缺点?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/530215/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-11 15:52:52  来源:igfitidea点击:

Hibernate vs JPA vs JDO - pros and cons of each?

javahibernateormjpajdo

提问by matt b

I'm familiar with ORM as a concept, and I've even used nHibernate several years ago for a .NET project; however, I haven't kept up with the topic of ORM in Java and haven't had a chance to use any of these tools.

我熟悉 ORM 作为一个概念,几年前我什至在一个 .NET 项目中使用过 nHibernate;但是,我没有跟上 Java 中 ORM 的话题,也没有机会使用这些工具中的任何一个。

But, now I may have the chance to begin to use some ORM tools for one of our applications, in an attempt to move away from a series of legacy web services.

但是,现在我可能有机会开始为我们的一个应用程序使用一些 ORM 工具,以尝试摆脱一系列遗留的 Web 服务。

I'm having a hard time telling the difference betweeen the JPA spec, what you get with the Hibernate library itself, and what JDO has to offer.

我很难说出 JPA 规范、您从 Hibernate 库本身获得的内容以及 JDO 必须提供的内容之间的区别。

So, I understand that this question is a bit open-ended, but I was hoping to get some opinions on:

所以,我知道这个问题有点开放,但我希望得到一些意见:

  • What are the pros and cons of each?
  • Which would you suggest for a new project?
  • Are there certain conditions when it would make sense to use one framework vs the other?
  • 各自的优缺点是什么?
  • 你会为一个新项目推荐哪个?
  • 在某些情况下,使用一种框架与另一种框架是否有意义?

采纳答案by toolkit

Some notes:

一些注意事项:

  • JDO and JPA are both specifications, not implementations.
  • The idea is you can swap JPA implementations, if you restrict your code to use standard JPA only. (Ditto for JDO.)
  • Hibernate can be used as one such implementation of JPA.
  • However, Hibernate provides a native API, with features above and beyond that of JPA.
  • JDO 和 JPA 都是规范,而不是实现。
  • 这个想法是你可以交换 JPA 实现,如果你限制你的代码只使用标准 JPA。(JDO 同上。)
  • Hibernate 可以用作 JPA 的一种此类实现。
  • 然而,Hibernate 提供了一个原生 API,其功能超出了 JPA。

IMO, I would recommend Hibernate.

海事组织,我会推荐休眠。



There have been some comments / questions about what you should do if you needto use Hibernate-specific features. There are many ways to look at this, but my advice would be:

如果您需要使用特定于 Hibernate 的功能,您应该如何做一些评论/问题。有很多方法可以看待这个问题,但我的建议是:

  • If you are not worried by the prospect of vendor tie-in, then make your choice between Hibernate, and other JPA and JDO implementations includingthe various vendor specific extensions in your decision making.

  • If you are worried by the prospect of vendor tie-in, and you can't use JPA without resorting to vendor specific extensions, then don't use JPA. (Ditto for JDO).

  • 如果您不担心供应商搭售的前景,那么请在 Hibernate 和其他 JPA 和 JDO 实现之间做出选择,包括您的决策中的各种供应商特定扩展。

  • 如果您担心供应商搭售的前景,并且在不求助于供应商特定扩展的情况下无法使用 JPA,那么请不要使用 JPA。(JDO 同上)。

In reality, you will probably need to trade-off how muchyou are worried by vendor tie-in versus how muchyou need those vendor specific extensions.

在现实中,你可能需要权衡多少你被厂商担心搭配与多少,你需要这些供应商特定的扩展。

And there are other factors too, like how well you / your staff know the respective technologies, how much the products will cost in licensing, and whose story you believe about what is going to happen in the future for JDO and JPA.

还有其他因素,例如您/您的员工对各自技术的了解程度,产品的许可费用是多少,以及您相信谁的故事关于 JDO 和 JPA 未来会发生什么。

回答by tapi

I've been looking into this myself and can't find a strong difference between the two. I think the big choice is in which implementation you use. For myself I've been considering the DataNucleusplatform as it is a data-store agnostic implementation of both.

我自己一直在研究这个问题,但找不到两者之间的明显区别。我认为最大的选择是您使用哪种实现。对于我自己,我一直在考虑DataNucleus平台,因为它是两者的数据存储不可知实现。

回答by oxbow_lakes

Which would you suggest for a new project?

你会为一个新项目推荐哪个?

I would suggest neither! Use Spring DAO's JdbcTemplatetogether with StoredProcedure, RowMapperand RowCallbackHandlerinstead.

我不建议!将 Spring DAOJdbcTemplateStoredProcedure,RowMapper和一起使用RowCallbackHandler

My own personal experience with Hibernate is that the time saved up-front is more than offset by the endless days you will spend down the line trying to understand and debug issues like unexpected cascading update behaviour.

我个人使用 Hibernate 的经验是,预先节省的时间远远被您花在尝试理解和调试诸如意外级联更新行为之类的问题上的无休止的日子所抵消。

If you are using a relational DB then the closer your code is to it, the more control you have. Spring's DAO layer allows fine control of the mapping layer, whilst removing the need for boilerplate code. Also, it integrates into Spring's transaction layer which means you can very easily add (via AOP) complicated transactional behaviour without this intruding into your code (of course, you get this with Hibernate too).

如果您使用的是关系数据库,那么您的代码越接近它,您拥有的控制权就越多。Spring 的 DAO 层允许对映射层进行精细控制,同时消除对样板代码的需要。此外,它集成到 Spring 的事务层中,这意味着您可以非常轻松地添加(通过 AOP)复杂的事务行为,而不会干扰您的代码(当然,您也可以通过 Hibernate 获得这一点)。

回答by DataNucleus

JDO is dead

JDO死了

JDO is not dead actually so please check your facts. JDO 2.2 was released in Oct 2008 JDO 2.3 is under development.

JDO 实际上并没有死,所以请检查你的事实。JDO 2.2 于 2008 年 10 月发布 JDO 2.3 正在开发中。

This is developed openly, under Apache. More releases than JPA has had, and its ORM specification is still in advance of even the JPA2 proposed features

这是在 Apache 下公开开发的。比 JPA 有更多的版本,它的 ORM 规范仍然领先于 JPA2 提出的特性

回答by DataNucleus

I am using JPA (OpenJPA implementation from Apache which is based on the KODO JDO codebase which is 5+ years old and extremely fast/reliable). IMHO anyone who tells you to bypass the specs is giving you bad advice. I put the time in and was definitely rewarded. With either JDO or JPA you can change vendors with minimal changes (JPA has orm mapping so we are talking less than a day to possibly change vendors). If you have 100+ tables like I do this is huge. Plus you get built0in caching with cluster-wise cache evictions and its all good. SQL/Jdbc is fine for high performance queries but transparent persistence is far superior for writing your algorithms and data input routines. I only have about 16 SQL queries in my whole system (50k+ lines of code).

我正在使用 JPA(来自 Apache 的 OpenJPA 实现,它基于 KODO JDO 代码库,该代码库已有 5 年以上的历史并且非常快速/可靠)。恕我直言,任何告诉你绕过规范的人都在给你不好的建议。我投入了时间,肯定得到了回报。使用 JDO 或 JPA,您可以以最少的更改更改供应商(JPA 具有 orm 映射,因此我们在不到一天的时间内讨论可能更改供应商)。如果你像我一样有 100 多张桌子,那就太棒了。此外,您可以通过集群缓存逐出获得内置缓存,这一切都很好。SQL/Jdbc 适用于高性能查询,但透明持久性对于编写算法和数据输入例程要好得多。我的整个系统中只有大约 16 个 SQL 查询(5 万多行代码)。

回答by Sandeep Manne

JDO is having advanced features than JPA see http://db.apache.org/jdo/jdo_v_jpa.html

JDO 具有比 JPA 先进的功能,请参阅http://db.apache.org/jdo/jdo_v_jpa.html

回答by Sean McCauliff

I've used Hibernate (JPA implementation) and JPOX (JDO implementation) in the same project. JPOX worked ok, but ran into bugs fairly quickly, there where some Java 5 language features it did not support at the time. It had problems playing nice with XA transactions. I was generating the database schema from the JDO objects. It wanted to connect to a database every time which is annoying if your Oracle connection happens not be working.

我在同一个项目中使用了 Hibernate(JPA 实现)和 JPOX(JDO 实现)。JPOX 工作正常,但很快就遇到了错误,当时它不支持某些 Java 5 语言功能。它在处理 XA 事务时遇到了问题。我正在从 JDO 对象生成数据库模式。它每次都想连接到数据库,如果您的 Oracle 连接不工作,这很烦人。

We then switched to Hibernate. We toyed around with just using pure JPA for awhile, but we needed to use some of the Hibernate specific features to do the mapping. Running the same code on multiple databases is very easy. Hibernate seems to cache objects aggressively or just have strange caching behavior at times. There are a few DDL constructs Hibernate can not handle and so they are defined in an additional file that is run to initialize the database. When I've run into a Hibernate problem there are often many people that have run into the same problem which makes googling for solutions easier. Finally, Hibernate seems to be well designed and reliable.

然后我们切换到 Hibernate。我们暂时只使用纯 JPA,但我们需要使用一些 Hibernate 特定功能来进行映射。在多个数据库上运行相同的代码非常容易。Hibernate 似乎积极地缓存对象,或者有时只是有奇怪的缓存行为。有一些 DDL 构造 Hibernate 无法处理,因此它们在运行以初始化数据库的附加文件中定义。当我遇到 Hibernate 问题时,通常会有很多人遇到同样的问题,这使得在谷歌上搜索解决方案变得更容易。最后,Hibernate 似乎设计良好且可靠。

Some other responders have suggested just using SQL. The real killer use case for object relational mapping is testing and development. The databases that are built to handle large volumes of data are typically expensive and or they are difficult to install. They are difficult to test with. There are plenty of in-memory Java databases that can be used to test with, but are typically useless for production. Being able to use a real, but limited database, will increase development productivity and code reliability.

其他一些响应者建议只使用 SQL。对象关系映射的真正杀手级用例是测试和开发。为处理大量数据而构建的数据库通常很昂贵,或者很难安装。它们很难测试。有很多内存 Java 数据库可用于测试,但通常对生产无用。能够使用真实但有限的数据库将提高开发效率和代码可靠性。

回答by Volksman

Make sure you evaluate the DataNucleus implementation of JDO. We started out with Hibernate because it appeared to be so popular but pretty soon realized that it's not a 100% transparent persistence solution. There are too many caveats and the documentation is full of 'if you have this situation then you must write your code like this' that took away the fun of freely modeling and coding however we want. JDO has nevercaused me to adjust my code or my model to get it to 'work properly'. I can just design and code simple POJOs as if I was going to use them 'in memory' only, yet I can persist them transparently.

确保您评估 JDO 的 DataNucleus 实现。我们开始使用 Hibernate 是因为它看起来很受欢迎,但很快就意识到它不是一个 100% 透明的持久性解决方案。有太多的警告,并且文档中充满了“如果您遇到这种情况,那么您必须像这样编写代码”,这剥夺了我们想要的自由建模和编码的乐趣。JDO从未让我调整代码或模型以使其“正常工作”。我可以设计和编码简单的 POJO,就好像我只打算在“内存中”使用它们一样,但我可以透明地保留它们。

The other advantage of JDO/DataNucleus over hibernate is that it doesn't have all the run time reflection overhead and is more memory efficient because it uses build time byte code enhancement (maybe add 1 sec to your build time for a large project) rather than hibernate's run time reflection powered proxy pattern.

JDO/DataNucleus 相对于休眠的另一个优点是它没有所有的运行时反射开销并且内存效率更高,因为它使用了构建时字节码增强(可能为大型项目的构建时间增加 1 秒)而不是比休眠的运行时反射驱动的代理模式。

Another thing you might find annoying with Hibernate is that a reference you have to what you think is the object... it's often a 'proxy' for the object. Without the benefit of byte code enhancement the proxy pattern is required to allow on demand loading (i.e. avoid pulling in your entire object graph when you pull in a top level object). Be prepared to override equals and hashcode because the object you think you're referencing is often just a proxy for that object.

您可能会发现 Hibernate 令人讨厌的另一件事是,您必须引用您认为是对象的内容……它通常是对象的“代理”。如果没有字节码增强的好处,代理模式需要允许按需加载(即避免在拉入顶级对象时拉入整个对象图)。准备好覆盖 equals 和 hashcode,因为您认为您引用的对象通常只是该对象的代理。

Here's an example of frustrations you'll get with Hibernate that you won't get with JDO:

下面是一个使用 Hibernate 会遇到的挫折示例,而使用 JDO 则不会:

http://blog.andrewbeacock.com/2008/08/how-to-implement-hibernate-safe-equals.html
http://burtbeckwith.com/blog/?p=53

http://blog.andrewbeacock.com/2008/08/how-to-implement-hibernate-safe-equals.html
http://burtbeckwith.com/blog/?p=53

If you like coding to 'workarounds' then, sure, Hibernate is for you. If you appreciate clean, pure, object oriented, model driven development where you spend all your time on modeling, design and coding and none of it on ugly workarounds then spend a few hours evaluating JDO/DataNucleus. The hours invested will be repaid a thousand fold.

如果您喜欢编码以“变通”,那么当然,Hibernate 适合您。如果您喜欢干净、纯粹、面向对象、模型驱动的开发,您将所有时间都花在建模、设计和编码上,而没有花在丑陋的解决方法上,那么请花几个小时评估JDO/DataNucleus。投入的时间将得到千倍的回报。

Update Feb 2017

2017 年 2 月更新

For quite some time now DataNucleus' implements the JPA persistence standard in addition to the JDO persistence standard so porting existing JPA projects from Hibernate to DataNucleus should be very straight forward and you can get all of the above mentioned benefits of DataNucleus with very little code change, if any. So in terms of the question, the choice of a particular standard, JPA (RDBMS only) vs JDO (RDBMS + No SQL + ODBMSes + others), DataNucleus supports both, Hibernate is restricted to JPA only.

很长一段时间以来,除了 JDO 持久性标准之外,DataNucleus 还实现了 JPA 持久性标准,因此将现有的 JPA 项目从 Hibernate 移植到 DataNucleus 应该非常简单,并且您只需很少的代码更改即可获得 DataNucleus 的所有上述好处,如果有的话。因此,就问题而言,特定标准的选择,JPA(仅限 RDBMS)与 JDO(RDBMS + No SQL + ODBMSes + 其他),DataNucleus 两者都支持,Hibernate 仅限于 JPA。

Performance of Hibernate DB updates

Hibernate DB 更新的性能

Another issue to consider when choosing an ORM is the efficiency of its dirty checking mechanism - that becomes very important when it needs to construct the SQL to update the objects that have changed in the current transaction - especially when there are a lot of objects. There is a detailed technical description of Hibernate's dirty checking mechanism in this SO answer: JPA with HIBERNATE insert very slow

选择 ORM 时要考虑的另一个问题是其脏检查机制的效率——当它需要构造 SQL 来更新当前事务中已更改的对象时,这变得非常重要——尤其是当有很多对象时。在这个 SO 答案中有详细的 Hibernate 脏检查机制的技术描述: JPA with HIBERNATE insert very slow

回答by Volksman

Anyone who says that JDO is dead is an astroturfing FUD monger and they know it.

任何说 JDO 已死的人都是 FUD 的大贩子,他们知道这一点。

JDO is alive and well. The specification is still more powerful, mature and advanced than the much younger and constrained JPA.

JDO 还活着。该规范仍然比年轻得多且受约束的 JPA 更强大、更成熟和更先进。

If you want to limit yourself to only what's available in the JPA standard you can write to JPA and use DataNucleus as a high performance, more transparent persistence implementation than the other implementations of JPA. Of course DataNucleus also implements the JDO standard if you want the flexibility and efficiency of modeling that JDO brings.

如果您只想将自己限制在 JPA 标准中可用的内容,您可以写入 JPA 并使用 DataNucleus 作为高性能、比 JPA 的其他实现更透明的持久性实现。当然,如果您想要 JDO 带来的建模的灵活性和效率,DataNucleus 也实现了 JDO 标准。

回答by Tom

I have recently evaluated and picked a persistence framework for a java project and my findings are as follows:

我最近评估并选择了一个 Java 项目的持久性框架,我的发现如下:

What I am seeing is that the support in favour of JDOis primarily:

我所看到的是,对JDO的支持主要是:

  • you can use non-sql datasources, db4o, hbase, ldap, bigtable, couchdb (plugins for cassandra) etc.
  • you can easily switch from an sql to non-sql datasource and vice-versa.
  • no proxy objects and therefore less pain with regards to hashcode() and equals() implementations
  • more POJO and hence less workarounds required
  • supports more relationship and field types
  • 您可以使用非 sql 数据源、db4o、hbase、ldap、bigtable、couchdb(cassandra 插件)等。
  • 您可以轻松地从 sql 切换到非 sql 数据源,反之亦然。
  • 没有代理对象,因此减少了 hashcode() 和 equals() 实现的痛苦
  • 更多的 POJO,因此需要更少的解决方法
  • 支持更多的关系和字段类型

and the support in favour of JPAis primarily:

支持JPA的主要是:

  • more popular
  • jdo is dead
  • doesnt use bytecode enhancement
  • 更流行
  • jdo死了
  • 不使用字节码增强

I am seeing a lot of pro-JPA posts from JPA developers who have clearly not used JDO/Datanucleus offering weak arguments for not using JDO.

我看到很多来自 JPA 开发人员的亲 JPA 帖子,他们显然没有使用 JDO/Datanucleus,为不使用 JDO 提供了弱论据。

I am also seeing a lot of posts from JDO users who have migrated to JDO and are much happier as a result.

我还看到很多来自 JDO 用户的帖子,他们迁移到 JDO 并因此感到更加快乐。

In respect of JPA being more popular, it seems that this is due in part due to RDBMS vendor support rather than it being technically superior. (Sounds like VHS/Betamax to me).

关于 JPA 更受欢迎,这似乎部分是由于 RDBMS 供应商的支持,而不是技术上的优越。(对我来说听起来像 VHS/Betamax)。

JDO and it's reference implementation Datanucleus is clearly not dead, as shown by Google's adoption of it for GAE and active development on the source-code (http://sourceforge.net/projects/datanucleus/).

JDO 及其参考实现 Datanucleus 显然还没有消亡,正如 Google 将其用于 GAE 并积极开发源代码 (http://sourceforge.net/projects/datanucleus/) 所表明的那样。

I have seen a number of complaints about JDO due to bytecode enhancement, but no explanation yet for why it is bad.

由于字节码增强,我看到了许多关于 JDO 的抱怨,但还没有解释为什么它很糟糕。

In fact, in a world that is becoming more and more obsessed by NoSQL solutions, JDO (and the datanucleus implementation) seems a much safer bet.

事实上,在一个越来越沉迷于 NoSQL 解决方案的世界中,JDO(和 datanucleus 实现)似乎是一个更安全的赌注。

I have just started using JDO/Datanucleus and have it set up so that I can switch easily between using db4o and mysql. It's helpful for rapid development to use db4o and not have to worry too much about the DB schema and then, once the schema is stabilised to deploy to a database. I also feel confident that later on, I could deploy all/part of my application to GAE or take advantage of distributed storage/map-reduce a la hbase /hadoop / cassandra without too much refactoring.

我刚刚开始使用 JDO/Datanucleus 并对其进行了设置,以便我可以在使用 db4o 和 mysql 之间轻松切换。使用 db4o 有助于快速开发,而不必过多担心 DB 模式,然后,一旦模式稳定即可部署到数据库。我也有信心,以后我可以将我的应用程序的全部/部分部署到 GAE 或利用分布式存储/map-reduce a la hbase /hadoop / cassandra,而无需进行太多重构。

I found the initial hurdle of getting started with Datanucleus a little tricky - The documentation on the datanucleus website is a little hard to get into - the tutorials are not as easily to follow as I would have liked. Having said that, the more detailed documentation on the API and mapping is very good once you get past the initial learning curve.

我发现开始使用 Datanucleus 的最初障碍有点棘手 - datanucleus 网站上的文档有点难以进入 - 教程并不像我希望的那样容易理解。话虽如此,一旦您过了最初的学习曲线,关于 API 和映射的更详细的文档是非常好的。

The answer is, it depends what you want. I would rather have cleaner code, no-vendor-lock-in, more pojo-orientated, nosql options verses more-popular.

答案是,这取决于你想要什么。我宁愿拥有更简洁的代码、无供应商锁定、更面向 pojo、nosql 选项和更受欢迎的内容。

If you want the warm fussy feeling that you are doing the same as the majority of other developers/sheep, choose JPA/hibernate. If you want to lead in your field, test drive JDO/Datanucleus and make your own mind up.

如果您想要与大多数其他开发人员/绵羊一样的温暖挑剔感觉,请选择 JPA/hibernate。如果您想在自己的领域处于领先地位,请试驾 JDO/Datanucleus 并下定决心。