latch 2.41.3__tar.gz → 2.41.3.dev1__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {latch-2.41.3/latch.egg-info → latch-2.41.3.dev1}/PKG-INFO +1 -1
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/ldata/type.py +7 -1
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/resources/tasks.py +39 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/types/metadata.py +63 -18
- {latch-2.41.3 → latch-2.41.3.dev1/latch.egg-info}/PKG-INFO +1 -1
- {latch-2.41.3 → latch-2.41.3.dev1}/latch.egg-info/SOURCES.txt +14 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/centromere/ctx.py +41 -4
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/docker_utils/__init__.py +16 -1
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/main.py +46 -2
- latch-2.41.3.dev1/latch_cli/nextflow/dependencies.py +91 -0
- latch-2.41.3.dev1/latch_cli/nextflow/workflow.py +169 -0
- latch-2.41.3.dev1/latch_cli/services/init/__pycache__/__init__.cpython-310.pyc +0 -0
- latch-2.41.3.dev1/latch_cli/services/init/__pycache__/__init__.cpython-311.pyc +0 -0
- latch-2.41.3.dev1/latch_cli/services/init/__pycache__/__init__.cpython-38.pyc +0 -0
- latch-2.41.3.dev1/latch_cli/services/init/__pycache__/__init__.cpython-39.pyc +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/init/__pycache__/init.cpython-310.pyc +0 -0
- latch-2.41.3.dev1/latch_cli/services/init/__pycache__/init.cpython-311.pyc +0 -0
- latch-2.41.3.dev1/latch_cli/services/init/__pycache__/init.cpython-38.pyc +0 -0
- latch-2.41.3.dev1/latch_cli/services/init/__pycache__/init.cpython-39.pyc +0 -0
- latch-2.41.3.dev1/latch_cli/services/init/assemble_and_sort/__pycache__/__init__.cpython-310.pyc +0 -0
- latch-2.41.3.dev1/latch_cli/services/init/example_conda/__pycache__/__init__.cpython-310.pyc +0 -0
- latch-2.41.3.dev1/latch_cli/services/init/example_nf_integration/latch_metadata/__pycache__/__init__.cpython-311.pyc +0 -0
- latch-2.41.3.dev1/latch_cli/services/init/example_r/__pycache__/__init__.cpython-310.pyc +0 -0
- latch-2.41.3.dev1/latch_cli/services/init/template/__pycache__/__init__.cpython-310.pyc +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/register/register.py +66 -24
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/snakemake/config/utils.py +20 -6
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/utils/__init__.py +1 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/setup.py +1 -1
- latch-2.41.3.dev1/tests/__init__.py +0 -0
- latch-2.41.3/latch_cli/services/init/__pycache__/__init__.cpython-310.pyc +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/LICENSE +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/MANIFEST.in +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/README.md +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/__init__.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/account.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/executions.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/functions/__init__.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/functions/messages.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/functions/operators.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/functions/secrets.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/ldata/__init__.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/ldata/_transfer/__init__.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/ldata/_transfer/download.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/ldata/_transfer/manager.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/ldata/_transfer/node.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/ldata/_transfer/progress.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/ldata/_transfer/remote_copy.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/ldata/_transfer/throttle.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/ldata/_transfer/upload.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/ldata/_transfer/utils.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/ldata/path.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/registry/__init__.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/registry/project.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/registry/record.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/registry/table.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/registry/types.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/registry/upstream_types/__init__.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/registry/upstream_types/types.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/registry/upstream_types/values.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/registry/utils.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/resources/__init__.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/resources/conditional.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/resources/dynamic.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/resources/launch_plan.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/resources/map_tasks.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/resources/reference_workflow.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/resources/workflow.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/types/__init__.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/types/directory.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/types/file.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/types/glob.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/types/json.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/types/utils.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/utils.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/verified/__init__.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/verified/deseq2.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/verified/mafft.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/verified/pathway.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/verified/rnaseq.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch/verified/trim_galore.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch.egg-info/dependency_links.txt +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch.egg-info/entry_points.txt +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch.egg-info/requires.txt +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch.egg-info/top_level.txt +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/__init__.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/auth/__init__.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/auth/csrf.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/auth/oauth2.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/auth/pkce.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/auth/utils.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/centromere/__init__.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/centromere/utils.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/click_utils.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/constants.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/exceptions/__init__.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/exceptions/cache.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/exceptions/errors.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/exceptions/handler.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/exceptions/traceback.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/menus.py +0 -0
- {latch-2.41.3/latch_cli/services/cp → latch-2.41.3.dev1/latch_cli/nextflow}/__init__.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/__init__.py +0 -0
- {latch-2.41.3/latch_cli/services/execute → latch-2.41.3.dev1/latch_cli/services/cp}/__init__.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/cp/autocomplete.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/cp/glob.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/cp/main.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/cp/utils.py +0 -0
- {latch-2.41.3/latch_cli/services/test_data → latch-2.41.3.dev1/latch_cli/services/execute}/__init__.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/execute/main.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/execute/utils.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/get.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/get_executions.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/get_params.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/init/__init__.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/init/assemble_and_sort/.env +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/init/assemble_and_sort/LICENSE +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/init/assemble_and_sort/README.md +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/init/assemble_and_sort/__init__.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/init/assemble_and_sort/assemble.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/init/assemble_and_sort/sort.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/init/assemble_and_sort/system-requirements.txt +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/init/common/.dockerignore +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/init/example_conda/__init__.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/init/example_conda/conda_task.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/init/example_conda/environment.yaml +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/init/example_docker/__init__.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/init/example_docker/task.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/init/example_nfcore/Dockerfile +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/init/example_nfcore/__init__.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/init/example_nfcore/task.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/init/example_r/__init__.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/init/example_r/environment.R +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/init/example_r/r_task.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/init/example_snakemake/.latch/latch_entrypoint +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/init/example_snakemake/Dockerfile +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/init/example_snakemake/Snakefile +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/init/example_snakemake/config.yaml +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/init/example_snakemake/environment.yaml +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/init/example_snakemake/latch_metadata.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/init/example_snakemake/scripts/plot-quals.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/init/example_snakemake/version +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/init/init.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/init/template/LICENSE +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/init/template/README.md +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/init/template/__init__.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/init/template/task.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/launch.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/local_dev.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/local_dev_old.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/login.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/ls.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/mkdir.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/move.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/preview.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/register/__init__.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/register/constants.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/register/utils.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/rm.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/stop_pod.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/sync.py +0 -0
- {latch-2.41.3/latch_cli/snakemake → latch-2.41.3.dev1/latch_cli/services/test_data}/__init__.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/test_data/ls.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/test_data/remove.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/test_data/upload.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/test_data/utils.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/services/workspace.py +0 -0
- {latch-2.41.3/latch_cli/snakemake/config → latch-2.41.3.dev1/latch_cli/snakemake}/__init__.py +0 -0
- {latch-2.41.3/latch_cli/tui → latch-2.41.3.dev1/latch_cli/snakemake/config}/__init__.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/snakemake/config/parser.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/snakemake/serialize.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/snakemake/serialize_utils.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/snakemake/single_task_snakemake.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/snakemake/utils.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/snakemake/workflow.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/tinyrequests.py +0 -0
- {latch-2.41.3/tests → latch-2.41.3.dev1/latch_cli/tui}/__init__.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/utils/path.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/latch_cli/workflow_config.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/pyproject.toml +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/setup.cfg +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/tests/cp/__init__.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/tests/fixtures.py +0 -0
- {latch-2.41.3 → latch-2.41.3.dev1}/tests/test_ls.py +0 -0
|
@@ -1,8 +1,14 @@
|
|
|
1
1
|
from enum import Enum
|
|
2
|
+
from typing import Optional
|
|
2
3
|
|
|
3
4
|
|
|
4
5
|
class LatchPathError(RuntimeError):
|
|
5
|
-
def __init__(
|
|
6
|
+
def __init__(
|
|
7
|
+
self,
|
|
8
|
+
message: str,
|
|
9
|
+
remote_path: Optional[str] = None,
|
|
10
|
+
acc_id: Optional[str] = None,
|
|
11
|
+
):
|
|
6
12
|
super().__init__(message)
|
|
7
13
|
self.message = message
|
|
8
14
|
self.remote_path = remote_path
|
|
@@ -33,9 +33,12 @@ from flytekit import task
|
|
|
33
33
|
from flytekitplugins.pod import Pod
|
|
34
34
|
from kubernetes.client.models import (
|
|
35
35
|
V1Container,
|
|
36
|
+
V1PersistentVolumeClaimVolumeSource,
|
|
36
37
|
V1PodSpec,
|
|
37
38
|
V1ResourceRequirements,
|
|
38
39
|
V1Toleration,
|
|
40
|
+
V1Volume,
|
|
41
|
+
V1VolumeMount,
|
|
39
42
|
)
|
|
40
43
|
|
|
41
44
|
from .dynamic import DynamicTaskConfig
|
|
@@ -179,6 +182,40 @@ def _get_small_pod() -> Pod:
|
|
|
179
182
|
)
|
|
180
183
|
|
|
181
184
|
|
|
185
|
+
def _get_nextflow_runtime_pod() -> Pod:
|
|
186
|
+
primary_container = V1Container(name="primary")
|
|
187
|
+
resources = V1ResourceRequirements(
|
|
188
|
+
requests={"cpu": "2", "memory": "4Gi", "ephemeral-storage": "100Gi"},
|
|
189
|
+
limits={"cpu": "2", "memory": "4Gi", "ephemeral-storage": "100Gi"},
|
|
190
|
+
)
|
|
191
|
+
primary_container.resources = resources
|
|
192
|
+
volume_mounts = [V1VolumeMount(mount_path="/nf-workdir", name="nextflow-workdir")]
|
|
193
|
+
primary_container.volume_mounts = volume_mounts
|
|
194
|
+
|
|
195
|
+
return Pod(
|
|
196
|
+
annotations={
|
|
197
|
+
"io.kubernetes.cri-o.userns-mode": (
|
|
198
|
+
"private:uidmapping=0:1048576:65536;gidmapping=0:1048576:65536"
|
|
199
|
+
)
|
|
200
|
+
},
|
|
201
|
+
pod_spec=V1PodSpec(
|
|
202
|
+
runtime_class_name="sysbox-runc",
|
|
203
|
+
service_account_name="rahul-test",
|
|
204
|
+
containers=[primary_container],
|
|
205
|
+
volumes=[
|
|
206
|
+
V1Volume(
|
|
207
|
+
name="nextflow-workdir",
|
|
208
|
+
persistent_volume_claim=V1PersistentVolumeClaimVolumeSource(
|
|
209
|
+
# this value will be injected by flytepropeller
|
|
210
|
+
claim_name="nextflow-pvc-placeholder"
|
|
211
|
+
),
|
|
212
|
+
)
|
|
213
|
+
],
|
|
214
|
+
),
|
|
215
|
+
primary_container_name="primary",
|
|
216
|
+
)
|
|
217
|
+
|
|
218
|
+
|
|
182
219
|
large_gpu_task = functools.partial(task, task_config=_get_large_gpu_pod())
|
|
183
220
|
"""This task will get scheduled on a large GPU-enabled node.
|
|
184
221
|
|
|
@@ -314,6 +351,8 @@ small_task = functools.partial(task, task_config=_get_small_pod())
|
|
|
314
351
|
- False
|
|
315
352
|
"""
|
|
316
353
|
|
|
354
|
+
nextflow_runtime_task = functools.partial(task, task_config=_get_nextflow_runtime_pod())
|
|
355
|
+
|
|
317
356
|
|
|
318
357
|
def custom_memory_optimized_task(cpu: int, memory: int):
|
|
319
358
|
"""Returns a custom task configuration requesting
|
|
@@ -3,11 +3,24 @@ from dataclasses import Field, asdict, dataclass, field
|
|
|
3
3
|
from enum import Enum
|
|
4
4
|
from pathlib import Path
|
|
5
5
|
from textwrap import indent
|
|
6
|
-
from typing import
|
|
6
|
+
from typing import (
|
|
7
|
+
Any,
|
|
8
|
+
ClassVar,
|
|
9
|
+
Collection,
|
|
10
|
+
Dict,
|
|
11
|
+
Generic,
|
|
12
|
+
List,
|
|
13
|
+
Optional,
|
|
14
|
+
Protocol,
|
|
15
|
+
Tuple,
|
|
16
|
+
Type,
|
|
17
|
+
TypeVar,
|
|
18
|
+
Union,
|
|
19
|
+
)
|
|
7
20
|
|
|
8
21
|
import click
|
|
9
22
|
import yaml
|
|
10
|
-
from typing_extensions import TypeAlias
|
|
23
|
+
from typing_extensions import Annotated, TypeAlias
|
|
11
24
|
|
|
12
25
|
from latch_cli.snakemake.config.utils import validate_snakemake_type
|
|
13
26
|
from latch_cli.utils import identifier_suffix_from_str
|
|
@@ -16,7 +29,6 @@ from .directory import LatchDir
|
|
|
16
29
|
from .file import LatchFile
|
|
17
30
|
|
|
18
31
|
|
|
19
|
-
@dataclass
|
|
20
32
|
class LatchRule:
|
|
21
33
|
"""Class describing a rule that a parameter input must follow"""
|
|
22
34
|
|
|
@@ -388,31 +400,33 @@ class _IsDataclass(Protocol):
|
|
|
388
400
|
|
|
389
401
|
|
|
390
402
|
ParameterType: TypeAlias = Union[
|
|
391
|
-
|
|
392
|
-
|
|
393
|
-
|
|
394
|
-
|
|
395
|
-
|
|
396
|
-
|
|
397
|
-
|
|
398
|
-
|
|
399
|
-
|
|
400
|
-
|
|
403
|
+
None,
|
|
404
|
+
int,
|
|
405
|
+
float,
|
|
406
|
+
str,
|
|
407
|
+
bool,
|
|
408
|
+
LatchFile,
|
|
409
|
+
LatchDir,
|
|
410
|
+
Enum,
|
|
411
|
+
_IsDataclass,
|
|
412
|
+
Collection["ParameterType"],
|
|
401
413
|
]
|
|
402
414
|
|
|
403
415
|
|
|
416
|
+
T = TypeVar("T", bound=ParameterType)
|
|
417
|
+
|
|
418
|
+
|
|
404
419
|
@dataclass
|
|
405
|
-
class SnakemakeParameter(LatchParameter):
|
|
406
|
-
type: Optional[
|
|
420
|
+
class SnakemakeParameter(Generic[T], LatchParameter):
|
|
421
|
+
type: Optional[Type[T]] = None
|
|
407
422
|
"""
|
|
408
423
|
The python type of the parameter.
|
|
409
424
|
"""
|
|
410
|
-
|
|
411
|
-
default: Optional[Any] = None
|
|
425
|
+
default: Optional[T] = None
|
|
412
426
|
|
|
413
427
|
|
|
414
428
|
@dataclass
|
|
415
|
-
class SnakemakeFileParameter(SnakemakeParameter):
|
|
429
|
+
class SnakemakeFileParameter(SnakemakeParameter[Union[LatchFile, LatchDir]]):
|
|
416
430
|
"""
|
|
417
431
|
Deprecated: use `file_metadata` keyword in `SnakemakeMetadata` instead
|
|
418
432
|
"""
|
|
@@ -456,6 +470,19 @@ class SnakemakeFileMetadata:
|
|
|
456
470
|
"""
|
|
457
471
|
|
|
458
472
|
|
|
473
|
+
@dataclass
|
|
474
|
+
class NextflowParameter(Generic[T], LatchParameter):
|
|
475
|
+
type: Optional[Type[T]] = None
|
|
476
|
+
"""
|
|
477
|
+
The python type of the parameter.
|
|
478
|
+
"""
|
|
479
|
+
default: Optional[T] = None
|
|
480
|
+
|
|
481
|
+
def __post_init__(self):
|
|
482
|
+
if self.samplesheet is True:
|
|
483
|
+
self.type = Annotated[self.type, "samplesheet"]
|
|
484
|
+
|
|
485
|
+
|
|
459
486
|
@dataclass
|
|
460
487
|
class LatchMetadata:
|
|
461
488
|
"""Class for organizing workflow metadata
|
|
@@ -651,3 +678,21 @@ class SnakemakeMetadata(LatchMetadata):
|
|
|
651
678
|
|
|
652
679
|
|
|
653
680
|
_snakemake_metadata: Optional[SnakemakeMetadata] = None
|
|
681
|
+
|
|
682
|
+
|
|
683
|
+
@dataclass
|
|
684
|
+
class NextflowMetadata(LatchMetadata):
|
|
685
|
+
name: Optional[str] = None
|
|
686
|
+
parameters: Dict[str, NextflowParameter] = field(default_factory=dict)
|
|
687
|
+
|
|
688
|
+
def __post_init__(self):
|
|
689
|
+
if self.name is None:
|
|
690
|
+
self.name = f"nf_{identifier_suffix_from_str(self.display_name.lower())}"
|
|
691
|
+
else:
|
|
692
|
+
self.name = identifier_suffix_from_str(self.name)
|
|
693
|
+
|
|
694
|
+
global _nextflow_metadata
|
|
695
|
+
_nextflow_metadata = self
|
|
696
|
+
|
|
697
|
+
|
|
698
|
+
_nextflow_metadata: Optional[NextflowMetadata] = None
|
|
@@ -80,6 +80,9 @@ latch_cli/exceptions/cache.py
|
|
|
80
80
|
latch_cli/exceptions/errors.py
|
|
81
81
|
latch_cli/exceptions/handler.py
|
|
82
82
|
latch_cli/exceptions/traceback.py
|
|
83
|
+
latch_cli/nextflow/__init__.py
|
|
84
|
+
latch_cli/nextflow/dependencies.py
|
|
85
|
+
latch_cli/nextflow/workflow.py
|
|
83
86
|
latch_cli/services/__init__.py
|
|
84
87
|
latch_cli/services/get.py
|
|
85
88
|
latch_cli/services/get_executions.py
|
|
@@ -107,7 +110,13 @@ latch_cli/services/execute/utils.py
|
|
|
107
110
|
latch_cli/services/init/__init__.py
|
|
108
111
|
latch_cli/services/init/init.py
|
|
109
112
|
latch_cli/services/init/__pycache__/__init__.cpython-310.pyc
|
|
113
|
+
latch_cli/services/init/__pycache__/__init__.cpython-311.pyc
|
|
114
|
+
latch_cli/services/init/__pycache__/__init__.cpython-38.pyc
|
|
115
|
+
latch_cli/services/init/__pycache__/__init__.cpython-39.pyc
|
|
110
116
|
latch_cli/services/init/__pycache__/init.cpython-310.pyc
|
|
117
|
+
latch_cli/services/init/__pycache__/init.cpython-311.pyc
|
|
118
|
+
latch_cli/services/init/__pycache__/init.cpython-38.pyc
|
|
119
|
+
latch_cli/services/init/__pycache__/init.cpython-39.pyc
|
|
111
120
|
latch_cli/services/init/assemble_and_sort/.env
|
|
112
121
|
latch_cli/services/init/assemble_and_sort/LICENSE
|
|
113
122
|
latch_cli/services/init/assemble_and_sort/README.md
|
|
@@ -115,18 +124,22 @@ latch_cli/services/init/assemble_and_sort/__init__.py
|
|
|
115
124
|
latch_cli/services/init/assemble_and_sort/assemble.py
|
|
116
125
|
latch_cli/services/init/assemble_and_sort/sort.py
|
|
117
126
|
latch_cli/services/init/assemble_and_sort/system-requirements.txt
|
|
127
|
+
latch_cli/services/init/assemble_and_sort/__pycache__/__init__.cpython-310.pyc
|
|
118
128
|
latch_cli/services/init/common/.dockerignore
|
|
119
129
|
latch_cli/services/init/example_conda/__init__.py
|
|
120
130
|
latch_cli/services/init/example_conda/conda_task.py
|
|
121
131
|
latch_cli/services/init/example_conda/environment.yaml
|
|
132
|
+
latch_cli/services/init/example_conda/__pycache__/__init__.cpython-310.pyc
|
|
122
133
|
latch_cli/services/init/example_docker/__init__.py
|
|
123
134
|
latch_cli/services/init/example_docker/task.py
|
|
135
|
+
latch_cli/services/init/example_nf_integration/latch_metadata/__pycache__/__init__.cpython-311.pyc
|
|
124
136
|
latch_cli/services/init/example_nfcore/Dockerfile
|
|
125
137
|
latch_cli/services/init/example_nfcore/__init__.py
|
|
126
138
|
latch_cli/services/init/example_nfcore/task.py
|
|
127
139
|
latch_cli/services/init/example_r/__init__.py
|
|
128
140
|
latch_cli/services/init/example_r/environment.R
|
|
129
141
|
latch_cli/services/init/example_r/r_task.py
|
|
142
|
+
latch_cli/services/init/example_r/__pycache__/__init__.cpython-310.pyc
|
|
130
143
|
latch_cli/services/init/example_snakemake/Dockerfile
|
|
131
144
|
latch_cli/services/init/example_snakemake/Snakefile
|
|
132
145
|
latch_cli/services/init/example_snakemake/config.yaml
|
|
@@ -139,6 +152,7 @@ latch_cli/services/init/template/LICENSE
|
|
|
139
152
|
latch_cli/services/init/template/README.md
|
|
140
153
|
latch_cli/services/init/template/__init__.py
|
|
141
154
|
latch_cli/services/init/template/task.py
|
|
155
|
+
latch_cli/services/init/template/__pycache__/__init__.cpython-310.pyc
|
|
142
156
|
latch_cli/services/register/__init__.py
|
|
143
157
|
latch_cli/services/register/constants.py
|
|
144
158
|
latch_cli/services/register/register.py
|
|
@@ -59,6 +59,7 @@ class _CentromereCtx:
|
|
|
59
59
|
default_container: _Container
|
|
60
60
|
workflow_type: WorkflowType
|
|
61
61
|
snakefile: Optional[Path]
|
|
62
|
+
nf_script: Optional[Path]
|
|
62
63
|
|
|
63
64
|
latch_register_api_url = config.api.workflow.register
|
|
64
65
|
latch_image_api_url = config.api.workflow.upload_image
|
|
@@ -80,6 +81,7 @@ class _CentromereCtx:
|
|
|
80
81
|
disable_auto_version: bool = False,
|
|
81
82
|
remote: bool = False,
|
|
82
83
|
snakefile: Optional[Path] = None,
|
|
84
|
+
nf_script: Optional[Path] = None,
|
|
83
85
|
use_new_centromere: bool = False,
|
|
84
86
|
):
|
|
85
87
|
self.use_new_centromere = use_new_centromere
|
|
@@ -93,13 +95,22 @@ class _CentromereCtx:
|
|
|
93
95
|
self.dkr_repo = config.dkr_repo
|
|
94
96
|
self.pkg_root = pkg_root.resolve()
|
|
95
97
|
|
|
96
|
-
if snakefile
|
|
97
|
-
|
|
98
|
-
|
|
98
|
+
if snakefile and nf_script:
|
|
99
|
+
raise ValueError(
|
|
100
|
+
"Cannot provide both a snakefile and nextflow script to the"
|
|
101
|
+
" register command."
|
|
102
|
+
)
|
|
103
|
+
if snakefile is not None:
|
|
99
104
|
self.workflow_type = WorkflowType.snakemake
|
|
100
105
|
self.snakefile = snakefile
|
|
106
|
+
elif nf_script is not None:
|
|
107
|
+
self.workflow_type = WorkflowType.nextflow
|
|
108
|
+
self.nf_script = nf_script
|
|
109
|
+
else:
|
|
110
|
+
self.workflow_type = WorkflowType.latchbiosdk
|
|
101
111
|
|
|
102
112
|
self.container_map: Dict[str, _Container] = {}
|
|
113
|
+
|
|
103
114
|
if self.workflow_type == WorkflowType.latchbiosdk:
|
|
104
115
|
_import_flyte_objects([self.pkg_root])
|
|
105
116
|
for entity in FlyteEntities.entities:
|
|
@@ -126,7 +137,7 @@ class _CentromereCtx:
|
|
|
126
137
|
fg="red",
|
|
127
138
|
)
|
|
128
139
|
raise click.exceptions.Exit(1)
|
|
129
|
-
|
|
140
|
+
elif self.workflow_type == WorkflowType.snakemake:
|
|
130
141
|
assert snakefile is not None
|
|
131
142
|
|
|
132
143
|
import latch.types.metadata as metadata
|
|
@@ -231,6 +242,32 @@ class _CentromereCtx:
|
|
|
231
242
|
# todo(kenny): support per container task and custom workflow
|
|
232
243
|
# name for snakemake
|
|
233
244
|
self.workflow_name = f"{metadata._snakemake_metadata.name}_jit_register"
|
|
245
|
+
else:
|
|
246
|
+
assert nf_script is not None
|
|
247
|
+
|
|
248
|
+
import latch.types.metadata as metadata
|
|
249
|
+
|
|
250
|
+
from ..services.register.utils import import_module_by_path
|
|
251
|
+
|
|
252
|
+
meta = pkg_root / "latch_metadata" / "__init__.py"
|
|
253
|
+
if meta.exists():
|
|
254
|
+
click.echo(f"Using metadata file {click.style(meta, italic=True)}")
|
|
255
|
+
import_module_by_path(meta)
|
|
256
|
+
|
|
257
|
+
if metadata._nextflow_metadata is None:
|
|
258
|
+
click.secho(
|
|
259
|
+
dedent("""
|
|
260
|
+
Failed to register Nextflow workflow.
|
|
261
|
+
Make sure the project root contains a `wf/__init__.py`
|
|
262
|
+
with a `NextflowMetadata` object defined.
|
|
263
|
+
"""),
|
|
264
|
+
fg="red",
|
|
265
|
+
)
|
|
266
|
+
raise click.exceptions.Exit(1)
|
|
267
|
+
|
|
268
|
+
self.workflow_name = metadata._nextflow_metadata.name
|
|
269
|
+
|
|
270
|
+
assert self.workflow_name is not None
|
|
234
271
|
|
|
235
272
|
version_file = self.pkg_root / "version"
|
|
236
273
|
try:
|
|
@@ -39,7 +39,7 @@ def get_prologue(
|
|
|
39
39
|
library_name = '"latch[snakemake]"'
|
|
40
40
|
else:
|
|
41
41
|
library_name = "latch"
|
|
42
|
-
|
|
42
|
+
directives = [
|
|
43
43
|
"# DO NOT CHANGE",
|
|
44
44
|
f"from {config.base_image}",
|
|
45
45
|
"",
|
|
@@ -68,6 +68,11 @@ def get_prologue(
|
|
|
68
68
|
f"run pip install {library_name}=={config.latch_version}",
|
|
69
69
|
"run mkdir /opt/latch",
|
|
70
70
|
]
|
|
71
|
+
if wf_type == WorkflowType.nextflow:
|
|
72
|
+
directives.append(
|
|
73
|
+
"run apt-get update && apt-get install -y default-jre-headless"
|
|
74
|
+
)
|
|
75
|
+
return directives
|
|
71
76
|
|
|
72
77
|
|
|
73
78
|
def get_epilogue(wf_type: WorkflowType = WorkflowType.latchbiosdk) -> List[str]:
|
|
@@ -78,8 +83,18 @@ def get_epilogue(wf_type: WorkflowType = WorkflowType.latchbiosdk) -> List[str]:
|
|
|
78
83
|
"",
|
|
79
84
|
"# Latch snakemake workflow entrypoint",
|
|
80
85
|
"# DO NOT CHANGE",
|
|
86
|
+
"",
|
|
81
87
|
"copy .latch/snakemake_jit_entrypoint.py /root/snakemake_jit_entrypoint.py",
|
|
82
88
|
]
|
|
89
|
+
elif wf_type == WorkflowType.nextflow:
|
|
90
|
+
cmds += [
|
|
91
|
+
"",
|
|
92
|
+
"# Latch nextflow workflow entrypoint",
|
|
93
|
+
"# DO NOT CHANGE",
|
|
94
|
+
"",
|
|
95
|
+
"copy .latch/bin/nextflow /root/nextflow",
|
|
96
|
+
"copy .latch/.nextflow /root/.nextflow",
|
|
97
|
+
]
|
|
83
98
|
|
|
84
99
|
cmds += [
|
|
85
100
|
"",
|
|
@@ -192,7 +192,15 @@ def init(
|
|
|
192
192
|
type=bool,
|
|
193
193
|
help="Generate a Dockerfile with arguments needed for Snakemake compatability",
|
|
194
194
|
)
|
|
195
|
-
|
|
195
|
+
@click.option(
|
|
196
|
+
"-n",
|
|
197
|
+
"--nextflow",
|
|
198
|
+
is_flag=True,
|
|
199
|
+
default=False,
|
|
200
|
+
type=bool,
|
|
201
|
+
help="Generate a Dockerfile with arguments needed for Nextflow compatability",
|
|
202
|
+
)
|
|
203
|
+
def dockerfile(pkg_root: str, snakemake: bool = False, nextflow: bool = False):
|
|
196
204
|
"""Generates a user editable dockerfile for a workflow and saves under `pkg_root/Dockerfile`.
|
|
197
205
|
|
|
198
206
|
Visit docs.latch.bio to learn more.
|
|
@@ -201,6 +209,14 @@ def dockerfile(pkg_root: str, snakemake: bool = False):
|
|
|
201
209
|
crash_handler.message = "Failed to generate Dockerfile."
|
|
202
210
|
crash_handler.pkg_root = pkg_root
|
|
203
211
|
|
|
212
|
+
if snakemake is True and nextflow is True:
|
|
213
|
+
click.secho(
|
|
214
|
+
f"Please specify only one workflow type to generate metadata for. Use"
|
|
215
|
+
f" either `--snakemake` or `--nextflow`.",
|
|
216
|
+
fg="red",
|
|
217
|
+
)
|
|
218
|
+
raise click.exceptions.Exit(1)
|
|
219
|
+
|
|
204
220
|
from latch_cli.docker_utils import generate_dockerfile
|
|
205
221
|
|
|
206
222
|
source = Path(pkg_root)
|
|
@@ -209,11 +225,14 @@ def dockerfile(pkg_root: str, snakemake: bool = False):
|
|
|
209
225
|
f"Dockerfile already exists at `{dest}`. Overwrite?"
|
|
210
226
|
):
|
|
211
227
|
return
|
|
228
|
+
|
|
212
229
|
workflow_type = WorkflowType.latchbiosdk
|
|
213
230
|
if snakemake is True:
|
|
214
231
|
workflow_type = WorkflowType.snakemake
|
|
215
|
-
|
|
232
|
+
elif nextflow is True:
|
|
233
|
+
workflow_type = WorkflowType.nextflow
|
|
216
234
|
|
|
235
|
+
generate_dockerfile(source, dest, wf_type=workflow_type)
|
|
217
236
|
click.secho(f"Successfully generated dockerfile `{dest}`", fg="green")
|
|
218
237
|
|
|
219
238
|
|
|
@@ -412,6 +431,25 @@ def execute(
|
|
|
412
431
|
" provided."
|
|
413
432
|
),
|
|
414
433
|
)
|
|
434
|
+
@click.option(
|
|
435
|
+
"--nf-script",
|
|
436
|
+
type=click.Path(exists=True, dir_okay=False, path_type=Path),
|
|
437
|
+
default=None,
|
|
438
|
+
help="Path to a nextflow script to register.",
|
|
439
|
+
)
|
|
440
|
+
@click.option(
|
|
441
|
+
"--redownload-dependencies",
|
|
442
|
+
type=bool,
|
|
443
|
+
is_flag=True,
|
|
444
|
+
default=False,
|
|
445
|
+
help="Redownload external Nextflow dependencies",
|
|
446
|
+
)
|
|
447
|
+
@click.option(
|
|
448
|
+
"--execution-profile",
|
|
449
|
+
type=str,
|
|
450
|
+
default=None,
|
|
451
|
+
help="Set execution profile for Nextflow workflow",
|
|
452
|
+
)
|
|
415
453
|
@requires_login
|
|
416
454
|
def register(
|
|
417
455
|
pkg_root: str,
|
|
@@ -422,6 +460,9 @@ def register(
|
|
|
422
460
|
open: bool,
|
|
423
461
|
snakefile: Optional[Path],
|
|
424
462
|
cache_tasks: bool,
|
|
463
|
+
nf_script: Optional[Path],
|
|
464
|
+
redownload_dependencies: bool,
|
|
465
|
+
execution_profile: Optional[str],
|
|
425
466
|
):
|
|
426
467
|
"""Register local workflow code to Latch.
|
|
427
468
|
|
|
@@ -442,6 +483,9 @@ def register(
|
|
|
442
483
|
skip_confirmation=yes,
|
|
443
484
|
open=open,
|
|
444
485
|
snakefile=snakefile,
|
|
486
|
+
nf_script=nf_script,
|
|
487
|
+
nf_redownload_dependencies=redownload_dependencies,
|
|
488
|
+
nf_execution_profile=execution_profile,
|
|
445
489
|
progress_plain=(docker_progress == "auto" and not sys.stdout.isatty())
|
|
446
490
|
or docker_progress == "plain",
|
|
447
491
|
use_new_centromere=use_new_centromere,
|
|
@@ -0,0 +1,91 @@
|
|
|
1
|
+
import shutil
|
|
2
|
+
import subprocess
|
|
3
|
+
from concurrent.futures import ProcessPoolExecutor
|
|
4
|
+
from ctypes import c_int
|
|
5
|
+
from multiprocessing.managers import SyncManager
|
|
6
|
+
from pathlib import Path
|
|
7
|
+
from urllib.parse import urljoin
|
|
8
|
+
|
|
9
|
+
import boto3
|
|
10
|
+
import click
|
|
11
|
+
|
|
12
|
+
from latch_cli import tinyrequests
|
|
13
|
+
from latch_cli.utils import dedent
|
|
14
|
+
|
|
15
|
+
|
|
16
|
+
def _do_download(
|
|
17
|
+
url: str,
|
|
18
|
+
output_path: Path,
|
|
19
|
+
total_count: int,
|
|
20
|
+
counter,
|
|
21
|
+
lock,
|
|
22
|
+
): # todo(ayush): figure out the right type annotation for counter/lock
|
|
23
|
+
res = tinyrequests.get(url)
|
|
24
|
+
output_path.parent.mkdir(parents=True, exist_ok=True)
|
|
25
|
+
output_path.write_bytes(res.content)
|
|
26
|
+
|
|
27
|
+
with lock:
|
|
28
|
+
counter.value += 1
|
|
29
|
+
progress_str = f"{counter.value}/{total_count}"
|
|
30
|
+
|
|
31
|
+
click.echo("\x1b[0K", nl=False)
|
|
32
|
+
click.secho(progress_str, dim=True, italic=True, nl=False)
|
|
33
|
+
click.echo(f"\x1b[{len(progress_str)}D", nl=False)
|
|
34
|
+
|
|
35
|
+
|
|
36
|
+
def download_nf_jars(pkg_root: Path):
|
|
37
|
+
s3_resource = boto3.resource("s3")
|
|
38
|
+
bucket = s3_resource.Bucket("latch-public")
|
|
39
|
+
|
|
40
|
+
objects = list(bucket.objects.filter(Prefix=".nextflow/"))
|
|
41
|
+
|
|
42
|
+
click.secho(" Downloading Nextflow binaries: \x1b[?25l", italic=True, nl=False)
|
|
43
|
+
|
|
44
|
+
with SyncManager() as man:
|
|
45
|
+
counter = man.Value(c_int, 0)
|
|
46
|
+
lock = man.Lock()
|
|
47
|
+
with ProcessPoolExecutor() as exec:
|
|
48
|
+
for obj in objects:
|
|
49
|
+
url = urljoin(
|
|
50
|
+
"https://latch-public.s3.us-west-2.amazonaws.com/", obj.key
|
|
51
|
+
)
|
|
52
|
+
obj_path = pkg_root / ".latch" / obj.key
|
|
53
|
+
|
|
54
|
+
exec.submit(_do_download, url, obj_path, len(objects), counter, lock)
|
|
55
|
+
|
|
56
|
+
click.echo("\x1b[0K", nl=False)
|
|
57
|
+
click.secho("Done. \x1b[?25h", italic=True)
|
|
58
|
+
|
|
59
|
+
|
|
60
|
+
def ensure_nf_dependencies(pkg_root: Path, *, force_redownload: bool = False):
|
|
61
|
+
try:
|
|
62
|
+
subprocess.run(["java", "--version"], check=True, capture_output=True)
|
|
63
|
+
except (subprocess.CalledProcessError, FileNotFoundError) as e:
|
|
64
|
+
click.secho(
|
|
65
|
+
dedent("""\
|
|
66
|
+
Java is not installed - this is a requirement to run Nextflow.
|
|
67
|
+
Please install Java and try again.
|
|
68
|
+
"""),
|
|
69
|
+
fg="red",
|
|
70
|
+
)
|
|
71
|
+
raise click.exceptions.Exit(1) from e
|
|
72
|
+
|
|
73
|
+
nf_executable = pkg_root / ".latch" / "bin" / "nextflow"
|
|
74
|
+
nf_jars = pkg_root / ".latch" / ".nextflow"
|
|
75
|
+
|
|
76
|
+
if force_redownload:
|
|
77
|
+
nf_executable.unlink(missing_ok=True)
|
|
78
|
+
if nf_jars.exists():
|
|
79
|
+
shutil.rmtree(nf_jars)
|
|
80
|
+
|
|
81
|
+
if not nf_executable.exists():
|
|
82
|
+
res = tinyrequests.get(
|
|
83
|
+
"https://latch-public.s3.us-west-2.amazonaws.com/nextflow"
|
|
84
|
+
)
|
|
85
|
+
nf_executable.parent.mkdir(parents=True, exist_ok=True)
|
|
86
|
+
|
|
87
|
+
nf_executable.write_bytes(res.content)
|
|
88
|
+
nf_executable.chmod(0o700)
|
|
89
|
+
|
|
90
|
+
if not nf_jars.exists():
|
|
91
|
+
download_nf_jars(pkg_root)
|