[Unit]
Description=Outline Distro — Shadowsocks + AmneziaWG VPN Server
Documentation=https://sourcecraft.dev/bigbes/outline-distro
After=network-online.target nss-lookup.target
Wants=network-online.target
[Service]
Type=simple
ExecStart=/usr/local/bin/outline-distro -c /etc/outline-distro/config.yaml
Restart=on-failure
RestartSec=5
WatchdogSec=60
# Logging — stdout/stderr go straight to journald.
# View with: journalctl -u outline-distro -f
# Filter errors: journalctl -u outline-distro -p err
StandardOutput=journal
StandardError=journal
SyslogIdentifier=outline-distro
# File descriptors
LimitNOFILE=65536
# Run as dedicated user (created by install script)
User=outline-distro
Group=outline-distro
# Capabilities — needed for:
# CAP_NET_BIND_SERVICE — bind to ports < 1024 (AWG on 443, ACME on 80)
# CAP_NET_ADMIN — create/configure TUN device (AWG)
# CAP_NET_RAW — raw socket for UDP listeners
AmbientCapabilities=CAP_NET_BIND_SERVICE CAP_NET_ADMIN CAP_NET_RAW
CapabilityBoundingSet=CAP_NET_BIND_SERVICE CAP_NET_ADMIN CAP_NET_RAW
# Security hardening
NoNewPrivileges=yes
ProtectSystem=strict
ProtectHome=yes
PrivateTmp=yes
PrivateDevices=no
ProtectKernelTunables=yes
ProtectKernelModules=yes
ProtectControlGroups=yes
RestrictSUIDSGID=yes
RestrictNamespaces=yes
RestrictRealtime=yes
LockPersonality=yes
MemoryDenyWriteExecute=yes
RemoveIPC=yes
SystemCallArchitectures=native
# Writable paths for state, certs, and TUN device
ReadWritePaths=/var/lib/outline-distro /etc/outline-distro /dev/net/tun
# Allow /dev/net/tun access for AWG
DeviceAllow=/dev/net/tun rw
[Install]
WantedBy=multi-user.target