Installation Guide
Step-by-step instructions to install SparkBox on a UGREEN NAS, VPS, or any server with Docker.
Prerequisites
For VPS
- Server running Ubuntu 22.04+ or Debian 12+
- Minimum: 2GB RAM, 1 vCPU, 20GB disk
- Recommended: 4-8GB RAM, 2-4 vCPU
- Root or sudo access
- SSH client (Terminal on Mac/Linux, PuTTY or Windows Terminal on Windows)
- Domain name (optional -- not needed if using Tailscale)
- VPN subscription (only if enabling the Media Center module)
For NAS
- UGREEN NASync NAS (DXP2800, DXP4800, or similar Docker-capable model)
- 4GB+ RAM (8GB recommended, 16GB for media + Immich)
- SSH access enabled on the NAS
- VPN subscription (only if enabling the Media Center module)
Windows / WSL2: SparkBox also works on Windows via WSL2 (Windows Subsystem for Linux). This is community-supported and not officially tested. Install Ubuntu from the Microsoft Store, then follow the VPS installation steps inside WSL2.
VPS Installation
Step 1: Connect to Your Server
ssh root@YOUR_SERVER_IP
If your provider set up a non-root user:
ssh youruser@YOUR_SERVER_IP
sudo -i # Switch to root
Step 2: Update Your System
apt update && apt upgrade -y
Step 3: Run the Installer
Quick Install (Recommended)
curl -sSL https://get.sparkbox.app/install.sh | sudo bash
This automatically:
- Installs Docker and required system packages
- Downloads SparkBox to
/opt/sparkbox - Configures the firewall (ports 22, 80, 443, 51820/udp)
- Launches the setup wizard
Manual Install
# Install Docker
curl -fsSL https://get.docker.com | sh
# Clone the repository
git clone https://github.com/tomsparkreview/sparkbox /opt/sparkbox
cd /opt/sparkbox
# Install dashboard dependencies
cd dashboard && npm install --production && cd ..
# Make the CLI executable and link it
chmod +x sparkbox
ln -sf /opt/sparkbox/sparkbox /usr/local/bin/sparkbox
# Run the setup wizard
sudo sparkbox install
Step 4: Setup Wizard
The wizard launches automatically after installation. See the Setup Wizard section below for details.
VPS Provider Recommendation
SparkBox runs on any VPS. We recommend Hostinger for the best balance of price, performance, and reliability. Other popular options:
| Provider | Minimum Plan | Notes |
|---|---|---|
| Hostinger | KVM 1 (4GB, 2 vCPU) ~$5/mo | Recommended -- fast, affordable, global locations |
| Hetzner | CX22 (4GB, 2 vCPU) ~$5/mo | Best value, EU + US locations |
| DigitalOcean | Basic 4GB ~$24/mo | Simple, reliable |
| Vultr | Cloud Compute 4GB ~$24/mo | Global locations |
| Contabo | VPS S 8GB ~$7/mo | Budget option, more RAM |
UGREEN NAS (DXP2800, DXP4800, etc.)
Before installing SparkBox on a UGREEN NAS, complete the privacy lockdown steps in the NAS Guide. This disables telemetry, blocks phone-home connections, and secures your device.
Step 1: Enable SSH
- Open the UGOS web interface in your browser
- Go to Control Panel > Terminal
- Check "Enable SSH Service"
- Leave port on 22
- Click Apply
- Restart the NAS -- SSH does not start listening until after a reboot
Step 2: Connect via SSH
Use PuTTY, not Windows' built-in SSH client. Windows' ssh command in PowerShell/Command Prompt often fails with "Permission denied" when VPN adapters (NordVPN, Surfshark, etc.) are installed. Download PuTTY from putty.org (single .exe, no install needed).
PuTTY settings:
- Host: Your NAS IP (e.g.,
192.168.1.17) - Port:
22 - Click Open
- Log in with your UGOS admin username and password
On Mac/Linux, the regular terminal SSH client works fine:
ssh your-admin-username@192.168.1.17
Step 3: Install Docker (if not already installed)
UGREEN NAS typically comes with Docker pre-installed. Verify:
docker --version
docker compose version
If Docker is missing:
curl -fsSL https://get.docker.com | sh
Step 4: Install SparkBox
sudo git clone https://github.com/tomsparkreview/sparkbox /opt/sparkbox
cd /opt/sparkbox
sudo chmod +x sparkbox
sudo ./sparkbox install
Note on UGREEN: The installer detects NAS environments and skips UFW firewall configuration (UGOS has its own firewall, plus you should have a router-level block per the NAS Guide). It also adjusts default ports to avoid conflicts with UGOS services.
Step 5: Handle Port Conflicts
UGOS uses several ports that conflict with SparkBox defaults:
| Port | Used By | SparkBox Default | Resolution |
|---|---|---|---|
| 80 | UGOS web UI | Nginx Proxy Manager HTTP | SparkBox uses 8080 on NAS |
| 443 | UGOS web UI | Nginx Proxy Manager HTTPS | SparkBox uses 8443 on NAS |
| 53 | dnsmasq (UGOS) | Pi-hole DNS | Disable dnsmasq: sudo systemctl disable dnsmasq |
| 5000/5001 | UGOS management | Not used | No conflict |
The installer handles port remapping automatically on detected NAS environments. See the Port Conflict Resolution section in the NAS Guide for manual port configuration.
Setup Wizard
The setup wizard runs automatically after installation. Here is what each step configures:
Server Address
Enter your server's IP address or domain name.
- No domain? Use your server's IP (e.g.,
203.0.113.42for VPS,192.168.1.17for NAS) - Have a domain? Enter it (e.g.,
myserver.example.com)
Timezone
Enter your timezone in Continent/City format:
| Region | Timezone |
|---|---|
| US Eastern | America/New_York |
| US Central | America/Chicago |
| US Pacific | America/Los_Angeles |
| UK | Europe/London |
| Central Europe | Europe/Berlin |
| Japan | Asia/Tokyo |
| Australia | Australia/Sydney |
Module Selection
After choosing a profile, you can toggle individual modules on or off. Use arrow keys to navigate, space to toggle, Enter to confirm.
VPN Credentials (Media Profile)
If you selected Media or Full profile, enter your VPN provider and credentials. See the VPN Provider Setup section in the Media Guide for step-by-step credential extraction for each provider.
Dashboard Password
Set a password for the SparkBox web dashboard. Leave blank to auto-generate one (saved to the credentials file).
Module Configuration
Depending on your selections:
- Privacy enabled: Set a Pi-hole admin password (or auto-generate)
- VPN Access enabled: Set a WireGuard web UI password (or auto-generate)
- Cloud enabled: Database passwords are auto-generated
Deploy
Say Yes to deploy immediately. SparkBox pulls container images and starts your services. This takes 2-10 minutes depending on internet speed and how many modules you enabled.
Profile Selection
Privacy Profile
Best for: VPS users focused on security and ad-blocking.
Modules enabled: Core, Dashboard, Privacy (Pi-hole + Vaultwarden + Authelia), Monitoring (Uptime Kuma), VPN Access (WireGuard)
Total RAM: ~750MB idle
Media Profile
Best for: Home server or NAS users building a private streaming platform.
Modules enabled: Core, Dashboard, Media Center (Gluetun + qBittorrent + Prowlarr + Sonarr + Radarr + Bazarr + Jellyfin + Seerr)
Total RAM: ~2.5GB idle
Requires: A VPN subscription (Surfshark, NordVPN, ProtonVPN, Mullvad, AirVPN, etc.)
Full Profile
Best for: Servers with 8GB+ RAM that want everything.
Modules enabled: All Privacy + Media modules, plus Cloud (Nextcloud), Paperless-ngx, File Browser, Monitoring, and more.
Total RAM: ~5-6GB idle
Custom Profile
Pick exactly what you want from the module catalog. Start with Core + Dashboard, add modules one at a time.
Post-Install
Accessing the Dashboard
Once deployment completes, open your browser:
http://YOUR_SERVER_IP:8443
Log in with the password you set during installation.
Finding Auto-Generated Credentials
If passwords were auto-generated during setup:
cat /opt/sparkbox/state/initial-credentials.txt
Save these passwords somewhere safe (e.g., Vaultwarden), then delete the file:
rm /opt/sparkbox/state/initial-credentials.txt
Verify All Services
sparkbox status
All enabled services should show as running. If any service is stopped, check its logs:
sparkbox logs sb-SERVICE_NAME
Post-Install Checklist
- Open the dashboard at
http://YOUR_SERVER:8443and verify login works - Change the NPM default password (open
http://YOUR_SERVER:81, login:admin@example.com/changeme) - Save your auto-generated credentials, then delete
initial-credentials.txt - If using Privacy: set your router or device DNS to your server's IP for ad-blocking
- If using Privacy: open Vaultwarden, create your account, install the Bitwarden browser extension
- If using Media: add your VPN credentials, configure Prowlarr indexers (see Prowlarr)
- If using Cloud: complete Nextcloud first-run wizard, set up domain + SSL first
- If using WireGuard: create client configs and scan QR codes on your devices
- If using Monitoring: add service monitors in Uptime Kuma, set up notifications
- Set up a domain for SSL (see below) or enable Tailscale for remote access
- Create your first backup:
sparkbox backup
Domain Setup with Nginx Proxy Manager
A domain lets you access services via URLs like vault.yourdomain.com instead of remembering port numbers. It also provides HTTPS encryption and is required for Nextcloud mobile apps.
Step 1: Get a Domain
Register a domain from any registrar (Cloudflare, Namecheap, Porkbun, etc.). Cost: ~$10/year.
Step 2: Create DNS Records
In your registrar's DNS settings, create an A record:
Type: A
Name: * (wildcard)
Value: YOUR_SERVER_IP
TTL: 300 (or Auto)
Step 3: Configure Nginx Proxy Manager
- Open NPM at
http://YOUR_SERVER:81 - Default login:
admin@example.com/changeme - Change the default password immediately
- Click Proxy Hosts > Add Proxy Host
- For each service:
- Domain Names:
vault.yourdomain.com - Forward Hostname / IP:
sb-vaultwarden(the container name) - Forward Port:
80(the container's internal port) - SSL tab: Request a new SSL certificate, check "Force SSL", agree to Let's Encrypt ToS
- Domain Names:
Suggested Subdomains
| Service | Subdomain | Container | Forward Port |
|---|---|---|---|
| Dashboard | dash.yourdomain.com | sb-dashboard | 8443 |
| Pi-hole | pihole.yourdomain.com | sb-pihole | 80 |
| Vaultwarden | vault.yourdomain.com | sb-vaultwarden | 80 |
| Nextcloud | cloud.yourdomain.com | sb-nextcloud | 443 |
| Jellyfin | watch.yourdomain.com | sb-jellyfin-media | 8096 |
| Seerr | request.yourdomain.com | sb-seerr | 5055 |
| Bazarr | subs.yourdomain.com | sb-bazarr | 6767 |
| Uptime Kuma | status.yourdomain.com | sb-uptime-kuma | 3001 |
| WireGuard | vpn.yourdomain.com | sb-wg-easy | 51821 |
| File Browser | files.yourdomain.com | sb-filebrowser | 80 |
Note: VPN-routed services (qBittorrent, Sonarr, Radarr, Prowlarr) are not on the sb_proxy network because they share Gluetun's network namespace. To proxy them through NPM, use your server's LAN IP or host.docker.internal as the hostname with the host-mapped port.
Remote Access
Option 1: Tailscale (Recommended)
Tailscale is the easiest way to access SparkBox from anywhere. It creates a secure mesh VPN using WireGuard under the hood, with zero configuration.
Enable the Tailscale Module
sparkbox enable tailscale
Get an Auth Key
- Go to https://login.tailscale.com/admin/settings/keys
- Create a new auth key (reusable is recommended)
- Copy the key
Configure and Start
# Add to /opt/sparkbox/.env
TS_AUTHKEY=tskey-auth-xxxxx
sparkbox up
All your services are now accessible at your Tailscale IP (e.g., http://100.x.x.x:8443 for the dashboard).
Tailscale on a NAS with Internet Blocked
If you followed the NAS privacy lockdown (blocking internet at the router):
- Temporarily disable the router firewall rule blocking the NAS
- Install and authenticate Tailscale
- Re-enable the router firewall rule
After initial authentication, Tailscale tunnels directly between devices -- the NAS does not need internet access to maintain the connection.
Option 2: WireGuard VPN (Self-Hosted)
Enable the VPN Module
sparkbox enable vpn
sparkbox up
Create a Client
- Open wg-easy at
http://YOUR_SERVER:51821 - Log in with your WireGuard password
- Click New Client and give it a name (e.g., "My Phone")
- Click the QR code icon
Connect
- Install the WireGuard app on your phone (iOS / Android)
- Tap Add Tunnel > Scan QR Code
- Scan the QR code from wg-easy
- Connect
Firewall note: Port 51820/UDP must be open. The installer configures this automatically on VPS. On NAS, you may need to forward this port on your router.
Option 3: Domain + Nginx Proxy Manager
For public-facing servers. See Domain Setup above.
CLI Quick Reference
sparkbox status # See what's running
sparkbox up # Start all enabled modules
sparkbox down # Stop everything
sparkbox restart # Restart all services
sparkbox restart privacy # Restart just one module
sparkbox update # Pull latest images
sparkbox logs sb-NAME # View service logs
sparkbox modules # List all modules
sparkbox enable cloud # Enable a module
sparkbox disable files # Disable a module
sparkbox backup # Create a backup
sparkbox restore FILE # Restore from backup
sparkbox urls # Show all service URLs
sparkbox help # Full command list
Updating
Update All Services
sparkbox update
This pulls the latest Docker images and recreates all containers. Your data and configuration are preserved.
Update a Specific Module
sparkbox update privacy
Update SparkBox Itself
cd /opt/sparkbox && git pull && sparkbox update
Backups
Create a Backup
sparkbox backup
Or from the dashboard: Settings > Backups > Create Backup Now
Restore from Backup
sparkbox restore /opt/sparkbox/backups/sparkbox-backup-TIMESTAMP.tar.gz
Backups include your configuration, module settings, and service data. Backups are automatically encrypted with AES-256-GCM when SB_BACKUP_KEY is set (done automatically during installation).
Note: Media files (movies, TV shows, music) are NOT included in backups due to size. Back those up separately.
Uninstalling
sparkbox down
rm -rf /opt/sparkbox
rm -f /usr/local/bin/sparkbox
This stops all containers and removes SparkBox. Docker remains installed.
Troubleshooting
Solutions for common issues across all SparkBox modules, organized by category.
Gluetun VPN Issues
Gluetun Is Unhealthy / Won't Connect
Symptoms: sb-gluetun shows "unhealthy" in sparkbox status or the dashboard. Media services that depend on Gluetun are also down.
Check logs:
sparkbox logs sb-gluetun
Common causes and fixes:
- Wrong VPN credentials -- This is the most common cause. VPN service credentials are NOT your login email/password.
Where to find credentials:bash
# Edit your credentials nano /opt/sparkbox/.env # Fix VPN_PROVIDER, WIREGUARD_PRIVATE_KEY, etc. sparkbox restart media- Surfshark: Manual Setup > WireGuard
- NordVPN: Manual Configuration > NordLynx
- ProtonVPN: Account > Downloads > WireGuard
- Mullvad: Account > WireGuard
- VPN subscription expired -- Verify your subscription is active with your provider.
- Corrupted Gluetun state -- Reset Gluetun's local data:
bash
sparkbox down rm -rf /opt/sparkbox/modules/media/config/gluetun sparkbox up - Server country unavailable -- Try a different country:
bash
# Edit .env SERVER_COUNTRIES=Netherlands sparkbox restart media - NAS internet blocked -- If you blocked internet at the router (per NAS Guide), you need a firewall exception for the VPN port. See Firewall and VPN Coexistence.
VPN Connected but Wrong Country
# Check current VPN location
docker exec sb-gluetun wget -qO- ipinfo.io
# Change country in .env
nano /opt/sparkbox/.env
# Change SERVER_COUNTRIES=United States to your preferred country
sparkbox restart media
VPN Connected but No Internet Through Tunnel
Symptoms: Gluetun shows "healthy" but qBittorrent cannot download and Prowlarr cannot reach indexers.
# Test internet connectivity from inside Gluetun
docker exec sb-gluetun wget -qO- --timeout=10 ifconfig.me
# If that fails, check DNS
docker exec sb-gluetun nslookup google.com
Fixes:
- Restart the media module:
sparkbox restart media - Check if your VPN provider is having an outage
- Try a different server country
qBittorrent Issues
Can't Log In to qBittorrent
qBittorrent generates a temporary password every time it starts.
docker logs sb-qbittorrent 2>&1 | grep "temporary password"
Default username is admin. After logging in, set a permanent password in Tools > Options > Web UI.
qBittorrent Can't Connect / No Downloads
- Check Gluetun is healthy:
If Gluetun is unhealthy, fix it first (see above).bash
docker ps --format "table {{.Names}}\t{{.Status}}" | grep gluetun - Verify VPN tunneling:
bash
docker exec sb-gluetun wget -qO- ifconfig.me - Check network interface: In qBittorrent, go to Tools > Options > Advanced > Network Interface -- it should be
tun0.
Downloads Are Slow
- VPN server too far away: Change
SERVER_COUNTRIESin.envto a closer country, thensparkbox restart media - Not enough seeders: Check the torrent in qBittorrent -- if it shows 0 seeds, try an alternative release in Radarr/Sonarr
- VPN throttling: Some VPN providers throttle torrents. Try a different server or provider
Arr App Issues (Radarr, Sonarr, Prowlarr)
"Root Folder Does Not Exist" in Radarr/Sonarr
The /data directory structure has not been created.
sudo mkdir -p /data/{torrents/{movies,tv,music},media/{movies,tv,music}}
sudo chown -R $(id -u):$(id -g) /data
sudo chmod -R 775 /data
Verify the root folder paths:
- Radarr:
/data/media/movies - Sonarr:
/data/media/tv - Lidarr:
/data/media/music
Downloads Stuck at "Importing" or "Waiting to Import"
This is almost always a permissions issue.
sudo chown -R $(id -u):$(id -g) /data
sudo chmod -R 775 /data
Also verify PUID/PGID in .env matches your user:
id
# Compare uid/gid with PUID/PGID in /opt/sparkbox/.env
No Indexers in Radarr/Sonarr
Indexers are managed by Prowlarr and synced automatically.
- Open Prowlarr at
http://YOUR_SERVER:8181 - Verify you have indexers added under Indexers
- Check Settings > Apps -- Radarr and Sonarr should be listed
- Click Sync App Indexers to force a sync
- Verify the API keys match between Prowlarr and Radarr/Sonarr
Services Can't Connect to Each Other
Do NOT use localhost when connecting services together across Docker containers. Use internal Docker IPs instead. See the Docker Networking reference in the Media Guide.
Jellyfin Issues
Empty Library After Downloads Finish
- Check library paths: Jellyfin libraries should point to:
- Movies:
/data/media/movies - TV Shows:
/data/media/tv - Music:
/data/media/music
- Movies:
- Force a library scan: Go to Dashboard > Libraries > click
...> Scan Library - Check if files exist:
bash
ls -la /data/media/movies/ ls -la /data/media/tv/
No Hardware Transcoding
Symptoms: Playback is slow or stuttering. Dashboard shows software transcoding (no "(HW)" indicator).
- Check /dev/dri exists:
bash
ls -la /dev/dri/ - Verify device mapping: The Jellyfin container must have
/dev/dri:/dev/drimapped. - Verify Jellyfin settings: Dashboard > Playback > Transcoding > Hardware acceleration: VAAPI, VA-API Device:
/dev/dri/renderD128
See Hardware Transcoding in the NAS Guide for full setup.
Jellyfin App Can't Connect
- On LAN: Use
http://YOUR_SERVER_IP:8096 - Remote via Tailscale: Use
http://YOUR_TAILSCALE_IP:8096 - With domain: Use
https://watch.yourdomain.com - Check Jellyfin is running:
sparkbox status
Port Conflicts
Finding What Uses a Port
# Show all listening ports
sudo ss -tlnp
# Check if a specific port is in use
sudo ss -tlnp | grep :80
Common Port Conflicts on NAS
| Port | Commonly Used By | SparkBox Service | Fix |
|---|---|---|---|
| 80 | NAS web UI (UGOS) | Nginx Proxy Manager | Set HTTP_PORT=8080 in .env |
| 443 | NAS web UI (HTTPS) | Nginx Proxy Manager | Set HTTPS_PORT=8443 in .env |
| 53 | NAS DNS (dnsmasq) | Pi-hole | Disable dnsmasq |
| 5055 | Various system services | Seerr | Change Seerr port in docker-compose.yml |
Changing SparkBox Ports
nano /opt/sparkbox/.env
# Change the relevant port variable
sparkbox restart
Permission Issues
PUID/PGID Mismatch
Symptoms: "Permission denied" errors in logs, files created with wrong ownership, imports failing.
# Find your user/group ID
id
# Check what's in .env
grep -E "PUID|PGID" /opt/sparkbox/.env
# Fix ownership
sudo chown -R 1000:1000 /data
sudo chown -R 1000:1000 /opt/sparkbox
# Restart
sparkbox restart
Docker Socket Permission Denied
# Add your user to the docker group (preferred)
sudo usermod -aG docker your-username
# Log out and back in for the change to take effect
NAS-Specific Issues
SSH Won't Connect (UGREEN)
- Verify SSH is enabled: UGOS web UI > Control Panel > Terminal > "Enable SSH Service" must be checked
- Restart the NAS: SSH may not start listening until after a reboot
- Use PuTTY, not Windows SSH: Windows' built-in SSH client fails when VPN adapters are installed. Download PuTTY
- Check SSH auto-disable: UGOS may auto-disable SSH after a timeout or firmware update
- Check the IP address: Make sure you are using the correct NAS IP from your router's DHCP client list
Firewall Blocking Services (UGREEN)
Skip the UGOS built-in firewall. In testing, it blocks SSH and Docker ports even when LAN traffic is explicitly allowed. Use router-level firewall rules instead.
Docker Not Working After NAS Firmware Update
# Check Docker is running
sudo systemctl status docker
# If stopped, start it
sudo systemctl start docker
sudo systemctl enable docker
# Check SparkBox services
sparkbox status
# If services are down, bring them up
sparkbox up
Also check: SSH is still enabled (may be reset by firmware update), dnsmasq is still disabled.
NAS Internet Block Breaking Docker Pulls
If you blocked internet at the router and need to pull Docker images:
- Temporarily disable the router firewall rule blocking the NAS
- Pull your images:
sparkbox updateordocker compose pull - Re-enable the router firewall rule
Dashboard Issues
Can't Log In to Dashboard
- Check the dashboard is running:
bash
sparkbox status | grep dashboard - Forgot password -- reset it:
This triggers the first-run password setup on next login.bash
nano /opt/sparkbox/.env # Find SB_ADMIN_PASSWORD_HASH= and delete the value (leave it blank) sparkbox restart dashboard - Browser cache issue: Try incognito/private browsing mode or clear your browser cache.
Disk Space Issues
Disk Filling Up
df -h
du -sh /data/torrents/*
du -sh /data/media/*
Common causes:
- qBittorrent keeping completed torrents: Enable auto-removal in Radarr/Sonarr > Settings > Download Clients > enable Remove Completed
- Hardlinks not working (double disk usage): Both
torrents/andmedia/must be on the same volume. See Check Hardlinks. - Docker images accumulating:
bash
docker image prune -a
How to Check VPN Is Working
# Get VPN IP (should NOT be your real IP)
docker exec sb-gluetun wget -qO- ifconfig.me
# Get your real IP (for comparison)
curl -s ifconfig.me
If both IPs are the same, the VPN is NOT working. Check Gluetun logs.
Full Verification
# Check VPN IP and location
docker exec sb-gluetun wget -qO- ipinfo.io
# Verify qBittorrent is tunneled (should match VPN IP)
docker exec sb-qbittorrent wget -qO- ifconfig.me
# Check Gluetun health status
docker inspect --format '{{.State.Health.Status}}' sb-gluetun
Continuous Monitoring
bash /opt/sparkbox/modules/media/test-media.sh
How to Check Hardlinks Are Working
Step 1: Verify Same Filesystem
df /data/torrents /data/media
Both must show the same device. If they show different devices, hardlinks will NOT work.
Step 2: Check Filesystem Type
df -T /data
Hardlinks work on: ext4, btrfs, xfs, zfs. Hardlinks do NOT work on: exFAT, ntfs-3g, fat32, network shares (NFS/SMB).
Step 3: Test Hardlink Creation
# Create a test file
touch /data/torrents/hardlink_test
# Create a hardlink
ln /data/torrents/hardlink_test /data/media/hardlink_test
# Verify -- inode numbers should match
ls -i /data/torrents/hardlink_test
ls -i /data/media/hardlink_test
# Clean up
rm /data/torrents/hardlink_test /data/media/hardlink_test
General Troubleshooting Steps
When something is not working and you are not sure where to start:
# 1. Check status
sparkbox status
# 2. Check logs for the failing service
sparkbox logs sb-SERVICE_NAME
# 3. Restart the module
sparkbox restart MODULE_NAME
# 4. Restart everything
sparkbox down
sparkbox up
# 5. Check system resources
free -h # RAM
df -h # Disk
top -bn1 | head -5 # CPU
NAS Guide
Everything you need to run SparkBox on a UGREEN NAS -- privacy lockdown, hardware transcoding, port conflicts, storage paths, and performance expectations.
Privacy Lockdown (Before Installing SparkBox)
Do this BEFORE installing SparkBox on a UGREEN NAS. UGOS Pro ships with telemetry enabled, cloud relay connections to Hong Kong, and DNS services that phone home. Lock it down first.
Why This Matters
UGREEN NAS devices (DXP2800, DXP4800, etc.) have several privacy concerns:
- Telemetry enabled by default -- tracks page visits, click behavior, IP address, device ID
- UGREENlink routes through Hong Kong -- relay servers transmit your device serial, hashed email, and device location
- Phones home even with remote access disabled -- DNS lookups to Chinese domains persist
- No disk encryption -- UGOS Pro has zero encryption at rest
- Known CVEs -- command injection, buffer overflow vulnerabilities published Dec 2025
Step-by-Step Lockdown
1. Disable Telemetry
Control Panel > Service > About > Device analysis tab
- Uncheck "Help UGREEN NAS improve its products and services"
- Click Apply
2. Disable WebFind
Same area -- uncheck "Enable WebFind". This unregisters your NAS from find.ugnas.com.
3. Disable UGREENlink
Control Panel > Remote Access
- Uncheck "UGREENlink remote access"
- Click Apply
After this, the UGREEN mobile and PC apps stop working outside your home network. They still work on LAN.
4. Handle Your UGREEN Cloud Account
Recommended: Leave the account bound but cut off access. Do NOT unbind the device -- UGREEN warns that unbinding removes all data. The account becomes useless once the firewall blocks internet in the next step.
5. Block the NAS from the Internet (Router Level)
This is the most important step. Block at your router so the NAS cannot bypass the block regardless of what UGOS does.
UniFi (Recommended):
- Go to Settings > Security > Traffic & Firewall Rules
- Create a new rule:
- Name: Block NAS Internet
- Action: Block
- Source: Your NAS IP address (e.g.,
192.168.1.17) - Destination: Internet
- Schedule: Always
- Save and apply
Pi-hole / AdGuard Home (domain-level blocking): If you want Docker to still pull images but block UGREEN domains:
*.ugnas.com
*.ug.link
*.ugreen.com
*.baidu.com
*.crashlytics.com
*.firebase.google.com
Skip the UGOS built-in firewall. In testing, it causes issues with SSH access even when LAN traffic is allowed. The router-level block is more reliable.
6. Enable SSH
Control Panel > Terminal -- Check "Enable SSH Service", leave port on 22, click Apply, then restart the NAS.
7. Kill dnsmasq
sudo systemctl stop dnsmasq
sudo systemctl disable dnsmasq
This disables a built-in DNS service used for UGREENlink routing. It conflicts with Pi-hole on port 53.
8. Verify Lockdown
sudo ss -tunp | grep -v '192.168'
You should only see 127.0.0.1 connections. If no external IPs appear, you are locked down.
9. Re-Login on Mobile App
After disabling UGREENlink, add the device again by IP address in the UGREEN NAS app. This connects directly over local WiFi instead of through UGREEN's servers.
What Changes After Lockdown
| Before | After |
|---|---|
| PC/mobile app works everywhere | Works on LAN only (use Tailscale for remote) |
| Updates happen automatically | Download firmware manually, upload via web UI |
| Docker images pull freely | Temporarily disable firewall rule, pull images, re-enable |
Optional: Encrypt Sensitive Data
Since UGOS Pro has no disk encryption, protect sensitive files with:
- Cryptomator -- encrypt files/folders before they reach the NAS
- VeraCrypt -- encrypted containers
- LUKS -- Linux-native encryption via SSH (advanced)
Firewall and VPN Coexistence
If you blocked your NAS from the internet at the router level AND want to use Gluetun VPN for media downloads, you need a targeted exception.
The Problem
Gluetun needs to reach your VPN provider's servers on the internet. If the NAS is fully blocked, the VPN tunnel cannot establish.
The Solution: UniFi Exception for VPN Port
Create a second firewall rule that allows ONLY the VPN traffic through:
- In UniFi, go to Settings > Security > Traffic & Firewall Rules
- Create a new rule above the "Block NAS Internet" rule:
- Name: Allow NAS VPN
- Action: Allow
- Source: Your NAS IP
- Destination: Internet
- Protocol: UDP
- Port:
51820(WireGuard) or1194(OpenVPN)
Order matters. The allow rule must be above the block rule. Rules are processed top-to-bottom.
Immich ML Model Downloads
The Immich ML container downloads machine learning models (~500MB) on first startup. If your NAS is firewalled, temporarily disable the block, start SparkBox, wait for models to download, then re-enable the block.
ls ${SB_ROOT}/modules/immich/config/model-cache/
Tailscale and the Firewall
Tailscale needs internet access for initial authentication only. After that, it works peer-to-peer. Temporarily disable the block, authenticate, then re-enable. If Tailscale loses connection, create an allow rule for UDP port 41641.
/dev/net/tun Device
Both Gluetun and Tailscale require /dev/net/tun. If the container fails to start with a tun error:
# Check if the TUN device exists
ls -la /dev/net/tun
# If it doesn't exist, load the kernel module
sudo modprobe tun
# Make it persist across reboots
echo "tun" | sudo tee /etc/modules-load.d/tun.conf
Hardware Transcoding
Intel Quick Sync hardware transcoding allows Jellyfin to transcode 4K HEVC video without heavy CPU usage. This is essential on a NAS.
Supported Devices
| Device | CPU | Quick Sync | Transcoding Capability |
|---|---|---|---|
| UGREEN DXP2800 | Intel N100 | Yes | 4K HEVC 8/10-bit, VP9, AV1 decode, multiple streams |
| UGREEN DXP4800 | Intel N100 | Yes | Same as above |
Setup: Mapping /dev/dri into Containers
Step 1: Verify /dev/dri Exists
ls -la /dev/dri/
Step 2: Set Permissions
sudo usermod -aG render your-username
sudo usermod -aG video your-username
Step 3: Enable in SparkBox
SparkBox's Jellyfin module automatically detects /dev/dri and maps it. If transcoding is not working, verify the device mapping in the module's docker-compose.yml:
devices:
- /dev/dri:/dev/dri
Step 4: Configure Jellyfin
- Open Jellyfin at
http://YOUR_NAS_IP:8096 - Go to Dashboard > Playback > Transcoding
- Set Hardware acceleration to Video Acceleration API (VAAPI)
- Set VA-API Device to
/dev/dri/renderD128 - Enable: H.264, HEVC, VP9, AV1 decode; H.264, HEVC encode
- Click Save
Performance: Intel N100 Transcoding
- 4K HEVC HDR (8-bit and 10-bit) -- smooth
- Multiple simultaneous 4K transcodes -- handles 2-3 concurrent streams
- Dolby TrueHD + Atmos passthrough -- confirmed
- AV1 hardware decode -- supported on N100 (12th gen+)
Port Conflict Resolution
UGREEN (UGOS Pro)
| Port | UGOS Uses For | SparkBox Service | Solution |
|---|---|---|---|
| 80 | UGOS web UI (HTTP) | Nginx Proxy Manager | Change HTTP_PORT to 8080 in .env |
| 443 | UGOS web UI (HTTPS) | Nginx Proxy Manager | Change HTTPS_PORT to 8443 in .env |
| 53 | dnsmasq | Pi-hole DNS | Disable dnsmasq |
| 9000 | UGOS Portainer | SparkBox Portainer | Change PORTAINER_PORT to 9001 |
| 5000/5001 | UGOS management | Not used | No conflict |
# Example: change Nginx Proxy Manager ports
HTTP_PORT=8080
HTTPS_PORT=8443
How to Find Port Conflicts
sudo ss -tlnp
sudo ss -tlnp | grep :80
sudo ss -tlnp | grep :443
sudo ss -tlnp | grep :53
PUID / PGID Setup
Finding Your PUID/PGID
id
# Example: uid=1000(kevin) gid=1000(kevin)
Setting PUID/PGID in SparkBox
Edit /opt/sparkbox/.env:
PUID=1000
PGID=1000
Common NAS User IDs
| NAS | Default Admin User | Typical PUID | Typical PGID |
|---|---|---|---|
| UGREEN | Your admin account | 1000 | 1000 |
Storage Paths on a NAS
Recommended Directory Structure
/volume1/ # Main data volume
├── docker/
│ └── sparkbox/ # SparkBox config
└── data/
├── torrents/
│ ├── movies/
│ ├── tv/
│ └── music/
└── media/
├── movies/
├── tv/
└── music/
Why This Structure Matters (Hardlinks)
Both torrents/ and media/ MUST be on the same filesystem/volume. When Radarr/Sonarr imports a download, they create hardlinks -- the file appears in both locations but only uses disk space once. If the directories are on different volumes, hardlinks fail and files are copied instead (using double the disk space).
df /data/torrents /data/media
# Both should show the same filesystem/device
Creating the Folder Structure
sudo mkdir -p /volume1/data/{torrents/{movies,tv,music},media/{movies,tv,music}}
sudo chown -R $(id -u):$(id -g) /volume1/data
sudo chmod -R 775 /volume1/data
Performance Expectations
UGREEN DXP2800 (Intel N100, 8GB RAM)
| Workload | CPU Usage | RAM Usage | Notes |
|---|---|---|---|
| Privacy profile only | 5-10% idle | ~1GB | Runs effortlessly |
| Media profile only | 10-15% idle | ~2.5GB | Comfortable, leaves 5GB free |
| Full profile | 15-25% idle | ~5-6GB | Tight on 8GB, works but no room for extras |
| Jellyfin 4K transcode (1 stream) | 20-30% | +200MB | Hardware transcode, barely noticed |
| Jellyfin 4K transcode (3 streams) | 40-60% | +500MB | Still handles it via Quick Sync |
| Immich ML processing | 80-100% | +1.5GB | CPU spikes during photo import, settles after |
Recommendations by RAM
| RAM | What You Can Run |
|---|---|
| 4GB | Privacy profile only. No media stack. |
| 8GB | Privacy + Media, OR Privacy + a few productivity apps. Not everything at once. |
| 16GB | Full profile comfortably. Everything at once. |
Upgrade Path
The DXP2800 has 1 DDR5 SODIMM slot (upgradeable). Replace the 8GB SODIMM with 16GB or 32GB DDR5 -- UGOS detects the new RAM automatically.
Disk I/O Considerations
- SATA drives (HDD): Fine for media storage and streaming. Slow for database-heavy apps
- M.2 NVMe SSD: Ideal for Docker containers and databases
- RAID 1 (mirrored): Recommended for data protection
Tip: Put SparkBox's configuration and container data on the M.2 SSD, and media files on the SATA drives. Fast app performance with large, cheap storage for movies/TV.
Backing Up SparkBox on a NAS
Backup Strategy
- SparkBox config: Use
sparkbox backup(automated, encrypted) - Media files: Use your NAS's built-in backup tools (rsync, UGOS Backup)
- Off-site backup: Copy backups to an external USB drive or cloud storage (encrypted with Cryptomator)
Backing Up to a Different Volume
mkdir -p /volume1/backups/sparkbox
ln -sfn /volume1/backups/sparkbox /opt/sparkbox/backups
What Is Backed Up
| Included | NOT Included |
|---|---|
| .env configuration | Media files (movies, TV, music) |
| Module settings | Docker images (re-pulled on restore) |
| Container config volumes | Temporary/cache files |
| Dashboard settings | Logs |
| Backup encryption key |
Additional NAS Tips
- SSH Auto-Disable: UGOS may auto-disable SSH after a timeout or firmware update. Re-enable it in Control Panel > Terminal
- After firmware updates: Verify SSH is enabled, dnsmasq is disabled, and SparkBox services are running
- VLAN Isolation (Advanced): For maximum security, put the NAS on its own VLAN with firewall rules allowing only LAN device access to NAS services
Media Guide
Complete setup guide for the Media Center module -- VPN configuration, the /data directory structure, hardlinks, and step-by-step configuration for every media service.
VPN Provider Setup
The Media Center module routes all download traffic through a commercial VPN via Gluetun. You MUST have an active VPN subscription.
Important: VPN credentials are NOT your login email/password. You need service credentials from your provider's manual setup or API section.
Surfshark
Surfshark offers the best value for long-term plans with fast WireGuard speeds.
- Go to my.surfshark.com/vpn/manual-setup/main
- Select WireGuard
- Generate or copy your credentials (private key + address)
VPN_PROVIDER=surfshark
VPN_TYPE=wireguard
WIREGUARD_PRIVATE_KEY=your_private_key_here
WIREGUARD_ADDRESSES=10.14.0.2/16
SERVER_COUNTRIES=United States
NordVPN
- Go to NordVPN Manual Configuration
- Select NordLynx (WireGuard)
- Generate a private key
VPN_PROVIDER=nordvpn
VPN_TYPE=wireguard
WIREGUARD_PRIVATE_KEY=your_private_key_here
WIREGUARD_ADDRESSES=10.5.0.2/16
SERVER_COUNTRIES=United States
ProtonVPN
ProtonVPN supports port forwarding, which can improve upload speeds and seeding.
VPN_PROVIDER=protonvpn
VPN_TYPE=wireguard
WIREGUARD_PRIVATE_KEY=your_private_key_here
WIREGUARD_ADDRESSES=10.2.0.2/32
SERVER_COUNTRIES=United States
VPN_PORT_FORWARDING=on
AirVPN
VPN_PROVIDER=airvpn
VPN_TYPE=wireguard
WIREGUARD_PRIVATE_KEY=your_private_key_here
WIREGUARD_PUBLIC_KEY=server_public_key_here
WIREGUARD_PRESHARED_KEY=your_preshared_key_here
WIREGUARD_ADDRESSES=your_assigned_ip/32
FIREWALL_VPN_INPUT_PORTS=your_forwarded_port
VPN_PORT_FORWARDING=on
Mullvad
VPN_PROVIDER=mullvad
VPN_TYPE=wireguard
WIREGUARD_PRIVATE_KEY=your_private_key_here
WIREGUARD_ADDRESSES=your_assigned_ip/32
SERVER_COUNTRIES=United States
Other Providers
Gluetun supports 30+ providers. See the full provider list for configuration details.
Applying VPN Credentials
sparkbox restart media
# Verify VPN is working
docker exec sb-gluetun wget -qO- ifconfig.me # VPN IP
curl -s ifconfig.me # Real IP (should differ)
The /data Directory Structure
/data/
├── torrents/ # qBittorrent downloads here
│ ├── movies/
│ ├── tv/
│ └── music/
└── media/ # Radarr/Sonarr organize here (Jellyfin reads from here)
├── movies/
├── tv/
└── music/
Creating the Structure
sudo mkdir -p /data/{torrents/{movies,tv,music},media/{movies,tv,music}}
sudo chown -R $(id -u):$(id -g) /data
sudo chmod -R 775 /data
On a NAS, replace /data with your volume path (e.g., /volume1/data).
Why Hardlinks Matter
When qBittorrent finishes downloading a movie, Radarr needs to move it to the media folder. There are two approaches:
- Copy -- duplicates the file. A 20GB movie uses 40GB of disk space
- Hardlink -- creates a second reference to the same data. The 20GB movie appears in both locations but uses only 20GB total
Hardlinks only work when both directories are on the same filesystem/drive.
Internal Docker Networking
Services sharing Gluetun's network (reach each other via localhost)
| Service | Address | Port |
|---|---|---|
| qBittorrent | localhost | 8080 |
| Prowlarr | localhost | 9696 |
| Sonarr | localhost | 8989 |
| Radarr | localhost | 7878 |
| Lidarr | localhost | 8686 |
| FlareSolverr | localhost | 8191 |
Services on the bridge network
| Service | Container Name | Port |
|---|---|---|
| Bazarr | sb-bazarr | 6767 |
| Jellyfin | sb-jellyfin-media | 8096 |
| Seerr | sb-seerr | 5055 |
Common Connection Reference
| From | To | Host | Port |
|---|---|---|---|
| Radarr | qBittorrent | localhost | 8080 |
| Sonarr | qBittorrent | localhost | 8080 |
| Prowlarr | Radarr | http://localhost:7878 | |
| Prowlarr | Sonarr | http://localhost:8989 | |
| Seerr | Jellyfin | sb-jellyfin-media | 8096 |
| Seerr | Radarr | sb-gluetun | 7878 |
| Seerr | Sonarr | sb-gluetun | 8989 |
| Bazarr | Radarr | sb-gluetun | 7878 |
| Bazarr | Sonarr | sb-gluetun | 8989 |
Configuring Prowlarr (Indexers)
Prowlarr manages your indexers and syncs them to Radarr, Sonarr, and Lidarr automatically.
Open Prowlarr: http://YOUR_SERVER:8181
Step 1: Add Indexers
- Go to Indexers > Add Indexer
- Add your preferred indexers. Recommended public indexers: 1337x, The Pirate Bay, LimeTorrents, EZTV (TV), YTS (movies)
- Test each indexer after adding
Tip: The more indexers you add, the more results you get. If you only have one or two, you will miss many releases.
Step 2: Set Up FlareSolverr
Some indexers use Cloudflare protection. FlareSolverr bypasses this.
- Go to Settings > Indexers
- Click + to add a new proxy
- Select FlareSolverr
- Host:
http://localhost:8191 - Tag: Create a tag like
flaresolverr - Add the same tag to any indexer blocked by Cloudflare
Step 3: Connect to Radarr and Sonarr
- Go to Settings > Apps
- Add Radarr:
- Prowlarr Server:
http://localhost:9696 - Radarr Server:
http://localhost:7878 - API Key: Copy from Radarr's Settings > General > API Key
- Prowlarr Server:
- Add Sonarr:
- Prowlarr Server:
http://localhost:9696 - Sonarr Server:
http://localhost:8989 - API Key: Copy from Sonarr's Settings > General > API Key
- Prowlarr Server:
- Click Sync App Indexers
Configuring Radarr (Movies)
Open Radarr: http://YOUR_SERVER:7878
Step 1: Add Download Client
- Go to Settings > Download Clients > + > qBittorrent
- Host:
localhost, Port:8080, Username:admin, Category:movies - Test and Save
Step 2: Set Root Folder
Settings > Media Management > Add Root Folder: /data/media/movies
Step 3: Configure Media Management
- Enable Rename Movies
- Enable Use Hardlinks instead of Copy -- this is critical
Step 4: Set Quality Profile
Strategy: grab 1080p quickly, then auto-upgrade to 4K if available.
- Go to Settings > Profiles
- Uncheck everything below 1080p
- Set Cutoff to
Bluray-1080p - Set Upgrade Until to
Bluray-2160p Remux
Step 5: Add Movies
Go to Movies > Add New, search, select quality profile and root folder, click Add Movie.
Configuring Sonarr (TV Shows)
Open Sonarr: http://YOUR_SERVER:8989
Sonarr works the same as Radarr but for TV shows.
Step 1: Add Download Client
Same as Radarr: Host localhost, Port 8080, Category tv
Step 2: Set Root Folder
Path: /data/media/tv
Step 3: Configure Media Management
- Enable Rename Episodes
- Enable Use Hardlinks instead of Copy
Step 4: Add TV Shows
Go to Series > Add New, search, select profile, root folder, and which seasons to monitor.
Configuring qBittorrent
Open qBittorrent: http://YOUR_SERVER:8080
Getting the Temporary Password
docker logs sb-qbittorrent 2>&1 | grep "temporary password"
Default username is admin.
Step 1: Set a Permanent Password
Go to Tools > Options > Web UI and set a permanent username and password.
Step 2: Configure Categories and Save Paths
| Category | Save Path |
|---|---|
movies | /data/torrents/movies |
tv | /data/torrents/tv |
music | /data/torrents/music |
Step 3: Important Settings
- Advanced > Network Interface: should be
tun0(the VPN tunnel) - BitTorrent > Seeding Limits: Set per your preference
- Downloads > Default Save Path:
/data/torrents
Configuring Jellyfin
Open Jellyfin: http://YOUR_SERVER:8096
Step 1: Complete First-Run Wizard
Create an admin account and set your preferred language.
Step 2: Add Media Libraries
| Library Type | Folder Path |
|---|---|
| Movies | /data/media/movies |
| Shows | /data/media/tv |
| Music | /data/media/music |
Step 3: Configure Hardware Transcoding
If your server has Intel Quick Sync, set Hardware acceleration to VAAPI and VA-API Device to /dev/dri/renderD128. See Hardware Transcoding for detailed setup.
Step 4: Install Client Apps
Jellyfin apps are available for Roku, Fire TV, Apple TV, Android TV, Samsung TV, LG TV, iOS, Android, and all desktop browsers. Enter your server address during app setup.
Configuring Seerr (Requests)
Open Seerr: http://YOUR_SERVER:5055
Step 1: Connect to Jellyfin
On the first-run wizard, select Jellyfin. URL: http://sb-jellyfin-media:8096. Sign in with your Jellyfin admin credentials.
Step 2: Connect to Radarr
Settings > Services > Radarr. Hostname: sb-gluetun, Port: 7878, API Key from Radarr.
Step 3: Connect to Sonarr
Settings > Services > Sonarr. Hostname: sb-gluetun, Port: 8989, API Key from Sonarr.
Step 4: Create User Accounts
Import users from Jellyfin or create local accounts. Set permissions for what they can request and auto-approve.
Configuring Bazarr (Subtitles)
Open Bazarr: http://YOUR_SERVER:6767
Step 1: Connect to Radarr & Sonarr
Settings > Radarr/Sonarr. Host: sb-gluetun, Port: 7878 (Radarr) or 8989 (Sonarr), API Key from each.
Step 2: Add Subtitle Providers
Recommended providers:
- OpenSubtitles.com -- the largest subtitle database (free account required)
- Subscene -- good for non-English content
- Addic7ed -- popular for TV shows
Step 3: Configure Languages
Add your preferred subtitle languages and set language profiles for movies and TV shows.
Configuring Lidarr (Music)
Open Lidarr: http://YOUR_SERVER:8686
Lidarr works the same as Radarr/Sonarr but for music. Download client: localhost:8080, Category: music, Root folder: /data/media/music.
For quality profiles, enable FLAC, MP3-320, MP3-256 with cutoff set to FLAC (prefer lossless).
Family Sharing
Share your media server with family and friends without exposing admin interfaces. They only see Jellyfin (to watch) and Seerr (to request).
Using Tailscale (Recommended)
- Invite family to your tailnet: In the Tailscale admin console, click Share on your SparkBox machine and enter their email
- They install Tailscale on their device and accept your invite
- Give them two links:
text
http://100.x.x.x:5055 # Seerr (request movies and shows) http://100.x.x.x:8096 # Jellyfin (watch everything) - Set up Jellyfin app on their TV: Install the Jellyfin app and enter your Tailscale IP as the server address
What NOT to Share
- Radarr, Sonarr, Prowlarr -- admin tools
- qBittorrent -- the torrent client
- SparkBox Dashboard -- full admin access
- Pi-hole, Vaultwarden, Authelia -- personal privacy tools
Using Tailscale Funnel (No Account Needed)
If you do not want family members to create Tailscale accounts:
tailscale funnel 8096
This creates a public HTTPS URL anyone can access. Set strong passwords and consider Authelia in front of it.
The test-media.sh Script
bash /opt/sparkbox/modules/media/test-media.sh
What It Checks
| Check | What It Verifies |
|---|---|
| Docker | Docker is installed and running |
| Configuration | .env exists and VPN credentials are set |
| Folder Structure | /data directories exist with correct permissions |
| Containers | All expected containers are running and healthy |
| VPN Connection | Gluetun is connected, VPN IP differs from real IP |
| VPN Tunneling | qBittorrent and Prowlarr traffic routes through VPN |
| Web UI Access | Each service's web UI responds on its expected port |
| Hard Links | torrents/ and media/ are on the same filesystem |
Interpreting Results
=========================================
Passed: 18 Failed: 0 Warnings: 2
=========================================
- PASS -- check succeeded, everything is working
- FAIL -- something is broken, follow the "Fix:" instructions
- WARN -- not critical but should be investigated