Clean up cloudflared service configuration and fix user/permissions

This commit is contained in:
Julian Sutter 2025-07-18 22:14:48 -07:00
parent 8646e5a9f8
commit 8454109f64

View file

@ -7,16 +7,27 @@ let
remoteHost = "warp.ftl.host"; # Cloudflare hostname remoteHost = "warp.ftl.host"; # Cloudflare hostname
remoteTarget = "localhost:22"; # Where traffic routes to remoteTarget = "localhost:22"; # Where traffic routes to
localBindPort = 4401; # Local port exposed by cloudflared localBindPort = 4401; # Local port exposed by cloudflared
logPath = "/var/log/cloudflared/warp.log"; logDir = "/var/lib/cloudflared"; # Directory for logs
}; };
}; };
in { in {
# Install cloudflared # Install cloudflared
environment.systemPackages = with pkgs; [ cloudflared ]; environment.systemPackages = with pkgs; [ cloudflared ];
# Ensure /var/log/cloudflared exists # Define cloudflared user and group at the top level
users.users.cloudflared = {
isSystemUser = true;
group = "cloudflared";
description = "Cloudflared service user";
home = "/var/lib/cloudflared";
createHome = true;
};
users.groups.cloudflared = {};
# Ensure /var/lib/cloudflared exists with proper permissions
systemd.tmpfiles.rules = [ systemd.tmpfiles.rules = [
"d /var/log/cloudflared 0755 root root -" "d /var/lib/cloudflared 0755 cloudflared cloudflared -"
]; ];
# Systemd services per tunnel # Systemd services per tunnel
@ -25,41 +36,27 @@ in {
after = [ "network-online.target" ]; after = [ "network-online.target" ];
wants = [ "network-online.target" ]; wants = [ "network-online.target" ];
wantedBy = [ "multi-user.target" ]; wantedBy = [ "multi-user.target" ];
# Create directory for log files
preStart = ''
mkdir -p "$(dirname ${tunnel.logPath})"
touch ${tunnel.logPath}
chmod 644 ${tunnel.logPath}
'';
serviceConfig = { serviceConfig = {
ExecStart = "${pkgs.cloudflared}/bin/cloudflared access tcp --hostname ${tunnel.remoteHost} --url ${tunnel.remoteTarget} --port ${toString tunnel.localBindPort} --logfile ${tunnel.logPath}";
# The key setting to ensure the service stays running # The key setting to ensure the service stays running
Type = "simple"; Type = "simple";
ExecStart = "${pkgs.cloudflared}/bin/cloudflared access tcp --hostname ${tunnel.remoteHost} --url ${tunnel.remoteTarget} --port ${toString tunnel.localBindPort} --logfile ${tunnel.logDir}/${name}.log";
# Automatic restart
Restart = "always"; Restart = "always";
RestartSec = "5s"; RestartSec = "5s";
# Configure service to wait for network
After = [ "network-online.target" ]; # Run as cloudflared user
Wants = [ "network-online.target" ]; User = "cloudflared";
# Run as dedicated user for better security Group = "cloudflared";
DynamicUser = true;
# Configure systemd runtime directory
RuntimeDirectory = "cloudflared";
RuntimeDirectoryMode = "0700";
# Standard outputs # Standard outputs
StandardOutput = "journal"; StandardOutput = "journal";
StandardError = "journal"; StandardError = "journal";
}; };
}) tunnels; }) tunnels;
# Activation step to ensure log directory exists # Documentation metadata
system.activationScripts.cloudflaredLogs = lib.stringAfter [ "users" ] ''
mkdir -p /var/log/cloudflared
chmod 755 /var/log/cloudflared
'';
# Optional documentation metadata
meta.doc = '' meta.doc = ''
This module defines persistent cloudflared TCP tunnels using access tcp. This module defines persistent cloudflared TCP tunnels using access tcp.
Add tunnels by appending to the `tunnels` attribute set. Add tunnels by appending to the `tunnels` attribute set.
@ -68,6 +65,6 @@ in {
- remoteHost: The public hostname exposed via Cloudflare Tunnel. - remoteHost: The public hostname exposed via Cloudflare Tunnel.
- remoteTarget: The internal service to forward traffic to (e.g. localhost:22). - remoteTarget: The internal service to forward traffic to (e.g. localhost:22).
- localBindPort: The port to expose locally (e.g. 4401). - localBindPort: The port to expose locally (e.g. 4401).
- logPath: File path to capture logs. - logDir: Directory path for log files.
''; '';
} }