1{
2 config,
3 lib,
4 pkgs,
5 ...
6}: let
7 # idk how to share this across files :(
8 mkNotify = {
9 message,
10 channel,
11 priority ? 1,
12 }: ''
13 LOGIN=$(cat "${config.age.secrets.ntfyAuto.path}")
14 ${pkgs.curl}/bin/curl -u $LOGIN \
15 -H "X-Priority: ${toString priority}" \
16 -d '${message}' \
17 https://${config.mySnippets.aylac-top.networkMap.ntfy.vHost}/${channel}
18 '';
19
20 repoMap = {
21 A = "rclone:a_gdrive:/backups/${config.networking.hostName}";
22 B = "rclone:b_gdrive:/backups/${config.networking.hostName}";
23 };
24 mkRepo = {
25 repo,
26 service,
27 }: "${repoMap.${repo}}/${service}";
28
29 stop = {
30 service,
31 repoPath,
32 }: ''
33 #!${pkgs.bash}/bin/bash
34 ${mkNotify {
35 message = "Backing up ${service} to ${repoPath}, stopping service";
36 channel = "network-status";
37 }}
38 ${pkgs.systemd}/bin/systemctl stop ${service}
39 '';
40
41 start = {
42 service,
43 repoPath,
44 }: ''
45 #!${pkgs.bash}/bin/bash
46 ${mkNotify {
47 message = "Back up for ${service} to ${repoPath} was completed (idk if successfully tho), starting service";
48 channel = "network-status";
49 }}
50 ${pkgs.systemd}/bin/systemctl start ${service}
51 '';
52
53 prepareNoService = {
54 service,
55 repoPath,
56 }: ''
57 #!${pkgs.bash}/bin/bash
58 ${mkNotify {
59 message = "Backing up ${service} to ${repoPath}";
60 channel = "network-status";
61 }}
62 '';
63
64 cleanupNoService = {
65 service,
66 repoPath,
67 }: ''
68 #!${pkgs.bash}/bin/bash
69 ${mkNotify {
70 message = "Back up for ${service} to ${repoPath} was completed (idk if successfully tho)";
71 channel = "network-status";
72 }}
73 '';
74
75 mkBackups = services:
76 lib.listToAttrs (map (service: let
77 repoKey = service.repo or "A";
78 repoPath = mkRepo {
79 repo = repoKey;
80 service = service.name;
81 };
82 systemdService =
83 if service.containerised or false
84 then "container@" + service.name
85 else service.name;
86 backupMode = service.backupMode or "stop"; # "stop", "notify", "quiet"
87
88 commands =
89 if backupMode == "stop"
90 then {
91 backupCleanupCommand = start {
92 service = systemdService;
93 inherit repoPath;
94 };
95 backupPrepareCommand = stop {
96 service = systemdService;
97 inherit repoPath;
98 };
99 }
100 else if backupMode == "notify"
101 then {
102 backupCleanupCommand = cleanupNoService {
103 service = service.name;
104 inherit repoPath;
105 };
106 backupPrepareCommand = prepareNoService {
107 service = service.name;
108 inherit repoPath;
109 };
110 }
111 else {};
112 in
113 lib.nameValuePair service.name (
114 config.mySnippets.restic
115 // {
116 repository = repoPath;
117 inherit (service) paths;
118 }
119 // commands
120 // (service.extraConfig or {})
121 )) (lib.filter (s: s.enable) services));
122in {
123 options.myNixOS.profiles.backups = {
124 enable = lib.mkEnableOption "automatically back up enabled services";
125 };
126
127 config = lib.mkIf config.myNixOS.profiles.backups.enable {
128 services.restic.backups = mkBackups [
129 {
130 name = "audiobookshelf";
131 inherit (config.services.audiobookshelf) enable;
132 paths = [config.services.audiobookshelf.dataDir];
133 }
134 {
135 name = "bazarr";
136 inherit (config.services.bazarr) enable;
137 paths = [config.services.bazarr.dataDir];
138 }
139 {
140 name = "couchdb";
141 inherit (config.services.couchdb) enable;
142 paths = [config.services.couchdb.databaseDir];
143 }
144 {
145 name = "forgejo";
146 inherit (config.services.forgejo) enable;
147 paths = [config.services.forgejo.stateDir];
148 }
149 # {
150 # name = "immich";
151 # inherit (config.services.immich) enable;
152 # name = "immich-server";
153 # paths = [
154 # "${config.services.immich.mediaLocation}/library"
155 # "${config.services.immich.mediaLocation}/profile"
156 # "${config.services.immich.mediaLocation}/upload"
157 # "${config.services.immich.mediaLocation}/backups"
158 # ];
159 # repo = "B";
160 # }
161 {
162 name = "jellyfin";
163 inherit (config.services.jellyfin) enable;
164 paths = [config.services.jellyfin.dataDir];
165 }
166 {
167 name = "lidarr";
168 inherit (config.services.lidarr) enable;
169 paths = [config.services.lidarr.dataDir];
170 }
171 {
172 name = "ombi";
173 inherit (config.services.ombi) enable;
174 paths = [config.services.ombi.dataDir];
175 }
176 {
177 # damn this is ugly
178 name = "pds";
179 containerised = true;
180 inherit (config.myNixOS.services.pds) enable;
181 paths = ["/var/lib/nixos-containers/pds${config.containers.pds.config.services.bluesky-pds.settings.PDS_DATA_DIRECTORY}"];
182 }
183 {
184 name = "plex";
185 inherit (config.services.plex) enable;
186 paths = [config.services.plex.dataDir];
187 extraConfig = {
188 exclude = ["${config.services.plex.dataDir}/Plex Media Server/Plug-in Support/Databases"];
189 };
190 }
191 {
192 name = "postgresql";
193 containerised = true;
194 inherit (config.services.postgresql) enable;
195 paths = [config.services.postgresql.dataDir];
196 backupMode = "quiet";
197 }
198 {
199 name = "prowlarr";
200 inherit (config.services.prowlarr) enable;
201 paths = [config.services.prowlarr.dataDir];
202 }
203 {
204 name = "qbittorrent";
205 inherit (config.services.qbittorrent) enable;
206 paths = [config.services.qbittorrent.dataDir];
207 }
208 {
209 name = "radarr";
210 inherit (config.services.radarr) enable;
211 paths = [config.services.radarr.dataDir];
212 }
213 {
214 name = "readarr";
215 inherit (config.services.readarr) enable;
216 paths = [config.services.readarr.dataDir];
217 }
218 {
219 name = "sonarr";
220 inherit (config.services.sonarr) enable;
221 paths = [config.services.sonarr.dataDir];
222 }
223 {
224 name = "autobrr";
225 inherit (config.services.autobrr) enable;
226 paths = ["${config.myNixOS.profiles.arr.dataDir}/autobrr"];
227 }
228 {
229 name = "tautulli";
230 inherit (config.services.tautulli) enable;
231 paths = [config.services.tautulli.dataDir];
232 }
233 {
234 name = "uptime-kuma";
235 inherit (config.services.uptime-kuma) enable;
236 paths = ["/var/lib/uptime-kuma"];
237 }
238 {
239 name = "vaultwarden";
240 inherit (config.services.vaultwarden) enable;
241 paths = ["/var/lib/vaultwarden"];
242 }
243 {
244 name = "passwords";
245 enable = builtins.elem config.networking.hostName config.mySnippets.syncthing.folders."Passwords".devices;
246 paths = [config.mySnippets.syncthing.folders."Passwords".path];
247 backupMode = "notify";
248 }
249 {
250 name = "radicale";
251 inherit (config.services.radicale) enable;
252 paths = ["/var/lib/radicale"];
253 }
254 {
255 name = "webdav";
256 inherit (config.services.webdav-server-rs) enable;
257 paths = ["/var/lib/webdav"];
258 backupMode = "notify";
259 }
260 {
261 name = "miniflux";
262 inherit (config.services.miniflux) enable;
263 paths = ["/var/lib/miniflux"];
264 }
265 {
266 name = "jellyseerr";
267 inherit (config.services.jellyseerr) enable;
268 paths = ["/var/lib/jellyseerr"];
269 }
270 {
271 name = "tangled-knot";
272 containerised = true;
273 inherit (config.myNixOS.services.tangled-knot) enable;
274 paths = ["/var/lib/nixos-containers/tangled-knot${config.containers.tangled-knot.config.services.tangled-knot.stateDir}"];
275 }
276 ];
277 };
278}