First issue: We don't use the data cache either! If I recall correctly, exactly for the same reason: for different use cases we may use different fetch plans for the same entity. (Actually at our client-side we have actually implement our home-made cache - backed by ehache - that uses the fetchplan name as part of the cache key.).
I was speaking about the entities in the persistence context. This is a non-shared first-level cache of the EntityManager that is only kept for the duration of one transaction. As far as I know this is always used by default and cannot be turned off. I believe it is also used internally by JPA. When multiple database queries are done in one transaction, JPA can use this temporary cache to find referenced entities that have already been loaded during the same transaction, even if you don't have shared second-level cache turned on. So if your performance issue is important I suggest giving my suggestion a try! Second issue: I haven't seen that before. Perhaps this depends on the inheritance strategy. We have had no problems with InheritanceType.TABLE_PER_CLASS but we have had issues with an incorrect query being generated when using InheritanceType.JOINED so we don't use that. Depending on your use case you may also use @MappedSuperclass which has been working fine for us. Regards, Henno -----Oorspronkelijk bericht----- Van: David Minor [mailto:[email protected]] Verzonden: maandag 21 juli 2014 17:53 Aan: [email protected] Onderwerp: RE: Avoiding N+1 on collection in recursive relation Unfortunately we have the data cache turned off - we use fetch groups fairly heavily, and we've found that they do not play well with the data cache (https://issues.apache.org/jira/browse/OPENJPA-1280 for instance). Another issue I found that complicated my situation was our class structure - the hierarchical entity consisted of a superclass and two subclasses, and OpenJPA doesn't do eager fetching of subclass fields. When I flattened them into a single class, the number of SQL queries was cut in half. ________________________________________ From: Henno Vermeulen <[email protected]> Sent: Monday, July 21, 2014 1:22 AM To: [email protected] Subject: RE: Avoiding N+1 on collection in recursive relation I did find a workaround for this issue. It's idea can also be used to work around some other performance issues in JPA. The main idea is to efficiently prefetch any entity that OpenJPA would otherwise fetch with single find-by-id queries. Turn on OpenJPA trace and find out which entities are separately selected. Write a query that fetches exactly these entities. Then when performing the main query, OpenJPA will find these from the EntityManager cache. See also my comment on https://issues.apache.org/jira/browse/OPENJPA-2299 Unfortunately this workaround is a bit brittle because it depends on OpenJPA behavior that may change, in particular your query will depend on the fact that only the entities of the second list in the Java code of the entity suffers from this problem, not the first list. Note that the problem I had in OPENJPA-2299 does not have a tree structure. Fetching (sub)trees with JPA also suffers from N+1 select problems, but I don't think that these are directly related to your and my issue described here. These are for the nodes themselves, not for other entities they refer to. But for tree structures you CAN use a similar idea to efficiently fetch a full tree: make a query that fetches all of the nodes, then query for the root node. See also http://www.tikalk.com/java/load-a-tree-with-jpa-and-hibernate Met vriendelijke groet, Henno Vermeulen +31-6-50643787 Paushuize | Kromme Nieuwegracht 49 | 3512 HE Utrecht Huize Molenaar | Korte Nieuwstraat 6 | 3512 NM Utrecht -- _____________ David Minor
