Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions docs/changelog/73.bugfix.rst
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
Canonicalize GraalVM to match GraalPy Python interpreter in PythonSpec and PythonInfo. - by :user:`timfel`.
2 changes: 2 additions & 0 deletions src/python_discovery/_py_info.py
Original file line number Diff line number Diff line change
Expand Up @@ -59,6 +59,8 @@ def __init__(self) -> None:
def _init_identity(self) -> None:
self.platform = sys.platform
self.implementation = platform.python_implementation()
if self.implementation == "GraalVM":
self.implementation = "GraalPy"
if self.implementation == "PyPy":
self.pypy_version_info = tuple(sys.pypy_version_info) # ty: ignore[unresolved-attribute] # pypy only

Expand Down
4 changes: 4 additions & 0 deletions src/python_discovery/_py_spec.py
Original file line number Diff line number Diff line change
Expand Up @@ -77,6 +77,8 @@ def _parse_spec_pattern(string_spec: str) -> PythonSpec | None:
impl = groups["impl"]
if impl in {"py", "python"}:
impl = None
if impl == "graalvm":
impl = "graalpy"
arch = _int_or_none(groups["arch"])
machine = groups.get("machine")
if machine is not None:
Expand All @@ -97,6 +99,8 @@ def _parse_specifier(string_spec: str) -> PythonSpec | None:
return None
if impl in {"py", "python"}:
impl = None
if impl == "graalvm":
impl = "graalpy"
return PythonSpec(string_spec, impl, None, None, None, None, None, version_specifier=version_specifier)


Expand Down
6 changes: 6 additions & 0 deletions tests/test_py_info_extra.py
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,12 @@ def test_py_info_pypy_version(mocker: MockerFixture) -> None:
assert info.pypy_version_info == (7, 3, 11, "final", 0)


def test_py_info_canonicalizes_graalvm(mocker: MockerFixture) -> None:
mocker.patch("platform.python_implementation", return_value="GraalVM")
info = PythonInfo()
assert info.implementation == "GraalPy"


def test_has_venv_attribute() -> None:
info = PythonInfo()
assert isinstance(info.has_venv, bool)
Expand Down
13 changes: 13 additions & 0 deletions tests/test_py_spec.py
Original file line number Diff line number Diff line change
Expand Up @@ -155,6 +155,12 @@ def test_specifier_with_implementation() -> None:
assert spec.version_specifier == SpecifierSet.from_string(">=3.12")


def test_specifier_with_graalpy_implementation_alias() -> None:
spec = PythonSpec.from_string_spec("graalvm>=3.12")
assert spec.implementation == "graalpy"
assert spec.version_specifier == SpecifierSet.from_string(">=3.12")


def test_specifier_satisfies_with_partial_information() -> None:
spec = PythonSpec.from_string_spec(">=3.12")
candidate = PythonSpec.from_string_spec("python3.12")
Expand Down Expand Up @@ -245,3 +251,10 @@ def test_normalize_isa(isa: str, normalized: str) -> None:
)
def test_spec_repr_machine(spec_str: str, in_repr: str) -> None:
assert in_repr in repr(PythonSpec.from_string_spec(spec_str))


@pytest.mark.parametrize(("left", "right"), [("graalpy", "graalvm"), ("graalvm", "graalpy")])
def test_spec_satisfies_graalpy_implementation_aliases(left: str, right: str) -> None:
spec_1 = PythonSpec.from_string_spec(left)
spec_2 = PythonSpec.from_string_spec(right)
assert spec_1.satisfies(spec_2) is True