clan: Add autoloaded clanModules from flake inputs. Rename 'directory' to 'self' in buildClan

This commit is contained in:
Qubasa
2025-01-24 12:32:04 +07:00
parent 83c6ad19eb
commit ed6aaf5f0c
14 changed files with 70 additions and 33 deletions

View File

@@ -41,7 +41,7 @@
{
clan = {
meta.name = "clan-core";
directory = self;
inherit self;
};
systems = import systems;
imports =

View File

@@ -0,0 +1,23 @@
{
lib,
self,
...
}:
let
# Returns an attrset with inputs that have the attribute `clanModules`
inputsWithClanModules = lib.filterAttrs (
_name: value: builtins.hasAttr "clanModules" value
) self.inputs;
flattenedClanModules = lib.foldl' (
acc: input:
lib.mkMerge [
acc
input.clanModules
]
) { } (lib.attrValues inputsWithClanModules);
in
{
inventory.modules = flattenedClanModules;
}

View File

@@ -8,7 +8,8 @@
}:
{
## Inputs
directory, # The directory containing the machines subdirectory # allows to include machine-specific modules i.e. machines.${name} = { ... }
directory ? null, # The directory containing the machines subdirectory # allows to include machine-specific modules i.e. machines.${name} = { ... }
self ? null,
# A map from arch to pkgs, if specified this nixpkgs will be only imported once for each system.
# This improves performance, but all nipxkgs.* options will be ignored.
# deadnix: skip
@@ -19,15 +20,27 @@
...
}@attrs:
let
eval = import ./eval.nix {
evalUnchecked = import ./eval.nix {
inherit
lib
nixpkgs
specialArgs
clan-core
;
self = directory;
inherit specialArgs;
self = if self != null then self else directory;
};
# Doing `self ? lib.trace "please use self" directory`, doesn't work
# as when both (directory and self) are set we get an infinite recursion error
eval =
if directory == null && self == null then
throw "The buildClan function requires argument 'self' to be set"
else if directory != null && self != null then
throw "Both 'self' and 'directory' are set, please remove 'directory' in favor of the 'self' argument"
else if directory != null then
lib.warn "The 'directory' argument in buildClan has been deprecated in favor of the 'self' argument" evalUnchecked
else
evalUnchecked;
rest = builtins.removeAttrs attrs [ "specialArgs" ];
in
eval {
@@ -35,5 +48,6 @@ eval {
rest
# implementation
./module.nix
./auto-imports.nix
];
}

View File

@@ -8,8 +8,7 @@ let
in
{
options = {
# Required options
directory = lib.mkOption {
self = lib.mkOption {
type = types.path;
default = self;
defaultText = "Root directory of the flake";

View File

@@ -7,7 +7,7 @@
}:
let
inherit (config)
directory
self
machines
pkgsForSystem
specialArgs
@@ -44,7 +44,7 @@ let
serviceConfigs = (
buildInventory {
inherit inventory;
inherit directory;
inherit self;
}
);
@@ -59,14 +59,14 @@ let
nixpkgs.lib.nixosSystem {
modules =
let
hwConfig = "${directory}/machines/${name}/hardware-configuration.nix";
diskoConfig = "${directory}/machines/${name}/disko.nix";
hwConfig = "${self}/machines/${name}/hardware-configuration.nix";
diskoConfig = "${self}/machines/${name}/disko.nix";
in
[
{
# Autoinclude configuration.nix and hardware-configuration.nix
imports = builtins.filter builtins.pathExists [
"${directory}/machines/${name}/configuration.nix"
"${self}/machines/${name}/configuration.nix"
hwConfig
diskoConfig
];
@@ -81,7 +81,7 @@ let
{
# Settings
clan.core.settings = {
inherit directory;
directory = self;
inherit (config.inventory.meta) name icon;
machine = {
@@ -160,7 +160,7 @@ let
) supportedSystems
);
inventoryFile = "${directory}/inventory.json";
inventoryFile = "${self}/inventory.json";
inventoryLoaded =
if builtins.pathExists inventoryFile then
@@ -171,6 +171,7 @@ let
in
{
imports = [
(lib.mkRenamedOptionModule [ "directory" ] [ "self" ])
# Merge the inventory file
{
inventory = _: {
@@ -180,9 +181,9 @@ in
}
# TODO: Figure out why this causes infinite recursion
{
inventory.machines = lib.optionalAttrs (builtins.pathExists "${directory}/machines") (
inventory.machines = lib.optionalAttrs (builtins.pathExists "${self}/machines") (
builtins.mapAttrs (_n: _v: { }) (
(lib.filterAttrs (_: t: t == "directory") (builtins.readDir "${directory}/machines"))
(lib.filterAttrs (_: t: t == "directory") (builtins.readDir "${self}/machines"))
)
);
}

View File

@@ -28,7 +28,7 @@ in
test_all_simple =
let
config = evalClan {
directory = ./.;
self = ./.;
machines = { };
inventory = {
meta.name = "test";

View File

@@ -197,7 +197,7 @@ let
machinesFromInventory :: Inventory -> { ${machine_name} :: NixOSConfiguration }
*/
buildInventory =
{ inventory, directory }:
{ inventory, self }:
# For every machine in the inventory, build a NixOS configuration
# For each machine generate config, forEach service, if the machine is used.
builtins.mapAttrs (
@@ -207,8 +207,8 @@ let
machineName
machineConfig
inventory
directory
;
directory = self;
}
) (inventory.machines or { });
in

View File

@@ -13,14 +13,14 @@ in
# Empty inventory should return an empty module
expr = buildInventory {
inventory = { };
directory = ./.;
self = ./.;
};
expected = { };
};
test_inventory_role_imports =
let
configs = buildInventory {
directory = ./.;
self = ./.;
inventory = {
modules = clan-core.clanModules;
services = {
@@ -62,7 +62,7 @@ in
test_inventory_tag_resolve =
let
configs = buildInventory {
directory = ./.;
self = ./.;
inventory = {
modules = clan-core.clanModules;
services = {
@@ -102,7 +102,7 @@ in
test_inventory_multiple_roles =
let
configs = buildInventory {
directory = ./.;
self = ./.;
inventory = {
modules = clan-core.clanModules;
services = {
@@ -132,7 +132,7 @@ in
test_inventory_module_doesnt_exist =
let
configs = buildInventory {
directory = ./.;
self = ./.;
inventory = {
modules = clan-core.clanModules;
services = {
@@ -157,7 +157,7 @@ in
test_inventory_role_doesnt_exist =
let
configs = buildInventory {
directory = ./.;
self = ./.;
inventory = {
modules = clan-core.clanModules;
services = {
@@ -183,7 +183,7 @@ in
test_inventory_tag_doesnt_exist =
let
configs = buildInventory {
directory = ./.;
self = ./.;
inventory = {
modules = clan-core.clanModules;
services = {
@@ -211,7 +211,7 @@ in
test_inventory_disabled_service =
let
configs = buildInventory {
directory = ./.;
self = ./.;
inventory = {
modules = clan-core.clanModules;
services = {

View File

@@ -9,7 +9,7 @@
{ self, clan-core }:
let
clan = clan-core.lib.buildClan {
directory = self;
inherit self;
meta.name = "test_flake_with_core";
machines = {
vm1 =

View File

@@ -9,7 +9,7 @@
{ self, clan-core }:
let
clan = clan-core.lib.buildClan {
directory = self;
inherit self;
meta.name = "test_flake_with_core_and_pass";
machines = {
vm1 =

View File

@@ -9,7 +9,7 @@
{ self, clan-core }:
let
clan = clan-core.lib.buildClan {
directory = self;
inherit self;
meta.name = "test_flake_with_core_dynamic_machines";
machines =
let

View File

@@ -29,7 +29,7 @@
specialArgs.self = {
inherit (self) inputs nixosModules packages;
};
directory = self;
inherit self;
machines = {
# "jon" will be the hostname of the machine
jon =

View File

@@ -6,7 +6,7 @@
{ self, clan-core, ... }:
let
# Usage see: https://docs.clan.lol
clan = clan-core.lib.buildClan { directory = self; };
clan = clan-core.lib.buildClan { inherit self; };
in
{
# all machines managed by Clan

View File

@@ -9,7 +9,7 @@
let
# Usage see: https://docs.clan.lol
clan = clan-core.lib.buildClan {
directory = self;
inherit self;
# Ensure this is unique among all clans you want to use.
meta.name = "__CHANGE_ME__";