nixos/newt: init

This commit is contained in:
jack 2025-06-05 22:21:58 +02:00
parent d5418126dd
commit 9501130c38
3 changed files with 168 additions and 0 deletions

View File

@ -40,6 +40,8 @@
- [postfix-tlspol](https://github.com/Zuplu/postfix-tlspol), MTA-STS and DANE resolver and TLS policy server for Postfix. Available as [services.postfix-tlspol](#opt-services.postfix-tlspol.enable).
- [Newt](https://github.com/fosrl/newt), a fully user space WireGuard tunnel client and TCP/UDP proxy, designed to securely expose private resources controlled by Pangolin. Available as [services.newt](options.html#opt-services.newt.enable).
- [Szurubooru](https://github.com/rr-/szurubooru), an image board engine inspired by services such as Danbooru, dedicated for small and medium communities. Available as [services.szurubooru](#opt-services.szurubooru.enable).
- The [Neat IP Address Planner](https://spritelink.github.io/NIPAP/) (NIPAP) can now be enabled through [services.nipap.enable](#opt-services.nipap.enable).

View File

@ -1241,6 +1241,7 @@
./services/networking/netclient.nix
./services/networking/networkd-dispatcher.nix
./services/networking/networkmanager.nix
./services/networking/newt.nix
./services/networking/nextdns.nix
./services/networking/nftables.nix
./services/networking/nghttpx/default.nix

View File

@ -0,0 +1,165 @@
{
config,
lib,
pkgs,
...
}:
let
cfg = config.services.newt;
in
{
options = {
services.newt = {
enable = lib.mkEnableOption "Newt, user space tunnel client for Pangolin";
# needs to be changed when newt-go changes to fosrl-newt
package = lib.mkPackageOption pkgs "newt-go" { };
id = lib.mkOption {
type = with lib.types; nullOr str;
default = null;
description = ''
The Newt Id that will be used to communicate to Pangolin. This is generated on site creation in the dashboard.
'';
};
endpoint = lib.mkOption {
type = with lib.types; nullOr str;
default = null;
description = ''
The endpoint where both Gerbil and Pangolin reside in order to connect to the websocket. The url of your Pangolin dashboard.
'';
};
logLevel = lib.mkOption {
type = lib.types.enum [
"DEBUG"
"INFO"
"WARN"
"ERROR"
"FATAL"
];
default = "INFO";
description = "The log level to use.";
};
# provide path to file to keep secrets out of the nix store
environmentFile = lib.mkOption {
type = with lib.types; nullOr path;
default = null;
description = ''
Path to a file containing sensitive environment variables for Newt. See https://docs.fossorial.io/Newt/overview#cli-args
These will overwrite anything defined in the config.
The file should contain environment-variable assignments like:
NEWT_ID=2ix2t8xk22ubpfy
NEWT_SECRET=nnisrfsdfc7prqsp9ewo1dvtvci50j5uiqotez00dgap0ii2
'';
};
};
};
config = lib.mkIf cfg.enable {
assertions = [
{
assertion = cfg.environmentFile != null;
message = "services.newt.environmentFile must be provided when Newt is enabled.";
}
];
systemd.services.newt = {
description = "Newt, user space tunnel client for Pangolin";
wantedBy = [ "multi-user.target" ];
after = [ "network.target" ];
environment = {
HOME = "/var/lib/private/newt";
};
# the flag values will all be overwritten if also defined in the env file
script = "
exec ${lib.getExe pkgs.newt-go} \\\n
${lib.optionalString (
!isNull cfg.id
) "--id ${cfg.id} \\\n"}
${lib.optionalString (
!isNull cfg.endpoint
) "--endpoint ${cfg.endpoint} \\\n"}
--log-level ${cfg.logLevel}
";
serviceConfig = {
DynamicUser = true;
StateDirectory = "newt";
StateDirectoryMode = "0700";
Restart = "always";
RestartSec = "10s";
EnvironmentFile = cfg.environmentFile;
# hardening
ProtectSystem = "strict";
ProtectHome = true;
PrivateTmp = "disconnected";
PrivateDevices = true;
PrivateUsers = true;
PrivateMounts = true;
ProtectKernelTunables = true;
ProtectKernelModules = true;
ProtectKernelLogs = true;
ProtectControlGroups = true;
LockPersonality = true;
RestrictRealtime = true;
ProtectClock = true;
ProtectProc = "noaccess";
ProtectHostname = true;
RemoveIPC = true;
NoNewPrivileges = true;
RestrictSUIDSGID = true;
MemoryDenyWriteExecute = true;
SystemCallArchitectures = "native";
UMask = "0077";
RestrictAddressFamilies = [
"AF_INET"
"AF_INET6"
"AF_NETLINK"
"AF_UNIX"
];
CapabilityBoundingSet = [
"~CAP_BLOCK_SUSPEND"
"~CAP_BPF"
"~CAP_CHOWN"
"~CAP_MKNOD"
"~CAP_NET_RAW"
"~CAP_PERFMON"
"~CAP_SYS_BOOT"
"~CAP_SYS_CHROOT"
"~CAP_SYS_MODULE"
"~CAP_SYS_NICE"
"~CAP_SYS_PACCT"
"~CAP_SYS_PTRACE"
"~CAP_SYS_TIME"
"~CAP_SYS_TTY_CONFIG"
"~CAP_SYSLOG"
"~CAP_WAKE_ALARM"
];
SystemCallFilter = [
"~@aio:EPERM"
"~@chown:EPERM"
"~@clock:EPERM"
"~@cpu-emulation:EPERM"
"~@debug:EPERM"
"~@keyring:EPERM"
"~@memlock:EPERM"
"~@module:EPERM"
"~@mount:EPERM"
"~@obsolete:EPERM"
"~@pkey:EPERM"
"~@privileged:EPERM"
"~@raw-io:EPERM"
"~@reboot:EPERM"
"~@resources:EPERM"
"~@sandbox:EPERM"
"~@setuid:EPERM"
"~@swap:EPERM"
"~@sync:EPERM"
"~@timer:EPERM"
];
};
};
};
meta.maintainers = with lib.maintainers; [ jackr ];
}