mirror of
				https://github.com/RGBCube/hjem
				synced 2025-10-31 13:42:44 +00:00 
			
		
		
		
	 0e3eb7d2fd
			
		
	
	
		0e3eb7d2fd
		
			
		
	
	
	
	
		
			
			Drops excessve reliance on Nixpkgs modules inside the module options, and prepares for further platform support.
		
			
				
	
	
		
			112 lines
		
	
	
	
		
			3.2 KiB
		
	
	
	
		
			Nix
		
	
	
	
	
	
			
		
		
	
	
			112 lines
		
	
	
	
		
			3.2 KiB
		
	
	
	
		
			Nix
		
	
	
	
	
	
| {
 | |
|   config,
 | |
|   pkgs,
 | |
|   lib,
 | |
|   ...
 | |
| }: let
 | |
|   inherit (lib.modules) mkIf mkMerge;
 | |
|   inherit (lib.options) mkOption;
 | |
|   inherit (lib.lists) filter map flatten concatLists;
 | |
|   inherit (lib.attrsets) filterAttrs mapAttrs' attrValues mapAttrsToList;
 | |
|   inherit (lib.trivial) flip;
 | |
|   inherit (lib.types) bool attrsOf submoduleWith listOf raw;
 | |
| 
 | |
|   hjemModule = submoduleWith {
 | |
|     description = "Hjem NixOS module";
 | |
|     class = "hjem";
 | |
|     specialArgs = {inherit pkgs lib;};
 | |
|     modules = concatLists [
 | |
|       [
 | |
|         ({name, ...}: {
 | |
|           imports = [../common.nix];
 | |
| 
 | |
|           config = {
 | |
|             user = config.users.users.${name}.name;
 | |
|             directory = config.users.users.${name}.home;
 | |
|           };
 | |
|         })
 | |
|       ]
 | |
| 
 | |
|       # Evaluate additional modules under 'hjem.users.<name>' so that
 | |
|       # module systems built on Hjem are more ergonomic.
 | |
|       cfg.extraModules
 | |
|     ];
 | |
|   };
 | |
| 
 | |
|   cfg = config.hjem;
 | |
| in {
 | |
|   imports = [
 | |
|     # This should be removed in the future, since 'homes' is a very vague
 | |
|     # namespace to occupy. Added 2024-12-27, remove 2025-01-27 to allow
 | |
|     # sufficient time to migrate.
 | |
|     (lib.mkRenamedOptionModule ["homes"] ["hjem" "users"])
 | |
|   ];
 | |
| 
 | |
|   options.hjem = {
 | |
|     clobberByDefault = mkOption {
 | |
|       type = bool;
 | |
|       default = false;
 | |
|       description = ''
 | |
|         The default override behaviour for files managed by Hjem.
 | |
| 
 | |
|         While `true`, existing files will be overriden with new
 | |
|         files on rebuild.
 | |
|       '';
 | |
|     };
 | |
| 
 | |
|     users = mkOption {
 | |
|       default = {};
 | |
|       type = attrsOf hjemModule;
 | |
|       description = "Home configurations to be managed";
 | |
|     };
 | |
| 
 | |
|     extraModules = mkOption {
 | |
|       type = listOf raw;
 | |
|       default = [];
 | |
|       description = ''
 | |
|         Additional modules to be evaluated as a part of the users module
 | |
|         inside {option}`config.hjem.users.<name>`. This can be used to
 | |
|         extend each user configuration with additional options.
 | |
|       '';
 | |
|     };
 | |
|   };
 | |
| 
 | |
|   config = mkMerge [
 | |
|     {
 | |
|       users.users = mapAttrs' (name: {packages, ...}: {
 | |
|         inherit name;
 | |
|         value.packages = packages;
 | |
|       }) (filterAttrs (_: u: u.packages != []) cfg.users);
 | |
| 
 | |
|       systemd.user.tmpfiles.users = mapAttrs' (name: {files, ...}: {
 | |
|         inherit name;
 | |
|         value.rules = map (
 | |
|           file: let
 | |
|             # L+ will recreate, i.e., clobber existing files.
 | |
|             mode =
 | |
|               if file.clobber
 | |
|               then "L+"
 | |
|               else "L";
 | |
|           in
 | |
|             # Constructed rule string that consists of the type, target, and source
 | |
|             # of a tmpfile. Files with 'null' sources are filtered before the rule
 | |
|             # is constructed.
 | |
|             "${mode} '${file.target}' - - - - ${file.source}"
 | |
|         ) (filter (f: f.enable && f.source != null) (attrValues files));
 | |
|       }) (filterAttrs (_: u: u.files != {}) cfg.users);
 | |
|     }
 | |
| 
 | |
|     (mkIf (cfg.users != {}) {
 | |
|       warnings = flatten (flip mapAttrsToList cfg.users (user: config:
 | |
|         flip map config.warnings (
 | |
|           warning: "${user} profile: ${warning}"
 | |
|         )));
 | |
| 
 | |
|       assertions = flatten (flip mapAttrsToList cfg.users (user: config:
 | |
|         flip map config.assertions (assertion: {
 | |
|           inherit (assertion) assertion;
 | |
|           message = "${user} profile: ${assertion.message}";
 | |
|         })));
 | |
|     })
 | |
|   ];
 | |
| }
 |