Storage AWS

Deluge 2.2.0 on AWS User Guide

| Product: Deluge 2.2.0 on Ubuntu 24.04 on AWS

Overview

This guide covers launching and using the Deluge 2.2.0 on Ubuntu 24.04 AMI from cloudimg on Amazon EC2. It is one version of the cloudimg file sharing and sync listing on AWS Marketplace; you pick it as the software version when you subscribe and launch.

Deluge is a lightweight, full featured BitTorrent client with a client/server design: the daemon (deluged) does all the downloading and seeding, and the Web UI (deluge-web) lets you add torrent files, URLs and magnet links, organise downloads and set bandwidth and connection limits from a browser. It is a simple way to run an always on download and seeding server on infrastructure you control, for example to distribute large open source images or your own content.

A stock Deluge Web UI ships with the well known password deluge, so an exposed install is open to anyone. The cloudimg image adds:

  • No default login. On first boot the instance generates its own Web UI password and stores it in Deluge's configuration only as a salted hash; the password deluge is never set. A second, separate secret is generated for the daemon's only account. Both are written to /root/deluge-credentials.txt, readable by root only.
  • Two locks on the Web UI. nginx asks for HTTP Basic authentication (user admin) before any request reaches Deluge, and Deluge then asks for its own login. Both use the same per-instance password, so you track one secret.
  • HTTPS from the first boot. nginx serves the Web UI on port 443 with a certificate generated on your instance. Port 80 redirects to HTTPS, and a request for a host name the instance does not serve gets no answer.
  • Nothing exposed that should not be. The daemon (port 58846) and the Web UI (port 8112) listen on 127.0.0.1 only. Peers reach Deluge on one fixed port, TCP and UDP 6881 (connections, DHT and uTP); UPnP, NAT-PMP and local peer discovery are off, so Deluge opens nothing else.
  • Fail closed. No password, hash, session or key is baked into the image, and the daemon, the Web UI and nginx refuse to start until first boot has created them.
  • Hardened defaults. Deluge fetches .torrent files from URLs you give it and contacts the trackers a torrent names, so the daemon, the Web UI and nginx are blocked from the instance metadata service, and the AMI requires IMDSv2. The daemon and Web UI run as an unprivileged deluge user under a locked down systemd profile. A browser request that another web site triggers is refused, and nginx hands Deluge the client address from the connection, never from a header a client can forge.
  • Your downloads on their own volume. Downloads go to a separate 32 GiB EBS volume mounted at /data, which you can resize and snapshot on its own. Nothing on it is served over HTTP.
  • Fully patched Ubuntu 24.04 LTS at build time, with unattended security upgrades switched on.

What is on the image: Deluge 2.2.0 in its own Python environment (/opt/deluge, installed from the checksum verified release), libtorrent-rasterbar 2.0.10 from Ubuntu, nginx, Ubuntu 24.04 LTS, cloud-init and the AWS Systems Manager agent.

Default user: ubuntu · Architecture: x86_64 · Recommended instance type: m5.large

Prerequisites

  • An AWS account subscribed to the listing, an EC2 key pair and a VPC subnet with a route to the internet.
  • A security group that allows TCP 443 (the Web UI) and TCP 80 (redirects to HTTPS) from the networks you manage Deluge from, TCP and UDP 6881 from anywhere (BitTorrent peers), and TCP 22 (SSH) from your own networks only.

Step 1: Launch the instance

In the AWS Marketplace listing choose Continue to Subscribe, then Continue to Configuration, pick Deluge 2.2.0 on Ubuntu 24.04 as the software version and your Region, then Launch through EC2. Choose m5.large, your key pair and a security group as above. Keep the second EBS volume: it is where downloads are stored. Grow it at launch if you plan to download a lot.

With the AWS CLI (replace the values in angle brackets):

aws ec2 run-instances --region <region> --image-id <ami-id-from-the-listing> \
  --instance-type m5.large --key-name <your-key-pair> \
  --security-group-ids <your-security-group> --subnet-id <your-subnet> \
  --metadata-options HttpTokens=required,HttpEndpoint=enabled \
  --tag-specifications 'ResourceType=instance,Tags=[{Key=Name,Value=deluge}]'

Step 2: Connect to your instance

Version SSH user
Deluge 2.2.0 on Ubuntu 24.04 ubuntu
ssh -i <your-key.pem> ubuntu@<public-ip>

Step 3: Check the services, ports and data volume

First boot takes a few seconds. Then the daemon, the Web UI, nginx and the first boot unit are active:

systemctl is-active deluged deluge-web nginx deluge-firstboot
active
active
active
active

nginx is the only web listener. The daemon (58846) and the Web UI (8112) listen on loopback only, and the daemon's peer port is 6881:

sudo ss -tlnp | awk 'NR==1 || /nginx|sshd|deluge/' | awk '{print $1, $4, $6}' | sed -E 's/,pid=[0-9]+,fd=[0-9]+//g'
State Local Peer
LISTEN 0.0.0.0:443 users:(("nginx"),("nginx"),("nginx"))
LISTEN 127.0.0.1:58846 users:(("deluged"))
LISTEN 0.0.0.0:22 users:(("sshd"),("systemd"))
LISTEN 0.0.0.0:80 users:(("nginx"),("nginx"),("nginx"))
LISTEN 127.0.0.1:8112 users:(("deluge-web"))
LISTEN <private-ip>%ens5:6881 users:(("deluged"))
LISTEN 127.0.0.1%lo:6881 users:(("deluged"))
LISTEN [::]:443 users:(("nginx"),("nginx"),("nginx"))
LISTEN [::]:22 users:(("sshd"),("systemd"))
LISTEN [::]:80 users:(("nginx"),("nginx"),("nginx"))

The same port carries DHT and uTP over UDP:

sudo ss -ulnp | awk '/deluged/ {print $1, $4, $6}' | sed -E 's/,pid=[0-9]+,fd=[0-9]+//g'
UNCONN <private-ip>%ens5:6881 users:(("deluged"))
UNCONN 127.0.0.1%lo:6881 users:(("deluged"))

Downloads are stored on the separate data volume:

findmnt -no SOURCE,TARGET,FSTYPE /data
df -h --output=size,avail,target /data
sudo ls -l /data/deluge
/dev/nvme1n1 /data  ext4
 Size Avail Mounted on
  32G   30G /data
total 12
drwxr-x--- 2 deluge deluge 4096 Oct 20 06:28 completed
drwxr-x--- 2 deluge deluge 4096 Oct 20 06:30 downloads
drwxr-x--- 2 deluge deluge 4096 Oct 20 06:28 torrents

Step 4: Get your URL and password

The address and the password generated on this instance are in a root only file:

sudo cat /root/deluge-credentials.txt
# Deluge 2.2.0 - generated on first boot by deluge-firstboot.service. Unique to this instance; keep it safe.
# The well-known Deluge default password 'deluge' is NOT set on this instance.

DELUGE_URL=https://<public-ip>/
DELUGE_USER=admin
DELUGE_PASS=<32 hexadecimal characters>

# The same password opens the browser's sign-in prompt (user admin) and the Deluge Web UI login form.
# Daemon account (RPC on 127.0.0.1:58846 only, for deluge-console or a thin client through an SSH tunnel):
DELUGE_DAEMON_USER=localclient
DELUGE_DAEMON_PASS=<40 hexadecimal characters>

# Downloads: /data/deluge/downloads (separate EBS volume, never served over HTTP).
# Peers: TCP and UDP 6881. Self test: sudo deluge-selftest   Change the host: sudo deluge-set-host <dns-name>

To see just the address and user name without printing a password:

sudo grep -E '^DELUGE_(URL|USER)=' /root/deluge-credentials.txt
DELUGE_URL=https://<public-ip>/
DELUGE_USER=admin

Step 5: Sign in to the Web UI

Open DELUGE_URL in your browser. The certificate is self signed (generated on your instance), so accept the browser warning once, or use your own name and certificate (Step 10). The browser asks for a user name and password: enter admin and DELUGE_PASS. Deluge then shows its own login; enter the same password:

The Deluge Web UI login dialog asking for the password, in front of the empty torrent list

The Web UI connects to the daemon on the instance automatically; the status bar shows the connection, the transfer rates and the free space on the download volume.

Step 6: Add a torrent

Click Add. Choose File to upload a .torrent file from your computer, or Url to paste the address of a .torrent file or a magnet link. Deluge lists the files in the torrent so you can untick any you do not want; the Options tab sets the download folder, bandwidth limits and whether to start paused:

The Add Torrents dialog with the Ubuntu 24.04.4 live server torrent loaded from a URL and its single ISO file ticked for download

Click Add. The torrent appears in the main list with its progress, speed and time remaining; select it to see its status, files, peers and trackers in the panel below:

The Deluge main window downloading the Ubuntu 24.04.4 live server ISO at about 29 MiB/s

Finished files are in /data/deluge/downloads. Copy them off the instance with scp or rsync over SSH, or move them to Amazon S3 with the AWS CLI. They are never served over HTTP by this instance.

Step 7: Check the appliance

The image ships a self test that proves the security model end to end over HTTPS: the Web UI refuses you without the password or with a wrong one, Deluge refuses the default password deluge and accepts yours, the Web UI is connected to the daemon, downloads go to the data volume and peers use port 6881:

sudo deluge-selftest
OK: healthz 200; no credential 401; wrong credential 401; default password 'deluge' refused; per-instance password accepted; Web UI connected to deluged 2.2.0; downloads /data/deluge/downloads; peer port 6881 - over TLS as <public-ip>

Step 8: Security checks

Plain HTTP redirects to HTTPS, the Web UI refuses you without the password, Deluge itself refuses the default password, a request another web site makes your browser send is refused even when the browser has your password cached, and a request for a host name the instance does not serve gets no answer. The password is read from the credentials file and handed to curl on standard input (-K -), so it never appears on a command line:

H=$(sudo sed -nE 's#^DELUGE_URL=https://([^/]+)/.*#\1#p' /root/deluge-credentials.txt)
auth() { sudo sed -nE 's/^DELUGE_PASS=(.*)$/user = "admin:\1"/p' /root/deluge-credentials.txt; }
curl -s -o /dev/null -w 'plain HTTP: %{http_code} -> %{redirect_url}\n' --resolve "$H:80:127.0.0.1" "http://$H/"
curl -sk -o /dev/null -w 'Web UI without the password: %{http_code}\n' --resolve "$H:443:127.0.0.1" "https://$H/"
auth | curl -sk -K - --resolve "$H:443:127.0.0.1" -H 'Content-Type: application/json' -d '{"method":"auth.login","params":["deluge"],"id":1}' "https://$H/json"; echo
auth | curl -sk -K - -o /dev/null -w 'request from another web site: %{http_code}\n' --resolve "$H:443:127.0.0.1" -H 'Origin: https://evil.example' -H 'Content-Type: application/json' -d '{"method":"web.connected","params":[],"id":2}' "https://$H/json"
curl -s -o /dev/null -w 'unknown host name: %{http_code}\n' -H 'Host: evil.example' http://127.0.0.1/ || true
plain HTTP: 301 -> https://<public-ip>/
Web UI without the password: 401
{"result": false, "error": null, "id": 1}
request from another web site: 403
unknown host name: 000

The daemon, the Web UI and nginx cannot reach the instance metadata service (so a .torrent URL or tracker pointing at it fails), and the secrets are readable by root or the deluge user only:

systemctl show deluged deluge-web nginx -p Id -p IPAddressDeny
sudo stat -c '%a %U:%G %n' /root/deluge-credentials.txt /etc/nginx/deluge.htpasswd /etc/nginx/ssl/deluge.key /var/lib/deluge/.config/deluge/auth /var/lib/deluge/.config/deluge/web.conf
IPAddressDeny=168.63.129.16/32 fd00:ec2::254/128 169.254.169.254/32
Id=deluged.service

IPAddressDeny=168.63.129.16/32 fd00:ec2::254/128 169.254.169.254/32
Id=deluge-web.service

IPAddressDeny=168.63.129.16/32 fd00:ec2::254/128 169.254.169.254/32
Id=nginx.service
600 root:root /root/deluge-credentials.txt
640 root:www-data /etc/nginx/deluge.htpasswd
600 root:root /etc/nginx/ssl/deluge.key
600 deluge:deluge /var/lib/deluge/.config/deluge/auth
600 deluge:deluge /var/lib/deluge/.config/deluge/web.conf

The certificate was generated on this instance and names its own addresses:

H=$(sudo sed -nE 's#^DELUGE_URL=https://([^/]+)/.*#\1#p' /root/deluge-credentials.txt)
echo | openssl s_client -connect 127.0.0.1:443 -servername "$H" 2>/dev/null | openssl x509 -noout -subject -ext subjectAltName
subject=CN = <public-ip>, O = cloudimg
X509v3 Subject Alternative Name:
    IP Address:<public-ip>, DNS:ec2-<public-ip-dashed>.compute-1.amazonaws.com, IP Address:<private-ip>, IP Address:127.0.0.1, DNS:localhost

Step 9: Peer port and download folders

Deluge listens for peers on port 6881 only, and UPnP, NAT-PMP and local peer discovery are off. The Network page of Preferences shows the same settings:

The Deluge Preferences Network page with Use Random Port unticked, incoming port 6881, and UPnP, NAT-PMP and LSD unticked

On the instance, deluge-console reads the same settings from the daemon (it signs in with the daemon account from Deluge's own configuration, so no password is typed):

sudo -u deluge -H /opt/deluge/bin/deluge-console -c /var/lib/deluge/.config/deluge "config listen_ports random_port upnp natpmp lsd download_location" 2>/dev/null
download_location: /data/deluge/downloads
listen_ports: (6881, 6881)
lsd: False
natpmp: False
random_port: False
upnp: False

If you change the incoming port in Preferences > Network, change the security group rule to match (TCP and UDP). Completed downloads can be moved to /data/deluge/completed with Preferences > Downloads > Move completed to.

Step 10: Your own DNS name and certificate

Point a DNS record at the instance, then set the name Deluge is served as. This mints a new self signed certificate for the name, updates nginx and the URL in /root/deluge-credentials.txt, and keeps the name across reboots:

sudo deluge-set-host <your-domain>

To use a certificate from your own certificate authority instead, copy it over the generated pair and reload nginx (running deluge-set-host again replaces it with a self signed one):

sudo install -m 0644 <your-domain>.crt /etc/nginx/ssl/deluge.crt
sudo install -m 0600 <your-domain>.key /etc/nginx/ssl/deluge.key
sudo nginx -t && sudo systemctl reload nginx

Step 11: Change the password

The password guards both the browser sign-in and the Deluge login. To change it, set a new Deluge password in Preferences > Interface > Password, then set the same value for the nginx sign-in (htpasswd prompts for it, so it never appears on a command line) and update DELUGE_PASS in /root/deluge-credentials.txt:

sudo htpasswd -B /etc/nginx/deluge.htpasswd admin

nginx uses the new password at once.

Step 12: Use the GTK or console client

The daemon accepts connections from 127.0.0.1 only. To drive it from the Deluge desktop client (in thin client mode) on your computer, forward the port over SSH and connect the client to 127.0.0.1:58846 as user localclient with DELUGE_DAEMON_PASS from the credentials file:

ssh -i <your-key.pem> -N -L 58846:127.0.0.1:58846 ubuntu@<public-ip>

Step 13: Server components

Component Path
Deluge 2.2.0 and its Python environment /opt/deluge
Python packages shipped /usr/share/doc/deluge/python-packages.txt
Deluge configuration (daemon account, settings, Web UI password hash) /var/lib/deluge/.config/deluge/
Downloads, completed downloads, copies of .torrent files /data/deluge/ (on the /data volume)
Services deluged.service, deluge-web.service, nginx.service
nginx site /etc/nginx/sites-available/cloudimg-deluge
Sign-in password hash /etc/nginx/deluge.htpasswd (root:www-data, 0640)
Certificate and key /etc/nginx/ssl/
First boot script /usr/local/sbin/deluge-firstboot.sh
Host name helper /usr/local/sbin/deluge-set-host
Self test /usr/local/sbin/deluge-selftest
Credentials /root/deluge-credentials.txt (mode 0600)
Licence /usr/share/doc/deluge/LICENSE

Step 14: Security recommendations

  • Allow ports 22, 80 and 443 in the security group from your own networks only; only the peer port 6881 needs to be open to everyone.
  • Keep the password private and change it if it may have leaked (Step 11).
  • Use your own DNS name and a certificate your browsers trust (Step 10), so nobody learns to click through certificate warnings.
  • Download and share only content you have the right to distribute.
  • Keep the operating system patched; unattended security upgrades are on, and sudo apt-get update && sudo apt-get upgrade applies everything else.

Support and licensing

Deluge is free software under the GNU General Public License, version 3 or (at your option) any later version, with an exception that permits linking with OpenSSL; a copy is at /usr/share/doc/deluge/LICENSE. There is no per user or per CPU licence fee. The AMI price covers cloudimg's hardening, first boot setup and support.

  • Email: support@cloudimg.co.uk
  • Website: https://www.cloudimg.co.uk
  • Support: 24/7, with a 24 hour response SLA