Skip to content

Commit

Permalink
feat: python bindings for PrefixRecord, RepoDataRecord and PackageRec…
Browse files Browse the repository at this point in the history
…ord construction, bind ExplicitEnvironment (#912)
  • Loading branch information
wolfv authored Nov 4, 2024
1 parent a8d5804 commit 84abcda
Show file tree
Hide file tree
Showing 22 changed files with 1,801 additions and 188 deletions.
486 changes: 347 additions & 139 deletions py-rattler/Cargo.lock

Large diffs are not rendered by default.

3 changes: 2 additions & 1 deletion py-rattler/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -49,10 +49,11 @@ reqwest = { version = "0.12.3", default-features = false }
reqwest-middleware = "0.3.0"

thiserror = "1.0.61"
url = "2.5.0"
url = "2.5.3"

openssl = { version = "0.10", optional = true }
pep508_rs = "0.9.1"
serde_json = "1.0.132"

[build-dependencies]
pyo3-build-config = "0.21"
Expand Down
2 changes: 2 additions & 0 deletions py-rattler/rattler/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@
FileMode,
IndexJson,
)
from rattler.package.no_arch_type import NoArchType
from rattler.prefix import PrefixRecord, PrefixPaths, PrefixPathsEntry, PrefixPathType
from rattler.platform import Platform
from rattler.utils.rattler_version import get_rattler_version as _get_rattler_version
Expand Down Expand Up @@ -88,4 +89,5 @@
"IndexJson",
"Gateway",
"SourceConfig",
"NoArchType",
]
3 changes: 3 additions & 0 deletions py-rattler/rattler/explicit_environment/__init__.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
from rattler.explicit_environment.environment import ExplicitEnvironmentSpec, ExplicitEnvironmentEntry

__all__ = ["ExplicitEnvironmentSpec", "ExplicitEnvironmentEntry"]
69 changes: 69 additions & 0 deletions py-rattler/rattler/explicit_environment/environment.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,69 @@
from pathlib import Path
from typing import List, Optional

from rattler.rattler import PyExplicitEnvironmentSpec as _PyExplicitEnvironmentSpec
from rattler.rattler import PyExplicitEnvironmentEntry as _PyExplicitEnvironmentEntry
from rattler.platform import Platform


class ExplicitEnvironmentEntry:
"""A wrapper around an explicit environment entry which represents a URL to a package"""

def __init__(self, inner: _PyExplicitEnvironmentEntry) -> None:
self._inner = inner

@property
def url(self) -> str:
"""Returns the URL of the package"""
return self._inner.url()


class ExplicitEnvironmentSpec:
"""The explicit environment (e.g. env.txt) file that contains a list of all URLs in a environment"""

def __init__(self, inner: _PyExplicitEnvironmentSpec) -> None:
self._inner = inner

@classmethod
def from_path(cls, path: Path) -> "ExplicitEnvironmentSpec":
"""Parses the object from a file specified by a `path`, using a format appropriate for the file type.
For example, if the file is in text format, this function reads the data from the file at
the specified path, parses the text and returns the resulting object. If the file is
not in a parsable format or if the file could not be read, this function raises an error.
"""
return cls(_PyExplicitEnvironmentSpec.from_path(path))

@classmethod
def from_str(cls, content: str) -> "ExplicitEnvironmentSpec":
"""
Parses the object from a string containing the explicit environment specification
Examples:
```python
>>> spec = ExplicitEnvironmentSpec.from_str('''@EXPLICIT
... # platform: linux-64
... http://repo.anaconda.com/pkgs/main/linux-64/python-3.9.0-h3.tar.bz2
... ''')
>>> spec.platform
Platform(linux-64)
>>> spec.packages[0].url
'http://repo.anaconda.com/pkgs/main/linux-64/python-3.9.0-h3.tar.bz2'
>>>
```
"""
return cls(_PyExplicitEnvironmentSpec.from_str(content))

@property
def platform(self) -> Optional[Platform]:
"""Returns the platform specified in the explicit environment specification"""
platform = self._inner.platform()
if platform is not None:
return Platform._from_py_platform(platform)
return None

@property
def packages(self) -> List[ExplicitEnvironmentEntry]:
"""Returns the environment entries (URLs) specified in the explicit environment specification"""
return [ExplicitEnvironmentEntry(p) for p in self._inner.packages()]
12 changes: 7 additions & 5 deletions py-rattler/rattler/package/no_arch_type.py
Original file line number Diff line number Diff line change
Expand Up @@ -10,13 +10,10 @@ class NoArchType:
def __init__(self, noarch: Optional[str] = None) -> None:
if noarch is None:
self._noarch = PyNoArchType.none()
self._source = None
elif noarch == "python":
self._noarch = PyNoArchType.python()
self._source = "python"
elif noarch == "generic":
self._noarch = PyNoArchType.generic()
self._source = "generic"
else:
raise ValueError(
"NoArchType constructor received unsupported value " f"{noarch} for the `noarch` parameter"
Expand All @@ -27,7 +24,6 @@ def _from_py_no_arch_type(cls, py_no_arch_type: PyNoArchType) -> NoArchType:
"""Construct Rattler NoArchType from FFI PyNoArchType object."""
no_arch_type = cls.__new__(cls)
no_arch_type._noarch = py_no_arch_type
no_arch_type._source = py_no_arch_type
return no_arch_type

@property
Expand Down Expand Up @@ -137,4 +133,10 @@ def __repr__(self) -> str:
>>>
```
"""
return f'NoArchType("{self._source}")'

if self._noarch.is_python:
return 'NoArchType("python")'
elif self._noarch.is_generic:
return 'NoArchType("generic")'
else:
return "NoArchType(None)"
5 changes: 4 additions & 1 deletion py-rattler/rattler/package/paths_json.py
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
from __future__ import annotations
import os
from pathlib import Path
from typing import List, Optional
from typing import List, Optional, Literal
from rattler.rattler import (
PyPathsJson,
PyPathsEntry,
Expand Down Expand Up @@ -456,6 +456,9 @@ class FileMode:

_inner: PyFileMode | None = None

def __init__(self, file_mode: Literal["binary", "text"]) -> None:
self._inner = PyFileMode(file_mode)

@property
def binary(self) -> bool:
"""
Expand Down
17 changes: 16 additions & 1 deletion py-rattler/rattler/platform/platform.py
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
from __future__ import annotations
from typing import Any, Dict, Literal, Tuple
from typing import Any, Dict, Literal, Tuple, Optional

from rattler.rattler import PyPlatform
from rattler.platform.arch import Arch
Expand Down Expand Up @@ -174,3 +174,18 @@ def arch(self) -> Arch:
```
"""
return Arch._from_py_arch(self._inner.arch())

@property
def only_platform(self) -> Optional[str]:
"""
Return the platform without the architecture.
Examples
--------
```python
>>> Platform("linux-64").only_platform
'linux'
>>>
```
"""
return self._inner.only_platform
Loading

0 comments on commit 84abcda

Please sign in to comment.