JPA/HIBERNATE - 缓存的对象实例是否仅按 id 索引?
可能这是一个基本问题,但无法在网络上的任何地方找到答案。
我正在尝试使用二级缓存(使用 ehcache),并且只是检查每次尝试加载某些对象时是否从数据库中检索它们,唯一的区别是我不是通过 id 获取它们,而是通过带有 id 的属性获取它们一个 SEO 友好的名称,用于在我正在工作的系统上创建 url。 jpa/hibernate 是否能够仅通过 obj 的 id 从缓存中检索对象?有什么方法可以让它工作而不需要激活查询缓存吗?
Probably it is a basic question, but could not found the answer anywhere in the web.
I am trying to use a second level cache (using ehcache) and just checked that some objects were being retrieved from database every time I tried to load them, the only difference was that I was not getting them by id but by a property that carries a SEO friendly name that are used to create urls on the system I am working. Is jpa/hibernate able to retrieve objects from cache just by with the id of the obj? Is there any way to get it working without need to activate the query cache?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(1)
是的,二级缓存适用于基于
Id
查找单个对象的查询,即使用EntityManager.find()
或EntityManager.getReference()< /code> (或 Hibernate API 中的等效
Session#get()
和Session#load()
)。 AFAIK,这适用于所有 JPA 实现。对于标准 JPA,除了使用查询缓存之外,我没有看到任何其他选项。
但如果你不介意使用 Hibernate API,可能还有一个替代方案
Query#iterate()
。使用Query#iterate ()
,Hibernate 将发出一个 SQL 查询,该查询将仅获取 ID,当您迭代结果时,它将从缓存中加载相应的实体。显然,如果您不使用二级缓存,
Query#iterate()
将比Query#list()
慢得多。就我个人而言,我会使用查询缓存。
另请参阅
Yes, the second level cache works for query that looks for a single object based on
Id
i.e. when usingEntityManager.find()
orEntityManager.getReference()
(or the equivalentSession#get()
andSession#load()
from the Hibernate API). AFAIK, this applies to all JPA implementations.With standard JPA, I don't see any other option than using the Query Cache.
But if you don't mind using Hibernate API, there might be an alternative with
Query#iterate()
. WithQuery#iterate()
, Hibernate will issue a SQL query that will fetch only the IDs and when you iterate over the results, it will load the corresponding entities from the cache.Obviously,
Query#iterate()
will be much slower thanQuery#list()
if you're not using a second level cache.Personally, I'd use the query cache.
See also