From 03f51384cf09363aa6321b36c21d5da47517dcde Mon Sep 17 00:00:00 2001 From: Gabriel Arazas Date: Wed, 21 Aug 2024 18:51:57 +0800 Subject: [PATCH] nixos/programs/gnome-session: add top-level `systemd` namespace for systemd-specific options Also included a little refactor. --- .../nixos/programs/gnome-session/default.nix | 18 +- .../submodules/component-type.nix | 201 +++++++++--------- .../gnome-session/submodules/session-type.nix | 68 +++--- 3 files changed, 150 insertions(+), 137 deletions(-) diff --git a/modules/nixos/programs/gnome-session/default.nix b/modules/nixos/programs/gnome-session/default.nix index 21080ef1..9159f10f 100644 --- a/modules/nixos/programs/gnome-session/default.nix +++ b/modules/nixos/programs/gnome-session/default.nix @@ -107,20 +107,20 @@ let pathToUnit serviceToUnit targetToUnit timerToUnit socketToUnit; mkSystemdUnits = name: component: { - "${component.id}.service" = serviceToUnit component.serviceUnit; - "${component.id}.target" = targetToUnit component.targetUnit; - } // lib.optionalAttrs (component.socketUnit != null) { - "${component.id}.socket" = socketToUnit component.socketUnit; - } // lib.optionalAttrs (component.timerUnit != null) { - "${component.id}.timer" = timerToUnit component.timerUnit; - } // lib.optionalAttrs (component.pathUnit != null) { - "${component.id}.path" = pathToUnit component.pathUnit; + "${component.id}.service" = serviceToUnit component.systemd.serviceUnit; + "${component.id}.target" = targetToUnit component.systemd.targetUnit; + } // lib.optionalAttrs (component.systemd.socketUnit != null) { + "${component.id}.socket" = socketToUnit component.systemd.socketUnit; + } // lib.optionalAttrs (component.systemd.timerUnit != null) { + "${component.id}.timer" = timerToUnit component.systemd.timerUnit; + } // lib.optionalAttrs (component.systemd.pathUnit != null) { + "${component.id}.path" = pathToUnit component.systemd.pathUnit; }; componentsUnits = lib.concatMapAttrs mkSystemdUnits session.components; in componentsUnits // { - "gnome-session@${session.name}.target" = targetToUnit session.targetUnit; + "gnome-session@${session.name}.target" = targetToUnit session.systemd.targetUnit; } ) cfg.sessions; diff --git a/modules/nixos/programs/gnome-session/submodules/component-type.nix b/modules/nixos/programs/gnome-session/submodules/component-type.nix index a5342482..dd5dbbc5 100644 --- a/modules/nixos/programs/gnome-session/submodules/component-type.nix +++ b/modules/nixos/programs/gnome-session/submodules/component-type.nix @@ -1,10 +1,13 @@ { name, config, pkgs, lib, utils, session, ... }: let - optionalSystemdUnitOption = type: systemdModuleAttribute: + optionalSystemdUnitOption = { + unitType, systemdModuleAttribute, otherType, + }: lib.mkOption { + type = lib.types.nullOr otherType; description = '' - An optional systemd ${type} configuration to be generated. This should + An optional systemd ${unitType} configuration to be generated. This should be configured if the session is managed by systemd. :::{.note} @@ -73,106 +76,114 @@ in }; }; - # Most of the systemd config types are trying to eliminate as much of the - # NixOS systemd extensions as much as possible. For more details, see - # `config` attribute of the `sessionType`. - serviceUnit = lib.mkOption { - type = - let - inherit (utils.systemdUtils.lib) unitConfig serviceConfig; - inherit (utils.systemdUtils.unitOptions) commonUnitOptions serviceOptions; - in - lib.types.submodule [ - commonUnitOptions - serviceOptions - serviceConfig - unitConfig - ]; - description = '' - systemd service configuration to be generated. This should be - configured if the session is managed by systemd. + systemd = { + # Most of the systemd config types are trying to eliminate as much of the + # NixOS systemd extensions as much as possible. For more details, see + # `config` attribute of the `sessionType`. + serviceUnit = lib.mkOption { + type = + let + inherit (utils.systemdUtils.lib) unitConfig serviceConfig; + inherit (utils.systemdUtils.unitOptions) commonUnitOptions serviceOptions; + in + lib.types.submodule [ + commonUnitOptions + serviceOptions + serviceConfig + unitConfig + ]; + description = '' + systemd service configuration to be generated. This should be + configured if the session is managed by systemd. - :::{.note} - This has the same options as {option}`systemd.user.services.` - but without certain options from stage 2 counterparts such as - `reloadTriggers` and `restartTriggers`. + :::{.note} + This has the same options as {option}`systemd.user.services.` + but without certain options from stage 2 counterparts such as + `reloadTriggers` and `restartTriggers`. - By default, this module sets the service unit as part of the respective - target unit (i.e., `PartOf=$COMPONENTID.target`). + By default, this module sets the service unit as part of the respective + target unit (i.e., `PartOf=$COMPONENTID.target`). - On a typical case, you shouldn't mess with much of the dependency - ordering of the service unit. You should configure `targetUnit` for - that instead. - ::: - ''; - default = { }; - visible = "shallow"; - }; + On a typical case, you shouldn't mess with much of the dependency + ordering of the service unit. You should configure `targetUnit` for + that instead. + ::: + ''; + default = { }; + visible = "shallow"; + }; - targetUnit = lib.mkOption { - type = - let - inherit (utils.systemdUtils.lib) unitConfig; - inherit (utils.systemdUtils.unitOptions) commonUnitOptions; - in - lib.types.submodule [ - commonUnitOptions - unitConfig - ]; - description = '' - systemd target configuration to be generated. This should be - configured if the session is managed by systemd. + targetUnit = lib.mkOption { + type = + let + inherit (utils.systemdUtils.lib) unitConfig; + inherit (utils.systemdUtils.unitOptions) commonUnitOptions; + in + lib.types.submodule [ + commonUnitOptions + unitConfig + ]; + description = '' + systemd target configuration to be generated. This should be + configured if the session is managed by systemd. - :::{.note} - This has the same options as {option}`systemd.user.targets.` - but without certain options from stage 2 counterparts such as - `reloadTriggers` and `restartTriggers`. + :::{.note} + This has the same options as {option}`systemd.user.targets.` + but without certain options from stage 2 counterparts such as + `reloadTriggers` and `restartTriggers`. - This module doesn't set the typical dependency ordering relative to - gnome-session targets. This is on the user to manually set them. - ::: - ''; - default = { }; - visible = "shallow"; - }; + This module doesn't set the typical dependency ordering relative to + gnome-session targets. This is on the user to manually set them. + ::: + ''; + default = { }; + visible = "shallow"; + }; - timerUnit = optionalSystemdUnitOption "timer" "timers" // { - type = - let - inherit (utils.systemdUtils.unitOptions) timerOptions commonUnitOptions; - inherit (utils.systemdUtils.lib) unitConfig; - in - with lib.types; nullOr (submodule [ - commonUnitOptions - timerOptions - unitConfig - ]); - }; + timerUnit = optionalSystemdUnitOption { + unitType = "timer"; + systemdModuleAttribute = "timers"; + otherType = + let + inherit (utils.systemdUtils.unitOptions) timerOptions commonUnitOptions; + inherit (utils.systemdUtils.lib) unitConfig; + in + lib.types.submodule [ + commonUnitOptions + timerOptions + unitConfig + ]; + }; - socketUnit = optionalSystemdUnitOption "socket" "sockets" // { - type = - let - inherit (utils.systemdUtils.unitOptions) socketOptions commonUnitOptions; - inherit (utils.systemdUtils.lib) unitConfig; - in - with lib.types; nullOr (submodule [ - commonUnitOptions - socketOptions - unitConfig - ]); - }; + socketUnit = optionalSystemdUnitOption { + unitType = "socket"; + systemdModuleAttribute = "sockets"; + otherType = + let + inherit (utils.systemdUtils.unitOptions) socketOptions commonUnitOptions; + inherit (utils.systemdUtils.lib) unitConfig; + in + lib.types.submodule [ + commonUnitOptions + socketOptions + unitConfig + ]; + }; - pathUnit = optionalSystemdUnitOption "path" "paths" // { - type = - let - inherit (utils.systemdUtils.unitOptions) pathOptions commonUnitOptions; - inherit (utils.systemdUtils.lib) unitConfig; - in - with lib.types; nullOr (submodule [ - commonUnitOptions - pathOptions - unitConfig - ]); + pathUnit = optionalSystemdUnitOption { + unitType = "path"; + systemdModuleAttribute = "paths"; + otherType = + let + inherit (utils.systemdUtils.unitOptions) pathOptions commonUnitOptions; + inherit (utils.systemdUtils.lib) unitConfig; + in + lib.types.submodule [ + commonUnitOptions + pathOptions + unitConfig + ]; + }; }; id = lib.mkOption { @@ -235,7 +246,7 @@ in systemd user unit, much of them are unnecessary and rarely needed (if ever like `Service.PrivateTmp=`?) so we didn't set such defaults here. */ - serviceUnit = { + systemd.serviceUnit = { script = lib.mkAfter config.script; description = lib.mkDefault config.description; @@ -282,7 +293,7 @@ in likely for a user to design their own desktop session with full control so it would be better for these options to be empty for less confusion. */ - targetUnit = { + systemd.targetUnit = { # This should be the dependency-related directive to be configured. The # rest is for the user to judge. wants = [ "${config.id}.service" ]; diff --git a/modules/nixos/programs/gnome-session/submodules/session-type.nix b/modules/nixos/programs/gnome-session/submodules/session-type.nix index 1f90817c..93a85e24 100644 --- a/modules/nixos/programs/gnome-session/submodules/session-type.nix +++ b/modules/nixos/programs/gnome-session/submodules/session-type.nix @@ -184,40 +184,42 @@ in ]; }; - targetUnit = lib.mkOption { - type = - let - inherit (utils.systemdUtils.lib) unitConfig; - inherit (utils.systemdUtils.unitOptions) commonUnitOptions; - in - lib.types.submodule [ - commonUnitOptions - unitConfig - ]; - description = '' - systemd target configuration to be generated for - `gnome-session@.target`. This should be configured if the - session is managed by systemd and you want to control the session - further (which is recommended since this module don't know what - components are more important, etc.). + systemd = { + targetUnit = lib.mkOption { + type = + let + inherit (utils.systemdUtils.lib) unitConfig; + inherit (utils.systemdUtils.unitOptions) commonUnitOptions; + in + lib.types.submodule [ + commonUnitOptions + unitConfig + ]; + description = '' + systemd target configuration to be generated for + `gnome-session@.target`. This should be configured if the + session is managed by systemd and you want to control the session + further (which is recommended since this module don't know what + components are more important, etc.). - By default, the session target will have all of its components from - {option}`.requiredComponents` under `Wants=` directive. It - also assumes all of them have a target unit at - `''${requiredComponent}.target`. + By default, the session target will have all of its components from + {option}`.requiredComponents` under `Wants=` directive. It + also assumes all of them have a target unit at + `''${requiredComponent}.target`. - :::{.note} - This has the same options as {option}`systemd.user.targets.` - but without certain options from stage 2 counterparts such as - `reloadTriggers` and `restartTriggers`. - ::: - ''; - visible = "shallow"; - defaultText = '' - { - wants = ... # All of the required components as a target unit. - } - ''; + :::{.note} + This has the same options as {option}`systemd.user.targets.` + but without certain options from stage 2 counterparts such as + `reloadTriggers` and `restartTriggers`. + ::: + ''; + visible = "shallow"; + defaultText = '' + { + wants = ... # All of the required components as a target unit. + } + ''; + }; }; }; @@ -225,7 +227,7 @@ in # Append the session argument. extraArgs = [ "--session=${name}" ]; - targetUnit = { + systemd.targetUnit = { overrideStrategy = lib.mkForce "asDropin"; wants = lib.mkDefault (builtins.map (c: "${c}.target") config.requiredComponents); };