236: init pkgs-lib and add tests and shell r=nrdxp a=Pacman99

Towards the goal of removing top level folders and putting more things in lib. This shifts shell and tests to lib under the `pkgs-lib` namespace. This namespace is separated by architecture, because those lib functions rely on nixpkgs architecture specific derivations. I think this is the cleanest way to do it, you don't have to instantiate pkgs-lib for each arch, and it exposes some of these functions for others to use.

This PR also fixes multi-arch checks.

Co-authored-by: Pacman99 <pachum99@gmail.com>
This commit is contained in:
bors[bot] 2021-04-10 21:01:33 +00:00 committed by GitHub
commit d5175f6cca
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
22 changed files with 82 additions and 101 deletions

View file

@ -30,7 +30,7 @@
outputs = inputs@{ deploy, nixos, nur, self, utils, ... }: outputs = inputs@{ deploy, nixos, nur, self, utils, ... }:
let let
lib = import ./lib { inherit self nixos inputs; }; lib = import ./lib { inherit self nixos utils inputs; };
in in
lib.mkFlake lib.mkFlake
{ {

View file

@ -19,6 +19,8 @@ lib.makeExtensible (final:
mkFlake = callLibs ./mkFlake; mkFlake = callLibs ./mkFlake;
pkgs-lib = callLibs ./pkgs-lib;
inherit (attrs) mapFilterAttrs genAttrs' safeReadDir inherit (attrs) mapFilterAttrs genAttrs' safeReadDir
pathsToImportedAttrs concatAttrs filterPackages; pathsToImportedAttrs concatAttrs filterPackages;
inherit (lists) pathsIn; inherit (lists) pathsIn;

View file

@ -34,27 +34,21 @@ let
systemOutputs = utils.lib.eachDefaultSystem (system: systemOutputs = utils.lib.eachDefaultSystem (system:
let let
pkgs = multiPkgs.${system}; pkgs = multiPkgs.${system};
pkgs-lib = dev.pkgs-lib.${system};
# all packages that are defined in ./pkgs # all packages that are defined in ./pkgs
legacyPackages = os.mkPackages { inherit pkgs; }; legacyPackages = os.mkPackages { inherit pkgs; };
in in
{ {
checks = checks = pkgs-lib.tests.mkChecks {
let inherit (self.deploy) nodes;
tests = nixos.lib.optionalAttrs (system == "x86_64-linux") hosts = self.nixosConfigurations;
(import "${self}/tests" { inherit self pkgs; }); homes = self.homeConfigurations;
deployHosts = nixos.lib.filterAttrs };
(n: _: self.nixosConfigurations.${n}.config.nixpkgs.system == system)
self.deploy.nodes;
deployChecks = deploy.lib.${system}.deployChecks { nodes = deployHosts; };
in
nixos.lib.recursiveUpdate tests deployChecks;
inherit legacyPackages; inherit legacyPackages;
packages = dev.filterPackages system legacyPackages; packages = dev.filterPackages system legacyPackages;
devShell = import "${self}/shell" { devShell = pkgs-lib.shell;
inherit self system;
};
}); });
in in
outputs // systemOutputs outputs // systemOutputs

20
lib/pkgs-lib/default.nix Normal file
View file

@ -0,0 +1,20 @@
args@{ lib, dev, utils, nixos, ... }:
lib.genAttrs utils.lib.defaultSystems (system:
lib.makeExtensible (final:
let
pkgs = import nixos { inherit system; };
callLibs = file: import file
(args // {
inherit pkgs system;
pkgs-lib = final;
});
in
with final;
{
inherit callLibs;
tests = callLibs ./tests;
shell = callLibs ./shell;
}
)
)

View file

@ -1,25 +1,23 @@
{ self ? (import ../compat).defaultNix { lib, dev, inputs, system, nixos, ... }:
, system ? builtins.currentSystem
, extern ? import ../extern { inherit (self) inputs; }
, overrides ? import ../overrides
}:
let let
pkgs = (self.lib.os.mkPkgs { overlays = [
inherit overrides extern; inputs.devshell.overlay
}).${system}; (final: prev: {
deploy-rs =
inputs.deploy.packages.${prev.system}.deploy-rs;
})
];
inherit (pkgs) lib; pkgs = dev.os.pkgImport nixos overlays system;
flk = pkgs.callPackage ./flk.nix { };
installPkgs = (lib.nixosSystem { installPkgs = (lib.nixosSystem {
inherit system; inherit system;
modules = [ ]; modules = [ ];
}).config.system.build; }).config.system.build;
flk = pkgs.callPackage ./flk.nix { };
in in
pkgs.devshell.mkShell pkgs.devshell.mkShell {
{
imports = [ (pkgs.devshell.importTOML ./devshell.toml) ]; imports = [ (pkgs.devshell.importTOML ./devshell.toml) ];
packages = with installPkgs; [ packages = with installPkgs; [

View file

@ -1,17 +1,29 @@
{ self, pkgs }: { pkgs-lib, pkgs, system, inputs, nixos, lib, ... }:
let let
inherit (self.inputs) nixos; mkChecks = { hosts, nodes, homes ? { } }:
inherit (self.nixosConfigurations.NixOS.config.lib) testModule specialArgs; let
deployHosts = lib.filterAttrs
(n: _: hosts.${n}.config.nixpkgs.system == system)
nodes;
deployChecks = inputs.deploy.lib.${system}.deployChecks { nodes = deployHosts; };
tests =
{ libTests = libTests; }
// lib.optionalAttrs (deployHosts != { }) {
profilesTest = profilesTest (hosts.${(builtins.head (builtins.attrNames deployHosts))});
} // lib.mapAttrs (n: v: v.home.activationPackage) homes;
mkTest = in
lib.recursiveUpdate tests deployChecks;
mkTest = host:
let let
nixosTesting = nixosTesting =
(import "${nixos}/nixos/lib/testing-python.nix" { (import "${nixos}/nixos/lib/testing-python.nix" {
inherit (pkgs.stdenv.hostPlatform) system; inherit system;
inherit specialArgs; inherit (host.config.lib) specialArgs;
inherit pkgs; inherit pkgs;
extraConfigurations = [ extraConfigurations = [
testModule host.config.lib.testModule
]; ];
}); });
in in
@ -27,9 +39,8 @@ let
else loadedTest; else loadedTest;
in in
nixosTesting.makeTest calledTest; nixosTesting.makeTest calledTest;
in
{ profilesTest = host: mkTest host {
profilesTest = mkTest {
name = "profiles"; name = "profiles";
machine = { suites, ... }: { machine = { suites, ... }: {
@ -41,14 +52,12 @@ in
''; '';
}; };
homeTest = self.homeConfigurations."nixos@NixOS".home.activationPackage;
libTests = pkgs.runCommandNoCC "devos-lib-tests" libTests = pkgs.runCommandNoCC "devos-lib-tests"
{ {
buildInputs = [ buildInputs = [
pkgs.nix pkgs.nix
( (
let tests = import ./lib.nix { inherit self pkgs; }; let tests = pkgs-lib.callLibs ./lib.nix;
in in
if tests == [ ] if tests == [ ]
then null then null
@ -70,5 +79,5 @@ in
touch $out touch $out
''; '';
} in
{ inherit mkTest libTests profilesTest mkChecks; }

View file

@ -1,6 +1,5 @@
{ self, pkgs }: { pkgs, lib, dev, ... }:
let inherit (self.inputs.nixos) lib; in with dev;
with self.lib;
lib.runTests { lib.runTests {
testConcatAttrs = { testConcatAttrs = {
expr = concatAttrs [{ foo = 1; } { bar = 2; } { baz = 3; }]; expr = concatAttrs [{ foo = 1; } { bar = 2; } { baz = 3; }];
@ -28,29 +27,24 @@ lib.runTests {
expected = { foobar = 1; }; expected = { foobar = 1; };
}; };
testPathsIn = testPathsIn = {
let testPaths = pkgs.runCommandNoCC "test-paths-in" { } '' expr = pathsIn (toString ./testPathsIn);
mkdir -p $out/{foo,bar,baz}
'';
in
{
expr = pathsIn testPaths;
expected = [ expected = map toString [
"${testPaths}/bar" ./testPathsIn/bar
"${testPaths}/baz" ./testPathsIn/baz
"${testPaths}/foo" ./testPathsIn/foo
]; ];
}; };
testPathsToImportedAttrs = { testPathsToImportedAttrs = {
expr = expr =
pathsToImportedAttrs [ pathsToImportedAttrs [
"${self}/tests/testPathsToImportedAttrs/dir" (toString ./testPathsToImportedAttrs/dir)
"${self}/tests/testPathsToImportedAttrs/foo.nix" ./testPathsToImportedAttrs/foo.nix
"${self}/tests/testPathsToImportedAttrs/bar.nix" ./testPathsToImportedAttrs/bar.nix
"${self}/tests/testPathsToImportedAttrs/t.nix" ./testPathsToImportedAttrs/t.nix
"${self}/tests/testPathsToImportedAttrs/f.nix" ./testPathsToImportedAttrs/f.nix
]; ];
expected = { expected = {
@ -70,7 +64,7 @@ lib.runTests {
]; ];
testSafeReadDir = { testSafeReadDir = {
expr = safeReadDir "${self}/tests/profiles" // safeReadDir "${self}/nonexistentdir"; expr = safeReadDir ./profiles // safeReadDir ./nonexistentdir;
expected = { expected = {
foo = "directory"; foo = "directory";
t = "directory"; t = "directory";

View file

View file

View file

View file

@ -1,36 +0,0 @@
# Testing
Testing is always an important aspect of any software development project, and
NixOS offers some incredibly powerful tools to write tests for your
configuration, and, optionally, run them in
[CI](../doc/integrations/hercules.md).
## Lib Tests
You can easily write tests for your own library functions in the
___tests/lib.nix___ file and they will be run on every `nix flake check` or
during a CI run.
## Unit Tests
Unit tests are can be created from regular derivations, and they can do
almost anything you can imagine. By convention, it is best to test your
packages during their [check phase][check]. All packages and their tests will
be built during CI.
## Integration Tests
You can write integration tests for one or more NixOS VMs that can,
optionally, be networked together, and yes, it's as awesome as it sounds!
Be sure to use the `mkTest` function, in the [___tests/default.nix___][default]
which wraps the official [testing-python][testing-python] function to ensure
that the system is setup exactly as it is for a bare DevOS system. There are
already great resources for learning how to use these tests effectively,
including the official [docs][test-doc], a fantastic [blog post][test-blog],
and the examples in [nixpkgs][nixos-tests].
[test-doc]: https://nixos.org/manual/nixos/stable/index.html#sec-nixos-tests
[test-blog]: https://www.haskellforall.com/2020/11/how-to-use-nixos-for-lightweight.html
[default]: https://github.com/divnix/devos/tree/core/tests/default.nix
[run-test]: https://github.com/NixOS/nixpkgs/blob/6571462647d7316aff8b8597ecdf5922547bf365/lib/debug.nix#L154-L166
[nixos-tests]: https://github.com/NixOS/nixpkgs/tree/master/nixos/tests
[testing-python]: https://github.com/NixOS/nixpkgs/tree/master/nixos/lib/testing-python.nix
[check]: https://nixos.org/manual/nixpkgs/stable/#ssec-check-phase