Skip to content

InfoByFqn.removeAllSources: rebuild the multi-source-set lists instead of removeIf - #210

Open
tomtourwe wants to merge 1 commit into
develfrom
fix/remove-all-sources-immutable-lists
Open

tomtourwe wants to merge 1 commit into
develfrom
fix/remove-all-sources-immutable-lists

Conversation

@tomtourwe

Copy link
Copy Markdown

Problem

Dropping the project hibernate-orm on the refactor server logs:

WARN ProjectServiceImpl - Releasing the old model's inspector of hibernate-orm--main failed
java.lang.UnsupportedOperationException
    at java.util.ImmutableCollections$AbstractImmutableCollection.removeIf
    at io.codelaser.maddi.inspection.resource.InfoByFqn.lambda$removeAllSources$0(InfoByFqn.java:83)
    at io.codelaser.maddi.inspection.openjdk.JavaInspectorImpl.invalidateAllSources(JavaInspectorImpl.java:221)
    at io.codelaser.jfocus.refactor.service.service.ProjectServiceImpl.releaseInspector(ProjectServiceImpl.java:1203)

multiTypeByFqn holds the names defined in more than one source set. Its lists are built with List.of and Stream.toList(), which cannot be changed, so list.removeIf(...) in removeAllSources() throws. removeType() in the same class already rebuilds these lists for this reason.

Consequence: invalidateAllSources() stops at its first line, so the javac file managers and the shared jar archives it should close stay open. This happens on every drop and every reload-after-write of a project where a class name exists in several source sets (hibernate-orm: 60 source sets). Results are not affected: the server builds a new inspector for the next model.

Change

// before
multiTypeByFqn.values().forEach(list -> list.removeIf(InfoByFqn::isSourceType));
// after
multiTypeByFqn.replaceAll((fqn, list) -> list.stream().filter(ti -> !isSourceType(ti)).toList());

The next line, multiTypeByFqn.values().removeIf(List::isEmpty), then drops the names left without a type.

Test

TestRemoveAllSourcesWithOneNameInTwoSourceSets: a.Helper is defined in the source sets core/main and core/test, and lib.Thing comes from a library jar. After removeAllSources() no copy of a.Helper is left and lib.Thing is still registered.

  • Before the change: fails with UnsupportedOperationException.
  • After: passes. maddi-inspection-openjdk test suite: 175 tests, 0 failures, 1 skipped (as before).

@github-actions

github-actions Bot commented Nov 13, 2026 •

Copy link
Copy Markdown

All contributors have signed the CLA ✍️ ✅
Posted by the CLA Assistant Lite bot.

…d of removeIf

A name defined in several source sets is registered with a list built by
List.of or Stream.toList(); those lists cannot be changed, so removeIf threw
UnsupportedOperationException. JavaInspectorImpl.invalidateAllSources() stopped
at its first line and left the javac file managers and shared jar archives
open. Seen on the refactor server when dropping hibernate-orm (60 source sets).

Test: TestRemoveAllSourcesWithOneNameInTwoSourceSets.
@tomtourwe
tomtourwe force-pushed the fix/remove-all-sources-immutable-lists branch from f3ef25f to cbbc5aa Compare November 13, 2026 17:12
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant