From 7ff7cbb3b2f2393a0f98cd1f257e61b3c2e8b081 Mon Sep 17 00:00:00 2001 From: Yuriy Taraday Date: Fri, 22 Sep 2023 07:09:25 +0200 Subject: [PATCH] Implement ShellApplication in Nickel Also move `run-tests` app from `flake.nix` to `project.ncl`. Part of https://github.com/nickel-lang/organist/issues/58 --- flake.nix | 26 ++--------------------- lib/builders.ncl | 54 ++++++++++++++++++++++++++++++++++++++++++++++++ project.ncl | 16 ++++++++++++++ 3 files changed, 72 insertions(+), 24 deletions(-) diff --git a/flake.nix b/flake.nix index 95d693f5..f4c5c711 100644 --- a/flake.nix +++ b/flake.nix @@ -73,33 +73,11 @@ } // computedOutputs // flake-utils.lib.eachDefaultSystem ( - system: let - lib = pkgs.callPackage ./lib/lib.nix { + system: { + lib = nixpkgs.legacyPackages.${system}.callPackage ./lib/lib.nix { organistSrc = self; nickel = inputs.nickel.packages."${system}".nickel-lang-cli; }; - pkgs = nixpkgs.legacyPackages.${system}; - in { - inherit lib; - - apps = - computedOutputs.apps.${system} - // { - run-test = let - testScript = pkgs.writeShellApplication { - name = "test-templates"; - runtimeInputs = [ - inputs.nickel.packages."${system}".nickel-lang-cli - pkgs.parallel - pkgs.gnused - ]; - text = builtins.readFile ./run-test.sh; - }; - in { - type = "app"; - program = pkgs.lib.getExe testScript; - }; - }; } ); } diff --git a/lib/builders.ncl b/lib/builders.ncl index 747ea608..e4d79d2f 100644 --- a/lib/builders.ncl +++ b/lib/builders.ncl @@ -8,6 +8,15 @@ let concat_strings_sep = fun sep values => else std.array.reduce_left (fun acc value => nix-s%"%{acc}%{sep}%{value}"%) values in + +let MutExclusiveWith = fun other name other_name label value => + if value == null && other == null then + std.fail_with "You must specify either %{name} or %{other_name} field" + else if value != null && other != null then + std.fail_with "You can set only one of %{name} or %{other_name} fields" + else + value +in { NickelPkg # we should only need two '%%', but a current Nickel bug (#XXX) bug makes the example being @@ -84,4 +93,49 @@ in structured_env.buildInputs = packages, } | (NickelPkg & { packages | { _ : Derivation } }), + + ShellApplication + | doc m%" + "% + = + NixpkgsPkg + & { + name, + version | default = "0.0.0", + content.text | NixString | optional, + content.file | NixString | default = lib.to_file name content.text, + runtime_inputs | { _ : Derivation } = {}, + shell_binary | NixString | default = lib.import_nix "nixpkgs#runtimeShell", + + env.buildInputs.coreutils = lib.import_nix "nixpkgs#coreutils", + env.buildCommand = nix-s%" + mkdir -p "${outputs[out]}/bin" + target="${outputs[out]}/bin/${name}" + (cat <<<"$scriptHeader"; cat "%{content.file}") > "$target" + chmod +x "$target" + %{lib.import_nix "nixpkgs#stdenv.shellDryRun"} "$target" + "%{lib.import_nix "nixpkgs#shellcheck"}/bin/shellcheck" "$target" + "%, + env.scriptHeader = + let path_line = + if std.record.is_empty runtime_inputs then + "" + else + let paths = + runtime_inputs + |> std.record.values + |> std.array.map (fun s => nix-s%"%{s}/bin"%) + |> concat_strings_sep ":" + in + nix-s%"export PATH="%{paths}:$PATH""% + in + nix-s%" + #!%{shell_binary} + set -o errexit + set -o nounset + set -o pipefail + %{path_line} + "%, + } + | NickelPkg, } diff --git a/project.ncl b/project.ncl index 1dd4d62d..e014b375 100644 --- a/project.ncl +++ b/project.ncl @@ -16,6 +16,22 @@ let import_nix = organist.lib.import_nix in }, }, + flake.apps.run-test = + let testScript | organist.builders.ShellApplication = { + name = "run-test.sh", + content.file = "./run-test.sh", + runtime_inputs = { + nickel = organist.lib.import_nix "nickel#nickel-lang-cli", + parallel = import_nix "nixpkgs#parallel", + gnused = import_nix "nixpkgs#gnused", + }, + } + in + { + type = "app", + program | organist.contracts.NixString = nix-s%"%{testScript}/bin/run-test.sh"% + }, + flake.checks | { _ | {