4 min read

Encrypted Server Backups to S3 with Duplicati

1 - How I Built My Own Server Using Local and Cloud Resources
2 - Deploying containers via Cloudflare Tunnel (Zero Trust)
3 - Reverse proxy on Oracle VPS with Traefik
4 - Encrypted Server Backups to S3 with Duplicati

This is the last part of the build-server series. After setting up a reverse proxy, it's important to keep your data safe. In this guide, we'll use Duplicati to back up your VPS (e.g Oracle VPS) to an S3-compatible service with encryption.

Duplicati is a lightweight and powerful backup tool with a user-friendly web interface. It supports encryption, scheduling, and remote destinations like S3, FTP, WebDAV, and others.


Requirements

Make sure you have the following before starting:

  • A VPS with Docker and Docker Compose installed
  • An S3-compatible storage provider (e.g., AWS S3, Backblaze B2, Wasabi, MinIO, etc.)
  • S3 access credentials (Access Key and Secret Key)
  • A domain if you're accessing Duplicati behind a reverse proxy (optional)

Step 1: Deploy Duplicati with Docker Compose

Here's the Docker Compose file I used.

services:
  duplicati:
    image: lscr.io/linuxserver/duplicati:latest
    container_name: duplicati
    environment:
      - PUID=0 # use 0 instead 1000 because some of my files using root owner
      - PGID=0
      - TZ=Asia/Jakarta
      - SETTINGS_ENCRYPTION_KEY=<YOUR_KEY_FOR_ENCRYPTION>
      # an env from linuxserver so i can use docker command
      - DOCKER_MODS=linuxserver/mods:universal-docker
    volumes:
      - <local-path-to-duplicati-dir>/config:/config
      - <local-path-to-duplicati-dir>/backups:/backups
      - <local-path-to-duplicati-dir>/scripts:/scripts
      - <dir-to-backup>:/source
      # because i need to run docker for my scripts, i need to bind the socket
      - /var/run/docker.sock:/var/run/docker.sock:ro
    # ports:
    #   - 8200:8200
    restart: unless-stopped
    labels:
      - "traefik.enable=true"
      - "traefik.http.routers.duplicati.rule=Host(`duplicati.domain.com`)"
      - "traefik.http.routers.duplicati.entrypoints=websecure"
      - "traefik.http.routers.duplicati.tls=true"
      - "traefik.http.services.duplicati.loadbalancer.server.port=8200"
    networks:
      - public-net

networks:
  public-net:
    external: true

Once your configuration is ready, deploy it with:

docker compose up -d

Open Duplicati in your browser at http://your-server-ip:8200 or via your reverse proxy domain if set up (https://duplicati.domain.com).


Step 2: Create Pre and Post Backup Scripts

To ensure certain files can be backed up properly, I stop specific containers before the backup and start them again afterward.

<local-path-to-duplicati-dir>/scripts/stop-docker.sh

#!/bin/bash
docker stop your-container-name

<local-path-to-duplicati-dir>/scripts/start-docker.sh

#!/bin/bash
docker start your-container-name

Make both scripts executable:

chmod +x <local-path-to-duplicati-dir>/scripts/stop-docker.sh <local-path-to-duplicati-dir>/scripts/start-docker.sh

You can then configure Duplicati to run these scripts using the Advanced Options in the backup job:

  • --run-script-before=/scripts/stop-docker.sh
  • --run-script-after=/scripts/start-docker.sh

Step 2: Initial Setup

Step 1. Open Duplicati in your browser (default password: changeme, then update it in Settings)

Step 2. Create a new backup (Add backup -> Configure a new backup)

Step 3. Fill in all the required fields.

Step 4. Set the Storage Type to S3 Compatible, then fill in the required fields and check the Use SSL checkbox

If you're using a custom URL, select Custom server URL and enter your S3 endpoint (e.g., s3.domain.com, without http/https).
Even if you're using MinIO, keep Amazon AWS SDK as the client library.

Step 5. Click Test connection to verify your S3 configuration. Make sure the connection is successful.

Step 6. Add the Source path. Since we mounted <dir-to-backup>:/source in the Docker Compose file earlier, your target directory will be under /computer/source.

Step 7. Set your backup schedule.

Step 8. Configure other options as needed. Under Advanced options, refer to the example image below. You can add more advanced options by following the documentation.

Step 9. Click Save, and your backup is now ready.


Step 3: Start the Backup

Click "Run now" to perform your first backup.
Once it’s done, verify that your data is saved in your S3 storage.


Optional: Test Restore

To restore your data, simply configure your S3 credentials and bucket in Duplicati again (if you're using a different Duplicati instance for restore). Once connected, you can browse and select which version or files you want to restore


Final Thoughts

From spinning up an local server using SBC, securing it with Cloudflare Tunnel, reverse proxying with Traefik, to backing everything up to S3 with encryption — you’ve now got yourself a solid, self-hosted setup. No public IP? No problem.

The best part? Most of this was done using free tools and services — just some time, curiosity, and coffee ☕.

Hopefully this series made things easier and gave you the confidence to manage your own server stack like a pro. Whether you're hosting a personal project or just tinkering around, you’re in control now.

Until the next project — happy self-hosting!