diff --git a/maven-resolver-impl/src/main/java/org/eclipse/aether/internal/impl/filter/GroupIdRemoteRepositoryFilterSource.java b/maven-resolver-impl/src/main/java/org/eclipse/aether/internal/impl/filter/GroupIdRemoteRepositoryFilterSource.java index 844616bcf..3d6643876 100644 --- a/maven-resolver-impl/src/main/java/org/eclipse/aether/internal/impl/filter/GroupIdRemoteRepositoryFilterSource.java +++ b/maven-resolver-impl/src/main/java/org/eclipse/aether/internal/impl/filter/GroupIdRemoteRepositoryFilterSource.java @@ -33,6 +33,7 @@ import java.util.Set; import java.util.TreeSet; import java.util.concurrent.ConcurrentHashMap; +import java.util.concurrent.ConcurrentMap; import java.util.concurrent.atomic.AtomicBoolean; import java.util.stream.Collectors; import java.util.stream.Stream; @@ -154,23 +155,34 @@ public final class GroupIdRemoteRepositoryFilterSource extends RemoteRepositoryF private final PathProcessor pathProcessor; - private final ConcurrentHashMap rules; - - private final ConcurrentHashMap ruleFiles; - - private final ConcurrentHashMap> recordedRules; - - private final AtomicBoolean onShutdownHandlerRegistered; - @Inject public GroupIdRemoteRepositoryFilterSource( RepositorySystemLifecycle repositorySystemLifecycle, PathProcessor pathProcessor) { this.repositorySystemLifecycle = requireNonNull(repositorySystemLifecycle); this.pathProcessor = requireNonNull(pathProcessor); - this.rules = new ConcurrentHashMap<>(); - this.ruleFiles = new ConcurrentHashMap<>(); - this.recordedRules = new ConcurrentHashMap<>(); - this.onShutdownHandlerRegistered = new AtomicBoolean(false); + } + + @SuppressWarnings("unchecked") + private ConcurrentMap rules(RepositorySystemSession session) { + return (ConcurrentMap) + session.getData().computeIfAbsent(getClass().getName() + ".rules", ConcurrentHashMap::new); + } + + @SuppressWarnings("unchecked") + private ConcurrentMap ruleFiles(RepositorySystemSession session) { + return (ConcurrentMap) + session.getData().computeIfAbsent(getClass().getName() + ".ruleFiles", ConcurrentHashMap::new); + } + + @SuppressWarnings("unchecked") + private ConcurrentMap> recordedRules(RepositorySystemSession session) { + return (ConcurrentMap>) + session.getData().computeIfAbsent(getClass().getName() + ".recordedRules", ConcurrentHashMap::new); + } + + private AtomicBoolean onShutdownHandlerRegistered(RepositorySystemSession session) { + return (AtomicBoolean) session.getData() + .computeIfAbsent(getClass().getName() + ".onShutdownHandlerRegistered", AtomicBoolean::new); } @Override @@ -206,8 +218,8 @@ public RemoteRepositoryFilter getRemoteRepositoryFilter(RepositorySystemSession @Override public void postProcess(RepositorySystemSession session, List artifactResults) { if (isEnabled(session) && isRecord(session)) { - if (onShutdownHandlerRegistered.compareAndSet(false, true)) { - repositorySystemLifecycle.addOnSystemEndedHandler(this::saveRecordedLines); + if (onShutdownHandlerRegistered(session).compareAndSet(false, true)) { + repositorySystemLifecycle.addOnSystemEndedHandler(() -> saveRecordedLines(session)); } for (ArtifactResult artifactResult : artifactResults) { if (artifactResult.isResolved() && artifactResult.getRepository() instanceof RemoteRepository) { @@ -216,10 +228,11 @@ public void postProcess(RepositorySystemSession session, List ar ruleFile(session, remoteRepository); // populate it; needed for save String line = "=" + artifactResult.getArtifact().getGroupId(); RemoteRepository normalized = normalizeRemoteRepository(session, remoteRepository); - recordedRules + recordedRules(session) .computeIfAbsent(normalized, k -> new TreeSet<>()) .add(line); - rules.compute(normalized, (k, v) -> { + rules(session) + .compute(normalized, (k, v) -> { if (v == null || v == GroupTree.SENTINEL) { v = new GroupTree(""); } @@ -233,7 +246,7 @@ public void postProcess(RepositorySystemSession session, List ar } private Path ruleFile(RepositorySystemSession session, RemoteRepository remoteRepository) { - return ruleFiles.computeIfAbsent(normalizeRemoteRepository(session, remoteRepository), r -> getBasedir( + return ruleFiles(session).computeIfAbsent(normalizeRemoteRepository(session, remoteRepository), r -> getBasedir( session, LOCAL_REPO_PREFIX_DIR, CONFIG_PROP_BASEDIR, false) .resolve(GROUP_ID_FILE_PREFIX + RepositoryIdHelper.cachedIdToPathSegment(session).apply(remoteRepository) @@ -241,8 +254,9 @@ private Path ruleFile(RepositorySystemSession session, RemoteRepository remoteRe } private GroupTree cacheRules(RepositorySystemSession session, RemoteRepository remoteRepository) { - return rules.computeIfAbsent( - normalizeRemoteRepository(session, remoteRepository), r -> loadRepositoryRules(session, r)); + return rules(session) + .computeIfAbsent( + normalizeRemoteRepository(session, remoteRepository), r -> loadRepositoryRules(session, r)); } private GroupTree loadRepositoryRules(RepositorySystemSession session, RemoteRepository remoteRepository) { @@ -315,10 +329,10 @@ private boolean isRecord(RepositorySystemSession session) { /** * On-close handler that saves recorded rules, if any. */ - private void saveRecordedLines() { + private void saveRecordedLines(RepositorySystemSession session) { ArrayList exceptions = new ArrayList<>(); - for (Map.Entry entry : ruleFiles.entrySet()) { - Set recorded = recordedRules.get(entry.getKey()); + for (Map.Entry entry : ruleFiles(session).entrySet()) { + Set recorded = recordedRules(session).get(entry.getKey()); if (recorded != null && !recorded.isEmpty()) { try { ArrayList result = new ArrayList<>(); diff --git a/maven-resolver-impl/src/main/java/org/eclipse/aether/internal/impl/filter/PrefixesRemoteRepositoryFilterSource.java b/maven-resolver-impl/src/main/java/org/eclipse/aether/internal/impl/filter/PrefixesRemoteRepositoryFilterSource.java index 854560a59..9a4b2c301 100644 --- a/maven-resolver-impl/src/main/java/org/eclipse/aether/internal/impl/filter/PrefixesRemoteRepositoryFilterSource.java +++ b/maven-resolver-impl/src/main/java/org/eclipse/aether/internal/impl/filter/PrefixesRemoteRepositoryFilterSource.java @@ -22,10 +22,13 @@ import javax.inject.Named; import javax.inject.Singleton; +import java.net.URI; import java.nio.file.Files; import java.nio.file.Path; import java.util.Collections; +import java.util.List; import java.util.concurrent.ConcurrentHashMap; +import java.util.concurrent.ConcurrentMap; import java.util.function.Supplier; import org.eclipse.aether.DefaultRepositorySystemSession; @@ -40,6 +43,7 @@ import org.eclipse.aether.repository.RemoteRepository; import org.eclipse.aether.resolution.MetadataRequest; import org.eclipse.aether.resolution.MetadataResult; +import org.eclipse.aether.spi.connector.checksum.ChecksumAlgorithmFactory; import org.eclipse.aether.spi.connector.filter.RemoteRepositoryFilter; import org.eclipse.aether.spi.connector.layout.RepositoryLayout; import org.eclipse.aether.spi.connector.layout.RepositoryLayoutProvider; @@ -191,10 +195,6 @@ public final class PrefixesRemoteRepositoryFilterSource extends RemoteRepository private final RepositoryLayoutProvider repositoryLayoutProvider; - private final ConcurrentHashMap prefixes; - - private final ConcurrentHashMap layouts; - @Inject public PrefixesRemoteRepositoryFilterSource( Supplier metadataResolver, @@ -203,8 +203,18 @@ public PrefixesRemoteRepositoryFilterSource( this.metadataResolver = requireNonNull(metadataResolver); this.remoteRepositoryManager = requireNonNull(remoteRepositoryManager); this.repositoryLayoutProvider = requireNonNull(repositoryLayoutProvider); - this.prefixes = new ConcurrentHashMap<>(); - this.layouts = new ConcurrentHashMap<>(); + } + + @SuppressWarnings("unchecked") + private ConcurrentMap prefixes(RepositorySystemSession session) { + return (ConcurrentMap) + session.getData().computeIfAbsent(getClass().getName() + ".prefixes", ConcurrentHashMap::new); + } + + @SuppressWarnings("unchecked") + private ConcurrentMap layouts(RepositorySystemSession session) { + return (ConcurrentMap) + session.getData().computeIfAbsent(getClass().getName() + ".layouts", ConcurrentHashMap::new); } @Override @@ -238,25 +248,26 @@ public RemoteRepositoryFilter getRemoteRepositoryFilter(RepositorySystemSession } /** - * Caches layout instances for remote repository. In case of unknown layout it returns {@code null}. + * Caches layout instances for remote repository. In case of unknown layout it returns {@link #NOT_SUPPORTED}. * - * @return the layout instance of {@code null} if layout not supported. + * @return the layout instance or {@link #NOT_SUPPORTED} if layout not supported. */ private RepositoryLayout cacheLayout(RepositorySystemSession session, RemoteRepository remoteRepository) { - return layouts.computeIfAbsent(normalizeRemoteRepository(session, remoteRepository), r -> { + return layouts(session).computeIfAbsent(normalizeRemoteRepository(session, remoteRepository), r -> { try { return repositoryLayoutProvider.newRepositoryLayout(session, remoteRepository); } catch (NoRepositoryLayoutException e) { - return null; + return NOT_SUPPORTED; } }); } private PrefixTree cachePrefixTree( RepositorySystemSession session, Path basedir, RemoteRepository remoteRepository) { - return prefixes.computeIfAbsent( - normalizeRemoteRepository(session, remoteRepository), - r -> loadPrefixTree(session, basedir, remoteRepository)); + return prefixes(session) + .computeIfAbsent( + normalizeRemoteRepository(session, remoteRepository), + r -> loadPrefixTree(session, basedir, remoteRepository)); } private PrefixTree loadPrefixTree( @@ -339,16 +350,15 @@ private Path resolvePrefixesFromRemoteRepository( session, Collections.emptyList(), Collections.singletonList(remoteRepository), true) .get(0); // retrieve prefix as metadata from repository - MetadataRequest request = - new MetadataRequest(new DefaultMetadata(PREFIX_FILE_TYPE, Metadata.Nature.RELEASE_OR_SNAPSHOT)); - request.setRepository(prepared); - request.setDeleteLocalCopyIfMissing(true); - request.setFavorLocalRepository(true); MetadataResult result = mr.resolveMetadata( new DefaultRepositorySystemSession(session) .setTransferListener(null) .setConfigProperty(CONFIG_PROP_SKIPPED, Boolean.TRUE.toString()), - Collections.singleton(request)) + Collections.singleton(new MetadataRequest( + new DefaultMetadata(PREFIX_FILE_TYPE, Metadata.Nature.RELEASE_OR_SNAPSHOT)) + .setRepository(prepared) + .setDeleteLocalCopyIfMissing(true) + .setFavorLocalRepository(true))) .get(0); if (result.isResolved()) { return result.getMetadata().getPath(); @@ -371,7 +381,7 @@ private PrefixesFilter(RepositorySystemSession session, Path basedir) { @Override public Result acceptArtifact(RemoteRepository remoteRepository, Artifact artifact) { RepositoryLayout repositoryLayout = cacheLayout(session, remoteRepository); - if (repositoryLayout == null) { + if (repositoryLayout == NOT_SUPPORTED) { return new SimpleResult(true, "Unsupported layout: " + remoteRepository); } return acceptPrefix( @@ -382,7 +392,7 @@ public Result acceptArtifact(RemoteRepository remoteRepository, Artifact artifac @Override public Result acceptMetadata(RemoteRepository remoteRepository, Metadata metadata) { RepositoryLayout repositoryLayout = cacheLayout(session, remoteRepository); - if (repositoryLayout == null) { + if (repositoryLayout == NOT_SUPPORTED) { return new SimpleResult(true, "Unsupported layout: " + remoteRepository); } return acceptPrefix( @@ -392,7 +402,7 @@ public Result acceptMetadata(RemoteRepository remoteRepository, Metadata metadat private Result acceptPrefix(RemoteRepository repository, String path) { PrefixTree prefixTree = cachePrefixTree(session, basedir, repository); - if (PrefixTree.SENTINEL == prefixTree) { + if (prefixTree == PrefixTree.SENTINEL) { return NOT_PRESENT_RESULT; } if (prefixTree.acceptedPath(path)) { @@ -405,4 +415,36 @@ private Result acceptPrefix(RemoteRepository repository, String path) { private static final RemoteRepositoryFilter.Result NOT_PRESENT_RESULT = new SimpleResult(true, "Prefix file not present"); + + private static final RepositoryLayout NOT_SUPPORTED = new RepositoryLayout() { + @Override + public List getChecksumAlgorithmFactories() { + throw new UnsupportedOperationException(); + } + + @Override + public boolean hasChecksums(Artifact artifact) { + throw new UnsupportedOperationException(); + } + + @Override + public URI getLocation(Artifact artifact, boolean upload) { + throw new UnsupportedOperationException(); + } + + @Override + public URI getLocation(Metadata metadata, boolean upload) { + throw new UnsupportedOperationException(); + } + + @Override + public List getChecksumLocations(Artifact artifact, boolean upload, URI location) { + throw new UnsupportedOperationException(); + } + + @Override + public List getChecksumLocations(Metadata metadata, boolean upload, URI location) { + throw new UnsupportedOperationException(); + } + }; }