fs: add experimental support for symlink entries
This commit is contained in:
@@ -24,6 +24,10 @@ let
|
|||||||
type = types.nullOr (mountEntryFor name);
|
type = types.nullOr (mountEntryFor name);
|
||||||
default = null;
|
default = null;
|
||||||
};
|
};
|
||||||
|
symlink = mkOption {
|
||||||
|
type = types.nullOr (symlinkEntryFor name);
|
||||||
|
default = null;
|
||||||
|
};
|
||||||
unit = mkOption {
|
unit = mkOption {
|
||||||
type = types.str;
|
type = types.str;
|
||||||
description = "name of the systemd unit which ensures this entry";
|
description = "name of the systemd unit which ensures this entry";
|
||||||
@@ -42,9 +46,13 @@ let
|
|||||||
# if defaulted, this module is responsible for finalizing the entry.
|
# if defaulted, this module is responsible for finalizing the entry.
|
||||||
# the user could override this if, say, they finalize some aspect of the entry
|
# the user could override this if, say, they finalize some aspect of the entry
|
||||||
# with a custom service.
|
# with a custom service.
|
||||||
unit = lib.mkDefault (if config.mount != null then
|
unit = lib.mkDefault (
|
||||||
|
if config.mount != null then
|
||||||
config.mount.unit
|
config.mount.unit
|
||||||
else config.dir.unit);
|
else if config.symlink != null then
|
||||||
|
config.symlink.unit
|
||||||
|
else config.dir.unit
|
||||||
|
);
|
||||||
};
|
};
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -92,7 +100,22 @@ let
|
|||||||
};
|
};
|
||||||
};
|
};
|
||||||
|
|
||||||
# given a fsEntry definition, output the `config` attrs it generates.
|
symlinkEntryFor = path: types.submodule {
|
||||||
|
options = {
|
||||||
|
target = mkOption {
|
||||||
|
type = types.str;
|
||||||
|
description = "fs path to link to";
|
||||||
|
default = null;
|
||||||
|
};
|
||||||
|
unit = mkOption {
|
||||||
|
type = types.str;
|
||||||
|
description = "name of the systemd unit which mounts this path";
|
||||||
|
default = mountNameFor path;
|
||||||
|
};
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
|
# given a dirEntry definition, evaluate its toplevel `config` output.
|
||||||
mkDirConfig = path: opt: {
|
mkDirConfig = path: opt: {
|
||||||
systemd.services."${serviceNameFor path}" = {
|
systemd.services."${serviceNameFor path}" = {
|
||||||
description = "prepare ${path}";
|
description = "prepare ${path}";
|
||||||
@@ -112,6 +135,7 @@ let
|
|||||||
};
|
};
|
||||||
};
|
};
|
||||||
|
|
||||||
|
# given a mountEntry definition, evaluate its toplevel `config` output.
|
||||||
mkMountConfig = path: opt: (let
|
mkMountConfig = path: opt: (let
|
||||||
underlying = cfg."${opt.mount.bind}";
|
underlying = cfg."${opt.mount.bind}";
|
||||||
in {
|
in {
|
||||||
@@ -131,8 +155,29 @@ let
|
|||||||
};
|
};
|
||||||
});
|
});
|
||||||
|
|
||||||
|
# given a symlinkEntry definition, evaluate its toplevel `config` output.
|
||||||
|
mkSymlinkConfig = path: opt: {
|
||||||
|
systemd.services."${serviceNameFor path}" = {
|
||||||
|
description = "prepare ${path}";
|
||||||
|
serviceConfig.Type = "oneshot";
|
||||||
|
|
||||||
|
script = ensure-symlink-script;
|
||||||
|
scriptArgs = "${path} ${opt.target}";
|
||||||
|
|
||||||
|
after = opt.dir.depends;
|
||||||
|
wants = opt.dir.depends;
|
||||||
|
# prevent systemd making this unit implicitly dependent on sysinit.target.
|
||||||
|
# see: <https://www.freedesktop.org/software/systemd/man/systemd.special.html>
|
||||||
|
unitConfig.DefaultDependencies = "no";
|
||||||
|
|
||||||
|
wantedBy = opt.dir.reverseDepends;
|
||||||
|
before = opt.dir.reverseDepends;
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
mkFsConfig = path: opt: mergeTopLevel [
|
mkFsConfig = path: opt: mergeTopLevel [
|
||||||
(mkDirConfig path opt)
|
(mkDirConfig path opt)
|
||||||
|
(lib.mkIf (opt.symlink != null) (mkSymlinkConfig path opt))
|
||||||
(lib.mkIf (opt.mount != null) (mkMountConfig path opt))
|
(lib.mkIf (opt.mount != null) (mkMountConfig path opt))
|
||||||
];
|
];
|
||||||
|
|
||||||
@@ -167,6 +212,14 @@ let
|
|||||||
chown "$user:$group" "$path"
|
chown "$user:$group" "$path"
|
||||||
'';
|
'';
|
||||||
|
|
||||||
|
# systemd/shell script used to create a symlink
|
||||||
|
ensure-symlink-script = ''
|
||||||
|
from="$1"
|
||||||
|
to="$2"
|
||||||
|
|
||||||
|
ln -sf "$2" "$1"
|
||||||
|
'';
|
||||||
|
|
||||||
# return all ancestors of this path.
|
# return all ancestors of this path.
|
||||||
# e.g. ancestorsOf "/foo/bar/baz" => [ "/" "/foo" "/foo/bar" ]
|
# e.g. ancestorsOf "/foo/bar/baz" => [ "/" "/foo" "/foo/bar" ]
|
||||||
ancestorsOf = path: if path-lib.hasParent path then
|
ancestorsOf = path: if path-lib.hasParent path then
|
||||||
|
Reference in New Issue
Block a user