当前位置: 首页 > 知识库问答 >
问题:

Hibernate ORM与GraalVM本机映像编译兼容吗?

谷梁宝
2023-03-14

根据文档,GraalVM项目中的本机映像编译器有一些动态代理的限制。既然Hibernate大量使用了代理,那么它在提前编译的项目中能正常工作吗?

Quarkus项目似乎表明它可以,但我的理解主要是基于Reddit的一篇帖子说

Hibernate ORM现在即使编译为GraalVM本机映像也可以工作--只要确保使用Quarkus构建应用程序即可。

如果我不想(或者不会)使用夸克呢?是否可以使用使用Hibernate的GraalVM(和SubstrateVM)编译本机映像应用程序?

Quarkus实际上做了什么来启用/支持Hibernate?

共有1个答案

澹台景山
2023-03-14

(免责声明:我是通过创建Quarkus扩展使Hibernate ORM在GraalVM本机映像上工作的人之一。我也是Hibernate研发团队的领导。)

谢谢你给我这个机会来写一点历史:)

最初我们没有使用夸克,因为它还不存在。

我最初的原型只是修补Hibernate ORM,并堆放了许多编译器开关,以传递给本机映像工具(硬编码为bash脚本),直到我的演示应用程序能够正常工作。

这种方法的问题在于,许多这样的标志实际上依赖于Hibernate ORM的内部知识、域模型的细节、配置细节,可能还有更多。

我开始记录这样的事情,但它变得复杂和毛茸茸的;尤其是不同方面相互依赖;此外,我的演示应用程序相当简单,而实际应用程序的情况必然会变得更加复杂。我不认为我们能写出一份既周到又“易懂”的好文件。

为最终用户保持简单的另一种方法是“在您可能使用这些类时启用对它们的反射”,但我是一个优化狂,这会创建更大更臃肿的二进制文件,而不是只包含应用程序真正需要的所有内容。

所以我们的团队决定编写一个工具来自动处理这些细节…它变成了一个构建工具,可以分析您的应用程序,找出最好的开关。而不是只关注Hibernate ORM,我们创建了“扩展”的概念,它将知道如何将同样的技巧应用于其他库,这样您就可以从使用支持库组合的更复杂应用程序中高度优化的二进制文件中获益,而不仅仅是Hibernate。

显然,这是必要的,因为不同的库可能有相互冲突的需求,并且需要将其他库和最终用户代码的编译器标志组合在一组一致的兼容标志中。

所以夸库斯就是这样变成一个东西的:)

要了解其工作原理的详细信息,我建议阅读指南和源代码:

  • https://quarkus.io/
  • https://github.com/quarkusio/quarkus

我还对它在公开演讲中的作用做了一些高层次的概述;Devoxx英国有一段很好的录音

  • https://youtu.be/za5csbx-ume

我的演讲专门讨论了Hibernate ORM;我没有太多的时间来详细介绍它所做的所有事情,但在阅读具体代码之前,它应该是一个很好的介绍。

如果我不想(或者不会)使用夸克呢?是否可以使用使用Hibernate的GraalVM(和SubstrateVM)编译本机映像应用程序

这是一个公平的问题--这当然是可能的,但夸库斯团队想知道为什么?

Quarkus所做的所有工作大多只在构建时完成;当然,由于它是一个非常年轻的项目,在这个阶段它可能会受到限制,但是如果您需要对其他任何东西的支持,那么在构建脚本中对其核心(或扩展)进行贡献应该比对复杂的编译器标志进行硬编码更容易。更重要的是,Quarkus社区正成为一个讨论如何解决Graal限制可能遇到的任何路障的好地方。

Hibernate ORM的所有最复杂的补丁都已合并到Hibernate上游存储库中,因此所有重要的补丁都包含在任何最新版本中。

假设你想和夸库斯保持距离(我不这么建议,但假设你想学习……),你仍然需要修补反射规则,而且夸库斯确实限制了一些特性,最明显的是一些细节仍然是“正在进行的工作”,或者我们认为人们不应该再使用的东西:)

具体地说,我和我的队友都不是线程绑定会话的超级粉丝。我不打算实现对它的支持,除非有人会为它做一个很好的理由:请打开一个特性请求,或者在理想情况下帮助为它和补丁做一个很好的理由?

  • https://github.com/quarkusio/quarkus/issues/
 类似资料:
  • GraalVM系统显然无法将Spring应用程序编译为本机映像。

  • 我有一个Java项目,我用GraalVM原生映像编译成可执行的二进制文件。我想为Travis CI的项目配置持续集成过程,这对我来说很难——Travis CI允许吗?如何配置。特拉维斯。用GraalVM原生图像构建的yml文件?

  • 我正在尝试用Dockers创建一个GraalVM本地映像。我已经创建了一个Micronaut项目,并成功创建了jar应用程序,并在docker中运行;此外,我已经用这个jar文件创建了一个GraalVM本机映像,现在可以运行这个应用程序,但我需要在docker中运行一个GraalVM本机映像,在论坛中寻找答案。我发现有必要在docker中构建本机映像。因此我尝试了这个docker文件: 它不会抛出

  • 我在这里将Micronaut应用程序作为Graalvm本地映像进行试用。

  • 我正在尝试使用graalVM v20.0.0CE创建一个简单的hello world本地映像。 最初,我收到了一个“本机工具链”错误,但从“x86 Native Tools Command Prompt for VS2017”启动了一个命令行,我就克服了这个障碍。 现在的问题是一串链接器错误: java.lib(jni_util.obj):错误LNK2019:函数jni _打印字符串中引用了未解析

  • 我的应用程序位于Quarkus框架之上。该应用程序的主要功能是简单的REST API,用于安排一些任务(现在它只是将一些消息发布到日志中)。 调度功能是我用Quartz framework实现的,通常情况下,当应用程序收到安排新事件的POST请求时,它会做两件事: 将实体从请求保存到数据库 在JSON中提到的日期和时间上安排Quartz作业 此外,当应用程序刚刚启动时,我创建了从数据库中获取所有实