diff --git a/.mvn/wrapper/maven-wrapper.properties b/.mvn/wrapper/maven-wrapper.properties index 2f94e61..649058b 100644 --- a/.mvn/wrapper/maven-wrapper.properties +++ b/.mvn/wrapper/maven-wrapper.properties @@ -1,19 +1,3 @@ -# Licensed to the Apache Software Foundation (ASF) under one -# or more contributor license agreements. See the NOTICE file -# distributed with this work for additional information -# regarding copyright ownership. The ASF licenses this file -# to you 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. -wrapperVersion=3.3.2 +wrapperVersion=3.3.4 distributionType=only-script distributionUrl=https://repo.maven.apache.org/maven2/org/apache/maven/apache-maven/3.9.10/apache-maven-3.9.10-bin.zip diff --git a/graalpy-maven-plugin/src/main/java/org/graalvm/python/maven/plugin/AbstractGraalPyMojo.java b/graalpy-maven-plugin/src/main/java/org/graalvm/python/maven/plugin/AbstractGraalPyMojo.java index b02bf04..d959c89 100644 --- a/graalpy-maven-plugin/src/main/java/org/graalvm/python/maven/plugin/AbstractGraalPyMojo.java +++ b/graalpy-maven-plugin/src/main/java/org/graalvm/python/maven/plugin/AbstractGraalPyMojo.java @@ -40,6 +40,7 @@ */ package org.graalvm.python.maven.plugin; +import java.util.ArrayList; import org.apache.maven.artifact.Artifact; import org.apache.maven.artifact.DefaultArtifact; import org.apache.maven.artifact.handler.DefaultArtifactHandler; @@ -110,6 +111,9 @@ public AbstractGraalPyMojo(ProjectBuilder projectBuilder) { @Parameter List packages; + @Parameter(property = "requirementsFile") + String requirementsFile; + @SuppressFBWarnings("UUF_UNUSED_FIELD") public static class PythonHome { @SuppressWarnings("unused") @@ -124,7 +128,7 @@ public static class PythonHome { @Parameter(defaultValue = "${session}", readonly = true, required = true) private MavenSession session; - private ProjectBuilder projectBuilder; + private final ProjectBuilder projectBuilder; private Set launcherClassPath; @@ -153,9 +157,17 @@ protected void preExec(boolean enableWarnings) throws MojoExecutionException { externalDirectory = normalizeEmpty(externalDirectory); resourceDirectory = normalizeEmpty(resourceDirectory); graalPyLockFile = normalizeEmpty(graalPyLockFile); - packages = packages != null - ? packages.stream().filter(p -> p != null && !p.trim().isEmpty()).toList() - : List.of(); + Path reqFilePath = resolveReqFile(); + if (reqFilePath != null) { + getLog().info("GraalPy requirements file: " + reqFilePath); + if (packages != null) { + throw new MojoExecutionException("Cannot use and at the same time. " + + "New option is a replacement for using with list of inline ."); + } + packages = new ArrayList<>(); + } else if (packages != null) { + packages = packages.stream().filter(p -> p != null && !p.trim().isEmpty()).toList(); + } if (pythonResourcesDirectory != null) { if (externalDirectory != null) { @@ -201,6 +213,22 @@ protected void preExec(boolean enableWarnings) throws MojoExecutionException { } } + protected Path resolveReqFile() throws MojoExecutionException { + if (requirementsFile == null || requirementsFile.isBlank()) { + return null; + } + + Path path = Path.of(requirementsFile); + Path finalPath = path.isAbsolute() ? path : project.getBasedir().toPath().resolve(path).normalize(); + + if (!Files.exists(finalPath)) { + throw new MojoExecutionException("The configured requirementsFile does not exist: " + finalPath + + "\nPlease provide a valid path to a pip-compatible requirements file."); + } + + return finalPath; + } + protected void postExec() throws MojoExecutionException { for (Resource r : project.getBuild().getResources()) { if (Files.exists(Path.of(r.getDirectory(), resourceDirectory, "proj"))) { @@ -249,12 +277,11 @@ private static String normalizeEmpty(String s) { } protected Launcher createLauncher() { - Launcher launcherArg = new Launcher(getLauncherPath()) { + return new Launcher(getLauncherPath()) { public Set computeClassPath() throws IOException { return calculateLauncherClasspath(project); } }; - return launcherArg; } protected Path getLockFile() { @@ -293,7 +320,8 @@ protected static String getGraalPyVersion(MavenProject project) throws IOExcepti private static Artifact getGraalPyArtifact(MavenProject project) throws IOException { var projectArtifacts = resolveProjectDependencies(project); - Artifact graalPyArtifact = projectArtifacts.stream().filter(a -> isPythonArtifact(a)).findFirst().orElse(null); + Artifact graalPyArtifact = projectArtifacts.stream().filter(AbstractGraalPyMojo::isPythonArtifact).findFirst() + .orElse(null); return Optional.ofNullable(graalPyArtifact).orElseThrow(() -> new IOException( "Missing GraalPy dependency. Please add to your pom either %s:%s or %s:%s".formatted(POLYGLOT_GROUP_ID, PYTHON_COMMUNITY_ARTIFACT_ID, POLYGLOT_GROUP_ID, PYTHON_ARTIFACT_ID))); @@ -326,6 +354,7 @@ private Set calculateLauncherClasspath(MavenProject project) throws IOEx && PYTHON_LAUNCHER_ARTIFACT_ID.equals(a.getArtifactId())) .findFirst().orElse(null); // python-launcher artifact + assert graalPyLauncherArtifact != null; launcherClassPath.add(graalPyLauncherArtifact.getFile().getAbsolutePath()); // and transitively all its dependencies launcherClassPath.addAll(resolveDependencies(graalPyLauncherArtifact)); diff --git a/graalpy-maven-plugin/src/main/java/org/graalvm/python/maven/plugin/InstallPackagesMojo.java b/graalpy-maven-plugin/src/main/java/org/graalvm/python/maven/plugin/InstallPackagesMojo.java index 105db79..5c18aac 100644 --- a/graalpy-maven-plugin/src/main/java/org/graalvm/python/maven/plugin/InstallPackagesMojo.java +++ b/graalpy-maven-plugin/src/main/java/org/graalvm/python/maven/plugin/InstallPackagesMojo.java @@ -40,12 +40,14 @@ */ package org.graalvm.python.maven.plugin; +import java.nio.file.Files; import org.apache.maven.plugin.MojoExecutionException; import org.apache.maven.plugins.annotations.LifecyclePhase; import org.apache.maven.plugins.annotations.Mojo; import org.apache.maven.plugins.annotations.ResolutionScope; import org.apache.maven.project.ProjectBuilder; import org.graalvm.python.embedding.tools.vfs.VFSUtils; +import org.graalvm.python.embedding.tools.vfs.VFSUtils.Launcher; import org.graalvm.python.embedding.tools.vfs.VFSUtils.PackagesChangedException; import javax.inject.Inject; @@ -98,9 +100,22 @@ private void manageVenv() throws MojoExecutionException { Path venvDirectory = getVenvDirectory(); MavenDelegateLog log = new MavenDelegateLog(getLog()); Path lockFile = getLockFile(); + Path reqFile = resolveReqFile(); + + boolean emptyPackages = packages == null || packages.isEmpty(); + boolean hasReqFile = reqFile != null && Files.exists(reqFile); + boolean hasLockFile = lockFile != null && Files.exists(lockFile); + + if (emptyPackages && !hasReqFile) { + if (hasLockFile) { + throw new MojoExecutionException( + "Lock file is present, but no Python packages or requirements.txt are configured."); + } + return; + } try { VFSUtils.createVenv(venvDirectory, packages, lockFile, MISSING_LOCK_FILE_WARNING, createLauncher(), - getGraalPyVersion(project), log); + getGraalPyVersion(project), log, reqFile); } catch (PackagesChangedException pce) { String pluginPkgsString = pce.getPluginPackages().isEmpty() ? "None" diff --git a/graalpy-maven-plugin/src/main/java/org/graalvm/python/maven/plugin/LockPackagesMojo.java b/graalpy-maven-plugin/src/main/java/org/graalvm/python/maven/plugin/LockPackagesMojo.java index 99a036d..5be042c 100644 --- a/graalpy-maven-plugin/src/main/java/org/graalvm/python/maven/plugin/LockPackagesMojo.java +++ b/graalpy-maven-plugin/src/main/java/org/graalvm/python/maven/plugin/LockPackagesMojo.java @@ -64,6 +64,47 @@ public class LockPackagesMojo extends AbstractGraalPyMojo { This file contains a list of all required Python packages with their specific versions, based on the packages defined in the plugin configuration and their dependencies. """; + public static final String MISSING_DEPENDENCY_CONFIGURATION_ERROR = """ + In order to run the lock-packages goal there have to be python packages declared in the graalpy-maven-plugin configuration. + + You must configure Python dependencies in one of the following ways: + + Option 1: Use with inline versioned package entries: + + + org.graalvm.python + graalpy-maven-plugin + + + {package_name}=={package_version} + + ... + + + + Option 2: Use a pip-compatible requirements.txt file: + + + org.graalvm.python + graalpy-maven-plugin + + requirements.txt + ... + + + + IMPORTANT: + • The requirementsFile workflow follows pip's native behavior. + • GraalPy lock files are NOT used or generated when requirementsFile is specified. + • The 'lock-packages' goal is NOT supported with . + • Users are expected to manage locking / freezing themselves using pip conventions (e.g., pip freeze). + • Do not define both and at the same time. + • The section must be declared on the graalpy-maven-plugin itself, + not inside a specific execution. + + For more details, see: + https://github.com/oracle/graalpython/blob/master/docs/user/Embedding-Build-Tools.md + """; @Inject public LockPackagesMojo(ProjectBuilder projectBuilder) { @@ -94,32 +135,16 @@ protected void manageVenv() throws MojoExecutionException { } private void checkEmptyPackages() throws MojoExecutionException { - if ((packages == null || packages.isEmpty())) { - getLog().error(""); - getLog().error( - "In order to run the lock-packages goal there have to be python packages declared in the graalpy-maven-plugin configuration."); - getLog().error(""); - getLog().error( - "NOTE that the section has to be declared for the whole graalpy-maven-plugin"); - getLog().error("and not specifically for the process-graalpy-resources execution goal."); + Path reqFilePath = resolveReqFile(); + boolean emptyPackages = packages == null || packages.isEmpty(); + boolean requirementsExists = reqFilePath != null; + // Disallow lock-packages when no packages OR when requirementsFile is used + if (emptyPackages || requirementsExists) { getLog().error(""); - getLog().error("Please add the section to your configuration as follows:"); - getLog().error(""); - getLog().error(" org.graalvm.python"); - getLog().error(" graalpy-maven-plugin"); - getLog().error(" "); - getLog().error(" "); - getLog().error(" {package_name}=={package_version}"); - getLog().error(" "); - getLog().error(" ..."); - getLog().error(" "); + getLog().error(MISSING_DEPENDENCY_CONFIGURATION_ERROR); getLog().error(""); - - getLog().error( - "For more information, please refer to https://github.com/oracle/graalpython/blob/master/docs/user/Embedding-Build-Tools.md"); - getLog().error(""); - - throw new MojoExecutionException("missing python packages in plugin configuration"); + throw new MojoExecutionException("In order to run the lock-packages goal there have to be python packages " + + "declared in the graalpy-maven-plugin configuration"); } } } diff --git a/integration-tests/prepare_venv_requirements_pom.xml b/integration-tests/prepare_venv_requirements_pom.xml new file mode 100644 index 0000000..9ed8e68 --- /dev/null +++ b/integration-tests/prepare_venv_requirements_pom.xml @@ -0,0 +1,99 @@ + + + + 4.0.0 + + archetype.it + requirements_packages + 1.0-SNAPSHOT + jar + + + + junit + junit + 3.8.1 + test + + + org.graalvm.polyglot + python + ${env.GRAALPY_VERSION} + pom + + + org.graalvm.python + python-launcher + ${env.GRAALPY_VERSION} + + + org.graalvm.python + python-embedding + ${env.GRAALPY_VERSION} + + + + + + + org.graalvm.python + graalpy-maven-plugin + ${env.GRAALPY_VERSION} + + + + process-graalpy-resources + + + + + + GRAALPY-VFS/${project.groupId}/${project.artifactId} + + requirements.txt + + + + + diff --git a/integration-tests/test_maven_plugin.py b/integration-tests/test_maven_plugin.py index 9b191e1..6357533 100644 --- a/integration-tests/test_maven_plugin.py +++ b/integration-tests/test_maven_plugin.py @@ -835,6 +835,42 @@ def test_multiple_namespaced_vfs(self): assert return_code == 0, log + def test_requirements_txt_packages(self): + with util.TemporaryTestDirectory() as dir: + target_name = "requirements_packages" + target_dir = os.path.join(str(dir), target_name) + pom_template = os.path.join( + os.path.dirname(__file__), + "prepare_venv_requirements_pom.xml", + ) + self.generate_app(dir, target_dir, target_name, pom_template) + + requirements_txt = os.path.join(target_dir, "requirements.txt") + if not os.path.exists(requirements_txt): + with open(requirements_txt, "w", encoding="utf-8") as f: + f.write("termcolor==2.4.0\n") + + mvnw_cmd = util.get_mvn_wrapper(target_dir, self.env) + + cmd = mvnw_cmd + ["process-resources"] + out, return_code = util.run_cmd(cmd, self.env, cwd=target_dir) + util.check_ouput("BUILD SUCCESS", out) + assert return_code == 0 + + lock_file = os.path.join(target_dir, "graalpy.lock") + assert not os.path.exists(lock_file), "lock-file must NOT exist for requirements.txt mode" + cmd = mvnw_cmd + ["package", "-DmainClass=it.pkg.GraalPy"] + out, return_code = util.run_cmd(cmd, self.env, cwd=target_dir) + util.check_ouput("BUILD SUCCESS", out) + assert return_code == 0 + + cmd = mvnw_cmd + ["exec:java", "-Dexec.mainClass=it.pkg.GraalPy"] + out, return_code = util.run_cmd(cmd, self.env, cwd=target_dir) + util.check_ouput("hello java", out) + util.check_ouput("BUILD SUCCESS", out) + assert return_code == 0 + + if __name__ == "__main__": run_path = os.path.join(os.path.abspath(__file__), 'run.py') print(f"Run this file using the run.py driver ({run_path})") diff --git a/integration-tests/util.py b/integration-tests/util.py index f5c6fb9..620bdf5 100644 --- a/integration-tests/util.py +++ b/integration-tests/util.py @@ -60,10 +60,17 @@ native_image_mode = "all" extra_maven_repos = [] +def _native_image_allowed_on_platform(): + return sys.platform != "darwin" + def native_image_all(): + if not _native_image_allowed_on_platform(): + return False return native_image_mode == "all" def native_image_smoke(): + if not _native_image_allowed_on_platform(): + return False return native_image_mode in ("all", "smoke") gradle_java_home = os.environ['JAVA_HOME'] diff --git a/mvnw b/mvnw index 19529dd..bd8896b 100755 --- a/mvnw +++ b/mvnw @@ -19,7 +19,7 @@ # ---------------------------------------------------------------------------- # ---------------------------------------------------------------------------- -# Apache Maven Wrapper startup batch script, version 3.3.2 +# Apache Maven Wrapper startup batch script, version 3.3.4 # # Optional ENV vars # ----------------- @@ -105,14 +105,17 @@ trim() { printf "%s" "${1}" | tr -d '[:space:]' } +scriptDir="$(dirname "$0")" +scriptName="$(basename "$0")" + # parse distributionUrl and optional distributionSha256Sum, requires .mvn/wrapper/maven-wrapper.properties while IFS="=" read -r key value; do case "${key-}" in distributionUrl) distributionUrl=$(trim "${value-}") ;; distributionSha256Sum) distributionSha256Sum=$(trim "${value-}") ;; esac -done <"${0%/*}/.mvn/wrapper/maven-wrapper.properties" -[ -n "${distributionUrl-}" ] || die "cannot read distributionUrl property in ${0%/*}/.mvn/wrapper/maven-wrapper.properties" +done <"$scriptDir/.mvn/wrapper/maven-wrapper.properties" +[ -n "${distributionUrl-}" ] || die "cannot read distributionUrl property in $scriptDir/.mvn/wrapper/maven-wrapper.properties" case "${distributionUrl##*/}" in maven-mvnd-*bin.*) @@ -130,7 +133,7 @@ maven-mvnd-*bin.*) distributionUrl="${distributionUrl%-bin.*}-$distributionPlatform.zip" ;; maven-mvnd-*) MVN_CMD=mvnd.sh _MVNW_REPO_PATTERN=/maven/mvnd/ ;; -*) MVN_CMD="mvn${0##*/mvnw}" _MVNW_REPO_PATTERN=/org/apache/maven/ ;; +*) MVN_CMD="mvn${scriptName#mvnw}" _MVNW_REPO_PATTERN=/org/apache/maven/ ;; esac # apply MVNW_REPOURL and calculate MAVEN_HOME @@ -227,7 +230,7 @@ if [ -n "${distributionSha256Sum-}" ]; then echo "Please disable validation by removing 'distributionSha256Sum' from your maven-wrapper.properties." >&2 exit 1 elif command -v sha256sum >/dev/null; then - if echo "$distributionSha256Sum $TMP_DOWNLOAD_DIR/$distributionUrlName" | sha256sum -c >/dev/null 2>&1; then + if echo "$distributionSha256Sum $TMP_DOWNLOAD_DIR/$distributionUrlName" | sha256sum -c - >/dev/null 2>&1; then distributionSha256Result=true fi elif command -v shasum >/dev/null; then @@ -252,8 +255,41 @@ if command -v unzip >/dev/null; then else tar xzf${__MVNW_QUIET_TAR:+"$__MVNW_QUIET_TAR"} "$TMP_DOWNLOAD_DIR/$distributionUrlName" -C "$TMP_DOWNLOAD_DIR" || die "failed to untar" fi -printf %s\\n "$distributionUrl" >"$TMP_DOWNLOAD_DIR/$distributionUrlNameMain/mvnw.url" -mv -- "$TMP_DOWNLOAD_DIR/$distributionUrlNameMain" "$MAVEN_HOME" || [ -d "$MAVEN_HOME" ] || die "fail to move MAVEN_HOME" + +# Find the actual extracted directory name (handles snapshots where filename != directory name) +actualDistributionDir="" + +# First try the expected directory name (for regular distributions) +if [ -d "$TMP_DOWNLOAD_DIR/$distributionUrlNameMain" ]; then + if [ -f "$TMP_DOWNLOAD_DIR/$distributionUrlNameMain/bin/$MVN_CMD" ]; then + actualDistributionDir="$distributionUrlNameMain" + fi +fi + +# If not found, search for any directory with the Maven executable (for snapshots) +if [ -z "$actualDistributionDir" ]; then + # enable globbing to iterate over items + set +f + for dir in "$TMP_DOWNLOAD_DIR"/*; do + if [ -d "$dir" ]; then + if [ -f "$dir/bin/$MVN_CMD" ]; then + actualDistributionDir="$(basename "$dir")" + break + fi + fi + done + set -f +fi + +if [ -z "$actualDistributionDir" ]; then + verbose "Contents of $TMP_DOWNLOAD_DIR:" + verbose "$(ls -la "$TMP_DOWNLOAD_DIR")" + die "Could not find Maven distribution directory in extracted archive" +fi + +verbose "Found extracted Maven distribution directory: $actualDistributionDir" +printf %s\\n "$distributionUrl" >"$TMP_DOWNLOAD_DIR/$actualDistributionDir/mvnw.url" +mv -- "$TMP_DOWNLOAD_DIR/$actualDistributionDir" "$MAVEN_HOME" || [ -d "$MAVEN_HOME" ] || die "fail to move MAVEN_HOME" clean || : exec_maven "$@" diff --git a/mvnw.cmd b/mvnw.cmd index b150b91..5761d94 100644 --- a/mvnw.cmd +++ b/mvnw.cmd @@ -19,7 +19,7 @@ @REM ---------------------------------------------------------------------------- @REM ---------------------------------------------------------------------------- -@REM Apache Maven Wrapper startup batch script, version 3.3.2 +@REM Apache Maven Wrapper startup batch script, version 3.3.4 @REM @REM Optional ENV vars @REM MVNW_REPOURL - repo url base for downloading maven distribution @@ -40,7 +40,7 @@ @SET __MVNW_ARG0_NAME__= @SET MVNW_USERNAME= @SET MVNW_PASSWORD= -@IF NOT "%__MVNW_CMD__%"=="" (%__MVNW_CMD__% %*) +@IF NOT "%__MVNW_CMD__%"=="" ("%__MVNW_CMD__%" %*) @echo Cannot start maven from wrapper >&2 && exit /b 1 @GOTO :EOF : end batch / begin powershell #> @@ -73,16 +73,30 @@ switch -wildcard -casesensitive ( $($distributionUrl -replace '^.*/','') ) { # apply MVNW_REPOURL and calculate MAVEN_HOME # maven home pattern: ~/.m2/wrapper/dists/{apache-maven-,maven-mvnd--}/ if ($env:MVNW_REPOURL) { - $MVNW_REPO_PATTERN = if ($USE_MVND) { "/org/apache/maven/" } else { "/maven/mvnd/" } - $distributionUrl = "$env:MVNW_REPOURL$MVNW_REPO_PATTERN$($distributionUrl -replace '^.*'+$MVNW_REPO_PATTERN,'')" + $MVNW_REPO_PATTERN = if ($USE_MVND -eq $False) { "/org/apache/maven/" } else { "/maven/mvnd/" } + $distributionUrl = "$env:MVNW_REPOURL$MVNW_REPO_PATTERN$($distributionUrl -replace "^.*$MVNW_REPO_PATTERN",'')" } $distributionUrlName = $distributionUrl -replace '^.*/','' $distributionUrlNameMain = $distributionUrlName -replace '\.[^.]*$','' -replace '-bin$','' -$MAVEN_HOME_PARENT = "$HOME/.m2/wrapper/dists/$distributionUrlNameMain" + +$MAVEN_M2_PATH = "$HOME/.m2" if ($env:MAVEN_USER_HOME) { - $MAVEN_HOME_PARENT = "$env:MAVEN_USER_HOME/wrapper/dists/$distributionUrlNameMain" + $MAVEN_M2_PATH = "$env:MAVEN_USER_HOME" +} + +if (-not (Test-Path -Path $MAVEN_M2_PATH)) { + New-Item -Path $MAVEN_M2_PATH -ItemType Directory | Out-Null +} + +$MAVEN_WRAPPER_DISTS = $null +if ((Get-Item $MAVEN_M2_PATH).Target[0] -eq $null) { + $MAVEN_WRAPPER_DISTS = "$MAVEN_M2_PATH/wrapper/dists" +} else { + $MAVEN_WRAPPER_DISTS = (Get-Item $MAVEN_M2_PATH).Target[0] + "/wrapper/dists" } -$MAVEN_HOME_NAME = ([System.Security.Cryptography.MD5]::Create().ComputeHash([byte[]][char[]]$distributionUrl) | ForEach-Object {$_.ToString("x2")}) -join '' + +$MAVEN_HOME_PARENT = "$MAVEN_WRAPPER_DISTS/$distributionUrlNameMain" +$MAVEN_HOME_NAME = ([System.Security.Cryptography.SHA256]::Create().ComputeHash([byte[]][char[]]$distributionUrl) | ForEach-Object {$_.ToString("x2")}) -join '' $MAVEN_HOME = "$MAVEN_HOME_PARENT/$MAVEN_HOME_NAME" if (Test-Path -Path "$MAVEN_HOME" -PathType Container) { @@ -134,7 +148,33 @@ if ($distributionSha256Sum) { # unzip and move Expand-Archive "$TMP_DOWNLOAD_DIR/$distributionUrlName" -DestinationPath "$TMP_DOWNLOAD_DIR" | Out-Null -Rename-Item -Path "$TMP_DOWNLOAD_DIR/$distributionUrlNameMain" -NewName $MAVEN_HOME_NAME | Out-Null + +# Find the actual extracted directory name (handles snapshots where filename != directory name) +$actualDistributionDir = "" + +# First try the expected directory name (for regular distributions) +$expectedPath = Join-Path "$TMP_DOWNLOAD_DIR" "$distributionUrlNameMain" +$expectedMvnPath = Join-Path "$expectedPath" "bin/$MVN_CMD" +if ((Test-Path -Path $expectedPath -PathType Container) -and (Test-Path -Path $expectedMvnPath -PathType Leaf)) { + $actualDistributionDir = $distributionUrlNameMain +} + +# If not found, search for any directory with the Maven executable (for snapshots) +if (!$actualDistributionDir) { + Get-ChildItem -Path "$TMP_DOWNLOAD_DIR" -Directory | ForEach-Object { + $testPath = Join-Path $_.FullName "bin/$MVN_CMD" + if (Test-Path -Path $testPath -PathType Leaf) { + $actualDistributionDir = $_.Name + } + } +} + +if (!$actualDistributionDir) { + Write-Error "Could not find Maven distribution directory in extracted archive" +} + +Write-Verbose "Found extracted Maven distribution directory: $actualDistributionDir" +Rename-Item -Path "$TMP_DOWNLOAD_DIR/$actualDistributionDir" -NewName $MAVEN_HOME_NAME | Out-Null try { Move-Item -Path "$TMP_DOWNLOAD_DIR/$MAVEN_HOME_NAME" -Destination $MAVEN_HOME_PARENT | Out-Null } catch { diff --git a/org.graalvm.python.embedding.tools/src/main/java/org/graalvm/python/embedding/tools/vfs/VFSUtils.java b/org.graalvm.python.embedding.tools/src/main/java/org/graalvm/python/embedding/tools/vfs/VFSUtils.java index 7845f99..cb602fe 100644 --- a/org.graalvm.python.embedding.tools/src/main/java/org/graalvm/python/embedding/tools/vfs/VFSUtils.java +++ b/org.graalvm.python.embedding.tools/src/main/java/org/graalvm/python/embedding/tools/vfs/VFSUtils.java @@ -40,6 +40,7 @@ */ package org.graalvm.python.embedding.tools.vfs; +import java.io.Serial; import org.graalvm.python.embedding.tools.exec.BuildToolLog; import org.graalvm.python.embedding.tools.exec.BuildToolLog.CollectOutputLog; import org.graalvm.python.embedding.tools.exec.GraalPyRunner; @@ -317,19 +318,16 @@ static InstalledPackages fromVenv(Path venvDirectory) throws IOException { return new InstalledPackages(venvDirectory, installed, pkgs); } - List freeze(BuildToolLog log) throws IOException { + void freeze(BuildToolLog log) throws IOException { CollectOutputLog collectOutputLog = new CollectOutputLog(log); runPip(venvDirectory, "freeze", collectOutputLog, "--local"); packages = new ArrayList<>(collectOutputLog.getOutput()); String toWrite = "# Generated by GraalPy Maven or Gradle plugin using pip freeze\n" + "# This file is used by GraalPy VirtualFileSystem\n" + String.join("\n", packages); - Files.write(installedFile, toWrite.getBytes(StandardCharsets.UTF_8), StandardOpenOption.CREATE, - StandardOpenOption.TRUNCATE_EXISTING); + Files.writeString(installedFile, toWrite, StandardOpenOption.CREATE, StandardOpenOption.TRUNCATE_EXISTING); logDebug(log, packages, "VFSUtils venv packages after install %s:", installedFile); - - return packages; } } @@ -365,9 +363,7 @@ static VenvContents fromVenv(Path venvDirectory) throws IOException { if (lines.get(0).startsWith("version=")) { // this was created with version >= 25 Map m = new HashMap<>(); - Iterator it = lines.iterator(); - while (it.hasNext()) { - String l = it.next(); + for (String l : lines) { int idx = l.indexOf("="); m.put(l.substring(0, idx), l.substring(idx + 1)); } @@ -405,17 +401,7 @@ void write(List pkgs) throws IOException { private static final String INPUT_PACKAGES_PREFIX = "# input-packages: "; private static final String INPUT_PACKAGES_DELIMITER = ","; - private static class LockFile { - - final Path path; - final List packages; - final List inputPackages; - - private LockFile(Path path, List inputPackages, List packages) { - this.path = path; - this.packages = packages; - this.inputPackages = inputPackages; - } + private record LockFile(Path path, List inputPackages, List packages) { static LockFile fromFile(Path file, BuildToolLog log) throws IOException { List packages = new ArrayList<>(); @@ -516,6 +502,7 @@ private static List getHeaderList(String lockFileHeader) { } public static final class PackagesChangedException extends Exception { + @Serial private static final long serialVersionUID = 9162516912727973035L; private final transient List pluginPackages; @@ -539,7 +526,7 @@ public List getLockFilePackages() { public static void createVenv(Path venvDirectory, List packagesArgs, Launcher launcherArgs, String graalPyVersion, BuildToolLog log) throws IOException { try { - createVenv(venvDirectory, packagesArgs, null, null, launcherArgs, graalPyVersion, log); + createVenv(venvDirectory, packagesArgs, null, null, launcherArgs, graalPyVersion, log, null); } catch (PackagesChangedException e) { // should not happen assert false; @@ -548,19 +535,68 @@ public static void createVenv(Path venvDirectory, List packagesArgs, Lau } public static void createVenv(Path venvDirectory, List packages, Path lockFilePath, - String missingLockFileWarning, Launcher launcher, String graalPyVersion, BuildToolLog log) + String missingLockFileWarning, Launcher launcher, String graalPyVersion, BuildToolLog log, Path reqFile) throws IOException, PackagesChangedException { + Objects.requireNonNull(venvDirectory); - Objects.requireNonNull(packages); Objects.requireNonNull(launcher); Objects.requireNonNull(graalPyVersion); Objects.requireNonNull(log); + if (installPackagesFromReqFile(venvDirectory, launcher, graalPyVersion, log, lockFilePath, reqFile)) { + return; + } + + installPackages(venvDirectory, packages, lockFilePath, missingLockFileWarning, launcher, graalPyVersion, log); + } + + static boolean installPackagesFromReqFile(Path venvDirectory, Launcher launcher, String graalPyVersion, + BuildToolLog log, Path lockFilePath, Path reqFile) throws IOException { + if (reqFile == null) { + return false; + } + if (!Files.exists(reqFile)) { + return false; + } + log.info("Using dependency mode."); + log.info("Installing Python dependencies from: " + reqFile); + + warnIfLockFileExists(lockFilePath, log); + + VenvContents vc = ensureVenv(venvDirectory, graalPyVersion, launcher, log); + + runPip(venvDirectory, "install", log, "--compile", "-r", reqFile.toString()); + List reqPackages = requirementsPackages(reqFile); + vc.write(reqPackages); + + InstalledPackages installed = InstalledPackages.fromVenv(venvDirectory); + installed.freeze(log); + + return true; + } + + private static void warnIfLockFileExists(Path lockFilePath, BuildToolLog log) { + if (lockFilePath == null) { + return; + } + if (Files.exists(lockFilePath)) { + log.warning("Lock file is ignored in mode."); + } + } + + static void installPackages(Path venvDirectory, List packages, Path lockFilePath, + String missingLockFileWarning, Launcher launcher, String graalPyVersion, BuildToolLog log) + throws IOException, PackagesChangedException { + Objects.requireNonNull(packages); + log.info("Using inline dependency mode."); + logVenvArgs(venvDirectory, packages, lockFilePath, launcher, graalPyVersion, log); List pluginPackages = trim(packages); - LockFile lockFile = null; + + VFSUtils.LockFile lockFile = null; if (lockFilePath != null && Files.exists(lockFilePath)) { + log.info("Lock-file detected: " + lockFilePath); lockFile = LockFile.fromFile(lockFilePath, log); } @@ -569,18 +605,20 @@ public static void createVenv(Path venvDirectory, List packages, Path lo } VenvContents venvContents = ensureVenv(venvDirectory, graalPyVersion, launcher, log); - InstalledPackages installedPackages = InstalledPackages.fromVenv(venvDirectory); + boolean installed; if (lockFile != null) { installed = install(venvDirectory, installedPackages, lockFile, log); } else { installed = install(venvDirectory, pluginPackages, venvContents, log); } + if (installed) { venvContents.write(pluginPackages); installedPackages.freeze(log); } + if (lockFile == null) { missingLockFileWarning(venvDirectory, pluginPackages, missingLockFileWarning, log); } @@ -717,13 +755,12 @@ private static void logPackages(List packages, Path lockFile, BuildToolL } private static List readPackagesFromFile(Path file) throws IOException { - return Files.readAllLines(file).stream().filter((s) -> { - if (s == null) { - return false; - } - String l = s.trim(); - return !l.startsWith("#") && !s.isEmpty(); - }).toList(); + return Files.readAllLines(file).stream().map(String::trim) + .filter(line -> !line.isEmpty() && !line.startsWith("#")).toList(); + } + + public static List requirementsPackages(Path requirementsFile) throws IOException { + return Files.exists(requirementsFile) ? readPackagesFromFile(requirementsFile) : Collections.emptyList(); } private static VenvContents ensureVenv(Path venvDirectory, String graalPyVersion, Launcher launcher, @@ -760,6 +797,15 @@ private static VenvContents ensureVenv(Path venvDirectory, String graalPyVersion return contents; } + private static boolean install(Path venvDirectory, Path requirementsFile, BuildToolLog log) throws IOException { + if (!Files.exists(requirementsFile)) { + throw new IOException("Requirements file not found: " + requirementsFile); + } + info(log, "Installing Python dependencies from requirements file: " + requirementsFile); + runPip(venvDirectory, "install", log, "--compile", "-r", requirementsFile.toString()); + return true; + } + private static boolean install(Path venvDirectory, InstalledPackages installedPackages, LockFile lockFile, BuildToolLog log) throws IOException { if (installedPackages.packages.size() != lockFile.packages.size() @@ -783,7 +829,7 @@ private static boolean install(Path venvDirectory, List newPackages, Ven private static void missingLockFileWarning(Path venvDirectory, List newPackages, String missingLockFileWarning, BuildToolLog log) throws IOException { if (missingLockFileWarning != null && !Boolean.getBoolean("graalpy.vfs.skipMissingLockFileWarning")) { - if (!newPackages.containsAll(InstalledPackages.fromVenv(venvDirectory).packages)) { + if (!new HashSet<>(newPackages).containsAll(InstalledPackages.fromVenv(venvDirectory).packages)) { if (log.isWarningEnabled()) { String txt = missingLockFileWarning + "\n"; for (String t : txt.split("\n")) { @@ -800,7 +846,7 @@ private static void missingLockFileWarning(Path venvDirectory, List newP private static void checkPluginPackagesInLockFile(List pluginPackages, LockFile lockFile) throws PackagesChangedException { if (pluginPackages.size() != lockFile.inputPackages.size() - || !pluginPackages.containsAll(lockFile.inputPackages)) { + || !new HashSet<>(pluginPackages).containsAll(lockFile.inputPackages)) { throw new PackagesChangedException(new ArrayList<>(pluginPackages), new ArrayList<>(lockFile.inputPackages)); } @@ -928,7 +974,7 @@ with open(pyvenvcfg, 'w', encoding='utf-8') as f: private static boolean installWantedPackages(Path venvDirectory, List packages, List installedPackages, BuildToolLog log) throws IOException { Set pkgsToInstall = new HashSet<>(packages); - pkgsToInstall.removeAll(installedPackages); + installedPackages.forEach(pkgsToInstall::remove); if (pkgsToInstall.isEmpty()) { return false; } @@ -948,7 +994,7 @@ private static boolean deleteUnwantedPackages(Path venvDirectory, List p } args.add(0, "-y"); - runPip(venvDirectory, "uninstall", log, args.toArray(new String[args.size()])); + runPip(venvDirectory, "uninstall", log, args.toArray(new String[0])); return true; } @@ -968,7 +1014,7 @@ private static void runPip(Path venvDirectory, String command, BuildToolLog log, throw new IOException(String.format("failed to execute pip %s", List.of(args)), e); } } - + @SuppressWarnings("SameParameterValue") private static void runVenvBin(Path venvDirectory, String bin, BuildToolLog log, String... args) throws IOException { try { @@ -980,6 +1026,7 @@ private static void runVenvBin(Path venvDirectory, String bin, BuildToolLog log, private static List trim(List l) { Iterator it = l.iterator(); + // noinspection Java8CollectionRemoveIf while (it.hasNext()) { String p = it.next(); if (p == null || p.trim().isEmpty()) { @@ -1000,6 +1047,7 @@ private static void info(BuildToolLog log, String txt, Object... args) { } } + @SuppressWarnings("SameParameterValue") private static void lifecycle(BuildToolLog log, String txt, Object... args) { if (log.isLifecycleEnabled()) { log.lifecycle(String.format(txt, args)); diff --git a/org.graalvm.python.embedding.tools/src/test/java/org/graalvm/python/embedding/tools/test/EmbeddingTestUtils.java b/org.graalvm.python.embedding.tools/src/test/java/org/graalvm/python/embedding/tools/test/EmbeddingTestUtils.java index ea8074a..21e4d43 100644 --- a/org.graalvm.python.embedding.tools/src/test/java/org/graalvm/python/embedding/tools/test/EmbeddingTestUtils.java +++ b/org.graalvm.python.embedding.tools/src/test/java/org/graalvm/python/embedding/tools/test/EmbeddingTestUtils.java @@ -71,7 +71,7 @@ public static void createVenv(Path venvDir, String graalPyVersion, BuildToolLog Launcher launcher = createLauncher(venvDir); if (lockFile != null) { VFSUtils.createVenv(venvDir, Arrays.asList(packages), lockFile, missingLockFileWarning, launcher, - graalPyVersion, log); + graalPyVersion, log, null); } else { VFSUtils.createVenv(venvDir, Arrays.asList(packages), launcher, graalPyVersion, log); } diff --git a/org.graalvm.python.embedding.tools/src/test/java/org/graalvm/python/embedding/tools/test/VFSUtilsTest.java b/org.graalvm.python.embedding.tools/src/test/java/org/graalvm/python/embedding/tools/test/VFSUtilsTest.java index 2fef207..2013941 100644 --- a/org.graalvm.python.embedding.tools/src/test/java/org/graalvm/python/embedding/tools/test/VFSUtilsTest.java +++ b/org.graalvm.python.embedding.tools/src/test/java/org/graalvm/python/embedding/tools/test/VFSUtilsTest.java @@ -108,12 +108,12 @@ private void clearOutput() { public void subProcessOut(String s) { println("[subout] ", s); - addLine(s.toString()); + addLine(s); } public void subProcessErr(String s) { println("[suberr] ", s); - addLine(s.toString()); + addLine(s); } public void info(String s) { @@ -185,7 +185,7 @@ private static boolean isVerbose() { /** * tests scenarios without lock file logic available, but not used - * + *

* - packages declared only in plugin config - lock file path is provided, but * does not exist */ @@ -203,7 +203,7 @@ public void withPackagesOnlyFromPluginConfig() throws IOException, PackagesChang Path lockFile = tmpDir.resolve("lockFile.txt"); Path contents = venvDir.resolve("contents"); - // no packages, lock file file does not exist - does nothing + // no packages, lock file does not exist - does nothing log.clearOutput(); createVenv(venvDir, "0.1", log, lockFile); assertFalse(Files.exists(venvDir)); @@ -324,23 +324,22 @@ public void lockFile() throws IOException { createWithLockFile(venvDir, lockFile, log); - List validLockFileHeader = createLockFileHeader("0.1", "pkg"); + List validLockFileHeader = createLockFileHeader("pkg"); List lockFileList; - int headerLineCount = LOCK_FILE_HEADER.split("\n").length; // bogus graalPyVersion line - int graalpVersionLineIdx = headerLineCount; + int graalpyVersionLineIdx = LOCK_FILE_HEADER.split("\n").length; lockFileList = new ArrayList<>(validLockFileHeader); - lockFileList.set(graalpVersionLineIdx, "test"); + lockFileList.set(graalpyVersionLineIdx, "test"); createWithLockFile(venvDir, lockFile, log, lockFileList); // empty graalPyVersion line lockFileList = new ArrayList<>(validLockFileHeader); - lockFileList.set(graalpVersionLineIdx, GRAALPY_VERSION_PREFIX); + lockFileList.set(graalpyVersionLineIdx, GRAALPY_VERSION_PREFIX); createWithLockFile(venvDir, lockFile, log, lockFileList); lockFileList = new ArrayList<>(validLockFileHeader); - lockFileList.set(graalpVersionLineIdx, GRAALPY_VERSION_PREFIX + " "); + lockFileList.set(graalpyVersionLineIdx, GRAALPY_VERSION_PREFIX + " "); createWithLockFile(venvDir, lockFile, log, lockFileList); // bogus input packages line @@ -379,12 +378,12 @@ private static void lock(Path venvDir, Path lockFile, TestLog log, String... pac "0.1", log); } - private static List createLockFileHeader(String graalPyVersion, String... packages) { + private static List createLockFileHeader(String... packages) { List lines = new ArrayList<>(); for (String s : LOCK_FILE_HEADER.split("\n")) { lines.add("# " + s); } - lines.add(GRAALPY_VERSION_PREFIX + graalPyVersion); + lines.add(GRAALPY_VERSION_PREFIX + "0.1"); lines.add(INPUT_PACKAGES_PREFIX + String.join(",", packages)); return lines; } @@ -594,30 +593,43 @@ public void packageRemoved() deleteDirOnShutdown(tmpDir); assertFalse(callPackageRemoved(Collections.emptyList(), Collections.emptyList(), Collections.emptyList())); - assertFalse(callPackageRemoved(Arrays.asList("pkg1"), Collections.emptyList(), Collections.emptyList())); - assertFalse(callPackageRemoved(Arrays.asList("pkg1"), Arrays.asList("pkg1"), Arrays.asList("pkg1==1"))); - assertFalse(callPackageRemoved(Arrays.asList("pkg1", "pkg2"), Arrays.asList("pkg1"), Arrays.asList("pkg1==1"))); + assertFalse(callPackageRemoved(Collections.singletonList("pkg1"), Collections.emptyList(), + Collections.emptyList())); + assertFalse(callPackageRemoved(Collections.singletonList("pkg1"), Collections.singletonList("pkg1"), + Collections.singletonList("pkg1==1"))); + assertFalse(callPackageRemoved(Arrays.asList("pkg1", "pkg2"), Collections.singletonList("pkg1"), + Collections.singletonList("pkg1==1"))); assertFalse(callPackageRemoved(Arrays.asList("pkg1", "pkg2"), Arrays.asList("pkg1", "pkg2"), Arrays.asList("pkg1==1", "pkg2==1"))); - assertFalse(callPackageRemoved(Arrays.asList("pkg1=="), Arrays.asList("pkg1=="), Arrays.asList("pkg1==1"))); - assertFalse(callPackageRemoved(Arrays.asList("==pkg1"), Arrays.asList("==pkg1"), Arrays.asList("pkg1==1"))); - assertFalse(callPackageRemoved(Arrays.asList("pkg1==1"), Arrays.asList("pkg1"), Arrays.asList("pkg1==1"))); - assertFalse(callPackageRemoved(Arrays.asList("pkg1"), Arrays.asList("pkg1"), Arrays.asList("pkg1==1"))); - - assertTrue(callPackageRemoved(Collections.emptyList(), Arrays.asList("pkg"), Arrays.asList("pkg==1"))); - assertTrue(callPackageRemoved(Arrays.asList("pkg2"), Arrays.asList("pkg1"), Arrays.asList("pkg1==1"))); - assertTrue(callPackageRemoved(Arrays.asList("pkg1"), Arrays.asList("pkg1", "pkg2"), + assertFalse(callPackageRemoved(Collections.singletonList("pkg1=="), Collections.singletonList("pkg1=="), + Collections.singletonList("pkg1==1"))); + assertFalse(callPackageRemoved(Collections.singletonList("==pkg1"), Collections.singletonList("==pkg1"), + Collections.singletonList("pkg1==1"))); + assertFalse(callPackageRemoved(Collections.singletonList("pkg1==1"), Collections.singletonList("pkg1"), + Collections.singletonList("pkg1==1"))); + assertFalse(callPackageRemoved(Collections.singletonList("pkg1"), Collections.singletonList("pkg1"), + Collections.singletonList("pkg1==1"))); + + assertTrue(callPackageRemoved(Collections.emptyList(), Collections.singletonList("pkg"), + Collections.singletonList("pkg==1"))); + assertTrue(callPackageRemoved(Collections.singletonList("pkg2"), Collections.singletonList("pkg1"), + Collections.singletonList("pkg1==1"))); + assertTrue(callPackageRemoved(Collections.singletonList("pkg1"), Arrays.asList("pkg1", "pkg2"), Arrays.asList("pkg1==1", "pkg2==1"))); - assertTrue(callPackageRemoved(Arrays.asList("pkg1"), Arrays.asList("pkg1=="), Arrays.asList("pkg1==1"))); - assertTrue(callPackageRemoved(Arrays.asList("pkg1=="), Arrays.asList("pkg1"), Arrays.asList("pkg1==1"))); - assertTrue(callPackageRemoved(Arrays.asList("==pkg1"), Arrays.asList("pkg1"), Arrays.asList("pkg1==1"))); + assertTrue(callPackageRemoved(Collections.singletonList("pkg1"), Collections.singletonList("pkg1=="), + Collections.singletonList("pkg1==1"))); + assertTrue(callPackageRemoved(Collections.singletonList("pkg1=="), Collections.singletonList("pkg1"), + Collections.singletonList("pkg1==1"))); + assertTrue(callPackageRemoved(Collections.singletonList("==pkg1"), Collections.singletonList("pkg1"), + Collections.singletonList("pkg1==1"))); - assertTrue(callPackageRemoved(Arrays.asList("pkg1==2"), Arrays.asList("pkg1==1"), Arrays.asList("pkg1==1"))); - assertTrue(callPackageRemoved(Arrays.asList("pkg1==2"), Arrays.asList("pkg1==1", "pkg2==1"), + assertTrue(callPackageRemoved(Collections.singletonList("pkg1==2"), Collections.singletonList("pkg1==1"), + Collections.singletonList("pkg1==1"))); + assertTrue(callPackageRemoved(Collections.singletonList("pkg1==2"), Arrays.asList("pkg1==1", "pkg2==1"), Arrays.asList("pkg1==1", "pkg2==1"))); - assertTrue(callPackageRemoved(Arrays.asList("pkg1==2"), Arrays.asList("pkg1", "pkg2"), + assertTrue(callPackageRemoved(Collections.singletonList("pkg1==2"), Arrays.asList("pkg1", "pkg2"), Arrays.asList("pkg1==1", "pkg2==1"))); } @@ -714,7 +726,7 @@ private static void checkLockFile(Path lockFile, String[] inputPackages, String. throws IOException { assertTrue(Files.exists(lockFile)); List lines = Files.readAllLines(lockFile); - List header = createLockFileHeader("0.1", inputPackages); + List header = createLockFileHeader(inputPackages); assertTrue(lines.size() >= header.size()); for (int i = 0; i < header.size(); i++) { assertEquals(header.get(i), lines.get(i)); diff --git a/org.graalvm.python.gradle.plugin/build.gradle b/org.graalvm.python.gradle.plugin/build.gradle index b9459ff..0a875ae 100644 --- a/org.graalvm.python.gradle.plugin/build.gradle +++ b/org.graalvm.python.gradle.plugin/build.gradle @@ -15,6 +15,14 @@ def polyglotVersion = project.properties.getOrDefault('polyglot.version', versio repositories { mavenLocal() mavenCentral() + if (project.hasProperty('localRepoUrl')) { + def path = project.localRepoUrl?.trim() + if (path) { + maven { + url uri(project.localRepoUrl) + } + } + } } gradlePlugin { @@ -30,6 +38,14 @@ java { sourceCompatibility = JavaVersion.VERSION_17 targetCompatibility = JavaVersion.VERSION_17 withSourcesJar() + withJavadocJar() +} + +tasks.withType(Javadoc).configureEach { + failOnError = false + options.addBooleanOption('Xdoclint:none', true) + options.addBooleanOption('quiet', true) + options.encoding = 'UTF-8' } sourceSets.main.java.srcDirs += ['../org.graalvm.python.embedding.tools/src/main/java'] diff --git a/org.graalvm.python.gradle.plugin/pom.xml b/org.graalvm.python.gradle.plugin/pom.xml index 3f8d940..9b850a7 100644 --- a/org.graalvm.python.gradle.plugin/pom.xml +++ b/org.graalvm.python.gradle.plugin/pom.xml @@ -133,6 +133,7 @@ SOFTWARE. -Dorg.gradle.java.home=${gradle.java.home} -Pversion=${revision} -Ppolyglot.version=${project.polyglot.version} + -PlocalRepoUrl=${local.repo.url} build @@ -150,6 +151,7 @@ SOFTWARE. -Dorg.gradle.java.home=${gradle.java.home} -Pversion=${revision} -Ppolyglot.version=${project.polyglot.version} + -PlocalRepoUrl=${local.repo.url} clean @@ -167,6 +169,7 @@ SOFTWARE. -Dorg.gradle.java.home=${gradle.java.home} -Pversion=${revision} -Ppolyglot.version=${project.polyglot.version} + -PlocalRepoUrl=${local.repo.url} publishToMavenLocal @@ -184,6 +187,7 @@ SOFTWARE. -Dorg.gradle.java.home=${gradle.java.home} -Pversion=${revision} -Ppolyglot.version=${project.polyglot.version} + -PlocalRepoUrl=${local.repo.url} -PaltDeploymentRepository=${altDeploymentRepository} publish diff --git a/org.graalvm.python.gradle.plugin/src/main/java/org/graalvm/python/tasks/InstallPackagesTask.java b/org.graalvm.python.gradle.plugin/src/main/java/org/graalvm/python/tasks/InstallPackagesTask.java index 92f6e82..5eccd30 100644 --- a/org.graalvm.python.gradle.plugin/src/main/java/org/graalvm/python/tasks/InstallPackagesTask.java +++ b/org.graalvm.python.gradle.plugin/src/main/java/org/graalvm/python/tasks/InstallPackagesTask.java @@ -98,7 +98,7 @@ public void exec() throws GradleException { Path lockFilePath = getLockFilePath(); try { VFSUtils.createVenv(venvDirectory, getPackages().get(), lockFilePath, MISSING_LOCK_FILE_WARNING, - createLauncher(), getPolyglotVersion().get(), getLog()); + createLauncher(), getPolyglotVersion().get(), getLog(), null); } catch (PackagesChangedException pce) { String pluginPkgsString = pce.getPluginPackages().isEmpty() ? "None" diff --git a/pom.xml b/pom.xml index 78d3321..dfd49f7 100644 --- a/pom.xml +++ b/pom.xml @@ -131,6 +131,25 @@ + + + org.graalvm.python + ${project.python.artifact} + ${project.polyglot.version} + pom + + + org.graalvm.polyglot + ${project.python.artifact} + ${project.polyglot.version} + pom + + + org.graalvm.python + python-launcher + ${project.polyglot.version} + + @@ -172,15 +191,6 @@ org.apache.maven.plugins maven-compiler-plugin 3.14.0 - - 17 - 17 - 17 - - -Xlint:all - -Werror - - org.apache.maven.plugins @@ -261,17 +271,10 @@ maven-surefire-plugin 3.5.3 - org.apache.maven.plugins maven-javadoc-plugin 3.11.2 - - false - - -Xdoclint:none - - @@ -305,6 +308,19 @@ + + org.apache.maven.plugins + maven-compiler-plugin + + 17 + 17 + 17 + + -Xlint:all + -Werror + + + org.apache.maven.plugins @@ -327,6 +343,25 @@ + + + org.apache.maven.plugins + maven-javadoc-plugin + + false + + -Xdoclint:none + + + + + attach-javadocs + + jar + + + + org.apache.maven.plugins