Skip to content

Commit

Permalink
Merge pull request #60 from mariusvniekerk/typer
Browse files Browse the repository at this point in the history
  • Loading branch information
mariusvniekerk authored Nov 9, 2022
2 parents 0631a83 + 0fedc0b commit 0f25c0a
Show file tree
Hide file tree
Showing 13 changed files with 605 additions and 278 deletions.
19 changes: 12 additions & 7 deletions .github/workflows/pythonpackage.yml
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ on:

jobs:
build:
runs-on: ubuntu-latest
runs-on: ${{ matrix.os }}
strategy:
max-parallel: 6
matrix:
Expand All @@ -21,24 +21,29 @@ jobs:
uses: actions/setup-python@v4
with:
python-version: ${{ matrix.python-version }}
cache: 'pip'
cache-dependency-path: |
pyproject.toml
ci/requirements.txt
- name: Install dependencies
run: |
python -m pip install --upgrade pip build
python -m pip install --upgrade --quiet pip build flake8 pytest
- name: Lint with flake8
run: |
pip install flake8
# stop the build if there are Python syntax errors or undefined names
flake8 . --count --select=E9,F63,F7,F82 --show-source --statistics
# exit-zero treats all errors as warnings. The GitHub editor is 127 chars wide
flake8 . --count --exit-zero --max-complexity=10 --max-line-length=127 --statistics
- name: Test with pytest
- name: Install local editable
run: |
pip install pytest
pip install -e .
pytest .
- name: Test with pytest
run: |
pytest --showlocals -vrsx .
- name: Attempt to install library
run: |
Expand All @@ -58,7 +63,7 @@ jobs:

- name: Run the installed package
run: |
export PATH="$PATH:${HOME}/.local/bin"
$env:Path = "$PATH;${HOME}/.local/bin"
black --help
if: matrix.os == 'windows-latest'

Expand Down
18 changes: 7 additions & 11 deletions .pre-commit-config.yaml
Original file line number Diff line number Diff line change
@@ -1,18 +1,14 @@
minimum_pre_commit_version: '2.9.0'
repos:
- repo: https://github.com/pre-commit/mirrors-isort
rev: v5.10.1
- repo: https://github.com/Zac-HD/shed
rev: 0.10.5
hooks:
- id: isort
args: ["--profile", "black", "--filter-files"]

- repo: https://github.com/psf/black
rev: 22.6.0
hooks:
- id: black
language_version: python3
- id: shed
# args: [--refactor, --py39-plus]
types_or: [python, markdown, rst]

- repo: https://github.com/pre-commit/mirrors-mypy
rev: v0.971
rev: v0.982
hooks:
- id: mypy
additional_dependencies: [types-requests, types-PyYAML]
4 changes: 4 additions & 0 deletions ci/requirements.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
pip
build
pytest
flake8
5 changes: 4 additions & 1 deletion condax/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,4 +5,7 @@
else:
from importlib.metadata import version

__version__ = version(__package__)
try:
__version__ = version(__package__)
except Exception:
__version__ = "unknown"
166 changes: 111 additions & 55 deletions condax/cli.py
Original file line number Diff line number Diff line change
@@ -1,49 +1,100 @@
import sys
from typing import List, Optional

import click
import typer

from . import config, core, paths

cli = typer.Typer(
name="condax",
help="Install and execute applications packaged by conda.",
no_args_is_help=True,
)

@click.group(help="Install and execute applications packaged by conda.")
def cli():
pass
_OPTION_MAMBA = typer.Option(
False,
"--mamba",
help="Force using mamba.",
)
_OPTION_LINK_ACTION = typer.Option(
core.LinkConflictAction.ERROR,
"--link-conflict",
"-l",
help=f"""\
How to handle conflicts when a link with the same name already exists in
`{config.CONFIG.link_destination}`. If `error` is specified, condax will exit with
an error if the link already exists. If `overwrite` is specified, condax will
overwrite the existing link. If `skip` is specified, condax will skip linking the
conflicting executable.""",
)


@cli.command(
help=f"""
Install a package with condax.
help=f"""\
Install a package with condax.
This will install a package into a new conda environment and link the executable
provided by it to `{config.CONDAX_LINK_DESTINATION}`.
"""
)
@click.option(
"--channel",
"-c",
multiple=True,
help=f"""Use the channels specified to install. If not specified condax will
default to using {config.DEFAULT_CHANNELS}.""",
This will install a package into a new conda environment and link the executable
provided by it to `{config.CONFIG.link_destination}`.
""",
)
@click.option(
"--link-conflict",
"-l",
default="error",
type=click.Choice([action.value for action in core.LinkConflictAction]),
help=f"""How to handle conflicts when a link with the same name already exists in
`{config.CONDAX_LINK_DESTINATION}`. If `error` is specified, condax will exit with
an error if the link already exists. If `overwrite` is specified, condax will
overwrite the existing link. If `skip` is specified, condax will skip linking the
conflicting executable.""",
)
@click.argument("package")
def install(channel, package, link_conflict):
def install(
channel: Optional[List[str]] = typer.Option(
None,
"--channel",
"-c",
help=f"""\
Use the channels specified to install. If not specified condax will
default to using {config.CONFIG.channels}.""",
),
link_conflict: core.LinkConflictAction = _OPTION_LINK_ACTION,
mamba: bool = _OPTION_MAMBA,
package: str = typer.Argument(...),
):
if channel is None or (len(channel) == 0):
channel = config.DEFAULT_CHANNELS
channel = config.CONFIG.channels
config.CONFIG.ensure_conda_executable(require_mamba=mamba)

core.install_package(
package,
channels=channel,
link_conflict_action=core.LinkConflictAction(link_conflict),
link_conflict_action=link_conflict,
)


@cli.command(
help=f"""\
Inject a package into a condax managed environment.
This will install a package into an existing condax environment.
""",
)
def inject(
channel: Optional[List[str]] = typer.Option(
None,
"--channel",
"-c",
help=f"""\
Use the channels specified to install. If not specified condax will
default to using {config.CONFIG.channels}.""",
),
mamba: bool = _OPTION_MAMBA,
link_conflict: core.LinkConflictAction = _OPTION_LINK_ACTION,
include_apps: bool = typer.Option(
False, "--include-apps", "Adds applications of injected package to PATH."
),
package: str = typer.Argument(..., help="The condax environment inject into."),
extra_packages: List[str] = typer.Argument(..., help="Extra packages to install."),
):
if channel is None or (len(channel) == 0):
channel = config.CONFIG.channels
config.CONFIG.ensure_conda_executable(require_mamba=mamba)

core.inject_packages(
package,
extra_packages,
channels=channel,
link_conflict_action=link_conflict,
include_apps=include_apps,
)


Expand All @@ -55,8 +106,12 @@ def install(channel, package, link_conflict):
conda environment.
"""
)
@click.argument("package")
def remove(package):
def remove(
package: str,
mamba: bool = _OPTION_MAMBA,
):
config.CONFIG.ensure_conda_executable(require_mamba=mamba)

core.remove_package(package)


Expand All @@ -66,8 +121,13 @@ def remove(package):
This can update shell configuration files like `~/.bashrc`."""
)
def ensure_path():
paths.add_path_to_environment(config.CONDAX_LINK_DESTINATION)
def ensure_path() -> None:
paths.add_path_to_environment(config.CONFIG.link_destination)


@cli.command(help="""Display the conda prefix for a condax package.""")
def prefix(package: str) -> None:
typer.echo(core.prefix(package))


@cli.command(
Expand All @@ -77,29 +137,25 @@ def ensure_path():
This will update the underlying conda environments(s) to the latest release of a package.
"""
)
@click.option(
"--all", is_flag=True, help="Set to update all packages installed by condax"
)
@click.option(
"--link-conflict",
"-l",
default="error",
type=click.Choice([action.value for action in core.LinkConflictAction]),
help=f"""How to handle conflicts when a link with the same name already exists in
`{config.CONDAX_LINK_DESTINATION}`. If `error` is specified, condax will exit with
an error if the link already exists. If `overwrite` is specified, condax will
overwrite the existing link. If `skip` is specified, condax will skip linking the
conflicting executable.""",
)
@click.argument("package", default="", required=False)
@click.pass_context
def update(ctx, all, link_conflict, package):
def update(
all: bool = typer.Option(
False, "--all", help="Set to update all packages installed by condax"
),
link_conflict: core.LinkConflictAction = _OPTION_LINK_ACTION,
mamba: bool = _OPTION_MAMBA,
package: Optional[str] = typer.Argument(None),
):
config.CONFIG.ensure_conda_executable(require_mamba=mamba)
if all and package is not None:
typer.echo("Cannot specify --all and a package name")
sys.exit(1)
if all:
core.update_all_packages(core.LinkConflictAction(link_conflict))
core.update_all_packages(link_conflict)
elif package:
core.update_package(package, core.LinkConflictAction(link_conflict))
core.update_package(package, link_conflict)
else:
print(ctx.get_help(), file=sys.stderr)
typer.echo("Must specify --all or a package name")
sys.exit(1)


if __name__ == "__main__":
Expand Down
Loading

0 comments on commit 0f25c0a

Please sign in to comment.