diff --git a/CODE_OF_CONDUCT.md b/CODE_OF_CONDUCT.md new file mode 100644 index 00000000..daeab101 --- /dev/null +++ b/CODE_OF_CONDUCT.md @@ -0,0 +1,73 @@ +# Contributor Covenant Code of Conduct + +## Our Pledge + +In the interest of fostering an open and welcoming environment, we as +contributors and maintainers pledge to making participation in our project and +our community a harassment-free experience for everyone, regardless of age, body +size, disability, ethnicity, gender identity and expression, level of experience, +education, socio-economic status, nationality, personal appearance, race, +religion, or sexual identity and orientation. + +## Our Standards + +Examples of behavior that contributes to creating a positive environment +include: + +* Using welcoming and inclusive language +* Being respectful of differing viewpoints and experiences +* Gracefully accepting constructive criticism +* Focusing on what is best for the community +* Showing empathy towards other community members + +Examples of unacceptable behavior by participants include: + +* The use of sexualized language or imagery and unwelcome sexual attention or + advances +* Trolling, insulting/derogatory comments, and personal or political attacks +* Public or private harassment +* Publishing others' private information, such as a physical or electronic + address, without explicit permission +* Other conduct which could reasonably be considered inappropriate in a + professional setting + +## Our Responsibilities + +Project maintainers are responsible for clarifying the standards of acceptable +behavior and are expected to take appropriate and fair corrective action in +response to any instances of unacceptable behavior. + +Project maintainers have the right and responsibility to remove, edit, or +reject comments, commits, code, wiki edits, issues, and other contributions +that are not aligned to this Code of Conduct, or to ban temporarily or +permanently any contributor for other behaviors that they deem inappropriate, +threatening, offensive, or harmful. + +## Scope + +This Code of Conduct applies both within project spaces and in public spaces +when an individual is representing the project or its community. Examples of +representing a project or community include using an official project e-mail +address, posting via an official social media account, or acting as an appointed +representative at an online or offline event. Representation of a project may be +further defined and clarified by project maintainers. + +## Enforcement + +Instances of abusive, harassing, or otherwise unacceptable behavior may be +reported by contacting the project team at webmaster@datamanager.kit.edu. All +complaints will be reviewed and investigated and will result in a response that +is deemed necessary and appropriate to the circumstances. The project team is +obligated to maintain confidentiality with regard to the reporter of an incident. +Further details of specific enforcement policies may be posted separately. + +Project maintainers who do not follow or enforce the Code of Conduct in good +faith may face temporary or permanent repercussions as determined by other +members of the project's leadership. + +## Attribution + +This Code of Conduct is adapted from the [Contributor Covenant][homepage], version 1.4, +available at + +[homepage]: https://www.contributor-covenant.org diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md new file mode 100644 index 00000000..dcbef8d7 --- /dev/null +++ b/CONTRIBUTING.md @@ -0,0 +1,16 @@ +# Contributing + +When contributing to this repository, please first discuss the change you wish to make via issue, +email, or any other method with the owners of this repository before making a change. + +Please note we have a code of conduct, please follow it in all your interactions with the project. + +## Pull Request Process + +1. Ensure any install or build dependencies are removed before the end of the layer when doing a build. +2. State in the Pull Request details of changes to the interface, this includes new environment variables, exposed ports, useful file locations and container parameters. +3. Pull Requests are merged after successful review of at least one of the project owners. + +## Code of Conduct + +By participating in this project, you agree to comply with our [Code of Conduct](CODE_OF_CONDUCT.md). diff --git a/build.gradle b/build.gradle index db005460..93e65f06 100644 --- a/build.gradle +++ b/build.gradle @@ -1,5 +1,5 @@ plugins { - id 'org.springframework.boot' version '3.5.8' + id 'org.springframework.boot' version '3.5.16' id 'io.spring.dependency-management' version '1.1.7' id 'io.freefair.lombok' version '9.1.0' id 'io.freefair.maven-publish-java' version '9.1.0' @@ -7,7 +7,7 @@ plugins { id 'org.asciidoctor.jvm.convert' version '4.0.5' id 'net.ltgt.errorprone' version '4.3.0' id 'net.researchgate.release' version '3.1.0' - id 'com.gorylenko.gradle-git-properties' version '2.5.4' + id 'com.gorylenko.gradle-git-properties' version '2.5.7' id 'java' id 'jacoco' } @@ -17,10 +17,10 @@ group = 'edu.kit.datamanager' ext { // versions of dependencies - springDocVersion = '2.8.14' + springDocVersion = '2.8.17' javersVersion = '7.9.0' keycloakVersion = '19.0.0' - errorproneVersion = '2.42.0' + errorproneVersion = '2.50.0' // directory for generated code snippets during tests snippetsDir = file("build/generated-snippets") } @@ -42,19 +42,33 @@ java { sourceCompatibility = JavaVersion.VERSION_17 targetCompatibility = JavaVersion.VERSION_17 } - -if (System.getProperty('profile') == 'minimal') { - println 'Using minimal profile for building ' + project.getName() - apply from: 'gradle/profile-minimal.gradle' -} else { - println 'Using default profile executing all tests for building ' + project.getName() - apply from: 'gradle/profile-complete.gradle' +// The build profile can be specified via command line using -PbuildProfile= +// For example: ./gradlew build -PbuildProfile=minimal +// Default build profile is "complete" if not specified +// Available profiles: +// - "minimal" Only necessary tests for building online REST documentation will be executed. +// This is useful for building a production ready jar file without executing all tests. +// - "release" Before releasing all tests will be executed. +// If successful, the release task will be executed to create a new release version and tag it in git. +// - "complete" All tests will be executed +// To ensure that the application is working as expected, it is recommended to use this profile for development and testing. +def buildProfile = project.findProperty("buildProfile") ?: "complete" + +def profileFile = file("$rootDir/gradle/profile-${buildProfile}.gradle") + +// The release task should only be executed with the "release" profile, which is defined in gradle/profile-minimal.gradle +// Throw exception if the release task is executed with a different profile +gradle.taskGraph.whenReady { graph -> + if (graph.allTasks.any { it.name == "release" } && + findProperty("buildProfile") != "release") { + throw new GradleException("Task 'release' is only available with '-PbuildProfile=release'!" ) + } } dependencies { // Spring - implementation 'org.springframework:spring-messaging:7.0.1' - implementation 'org.springframework.cloud:spring-cloud-gateway-mvc:4.3.2' + implementation 'org.springframework:spring-messaging:7.0.8' + implementation 'org.springframework.cloud:spring-cloud-gateway-mvc:4.3.5' // Spring Boot implementation "org.springframework.boot:spring-boot-starter-data-rest" @@ -73,8 +87,8 @@ dependencies { // cloud support - implementation "org.springframework.cloud:spring-cloud-starter-config:4.3.0" - implementation "org.springframework.cloud:spring-cloud-starter-netflix-eureka-client:4.3.0" + implementation "org.springframework.cloud:spring-cloud-starter-config:4.3.4" + implementation "org.springframework.cloud:spring-cloud-starter-netflix-eureka-client:4.3.3" // springdoc implementation "org.springdoc:springdoc-openapi-starter-webmvc-ui:${springDocVersion}" @@ -98,12 +112,12 @@ dependencies { implementation "org.javers:javers-core:${javersVersion}" // driver for postgres - implementation "org.postgresql:postgresql:42.7.8" + implementation "org.postgresql:postgresql:42.7.13" //driver for h2 implementation "com.h2database:h2:2.4.240" // apache - implementation "commons-io:commons-io:2.21.0" + implementation "commons-io:commons-io:2.22.0" implementation "org.apache.tika:tika-core:3.2.3" // JSON validator @@ -117,7 +131,7 @@ dependencies { implementation "edu.kit.datamanager:service-base:1.3.6" // elasticsearch (since service-base 1.1.0) - implementation "org.springframework.data:spring-data-elasticsearch:5.5.6" + implementation "org.springframework.data:spring-data-elasticsearch:5.5.13" // DOIP SDK implementation "net.dona.doip:doip-sdk:2.2.0" @@ -125,8 +139,9 @@ dependencies { runtimeOnly "org.apache.httpcomponents:httpclient:4.5.14" // Additional libraries for tests - testImplementation "com.google.guava:guava:33.5.0-jre" - testImplementation "org.springframework.restdocs:spring-restdocs-mockmvc:3.0.5" + testImplementation "org.springframework.cloud:spring-cloud-contract-wiremock:4.3.4" + testImplementation "com.google.guava:guava:33.6.0-jre" + testImplementation "org.springframework.restdocs:spring-restdocs-mockmvc:3.0.6" testImplementation "org.springframework.boot:spring-boot-starter-test" testImplementation "org.springframework:spring-test" testImplementation "org.springframework.security:spring-security-test" @@ -143,14 +158,14 @@ dependencies { errorprone "com.google.errorprone:error_prone_core:${errorproneVersion}" // monitoring - implementation 'io.micronaut.micrometer:micronaut-micrometer-registry-prometheus:5.13.1' - implementation 'org.springframework.boot:spring-boot-starter-actuator:3.5.8' + implementation 'io.micronaut.micrometer:micronaut-micrometer-registry-prometheus:5.13.2' + implementation 'org.springframework.boot:spring-boot-starter-actuator:3.5.16' } compileJava { // options.errorprone.disableAllWarnings = true options.errorprone.disableWarningsInGeneratedCode = true - options.compilerArgs << "-Xlint:unchecked" << "-Xlint:deprecation" << "-Xmaxwarns" << "200" + options.compilerArgs << "-Xlint:unchecked" << "-Xlint:deprecation" << "-XDaddTypeAnnotationsToSymbol=true" << "-Xmaxwarns" << "200" } compileTestJava { @@ -184,7 +199,7 @@ tasks.withType(Test) { } jacoco { - toolVersion = "0.8.14" + toolVersion = "0.8.15" } import java.text.SimpleDateFormat @@ -238,8 +253,12 @@ bootJar { launchScript() } -release { - tagTemplate = 'v${version}' +// Apply profile-specific build configuration at the end of this build script +// to ensure that all settings are available. +if (profileFile.exists()) { + apply from: profileFile +} else { + throw new GradleException("Profile-file missing: $profileFile") } // task for printing project name. diff --git a/build.sh b/build.sh index 63aedbef..168a0d0f 100644 --- a/build.sh +++ b/build.sh @@ -116,7 +116,7 @@ printInfo "Build microservice of $REPO_NAME at '$INSTALLATION_DIRECTORY'" # Build service ################################################################################ echo Build service... -./gradlew -Dprofile=minimal clean build +./gradlew -PbuildProfile=minimal clean build echo "Copy configuration to '$INSTALLATION_DIRECTORY'..." diff --git a/codemeta.json b/codemeta.json new file mode 100644 index 00000000..b0f0cfa9 --- /dev/null +++ b/codemeta.json @@ -0,0 +1,95 @@ +{ + "@context": "https://w3id.org/codemeta/3.0", + "type": "SoftwareSourceCode", + "applicationCategory": "Metadata management", + "applicationSubCategory": "JSON & XML Processing", + "codeRepository": "https://github.com/kit-data-manager/metastore2.git", + "name": "MetaStore", + "dateCreated": "2025-12-17", + "description": "JSONPatch is a Java library that implements the JSON Patch standard (RFC 6902) for applying partial modifications to JSON documents. It provides functionality to create, apply, and validate JSON Patch operations, making it easier to manage and manipulate JSON data structures in Java applications.", + "author": [ + { + "@type": "Person", + "givenName": "Volker", + "familyName": "Hartmann", + "email": "volker.hartmann@kit.edu", + "@id": "https://orcid.org/0000-0001-6383-5214", + "identifier": "https://orcid.org/0000-0001-6383-5214", + "affiliation": { + "type": "Organization", + "name": "Karlsruhe Institute of Technology (KIT)" + } + }, + { + "@type": "Person", + "givenName": "Thomas", + "familyName": "Jejkal", + "email": "thomas.jejkal@kit.edu", + "@id": "https://orcid.org/0000-0003-2804-688X", + "identifier": "https://orcid.org/0000-0003-2804-688X", + "affiliation": { + "type": "Organization", + "name": "Karlsruhe Institute of Technology (KIT)" + } + } + ], + "maintainer": [ + { + "@type": "Person", + "givenName": "Volker", + "familyName": "Hartmann", + "email": "volker.hartmann@kit.edu", + "@id": "https://orcid.org/0000-0001-6383-5214", + "identifier": "https://orcid.org/0000-0001-6383-5214", + "affiliation": { + "type": "Organization", + "name": "Karlsruhe Institute of Technology (KIT)" + } + }, + { + "@type": "Person", + "givenName": "Thomas", + "familyName": "Jejkal", + "email": "thomas.jejkal@kit.edu", + "@id": "https://orcid.org/0000-0003-2804-688X", + "identifier": "https://orcid.org/0000-0003-2804-688X", + "affiliation": { + "type": "Organization", + "name": "Karlsruhe Institute of Technology (KIT)" + } + } + ], + "funder": [ + { + "@type": "Organization", + "name": "Helmholtz Association of German Research Centers", + "@id": "https://ror.org/0281dp749", + "url": "https://www.helmholtz.de/" + }, + { + "@type": "Organization", + "name": "Helmholtz Metadata Collaboration (HMC)", + "@id": "https://ror.org/04v4h0v24", + "url": "https://helmholtz-metadaten.de/" + } + ], + "keywords": [ + "Java", + "JSON", + "JSON Patch", + "RFC 6902", + "RFC 7396", + "Jackson 3", + "Library" + ], + "license": "https://spdx.org/licenses/Apache-2.0", + "runtimePlatform": "JVM", + "softwareRequirements": [ + "https://www.oracle.com/java/technologies/downloads/#java21" + ], + "developmentStatus": "Production/Stable", + "issueTracker": "https://github.com/kit-data-manager/JSONPatch/issues", + "version": "1.0.0", + "softwareVersion": "1.0.0", + "dateModified": "2026-06-17" +} \ No newline at end of file diff --git a/gradle.properties b/gradle.properties index 1df96d04..1ba78691 100644 --- a/gradle.properties +++ b/gradle.properties @@ -1,17 +1,17 @@ systemProp.jdk.tls.client.protocols="TLSv1,TLSv1.1,TLSv1.2" -//----------------------------- -// Properties for build.gradle -//----------------------------- +# ----------------------------- +# Properties for build.gradle +# ----------------------------- version=2.1.3-SNAPSHOT -//--------------------------- -// Netbeans specific actions -//--------------------------- +# --------------------------- +# Netbeans specific actions +# --------------------------- action.custom-1=releaseNewVersion -action.custom-1.args=--configure-on-demand -w -Dprofile=minimal release +action.custom-1.args=--configure-on-demand -w -DbuidProfile=release release action.custom-2=testBuildRelease -action.custom-2.args=--configure-on-demand -w -Dprofile=minimal clean build +action.custom-2.args=--configure-on-demand -w -DbuildProfile=release clean build action.custom-3=asciidoctor action.custom-3.args=--configure-on-demand -w -x check asciidoctor action.custom-4=buildRunnableJar diff --git a/gradle/profile-complete.gradle b/gradle/profile-complete.gradle index 72425168..b6fcf1d8 100644 --- a/gradle/profile-complete.gradle +++ b/gradle/profile-complete.gradle @@ -1,3 +1,24 @@ +/* + * Copyright 2026 Karlsruhe Institute of Technology. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +//////////////////////////////////////////////////////////////////////////////// +// Build jar file with all tests executed. +// Before releasing code you should at least once run all the tests. +//////////////////////////////////////////////////////////////////////////////// +println "Using complete profile for building '${name}'" + test { println 'Execute all tests...' outputs.dir snippetsDir diff --git a/gradle/profile-minimal.gradle b/gradle/profile-minimal.gradle index dec5addd..caffe38e 100644 --- a/gradle/profile-minimal.gradle +++ b/gradle/profile-minimal.gradle @@ -1,10 +1,24 @@ -// For faster execution only neccessary tests will be executed +/* + * Copyright 2026 Karlsruhe Institute of Technology. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +println "Using minimal profile for faster execution of tests while building '${name}'" + +/////////////////////////////////////////////////////////////////////////////// +// For faster execution only necessary tests will be executed +/////////////////////////////////////////////////////////////////////////////// test { outputs.dir snippetsDir include "**/*SchemaRegistryControllerDocumentation*" } - -release { - // define tag pattern (tags have to start with 'v') - tagTemplate = 'v${version}' -} \ No newline at end of file diff --git a/gradle/profile-release.gradle b/gradle/profile-release.gradle new file mode 100644 index 00000000..19a9760f --- /dev/null +++ b/gradle/profile-release.gradle @@ -0,0 +1,89 @@ +/* + * Copyright 2026 Karlsruhe Institute of Technology. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +/////////////////////////////////////////////////////////////////////////////////////// +// Version tags start with 'v' e.g. v1.0.0 +// codemeta.json and CITATION.cff are updated before release +// dateModified/releaseDate and version are updated in codemeta.json and CITATION.cff +/////////////////////////////////////////////////////////////////////////////////////// +println "Using release profile for releasing a new version of '${name}'" + +import java.time.LocalDate +import java.time.format.DateTimeFormatter +import groovy.json.JsonSlurper +import groovy.json.JsonOutput + + +def todayDate = LocalDate.now().format(DateTimeFormatter.ISO_DATE) + +/////////////////////////////////////////////////////////////////////////////////////// +//for plugin net.researchgate.release +//see https://github.com/researchgate/gradle-release +/////////////////////////////////////////////////////////////////////////////////////// +release { + //define template for tagging, e.g. v1.0.0 + tagTemplate = 'v${version}' + //set source file of version property + versionPropertyFile = 'gradle.properties' + //set possible properties which may contain the version + versionProperties = ['version', 'mainversion'] + git { + //branch from where to release (default: main) + requireBranch.set('main') + } +} + +/////////////////////////////////////////////////////////////////////////////////////// +// update CITATION.cff file (just date and version) +/////////////////////////////////////////////////////////////////////////////////////// +tasks.register('updateCitationFile') { + doLast { + def citationFile = file("$rootDir/CITATION.cff") + def lines = citationFile.readLines() + def map = ['version': project.version, 'date-released': todayDate] + map.each { key, value -> + lines = lines.collect { line -> + if (line.trim().startsWith("${key}:")) { + return "${key}: ${value}" + } else { + return "${line}" + } + } + } + citationFile.text = lines.join(System.lineSeparator()) + println "Updated CITATION.cff with version ${project.version} and date ${todayDate}" + } +} +/////////////////////////////////////////////////////////////////////////////////////// +// update codemeta.json file (just date and version) +/////////////////////////////////////////////////////////////////////////////////////// +tasks.register('updateCodemetaFile') { + doLast { + def codemetaFile = file('codemeta.json') + def codemeta = new JsonSlurper().parseText(codemetaFile.text) + codemeta.version = project.version + codemeta.softwareVersion = project.version + codemeta.dateModified = todayDate + + codemetaFile.text = JsonOutput.prettyPrint(JsonOutput.toJson(codemeta)) + println "Updated codemeta.json with (software)version ${project.version} and date ${todayDate}" + } +} +/////////////////////////////////////////////////////////////////////////////////////// +// Hook the update tasks into the release process +/////////////////////////////////////////////////////////////////////////////////////// +tasks.named('beforeReleaseBuild') { + dependsOn 'updateCitationFile', 'updateCodemetaFile' +} diff --git a/gradle/wrapper/gradle-wrapper.jar b/gradle/wrapper/gradle-wrapper.jar index f8e1ee31..b1b8ef56 100644 Binary files a/gradle/wrapper/gradle-wrapper.jar and b/gradle/wrapper/gradle-wrapper.jar differ diff --git a/gradle/wrapper/gradle-wrapper.properties b/gradle/wrapper/gradle-wrapper.properties index 23449a2b..a9db1155 100644 --- a/gradle/wrapper/gradle-wrapper.properties +++ b/gradle/wrapper/gradle-wrapper.properties @@ -1,7 +1,9 @@ distributionBase=GRADLE_USER_HOME distributionPath=wrapper/dists -distributionUrl=https\://services.gradle.org/distributions/gradle-9.2.1-bin.zip +distributionUrl=https\://services.gradle.org/distributions/gradle-9.6.1-bin.zip networkTimeout=10000 +retries=0 +retryBackOffMs=500 validateDistributionUrl=true zipStoreBase=GRADLE_USER_HOME zipStorePath=wrapper/dists diff --git a/gradlew b/gradlew index adff685a..249efbb0 100755 --- a/gradlew +++ b/gradlew @@ -20,7 +20,7 @@ ############################################################################## # -# Gradle start up script for POSIX generated by Gradle. +# gradlew start up script for POSIX generated by Gradle. # # Important for running: # @@ -29,7 +29,7 @@ # bash, then to run this script, type that shell name before the whole # command line, like: # -# ksh Gradle +# ksh gradlew # # Busybox and similar reduced shells will NOT work, because this script # requires all of these POSIX shell features: @@ -57,7 +57,7 @@ # Darwin, MinGW, and NonStop. # # (3) This script is generated from the Groovy template -# https://github.com/gradle/gradle/blob/HEAD/platforms/jvm/plugins-application/src/main/resources/org/gradle/api/internal/plugins/unixStartScript.txt +# https://github.com/gradle/gradle/blob/3d91ce3b8caaf77ad09f381f43615b715b53f72c/platforms/jvm/plugins-application/src/main/resources/org/gradle/api/internal/plugins/unixStartScript.txt # within the Gradle project. # # You can find Gradle at https://github.com/gradle/gradle/. diff --git a/gradlew.bat b/gradlew.bat index e509b2dd..8508ef68 100644 --- a/gradlew.bat +++ b/gradlew.bat @@ -19,12 +19,12 @@ @if "%DEBUG%"=="" @echo off @rem ########################################################################## @rem -@rem Gradle startup script for Windows +@rem gradlew startup script for Windows @rem @rem ########################################################################## -@rem Set local scope for the variables with windows NT shell -if "%OS%"=="Windows_NT" setlocal +@rem Set local scope for the variables, and ensure extensions are enabled +setlocal EnableExtensions set DIRNAME=%~dp0 if "%DIRNAME%"=="" set DIRNAME=. @@ -51,7 +51,7 @@ echo. 1>&2 echo Please set the JAVA_HOME variable in your environment to match the 1>&2 echo location of your Java installation. 1>&2 -goto fail +"%COMSPEC%" /c exit 1 :findJavaFromJavaHome set JAVA_HOME=%JAVA_HOME:"=% @@ -65,29 +65,18 @@ echo. 1>&2 echo Please set the JAVA_HOME variable in your environment to match the 1>&2 echo location of your Java installation. 1>&2 -goto fail +"%COMSPEC%" /c exit 1 :execute @rem Setup the command line -@rem Execute Gradle -"%JAVA_EXE%" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% "-Dorg.gradle.appname=%APP_BASE_NAME%" -jar "%APP_HOME%\gradle\wrapper\gradle-wrapper.jar" %* +@rem Execute gradlew +@rem endlocal doesn't take effect until after the line is parsed and variables are expanded +@rem which allows us to clear the local environment before executing the java command +endlocal & "%JAVA_EXE%" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% "-Dorg.gradle.appname=%APP_BASE_NAME%" -jar "%APP_HOME%\gradle\wrapper\gradle-wrapper.jar" %* & call :exitWithErrorLevel -:end -@rem End local scope for the variables with windows NT shell -if %ERRORLEVEL% equ 0 goto mainEnd - -:fail -rem Set variable GRADLE_EXIT_CONSOLE if you need the _script_ return code instead of -rem the _cmd.exe /c_ return code! -set EXIT_CODE=%ERRORLEVEL% -if %EXIT_CODE% equ 0 set EXIT_CODE=1 -if not ""=="%GRADLE_EXIT_CONSOLE%" exit %EXIT_CODE% -exit /b %EXIT_CODE% - -:mainEnd -if "%OS%"=="Windows_NT" endlocal - -:omega +:exitWithErrorLevel +@rem Use "%COMSPEC%" /c exit to allow operators to work properly in scripts +"%COMSPEC%" /c exit %ERRORLEVEL% diff --git a/renovate.json b/renovate.json index 9974e463..e73ef495 100644 --- a/renovate.json +++ b/renovate.json @@ -1,4 +1,7 @@ { + "extends": ["config:recommended"], "labels": ["dependencies"], - "baseBranches": ["development", "Version_1.x.x"] + "baseBranches": ["development", "Version_1.x.x"], + "prConcurrentLimit": 20, + "prHourlyLimit": 2 } diff --git a/src/test/java/edu/kit/datamanager/metastore2/util/DownloadUtilTest.java b/src/test/java/edu/kit/datamanager/metastore2/util/DownloadUtilTest.java index e5d1384f..8d3878de 100644 --- a/src/test/java/edu/kit/datamanager/metastore2/util/DownloadUtilTest.java +++ b/src/test/java/edu/kit/datamanager/metastore2/util/DownloadUtilTest.java @@ -15,6 +15,7 @@ */ package edu.kit.datamanager.metastore2.util; +import com.github.tomakehurst.wiremock.WireMockServer; import com.google.common.io.Files; import edu.kit.datamanager.exceptions.CustomInternalServerError; import java.io.File; @@ -32,13 +33,30 @@ import org.junit.BeforeClass; import org.junit.Test; import static org.junit.Assert.*; +import org.junit.runner.RunWith; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.boot.test.context.SpringBootTest; +import org.springframework.cloud.contract.wiremock.AutoConfigureWireMock; +import org.springframework.test.context.ActiveProfiles; +import org.springframework.test.context.junit4.SpringRunner; + +import static com.github.tomakehurst.wiremock.client.WireMock.*; /** * * @author hartmann-v */ +@RunWith(SpringRunner.class) +@AutoConfigureWireMock(port = 0) +@SpringBootTest(webEnvironment = SpringBootTest.WebEnvironment.RANDOM_PORT) +@ActiveProfiles("test") public class DownloadUtilTest { + int port; + + @Autowired + WireMockServer wireMockServer; + public DownloadUtilTest() { } @@ -65,7 +83,13 @@ public void tearDown() { public void testDownloadResource() throws URISyntaxException { System.out.println("downloadResource"); assertNotNull(new DownloadUtil()); - URI resourceURL = new URI("https://www.example.org"); + port = wireMockServer.port(); + System.out.println("port: " + port); + stubFor(get(urlEqualTo("/any")).willReturn(aResponse() + .withStatus(200) + .withHeader("Content-Type", "text/html") + .withBody("any content"))); + URI resourceURL = new URI("http://localhost:" + port + "/any"); Optional result = DownloadUtil.downloadResource(resourceURL); assertTrue("No file available!", result.isPresent()); assertTrue("File '" + result.get() + "' doesn't exist!", result.get().toFile().exists()); @@ -78,9 +102,13 @@ public void testDownloadResource() throws URISyntaxException { */ @Test public void testDownloadResourceWithPath() throws URISyntaxException { - System.out.println("downloadResource"); - assertNotNull(new DownloadUtil()); - URI resourceURL = new URI("https://httpbin.org/json"); + System.out.println("downloadResourceWithPath"); + port = wireMockServer.port(); + stubFor(get(urlEqualTo("/json")).willReturn(aResponse() + .withStatus(200) + .withHeader("Content-Type", "application/json") + .withBody("{\"author\": \"me\",\"date\": \"today\"}"))); + URI resourceURL = new URI("http://localhost:" + port + "/json"); Optional result = DownloadUtil.downloadResource(resourceURL); assertTrue("No file available!", result.isPresent()); assertTrue("File '" + result.get() + "' doesn't exist!", result.get().toFile().exists()); @@ -97,7 +125,7 @@ public void testDownloadInvalidResource() throws URISyntaxException { try { URI resourceURL = new URI("https://invalidhttpaddress.de"); - Optional result = DownloadUtil.downloadResource(resourceURL); + DownloadUtil.downloadResource(resourceURL); fail(); } catch (CustomInternalServerError ie) { assertTrue(true); @@ -109,7 +137,7 @@ public void testDownloadInvalidResource() throws URISyntaxException { * Test of downloadResource method, of class GemmaMapping. */ @Test - public void testDownloadLocalResource() throws URISyntaxException, IOException { + public void testDownloadLocalResource() { System.out.println("testDownloadLocalResource"); File srcFile = new File("src/test/resources/examples/simple.json"); assertTrue("File doesn't exist: " + srcFile, srcFile.exists()); @@ -125,8 +153,8 @@ public void testDownloadLocalResource() throws URISyntaxException, IOException { * Test of downloadResource method, of class GemmaMapping. */ @Test - public void testDownloadLocalJsonFileWithoutSuffix() throws URISyntaxException, IOException { - System.out.println("testDownloadLocalResource"); + public void testDownloadLocalJsonFileWithoutSuffix() throws IOException { + System.out.println("testDownloadLocalJsonFileWithoutSuffix"); File srcFile = new File("src/test/resources/examples/simple.json"); assertTrue("File doesn't exist: " + srcFile, srcFile.exists()); Path createTempFile = DownloadUtil.createTempFile(null, "nosuffix"); @@ -143,8 +171,8 @@ public void testDownloadLocalJsonFileWithoutSuffix() throws URISyntaxException, * Test of downloadResource method, of class GemmaMapping. */ @Test - public void testDownloadLocalXMLFileWithoutSuffix() throws URISyntaxException, IOException { - System.out.println("testDownloadLocalResource"); + public void testDownloadLocalXMLFileWithoutSuffix() throws IOException { + System.out.println("testDownloadLocalXMLFileWithoutSuffix"); File srcFile = new File("src/test/resources/examples/simple.xml"); assertTrue("File doesn't exist: " + srcFile, srcFile.exists()); Path createTempFile = DownloadUtil.createTempFile(null, "nosuffix"); @@ -161,8 +189,8 @@ public void testDownloadLocalXMLFileWithoutSuffix() throws URISyntaxException, I * Test of downloadResource method, of class GemmaMapping. */ @Test - public void testDownloadLocalResourceWithoutSuffix() throws URISyntaxException, IOException { - System.out.println("testDownloadLocalResource"); + public void testDownloadLocalResourceWithoutSuffix() { + System.out.println("testDownloadLocalResourceWithoutSuffix"); File srcFile = new File("src/test/resources/examples/anyContentWithoutSuffix"); assertTrue("File doesn't exist: " + srcFile, srcFile.exists()); Optional result = DownloadUtil.downloadResource(srcFile.getAbsoluteFile().toURI()); @@ -176,11 +204,11 @@ public void testDownloadLocalResourceWithoutSuffix() throws URISyntaxException, * Test of downloadResource method, of class GemmaMapping. */ @Test - public void testDownloadInvalidLocalResource() throws URISyntaxException, IOException { + public void testDownloadInvalidLocalResource() { System.out.println("testDownloadInvalidLocalResource"); try { URI resourceURL = new File("/invalid/path/to/local/file").toURI(); - Optional result = DownloadUtil.downloadResource(resourceURL); + DownloadUtil.downloadResource(resourceURL); fail(); } catch (CustomInternalServerError ie) { assertTrue(true); @@ -192,8 +220,8 @@ public void testDownloadInvalidLocalResource() throws URISyntaxException, IOExce * Test of downloadResource method, of class GemmaMapping. */ @Test - public void testDownloadResourceNoParameter() throws URISyntaxException { - System.out.println("downloadResource"); + public void testDownloadResourceNoParameter() { + System.out.println("downloadResourceNoParameter"); Optional result = DownloadUtil.downloadResource(null); assertFalse(result.isPresent()); } @@ -238,11 +266,9 @@ public void testCreateInvalidTempFile() { System.out.println("createTempFile"); String[] prefix = {"/prefix", null, "/prefix"}; String[] suffix = {null, "/suffix", "/suffix"}; - HashSet allPaths = new HashSet<>(); - String path = null; for (int index = 0; index < prefix.length; index++) { try { - Path tmpPath = DownloadUtil.createTempFile(prefix[index], suffix[index]); + DownloadUtil.createTempFile(prefix[index], suffix[index]); fail(); } catch (CustomInternalServerError cise) { assertTrue(true); @@ -337,7 +363,7 @@ public void testFixFileExtensionUnknown() throws IOException { } @Test - public void testFixFileExtensionWrongFile() throws IOException { + public void testFixFileExtensionWrongFile() { System.out.println("testFixFileExtensionUnknown"); File srcFile = new File("/tmp"); Path result = DownloadUtil.fixFileExtension(srcFile.toPath()); @@ -345,7 +371,6 @@ public void testFixFileExtensionWrongFile() throws IOException { srcFile = new File("/invalid/path/for/file"); result = DownloadUtil.fixFileExtension(srcFile.toPath()); assertEquals(result, srcFile.toPath()); - srcFile = null; result = DownloadUtil.fixFileExtension(null); assertNull(result); }