Skip to content

Commit

Permalink
feat: add constructor (#541)
Browse files Browse the repository at this point in the history
Adds constructors for:
- LockFile 
- Environment 
	
Also adds missing docs to website
  • Loading branch information
tarunps authored Feb 26, 2024
1 parent a008932 commit d253e65
Show file tree
Hide file tree
Showing 15 changed files with 145 additions and 19 deletions.
24 changes: 12 additions & 12 deletions py-rattler/Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

3 changes: 3 additions & 0 deletions py-rattler/docs/environment.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
# Environment

::: rattler.lock.environment
3 changes: 3 additions & 0 deletions py-rattler/docs/environment_creation_error.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
# EnvironmentCreationError

::: rattler.exceptions.EnvironmentCreationError
3 changes: 3 additions & 0 deletions py-rattler/docs/lock_file.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
# LockFile

::: rattler.lock.LockFile
3 changes: 3 additions & 0 deletions py-rattler/docs/locked_package.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
# LockedPackage

::: rattler.lock.LockedPackage
3 changes: 3 additions & 0 deletions py-rattler/docs/package_hashes.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
# PackageHashes

::: rattler.lock.PackageHashes
3 changes: 3 additions & 0 deletions py-rattler/docs/pypi_package_data.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
# PypiPackageData

::: rattler.lock.PypiPackageData
3 changes: 3 additions & 0 deletions py-rattler/docs/pypi_package_environment_data.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
# PypiPackageEnvironmentData

::: rattler.lock.PypiPackageEnvironmentData
8 changes: 8 additions & 0 deletions py-rattler/mkdocs.yml
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,13 @@ nav:
- channel:
- ChannelConfig: channel_config.md
- Channel: channel.md
- lock:
- LockFile: lock_file.md
- Environment: environment.md
- LockedPackage: locked_package.md
- PackageHashes: package_hashes.md
- PypiPackageData: pypi_package_data.md
- PypiPackageEnvironmentData: pypi_package_environment_data.md
- metadata:
- AboutJson: about_json.md
- match_spec:
Expand Down Expand Up @@ -76,6 +83,7 @@ nav:
- ActivationError: activation_error.md
- CacheDirError: cache_dir_error.md
- DetectVirtualPackageError: detect_virtual_package_error.md
- EnvironmentCreationError: environment_creation_error.md
- FetchRepoDataError: fetch_repo_data_error.md
- InvalidChannelError: invalid_channel_error.md
- InvalidMatchSpecError: invalid_match_spec_error.md
Expand Down
5 changes: 5 additions & 0 deletions py-rattler/rattler/exceptions.py
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@
SolverError,
ConvertSubdirError,
VersionBumpError,
EnvironmentCreationError,
)
except ImportError:
# They are only redefined for documentation purposes
Expand Down Expand Up @@ -73,6 +74,9 @@ class ConvertSubdirError(Exception): # type: ignore[no-redef]
class VersionBumpError(Exception): # type: ignore[no-redef]
"""An error that can occur when bumping a version."""

class EnvironmentCreationError(Exception): # type: ignore[no-redef]
"""An error that can occur when creating an environment."""


__all__ = [
"ActivationError",
Expand All @@ -92,4 +96,5 @@ class VersionBumpError(Exception): # type: ignore[no-redef]
"TransactionError",
"ConvertSubdirError",
"VersionBumpError",
"EnvironmentCreationError",
]
12 changes: 12 additions & 0 deletions py-rattler/rattler/lock/environment.py
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,18 @@ class Environment:

_env: PyEnvironment

def __init__(
self, name: str, requirements: Dict[Platform, List[RepoDataRecord]]
) -> None:
self._env = PyEnvironment(
name,
# TODO: move this logic to rust
{
platform._inner: [record._record for record in records]
for (platform, records) in requirements.items()
},
)

def platforms(self) -> List[Platform]:
"""
Returns all the platforms for which we have a locked-down environment.
Expand Down
5 changes: 4 additions & 1 deletion py-rattler/rattler/lock/lock_file.py
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
from __future__ import annotations
import os
from typing import List, Optional, Tuple
from typing import Dict, List, Optional, Tuple
from rattler.lock.environment import Environment

from rattler.rattler import PyLockFile
Expand All @@ -14,6 +14,9 @@ class LockFile:

_lock_file: PyLockFile

def __init__(self, envs: Dict[str, Environment]) -> None:
self._lock_file = PyLockFile({name: env._env for (name, env) in envs.items()})

@staticmethod
def from_path(path: os.PathLike[str]) -> LockFile:
"""
Expand Down
6 changes: 6 additions & 0 deletions py-rattler/src/error.rs
Original file line number Diff line number Diff line change
Expand Up @@ -57,6 +57,8 @@ pub enum PyRattlerError {
ConversionError(#[from] ConversionError),
#[error("{0}")]
RequirementError(String),
#[error("{0}")]
EnvironmentCreationError(String),
}

impl From<PyRattlerError> for PyErr {
Expand Down Expand Up @@ -100,6 +102,9 @@ impl From<PyRattlerError> for PyErr {
}
PyRattlerError::ConversionError(err) => ConversionException::new_err(err.to_string()),
PyRattlerError::RequirementError(err) => RequirementException::new_err(err),
PyRattlerError::EnvironmentCreationError(err) => {
EnvironmentCreationException::new_err(err)
}
}
}
}
Expand All @@ -124,3 +129,4 @@ create_exception!(exceptions, VersionBumpException, PyException);
create_exception!(exceptions, ParseCondaLockException, PyException);
create_exception!(exceptions, ConversionException, PyException);
create_exception!(exceptions, RequirementException, PyException);
create_exception!(exceptions, EnvironmentCreationException, PyException);
16 changes: 12 additions & 4 deletions py-rattler/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -23,10 +23,11 @@ use about_json::PyAboutJson;
use channel::{PyChannel, PyChannelConfig};
use error::{
ActivationException, CacheDirException, ConvertSubdirException, DetectVirtualPackageException,
FetchRepoDataException, InvalidChannelException, InvalidMatchSpecException,
InvalidPackageNameException, InvalidUrlException, InvalidVersionException, IoException,
LinkException, ParseArchException, ParsePlatformException, PyRattlerError, SolverException,
TransactionException, VersionBumpException,
EnvironmentCreationException, FetchRepoDataException, InvalidChannelException,
InvalidMatchSpecException, InvalidPackageNameException, InvalidUrlException,
InvalidVersionException, IoException, LinkException, ParseArchException,
ParsePlatformException, PyRattlerError, SolverException, TransactionException,
VersionBumpException,
};
use generic_virtual_package::PyGenericVirtualPackage;
use lock::{
Expand Down Expand Up @@ -162,5 +163,12 @@ fn rattler(py: Python<'_>, m: &PyModule) -> PyResult<()> {
.unwrap();
m.add("VersionBumpError", py.get_type::<VersionBumpException>())
.unwrap();

m.add(
"EnvironmentCreationError",
py.get_type::<EnvironmentCreationException>(),
)
.unwrap();

Ok(())
}
67 changes: 65 additions & 2 deletions py-rattler/src/lock/mod.rs
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
use std::{
collections::{BTreeSet, HashMap},
collections::{BTreeSet, HashMap, HashSet},
path::PathBuf,
str::FromStr,
};
Expand All @@ -12,7 +12,11 @@ use rattler_lock::{
PypiPackageEnvironmentData,
};

use crate::{error::PyRattlerError, platform::PyPlatform, record::PyRecord};
use crate::{
error::PyRattlerError,
platform::PyPlatform,
record::{self, PyRecord},
};

/// Represents a lock-file for both Conda packages and Pypi packages.
///
Expand All @@ -38,6 +42,31 @@ impl From<PyLockFile> for LockFile {

#[pymethods]
impl PyLockFile {
#[new]
pub fn new(envs: HashMap<String, PyEnvironment>) -> PyResult<Self> {
let mut lock = LockFile::builder();
for (name, env) in envs {
lock.set_channels(&name, env.channels());
for (platform, records) in env
.inner
.conda_repodata_records()
.map_err(PyRattlerError::from)?
{
for record in records {
lock.add_conda_package(&name, platform, record.into());
}
}

for (platform, records) in env.inner.pypi_packages() {
for (pkg_data, pkg_env_data) in records {
lock.add_pypi_package(&name, platform, pkg_data, pkg_env_data);
}
}
}

Ok(lock.finish().into())
}

/// Writes the conda lock to a file
pub fn to_path(&self, path: PathBuf) -> PyResult<()> {
Ok(self.inner.to_path(&path).map_err(PyRattlerError::from)?)
Expand Down Expand Up @@ -91,6 +120,40 @@ impl From<PyEnvironment> for Environment {

#[pymethods]
impl PyEnvironment {
#[new]
pub fn new(name: String, req: HashMap<PyPlatform, Vec<PyRecord>>) -> PyResult<Self> {
let mut lock = LockFile::builder();
let channels = req
.values()
.flat_map(|records| {
records
.iter()
.map(record::PyRecord::channel)
.collect::<Vec<PyResult<_>>>()
})
.collect::<PyResult<HashSet<_>>>()?;

lock.set_channels(&name, channels);

for (platform, records) in req {
for record in records {
lock.add_conda_package(
&name,
platform.inner,
record.try_as_repodata_record()?.clone().into(),
);
}
}

Ok(lock
.finish()
.environment(&name)
.ok_or(PyRattlerError::EnvironmentCreationError(
"Environment creation failed.".into(),
))?
.into())
}

/// Returns all the platforms for which we have a locked-down environment.
pub fn platforms(&self) -> Vec<PyPlatform> {
self.inner.platforms().map(Into::into).collect::<Vec<_>>()
Expand Down

0 comments on commit d253e65

Please sign in to comment.