maven artifacts resolution: reading archive entries number as a validation check

GitOrigin-RevId: d8cbc1e5cb8501534524ea19c17e68b35a83bfaf
This commit is contained in:
Dmitriy.Panov
2022-09-01 14:18:20 +02:00
committed by intellij-monorepo-bot
parent 00e9e634a1
commit fb466bce52
3 changed files with 152 additions and 1 deletions

View File

@@ -161,7 +161,7 @@ public final class ArtifactRepositoryManager {
}
// setup session here
session.setLocalRepositoryManager(ourSystem.newLocalRepositoryManager(session, new LocalRepository(localRepositoryPath)));
session.setLocalRepositoryManager(new StrictLocalRepositoryManager(ourSystem.newLocalRepositoryManager(session, new LocalRepository(localRepositoryPath))));
session.setProxySelector(ourProxySelector);
session.setOffline(offline);
session.setReadOnly();

View File

@@ -0,0 +1,99 @@
// Copyright 2000-2022 JetBrains s.r.o. and contributors. Use of this source code is governed by the Apache 2.0 license.
package org.jetbrains.idea.maven.aether;
import org.eclipse.aether.RepositorySystemSession;
import org.eclipse.aether.artifact.Artifact;
import org.eclipse.aether.metadata.Metadata;
import org.eclipse.aether.repository.*;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.io.IOException;
import java.nio.file.Files;
import java.util.zip.ZipFile;
class StrictLocalRepositoryManager implements LocalRepositoryManager {
private static final Logger LOG = LoggerFactory.getLogger(StrictLocalRepositoryManager.class);
private static final boolean STRICT_VALIDATION = "true".equals(System.getProperty("org.jetbrains.idea.maven.aether.strictValidation"));
private final LocalRepositoryManager delegate;
StrictLocalRepositoryManager(LocalRepositoryManager delegate) {
this.delegate = delegate;
}
@Override
public LocalArtifactResult find(RepositorySystemSession session, LocalArtifactRequest request) {
var result = delegate.find(session, request);
// TODO: to be revised after IDEA-269182 is implemented
if (STRICT_VALIDATION &&
result.isAvailable() &&
(result.getFile().getName().endsWith(".jar") ||
result.getFile().getName().endsWith(".zip"))) {
validateArchive(result);
}
return result;
}
private static void validateArchive(LocalArtifactResult artifact) {
long entriesCount;
var file = artifact.getFile();
try (var zip = new ZipFile(file)) {
entriesCount = zip.size();
}
catch (IOException e) {
LOG.warn("Unable to read a number of entries in " + file, e);
entriesCount = 0;
}
if (entriesCount <= 0) {
LOG.warn(file + " is probably corrupted, deleting");
try {
Files.deleteIfExists(file.toPath());
}
catch (IOException e) {
throw new RuntimeException("Unable to delete " + file, e);
}
artifact.setFile(null);
artifact.setAvailable(false);
}
}
@Override
public LocalRepository getRepository() {
return delegate.getRepository();
}
@Override
public String getPathForLocalArtifact(Artifact artifact) {
return delegate.getPathForLocalArtifact(artifact);
}
@Override
public String getPathForRemoteArtifact(Artifact artifact, RemoteRepository repository, String context) {
return delegate.getPathForRemoteArtifact(artifact, repository, context);
}
@Override
public String getPathForLocalMetadata(Metadata metadata) {
return delegate.getPathForLocalMetadata(metadata);
}
@Override
public String getPathForRemoteMetadata(Metadata metadata, RemoteRepository repository, String context) {
return delegate.getPathForRemoteMetadata(metadata, repository, context);
}
@Override
public void add(RepositorySystemSession session, LocalArtifactRegistration request) {
delegate.add(session, request);
}
@Override
public LocalMetadataResult find(RepositorySystemSession session, LocalMetadataRequest request) {
return delegate.find(session, request);
}
@Override
public void add(RepositorySystemSession session, LocalMetadataRegistration request) {
delegate.add(session, request);
}
}

View File

@@ -31,11 +31,13 @@ import java.util.Collections;
import java.util.List;
import java.util.stream.Collectors;
import java.util.stream.Stream;
import java.util.zip.ZipFile;
public class ArtifactRepositoryManagerTest extends UsefulTestCase {
private static final RemoteRepository mavenLocal;
static {
System.setProperty("org.jetbrains.idea.maven.aether.strictValidation", "true");
File mavenLocalDir = new File(SystemProperties.getUserHome(), ".m2/repository");
mavenLocal = new RemoteRepository
.Builder("mavenLocal", "default", "file://" + mavenLocalDir.getAbsolutePath())
@@ -114,6 +116,56 @@ public class ArtifactRepositoryManagerTest extends UsefulTestCase {
}
}
private Path resolveSomeSingleJar() throws Exception {
myRepositoryManager.resolveDependency(
"org.jetbrains", "annotations", "20.1.0",
false, Collections.emptyList()
);
try (var stream = Files.walk(localRepository.toPath())) {
var resolvedJars = stream.filter(file -> file.getFileName().toString().endsWith(".jar")).collect(Collectors.toList());
assertSize(1, resolvedJars);
var resolvedJar = resolvedJars.get(0);
try (var zip = new ZipFile(resolvedJar.toFile())) {
assert zip.size() > 0;
}
return resolvedJar;
}
}
public void testResolutionForEmptyJar() throws Exception {
var resolvedJar = resolveSomeSingleJar();
Files.delete(resolvedJar);
Files.createFile(resolvedJar);
assert Files.size(resolvedJar) == 0;
resolveSomeSingleJar();
}
public void testResolutionForSymbolicLinkToEmptyJar() throws Exception {
var resolvedJar = resolveSomeSingleJar();
Files.delete(resolvedJar);
var brokenTarget = Files.createTempFile("empty", ".jar");
assert Files.size(brokenTarget) == 0;
Files.createSymbolicLink(resolvedJar, brokenTarget);
resolveSomeSingleJar();
}
public void testResolutionForMalformedJar() throws Exception {
var resolvedJar = resolveSomeSingleJar();
Files.delete(resolvedJar);
Files.createFile(resolvedJar);
Files.writeString(resolvedJar, "malformed jar content");
resolveSomeSingleJar();
}
public void testResolutionForSymbolicLinkToMalformedJar() throws Exception {
var resolvedJar = resolveSomeSingleJar();
Files.delete(resolvedJar);
var brokenTarget = Files.createTempFile("malformed", ".jar");
Files.writeString(brokenTarget, "malformed jar content");
Files.createSymbolicLink(resolvedJar, brokenTarget);
resolveSomeSingleJar();
}
private static void assertCoordinates(Artifact artifact, String groupId, String artifactId, String version) {
assertEquals(groupId, artifact.getGroupId());
assertEquals(artifactId, artifact.getArtifactId());