Add verification metadata for dependencies (#88814)

Removing the custom dependency checksum functionality in favor of Gradle build-in dependency verification support. 

- Use sha256 in favor of sha1 as sha1 is not considered safe these days.

Closes https://github.com/elastic/elasticsearch/issues/69736
This commit is contained in:
Rene Groeschke 2022-08-04 09:51:16 +02:00 committed by GitHub
parent 1c56d68f49
commit 3909b5eaf9
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
348 changed files with 3642 additions and 734 deletions

View file

@ -63,6 +63,38 @@ E.g. [configuration-cache support](https://github.com/elastic/elasticsearch/issu
There are a few guidelines to follow that should make your life easier to make changes to the elasticsearch build.
Please add a member of the `es-delivery` team as a reviewer if you're making non-trivial changes to the build.
#### Adding or updating a dependency
We rely on [Gradle dependency verification](https://docs.gradle.org/current/userguide/dependency_verification.html) to mitigate the security risks and avoid integrating compromised dependencies.
This requires to have third party dependencies and their checksums listed in `gradle/verification-metadata.xml`.
For updated or newly added dependencies you need to add an entry to this verification file or update the existing one:
```
<component group="asm" name="asm" version="3.1">
<artifact name="asm-3.1.jar">
<sha256 value="333ff5369043975b7e031b8b27206937441854738e038c1f47f98d072a20437a" origin="official site"/>
</artifact>
</component>
```
You can also automate the generation of this entry by running your build using the `--write-verification-metadata` commandline option:
```
>./gradlew --write-verification-metadata sha256 precommit
```
The `--write-verification-metadata` Gradle option is generally able to resolve reachable configurations,
but we use detached configurations for a certain set of plugins and tasks. Therefore, please ensure you run this option with a task that
uses the changed dependencies. In most cases, `precommit` or `check` are good candidates.
We prefer sha256 checksums as md5 and sha1 are not considered safe anymore these days. The generated entry
will have the `origin` attribute been set to `Generated by Gradle`.
>A manual confirmation of the Gradle generated checksums is currently not mandatory.
>If you want to add a level of verification you can manually confirm the checksum (e.g by looking it up on the website of the library)
>Please replace the content of the `origin` attribute by `official site` in that case.
>
#### Custom Plugin and Task implementations
Build logic that is used across multiple subprojects should considered to be moved into a Gradle plugin with according Gradle task implmentation.

View file

@ -34,9 +34,6 @@ public class DependencyLicensesPrecommitPlugin extends PrecommitPlugin {
runtimeClasspath.fileCollection(dependency -> dependency instanceof ProjectDependency == false).minus(compileOnly)
);
});
// we also create the updateShas helper task that is associated with dependencyLicenses
project.getTasks().register("updateShas", UpdateShasTask.class, t -> t.setParentTask(dependencyLicenses));
return dependencyLicenses;
}
}

View file

@ -7,7 +7,6 @@
*/
package org.elasticsearch.gradle.internal.precommit;
import org.apache.commons.codec.binary.Hex;
import org.elasticsearch.gradle.internal.precommit.LicenseAnalyzer.LicenseInfo;
import org.gradle.api.DefaultTask;
import org.gradle.api.GradleException;
@ -23,30 +22,21 @@ import org.gradle.api.provider.Provider;
import org.gradle.api.tasks.Input;
import org.gradle.api.tasks.InputDirectory;
import org.gradle.api.tasks.InputFiles;
import org.gradle.api.tasks.Internal;
import org.gradle.api.tasks.Optional;
import org.gradle.api.tasks.OutputDirectory;
import org.gradle.api.tasks.TaskAction;
import java.io.File;
import java.io.IOException;
import java.nio.charset.StandardCharsets;
import java.nio.file.Files;
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.HashMap;
import java.util.HashSet;
import java.util.LinkedHashMap;
import java.util.LinkedHashSet;
import java.util.List;
import java.util.Locale;
import java.util.Map;
import java.util.Set;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import java.util.stream.Collectors;
import javax.inject.Inject;
@ -193,7 +183,7 @@ public class DependencyLicensesTask extends DefaultTask {
}
@TaskAction
public void checkDependencies() throws IOException, NoSuchAlgorithmException {
public void checkDependencies() {
if (dependencies == null) {
throw new GradleException("No dependencies variable defined.");
}
@ -214,12 +204,9 @@ public class DependencyLicensesTask extends DefaultTask {
Map<String, Boolean> licenses = new HashMap<>();
Map<String, Boolean> notices = new HashMap<>();
Map<String, Boolean> sources = new HashMap<>();
Set<File> shaFiles = new HashSet<>();
for (File file : licensesDirAsFile.listFiles()) {
String name = file.getName();
if (name.endsWith(SHA_EXTENSION)) {
shaFiles.add(file);
} else if (name.endsWith("-LICENSE") || name.endsWith("-LICENSE.txt")) {
if (name.endsWith("-LICENSE") || name.endsWith("-LICENSE.txt")) {
// TODO: why do we support suffix of LICENSE *and* LICENSE.txt??
licenses.put(name, false);
} else if (name.contains("-NOTICE") || name.contains("-NOTICE.txt")) {
@ -233,18 +220,13 @@ public class DependencyLicensesTask extends DefaultTask {
notices.keySet().removeAll(ignoreFiles);
sources.keySet().removeAll(ignoreFiles);
checkDependencies(licenses, notices, sources, shaFiles);
checkDependencies(licenses, notices, sources);
licenses.forEach((item, exists) -> failIfAnyMissing(item, exists, "license"));
notices.forEach((item, exists) -> failIfAnyMissing(item, exists, "notice"));
sources.forEach((item, exists) -> failIfAnyMissing(item, exists, "sources"));
if (shaFiles.isEmpty() == false) {
throw new GradleException("Unused sha files found: \n" + joinFilenames(shaFiles));
}
}
// This is just a marker output folder to allow this task being up-to-date.
@ -261,18 +243,10 @@ public class DependencyLicensesTask extends DefaultTask {
}
}
private void checkDependencies(
Map<String, Boolean> licenses,
Map<String, Boolean> notices,
Map<String, Boolean> sources,
Set<File> shaFiles
) throws NoSuchAlgorithmException, IOException {
private void checkDependencies(Map<String, Boolean> licenses, Map<String, Boolean> notices, Map<String, Boolean> sources) {
for (File dependency : dependencies) {
String jarName = dependency.getName();
String depName = regex.matcher(jarName).replaceFirst("");
validateSha(shaFiles, dependency, jarName, depName);
String dependencyName = getDependencyName(mappings, depName);
logger.info("mapped dependency name {} to {} for license/notice check", depName, dependencyName);
checkFile(dependencyName, jarName, licenses, "LICENSE");
@ -286,24 +260,6 @@ public class DependencyLicensesTask extends DefaultTask {
}
}
private void validateSha(Set<File> shaFiles, File dependency, String jarName, String depName) throws NoSuchAlgorithmException,
IOException {
if (ignoreShas.contains(depName)) {
// local deps should not have sha files!
if (getShaFile(jarName).exists()) {
throw new GradleException("SHA file " + getShaFile(jarName) + " exists for ignored dependency " + depName);
}
} else {
logger.info("Checking sha for {}", jarName);
checkSha(dependency, jarName, shaFiles);
}
}
private String joinFilenames(Set<File> shaFiles) {
List<String> names = shaFiles.stream().map(File::getName).collect(Collectors.toList());
return String.join("\n", names);
}
public static String getDependencyName(Map<String, String> mappings, String dependencyName) {
// order is the same for keys and values iteration since we use a linked hashmap
List<String> mapped = new ArrayList<>(mappings.values());
@ -319,30 +275,6 @@ public class DependencyLicensesTask extends DefaultTask {
return dependencyName;
}
private void checkSha(File jar, String jarName, Set<File> shaFiles) throws NoSuchAlgorithmException, IOException {
File shaFile = getShaFile(jarName);
if (shaFile.exists() == false) {
throw new GradleException("Missing SHA for " + jarName + ". Run \"gradle updateSHAs\" to create them");
}
// TODO: shouldn't have to trim, sha files should not have trailing newline
byte[] fileBytes = Files.readAllBytes(shaFile.toPath());
String expectedSha = new String(fileBytes, StandardCharsets.UTF_8).trim();
String sha = getSha1(jar);
if (expectedSha.equals(sha) == false) {
final String exceptionMessage = String.format(Locale.ROOT, """
SHA has changed! Expected %s for %s but got %s.
This usually indicates a corrupt dependency cache or artifacts changed upstream.
Either wipe your cache, fix the upstream artifact, or delete %s and run updateShas
""", expectedSha, jarName, sha, shaFile);
throw new GradleException(exceptionMessage);
}
shaFiles.remove(shaFile);
}
private void checkFile(String name, String jarName, Map<String, Boolean> counters, String type) {
String fileName = getFileName(name, counters, type);
@ -375,27 +307,4 @@ public class DependencyLicensesTask extends DefaultTask {
return new LinkedHashMap<>(mappings);
}
File getShaFile(String jarName) {
return new File(licensesDir.get().getAsFile(), jarName + SHA_EXTENSION);
}
@Internal
Set<File> getShaFiles() {
File licenseDirAsFile = licensesDir.get().getAsFile();
File[] array = licenseDirAsFile.listFiles();
if (array == null) {
throw new GradleException("\"" + licenseDirAsFile.getPath() + "\" isn't a valid directory");
}
return Arrays.stream(array).filter(file -> file.getName().endsWith(SHA_EXTENSION)).collect(Collectors.toSet());
}
String getSha1(File file) throws IOException, NoSuchAlgorithmException {
byte[] bytes = Files.readAllBytes(file.toPath());
MessageDigest digest = MessageDigest.getInstance("SHA-1");
char[] encoded = Hex.encodeHex(digest.digest(bytes));
return String.copyValueOf(encoded);
}
}

View file

@ -1,78 +0,0 @@
/*
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
* or more contributor license agreements. Licensed under the Elastic License
* 2.0 and the Server Side Public License, v 1; you may not use this file except
* in compliance with, at your election, the Elastic License 2.0 or the Server
* Side Public License, v 1.
*/
package org.elasticsearch.gradle.internal.precommit;
import org.gradle.api.DefaultTask;
import org.gradle.api.logging.Logger;
import org.gradle.api.logging.Logging;
import org.gradle.api.tasks.Internal;
import org.gradle.api.tasks.TaskAction;
import org.gradle.api.tasks.TaskProvider;
import java.io.File;
import java.io.IOException;
import java.nio.charset.StandardCharsets;
import java.nio.file.Files;
import java.nio.file.StandardOpenOption;
import java.security.NoSuchAlgorithmException;
import java.util.Set;
/**
* A task to update shas used by {@code DependencyLicensesCheck}
*/
public class UpdateShasTask extends DefaultTask {
private final Logger logger = Logging.getLogger(getClass());
/** The parent dependency licenses task to use configuration from */
private TaskProvider<DependencyLicensesTask> parentTask;
public UpdateShasTask() {
setDescription("Updates the sha files for the dependencyLicenses check");
setOnlyIf(element -> parentTask.get().getLicensesDir() != null);
}
@TaskAction
public void updateShas() throws NoSuchAlgorithmException, IOException {
Set<File> shaFiles = parentTask.get().getShaFiles();
for (File dependency : parentTask.get().getDependencies()) {
String jarName = dependency.getName();
File shaFile = parentTask.get().getShaFile(jarName);
if (shaFile.exists() == false) {
createSha(dependency, jarName, shaFile);
} else {
shaFiles.remove(shaFile);
}
}
for (File shaFile : shaFiles) {
logger.lifecycle("Removing unused sha " + shaFile.getName());
shaFile.delete();
}
}
private void createSha(File dependency, String jarName, File shaFile) throws IOException, NoSuchAlgorithmException {
logger.lifecycle("Adding sha for " + jarName);
String sha = parentTask.get().getSha1(dependency);
Files.write(shaFile.toPath(), sha.getBytes(StandardCharsets.UTF_8), StandardOpenOption.CREATE);
}
@Internal
public DependencyLicensesTask getParentTask() {
return parentTask.get();
}
public void setParentTask(TaskProvider<DependencyLicensesTask> parentTask) {
this.parentTask = parentTask;
}
}

View file

@ -26,8 +26,6 @@ import java.io.IOException;
import java.nio.charset.StandardCharsets;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.StandardOpenOption;
import java.security.NoSuchAlgorithmException;
import java.util.HashMap;
import java.util.Map;
@ -41,8 +39,6 @@ public class DependencyLicensesTaskTests {
@Rule
public ExpectedException expectedException = ExpectedException.none();
private UpdateShasTask updateShas;
private TaskProvider<DependencyLicensesTask> task;
private Project project;
@ -53,7 +49,6 @@ public class DependencyLicensesTaskTests {
public void prepare() {
project = createProject();
task = createDependencyLicensesTask(project);
updateShas = createUpdateShasTask(project, task);
dependency = project.getDependencies().localGroovy();
task.configure(new Action<DependencyLicensesTask>() {
@Override
@ -87,19 +82,6 @@ public class DependencyLicensesTaskTests {
task.get().checkDependencies();
}
@Test
public void givenProjectWithDependencyButNoShaFileThenShouldReturnException() throws Exception {
expectedException.expect(GradleException.class);
expectedException.expectMessage(containsString("Missing SHA for "));
File licensesDir = getLicensesDir(project);
createFileIn(licensesDir, "groovy-all-LICENSE.txt", PERMISSIVE_LICENSE_TEXT);
createFileIn(licensesDir, "groovy-all-NOTICE.txt", "");
project.getDependencies().add("implementation", project.getDependencies().localGroovy());
task.get().checkDependencies();
}
@Test
public void givenProjectWithDependencyButNoLicenseFileThenShouldReturnException() throws Exception {
expectedException.expect(GradleException.class);
@ -108,7 +90,6 @@ public class DependencyLicensesTaskTests {
project.getDependencies().add("implementation", project.getDependencies().localGroovy());
getLicensesDir(project).mkdir();
updateShas.updateShas();
task.get().checkDependencies();
}
@ -121,7 +102,6 @@ public class DependencyLicensesTaskTests {
createFileIn(getLicensesDir(project), "groovy-LICENSE.txt", PERMISSIVE_LICENSE_TEXT);
updateShas.updateShas();
task.get().checkDependencies();
}
@ -135,7 +115,6 @@ public class DependencyLicensesTaskTests {
createFileIn(getLicensesDir(project), "groovy-LICENSE.txt", STRICT_LICENSE_TEXT);
createFileIn(getLicensesDir(project), "groovy-NOTICE.txt", "");
updateShas.updateShas();
task.get().checkDependencies();
}
@ -147,7 +126,6 @@ public class DependencyLicensesTaskTests {
createFileIn(getLicensesDir(project), "groovy-NOTICE.txt", "");
createFileIn(getLicensesDir(project), "groovy-SOURCES.txt", "");
updateShas.updateShas();
task.get().checkDependencies();
}
@ -190,37 +168,6 @@ public class DependencyLicensesTaskTests {
task.get().checkDependencies();
}
@Test
public void givenProjectWithAShaButWithoutTheDependencyThenShouldThrowException() throws Exception {
expectedException.expect(GradleException.class);
expectedException.expectMessage(containsString("Unused sha files found: \n"));
project.getDependencies().add("implementation", dependency);
File licensesDir = getLicensesDir(project);
createAllDefaultDependencyFiles(licensesDir, "groovy");
createFileIn(licensesDir, "non-declared.sha1", "");
task.get().checkDependencies();
}
@Test
public void givenProjectWithADependencyWithWrongShaThenShouldThrowException() throws Exception {
expectedException.expect(GradleException.class);
expectedException.expectMessage(containsString("SHA has changed! Expected "));
project.getDependencies().add("implementation", dependency);
File licensesDir = getLicensesDir(project);
createAllDefaultDependencyFiles(licensesDir, "groovy");
Path groovySha = Files.list(licensesDir.toPath()).filter(file -> file.toFile().getName().contains("sha")).findFirst().get();
Files.write(groovySha, new byte[] { 1 }, StandardOpenOption.CREATE);
task.get().checkDependencies();
}
@Test
public void givenProjectWithADependencyMappingThenShouldReturnSilently() throws Exception {
project.getDependencies().add("implementation", dependency);
@ -261,14 +208,6 @@ public class DependencyLicensesTaskTests {
task.get().checkDependencies();
}
@Test
public void givenProjectWithoutLicensesDirWhenAskingForShaFilesThenShouldThrowException() {
expectedException.expect(GradleException.class);
expectedException.expectMessage(containsString("isn't a valid directory"));
task.get().getShaFiles();
}
private Project createProject() {
Project project = ProjectBuilder.builder().build();
project.getPlugins().apply(JavaPlugin.class);
@ -276,11 +215,9 @@ public class DependencyLicensesTaskTests {
return project;
}
private void createAllDefaultDependencyFiles(File licensesDir, String dependencyName) throws IOException, NoSuchAlgorithmException {
private void createAllDefaultDependencyFiles(File licensesDir, String dependencyName) throws IOException {
createFileIn(licensesDir, dependencyName + "-LICENSE.txt", PERMISSIVE_LICENSE_TEXT);
createFileIn(licensesDir, dependencyName + "-NOTICE.txt", "");
updateShas.updateShas();
}
private File getLicensesDir(Project project) {
@ -300,13 +237,6 @@ public class DependencyLicensesTaskTests {
Files.write(file, content.getBytes(StandardCharsets.UTF_8));
}
private UpdateShasTask createUpdateShasTask(Project project, TaskProvider<DependencyLicensesTask> dependencyLicensesTask) {
UpdateShasTask task = project.getTasks().register("updateShas", UpdateShasTask.class).get();
task.setParentTask(dependencyLicensesTask);
return task;
}
private TaskProvider<DependencyLicensesTask> createDependencyLicensesTask(Project project) {
TaskProvider<DependencyLicensesTask> task = project.getTasks()
.register("dependencyLicenses", DependencyLicensesTask.class, new Action<DependencyLicensesTask>() {

View file

@ -1,146 +0,0 @@
/*
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
* or more contributor license agreements. Licensed under the Elastic License
* 2.0 and the Server Side Public License, v 1; you may not use this file except
* in compliance with, at your election, the Elastic License 2.0 or the Server
* Side Public License, v 1.
*/
package org.elasticsearch.gradle.internal.precommit;
import org.apache.commons.io.FileUtils;
import org.gradle.api.GradleException;
import org.gradle.api.Project;
import org.gradle.api.artifacts.Dependency;
import org.gradle.api.file.FileCollection;
import org.gradle.api.plugins.JavaPlugin;
import org.gradle.api.tasks.TaskProvider;
import org.gradle.testfixtures.ProjectBuilder;
import org.junit.Before;
import org.junit.Rule;
import org.junit.Test;
import org.junit.rules.ExpectedException;
import java.io.File;
import java.io.IOException;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.StandardOpenOption;
import java.security.NoSuchAlgorithmException;
import static org.hamcrest.CoreMatchers.containsString;
import static org.hamcrest.CoreMatchers.equalTo;
import static org.hamcrest.MatcherAssert.assertThat;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertTrue;
public class UpdateShasTaskTests {
public static final String GROOVY_JAR_REGEX = "groovy-\\d\\.\\d+\\.\\d+\\.jar";
@Rule
public ExpectedException expectedException = ExpectedException.none();
private UpdateShasTask task;
private Project project;
private Dependency dependency;
@Before
public void prepare() throws IOException {
project = createProject();
task = createUpdateShasTask(project);
dependency = project.getDependencies().localGroovy();
}
@Test
public void whenDependencyDoesntExistThenShouldDeleteDependencySha() throws IOException, NoSuchAlgorithmException {
File unusedSha = createFileIn(getLicensesDir(project), "test.sha1", "");
task.updateShas();
assertFalse(unusedSha.exists());
}
@Test
public void whenDependencyExistsButShaNotThenShouldCreateNewShaFile() throws IOException, NoSuchAlgorithmException {
project.getDependencies().add("implementation", dependency);
getLicensesDir(project).mkdir();
task.updateShas();
Path groovySha = Files.list(getLicensesDir(project).toPath())
.filter(p -> p.toFile().getName().matches(GROOVY_JAR_REGEX + ".sha1"))
.findFirst()
.get();
assertTrue(groovySha.toFile().getName().startsWith("groovy"));
}
@Test
public void whenDependencyAndWrongShaExistsThenShouldNotOverwriteShaFile() throws IOException, NoSuchAlgorithmException {
project.getDependencies().add("implementation", dependency);
File groovyJar = task.getParentTask()
.getDependencies()
.getFiles()
.stream()
.filter(f -> f.getName().matches(GROOVY_JAR_REGEX))
.findFirst()
.get();
String groovyShaName = groovyJar.getName() + ".sha1";
File groovySha = createFileIn(getLicensesDir(project), groovyShaName, "content");
task.updateShas();
assertThat(FileUtils.readFileToString(groovySha), equalTo("content"));
}
@Test
public void whenLicensesDirDoesntExistThenShouldThrowException() throws IOException, NoSuchAlgorithmException {
expectedException.expect(GradleException.class);
expectedException.expectMessage(containsString("isn't a valid directory"));
task.updateShas();
}
private Project createProject() {
Project project = ProjectBuilder.builder().build();
project.getPlugins().apply(JavaPlugin.class);
return project;
}
private File getLicensesDir(Project project) {
return getFile(project, "licenses");
}
private File getFile(Project project, String fileName) {
return project.getProjectDir().toPath().resolve(fileName).toFile();
}
private File createFileIn(File parent, String name, String content) throws IOException {
parent.mkdir();
Path path = parent.toPath().resolve(name);
File file = path.toFile();
Files.write(path, content.getBytes(), StandardOpenOption.CREATE);
return file;
}
private UpdateShasTask createUpdateShasTask(Project project) {
UpdateShasTask task = project.getTasks().register("updateShas", UpdateShasTask.class).get();
task.setParentTask(createDependencyLicensesTask(project));
return task;
}
private TaskProvider<DependencyLicensesTask> createDependencyLicensesTask(Project project) {
return project.getTasks()
.register(
"dependencyLicenses",
DependencyLicensesTask.class,
dependencyLicensesTask -> dependencyLicensesTask.setDependencies(getDependencies(project))
);
}
private FileCollection getDependencies(Project project) {
return project.getConfigurations().getByName("compileClasspath");
}
}

View file

@ -1 +0,0 @@
3cb1181b2141a7e752f5bdc998b7ef1849f726cf

View file

@ -1 +0,0 @@
f6f66e966c70a83ffbdb6f17a0919eaf7c8aca7f

View file

@ -1 +0,0 @@
cd18227f1eb8e9a263286c1d7362ceb24f6f9b32

View file

@ -1 +0,0 @@
e5f6cae5ca7ecaac1ec2827a9e2d65ae2869cada

View file

@ -1 +0,0 @@
853b96d3afbb7bf8cc303fe27ee96836a10c1834

View file

@ -1 +0,0 @@
3f897ace4d7f10f0ea6a58f524a3b105dd483653

View file

@ -1 +0,0 @@
3cb1181b2141a7e752f5bdc998b7ef1849f726cf

View file

@ -1 +0,0 @@
f6f66e966c70a83ffbdb6f17a0919eaf7c8aca7f

View file

@ -1 +0,0 @@
e5f6cae5ca7ecaac1ec2827a9e2d65ae2869cada

View file

@ -1 +0,0 @@
853b96d3afbb7bf8cc303fe27ee96836a10c1834

View file

@ -1 +0,0 @@
0a6a0e0620d51833feffc67bccb51937b2345763

View file

@ -1 +0,0 @@
321c614f85f1dea6bb08c1817c60d53b7f3552fd

View file

@ -1 +0,0 @@
4fb5db5f03d00f6a94e43b78d097978190e4abb2

View file

@ -1 +0,0 @@
1a838a87959d9c2cee658f4a4e1869e28f6b9976

View file

@ -17,3 +17,6 @@ systemProp.jdk.tls.client.protocols=TLSv1.2
# java homes resolved by environment variables
org.gradle.java.installations.auto-detect=false
org.gradle.java.installations.fromEnv=JAVA_TOOLCHAIN_HOME,JAVA_HOME,RUNTIME_JAVA_HOME,JAVA19_HOME,JAVA18_HOME,JAVA17_HOME,JAVA16_HOME,JAVA15_HOME,JAVA14_HOME,JAVA13_HOME,JAVA12_HOME,JAVA11_HOME,JAVA8_HOME
# log some dependency verification info to console
org.gradle.dependency.verification.console=verbose

View file

@ -25,10 +25,10 @@ json-assert = "org.skyscreamer:jsonassert:1.5.0"
jackson-dataformat-yaml = { group = "com.fasterxml.jackson.dataformat", name="jackson-dataformat-yaml", version.ref="jackson" }
jackson-platform = { group = "com.fasterxml.jackson", name="jackson-bom", version.ref="jackson" }
jna = "net.java.dev.jna:jna:5.10.0"
junit = "junit:junit:4.12"
junit = "junit:junit:4.13.2"
junit5-platform = { group = "org.junit", name="junit-bom", version.ref="junit5" }
junit5-jupiter = { group = "org.junit.jupiter", name="junit-jupiter", version.ref="junit5" }
junit5-platform-launcher = "org.junit.platform:junit-platform-launcher:1.8.0"
junit5-platform-launcher = "org.junit.platform:junit-platform-launcher:1.8.1"
junit5-vintage = { group = "org.junit.vintage", name="junit-vintage-engine", version.ref="junit5" }
maven-model = "org.apache.maven:maven-model:3.6.2"
mockito-core = "org.mockito:mockito-core:1.9.5"

File diff suppressed because it is too large Load diff

View file

@ -1 +0,0 @@
98cafc6081d5632b61be2c9e60650b64ddbc637c

View file

@ -1 +0,0 @@
a6884b2fd8fd9a56874db05afaa22435043a2e3e

View file

@ -1 +0,0 @@
3cb751702e1194ff24259155db4d37e9383d4320

View file

@ -1 +0,0 @@
4b986a99445e49ea5fbf5d149c4b63f6ed6c6780

View file

@ -1 +0,0 @@
0a6a0e0620d51833feffc67bccb51937b2345763

View file

@ -1 +0,0 @@
4fc77e1ec6922fc48bf1181e4b38f600dac222ff

View file

@ -1 +0,0 @@
984bb22f310ebbedc967d206e672f8acf766a98e

View file

@ -1 +0,0 @@
5601496b5b6e43d947aeeffbffadb2b18961c731

View file

@ -1 +0,0 @@
8fde7fe2586328ac3c68db92045e1c8759125000

View file

@ -1 +0,0 @@
8467c813d442837fcaeddbc42cf5c5359fab4933

View file

@ -1 +0,0 @@
0fc7258f948358c8caace27b9b191437a50a7ecc

View file

@ -1 +0,0 @@
6808f50c447fb033b334ca5ca25830647d85abe1

View file

@ -1 +0,0 @@
3cb1181b2141a7e752f5bdc998b7ef1849f726cf

View file

@ -1 +0,0 @@
a4cf4688fe1c7e3a63aa636cc96d013af537768e

View file

@ -1 +0,0 @@
4ec95b60d4e86b5c95a0e919cb172a0af98011ef

View file

@ -1 +0,0 @@
a2503f302b11ebde7ebc3df41daebe0e4eea3689

View file

@ -1 +0,0 @@
0122c7cee69b53ed4a7681c03d4ee4c0e2765da5

View file

@ -1 +0,0 @@
f6f66e966c70a83ffbdb6f17a0919eaf7c8aca7f

View file

@ -1 +0,0 @@
e4ba98f1d4b3c80ec46392f25e094a6a2e58fcbf

View file

@ -1 +0,0 @@
4e416198adde54b753e41d3312f799640dac5687

View file

@ -1 +0,0 @@
1f41de81768ef84ca2d8cda4cb79e9272c8ee966

View file

@ -1 +0,0 @@
cd49678784c46aa8789c060538e0154013bb421b

View file

@ -1 +0,0 @@
67b85a6aea4a1c846448e3513161d6c260d6e0d9

View file

@ -1 +0,0 @@
5513d31545085c33809c4b6553c2009fd19a6016

View file

@ -1 +0,0 @@
a201b5bdc92c0fae4bed4b8e5546388c4c2f9eb0

View file

@ -1 +0,0 @@
5df31b69375131fc2163a5557093cb112be90ce1

View file

@ -1 +0,0 @@
8c5cd5f1b3e7b3656ab983b73bbbf8bf5f14f793

View file

@ -1 +0,0 @@
8619e95939167fb37245b5670135e4feb0ec7d50

View file

@ -1 +0,0 @@
5584627487e984c03456266d3f8802eb85a9ce97

View file

@ -1 +0,0 @@
97b2454943127857a8304319be658d6d7ff4fff1

View file

@ -1 +0,0 @@
f36cad41d61ad3a49e61ca6a2327cf364ec110e1

View file

@ -1 +0,0 @@
6d3fcb9c539fde6ba7f175a82fa14466e69ba7a2

View file

@ -1 +0,0 @@
02a220afa62cc703233fe9b1787128e4391f59c5

View file

@ -1 +0,0 @@
433b17482c209554449abc5503e65b9e1feeefbc

View file

@ -1 +0,0 @@
7ada9deb2ef1cd17c1b4313147dac5aa4b965e6d

View file

@ -1 +0,0 @@
0fda489271d30f6f0e3f7f92908d029f1b76c5e2

View file

@ -1 +0,0 @@
6b18b232d4ae95ab67839f46f3e8413e7cc12eab

View file

@ -1 +0,0 @@
181647dc6b748be73410f8a624a8b279f2e75407

View file

@ -1 +0,0 @@
6fe6806d2604441f770ad775f6cba2fc6e1032b9

View file

@ -1 +0,0 @@
a35f88b193c8e43bdf909e022a0325b306a43c87

View file

@ -1 +0,0 @@
e1ef1382ae9dfb2438b82b6dd575566355c2f30f

View file

@ -1 +0,0 @@
c4f7d054303948eb6a4066194253886c8af07128

View file

@ -1 +0,0 @@
e5f6cae5ca7ecaac1ec2827a9e2d65ae2869cada

View file

@ -1 +0,0 @@
853b96d3afbb7bf8cc303fe27ee96836a10c1834

View file

@ -1 +0,0 @@
523b0d63f3dbeacb7dfceb7431cb17fa56cf79fa

View file

@ -1 +0,0 @@
1cbcbe4623113e6af92ccaa89884a345270f1a87

View file

@ -1 +0,0 @@
51ae921a2ed1e06ca8876f12f32f265e83c0b2b8

View file

@ -1 +0,0 @@
698b2d2b15d9a1b7aae025f1d9f576842285e7f6

View file

@ -1 +0,0 @@
e7e0fd82da0a160b7928ba214e699a7e6a74fff4

View file

@ -1 +0,0 @@
66144204f9d6d7d3f3f775622c2dd7e9bd511d97

View file

@ -1 +0,0 @@
fa637eb67eb7628c915d73762b681ae7ff0b9731

View file

@ -1 +0,0 @@
b6e6abe057f23630113f4167c34bda7086691258

View file

@ -1 +0,0 @@
ca2954e8d92a05bacc28ff465b25c70e0f512497

View file

@ -1 +0,0 @@
3a23cc36edaf8fc5a89cb100182758ccb5991487

View file

@ -1 +0,0 @@
6111ae24e3be9ecbd75f5fe908583fc14b4f0174

View file

@ -1 +0,0 @@
2609e36f18f7e8d593cc1cddfb2ac776dc96b8e0

View file

@ -1 +0,0 @@
fa637eb67eb7628c915d73762b681ae7ff0b9731

View file

@ -1 +0,0 @@
b6e6abe057f23630113f4167c34bda7086691258

View file

@ -1 +0,0 @@
ca2954e8d92a05bacc28ff465b25c70e0f512497

View file

@ -1 +0,0 @@
3a23cc36edaf8fc5a89cb100182758ccb5991487

View file

@ -1 +0,0 @@
a3ae34e57fa8a4040e28247291d0cc3d6b8c7bcf

View file

@ -1 +0,0 @@
0a6a0e0620d51833feffc67bccb51937b2345763

View file

@ -1 +0,0 @@
705981b7e25d05a76a3654e597dab6ba423eb79e

View file

@ -1 +0,0 @@
84d3b2d97dd176bd705e4968a88fba0ea30fe991

View file

@ -1 +0,0 @@
faa8ba85d503da4ab872d17ba8c00da0098ab2f2

View file

@ -1 +0,0 @@
75a2db538d218e2bd3c2cbdf04c955b8f6db6626

View file

@ -1 +0,0 @@
1d1f34b3e60db038f3913007a2706a820383dc26

View file

@ -1 +0,0 @@
74b92065815f7affb0cd7897b683369b9ed982fd

View file

@ -1 +0,0 @@
34f9c0563714e666ee6f44430152f46a5f760932

View file

@ -1 +0,0 @@
ec18851f1976d5b810ae1a5fcc32520d2d38f77a

View file

@ -1 +0,0 @@
0a6a0e0620d51833feffc67bccb51937b2345763

View file

@ -1 +0,0 @@
ffeb635597d093509f33e1e94274d14be610f933

View file

@ -1 +0,0 @@
cb6a722f128ff0ce2494384d419b6ff20fad25ab

View file

@ -1 +0,0 @@
cddd9380efd4b81ea01e98be8fbdc9765a81793b

View file

@ -1 +0,0 @@
e2f198c512f0f0ccbd6d618baecc9dde9975eadf

View file

@ -1 +0,0 @@
562a587face36ec7eff2db7f2fc95425c6602bc1

View file

@ -1 +0,0 @@
8d49996a4338670764d7ca4b85a1c4ccf7fe665d

Some files were not shown because too many files have changed in this diff Show more