eclipselink
eclipselink copied to clipboard
Bug 371743 - Fetching Lazy-Fields (Basic-Mapping) causes inconsistent database reload on the whole entity
The bug originally reported at https://bugs.eclipse.org/bugs/show_bug.cgi?id=371743 since EclipseLink 2.1.3 exists, still. When triggering a lazy-loaded basic attribute existing changes made to the entity are reset.
That is because the ReadObjectQuery issued at https://github.com/eclipse-ee4j/eclipselink/blob/master/foundation/org.eclipse.persistence.core/src/main/java/org/eclipse/persistence/queries/FetchGroup.java#L145 does not respect an existing changeset of the entity.
As stated in the comments of the original bug report, this bug effectively renders lazy-loaded basic attributes pretty much unusable.
Unlike the original report, that asked for the code to fetch all lazy-loaded attributes at once, I do believe the correct fix would be to fetch the yet unfetched attribute only.
Is this still occurring in recent releases? The original bug report as well as stackoverflow mention LOBs - is this limited to LOBs and if not - of what java and sql type are your lazily-fetched Basic-Mapping fields?
Not just LOBs but basic strings mapped to an ordinary varchar column. Last time I checked this behavior was present, still. This was the current version when I filed this report.
Ah, I did not realize at first that this is a fetch group-related issue.
We disabled fetch group support from the very beginning (ironically for performance reasons) but it's surprising that fetch groups seem to also affect correctness, if this issue holds true.
Are you willing to provide a minimalistic unit test which reproduces the problem?
To me the fetchgroups actually provide a lot flexibility, entity graphs won't work without. Wasn't even aware that can be disabled? Ah, by turning off that weaving option.
Is there an existing test that I could build upon, that has weaving enable? I had a look around the codebase and found the jpa test submodule to be concerned with interface contracts mainly. Advice what to look at would save me some time.
Also I tries running the tests using mvn test and it failed building due to module dependencies. Is there any documentation on how to run the tests? The wiki pages refer to ant and are outdated.
You could adapt this maven project I created for another issue. It has a basic, statically weaved PU and by default uses an in-memory derby DB. I found this approach with an external project to be easier than adapting eclipselink's own unit tests.
Thanks @Zuplyx, find attached a minimal reproduction of the issue. The test fails because the changed but not yet persisted newName gets reset to the oldName when the lazyValis fetched by accessing it.
@Test
void test() {
var entity = new MyTestEntity();
entity.setId(1L);
entity.setName("oldName");
entity.setLazy("lazyVal");
em.persist(entity);
em.flush();
em.clear();
entity = em.find(MyTestEntity.class, 1L);
Assertions.assertEquals("oldName", entity.getName());
entity.setName("newName");
Assertions.assertEquals("newName", entity.getName());
Assertions.assertEquals("lazyVal", entity.getLazy());
Assertions.assertEquals("newName", entity.getName());
}
The last assertion fails.