8000 Merge pull request #83 from scijava/config-cjdk · scijava/scyjava@60008a5 · GitHub
[go: up one dir, main page]

Skip to content

Commit 60008a5

Browse files
authored
Merge pull request #83 from scijava/config-cjdk
Configure cjdk behavior via scyjava.config
2 parents 0b2e964 + 630ff9d commit 60008a5

File tree

4 files changed

+159
-38
lines changed

4 files changed

+159
-38
lines changed

src/scyjava/__init__.py

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,22 @@
4040
+++oo*OO######O**oo+++++oo*OO######O**oo+++++oo*OO######O**oo+++
4141
+++oo*OO######OO*oo+++++oo*OO######OO*oo+++++oo*OO######OO*oo+++
4242
43+
Bootstrap a Java installation:
44+
45+
>>> from scyjava import config, jimport
46+
>>> config.set_java_constraints(fetch=True, vendor='zulu', version='17')
47+
>>> System = jimport('java.lang.System')
48+
cjdk: Installing JDK zulu:17.0.15 to /home/chuckles/.cache/cjdk
49+
Download 100% of 189.4 MiB |##########| Elapsed Time: 0:00:02 Time: 0:00:02
50+
Extract | | # | 714 Elapsed Time: 0:00:01
51+
cjdk: Installing Maven to /home/chuckles/.cache/cjdk
52+
Download 100% of 8.7 MiB |##########| Elapsed Time: 0:00:00 Time: 0:00:00
53+
Extract | |# | 102 Elapsed Time: 0:00:00
54+
>>> System.getProperty('java.vendor')
55+
'Azul Systems, Inc.'
56+
>>> System.getProperty('java.version')
57+
'17.0.15'< 8000 /span>
58+
4359
Convert Java collections to Python:
4460
4561
>>> from scyjava import jimport

src/scyjava/_cjdk_fetch.py

Lines changed: 28 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,7 @@
1+
"""
2+
Utility functions for fetching JDK/JRE and Maven.
3+
"""
4+
15
from __future__ import annotations
26

37
import logging
@@ -9,21 +13,23 @@
913
import cjdk
1014
import jpype
1115

16+
import scyjava.config
17+
1218
if TYPE_CHECKING:
1319
from pathlib import Path
1420

1521
_logger = logging.getLogger(__name__)
16-
_DEFAULT_MAVEN_URL = "tgz+https://dlcdn.apache.org/maven/maven-3/3.9.9/binaries/apache-maven-3.9.9-bin.tar.gz" # noqa: E501
17-
_DEFAULT_MAVEN_SHA = "a555254d6b53d267965a3404ecb14e53c3827c09c3b94b5678835887ab404556bfaf78dcfe03ba76fa2508649dca8531c74bca4d5846513522404d48e8c4ac8b" # noqa: E501
18-
_DEFAULT_JAVA_VENDOR = "zulu-jre"
19-
_DEFAULT_JAVA_VERSION = "11"
2022

2123

2224
def ensure_jvm_available() -> None:
2325
"""Ensure that the JVM is available and Maven is installed."""
24-
if not is_jvm_available():
26+
fetch = scyjava.config.get_fetch_java()
27+
if fetch == "never":
28+
# Not allowed to use cjdk.
29+
return
30+
if fetch == "always" or not is_jvm_available():
2531
cjdk_fetch_java()
26-
if not shutil.which("mvn"):
32+
if fetch == "always" or not shutil.which("mvn"):
2733
cjdk_fetch_maven()
2834

2935

@@ -47,27 +53,27 @@ def _silent_check_output(*args, **kwargs):
4753
return True
4854

4955

50-
def cjdk_fetch_java(vendor: str = "", version: str = "") -> None:
56+
def cjdk_fetch_java(vendor: str | None = None, version: str | None = None) -> None:
5157
"""Fetch java using cjdk and add it to the PATH."""
52-
if not vendor:
53-
vendor = os.getenv("JAVA_VENDOR", _DEFAULT_JAVA_VENDOR)
54-
version = os.getenv("JAVA_VERSION", _DEFAULT_JAVA_VERSION)
58+
if vendor is None:
59+
vendor = scyjava.config.get_java_vendor()
60+
if version is None:
61+
version = scyjava.config.get_java_version()
5562

56-
_logger.info(f"No JVM found, fetching {vendor}:{version} using cjdk...")
57-
home = cjdk.java_home(vendor=vendor, version=version)
58-
_add_to_path(str(home / "bin"))
59-
os.environ["JAVA_HOME"] = str(home)
63+
_logger.info(f"Fetching {vendor}:{version} using cjdk...")
64+
java_home = cjdk.java_home(vendor=vendor, version=version)
65+
_logger.debug(f"java_home -> {java_home}")
66+
_add_to_path(str(java_home / "bin"), front=True)
67+
os.environ["JAVA_HOME"] = str(java_home)
6068

6169

6270
def cjdk_fetch_maven(url: str = "", sha: str = "") -> None:
6371
"""Fetch Maven using cjdk and add it to the PATH."""
64-
# if url was passed as an argument, or env_var, use it with provided sha
72+
# if url was passed as an argument, use it with provided sha
6573
# otherwise, use default values for both
66-
if url := url or os.getenv("MAVEN_URL", ""):
67-
sha = sha or os.getenv("MAVEN_SHA", "")
68-
else:
69-
url = _DEFAULT_MAVEN_URL
70-
sha = _DEFAULT_MAVEN_SHA
74+
if not url:
75+
url = scyjava.config.get_maven_url()
76+
sha = scyjava.config.get_maven_sha()
7177

7278
# fix urls to have proper prefix for cjdk
7379
if url.startswith("http"):
@@ -88,7 +94,9 @@ def cjdk_fetch_maven(url: str = "", sha: str = "") -> None:
8894
)
8995
kwargs = {sha_lengths[sha_len]: sha}
9096

97+
_logger.info("Fetching Maven using cjdk...")
9198
maven_dir = cjdk.cache_package("Maven", url, **kwargs)
99+
_logger.debug(f"maven_dir -> {maven_dir}")
92100
if maven_bin := next(maven_dir.rglob("apache-maven-*/**/mvn"), None):
93101
_add_to_path(maven_bin.parent, front=True)
94102
else: # pragma: no cover

src/scyjava/_jvm.py

Lines changed: 5 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -11,13 +11,15 @@
1111
from functools import lru_cache
1212
from importlib import import_module
1313
from pathlib import Path
14+
from typing import Sequence
1415

1516
import jpype
1617
import jpype.config
1718
from jgo import jgo
1819

1920
import scyjava.config
2021
from scyjava.config import Mode, mode
22+
from scyjava._cjdk_fetch import ensure_jvm_available
2123

2224
_logger = logging.getLogger(__name__)
2325

@@ -106,7 +108,7 @@ def jvm_version() -> tuple[int, ...]:
106108
return tuple(map(int, m.group(1).split(".")))
107109

108110

109-
def start_jvm(options=None, *, fetch_java: bool = True) -> None:
111+
def start_jvm(options: Sequence[str] = None) -> None:
110112
"""
111113
Explicitly connect to the Java virtual machine (JVM). Only one JVM can
112114
be active; does nothing if the JVM has already been started. Calling
@@ -118,19 +120,6 @@ def start_jvm(options=None, *, fetch_java: bool = True) -> None:
118120
List of options to pass to the JVM.
119121
For example: ['-Dfoo=bar', '-XX:+UnlockExperimentalVMOptions']
120122
See also scyjava.config.add_options.
121-
:param fetch_java:
122-
If True (default), when a JVM/or maven cannot be located on the system,
123-
[`cjdk`](https://github.com/cachedjdk/cjdk) will be used to download
124-
a JRE distribution and set up the JVM. The following environment variables
125-
may be used to configure the JRE and Maven distributions to download:
126-
* `JAVA_VENDOR`: The vendor of the JRE distribution to download.
127-
Defaults to "zulu-jre".
128-
* `JAVA_VERSION`: The version of the JRE distribution to download.
129-
Defaults to "11".
130-
* `MAVEN_URL`: The URL of the Maven distribution to download.
131-
Defaults to https://dlcdn.apache.org/maven/maven-3/3.9.9/
132-
* `MAVEN_SHA`: The SHA512 hash of the Maven distribution to download, if
133-
providing a custom MAVEN_URL.
134123
"""
135124
# if JVM is already running -- break
136125
if jvm_started():
@@ -147,10 +136,8 @@ def start_jvm(options=None, *, fetch_java: bool = True) -> None:
147136
# use the logger to notify user that endpoints are being added
148137
_logger.debug("Adding jars from endpoints {0}".format(endpoints))
149138

150-
if fetch_java:
151-
from scyjava._cjdk_fetch import ensure_jvm_available
152-
153-
ensure_jvm_available()
139+
# download JDK/JRE and Maven as appropriate
140+
ensure_jvm_available()
154141

155142
# get endpoints and add to JPype class path
156143
if len(endpoints) > 0:

src/scyjava/config.py

Lines changed: 110 additions & 0 deletions
< 1CF5 tr class="diff-line-row">
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,13 @@
1212

1313
_logger = _logging.getLogger(__name__)
1414

15+
# Constraints on the Java installation to be used.
16+
_fetch_java: str = "auto"
17+
_java_vendor: str = "zulu-jre"
18+
_java_version: str = "11"
19+
_maven_url: str = "tgz+https://dlcdn.apache.org/maven/maven-3/3.9.9/binaries/apache-maven-3.9.9-bin.tar.gz" # noqa: E501
20+
_maven_sha: str = "a555254d6b53d267965a3404ecb14e53c3827c09c3b94b5678835887ab404556bfaf78dcfe03ba76fa2508649dca8531c74bca4d5846513522404d48e8c4ac8b" # noqa: E501
21+
1522
endpoints: list[str] = []
1623

1724
_repositories = {"scijava.public": _scijava_public()}
@@ -37,6 +44,109 @@ class Mode(_enum.Enum):
3744
mode = Mode.JPYPE
3845

3946

47+
def set_java_constraints(
48+
fetch: str | bool | None = None,
49+
vendor: str | None = None,
50+
version: str | None = None,
51+
maven_url: str | None = None,
52+
maven_sha: str | None = None,
53+
) -> None:
54+
"""
55+
Set constraints on the version of Java to be used.
56+
57+
:param fetch:
58+
If "auto" (default), when a JVM/or maven cannot be located on the system,
59+
[`cjdk`](https://github.com/cachedjdk/cjdk) will be used to download
60+
a JDK/JRE distribution and set up the JVM.
61+
If "always", cjdk will always be used; if "never", cjdk will never be used.
62+
:param vendor:
63+
The vendor of the JDK/JRE distribution for cjdk to download and cache.
64+
Defaults to "zulu-jre". See the cjdk documentation for details.
65+
:param version:
66+
Expression defining the Java version for cjdk to download and cache.
67+
Defaults to "11". See the cjdk documentation for details.
68+
:param maven_url:
69+
URL of the Maven distribution for cjdk to download and cache.
70+
Defaults to the Maven 3.9.9 binary distribution from dlcdn.apache.org.
71+
:param maven_sha:
72+
The SHA512 (or SHA256 or SHA1) hash of the Maven distribution to download,
73+
if providing a custom maven_url.
74+
"""
75+
global _fetch_java, _java_vendor, _java_version, _maven_url, _maven_sha
76+
if fetch is not None:
77+
if isinstance(fetch, bool):
78+
# Be nice and allow boolean values as a convenience.
79+
fetch = "always" if fetch else "never"
80+
expected = ["auto", "always", "never"]
81+
if fetch not in expected:
82+
raise ValueError(f"Fetch mode {fetch} is not one of {expected}")
83+
_fetch_java = fetch
84+
if vendor is not None:
85+
_java_vendor = vendor
86+
if version is not None:
87+
_java_version = version
88+
if maven_url is not None:
89+
_maven_url = maven_url
90+
_maven_sha = ""
91+
if maven_sha is not None:
92+
_maven_sha = maven_sha
93+
94+
95+
def get_fetch_java() -> str:
96+
"""
97+
Get whether [`cjdk`](https://github.com/cachedjdk/cjdk)
98+
will be used to download a JDK/JRE distribution and set up the JVM.
99+
To set this value, see set_java_constraints.
100+
101+
:return:
102+
"always" for cjdk to obtain the JDK/JRE;
103+
"never" for cjdk *not* to obtain a JDK/JRE;
104+
"auto" for cjdk to be used only when a JVM/or Maven is not on the system path.
105+
"""
106+
return _fetch_java
107+
108+
109+
def get_java_vendor() -> str:
110+
"""
111+
Get the vendor of the JDK/JRE distribution to download.
112+
Vendor of the Java installation for cjdk to download and cache.
113+
To set this value, see set_java_constraints.
114+
115+
:return: String defining the desired JDK/JRE vendor for downloaded JDK/JREs.
116+
"""
117+
return _java_vendor
118+
119+
120+
def get_java_version() -> str:
121+
"""
122+
Expression defining the Java version for cjdk to download and cache.
123+
To set this value, see set_java_constraints.
124+
125+
:return: String defining the desired JDK/JRE version for downloaded JDK/JREs.
126+
"""
127+
return _java_version
128+
129+
130+
def get_maven_url() -> str:
131+
"""
132+
The URL of the Maven distribution to download.
133+
To set this value, see set_java_constraints.
134+
135+
:return: URL pointing to the Maven distribution.
136+
"""
137+
return _maven_url
138+
139+
140+
def get_maven_sha() -> str:
141+
"""
142+
The SHA512 (or SHA256 or SHA1) hash of the Maven distribution to download,
143+
if providing a custom maven_url. To set this value, see set_java_constraints.
144+
145+
:return: Hash value of the Maven distribution, or empty string to skip hash check.
146+
"""
147+
return _maven_sha
148+
149+
40150
def add_repositories(*args, **kwargs) -> None:
41151
"""
42152
Add one or more Maven repositories to be used by jgo for downloading dependencies.

0 commit comments

Comments
 (0)
0