summary refs log tree commit diff
path: root/pkgs/build-support/testers/default.nix
blob: fc10597e3e120ededf66e685290c823df19a0223 (plain) (blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
{ pkgs, buildPackages, lib, callPackage, runCommand, stdenv, substituteAll, testers }:
# Documentation is in doc/builders/testers.chapter.md
{
  # See https://nixos.org/manual/nixpkgs/unstable/#tester-testBuildFailure
  # or doc/builders/testers.chapter.md
  testBuildFailure = drv: drv.overrideAttrs (orig: {
    builder = buildPackages.bash;
    args = [
      (substituteAll { coreutils = buildPackages.coreutils; src = ./expect-failure.sh; })
      orig.realBuilder or stdenv.shell
    ] ++ orig.args or ["-e" (orig.builder or ../../stdenv/generic/default-builder.sh)];
  });

  # See https://nixos.org/manual/nixpkgs/unstable/#tester-testEqualDerivation
  # or doc/builders/testers.chapter.md
  testEqualDerivation = callPackage ./test-equal-derivation.nix { };

  # See https://nixos.org/manual/nixpkgs/unstable/#tester-testEqualContents
  # or doc/builders/testers.chapter.md
  testEqualContents = {
    assertion,
    actual,
    expected,
  }: runCommand "equal-contents-${lib.strings.toLower assertion}" {
    inherit assertion actual expected;
  } ''
    echo "Checking:"
    echo "$assertion"
    if ! diff -U5 -r "$actual" "$expected" --color=always
    then
      echo
      echo 'Contents must be equal, but were not!'
      echo
      echo "+: expected,   at $expected"
      echo "-: unexpected, at $actual"
      exit 1
    else
      find "$expected" -type f -executable > expected-executables | sort
      find "$actual" -type f -executable > actual-executables | sort
      if ! diff -U0 actual-executables expected-executables --color=always
      then
        echo
        echo "Contents must be equal, but some files' executable bits don't match"
        echo
        echo "+: make this file executable in the actual contents"
        echo "-: make this file non-executable in the actual contents"
        exit 1
      else
        echo "expected $expected and actual $actual match."
        echo 'OK'
        touch $out
      fi
    fi
  '';

  # See https://nixos.org/manual/nixpkgs/unstable/#tester-testVersion
  # or doc/builders/testers.chapter.md
  testVersion =
    { package,
      command ? "${package.meta.mainProgram or package.pname or package.name} --version",
      version ? package.version,
    }: runCommand "${package.name}-test-version" { nativeBuildInputs = [ package ]; meta.timeout = 60; } ''
      if output=$(${command} 2>&1); then
        if grep -Fw -- "${version}" - <<< "$output"; then
          touch $out
        else
          echo "Version string '${version}' not found!" >&2
          echo "The output was:" >&2
          echo "$output" >&2
          exit 1
        fi
      else
        echo -n ${lib.escapeShellArg command} >&2
        echo " returned a non-zero exit code." >&2
        echo "$output" >&2
        exit 1
      fi
    '';

  # See doc/builders/testers.chapter.md or
  # https://nixos.org/manual/nixpkgs/unstable/#tester-invalidateFetcherByDrvHash
  invalidateFetcherByDrvHash = f: args:
    let
      drvPath = (f args).drvPath;
      # It's safe to discard the context, because we don't access the path.
      salt = builtins.unsafeDiscardStringContext (lib.substring 0 12 (baseNameOf drvPath));
      # New derivation incorporating the original drv hash in the name
      salted = f (args // { name = "${args.name or "source"}-salted-${salt}"; });
      # Make sure we did change the derivation. If the fetcher ignores `name`,
      # `invalidateFetcherByDrvHash` doesn't work.
      checked =
        if salted.drvPath == drvPath
        then throw "invalidateFetcherByDrvHash: Adding the derivation hash to the fixed-output derivation name had no effect. Make sure the fetcher's name argument ends up in the derivation name. Otherwise, the fetcher will not be re-run when its implementation changes. This is important for testing."
        else salted;
    in checked;

  # See doc/builders/testers.chapter.md or
  # https://nixos.org/manual/nixpkgs/unstable/#tester-runNixOSTest
  runNixOSTest =
    let nixos = import ../../../nixos/lib {
      inherit lib;
    };
    in testModule:
        nixos.runTest {
          _file = "pkgs.runNixOSTest implementation";
          imports = [
            (lib.setDefaultModuleLocation "the argument that was passed to pkgs.runNixOSTest" testModule)
          ];
          hostPkgs = pkgs;
          node.pkgs = pkgs;
        };

  # See doc/builders/testers.chapter.md or
  # https://nixos.org/manual/nixpkgs/unstable/#tester-invalidateFetcherByDrvHash
  nixosTest =
    let
      /* The nixos/lib/testing-python.nix module, preapplied with arguments that
       * make sense for this evaluation of Nixpkgs.
       */
      nixosTesting =
        (import ../../../nixos/lib/testing-python.nix {
          inherit (stdenv.hostPlatform) system;
          inherit pkgs;
          extraConfigurations = [(
            { lib, ... }: {
              config.nixpkgs.pkgs = lib.mkDefault pkgs;
            }
          )];
        });
    in
      test:
        let
          loadedTest = if builtins.typeOf test == "path"
            then import test
            else test;
          calledTest = lib.toFunction loadedTest pkgs;
        in
          nixosTesting.simpleTest calledTest;

  hasPkgConfigModule =
    { moduleName, ... }@args:
    lib.warn "testers.hasPkgConfigModule has been deprecated in favor of testers.hasPkgConfigModules. It accepts a list of strings via the moduleNames argument instead of a single moduleName." (
      testers.hasPkgConfigModules (builtins.removeAttrs args [ "moduleName" ] // {
        moduleNames = [ moduleName ];
      })
    );
  hasPkgConfigModules = callPackage ./hasPkgConfigModules/tester.nix { };

  testMetaPkgConfig = callPackage ./testMetaPkgConfig/tester.nix { };
}