8000 Refactor to eliminate code duplication in test by maresb · Pull Request #790 · conda/conda-lock · GitHub
[go: up one dir, main page]
More Web Proxy on the site http://driver.im/
Skip to content

Refactor to eliminate code duplication in test #790

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 1 commit into from
Apr 2, 2025
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
73 changes: 43 additions & 30 deletions conda_lock/conda_solver.py
Original file line number Diff line number Diff line change
Expand Up @@ -393,6 +393,48 @@ def print_proc(proc: subprocess.CompletedProcess) -> None:
raise RuntimeError(f"Failed to parse json: '{proc.stdout}'") from e


def _get_installed_conda_packages(
conda: PathLike,
platform: str,
prefix: str,
) -> Dict[str, LinkAction]:
"""
Get the installed conda packages for the given prefix.

Try to get installed packages, first with --no-pip flag, then without if that fails.
The --no-pip flag was added in Conda v2.1.0 (2013), but for mamba/micromamba only in
v2.0.7 (March 2025).
"""
try:
output = subprocess.check_output(
[str(conda), "list", "--no-pip", "-p", prefix, "--json"],
env=conda_env_override(platform),
stderr=subprocess.STDOUT,
)
except subprocess.CalledProcessError as e:
err_output = (
e.output.decode("utf-8") if isinstance(e.output, bytes) else e.output
)
if "The following argument was not expected: --no-pip" in err_output:
logger.warning(
f"The '--no-pip' flag is not supported by {conda}. Please consider upgrading."
)
# Retry without --no-pip
output = subprocess.check_output(
[str(conda), "list", "-p", prefix, "--json"],
env=conda_env_override(platform),
stderr=subprocess.STDOUT,
)
else:
# Re-raise if it's a different error.
raise
decoded_output = output.decode("utf-8")
installed: Dict[str, LinkAction] = {
entry["name"]: entry for entry in json.loads(decoded_output)
}
return installed


def update_specs_for_arch(
conda: PathLike,
specs: List[str],
Expand Down Expand Up @@ -422,36 +464,7 @@ def update_specs_for_arch(
"""

with fake_conda_environment(locked.values(), platform=platform) as prefix:
# Try to get installed packages, first with --no-pip flag, then without if that fails.
# The --no-pip flag was added in Conda v2.1.0 (2013), but for mamba/micromamba only in
# v2.0.7 (March 2025).
try:
output = subprocess.check_output(
[str(conda), "list", "--no-pip", "-p", prefix, "--json"],
env=conda_env_override(platform),
stderr=subprocess.STDOUT,
)
except subprocess.CalledProcessError as e:
err_output = (
e.output.decode("utf-8") if isinstance(e.output, bytes) else e.output
)
if "The following argument was not expected: --no-pip" in err_output:
logger.warning(
f"The '--no-pip' flag is not supported by {conda}. Please consider upgrading."
)
# Retry without --no-pip
output = subprocess.check_output(
[str(conda), "list", "-p", prefix, "--json"],
env=conda_env_override(platform),
stderr=subprocess.STDOUT,
)
else:
# Re-raise if it's a different error.
raise
decoded_output = output.decode("utf-8")
installed: Dict[str, LinkAction] = {
entry["name"]: entry for entry in json.loads(decoded_output)
}
installed = _get_installed_conda_packages(conda, platform, prefix)
spec_for_name = {MatchSpec(v).name: v for v in specs} # pyright: ignore
to_update = [
spec_for_name[name] for name in set(installed).intersection(update)
Expand Down
10 changes: 4 additions & 6 deletions tests/test_conda_lock.py
Original file line number Diff line number Diff line change
Expand Up @@ -50,6 +50,7 @@
run_lock,
)
from conda_lock.conda_solver import (
_get_installed_conda_packages,
_get_pkgs_dirs,
extract_json_object,
fake_conda_environment,
Expand All @@ -70,7 +71,6 @@
from conda_lock.lookup import DEFAULT_MAPPING_URL, conda_name_to_pypi_name
from conda_lock.models.channel import Channel
from conda_lock.models.lock_spec import (
Dependency,
PathDependency,
VCSDependency,
VersionedDependency,
Expand Down Expand Up @@ -2792,9 +2792,7 @@ def test_fake_conda_env(conda_exe: str, conda_lock_yaml: Path):
with fake_conda_environment(
lockfile_content.package, platform="linux-64"
) as prefix:
cmd = [str(conda_exe), "list", "--debug", "--no-pip", "-p", prefix, "--json"]
result = subprocess.check_output(cmd)
packages = json.loads(result)
packages = _get_installed_conda_packages(conda_exe, "linux-64", prefix)
locked = {
p.name: p
for p in lockfile_content.package
Expand All @@ -2803,7 +2801,7 @@ def test_fake_conda_env(conda_exe: str, conda_lock_yaml: Path):
if len(packages) != len(locked):
# There's a discrepancy. Do further analysis and raise an error.
locked_names = set(locked.keys())
package_names = {p["name"] for p in packages}
package_names = set(packages.keys())
if len(package_names) != len(packages):
raise RuntimeError(
f"Found duplicate packages in conda list output: {packages}"
Expand All @@ -2815,7 +2813,7 @@ def test_fake_conda_env(conda_exe: str, conda_lock_yaml: Path):
f"{len(locked)} in lockfile: {not_locked} not in lockfile, "
f"{extra_locked} in lockfile but not in conda list output"
)
for env_package in packages:
for env_package in packages.values():
locked_package = locked[env_package["name"]]

platform = env_package["platform"]
Expand Down
Loading
0