summaryrefslogtreecommitdiff
path: root/accounts/gkleen@sif/systemd.nix
diff options
context:
space:
mode:
Diffstat (limited to 'accounts/gkleen@sif/systemd.nix')
-rw-r--r--accounts/gkleen@sif/systemd.nix321
1 files changed, 210 insertions, 111 deletions
diff --git a/accounts/gkleen@sif/systemd.nix b/accounts/gkleen@sif/systemd.nix
index 119d8cc3..a2d6e4ff 100644
--- a/accounts/gkleen@sif/systemd.nix
+++ b/accounts/gkleen@sif/systemd.nix
@@ -6,7 +6,7 @@ let
6 cfg = config.home-manager.users.${userName}; 6 cfg = config.home-manager.users.${userName};
7 7
8 autossh-socks-script = pkgs.writeScript "autossh" '' 8 autossh-socks-script = pkgs.writeScript "autossh" ''
9 #!${pkgs.zsh}/bin/zsh -xe 9 #!${lib.getExe pkgs.zsh} -xe
10 10
11 host="''${1%:*}" 11 host="''${1%:*}"
12 port="''${1#*:}" 12 port="''${1#*:}"
@@ -15,31 +15,29 @@ let
15 cmd=() 15 cmd=()
16 16
17 if [[ -n "''${SSHPASS_SECRET}" ]]; then 17 if [[ -n "''${SSHPASS_SECRET}" ]]; then
18 cmd+=(${pkgs.sshpassSecret}/bin/sshpass-secret) 18 cmd+=(${lib.getExe' pkgs.sshpassSecret "sshpass-secret"})
19 cmd+=("''${(@s/:/)SSHPASS_SECRET}") 19 cmd+=("''${(@s/:/)SSHPASS_SECRET}")
20 cmd+=(--) 20 cmd+=(--)
21 fi 21 fi
22 22
23 cmd+=(${pkgs.openssh}/bin/ssh -vN -D localhost:''${port} "''${host}") 23 cmd+=(${lib.getExe' pkgs.openssh "ssh"} -vN -D 127.0.0.1:''${port} "''${host}")
24 24
25 ( exec -a "''${cmd[1]}" -- ''${cmd} ) & 25 ( exec -a "''${cmd[1]}" -- ''${cmd} ) &
26 pid=$! 26 pid=$!
27 27
28 newpid="" 28 newpid=""
29 i=200 29 i=200
30 while ! newpid=$(${pkgs.lsof}/bin/lsof -Pi @localhost:"''${port}" -sTCP:LISTEN -t); do 30 while ! { newpid=$(${lib.getExe' pkgs.iproute2 "ss"} -HO -pln "src localhost sport ''${port}" | ${lib.getExe pkgs.gnused} -r 's/^.*pid=([0-9]+).*$/\1/'); [[ -n $newpid ]] }; do
31 if ! kill -0 "''${pid}"; then 31 if ! kill -0 "''${pid}"; then
32 wait "''${pid}" 32 wait "''${pid}"
33 exit $? 33 exit $?
34 fi 34 fi
35 [[ "''${i}" -gt 0 ]] || exit 1 35 [[ "''${i}" -gt 0 ]] || exit 1
36 i=$((''${i} - 1)) 36 i=$((''${i} - 1))
37 ${pkgs.coreutils}/bin/sleep 0.1 37 ${lib.getExe' pkgs.coreutils "sleep"} 0.1
38 done 38 done
39 39
40 ${config.systemd.package}/bin/systemd-notify --ready 40 ${lib.getExe' config.systemd.package "systemd-notify"} --pid=''${newpid} --ready
41
42 wait "''${pid}" "''${newpid}"
43 ''; 41 '';
44in { 42in {
45 tmpfiles.rules = [ 43 tmpfiles.rules = [
@@ -48,11 +46,11 @@ in {
48 ]; 46 ];
49 47
50 services = { 48 services = {
51 sync-keepass = { 49 "sync-keepass@" = {
52 Service = { 50 Service = {
53 Type = "oneshot"; 51 Type = "oneshot";
54 WorkingDirectory = "~"; 52 WorkingDirectory = "~";
55 ExecStart = toString (pkgs.writers.writePython3 "sync-keepass" { 53 ExecStart = "${pkgs.writers.writePython3 "sync-keepass" {
56 libraries = with pkgs.python3Packages; [ python-dateutil ]; 54 libraries = with pkgs.python3Packages; [ python-dateutil ];
57 } '' 55 } ''
58 import json 56 import json
@@ -61,13 +59,13 @@ in {
61 from datetime import datetime 59 from datetime import datetime
62 from dateutil.tz import tzlocal 60 from dateutil.tz import tzlocal
63 from dateutil.parser import isoparse 61 from dateutil.parser import isoparse
64 from sys import stderr 62 from sys import stderr, argv
65 63
66 64
67 remote_fs = 'surtr' 65 remote_fs = 'surtr' if argv[1] == 'store.kdbx' else 'mathcloud'
68 remote_file = 'store.kdbx' 66 remote_file = argv[1]
69 target_file = expanduser('~/store.kdbx') 67 target_file = expanduser(f'~/{argv[1]}')
70 meta_file = expanduser('~/.store.kdbx.json') 68 meta_file = expanduser(f'~/.{argv[1]}.json')
71 69
72 upload_time = None 70 upload_time = None
73 our_last_upload_time = None 71 our_last_upload_time = None
@@ -117,22 +115,14 @@ in {
117 do_upload() 115 do_upload()
118 elif upload_time is not None and (mod_time is None or upload_time > mod_time) and (our_last_upload_time is None or upload_time > our_last_upload_time): # noqa: E501 116 elif upload_time is not None and (mod_time is None or upload_time > mod_time) and (our_last_upload_time is None or upload_time > our_last_upload_time): # noqa: E501
119 do_download() 117 do_download()
120 ''); 118 ''} \"%I\"";
121 Environment = [ "RCLONE_PASSWORD_COMMAND=\"${pkgs.coreutils}/bin/cat ${config.sops.secrets.gkleen-rclone.path}\"" "PATH=${pkgs.rclone}/bin" ]; 119 Environment = [ "RCLONE_PASSWORD_COMMAND=\"${pkgs.coreutils}/bin/cat ${config.sops.secrets.gkleen-rclone.path}\"" "PATH=${pkgs.rclone}/bin" ];
122 }; 120 };
123 }; 121 };
124 emacs = { 122 emacs = {
125 Unit = { 123 Unit = {
126 After = ["graphical-session-pre.target"]; 124 After = [ "graphical-session.target" ];
127 }; 125 BindsTo = [ "graphical-session.target" ];
128 };
129 dunst = {
130 Service = {
131 ExecStart = lib.mkForce "${cfg.services.dunst.package}/bin/dunst";
132 Restart = "always";
133 };
134 Install = {
135 WantedBy = ["graphical-session.target"];
136 }; 126 };
137 }; 127 };
138 keepassxc = { 128 keepassxc = {
@@ -144,8 +134,8 @@ in {
144 Environment = [ "QT_QPA_PLATFORM=wayland" ]; 134 Environment = [ "QT_QPA_PLATFORM=wayland" ];
145 }; 135 };
146 Unit = { 136 Unit = {
147 Requires = ["graphical-session-pre.target"]; 137 After = [ "graphical-session.target" ];
148 After = ["graphical-session-pre.target"]; 138 BindsTo = [ "graphical-session.target" ];
149 }; 139 };
150 }; 140 };
151 mpris-proxy = { 141 mpris-proxy = {
@@ -154,7 +144,7 @@ in {
154 Service.ExecStart = "${pkgs.bluez}/bin/mpris-proxy"; 144 Service.ExecStart = "${pkgs.bluez}/bin/mpris-proxy";
155 Install.WantedBy = [ "default.target" ]; 145 Install.WantedBy = [ "default.target" ];
156 }; 146 };
157 "autossh-socks@proxy.mathw0h:8119" = { 147 "autossh-socks@proxy.ssh.math.lmu.de:8119" = {
158 Service = { 148 Service = {
159 Type = "notify"; 149 Type = "notify";
160 NotifyAccess = "all"; 150 NotifyAccess = "all";
@@ -162,7 +152,7 @@ in {
162 Restart = "always"; 152 Restart = "always";
163 RestartSec = "23s"; 153 RestartSec = "23s";
164 ExecStart = "${autossh-socks-script} \"%I\""; 154 ExecStart = "${autossh-socks-script} \"%I\"";
165 Environment = [ "SSHPASS_SECRET=gkleen@mathw0g.math.lmu.de" ]; 155 Environment = [ "SSHPASS_SECRET=gkleen@ssh.math.lmu.de" ];
166 }; 156 };
167 Unit = { 157 Unit = {
168 StopWhenUnneeded = true; 158 StopWhenUnneeded = true;
@@ -181,102 +171,91 @@ in {
181 }; 171 };
182 Unit = { 172 Unit = {
183 StopWhenUnneeded = true; 173 StopWhenUnneeded = true;
174 StartLimitInterval = "2s";
175 StartLimitBurst = 25;
184 }; 176 };
185 }; 177 };
186 swayidle = { 178 "autossh-socks@proxy.mathw0h:8123" = {
187 Service = { 179 Service = {
188 RuntimeDirectory = "swayidle"; 180 Type = "notify";
181 NotifyAccess = "all";
182 WorkingDirectory = "~";
183 Restart = "always";
184 RestartSec = "23s";
185 ExecStart = "${autossh-socks-script} \"%I\"";
186 Environment = [ "SSHPASS_SECRET=gkleen@mathw0h.mathinst.loc" ];
187 };
188 Unit = {
189 StopWhenUnneeded = true;
190 StartLimitInterval = "180s";
191 StartLimitBurst = 7;
189 }; 192 };
190 }; 193 };
191 psi-notify = { 194 "autossh-socks@proxy.mathw0e:8125" = {
192 Install = { 195 Service = {
193 WantedBy = ["graphical-session.target"]; 196 Type = "notify";
197 NotifyAccess = "all";
198 WorkingDirectory = "~";
199 Restart = "always";
200 RestartSec = "23s";
201 ExecStart = "${autossh-socks-script} \"%I\"";
202 Environment = [ "SSHPASS_SECRET=gkleen@mathw0e.mathinst.loc" ];
194 }; 203 };
195 Unit = { 204 Unit = {
196 Requires = ["graphical-session-pre.target"]; 205 StopWhenUnneeded = true;
197 After = ["graphical-session-pre.target"]; 206 StartLimitInterval = "180s";
207 StartLimitBurst = 7;
198 }; 208 };
209 };
210 "autossh-socks@proxy.cip04:8127" = {
199 Service = { 211 Service = {
200 ExecStart = lib.getExe pkgs.psi-notify;
201 ExecReload = "${pkgs.coreutils}/bin/kill -HUP $MAINPID";
202 Type = "notify"; 212 Type = "notify";
213 NotifyAccess = "all";
214 WorkingDirectory = "~";
203 Restart = "always"; 215 Restart = "always";
204 WatchdogSec = "2s"; 216 RestartSec = "23s";
217 ExecStart = "${autossh-socks-script} \"%I\"";
218 Environment = [ "SSHPASS_SECRET=gkleen@cip04.cipmath.loc" ];
219 };
220 Unit = {
221 StopWhenUnneeded = true;
222 StartLimitInterval = "180s";
223 StartLimitBurst = 7;
205 }; 224 };
206 }; 225 };
207 gtklock = { 226 psi-notify = {
227 Install = {
228 WantedBy = ["graphical-session.target"];
229 };
208 Unit = { 230 Unit = {
209 Requisite = ["graphical-session.target"]; 231 After = [ "graphical-session.target" ];
210 PartOf = ["graphical-session.target"]; 232 PartOf = [ "graphical-session.target" ];
211 }; 233 };
212 Service = { 234 Service = {
235 ExecStart = lib.getExe pkgs.psi-notify;
236 ExecReload = "${pkgs.coreutils}/bin/kill -HUP $MAINPID";
213 Type = "notify"; 237 Type = "notify";
214 RuntimeDirectory = "gtklock"; 238 Restart = "always";
215 CacheDirectory = "gtklock"; 239 WatchdogSec = "2s";
216 ExecStartPre = [
217 "${pkgs.libsForQt5.qt5.qttools.bin}/bin/qdbus org.keepassxc.KeePassXC.MainWindow /keepassxc org.keepassxc.KeePassXC.MainWindow.lockAllDatabases"
218 "${config.systemd.package}/bin/systemctl --user stop gpg-agent.service"
219 (pkgs.writeShellScript "generate-css" ''
220 set -x
221 export PATH="${lib.makeBinPath [cfg.programs.wpaperd.package pkgs.jq pkgs.coreutils pkgs.imagemagick pkgs.findutils]}:$PATH"
222
223 declare -A monitors
224 monitors=()
225 while IFS= read -r entry; do
226 path=$(jq -r ".path" <<<"$entry")
227 [[ -z "$path" || ! -f "$path" ]] && continue
228 blurred_path="$CACHE_DIRECTORY"/"$(b2sum -l 128 <<<"$path" | cut -d' ' -f1)"."''${path##*.}"
229 monitor=$(jq -r ".display" <<<"$entry")
230 if [[ ! -f "$blurred_path" ]]; then
231 mkdir -p "$(dirname "$blurred_path")"
232 magick "$path" -filter Gaussian -resize 6.25% -define filter:sigma=2.5 -resize 1600% "$blurred_path" &
233 fi
234 monitors+=([$monitor]="$blurred_path")
235 done < <(wpaperctl all-wallpapers -j | jq -c ".[]")
236 wait
237
238 cp --no-preserve=mode ${pkgs.writeText "gtklock.css" ''
239 #window-box {
240 padding: 64px;
241 /* border: 1px solid black; */
242 border-radius: 4px;
243 box-shadow: rgba(0, 0, 0, 0.8) 0px 4px 12px;
244 /* background-color: white; */
245 background-color: rgba(0, 0, 0, 0.5);
246 }
247 ''} "$RUNTIME_DIRECTORY"/style.css
248 for monitor in "''${!monitors[@]}"; do
249 cat >>"$RUNTIME_DIRECTORY"/style.css <<EOF
250 window#''${monitor} {
251 background-image: url("''${monitors[$monitor]}");
252 background-repeat: no-repeat;
253 background-size: 100% 100%;
254 background-origin: content-box;
255 }
256 EOF
257 done
258 '')
259 ];
260 NotifyAccess = "all";
261 ExecStart = ''${lib.getExe pkgs.gtklock} -s "''${RUNTIME_DIRECTORY}/style.css" -L ${pkgs.writeShellScript "after-lock" ''
262 ${cfg.wayland.windowManager.hyprland.package}/bin/hyprctl dispatch dpms off
263 ${config.systemd.package}/bin/systemd-notify --ready
264 ''}'';
265 }; 240 };
266 }; 241 };
267 "yt-dlp@" = { 242 "yt-dlp@" = {
268 Service = { 243 Service = {
269 Type = "notify"; 244 Type = "notify";
270 CacheDirectory = "yt-dlp/%N"; 245 CacheDirectory = "yt-dlp/%N";
246 RuntimeDirectory = "yt-dlp/%N";
271 StandardInput = "socket"; 247 StandardInput = "socket";
272 StandardOutput = "journal"; 248 StandardOutput = "journal";
273 WatchdogSec = "30min"; 249 WatchdogSec = "30min";
250 CPUSchedulingPolicy = "idle";
251 IOSchedulingClass = "idle";
274 Environment = [ 252 Environment = [
275 "PATH=${lib.makeBinPath (with pkgs; [atomicparsley ffmpeg-headless rtmpdump])}" 253 "PATH=${lib.makeBinPath (with pkgs; [atomicparsley ffmpeg-headless rtmpdump])}"
276 "DSCP=8" 254 "DSCP=8"
277 ]; 255 ];
278 ExecStart = ''${lib.getExe pkgs.dscp} ${pkgs.writers.writePython3 "yt-dlp" { 256 ExecStart = ''${lib.getExe pkgs.dscp} ${pkgs.writers.writePython3 "yt-dlp" {
279 libraries = with pkgs.python3Packages; [ yt-dlp sdnotify ]; 257 libraries = with pkgs.python3Packages; [ yt-dlp sdnotify ];
258 flakeIgnore = [ "E501" ];
280 } '' 259 } ''
281 import json 260 import json
282 from yt_dlp import YoutubeDL, parse_options 261 from yt_dlp import YoutubeDL, parse_options
@@ -284,14 +263,46 @@ in {
284 from sdnotify import SystemdNotifier 263 from sdnotify import SystemdNotifier
285 from os import environ 264 from os import environ
286 from pathlib import Path 265 from pathlib import Path
266 import threading
267 import socketserver
287 268
288 269
289 n = SystemdNotifier() 270 status = None
271 status_notifier = threading.Condition()
272
273
274 class StatusRequestHandler(socketserver.BaseRequestHandler):
275 def handle(self):
276 with self.request.makefile('w', encoding='utf-8') as fh:
277 while True:
278 with status_notifier:
279 json.dump(status, fh)
280 fh.write('\n')
281 fh.flush()
282 status_notifier.wait()
283
284
285 class ThreadedUnixStreamServer(socketserver.ThreadingMixIn, socketserver.UnixStreamServer):
286 pass
287
288
289 def progress_hook(d):
290 global status
291 n.notify('WATCHDOG=1\nSTATUS=' + d['status'])
292 with status_notifier:
293 status = {
294 **{k: v for k, v in d.items() if k in {'status', 'downloaded_bytes', 'total_bytes', 'total_bytes_estimate', 'fragment_count', 'fragment_index'}},
295 **{k: v for k, v in (d['info_dict'] if 'info_dict' in d else {}).items() if k in {'title', 'filename'}},
296 }
297 status_notifier.notify_all()
298
299
300 n = SystemdNotifier(debug=True)
290 args = json.load(stdin) 301 args = json.load(stdin)
291 ydl_opts = { 302 ydl_opts = {
292 **parse_options().ydl_opts, 303 **parse_options().ydl_opts,
293 'progress_hooks': [lambda _d: n.notify('WATCHDOG=1')], 304 'progress_hooks': [progress_hook],
294 'postprocessor_hooks': [lambda _d: n.notify('WATCHDOG=1')], 305 'postprocessor_hooks': [progress_hook],
295 'progress_with_newline': True, 306 'progress_with_newline': True,
296 'progress_delta': 5, 307 'progress_delta': 5,
297 'paths': { 308 'paths': {
@@ -301,6 +312,9 @@ in {
301 'noplaylist': True, 312 'noplaylist': True,
302 **(args['params'] if 'params' in args else {}), 313 **(args['params'] if 'params' in args else {}),
303 } 314 }
315 status_server = ThreadedUnixStreamServer(str(Path(environ['RUNTIME_DIRECTORY']) / 'status.sock'), StatusRequestHandler)
316 status_server.daemon_threads = True
317 threading.Thread(target=status_server.serve_forever, daemon=True).start()
304 with YoutubeDL(ydl_opts) as ytdl: 318 with YoutubeDL(ydl_opts) as ytdl:
305 n.notify('READY=1') 319 n.notify('READY=1')
306 ytdl.download(args['urls']) 320 ytdl.download(args['urls'])
@@ -308,38 +322,101 @@ in {
308 ExecStopPost = "${pkgs.coreutils}/bin/rm -rfv \"$CACHE_DIRECTORY\""; 322 ExecStopPost = "${pkgs.coreutils}/bin/rm -rfv \"$CACHE_DIRECTORY\"";
309 }; 323 };
310 }; 324 };
311 wpaperd = { 325 # wpaperd = {
326 # Install = {
327 # WantedBy = ["graphical-session.target"];
328 # };
329 # Unit = {
330 # After = [ "graphical-session.target" ];
331 # PartOf = [ "graphical-session.target" ];
332 # };
333 # Service = {
334 # ExecStart = lib.getExe cfg.services.wpaperd.package;
335 # Type = "simple";
336 # Restart = "always";
337 # RestartSec = "2s";
338 # };
339 # };
340 xembed-sni-proxy = {
341 Unit = {
342 PartOf = lib.mkForce ["tray.target"];
343 };
344 };
345 poweralertd = {
346 Unit = {
347 After = ["graphical-session.target"];
348 };
349 };
350 network-manager-applet = {
351 Unit = {
352 PartOf = lib.mkForce ["tray.target"];
353 };
354 };
355 udiskie = {
356 Unit = {
357 PartOf = lib.mkForce ["tray.target"];
358 };
359 };
360 blueman-applet = {
361 Unit = {
362 PartOf = lib.mkForce ["tray.target"];
363 };
312 Install = { 364 Install = {
313 WantedBy = ["graphical-session.target"]; 365 WantedBy = lib.mkForce ["tray.target"];
314 }; 366 };
367 };
368 alacritty = {
315 Unit = { 369 Unit = {
316 BindsTo = ["graphical-session-pre.target"]; 370 Requisite = ["graphical-session.target"];
317 After = ["graphical-session-pre.target"]; 371 After = [ "graphical-session.target" ];
318 }; 372 };
319 Service = { 373 Service = {
320 ExecStart = lib.getExe cfg.programs.wpaperd.package; 374 ExecStart = "${lib.getExe pkgs.alacritty} --daemon --socket %t/alacritty-activated.sock";
321 Type = "simple"; 375 };
322 Restart = "always"; 376 };
323 RestartSec = "2s"; 377 alacritty-proxy = {
378 Unit = {
379 Requires = ["alacritty.service" "alacritty-proxy.socket"];
380 After = ["alacritty.service" "alacritty-proxy.socket"];
381 };
382 Service = {
383 Type = "notify";
384 ExecStart = "${config.systemd.package}/lib/systemd/systemd-socket-proxyd %t/alacritty-activated.sock";
324 }; 385 };
325 }; 386 };
326 } // listToAttrs (map ({host, port}: nameValuePair "proxy-to-autossh-socks@${toString port}" { 387 } // listToAttrs (map ({host, port}: nameValuePair "proxy-to-autossh-socks@${toString port}" {
327 Unit = { 388 Unit = {
328 Requires = ["autossh-socks@${host}:${toString (port + 1)}.service" "proxy-to-autossh-socks@${toString port}.socket"]; 389 BindsTo = ["autossh-socks@${host}:${toString (port + 1)}.service" "proxy-to-autossh-socks@${toString port}.socket"];
329 After = ["autossh-socks@${host}:${toString (port + 1)}.service" "proxy-to-autossh-socks@${toString port}.socket"]; 390 After = ["autossh-socks@${host}:${toString (port + 1)}.service" "proxy-to-autossh-socks@${toString port}.socket"];
330 }; 391 };
331 Service = { 392 Service = {
332 ExecStart = "${config.systemd.package}/lib/systemd/systemd-socket-proxyd --exit-idle-time=10s localhost:${toString (port + 1)}"; 393 ExecStart = "${config.systemd.package}/lib/systemd/systemd-socket-proxyd --exit-idle-time=60s 127.0.0.1:${toString (port + 1)}";
394 Restart = "always";
395 RestartSec = "23s";
333 }; 396 };
334 }) [{ host = "proxy.mathw0h"; port = 8118; } { host = "proxy.vidhar"; port = 8120; }]); 397 }) [{ host = "proxy.ssh.math.lmu.de"; port = 8118; } { host = "proxy.vidhar"; port = 8120; } { host = "proxy.mathw0h"; port = 8122; } { host = "proxy.mathw0e"; port = 8124; } { host = "proxy.cip04"; port = 8126; }]);
335 sockets = listToAttrs (map (port: nameValuePair "proxy-to-autossh-socks@${toString port}" { 398 sockets = listToAttrs (map (port: nameValuePair "proxy-to-autossh-socks@${toString port}" {
336 Socket = { 399 Socket = {
337 ListenStream = "%I"; 400 ListenStream = "%I";
401 TriggerLimitIntervalSec = 0;
402 PollLimitIntervalSec = "180s";
403 PollLimitBurst = 6;
338 }; 404 };
339 Install = { 405 Install = {
340 WantedBy = ["default.target"]; 406 WantedBy = ["sockets.target"];
407 };
408 }) [8118 8122 8124 8126]) // {
409 "proxy-to-autossh-socks@8120" = {
410 Socket = {
411 ListenStream = "%I";
412 TriggerLimitIntervalSec = 0;
413 PollLimitIntervalSec = "2s";
414 PollLimitBurst = 20;
415 };
416 Install = {
417 WantedBy = ["sockets.target"];
418 };
341 }; 419 };
342 }) [8118 8120]) // {
343 "yt-dlp" = { 420 "yt-dlp" = {
344 Socket = { 421 Socket = {
345 SocketMode = "0600"; 422 SocketMode = "0600";
@@ -351,9 +428,18 @@ in {
351 WantedBy = ["sockets.target"]; 428 WantedBy = ["sockets.target"];
352 }; 429 };
353 }; 430 };
431 "alacritty-proxy" = {
432 Socket = {
433 SocketMode = "0600";
434 ListenStream = "%t/alacritty.sock";
435 };
436 Install = {
437 WantedBy = ["sockets.target"];
438 };
439 };
354 }; 440 };
355 timers = { 441 timers = {
356 sync-keepass = { 442 "sync-keepass@store.kdbx" = {
357 Timer = { 443 Timer = {
358 OnActiveSec = "1m"; 444 OnActiveSec = "1m";
359 OnUnitActiveSec = "1m"; 445 OnUnitActiveSec = "1m";
@@ -363,6 +449,16 @@ in {
363 WantedBy = ["default.target"]; 449 WantedBy = ["default.target"];
364 }; 450 };
365 }; 451 };
452 "sync-keepass@rz.kdbx" = {
453 Timer = {
454 OnActiveSec = "1d";
455 OnUnitActiveSec = "1d";
456 };
457
458 Install = {
459 WantedBy = ["default.target"];
460 };
461 };
366 }; 462 };
367 targets = { 463 targets = {
368 graphical-session = { 464 graphical-session = {
@@ -373,6 +469,9 @@ in {
373 }; 469 };
374 tray = { 470 tray = {
375 Unit = { 471 Unit = {
472 PartOf = [ "graphical-session.target" ];
473 # Requires = [ "waybar.service" ];
474 After = [ "graphical-session.target" ]; # "waybar.service" ];
376 Wants = ["blueman-applet.service" "udiskie.service" "network-manager-applet.service"]; 475 Wants = ["blueman-applet.service" "udiskie.service" "network-manager-applet.service"];
377 }; 476 };
378 }; 477 };