users/services: refactor: replace ExecStart/ExecStopPost with command/cleanupCommand

note that this completely breaks the systemd backend (though easily fixable if wanted)
This commit is contained in:
2024-03-21 15:05:23 +00:00
parent 5c9c7f8073
commit d2f6648bce
30 changed files with 90 additions and 102 deletions

View File

@@ -88,7 +88,7 @@ in
services.abaddon = {
description = "unofficial Discord chat client";
wantedBy = lib.mkIf cfg.config.autostart [ "graphical-session.target" ];
serviceConfig.ExecStart = "abaddon";
command = "abaddon";
};
};
}

View File

@@ -121,8 +121,8 @@ in
after = [ "graphical-session.target" ];
wantedBy = [ "graphical-session.target" ];
serviceConfig.ExecStart = "bonsaid -t ${cfg.config.configFile}";
serviceConfig.ExecStopPost = "rm -f $XDG_RUNTIME_DIR/bonsai";
command = "bonsaid -t ${cfg.config.configFile}";
cleanupCommand = "rm -f $XDG_RUNTIME_DIR/bonsai";
};
};
}

View File

@@ -46,7 +46,7 @@ in
description = "gnome-calls daemon to monitor incoming SIP calls";
wantedBy = lib.mkIf cfg.config.autostart [ "graphical-session.target" ];
# add --verbose for more debugging
serviceConfig.ExecStart = "env G_MESSAGES_DEBUG=all gnome-calls --daemon";
command = "env G_MESSAGES_DEBUG=all gnome-calls --daemon";
};
};
programs.calls = lib.mkIf cfg.enabled {

View File

@@ -1,4 +1,4 @@
{ config, pkgs, ... }:
{ pkgs, ... }:
{
sane.programs.conky = {
# TODO: non-sandboxed `conky` still ships via `sxmo-utils`, but unused
@@ -14,6 +14,7 @@
fs.".config/conky/conky.conf".symlink.target =
let
# TODO: make this just another `suggestedPrograms`!
battery_estimate = pkgs.static-nix-shell.mkBash {
pname = "battery_estimate";
srcRoot = ./.;
@@ -30,7 +31,7 @@
# partOf = [ "graphical-session.target" ]; # propagate stop/restart signal from graphical-session to this unit
wantedBy = [ "graphical-session.target" ];
serviceConfig.ExecStart = "${config.sane.programs.conky.package}/bin/conky";
command = "conky";
};
};
}

View File

@@ -36,8 +36,7 @@ in
description = "dconf configuration database/server";
after = [ "graphical-session.target" ];
wantedBy = [ "graphical-session.target" ];
serviceConfig.ExecStart = "${lib.getLib cfg.package}/libexec/dconf-service";
command = "${lib.getLib cfg.package}/libexec/dconf-service";
};
# supposedly necessary for packages which haven't been wrapped (i.e. wrapGtkApp?),

View File

@@ -80,7 +80,7 @@ in
#
# note that debug logging during calls produces so much journal spam that it pegs the CPU and causes dropped audio
# env G_MESSAGES_DEBUG = "all";
serviceConfig.ExecStart = "env PULSE_LATENCY_MSEC=20 dino";
command = "env PULSE_LATENCY_MSEC=20 dino";
};
};
}

View File

@@ -59,8 +59,7 @@ in
description = "dissent Discord client";
after = [ "graphical-session.target" ];
wantedBy = lib.mkIf cfg.config.autostart [ "graphical-session.target" ];
serviceConfig.ExecStart = "dissent";
command = "dissent";
};
};
}

View File

@@ -100,7 +100,7 @@
after = [ "graphical-session.target" ];
wantedBy = [ "graphical-session.target" ];
serviceConfig.ExecStart = "fcitx5";
command = "fcitx5";
};
env.XMODIFIERS = "@im=fcitx";

View File

@@ -97,7 +97,7 @@ in
services.feedbackd = {
description = "feedbackd audio/vibration/led controller";
wantedBy = [ "default.target" ]; #< should technically be `sound.target`, but that doesn't seem to get auto-started?
serviceConfig.ExecStart = lib.concatStringsSep " " ([
command = lib.concatStringsSep " " ([
"env"
"G_MESSAGES_DEBUG=all"
] ++ lib.optionals cfg.config.proxied [

View File

@@ -73,7 +73,7 @@ in
wantedBy = lib.mkIf cfg.config.autostart [ "graphical-session.target" ];
# env "G_MESSAGES_DEBUG=all"
serviceConfig.ExecStart = "fractal";
command = "fractal";
};
};
}

View File

@@ -90,8 +90,7 @@ in
after = [ "graphical-session.target" ];
# partOf = [ "graphical-session.target" ];
wantedBy = lib.mkIf cfg.config.autostart [ "graphical-session.target" ];
serviceConfig.ExecStart = "geary";
command = "geary";
};
};

View File

@@ -50,9 +50,9 @@
description = "gnome-keyring-daemon: secret provider";
after = [ "graphical-session.target" ];
wantedBy = [ "graphical-session.target" ];
serviceConfig.ExecStart = let
command = let
gkr-start = pkgs.writeShellScriptBin "gnome-keyring-daemon-start" ''
mkdir -m 0700 -p %t/keyring
mkdir -m 0700 -p $XDG_RUNTIME_DIR/keyring
exec gnome-keyring-daemon --start --foreground --components=secrets
'';
in "${gkr-start}/bin/gnome-keyring-daemon-start";

View File

@@ -54,8 +54,7 @@
services.mako = {
description = "mako desktop notification daemon";
wantedBy = [ "graphical-session.target" ];
serviceConfig.ExecStart = "${config.sane.programs.mako.package}/bin/mako";
command = "${config.sane.programs.mako.package}/bin/mako";
};
};
}

View File

@@ -28,7 +28,7 @@ in
services.ntfy-sub = {
description = "listen for push-notifications";
wantedBy = lib.mkIf cfg.config.autostart [ "default.target" ];
serviceConfig.ExecStart = let
command = let
sub = pkgs.writeShellScriptBin "ntfy-sub" ''
topic=$(cat ~/.config/ntfy-sh/topic)
exec ntfy sub "https://ntfy.uninsane.org:2587/$topic"

View File

@@ -32,39 +32,25 @@ in
description = "pipewire: multimedia service";
after = [ "graphical-session.target" ];
wantedBy = [ "graphical-session.target" ];
serviceConfig = {
# env PIPEWIRE_LOG_SYSTEMD=false"
# env PIPEWIRE_DEBUG"*:3,mod.raop*:5,pw.rtsp-client*:5"
ExecStart = "pipewire";
ExecStartPost = pkgs.writeShellScript "pipewire-wait-started" ''
waitFor() {
while [ ! -e "$1" ]; do
sleep 1
done
}
waitFor "$XDG_RUNTIME_DIR/pipewire-0"
waitFor "$XDG_RUNTIME_DIR/pipewire-0-manager"
'';
ExecStopPost = ''rm -f "$XDG_RUNTIME_DIR/{pipewire-0,pipewire-0.lock,pipewire-0-manager,pipewire-0-manager.lock}"'';
};
# env PIPEWIRE_LOG_SYSTEMD=false"
# env PIPEWIRE_DEBUG"*:3,mod.raop*:5,pw.rtsp-client*:5"
command = "pipewire";
pollReadyCommand = pkgs.writeShellScript "pipewire-wait-started" ''
[ -e "$XDG_RUNTIME_DIR/pipewire-0" ] && \
[ -e "$XDG_RUNTIME_DIR/pipewire-0-manager" ]
'';
cleanupCommand = ''rm -f "$XDG_RUNTIME_DIR/{pipewire-0,pipewire-0.lock,pipewire-0-manager,pipewire-0-manager.lock}"'';
};
services.pipewire-pulse = {
description = "pipewire-pulse: Pipewire compatibility layer for PulseAudio clients";
after = [ "pipewire.service" ];
wantedBy = [ "pipewire.service" ];
serviceConfig = {
ExecStart = "pipewire-pulse";
ExecStartPost = pkgs.writeShellScript "pipewire-pulse-wait-started" ''
waitFor() {
while [ ! -e "$1" ]; do
sleep 1
done
}
waitFor "$XDG_RUNTIME_DIR/pulse/native"
waitFor "$XDG_RUNTIME_DIR/pulse/pid"
'';
ExecStopPost = ''rm -f "$XDG_RUNTIME_DIR/pulse/{native,pid}"'';
};
command = "pipewire-pulse";
pollReadyCommand = pkgs.writeShellScript "pipewire-pulse-wait-started" ''
[ -e "$XDG_RUNTIME_DIR/pulse/native" ] && \
[ -e "$XDG_RUNTIME_DIR/pulse/pid" ]
'';
cleanupCommand = ''rm -f "$XDG_RUNTIME_DIR/pulse/{native,pid}"'';
};
};

View File

@@ -1,4 +1,4 @@
{ config, ... }:
{ ... }:
{
sane.programs.playerctl = {
sandbox.method = "bwrap";
@@ -9,7 +9,7 @@
description = "playerctl daemon to keep track of which MPRIS players were recently active";
documentation = [ "https://github.com/altdesktop/playerctl/issues/161" ];
wantedBy = [ "default.target" ]; #< TODO: maybe better to zero `wantedBy` here and have the specific consumers (e.g. swaync) explicitly depend on this.
serviceConfig.ExecStart = "${config.sane.programs.playerctl.package}/bin/playerctld";
command = "playerctld";
# serviceConfig.BusName = "org.mpris.MediaPlayer2.Player";
};
};

View File

@@ -51,7 +51,7 @@ in
wantedBy = lib.mkIf cfg.config.autostart [ "graphical-session.target" ];
# for some reason the --ozone-platform-hint=auto flag fails when signal-desktop is launched from a service
serviceConfig.ExecStart = "env NIXOS_OZONE_WL=1 signal-desktop";
command = "env NIXOS_OZONE_WL=1 signal-desktop";
};
};
}

View File

@@ -32,7 +32,7 @@ in
services.sway-autoscaler = {
description = "adjust global desktop scale to match the activate application";
wantedBy = lib.mkIf cfg.config.autostart [ "graphical-session.target" ];
serviceConfig.ExecStart = lib.escapeShellArgs [
command = lib.escapeShellArgs [
"env"
"SWAY_DEFAULT_SCALE=${builtins.toString cfg.config.defaultScale}"
"sway-autoscaler"

View File

@@ -254,7 +254,7 @@ in
services.sway = {
description = "sway: tiling wayland desktop environment";
wantedBy = [ "default.target" ];
serviceConfig.ExecStart = "sway";
command = "sway";
};
};

View File

@@ -57,7 +57,7 @@ in
after = [ "graphical-session.target" ];
wantedBy = [ "graphical-session.target" ];
serviceConfig.ExecStart = lib.escapeShellArgs (
command = lib.escapeShellArgs (
[
"swayidle"
"-w"

View File

@@ -478,7 +478,7 @@ in
# partOf = [ "graphical-session.target" ];
wantedBy = [ "graphical-session.target" ];
serviceConfig.ExecStart = "env G_MESSAGES_DEBUG=all swaync";
command = "env G_MESSAGES_DEBUG=all swaync";
# serviceConfig.BusName = "org.freedesktop.Notifications";
};
};

View File

@@ -63,7 +63,7 @@
# -{H,W} N to set the height/width of the notifier, in px.
# -i N to set the size of the volume icon
# -P to hide percentage text
serviceConfig.ExecStart = "sysvol -p 0 -t 1 -m 22 -H 39 -W 256 -i 32 -P";
command = "sysvol -p 0 -t 1 -m 22 -H 39 -W 256 -i 32 -P";
};
};
}

View File

@@ -120,7 +120,7 @@ in
wantedBy = [ "graphical-session.target" ];
# env G_MESSAGES_DEBUG=all
serviceConfig.ExecStart = "waybar";
command = "waybar";
};
};
}

View File

@@ -34,7 +34,7 @@
after = [ "pipewire.service" ];
bindsTo = [ "pipewire.service" ];
wantedBy = [ "pipewire.service" ];
serviceConfig.ExecStart = "wireplumber";
command = "wireplumber";
};
};
}

View File

@@ -17,7 +17,7 @@
description = "wvkbd: wayland virtual keyboard";
after = [ "graphical-session.target" ];
wantedBy = [ "graphical-session.target" ];
serviceConfig.ExecStart = lib.escapeShellArgs [
command = lib.escapeShellArgs [
"env"
# --hidden: send SIGUSR2 to unhide
# wvkbd layers:

View File

@@ -45,10 +45,8 @@ in
before = [ "xdg-desktop-portal.service" ];
wantedBy = [ "xdg-desktop-portal.service" ];
serviceConfig = {
ExecStart = "${cfg.package}/libexec/xdg-desktop-portal-gtk";
BusName = "org.freedesktop.impl.portal.desktop.gtk";
};
command = "${cfg.package}/libexec/xdg-desktop-portal-gtk";
serviceConfig.BusName = "org.freedesktop.impl.portal.desktop.gtk";
};
};
}

View File

@@ -30,10 +30,8 @@ in
before = [ "xdg-desktop-portal.service" ];
wantedBy = [ "xdg-desktop-portal.service" ];
serviceConfig = {
ExecStart = "${cfg.package}/libexec/xdg-desktop-portal-wlr";
BusName = "org.freedesktop.impl.portal.desktop.wlr";
};
command = "${cfg.package}/libexec/xdg-desktop-portal-wlr";
serviceConfig.BusName = "org.freedesktop.impl.portal.desktop.wlr";
};
};
}

View File

@@ -58,20 +58,18 @@ in
# partOf = [ "graphical-session.target" ];
wantedBy = [ "graphical-session.target" ];
serviceConfig = {
# tracking issue for having xdg-desktop-portal locate portals via more standard directories, obviating this var:
# - <https://github.com/flatpak/xdg-desktop-portal/issues/603>
# i can actually almost omit it today; problem is that if you don't set it it'll look for `sway-portals.conf` in ~/.config/xdg-desktop-portal
# but then will check its *own* output dir for {gtk,wlr}.portal.
# arguable if that's a packaging bug, or limitation...
ExecStart = lib.concatStringsSep " " [
"env"
"XDG_DESKTOP_PORTAL_DIR=$HOME/.config/xdg-desktop-portal"
# "G_MESSAGES_DEBUG=all" #< also applies to all apps launched by the portal
"${cfg.package}/libexec/xdg-desktop-portal"
];
BusName = "org.freedesktop.portal.Desktop";
};
# tracking issue for having xdg-desktop-portal locate portals via more standard directories, obviating this var:
# - <https://github.com/flatpak/xdg-desktop-portal/issues/603>
# i can actually almost omit it today; problem is that if you don't set it it'll look for `sway-portals.conf` in ~/.config/xdg-desktop-portal
# but then will check its *own* output dir for {gtk,wlr}.portal.
# arguable if that's a packaging bug, or limitation...
command = lib.concatStringsSep " " [
"env"
"XDG_DESKTOP_PORTAL_DIR=$HOME/.config/xdg-desktop-portal"
# "G_MESSAGES_DEBUG=all" #< also applies to all apps launched by the portal
"${cfg.package}/libexec/xdg-desktop-portal"
];
serviceConfig.BusName = "org.freedesktop.portal.Desktop";
};
services.xdg-permission-store = {
@@ -82,14 +80,12 @@ in
before = [ "xdg-desktop-portal.service" ];
wantedBy = [ "xdg-desktop-portal.service" ];
serviceConfig = {
ExecStart = lib.concatStringsSep " " [
"env"
"XDG_DESKTOP_PORTAL_DIR=$HOME/.config/xdg-desktop-portal"
"${cfg.package}/libexec/xdg-permission-store"
];
BusName = "org.freedesktop.impl.portal.PermissionStore";
};
command = lib.concatStringsSep " " [
"env"
"XDG_DESKTOP_PORTAL_DIR=$HOME/.config/xdg-desktop-portal"
"${cfg.package}/libexec/xdg-permission-store"
];
serviceConfig.BusName = "org.freedesktop.impl.portal.PermissionStore";
};
# also available: ${cfg.package}/libexec/xdg-document-portal
# - <https://flatpak.github.io/xdg-desktop-portal/docs/doc-org.freedesktop.portal.Documents.html>

View File

@@ -38,17 +38,30 @@ let
default = [];
};
serviceConfig.ExecStart = mkOption {
command = mkOption {
type = types.nullOr (types.coercedTo types.package toString types.str);
default = null;
description = ''
long-running command which represents this service.
when the command returns, the service is considered "failed", and restarted unless explicitly `down`d.
'';
};
serviceConfig.ExecStartPost = mkOption {
type = types.nullOr (types.coercedTo types.package toString types.str);
default = null;
};
serviceConfig.ExecStopPost = mkOption {
cleanupCommand = mkOption {
type = types.nullOr types.str;
default = null;
description = ''
command which is run after the service has exited.
restart of the service (if applicable) is blocked on this command.
'';
};
pollReadyCommand = mkOption {
type = types.nullOr (types.coercedTo types.package toString types.str);
default = null;
description = ''
path to executable which exits zero only when the service is ready.
this may be invoked repeatedly (with delay),
though it's not an error for it to block either (it may, though, be killed and restarted if it blocks too long)
'';
};
serviceConfig.BusName = mkOption {
type = types.nullOr types.str;

View File

@@ -153,8 +153,8 @@ let
s6SvcsFromConfigServices = services: lib.mapAttrsToList
(name: service: {
inherit name;
run = service.serviceConfig.ExecStart;
finish = service.serviceConfig.ExecStopPost;
run = service.command;
finish = service.cleanupCommand;
depends = service.wants ++ builtins.attrNames (
lib.filterAttrs (_: cfg: lib.elem name cfg.wantedBy || lib.elem "${name}.service" cfg.wantedBy) services
);
@@ -167,14 +167,14 @@ let
# map them onto s6 "bundles". their contents are determined via reverse dependency mapping (`wantedBy` of every other service).
implicitServices = {
"default.target" = {
serviceConfig.ExecStart = null;
serviceConfig.ExecStopPost = null;
command = null;
cleanupCommand = null;
wants = [];
wantedBy = [];
};
"graphical-session.target" = {
serviceConfig.ExecStart = null;
serviceConfig.ExecStopPost = null;
command = null;
cleanupCommand = null;
wants = [];
wantedBy = [];
};