diff --git a/pkgs/applications/science/misc/snakemake/assets.nix b/pkgs/applications/science/misc/snakemake/assets.nix new file mode 100644 index 000000000000..9ca00ebe09a6 --- /dev/null +++ b/pkgs/applications/science/misc/snakemake/assets.nix @@ -0,0 +1,67 @@ +{ fetchurl }: +{ + "snakemake/LICENSE.md" = fetchurl { + url = "https://raw.githubusercontent.com/snakemake/snakemake/main/LICENSE.md"; + sha256 = "84a1a82b05c80637744d3fe8257235c15380efa6cc32608adf4b21f17af5d2b8"; + }; + "pygments/LICENSE" = fetchurl { + url = "https://raw.githubusercontent.com/pygments/pygments/master/LICENSE"; + sha256 = "a9d66f1d526df02e29dce73436d34e56e8632f46c275bbdffc70569e882f9f17"; + }; + "tailwindcss/LICENSE" = fetchurl { + url = "https://raw.githubusercontent.com/tailwindlabs/tailwindcss/master/LICENSE"; + sha256 = "60e0b68c0f35c078eef3a5d29419d0b03ff84ec1df9c3f9d6e39a519a5ae7985"; + }; + "tailwindcss/tailwind.css" = fetchurl { + url = "https://cdn.tailwindcss.com/3.0.23?plugins=forms@0.4.0,typography@0.5.2"; + sha256 = "8a597dc918fb62e05db23a5f810327a045a62c57cfda16646075138a6ac696fa"; + }; + "react/LICENSE" = fetchurl { + url = "https://raw.githubusercontent.com/facebook/react/main/LICENSE"; + sha256 = "da6d3703ed11cbe42bd212c725957c98da23cbff1998c05fa4b3d976d1a58e93"; + }; + "react/react.production.min.js" = fetchurl { + url = "https://cdnjs.cloudflare.com/ajax/libs/react/18.2.0/umd/react.production.min.js"; + sha256 = "4b4969fa4ef3594324da2c6d78ce8766fbbc2fd121fff395aedf997db0a99a06"; + }; + "react/react-dom.production.min.js" = fetchurl { + url = "https://cdnjs.cloudflare.com/ajax/libs/react-dom/18.2.0/umd/react-dom.production.min.js"; + sha256 = "21758ed084cd0e37e735722ee4f3957ea960628a29dfa6c3ce1a1d47a2d6e4f7"; + }; + "vega/vega.js" = fetchurl { + url = "https://cdnjs.cloudflare.com/ajax/libs/vega/5.21.0/vega.js"; + sha256 = "b34c43055ef5d39a093e937522955dc359fbaec6c5b0259ae2de4c9da698e9fe"; + }; + "vega/LICENSE" = fetchurl { + url = "https://raw.githubusercontent.com/vega/vega/main/LICENSE"; + sha256 = "63727832aaf62004a2b249c933e327f3c90caf49e41a72f4bf436edf632cbda8"; + }; + "vega-lite/vega-lite.js" = fetchurl { + url = "https://cdnjs.cloudflare.com/ajax/libs/vega-lite/5.2.0/vega-lite.js"; + sha256 = "6eb7f93121cd9f44cf8640244f87c5e143f87c7a0b6cd113da4a9e41e3adf0aa"; + }; + "vega-lite/LICENSE" = fetchurl { + url = "https://raw.githubusercontent.com/vega/vega-lite/next/LICENSE"; + sha256 = "f618900fd0d64046963b29f40590cdd1e341a2f41449f99110d82fd81fea808c"; + }; + "vega-embed/vega-embed.js" = fetchurl { + url = "https://cdnjs.cloudflare.com/ajax/libs/vega-embed/6.20.8/vega-embed.js"; + sha256 = "4e546c1f86eb200333606440e92f76e2940b905757018d9672cd1708e4e6ff0a"; + }; + "vega-embed/LICENSE" = fetchurl { + url = "https://raw.githubusercontent.com/vega/vega-embed/next/LICENSE"; + sha256 = "32df67148f0fc3db0eb9e263a7b75d07f1eb14c61955005a4a39c6918d10d137"; + }; + "heroicons/LICENSE" = fetchurl { + url = "https://raw.githubusercontent.com/tailwindlabs/heroicons/master/LICENSE"; + sha256 = "60e0b68c0f35c078eef3a5d29419d0b03ff84ec1df9c3f9d6e39a519a5ae7985"; + }; + "prop-types/prop-types.min.js" = fetchurl { + url = "https://cdnjs.cloudflare.com/ajax/libs/prop-types/15.7.2/prop-types.min.js"; + sha256 = "4c88350517ee82aa4f3368e67ef1a453ca6636dcfa6449b4e3d6faa5c877066e"; + }; + "prop-types/LICENSE" = fetchurl { + url = "https://raw.githubusercontent.com/facebook/prop-types/main/LICENSE"; + sha256 = "f657f99d3fb9647db92628e96007aabb46e5f04f33e49999075aab8e250ca7ce"; + }; +} diff --git a/pkgs/applications/science/misc/snakemake/assets.sed b/pkgs/applications/science/misc/snakemake/assets.sed new file mode 100644 index 000000000000..df104ecf567d --- /dev/null +++ b/pkgs/applications/science/misc/snakemake/assets.sed @@ -0,0 +1,9 @@ +/Asset(.*/ { # find Asset declaration +s/: Asset(/ = fetchurl {/; # replace leading + :b; # a label + $!N; # if not EOF, include next line + s/",/";/; # provide separators between attributes + /)/!bb; # repeat until a closing bracket is located + s/),/};/; # provide separators between assets + p # output what we have +} diff --git a/pkgs/applications/science/misc/snakemake/default.nix b/pkgs/applications/science/misc/snakemake/default.nix index 7f0e70c64213..e7318d60a278 100644 --- a/pkgs/applications/science/misc/snakemake/default.nix +++ b/pkgs/applications/science/misc/snakemake/default.nix @@ -1,31 +1,52 @@ { lib , fetchFromGitHub +, fetchpatch +, fetchurl , python3 , runtimeShell +, stress }: python3.pkgs.buildPythonApplication rec { pname = "snakemake"; - version = "8.14.0"; + version = "8.19.3"; format = "setuptools"; src = fetchFromGitHub { owner = "snakemake"; repo = pname; rev = "refs/tags/v${version}"; - hash = "sha256-6oguN4u4OUDXpDsbueSBNwtWgLCaKmgq3w/d/MsMh7Y="; + hash = "sha256-DWlMF/aNRCYDfTP41ALaGJFBTBjHxqZtx/0PtD/37KY="; # https://github.com/python-versioneer/python-versioneer/issues/217 postFetch = '' sed -i "$out"/snakemake/_version.py -e 's#git_refnames = ".*"#git_refnames = " (tag: v${version})"#' ''; }; + patches = [ + # Avoid downloading if files are provided + # https://github.com/snakemake/snakemake/pull/3072 + (fetchpatch { + url = "https://github.com/snakemake/snakemake/commit/ea89ec2f20faa0db303fdab0eafa640c9147cc14.diff"; + hash = "sha256-gzmto3Kusk40kPH29DkvYcJgAx2VAOq3mw5vPSCp5mI="; + }) + ]; + postPatch = '' patchShebangs --build tests/ - patchShebangs --host snakemake/executors/jobscript.sh - substituteInPlace snakemake/shell.py \ - --replace "/bin/sh" "${runtimeShell}" - ''; + substituteInPlace tests/common.py \ + --replace-fail 'os.environ["PYTHONPATH"] = os.getcwd()' "pass" \ + --replace-fail 'del os.environ["PYTHONPATH"]' "pass" + substituteInPlace snakemake/unit_tests/__init__.py \ + --replace-fail '"unit_tests/templates"' '"'"$PWD"'/snakemake/unit_tests/templates"' + '' + (let + assets = import ./assets.nix { inherit fetchurl; }; + in + # Use fetchPypi once https://github.com/snakemake/snakemake/pull/3073 is available + lib.concatStrings (lib.mapAttrsToList (name: file: '' + echo install -D "${file}" snakemake/assets/data/${name} + install -D "${file}" snakemake/assets/data/${name} + '') assets)); propagatedBuildInputs = with python3.pkgs; [ appdirs @@ -41,6 +62,7 @@ python3.pkgs.buildPythonApplication rec { nbformat psutil pulp + pygments pyyaml requests reretry @@ -66,16 +88,97 @@ python3.pkgs.buildPythonApplication rec { numpy pandas pytestCheckHook + pytest-mock requests-mock snakemake-executor-plugin-cluster-generic + snakemake-storage-plugin-fs + stress ]; - disabledTestPaths = [ - "tests/test_conda_python_3_7_script/test_script.py" + pytestFlagsArray = [ + "tests/tests.py" + "tests/test_expand.py" + "tests/test_io.py" + "tests/test_schema.py" + "tests/test_executor_test_suite.py" + "tests/test_api.py" ]; + # Some will be disabled via https://github.com/snakemake/snakemake/pull/3074 disabledTests = [ + # requires network connection "test_deploy_sources" + "test_modules_meta_wrapper" + "test_module_complex" + "test_module_complex2" + "test_module_with_script" + "test_module_report" + "test_load_metawrapper" + # requires conda + "test_archive" + "test_script" + "test_conda" + "test_conda_list_envs" + "test_upstream_conda" + "test_deploy_script" + "test_deploy_hashing" + "test_conda_custom_prefix" + "test_conda_cmd_exe" + "test_wrapper" + "test_wrapper_local_git_prefix" + "test_singularity_conda" + "test_issue635" + "test_issue1093" + "test_jupyter_notebook" + "test_jupyter_notebook_draft" + "test_converting_path_for_r_script" + "test_conda_named" + "test_conda_function" + "test_conda_pin_file" + "test_conda_python_script" + "test_conda_python_3_7_script" + "test_prebuilt_conda_script" + "test_conda_global" + "test_script_pre_py39" + "test_resource_string_in_cli_or_profile" + "test_conda" + "test_env_modules" + "test_script_pre_py39" + # requires graphviz + "test_filegraph" + # requires s3 + "test_storage" + "test_default_storage" + "test_output_file_cache_storage" + # requires peppy and eido + "test_pep" + # requires perl + "test_shadow" + # requires snakemake-storage-plugin-http + "test_ancient" + "test_modules_prefix" + # weird + "test_strict_mode" + "test_issue1256" + "test_issue2574" + # requires apptainer + "test_singularity" + "test_singularity_cluster" + "test_singularity_invalid" + "test_singularity_module_invalid" + "test_singularity_none" + "test_singularity_global" + "test_cwl_singularity" + "test_issue1083" + "test_github_issue78" + "test_container" + "test_shell_exec" + "test_containerized" + # future-proofing + "conda" + "singularity" + "apptainer" + "container" ]; pythonImportsCheck = [ @@ -86,6 +189,8 @@ python3.pkgs.buildPythonApplication rec { export HOME="$(mktemp -d)" ''; + passthru.updateScript = ./update.sh; + meta = with lib; { homepage = "https://snakemake.github.io"; license = licenses.mit; diff --git a/pkgs/applications/science/misc/snakemake/update.sh b/pkgs/applications/science/misc/snakemake/update.sh new file mode 100755 index 000000000000..bd368d4fe279 --- /dev/null +++ b/pkgs/applications/science/misc/snakemake/update.sh @@ -0,0 +1,21 @@ +#!/usr/bin/env nix-shell +#!nix-shell -i bash -p curl common-updater-scripts gnused nixfmt-rfc-style + +set -eu -o pipefail + +version=${1:-$(curl -s https://api.github.com/repos/snakemake/snakemake/releases/latest | jq --raw-output '.tag_name[1:]')} +update-source-version snakemake $version + +basedir="$(dirname "$0")" +cat < "$basedir/assets.nix" +{ fetchurl }: +{ +EOF +outlink="$basedir/src" +nix-build . -A snakemake.src -o "$outlink" +sed "$outlink"/snakemake/assets/__init__.py -n -f "$basedir/assets.sed" >> "$basedir/assets.nix" +rm "$outlink" +cat <> "$basedir/assets.nix" +} +EOF +nixfmt "$basedir/assets.nix"