summaryrefslogtreecommitdiffstats
path: root/krebs/3modules
diff options
context:
space:
mode:
Diffstat (limited to 'krebs/3modules')
-rw-r--r--krebs/3modules/backup.nix8
-rw-r--r--krebs/3modules/brockman.nix1
-rw-r--r--krebs/3modules/default.nix1
-rw-r--r--krebs/3modules/external/mic92.nix66
-rw-r--r--krebs/3modules/htgen.nix7
-rw-r--r--krebs/3modules/repo-sync.nix2
-rw-r--r--krebs/3modules/setuid.nix29
-rw-r--r--krebs/3modules/shadow.nix8
-rw-r--r--krebs/3modules/tv/default.nix25
-rw-r--r--krebs/3modules/upstream/default.nix10
-rw-r--r--krebs/3modules/upstream/desktop-managers/coma.nix21
-rw-r--r--krebs/3modules/upstream/desktop-managers/default.nix6
-rw-r--r--krebs/3modules/upstream/desktop-managers/none.nix11
-rw-r--r--krebs/3modules/upstream/window-managers/default.nix22
-rw-r--r--krebs/3modules/upstream/window-managers/xmonad.nix189
15 files changed, 385 insertions, 21 deletions
diff --git a/krebs/3modules/backup.nix b/krebs/3modules/backup.nix
index c0b218c15..910324f3c 100644
--- a/krebs/3modules/backup.nix
+++ b/krebs/3modules/backup.nix
@@ -226,10 +226,14 @@ let
# XXX Is one ping enough to determine fastest address?
fastest-address = host: ''
- { ${pkgs.fping}/bin/fping </dev/null -a \
+ { ${pkgs.fping}/bin/fping </dev/null -a -e \
${concatMapStringsSep " " shell.escape
(mapAttrsToList (_: net: head net.aliases) host.nets)} \
- | ${pkgs.coreutils}/bin/head -1; }
+ | ${pkgs.gnused}/bin/sed -r 's/^(\S+) \(([0-9.]+) ms\)$/\2\t\1/' \
+ | ${pkgs.coreutils}/bin/sort -n \
+ | ${pkgs.coreutils}/bin/cut -f2 \
+ | ${pkgs.coreutils}/bin/head -n 1
+ }
'';
in out
diff --git a/krebs/3modules/brockman.nix b/krebs/3modules/brockman.nix
index 32aa3489b..9b2ed4a71 100644
--- a/krebs/3modules/brockman.nix
+++ b/krebs/3modules/brockman.nix
@@ -29,6 +29,7 @@ in {
PrivateTmp = true;
RuntimeDirectory = "brockman";
WorkingDirectory = "%t/brockman";
+ RestartSec = 5;
};
};
};
diff --git a/krebs/3modules/default.nix b/krebs/3modules/default.nix
index e7d04ead8..85d27459b 100644
--- a/krebs/3modules/default.nix
+++ b/krebs/3modules/default.nix
@@ -55,6 +55,7 @@ let
./sync-containers.nix
./tinc.nix
./tinc_graphs.nix
+ ./upstream
./urlwatch.nix
./repo-sync.nix
./xresources.nix
diff --git a/krebs/3modules/external/mic92.nix b/krebs/3modules/external/mic92.nix
index 29d0b27fa..306ab34eb 100644
--- a/krebs/3modules/external/mic92.nix
+++ b/krebs/3modules/external/mic92.nix
@@ -97,6 +97,27 @@ in {
};
};
};
+ dimitriosxps = {
+ owner = config.krebs.users.mic92;
+ nets = {
+ retiolum = {
+ ip4.addr = "10.243.29.189";
+ aliases = [
+ "dimitriosxps.r"
+ ];
+ tinc.pubkey = ''
+ -----BEGIN RSA PUBLIC KEY-----
+ MIIBCgKCAQEAz9aKIhzk8+ZNBQmU054yc1yTdMyaw1aqWXYyQZoCmFaBIlMvF8I0
+ dd+56cGjK8O7KkEhheDL/ijj9cCcxbqHSTktXz47ScyTaN63h13+MBUIUzDwSO4E
+ 9fRUUn3lbZenhGoON7hlaHb/qAR0yLxip0Tw77bcq4hvKleD74NnAJILPoP1KRDY
+ O5vs8C8wpdJUtnlsfkAa058wDI+7GNPb0cs0/pBQVR2GUGb1xqVJ5obO/lFKOJ/e
+ DKemnlg736cEaIF6v9M+w4VmL8mNudDy6RxA6/xIErP5Ru2aK5lH5UBHVCwdLLCy
+ 8y3It9Tgji3G9nOFbhaeKDjeIAJ8sG+WjQIDAQAB
+ -----END RSA PUBLIC KEY-----
+ '';
+ };
+ };
+ };
donna = {
owner = config.krebs.users.mic92;
nets = rec {
@@ -453,6 +474,51 @@ in {
};
};
};
+
+ redha = {
+ owner = config.krebs.users.mic92;
+ nets = {
+ retiolum = {
+ ip4.addr = "10.243.29.188";
+ aliases = [
+ "redha.r"
+ ];
+ tinc.pubkey = ''
+ -----BEGIN RSA PUBLIC KEY-----
+ MIIBCgKCAQEAx7STxTTPMxXugweHpUGOeLUrrTSCt7j5l+fjNtArIygOGKEiAC5O
+ s0G4WHK2IcrNnv7pxS09S5mnXywi51aAL+G2fKzcU3YgLFuoUN4Kk5LohMvBynEE
+ a3kZK2/D+LMeFfpK2RWBPjLnulN29ke11Iot42TC6+NIMWiZh/Y2T0mKirUJQGsH
+ RV3zRlR7YfIOdR1AZ5S+qrmPF8hLb7O08TTXrHo8NQk5NAVUS89OYcn1pc9hnf/e
+ FK5qRrQFMRFB8KGV+n3+cx3XCM2q0ZPTNf06N+Usx6vTKLASa/4GaTcbBx+9Dndm
+ mFVWq9JjLa8e65tojzj8PhmgxqaNCf8aKwIDAQAB
+ -----END RSA PUBLIC KEY-----
+ '';
+ };
+ };
+ };
+
+ grandalf = {
+ owner = config.krebs.users.mic92;
+ nets = {
+ retiolum = {
+ ip4.addr = "10.243.29.187";
+ aliases = [
+ "grandalf.r"
+ ];
+ tinc.pubkey = ''
+ -----BEGIN RSA PUBLIC KEY-----
+ MIIBCgKCAQEAn1wLOI8DluJAKvscyImoyG0gjxyVC1/Ky8A63YO7INy0SYBg3wU7
+ XPSbix5VJZdADQ382LWg31ORYjnDg40c49gCGLfR6+awgd+Rb0sb4eAz07XENXJC
+ qc70oQrrXLi8HIfeckCsJHe514LJOMA3pU+muaMShOiSygoTiTlEH6RRrkC8HROL
+ 2/V7Hm2Sg7YS+MY8bI/x61MIagfkQKH2eFyqGG54Y80bIhm5SohMkiANu78GdngI
+ jb+EGlT/vq3+oGNFJ7Shy/VsR5GLDoZ5KCsT45DM87lOjGB7m+bOdizZQtWmJtC/
+ /btEPWJPAD9lIY2iGtPrmeMWDNTW9c0iCwIDAQAB
+ -----END RSA PUBLIC KEY-----
+ '';
+ };
+ };
+ };
+
eva = {
owner = config.krebs.users.mic92;
nets = rec {
diff --git a/krebs/3modules/htgen.nix b/krebs/3modules/htgen.nix
index 0dddca6c8..70c4fcd2b 100644
--- a/krebs/3modules/htgen.nix
+++ b/krebs/3modules/htgen.nix
@@ -20,6 +20,11 @@ let
default = config._module.args.name;
};
+ package = mkOption {
+ default = pkgs.htgen;
+ type = types.package;
+ };
+
port = mkOption {
type = types.uint;
};
@@ -52,7 +57,7 @@ let
User = htgen.user.name;
PrivateTmp = true;
Restart = "always";
- ExecStart = "${pkgs.htgen}/bin/htgen --serve";
+ ExecStart = "${htgen.package}/bin/htgen --serve";
};
}
) cfg;
diff --git a/krebs/3modules/repo-sync.nix b/krebs/3modules/repo-sync.nix
index 91111f3eb..f9877c0f8 100644
--- a/krebs/3modules/repo-sync.nix
+++ b/krebs/3modules/repo-sync.nix
@@ -176,7 +176,7 @@ let
];
environment = {
- GIT_SSH_COMMAND = "${pkgs.openssh}/bin/ssh -i ${cfg.stateDir}/ssh.priv";
+ GIT_SSH_COMMAND = "${pkgs.openssh}/bin/ssh -i ${cfg.privateKeyFile.path}";
REPONAME = "${name}.git";
};
diff --git a/krebs/3modules/setuid.nix b/krebs/3modules/setuid.nix
index 97cf21cdd..64fedb911 100644
--- a/krebs/3modules/setuid.nix
+++ b/krebs/3modules/setuid.nix
@@ -1,24 +1,20 @@
-{ config, pkgs, lib, ... }:
with import <stockholm/lib>;
-let
- cfg = config.krebs.setuid;
+{ config, pkgs, ... }: let
out = {
options.krebs.setuid = api;
- config = mkIf (cfg != {}) imp;
+ config = mkIf (config.krebs.setuid != {}) imp;
};
api = mkOption {
default = {};
type = let
- # TODO make wrapperDir configurable
- inherit (config.security) wrapperDir;
inherit (config.users) groups users;
- in types.attrsOf (types.submodule ({ config, ... }: {
+ in types.attrsOf (types.submodule (self: let cfg = self.config; in {
options = {
name = mkOption {
type = types.filename;
- default = config._module.args.name;
+ default = cfg._module.args.name;
};
envp = mkOption {
type = types.nullOr (types.attrsOf types.str);
@@ -51,6 +47,10 @@ let
merge = mergeOneOption;
};
};
+ wrapperDir = mkOption {
+ default = config.security.wrapperDir;
+ type = types.absolute-pathname;
+ };
activate = mkOption {
type = types.str;
visible = false;
@@ -58,21 +58,22 @@ let
};
};
config.activate = let
- src = pkgs.exec config.name {
- inherit (config) envp filename;
+ src = pkgs.exec cfg.name {
+ inherit (cfg) envp filename;
};
- dst = "${wrapperDir}/${config.name}";
+ dst = "${cfg.wrapperDir}/${cfg.name}";
in ''
+ mkdir -p ${cfg.wrapperDir}
cp ${src} ${dst}
- chown ${config.owner}.${config.group} ${dst}
- chmod ${config.mode} ${dst}
+ chown ${cfg.owner}.${cfg.group} ${dst}
+ chmod ${cfg.mode} ${dst}
'';
}));
};
imp = {
system.activationScripts."krebs.setuid" = stringAfter [ "wrappers" ]
- (concatMapStringsSep "\n" (getAttr "activate") (attrValues cfg));
+ (concatMapStringsSep "\n" (getAttr "activate") (attrValues config.krebs.setuid));
};
in out
diff --git a/krebs/3modules/shadow.nix b/krebs/3modules/shadow.nix
index cff66492d..9505efb0c 100644
--- a/krebs/3modules/shadow.nix
+++ b/krebs/3modules/shadow.nix
@@ -4,19 +4,21 @@ with import <stockholm/lib>;
cfg = config.krebs.shadow;
mergeShadowsJq = pkgs.writeJq "merge-shadows.jq" ''
- def fields_3_to_9: ["1", "", "", "", "", "", ""];
+ def is_int: . == (. | floor);
+ def fields_4_to_9: ["", "", "", "", "", ""];
+ def check_fields_3_to_9: (.[2] | tonumber | is_int) and .[3:] == fields_4_to_9;
def read_value:
split(":") |
if length == 9 then
- if .[2:] == fields_3_to_9 then
+ if check_fields_3_to_9 then
.
else
error("unrecognized field contents")
end
elif length == 2 then
if .[1] | test("^\\$6\\$") then
- . + fields_3_to_9
+ . + ["1"] + fields_4_to_9
else
error("unrecognized hashed password")
end
diff --git a/krebs/3modules/tv/default.nix b/krebs/3modules/tv/default.nix
index 6a09cc834..92f1a5bcd 100644
--- a/krebs/3modules/tv/default.nix
+++ b/krebs/3modules/tv/default.nix
@@ -82,6 +82,31 @@ in {
ssh.privkey.path = config.krebs.secret.file "ssh.id_ed25519";
ssh.pubkey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIBsqDuhGJpjpqNv4QmjoOhcODObrPyY3GHLvtVkgXV0g root@au";
};
+ hu = {
+ nets = {
+ retiolum = {
+ ip4.addr = "10.243.13.41";
+ aliases = [
+ "hu.r"
+ ];
+ tinc.pubkey = ''
+ -----BEGIN RSA PUBLIC KEY-----
+ MIIBCgKCAQEAwj5T9Rejp8zGVrHjqA+OeMvcVpax4VazssnRPSUznUEOdVEeSJL5
+ 8gDBJPtIfxF8iunXr5K7CW036tKvYaGMDwYMOPJZXhFCmU2yUF2g4BcqEhuDdIfO
+ +D2Pfr4lc9xO90SKOgwJ53qhf5yqeU/WQ3dpCF/n8k4SUmdafTsvh00UrxYpHuTU
+ C22BRXIKR4r/sCJUitWQSWNdSQUxh3lu7sUPr+6sZyJov+eu8oBVlPgYOv6u9nZe
+ YhrbCPDKMGPfnQTAtWfHIxNt70Ec5AG6ddQzLeVcM2gP5qi957Fert+C2RNtbz5s
+ Brbw1bqZ3P+CGzvxVJZtirvR2f3HkidGPQIDAQAB
+ -----END RSA PUBLIC KEY-----
+ '';
+ tinc.pubkey_ed25519 =
+ "Ed25519PublicKey = PV8Dz9ni2cPXyJGiG5oU0XWdJkUPgrMzDuzHj7kpMzO";
+ };
+ };
+ secure = true;
+ ssh.privkey.path = config.krebs.secret.file "ssh.id_ed25519";
+ ssh.pubkey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIO+Rrf9tvuusYlnSZwUiHS4O+AhrpVZ/6n7peSRKojTc root@hu";
+ };
mu = {
ci = true;
cores = 2;
diff --git a/krebs/3modules/upstream/default.nix b/krebs/3modules/upstream/default.nix
new file mode 100644
index 000000000..ce7bd1644
--- /dev/null
+++ b/krebs/3modules/upstream/default.nix
@@ -0,0 +1,10 @@
+with import <stockholm/lib>;
+
+{
+ imports =
+ map
+ (name: ./. + "/${name}")
+ (filter
+ (name: name != "default.nix" && !hasPrefix "." name)
+ (attrNames (readDir ./.)));
+}
diff --git a/krebs/3modules/upstream/desktop-managers/coma.nix b/krebs/3modules/upstream/desktop-managers/coma.nix
new file mode 100644
index 000000000..95db7fb5c
--- /dev/null
+++ b/krebs/3modules/upstream/desktop-managers/coma.nix
@@ -0,0 +1,21 @@
+with import <stockholm/lib>;
+{ config, pkgs, ... }: {
+ options = {
+ services.xserver.desktopManager.coma = {
+ enable = mkEnableOption "sleep as a desktop manager";
+ };
+ };
+ config = mkIf config.services.xserver.desktopManager.coma.enable {
+ services.xserver.desktopManager.session = singleton {
+ name = "coma";
+ bgSupport = true;
+ start = /* sh */ ''
+ if test -n "$waitPID"; then
+ ${pkgs.uutils-coreutils}/bin/uutils-sleep 1s && kill $waitPID &
+ wait $waitPID
+ fi
+ exec -a sleep ${pkgs.uutils-coreutils}/bin/uutils-sleep infinity
+ '';
+ };
+ };
+}
diff --git a/krebs/3modules/upstream/desktop-managers/default.nix b/krebs/3modules/upstream/desktop-managers/default.nix
new file mode 100644
index 000000000..22e75439d
--- /dev/null
+++ b/krebs/3modules/upstream/desktop-managers/default.nix
@@ -0,0 +1,6 @@
+{
+ imports = [
+ ./coma.nix
+ ./none.nix
+ ];
+}
diff --git a/krebs/3modules/upstream/desktop-managers/none.nix b/krebs/3modules/upstream/desktop-managers/none.nix
new file mode 100644
index 000000000..892def985
--- /dev/null
+++ b/krebs/3modules/upstream/desktop-managers/none.nix
@@ -0,0 +1,11 @@
+# Replace upstream none desktop-manager by a real none, that doesn't pull in
+# any dependencies.
+with import <stockholm/lib>;
+{
+ disabledModules = singleton "services/x11/desktop-managers/none.nix";
+ config.services.xserver.desktopManager.session = singleton {
+ name = "none";
+ bgSupport = true;
+ start = "";
+ };
+}
diff --git a/krebs/3modules/upstream/window-managers/default.nix b/krebs/3modules/upstream/window-managers/default.nix
new file mode 100644
index 000000000..eecadca7e
--- /dev/null
+++ b/krebs/3modules/upstream/window-managers/default.nix
@@ -0,0 +1,22 @@
+{
+ imports = [
+ # Replace upstream xmonad module with one that will be reloaded if changed.
+ #
+ # This module is intended to be upstreamed once fully tested.
+ # The patch to be committed can be obtained using:
+ #
+ # diff -u <nixpkgs/nixos/modules/services/x11/window-managers/xmonad.nix> \
+ # <stockholm/tv/3modules/window-managers/xmonad.nix>
+ #
+ {
+ disabledModules = [ "services/x11/window-managers/xmonad.nix" ];
+ imports = [ ./xmonad.nix ];
+ nixpkgs.overlays = [(self: super: {
+ writers = super.writers // {
+ writeHaskellBin = name: spec: with import <stockholm/lib>;
+ super.writers.writeHaskellBin name (removeAttrs spec ["ghcArgs"]);
+ };
+ })];
+ }
+ ];
+}
diff --git a/krebs/3modules/upstream/window-managers/xmonad.nix b/krebs/3modules/upstream/window-managers/xmonad.nix
new file mode 100644
index 000000000..356fa46bf
--- /dev/null
+++ b/krebs/3modules/upstream/window-managers/xmonad.nix
@@ -0,0 +1,189 @@
+{pkgs, lib, config, ...}:
+
+with lib;
+let
+ inherit (lib) mkOption mkIf optionals literalExample;
+ cfg = config.services.xserver.windowManager.xmonad;
+
+ ghcWithPackages = cfg.haskellPackages.ghcWithPackages;
+ packages = self: cfg.extraPackages self ++
+ optionals cfg.enableContribAndExtras
+ [ self.xmonad-contrib self.xmonad-extras ];
+
+ xmonad-vanilla = pkgs.xmonad-with-packages.override {
+ inherit ghcWithPackages packages;
+ };
+
+ xmonad-config =
+ let
+ xmonadAndPackages = self: [ self.xmonad ] ++ packages self;
+ xmonadEnv = ghcWithPackages xmonadAndPackages;
+ configured = pkgs.writers.writeHaskellBin "xmonad" {
+ ghc = cfg.haskellPackages.ghc;
+ libraries = xmonadAndPackages cfg.haskellPackages;
+ inherit (cfg) ghcArgs;
+ } cfg.config;
+ in
+ pkgs.runCommandLocal "xmonad" {
+ nativeBuildInputs = [ pkgs.makeWrapper ];
+ } ''
+ install -D ${xmonadEnv}/share/man/man1/xmonad.1.gz $out/share/man/man1/xmonad.1.gz
+ makeWrapper ${configured}/bin/xmonad $out/bin/xmonad \
+ --set NIX_GHC "${xmonadEnv}/bin/ghc" \
+ --set XMONAD_XMESSAGE "${pkgs.xorg.xmessage}/bin/xmessage"
+ '';
+
+ xmonad = if (cfg.config != null) then xmonad-config else xmonad-vanilla;
+in {
+ meta.maintainers = with maintainers; [ lassulus xaverdh ivanbrennan ];
+
+ options = {
+ services.xserver.windowManager.xmonad = {
+ enable = mkEnableOption "xmonad";
+ haskellPackages = mkOption {
+ default = pkgs.haskellPackages;
+ defaultText = "pkgs.haskellPackages";
+ example = literalExample "pkgs.haskell.packages.ghc784";
+ description = ''
+ haskellPackages used to build Xmonad and other packages.
+ This can be used to change the GHC version used to build
+ Xmonad and the packages listed in
+ <varname>extraPackages</varname>.
+ '';
+ };
+
+ extraPackages = mkOption {
+ default = self: [];
+ defaultText = "self: []";
+ example = literalExample ''
+ haskellPackages: [
+ haskellPackages.xmonad-contrib
+ haskellPackages.monad-logger
+ ]
+ '';
+ description = ''
+ Extra packages available to ghc when rebuilding Xmonad. The
+ value must be a function which receives the attrset defined
+ in <varname>haskellPackages</varname> as the sole argument.
+ '';
+ };
+
+ enableContribAndExtras = mkOption {
+ default = false;
+ type = lib.types.bool;
+ description = "Enable xmonad-{contrib,extras} in Xmonad.";
+ };
+
+ config = mkOption {
+ default = null;
+ type = with lib.types; nullOr (either path str);
+ description = ''
+ Configuration from which XMonad gets compiled. If no value is
+ specified, a vanilla xmonad binary is put in PATH, which will
+ attempt to recompile and exec your xmonad config from $HOME/.xmonad.
+ This setup is then analogous to other (non-NixOS) linux distributions.
+
+ If you do set this option, you likely want to use "launch" as your
+ entry point for xmonad (as in the example), to avoid xmonad's
+ recompilation logic on startup. Doing so will render the default
+ "mod+q" restart key binding dysfunctional though, because that attempts
+ to call your binary with the "--restart" command line option, unless
+ you implement that yourself. You way mant to bind "mod+q" to
+ <literal>(restart "xmonad" True)</literal> instead, which will just restart
+ xmonad from PATH. This allows e.g. switching to the new xmonad binary
+ after rebuilding your system with nixos-rebuild.
+
+ If you actually want to run xmonad with a config specified here, but
+ also be able to recompile and restart it from a copy of that source in
+ $HOME/.xmonad on the fly, you will have to implement that yourself
+ using something like "compileRestart" from the example.
+ This should allow you to switch at will between the local xmonad and
+ the one NixOS puts in your PATH.
+ '';
+ example = ''
+ import XMonad
+ import XMonad.Util.EZConfig (additionalKeys)
+ import Control.Monad (when)
+ import Text.Printf (printf)
+ import System.Posix.Process (executeFile)
+ import System.Info (arch,os)
+ import System.Environment (getArgs)
+ import System.FilePath ((</>))
+
+ compiledConfig = printf "xmonad-%s-%s" arch os
+
+ compileRestart resume =
+ whenX (recompile True) $
+ when resume writeStateToFile
+ *> catchIO
+ ( do
+ dir <- getXMonadDataDir
+ args <- getArgs
+ executeFile (dir </> compiledConfig) False args Nothing
+ )
+
+ main = launch defaultConfig
+ { modMask = mod4Mask -- Use Super instead of Alt
+ , terminal = "urxvt" }
+ `additionalKeys`
+ [ ( (mod4Mask,xK_r), compileRestart True)
+ , ( (mod4Mask,xK_q), restart "xmonad" True ) ]
+ '';
+ };
+
+ xmonadCliArgs = mkOption {
+ default = [];
+ type = with lib.types; listOf str;
+ description = ''
+ Command line arguments passed to the xmonad binary.
+ '';
+ };
+
+ ghcArgs = mkOption {
+ default = [];
+ type = with lib.types; listOf str;
+ description = ''
+ Command line arguments passed to the compiler (ghc)
+ invocation when xmonad.config is set.
+ '';
+ };
+
+ };
+ };
+ config = mkIf cfg.enable {
+ services.xserver.windowManager = {
+ session = [{
+ name = "xmonad";
+ start = ''
+ systemctl --user start --wait xmonad.service &
+ waitPID=$!
+ '';
+ }];
+ };
+
+ system.userActivationScripts.xmonad-reload = /* sh */ ''
+ if ${pkgs.systemd}/bin/systemctl --user is-active --quiet xmonad.service; then
+ if [ "$(readlink -f "$XDG_RUNTIME_DIR"/xmonad/xmonad)" != ${xmonad}/bin/xmonad ]; then
+ ${pkgs.systemd}/bin/systemctl --user reload xmonad.service
+ fi
+ fi
+ '';
+
+ systemd.user.services.xmonad = {
+ requisite = [ "graphical-session.target" ];
+ after = [ "graphical-session.target" ];
+ environment.PATH = mkForce "%t/xmonad";
+ environment.XMONAD_DATA_DIR = "%t/xmonad";
+ serviceConfig = rec {
+ ExecStartPre = [
+ "${pkgs.coreutils}/bin/mkdir -p %t/xmonad"
+ "${pkgs.coreutils}/bin/ln -fns ${xmonad}/bin/xmonad %t/xmonad/xmonad"
+ ];
+ ExecStart = "%t/xmonad/xmonad ${lib.escapeShellArgs cfg.xmonadCliArgs}";
+ ExecReload = ExecStartPre ++ [ "${xmonad-vanilla}/bin/xmonad --restart" ];
+ };
+ };
+
+ environment.systemPackages = [ xmonad ];
+ };
+}