From ad97ab279e097960d6d080db10391c92cf25f8ca Mon Sep 17 00:00:00 2001 From: Jonas Rabenstein Date: Sat, 20 Sep 2025 00:17:22 +0200 Subject: [PATCH] module: plugin description --- module/plugins.nix | 63 ++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 63 insertions(+) create mode 100644 module/plugins.nix diff --git a/module/plugins.nix b/module/plugins.nix new file mode 100644 index 0000000..31937e3 --- /dev/null +++ b/module/plugins.nix @@ -0,0 +1,63 @@ +{ + pkgs, + config, + lib, + ... +}: +let + cfg = config.services.jellyfin; + + plugin = name: pks."jellyfin-plugin-${name}"; + + per-file = pkg: fn: lib.lists.foldl (acc: dll: acc ++ (fn dll)) pkg.pluginLibraries; + + serviceConfig = + pkg: + let + make-rw = pkgs.writeShellScript "make-rw" '' + readonly src="${pkg}/''${1}" + readonly dst="${cfg.dataDir}/''${1}" + mkdir -p "''${dst%/*}" + [[ -f "''${dst}" ]] || cp "''${src}" "''${dst}" + ''; + in + { + BindReadOnlyPaths = per-file pkg ( + name: "${pkg}/${name}:${cfg.dataDir}/plugins/${pkg.name}/${name}" + ); + BindPaths = per-file pkg ( + name: lib.optional (rw name) "${cfg.dataDir}/plugins/${pkg.name}/${name}" + ); + }; + + type.plugin = lib.types.addCheck lib.types.package (builtins.hasAttr "pluginLibraries"); +in +{ + options.services.jellyfin.plugins = lib.mkOption { + type = lib.types.listOf (lib.types.coercedTo lib.types.nonEmptyStr plugin type.plugin); + default = { }; + }; + + config.systemd = lib.mkIf (cfg.plugins != { }) { + services.jellyfin.serviceConfig = lib.mkMerge ( + [ + { TemporaryFileSystem = [ "${cfg.dataDir}/plugins:ro" ]; } + { BindPaths = [ "${cfg.dataDir}/plugins/configurations/" ]; } + ] + ++ builtins.map serviceConfig cfg.plugins + ); + + tmpfiles.settings = lib.lists.foldl ( + acc: pkg: + acc + // { + ${pkg.name}."${cfg.dataDir}/plugins/${pkgs.name}/${name}".C = { + group = cfg.group; + user = cfg.user; + mode = "0700"; + argument = "${pkg}/${name}"; + }; + } + ) { } cfg.plugins; + }; +}