test/shellcheck-services: add configurable source prefix

This allows using this module for services defined outside of nix-bitcoin.
This commit is contained in:
Erik Arvstedt 2022-10-22 19:37:44 +02:00
parent dcca4fb262
commit b840548d40
No known key found for this signature in database
GPG Key ID: 33312B944DD97846
2 changed files with 50 additions and 21 deletions

View File

@ -22,8 +22,7 @@ name: testConfig:
cores = lib.mkDefault 2; cores = lib.mkDefault 2;
}; };
# Run shellcheck on all nix-bitcoin services during machine build time test.shellcheckServices.enable = true;
system.extraDependencies = [ config.test.shellcheckServices ];
}; };
testScript = nodes: let testScript = nodes: let

View File

@ -1,8 +1,24 @@
{ config, pkgs, lib, extendModules, ... }@args: { config, pkgs, lib, extendModules, ... }@args:
with lib; with lib;
let let
options = { options.test.shellcheckServices = {
test.shellcheckServices = mkOption { enable = mkOption {
type = types.bool;
default = false;
description = ''
Whether to shellcheck services during system build time.
'';
};
sourcePrefix = mkOption {
type = with types; nullOr str;
default = null;
description = ''
The definition source path prefix of services to include in the shellcheck.
'';
};
runShellcheck = mkOption {
readOnly = true; readOnly = true;
description = '' description = ''
A derivation that runs shellcheck on all bash scripts included A derivation that runs shellcheck on all bash scripts included
@ -12,26 +28,29 @@ let
}; };
}; };
# A list of all service names that are defined by nix-bitcoin. cfg = config.test.shellcheckServices;
# A list of all service names that are defined in source paths prefixed by
# `sourcePrefix`.
# [ "bitcoind", "clightning", ... ] # [ "bitcoind", "clightning", ... ]
# #
# Algorithm: Parse defintions of `systemd.services` and return all services # Algorithm: Parse defintions of `systemd.services` and return all services
# that only have definitions located in the nix-bitcoin source. # that only have definitions located within `sourcePrefix`.
nix-bitcoin-services = let servicesToCheck = let
inherit (cfg) sourcePrefix;
systemdServices = args.options.systemd.services; systemdServices = args.options.systemd.services;
configSystemdServices = args.config.systemd.services; configSystemdServices = args.config.systemd.services;
nix-bitcoin-source = toString ../..; matchingServices = collectServices true;
nbServices = collectServices true; nonMatchingServices = collectServices false;
nonNbServices = collectServices false;
# Return set of services ({ service1 = true; service2 = true; ... }) # Return set of services ({ service1 = true; service2 = true; ... })
# which are either defined or not defined by nix-bitcoin, depending # which are either defined or not defined within `sourcePrefix`, depending
# on `fromNixBitcoin`. # on `shouldMatch`.
collectServices = fromNixBitcoin: lib.listToAttrs (builtins.concatLists (zipListsWith (services: file: collectServices = shouldMatch: lib.listToAttrs (builtins.concatLists (zipListsWith (services: file:
let let
isNbSource = lib.hasPrefix nix-bitcoin-source file; isMatching = lib.hasPrefix sourcePrefix file;
in in
# Nix has no boolean XOR, so use `if` # Nix has no boolean XOR, so use `if`
lib.optionals (if fromNixBitcoin then isNbSource else !isNbSource) ( lib.optionals (if shouldMatch then isMatching else !isMatching) (
(map (service: { name = service; value = true; }) (builtins.attrNames services)) (map (service: { name = service; value = true; }) (builtins.attrNames services))
) )
# TODO-EXTERNAL: # TODO-EXTERNAL:
@ -39,13 +58,13 @@ let
# is included in nixpkgs stable. # is included in nixpkgs stable.
) systemdServices.definitions systemdServices.files)); ) systemdServices.definitions systemdServices.files));
in in
# Calculate set difference: nbServices - nonNbServices # Calculate set difference: matchingServices - nonMatchingServices
# and exclude unavailable services (defined via `mkIf false ...`) by checking `configSystemdServices`. # and exclude unavailable services (defined via `mkIf false ...`) by checking `configSystemdServices`.
builtins.filter (nbService: builtins.filter (prefixedService:
configSystemdServices ? ${nbService} && (! nonNbServices ? ${nbService}) configSystemdServices ? ${prefixedService} && (! nonMatchingServices ? ${prefixedService})
) (builtins.attrNames nbServices); ) (builtins.attrNames matchingServices);
# The concatenated list of values of ExecStart, ExecStop, ... (`scriptAttrs`) of all `nix-bitcoin-services`. # The concatenated list of values of ExecStart, ExecStop, ... (`scriptAttrs`) of all `servicesToCheck`.
serviceCmds = let serviceCmds = let
scriptAttrs = [ scriptAttrs = [
"ExecStartPre" "ExecStartPre"
@ -69,7 +88,7 @@ let
if builtins.typeOf cmd == "list" then cmd else [ cmd ] if builtins.typeOf cmd == "list" then cmd else [ cmd ]
) )
) scriptAttrs ) scriptAttrs
) nix-bitcoin-services; ) servicesToCheck;
# A list of all binaries included in `serviceCmds` # A list of all binaries included in `serviceCmds`
serviceBinaries = map (cmd: builtins.head ( serviceBinaries = map (cmd: builtins.head (
@ -95,4 +114,15 @@ let
in in
{ {
inherit options; inherit options;
config = mkIf (cfg.enable && cfg.sourcePrefix != null) {
assertions = [
{
assertion = builtins.length servicesToCheck > 0;
message = "test.shellcheckServices: No services found with source prefix `${cfg.sourcePrefix}`";
}
];
system.extraDependencies = [ shellcheckServices ];
};
} }