[OPENJPA-2962] Do not create a broker to obtain a class loader - #177
Open
rzo1 wants to merge 1 commit into
Open
Conversation
The four schema management methods each built a Broker through newBrokerImpl() only to call getClassLoader() on it. That loader was always null: BrokerImpl assigns it in initialize(), which newBrokerImpl() does not reach, so the broker answered a question it could not answer and was then dropped. They now pass the thread context class loader, which is the value initialize() would have assigned and which postCreationCallback() already passes for the same synchronizeMappings() calls. Closing the broker instead was not an option: close() runs free(), which dereferences a cache that an uninitialized broker has not got, so it throws. Nothing heavyweight leaked, though, since without initialize() there is no store manager, no connection and no registration with the factory; what the call cost was a finalizable object per invocation whose finalizer threw and was discarded. The only behaviour that changes is that a class loader now reaches MappingTool, so a custom openjpa.Sequence class resolves where it previously fell back to the bootstrap loader. The ticket also names dropPersistenceStrucuture and validatePersistenceStruture; cbb19f7 has since corrected both spellings.
solomax
approved these changes
Sep 3, 2026
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
The four schema management methods each built a
BrokerthroughnewBrokerImpl()only to callgetClassLoader()on it. That loader was alwaysnull:BrokerImplassigns it ininitialize(), whichnewBrokerImpl()never reaches, so the broker was asked a question it structurally could not answer and then dropped.They now pass the thread context class loader, which is the value
initialize()would have assigned, and whichpostCreationCallback()already passes for the samesynchronizeMappings()calls.Closing the broker instead was not available:
close()runsfree(), which dereferences a cache an uninitialized broker has not got, so afinally { broker.close(); }would have turned four working methods into four that throw. Nothing heavyweight leaked either — withoutinitialize()there is no store manager, no connection and no registration with the factory; the cost was a finalizable object per call whose finalizer threw and was discarded.The only behaviour that changes is that a class loader now reaches
MappingTool, so a customopenjpa.Sequenceclass resolves where it previously fell back to the bootstrap loader.Routing through
getClassResolverInstance()was considered and rejected: where OpenJPA's own loader differs from the context loader it returns aMultiClassLoaderthat is then re-resolved downstream against a different context class, producing a nesting an initialized broker would never produce.The ticket also names
dropPersistenceStrucutureandvalidatePersistenceStruture; cbb19f7 has since corrected both spellings.