[NO ISSUE][LIC] Add ability to exclude specific shadowed artifacts
Change-Id: Iaa63954b8c328862f0e93c9c1f9fc32cc13e822a
Reviewed-on: https://asterix-gerrit.ics.uci.edu/c/asterixdb/+/17317
Reviewed-by: Michael Blow <mblow@apache.org>
Reviewed-by: Murtadha Hubail <mhubail@apache.org>
Tested-by: Michael Blow <mblow@apache.org>
diff --git a/hyracks-fullstack/hyracks/hyracks-maven-plugins/license-automation-plugin/src/main/java/org/apache/hyracks/maven/license/GenerateFileMojo.java b/hyracks-fullstack/hyracks/hyracks-maven-plugins/license-automation-plugin/src/main/java/org/apache/hyracks/maven/license/GenerateFileMojo.java
index 8edc1b2..297160e 100644
--- a/hyracks-fullstack/hyracks/hyracks-maven-plugins/license-automation-plugin/src/main/java/org/apache/hyracks/maven/license/GenerateFileMojo.java
+++ b/hyracks-fullstack/hyracks/hyracks-maven-plugins/license-automation-plugin/src/main/java/org/apache/hyracks/maven/license/GenerateFileMojo.java
@@ -20,11 +20,13 @@
import static org.apache.hyracks.maven.license.GenerateFileMojo.EmbeddedArtifact.LICENSE;
import static org.apache.hyracks.maven.license.GenerateFileMojo.EmbeddedArtifact.NOTICE;
+import static org.apache.hyracks.maven.license.LicenseUtil.toGav;
import static org.apache.hyracks.maven.license.ProjectFlag.ALTERNATE_LICENSE_FILE;
import static org.apache.hyracks.maven.license.ProjectFlag.ALTERNATE_NOTICE_FILE;
import static org.apache.hyracks.maven.license.ProjectFlag.IGNORE_MISSING_EMBEDDED_LICENSE;
import static org.apache.hyracks.maven.license.ProjectFlag.IGNORE_MISSING_EMBEDDED_NOTICE;
import static org.apache.hyracks.maven.license.ProjectFlag.IGNORE_NOTICE_OVERRIDE;
+import static org.apache.hyracks.maven.license.ProjectFlag.IGNORE_SHADOWED_DEPENDENCIES;
import static org.apache.hyracks.maven.license.ProjectFlag.ON_MULTIPLE_EMBEDDED_LICENSE;
import static org.apache.hyracks.maven.license.ProjectFlag.ON_MULTIPLE_EMBEDDED_NOTICE;
@@ -36,6 +38,7 @@
import java.io.Writer;
import java.nio.charset.StandardCharsets;
import java.util.ArrayList;
+import java.util.Collections;
import java.util.Comparator;
import java.util.Enumeration;
import java.util.HashMap;
@@ -55,8 +58,10 @@
import java.util.jar.JarEntry;
import java.util.jar.JarFile;
import java.util.regex.Pattern;
+import java.util.stream.Collectors;
import org.apache.commons.io.IOUtils;
+import org.apache.commons.lang3.ArrayUtils;
import org.apache.commons.lang3.StringUtils;
import org.apache.commons.lang3.tuple.Pair;
import org.apache.hyracks.maven.license.freemarker.IndentDirective;
@@ -527,39 +532,50 @@
Set<MavenProject> projects = new TreeSet<>(Comparator.comparing(MavenProject::getId));
projects.addAll(dependencyLicenseMap.keySet());
for (MavenProject p : projects) {
- boolean finished = false;
File artifactFile = p.getArtifact().getFile();
if (!artifactFile.exists()) {
throw new MojoExecutionException("Artifact file " + artifactFile + " does not exist!");
} else if (!artifactFile.getName().endsWith(".jar")) {
getLog().info("Skipping unknown artifact file type: " + artifactFile);
- finished = true;
+ continue;
}
- if (!finished) {
- try (JarFile jarFile = new JarFile(artifactFile)) {
- SortedMap<String, JarEntry> matches = gatherMatchingEntries(jarFile,
- entry -> entry.getName().matches("(.*/|^)" + "pom\\.properties"));
- if (!matches.isEmpty()) {
- for (JarEntry entry : matches.values()) {
- Properties props = new Properties();
- props.load(jarFile.getInputStream(entry));
- String groupId = props.getProperty("groupId");
- String artifactId = props.getProperty("artifactId");
- String version = props.getProperty("version");
- String gav = groupId + ":" + artifactId + ":" + version;
- if (!dependencyGavMap.containsKey(gav)) {
- getLog().info("adding " + gav + " (shadowed from " + p.getId() + ")");
- ArtifactHandler handler = new DefaultArtifactHandler("jar");
- String[] gavParts = StringUtils.split(gav, ':');
- Artifact manualDep = new DefaultArtifact(gavParts[0], gavParts[1], gavParts[2],
- Artifact.SCOPE_COMPILE, "jar", null, handler);
- processArtifact(manualDep, dependencyLicenseMap, dependencyGavMap, true);
+ @SuppressWarnings("unchecked")
+ List<String[]> specs = (List<String[]>) getProjectFlags()
+ .getOrDefault(Pair.of(toGav(p), IGNORE_SHADOWED_DEPENDENCIES), Collections.emptyList());
+ getLog().debug(p + " has " + IGNORE_SHADOWED_DEPENDENCIES.propName() + " set to "
+ + specs.stream().map(ArrayUtils::toString).collect(Collectors.joining(",")));
+ try (JarFile jarFile = new JarFile(artifactFile)) {
+ SortedMap<String, JarEntry> matches = gatherMatchingEntries(jarFile,
+ entry -> entry.getName().matches("(.*/|^)" + "pom\\.properties"));
+ if (!matches.isEmpty()) {
+ jarEntryLoop: for (JarEntry entry : matches.values()) {
+ Properties props = new Properties();
+ props.load(jarFile.getInputStream(entry));
+ String groupId = props.getProperty("groupId");
+ String artifactId = props.getProperty("artifactId");
+ String version = props.getProperty("version");
+ String gav = groupId + ":" + artifactId + ":" + version;
+ if (!dependencyGavMap.containsKey(gav)) {
+ for (String[] ignoreSpec : specs) {
+ if ((ignoreSpec[0].equals(groupId) || ignoreSpec[0].equals("*"))
+ && (ignoreSpec[1].equals(artifactId) || ignoreSpec[1].equals("*"))
+ && (ignoreSpec[2].equals(version) || ignoreSpec[2].equals("*"))) {
+ getLog().info("skipping " + gav + " (shadowed from " + p.getId()
+ + "), as it matches " + IGNORE_SHADOWED_DEPENDENCIES.propName());
+ continue jarEntryLoop;
+ }
}
+ getLog().info("adding " + gav + " (shadowed from " + p.getId() + ")");
+ ArtifactHandler handler = new DefaultArtifactHandler("jar");
+ String[] gavParts = StringUtils.split(gav, ':');
+ Artifact manualDep = new DefaultArtifact(gavParts[0], gavParts[1], gavParts[2],
+ Artifact.SCOPE_COMPILE, "jar", null, handler);
+ processArtifact(manualDep, dependencyLicenseMap, dependencyGavMap, true);
}
}
- } catch (IOException e) {
- throw new MojoExecutionException(e);
}
+ } catch (IOException e) {
+ throw new MojoExecutionException(e);
}
}
}
diff --git a/hyracks-fullstack/hyracks/hyracks-maven-plugins/license-automation-plugin/src/main/java/org/apache/hyracks/maven/license/LicenseMojo.java b/hyracks-fullstack/hyracks/hyracks-maven-plugins/license-automation-plugin/src/main/java/org/apache/hyracks/maven/license/LicenseMojo.java
index 73cc695..3b5fde6 100644
--- a/hyracks-fullstack/hyracks/hyracks-maven-plugins/license-automation-plugin/src/main/java/org/apache/hyracks/maven/license/LicenseMojo.java
+++ b/hyracks-fullstack/hyracks/hyracks-maven-plugins/license-automation-plugin/src/main/java/org/apache/hyracks/maven/license/LicenseMojo.java
@@ -407,6 +407,7 @@
protected void gatherProjectDependencies(MavenProject project,
Map<MavenProject, List<Pair<String, String>>> dependencyLicenseMap,
Map<String, MavenProject> dependencyGavMap) throws ProjectBuildingException, MojoExecutionException {
+ getLog().debug("+gatherProjectDependencies " + toGav(project));
final Set<Artifact> dependencyArtifacts = project.getArtifacts();
if (dependencyArtifacts != null) {
for (Artifact depArtifact : dependencyArtifacts) {
@@ -440,6 +441,7 @@
Map<String, MavenProject> dependencyGavMap, boolean shadowed) throws ProjectBuildingException {
if (!excludedScopes.contains(depArtifact.getScope())) {
MavenProject dep = resolveDependency(depArtifact);
+ getLog().debug("+processArtifact " + toGav(dep));
if (!depArtifact.isResolved()) {
ArtifactResolutionRequest arr = new ArtifactResolutionRequest();
arr.setLocalRepository(localRepository);
@@ -476,6 +478,10 @@
} catch (ProjectBuildingException e) {
throw new ProjectBuildingException(key, "Error creating dependent artifacts", e);
}
+ // override the gav in the built dependency with the gavs in depObj
+ depProj.setGroupId(depObj.getGroupId());
+ depProj.setArtifactId(depObj.getArtifactId());
+ depProj.setVersion(depObj.getVersion());
Model supplement = supplementModels
.get(SupplementalModelHelper.generateSupplementMapKey(depObj.getGroupId(), depObj.getArtifactId()));
diff --git a/hyracks-fullstack/hyracks/hyracks-maven-plugins/license-automation-plugin/src/main/java/org/apache/hyracks/maven/license/ProjectFlag.java b/hyracks-fullstack/hyracks/hyracks-maven-plugins/license-automation-plugin/src/main/java/org/apache/hyracks/maven/license/ProjectFlag.java
index d61dde1..eb46041 100644
--- a/hyracks-fullstack/hyracks/hyracks-maven-plugins/license-automation-plugin/src/main/java/org/apache/hyracks/maven/license/ProjectFlag.java
+++ b/hyracks-fullstack/hyracks/hyracks-maven-plugins/license-automation-plugin/src/main/java/org/apache/hyracks/maven/license/ProjectFlag.java
@@ -20,9 +20,12 @@
import static org.apache.hyracks.maven.license.LicenseUtil.toGav;
+import java.util.ArrayList;
import java.util.Arrays;
+import java.util.List;
import java.util.Properties;
+import org.apache.commons.lang3.ArrayUtils;
import org.apache.commons.lang3.StringUtils;
import org.apache.commons.lang3.tuple.Pair;
import org.apache.hyracks.util.StringUtil;
@@ -36,13 +39,15 @@
ON_MULTIPLE_EMBEDDED_LICENSE,
ON_MULTIPLE_EMBEDDED_NOTICE,
ALTERNATE_LICENSE_FILE,
- ALTERNATE_NOTICE_FILE;
+ ALTERNATE_NOTICE_FILE,
+ IGNORE_SHADOWED_DEPENDENCIES;
String propName() {
return "license." + StringUtil.toCamelCase(name());
}
void visit(MavenProject depObj, Properties properties, LicenseMojo licenseMojo) {
+ licenseMojo.getLog().debug("+" + propName() + ".visit: " + toGav(depObj));
String value = properties.getProperty(propName());
if (value == null) {
return;
@@ -59,12 +64,34 @@
+ " for " + toGav(depObj));
}
break;
+ case IGNORE_SHADOWED_DEPENDENCIES:
+ // <license.ignoreShadowedDependencies>*:com.couchbase.client:core-io:*</license.ignoreShadowedDependencies>
+ List<String[]> specsList = new ArrayList<>();
+ for (String spec : StringUtils.split(value, ",")) {
+ boolean found = false;
+ String[] specSplit = StringUtils.split(spec, ":");
+ if (specSplit.length != 4) {
+ throw new IllegalArgumentException(spec);
+ }
+ if (specSplit[0].equals(depObj.getVersion()) || specSplit[0].equals("*")) {
+ specsList.add(ArrayUtils.subarray(specSplit, 1, specSplit.length));
+ found = true;
+ }
+ if (!found) {
+ licenseMojo.getLog().info(propName() + " defined on versions that *do not* match: "
+ + specSplit[0] + " for " + toGav(depObj));
+ }
+ }
+ if (!specsList.isEmpty()) {
+ licenseMojo.getProjectFlags().put(Pair.of(toGav(depObj), this), specsList);
+ }
+ break;
case ALTERNATE_LICENSE_FILE:
case ALTERNATE_NOTICE_FILE:
case ON_MULTIPLE_EMBEDDED_NOTICE:
case ON_MULTIPLE_EMBEDDED_LICENSE:
- boolean found = false;
for (String spec : StringUtils.split(value, ",")) {
+ boolean found = false;
String[] specSplit = StringUtils.split(spec, ":");
if (specSplit.length != 2) {
throw new IllegalArgumentException(spec);
@@ -73,10 +100,10 @@
licenseMojo.getProjectFlags().put(Pair.of(toGav(depObj), this), specSplit[1]);
found = true;
}
- }
- if (!found) {
- licenseMojo.getLog().info(propName() + " defined on versions that *do not* match: " + value
- + " for " + toGav(depObj));
+ if (!found) {
+ licenseMojo.getLog().info(propName() + " defined on versions that *do not* match: " + value
+ + " for " + toGav(depObj));
+ }
}
break;
default: