diff --git a/lib/default.nix b/bootstrap.nix similarity index 52% rename from lib/default.nix rename to bootstrap.nix index 237d370..7083b15 100644 --- a/lib/default.nix +++ b/bootstrap.nix @@ -1,12 +1,31 @@ +# Turns the abstract per system configuration in ‹flake.nix› to individual +# nixos, darwin and home-manager configs. Additionally for each system architecture +# defines formatting with ‹nix fmt› and a custom ‹nix develop› shell with helpers +# for activating configurations on new machines. Also defines a custom lib with +# extensions defined in ‹lib.nix›. +# +# For all nixos, darwin, and home-manager config autoloads ‹config.nix›, agenix, and +# all autoloaded modules. +# +# Usage: +# ``` +# import ./bootstrap.nix inputs { +# = { +# homes. = path; +# systems. = path; +# }; +# } +# ``` inputs @ { agenix, - home-manager, - nix-darwin, nixpkgs, self, ... }: systems: let - inherit ((import nixpkgs {system = "x86_64-linux";}).lib) foldl mapAttrsToList recursiveUpdate; + # system agnostic lib with custom extensions + lib = nixpkgs.lib.extend (import ./lib.nix inputs); + + inherit (lib) foldl recursiveUpdate mapAttrsToList; mapSystem = system: { homes ? {}, @@ -17,30 +36,16 @@ inputs @ { config.allowUnfree = true; }; - lib = pkgs.lib.extend (lib: super: let - # Automatically detect all .nix files in lib/ directory, excluding default.nix - libs = - builtins.filter - (path: path != "default.nix" && lib.strings.hasSuffix ".nix" path) - (builtins.attrNames (builtins.readDir ./.)); - importLib = path: import ./${path} {inherit inputs lib pkgs system;}; - in { - # Expose custom lib extensions via `_.` prefix - _ = lib.foldr (a: b: a // b) {} (map importLib libs); - # Make sure to keep library extensions from home-manager - hm = home-manager.lib.hm; - }); - systemSpecifics = - if system == "aarch64-darwin" || system == "x86_64-darwin" + if pkgs.stdenv.isDarwin then { - fn = nix-darwin.lib.darwinSystem; + fn = lib.darwinSystem; option = "darwinConfigurations"; command = "nix run nix-darwin --"; agenixModule = agenix.darwinModules.default; } else { - fn = nixpkgs.lib.nixosSystem; + fn = lib.nixosSystem; option = "nixosConfigurations"; command = "nixos-rebuild"; agenixModule = agenix.nixosModules.default; @@ -52,35 +57,31 @@ inputs @ { specialArgs = {inherit inputs lib pkgs self system osName;}; modules = [ - ../config.nix + ./config.nix systemSpecifics.agenixModule {networking.hostName = lib.mkDefault osName;} path ] - ++ lib._.autoloadedModules; + ++ lib.autoloadedModules; }); mapHomes = builtins.mapAttrs (homeName: path: - home-manager.lib.homeManagerConfiguration { + lib.homeManagerConfiguration { inherit pkgs; extraSpecialArgs = {inherit inputs lib system homeName;}; modules = [ - ../config.nix + ./config.nix agenix.homeManagerModules.default path ] - ++ lib._.autoloadedModules; + ++ lib.autoloadedModules; }); in { formatter.${system} = pkgs.alejandra; devShells.${system}.default = pkgs.mkShell { packages = [pkgs.alejandra pkgs.home-manager]; shellHook = '' - # Set custom prompt colors using ANSI escape codes - # \[\e[1;32m\] - Bold Green - # \[\e[1;34m\] - Bold Blue - # \[\e[0m\] - Reset formatting export PS1='\[\e[1;32m\][${system}:\w]\$\[\e[0m\] ' echo echo "‹os›: ${builtins.concatStringsSep ", " (builtins.attrNames hosts)}" @@ -100,15 +101,18 @@ inputs @ { homeConfigurations = mapHomes homes; }; - mappedSystems = foldl recursiveUpdate {} (mapAttrsToList mapSystem systems); + configuration = foldl recursiveUpdate {} (mapAttrsToList mapSystem systems); - # Merge all options into one attribute set for use with ‹nixd› - options = let - getOptions = configs: foldl recursiveUpdate {} (mapAttrsToList (_: value: value.options) configs); - in { - nixos = getOptions mappedSystems.nixosConfigurations; - darwin = getOptions mappedSystems.darwinConfigurations; - home-manager = getOptions mappedSystems.homeConfigurations; - }; + getOptions = configs: foldl recursiveUpdate {} (mapAttrsToList (_: value: value.options) configs); in - mappedSystems // {inherit options;} + configuration + // { + inherit lib; + + # Merge all options into one attribute set for use with ‹nixd› + options = { + nixos = getOptions self.nixosConfigurations; + darwin = getOptions self.darwinConfigurations; + home-manager = getOptions self.homeConfigurations; + }; + } diff --git a/flake.nix b/flake.nix index 1fb6924..5338c91 100644 --- a/flake.nix +++ b/flake.nix @@ -28,7 +28,7 @@ }; outputs = inputs: - import ./lib inputs { + import ./bootstrap.nix inputs { aarch64-darwin = { homes.jakub-macos = ./homes/jakub-macos; hosts.nyckelharpa = ./hosts/nyckelharpa; diff --git a/homes/jakub-macos/default.nix b/homes/jakub-macos/default.nix index b3d1cbc..da9edc8 100644 --- a/homes/jakub-macos/default.nix +++ b/homes/jakub-macos/default.nix @@ -4,7 +4,7 @@ pkgs, ... }: { - imports = lib._.moduleImports [ + imports = lib.moduleImports [ "common/aliases" "common/env" "common/ghostty" diff --git a/homes/jakub-nixos/default.nix b/homes/jakub-nixos/default.nix index 2e65981..bb66fbd 100644 --- a/homes/jakub-nixos/default.nix +++ b/homes/jakub-nixos/default.nix @@ -4,7 +4,7 @@ pkgs, ... }: { - imports = lib._.moduleImports [ + imports = lib.moduleImports [ "common/aliases" "common/env" "common/git" diff --git a/homes/jakub-server/default.nix b/homes/jakub-server/default.nix index df3bdc3..ed3af31 100644 --- a/homes/jakub-server/default.nix +++ b/homes/jakub-server/default.nix @@ -1,5 +1,5 @@ {lib, ...}: { - imports = lib._.moduleImports [ + imports = lib.moduleImports [ "common/aliases" "common/env" "common/git" diff --git a/hosts/harmonium/default.nix b/hosts/harmonium/default.nix index 003ca6f..94f3b01 100644 --- a/hosts/harmonium/default.nix +++ b/hosts/harmonium/default.nix @@ -11,7 +11,7 @@ inputs.nixos-hardware.nixosModules.lenovo-thinkpad-p14s-amd-gen2 ./hardware-configuration.nix ] - ++ lib._.moduleImports [ + ++ lib.moduleImports [ "common/nix" "common/packages" ]; diff --git a/hosts/nyckelharpa/default.nix b/hosts/nyckelharpa/default.nix index 0be74a0..861b475 100644 --- a/hosts/nyckelharpa/default.nix +++ b/hosts/nyckelharpa/default.nix @@ -9,7 +9,7 @@ ./homebrew.nix ./system.nix ] - ++ lib._.moduleImports [ + ++ lib.moduleImports [ "common/nix" "common/packages" "darwin/icons" diff --git a/hosts/organ/default.nix b/hosts/organ/default.nix index d24473f..5583779 100644 --- a/hosts/organ/default.nix +++ b/hosts/organ/default.nix @@ -16,7 +16,7 @@ ./syncthing.nix ./users.nix ] - ++ lib._.moduleImports [ + ++ lib.moduleImports [ "common/nix" "common/packages" "server/dns" @@ -24,8 +24,9 @@ "server/tailscale" ]; - age.secrets = lib._.defineSecrets ["organ-tailscale-auth-key"] { - "organ-seafile-password" = { + age.secrets = lib.defineSecrets { + organ-tailscale-auth-key = {}; + organ-seafile-password = { owner = config.services.seafile.user; mode = "0600"; }; diff --git a/hosts/organ/mail.nix b/hosts/organ/mail.nix index e2fbe01..3ca4b35 100644 --- a/hosts/organ/mail.nix +++ b/hosts/organ/mail.nix @@ -8,7 +8,7 @@ in { imports = [inputs.simple-nixos-mailserver.nixosModule]; - age.secrets = lib._.defineSecrets ["organ-sasl-passwd"] {}; + age.secrets = lib.defineSecrets {organ-sasl-passwd = {};}; mailserver = { enable = true; diff --git a/hosts/organ/users.nix b/hosts/organ/users.nix index 3a80776..01818e4 100644 --- a/hosts/organ/users.nix +++ b/hosts/organ/users.nix @@ -4,7 +4,7 @@ pkgs, ... }: { - age.secrets = lib._.defineSecrets ["organ-jakub-password-hash"] {}; + age.secrets = lib.defineSecrets {organ-jakub-password-hash = {};}; users.users = { ${config.username} = { diff --git a/lib.nix b/lib.nix new file mode 100644 index 0000000..eed46c8 --- /dev/null +++ b/lib.nix @@ -0,0 +1,40 @@ +inputs: lib: _: +{ + autoloadedModules = let + optionsDir = ./modules/autoload; + nixFiles = lib.filterAttrs (n: _: lib.hasSuffix ".nix" n) (builtins.readDir optionsDir); + in + map (file: optionsDir + "/${file}") (builtins.attrNames nixFiles); + + # Helper to easily import modules in home/system configs + moduleImports = let + modulePath = path: + if builtins.pathExists ./modules/${path} + then ./modules/${path} + else ./modules/${path}.nix; + in + builtins.map modulePath; + + # On macOS creates a simple package that symlinks to a package installed by homebrew + brew-alias = pkgs: name: + lib.mkIf pkgs.stdenv.isDarwin + (pkgs.stdenv.mkDerivation { + name = "${name}-brew"; + version = "1.0.0"; + dontUnpack = true; + installPhase = '' + mkdir -p $out/bin + ln -s /opt/homebrew/bin/${name} $out/bin/${name} + ''; + meta = with pkgs.lib; { + mainProgram = "${name}"; + description = "Wrapper for Homebrew-installed ${name}"; + platforms = platforms.darwin; + }; + }); + + defineSecrets = secrets: lib.mapAttrs (name: options: {file = ../secrets + "/${name}.age";} // options) secrets; +} +# Make sure to add lib extensions from inputs +// inputs.home-manager.lib +// inputs.nix-darwin.lib diff --git a/lib/README.md b/lib/README.md deleted file mode 100644 index d8db78c..0000000 --- a/lib/README.md +++ /dev/null @@ -1,64 +0,0 @@ -# lib - -Library has three important functions: - -1. Moves configuration boilerplate out of the main `flake.nix` by providing an abstraction to define - home-manager and system configurations. For each defined system architecture it configures: - - `nix fmt` - Alejandra formatter - - `nix develop` - custom shell with `hm` and `os` aliases for activating the configurations - -2. Autoloads [`config.nix`](../config.nix), [agenix](https://github.com/ryantm/agenix), - and [`autoloaded modules`](../modules/autoload) for all home-manager and system configurations - -3. Extends the default lib by loading all `.nix` file in the `lib` directory under the `_` namespace - -## Configuration abstraction -```nix -import ./lib inputs { - = { - homes. = path; - systems. = path; - }; -} -``` - -## `lib` extensions - -### `lib._.moduleImports` -Helper to make it easier to import modules from the `modules` directory. -Automatically includes `.nix` suffix for supplied paths, where necessary. - -```nix -{lib, ...}: { - imports = lib._.moduleImports [ - "common/git" - "common/zsh" - # ... - ]; -} -``` - -### `lib._.autoloadedModules` -Helper to autoload modules from the `modules/autoload` directory. -Automatically used when creating home-manager and system configurations. - -### `lib._.defineSecrets` -Helper to define agenix secrets in a more concise way. - -```nix -{lib, ...}: { - age.secrets = lib._.defineSecrets ["secret1" "secret2"] { - secret3 = {owner = "foobar";}; - }; - - # produces equivalent configuration to - # age.secrets = { - # secret1.file = ../secrets/secret1.age; - # secret2.file = ../secrets/secret2.age; - # secret3 = { - # file = ../secrets/secret3.age; - # owner = "foobar"; - # }; - # } -} -``` diff --git a/lib/autoload.nix b/lib/autoload.nix deleted file mode 100644 index 9d662e6..0000000 --- a/lib/autoload.nix +++ /dev/null @@ -1,7 +0,0 @@ -{lib, ...}: { - autoloadedModules = let - optionsDir = ../modules/autoload; - nixFiles = lib.filterAttrs (n: _: lib.hasSuffix ".nix" n) (builtins.readDir optionsDir); - in - map (file: optionsDir + "/${file}") (builtins.attrNames nixFiles); -} diff --git a/lib/brew-alias.nix b/lib/brew-alias.nix deleted file mode 100644 index 64ca23d..0000000 --- a/lib/brew-alias.nix +++ /dev/null @@ -1,23 +0,0 @@ -{ - lib, - pkgs, - ... -}: { - # On macOS creates a simple package that symlinks to a package installed by homebrew - brew-alias = name: - lib.mkIf pkgs.stdenv.isDarwin - (pkgs.stdenv.mkDerivation { - name = "${name}-brew"; - version = "1.0.0"; - dontUnpack = true; - installPhase = '' - mkdir -p $out/bin - ln -s /opt/homebrew/bin/${name} $out/bin/${name} - ''; - meta = with pkgs.lib; { - mainProgram = "${name}"; - description = "Wrapper for Homebrew-installed ${name}"; - platforms = platforms.darwin; - }; - }); -} diff --git a/lib/modules.nix b/lib/modules.nix deleted file mode 100644 index 399d258..0000000 --- a/lib/modules.nix +++ /dev/null @@ -1,9 +0,0 @@ -{...}: { - moduleImports = let - modulePath = path: - if builtins.pathExists ../modules/${path} - then ../modules/${path} - else ../modules/${path}.nix; - in - builtins.map modulePath; -} diff --git a/lib/secrets.nix b/lib/secrets.nix deleted file mode 100644 index b507fb0..0000000 --- a/lib/secrets.nix +++ /dev/null @@ -1,7 +0,0 @@ -{lib, ...}: { - defineSecrets = secretNames: secretsSet: let - simpleSecrets = lib.genAttrs secretNames (name: {file = ../secrets + "/${name}.age";}); - complexSecrets = lib.mapAttrs (name: options: {file = ../secrets + "/${name}.age";} // options) secretsSet; - in - simpleSecrets // complexSecrets; -} diff --git a/modules/common/ghostty.nix b/modules/common/ghostty.nix index a1a885e..7b122e4 100644 --- a/modules/common/ghostty.nix +++ b/modules/common/ghostty.nix @@ -1,9 +1,13 @@ # [home-manager] -{lib, ...}: { +{ + lib, + pkgs, + ... +}: { programs.ghostty = { enable = true; # On macOS the nix build of ghostty is broken - package = lib._.brew-alias "ghostty"; + package = lib.brew-alias pkgs "ghostty"; enableZshIntegration = true; settings = { theme = "dark:rose-pine,light:rose-pine-dawn"; diff --git a/modules/common/mise.nix b/modules/common/mise.nix index 3807a81..8bc2d2e 100644 --- a/modules/common/mise.nix +++ b/modules/common/mise.nix @@ -2,6 +2,7 @@ { config, lib, + pkgs, ... }: let inherit (config.xdg) configHome; @@ -26,7 +27,7 @@ in { programs.mise = { enable = true; # On macOS manage mise by homebrew - more frequent updates - package = lib._.brew-alias "mise"; + package = lib.brew-alias pkgs "mise"; globalConfig = { tools = { bun = "latest"; diff --git a/modules/server/dns/default.nix b/modules/server/dns/default.nix index dea919d..fbff622 100644 --- a/modules/server/dns/default.nix +++ b/modules/server/dns/default.nix @@ -3,7 +3,7 @@ # # Usage: # -# imports = lib._.moduleImports ["server/dns"] +# imports = lib.moduleImports ["server/dns"] # server.dns.zones."jakubarbet.me" = ./jakubarbet.me.zone; { config,