mirror of
https://git.pvv.ntnu.no/Drift/pvv-nixos-config.git
synced 2026-03-27 01:57:33 +01:00
This also fixes a few issues, such as enabling `createLocalDatabase` for multiple programs, and wraps all the screen logic within a screenrc file. Some assertions were also added to avoid some easy-to-make mistakes.
199 lines
5.3 KiB
Nix
199 lines
5.3 KiB
Nix
{
|
|
config,
|
|
pkgs,
|
|
lib,
|
|
...
|
|
}:
|
|
let
|
|
cfg = config.services.drumknotty;
|
|
in
|
|
{
|
|
imports = [
|
|
./dibbler.nix
|
|
./worblehat.nix
|
|
];
|
|
|
|
options.services.drumknotty = {
|
|
enable = lib.mkEnableOption "DrumknoTTY";
|
|
|
|
kioskMode = lib.mkEnableOption "" // {
|
|
description = ''
|
|
Whether to let dibbler take over the entire machine.
|
|
|
|
This will restrict the machine to a single TTY and make the program unquittable.
|
|
You can still get access to PTYs via SSH and similar, if enabled.
|
|
'';
|
|
};
|
|
|
|
screen = {
|
|
package = lib.mkPackageOption pkgs "screen" { };
|
|
|
|
sessionName = lib.mkOption {
|
|
type = lib.types.str;
|
|
default = "drumknotty";
|
|
example = "myscreensessionname";
|
|
description = ''
|
|
Sets the screen session name.
|
|
'';
|
|
};
|
|
|
|
limitHeight = lib.mkOption {
|
|
type = with lib.types; nullOr ints.unsigned;
|
|
default = null;
|
|
example = 42;
|
|
description = ''
|
|
If set, limits the height of the screen dibbler uses to the given number of lines.
|
|
'';
|
|
};
|
|
|
|
limitWidth = lib.mkOption {
|
|
type = with lib.types; nullOr ints.unsigned;
|
|
default = null;
|
|
example = 80;
|
|
description = ''
|
|
If set, limits the width of the screen dibbler uses to the given number of columns.
|
|
'';
|
|
};
|
|
};
|
|
};
|
|
|
|
config = lib.mkIf cfg.enable {
|
|
assertions = [
|
|
{
|
|
assertion = cfg.enable -> lib.any (b: b) [
|
|
cfg.dibbler.enable
|
|
cfg.worblehat.enable
|
|
];
|
|
message = "DrumknoTTY must have at least one service enabled";
|
|
}
|
|
];
|
|
|
|
users = {
|
|
users.drumknotty = {
|
|
group = "drumknotty";
|
|
extraGroups = [ "lp" ];
|
|
isNormalUser = true;
|
|
|
|
# TODO: make this display the error log or error message in case that
|
|
# the screen session service is bootlooping or otherwise off.
|
|
shell =
|
|
lib.mkIf cfg.kioskMode
|
|
(pkgs.writeShellScriptBin "login-shell"
|
|
"${lib.getExe' cfg.screen.package "screen"} -x ${cfg.screen.sessionName} -p dibbler"
|
|
// {
|
|
shellPath = "/bin/login-shell";
|
|
});
|
|
};
|
|
groups.drumknotty = { };
|
|
};
|
|
|
|
boot.kernelParams = lib.mkIf cfg.kioskMode [
|
|
"console=tty1"
|
|
];
|
|
|
|
services.getty.autologinUser = lib.mkIf cfg.kioskMode "drumknotty";
|
|
|
|
systemd.services.drumknotty-screen-session = lib.mkIf cfg.kioskMode {
|
|
description = "Drumknotty Screen Session";
|
|
wantedBy = [
|
|
"default.target"
|
|
];
|
|
after =
|
|
# TODO: this could be refined
|
|
if (cfg.dibbler.createLocalDatabase || cfg.worblehat.createLocalDatabase) then
|
|
[
|
|
"postgresql.service"
|
|
"dibbler-setup-database.service"
|
|
"worblehat-setup-database.service"
|
|
]
|
|
else
|
|
[
|
|
"network.target"
|
|
];
|
|
|
|
serviceConfig = {
|
|
Type = "forking";
|
|
RemainAfterExit = false;
|
|
Restart = "always";
|
|
RestartSec = "5s";
|
|
SuccessExitStatus = 1;
|
|
|
|
User = "drumknotty";
|
|
Group = "drumknotty";
|
|
|
|
ExecStartPre =
|
|
let
|
|
screenArgs = lib.escapeShellArgs [
|
|
# Send the specified command to a running screen session
|
|
"-X"
|
|
|
|
# Session name
|
|
"-S"
|
|
"${cfg.screen.sessionName}"
|
|
|
|
"kill"
|
|
];
|
|
in
|
|
"-${lib.getExe' cfg.screen.package "screen"} ${screenArgs}";
|
|
|
|
ExecStart =
|
|
let
|
|
screenrc = let
|
|
convertToFile = lines: lib.pipe lines [
|
|
lib.concatLists
|
|
(lib.concatStringsSep "\n")
|
|
(pkgs.writeText "drumknotty-screenrc")
|
|
];
|
|
in convertToFile [
|
|
(lib.optionals (cfg.screen.limitWidth != null) [
|
|
"screen width ${toString cfg.screen.limitWidth}"
|
|
])
|
|
(lib.optionals (cfg.screen.limitHeight != null) [
|
|
"screen height ${toString cfg.screen.limitHeight}"
|
|
])
|
|
|
|
(let
|
|
dibblerArgs = lib.cli.toCommandLineShellGNU { } {
|
|
config = "/etc/dibbler/dibbler.toml";
|
|
};
|
|
in lib.optionals cfg.dibbler.enable [
|
|
"screen -t worblehat ${lib.getExe cfg.dibbler.package} ${dibblerArgs} loop"
|
|
|
|
])
|
|
|
|
(let
|
|
worblehatArgs = lib.cli.toCommandLineShellGNU { } {
|
|
config = "/etc/worblehat/config.toml";
|
|
};
|
|
in lib.optionals cfg.worblehat.enable [
|
|
"screen -t worblehat ${lib.getExe cfg.worblehat.package} ${worblehatArgs} cli"
|
|
])
|
|
|
|
[ "select 0" ]
|
|
];
|
|
|
|
screenArgs = lib.escapeShellArgs [
|
|
# -dm creates the screen in detached mode without accessing it
|
|
"-dm"
|
|
|
|
# Session name
|
|
"-S"
|
|
"${cfg.screen.sessionName}"
|
|
|
|
# Set optimal output mode instead of VT100 emulation
|
|
"-O"
|
|
|
|
# Enable login mode, updates utmp entries
|
|
"-l"
|
|
|
|
# Config file path
|
|
"-c"
|
|
"${screenrc}"
|
|
];
|
|
in
|
|
"${lib.getExe' cfg.screen.package "screen"} ${screenArgs}";
|
|
};
|
|
};
|
|
};
|
|
}
|