diff --git a/src/main/java/eu/fasten/vulnerabilityproducer/utils/mappers/VersionRanger.java b/src/main/java/eu/fasten/vulnerabilityproducer/utils/mappers/VersionRanger.java index 17b121e..ce50bd2 100644 --- a/src/main/java/eu/fasten/vulnerabilityproducer/utils/mappers/VersionRanger.java +++ b/src/main/java/eu/fasten/vulnerabilityproducer/utils/mappers/VersionRanger.java @@ -19,6 +19,8 @@ package eu.fasten.vulnerabilityproducer.utils.mappers; import com.google.common.collect.Lists; +import com.google.common.collect.Sets; + import eu.fasten.vulnerabilityproducer.utils.Vulnerability; import eu.fasten.vulnerabilityproducer.utils.connections.JavaHttpClient; import org.apache.commons.lang3.tuple.ImmutablePair; @@ -341,18 +343,20 @@ public List getVulnerableVersionsYAML(List encodedRangeVersions, public List getVulnerableVersionsJSON(String encodedRangeVersions, List allVersions) { var allParsedVersions = allVersions.stream().map(ComparableVersion::new).collect(Collectors.toList()); - var vulnerableVersions = Lists.newArrayList(allVersions); + Set vulnerableVersions = Sets.newLinkedHashSet(allVersions); + + List versionIndicesToRemove = Lists.newArrayList(); + List versionIndicesToKeep = Lists.newArrayList(); for (String range : encodedRangeVersions.split(",")) { String operator = range.strip().split("[0-9]")[0].strip(); var versionFromRange = range.strip().substring(operator.length()).strip(); var parsedVersionFromRange = new ComparableVersion(versionFromRange); - List versionIndicesToRemove = Lists.newArrayList(); switch (operator) { case "==": case "=": { - versionIndicesToRemove = findUnequalVersions(parsedVersionFromRange, allParsedVersions); + versionIndicesToKeep.addAll(findEqualVersions(parsedVersionFromRange, allParsedVersions)); break; } case "<=": { @@ -374,10 +378,14 @@ public List getVulnerableVersionsJSON(String encodedRangeVersions, List< default: logger.warn("getVulnerableVersionsJSON: unknown operator " + operator); } - versionIndicesToRemove.stream().map(allVersions::get).forEach(vulnerableVersions::remove); + // If we only have some specific versions in the spec, only those should be kept. + if(versionIndicesToRemove.size() == 0 && versionIndicesToKeep.size() > 0) { + vulnerableVersions.clear(); + } + versionIndicesToRemove.stream().map(allVersions::get).forEach(vulnerableVersions::remove); + versionIndicesToKeep.stream().map(allVersions::get).forEach(vulnerableVersions::add); } - - return vulnerableVersions; + return vulnerableVersions.stream().collect(Collectors.toList()); } private List findUnequalVersions(ComparableVersion v, List allVersions) { diff --git a/src/test/java/eu/fasten/vulnerabilityproducer/mappers/VersionRangerTest.java b/src/test/java/eu/fasten/vulnerabilityproducer/mappers/VersionRangerTest.java index 1605594..2c31e4f 100644 --- a/src/test/java/eu/fasten/vulnerabilityproducer/mappers/VersionRangerTest.java +++ b/src/test/java/eu/fasten/vulnerabilityproducer/mappers/VersionRangerTest.java @@ -198,6 +198,20 @@ public void testVulnerableVersionsJSON_Equal() { assertEquals(vvCheck, vv); } + @Test + public void testVulnerableVersionsJSON_EqualTwice() { + when(clientMock.sendGet("https://pypi.org/pypi/mock/json")).thenReturn(pythonPgk); + + var allVersions = vr.getVersions("pkg:pypi/mock"); + String encodedRange = "==1.0.1rc,=2.0"; + List vv = vr.getVulnerableVersionsJSON(encodedRange, allVersions); + List vvCheck = new ArrayList<>(); + vvCheck.add("1.0.1rc"); + vvCheck.add("2.0"); + + assertEquals(vvCheck, vv); + } + @Test public void testVulnerableVersionsJSON_SmallerThanOrEqual() { when(clientMock.sendGet("https://pypi.org/pypi/mock/json")).thenReturn(pythonPgk); @@ -296,6 +310,19 @@ public void testVulnerableVersionJSON_Compound2() { assertEquals(vvCheck, vv); } + @Test + public void testVulnerableVersionJSON_Compound3() { + when(clientMock.sendGet("https://pypi.org/pypi/mock/json")).thenReturn(pythonPgk); + List allVersions = vr.getVersions("pkg:pypi/mock"); + String encodedRange = ">1.0.2, <=2.0, =2.0.2"; + List vv = vr.getVulnerableVersionsJSON(encodedRange, allVersions); + List vvCheck = new ArrayList<>(); + vvCheck.add("1.0.9"); + vvCheck.add("2.0"); + vvCheck.add("2.0.2"); + assertEquals(vvCheck, vv); + } + @Test public void testVulnerableVersionsYAMLPartOne() { when(clientMock.sendGet("https://pypi.org/pypi/mock/json")).thenReturn(pythonPgk);