Great Blog

01 Mar 2021

Full system backup with restic and minio



mkdir /opt/minio
cd /opt/minio
chmod +x mc minio
echo 'PATH="${PATH}:/opt/minio"' >> /root/.bashrc
useradd minio
mkdir -p /data/minio
chown minio: -R /opt/minio /data/minio

Configure Systemd service

nano /etc/systemd/system/minio.service

Paste the following in the above file





ExecStartPre=/bin/bash -c "if [ -z \"${MINIO_VOLUMES}\" ]; then echo \"Variable MINIO_VOLUMES not set in /etc/default/minio\"; exit 1; fi"

ExecStart=/opt/minio/minio server $MINIO_OPTS $MINIO_VOLUMES

# Let systemd restart this service always

# Specifies the maximum file descriptor number that can be opened by this process

# Specifies the maximum number of threads this process can create

# Disable timeout logic and wait until process is stopped


# Built for ${}-${project.version} (${})

nano /etc/default/minio

Paste the following in the above file. Make sure to change RANDOM_ROOT_USERNAME and RANDOM_ROOT_PASSWORD, and change MINIO_VOLUMES to where you’d like the data to be stored.

# Volume to be used for MinIO server.
# Use if you want to run MinIO on a custom port.
MINIO_OPTS="--address :9199"
# Root user for the server.
# Root secret for the server.

systemctl daemon-reload

systemctl enable minio --now

Minio is now started

Configure Minio

configure minio-client

We will configure mc to connect to the minio server

mc config host add minio http://localhost:9199 RANDOM_ROOT_USERNAME 'RANDOM_ROOT_PASSWORD'

Create User


Create bucket via WebUI

  1. Log in to the WebUI by going to http://IP_OF_SERVER:9199 and use your RANDOM_ROOT_USERNAME and RANDOM_ROOT_PASSWORD.

  2. Go to the lower right hand corner where the plus sign is and click it.

  3. Click the middle icon (looks like a bucket, if you hover over it, it will say “Create Bucket”

  4. Input what you’d like your bucket name to be. For this tut I’m using BUCKETNAME.

  5. The bucket is now created.

Grant user access to bucket

We will be creating the json file with permissions

mkdir /opt/minio/json
cd /opt/minio/json
nano server-domain-com-rw.json

Below is the json file with the permissions. Can be pasted into the file above

  "Version": "2012-10-17",
  "Statement": [
      "Effect": "Allow",
      "Action": "s3:ListBucket",
      "Resource": "arn:aws:s3:::BUCKETNAME"
  "Effect": "Allow",
      "Action": [
      "Resource": "arn:aws:s3:::BUCKETNAME/server-domain-com/*"

Now we will import the json policy to make it a policy in minio

mc admin policy add minio server-domain-com-rw server-domain-com.json

Now we assign the policy to the user created before.

mc admin policy set minio server-domain-com-rw user=RANDOM_RESTIC_USERNAME

Minio should now be up and working. You should be able to access your S3 dashboard now by http://IP_OF_SERVER:9199 and you should be able to log in with RANDOM_RESTIC_USERNAME and RANDOM_ROOT_USERNAME credentials from above.

Configure NGiNX reverse proxy

config files

You will have to get the SSL certs installed at /etc/nginx/ssl/ and /etc/nginx/ssl/ I have in instructions HERE

nano /etc/nginx/conf.d/

server {
  listen 443 ssl http2;

  ssl_certificate /etc/nginx/ssl/;
  ssl_certificate_key /etc/nginx/ssl/;

  access_log /var/log/nginx/minio.domain.com_access.log;

  # To allow special characters in headers
  ignore_invalid_headers off;
  # Allow any size file to be uploaded.
  # Set to a value such as 1000m; to restrict file size to a specific value
  client_max_body_size 0;
  # To disable buffering
  proxy_buffering off;

  location / {
    proxy_set_header X-Real-IP $remote_addr;
    proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
    proxy_set_header X-Forwarded-Proto $scheme;
    proxy_set_header Host $http_host;

    proxy_connect_timeout 300;
    # Default is HTTP/1, keepalive is only enabled in HTTP/1.1
    proxy_http_version 1.1;
    proxy_set_header Connection "";
    chunked_transfer_encoding off;

    proxy_pass http://minio_backend; # If you are using docker-compose this would be the hostname i.e. minio
    # Health Check endpoint might go here. See
    # /minio/health/live;

nano /etc/nginx/conf.d/upstream.conf

upstream minio_backend {

Check nginx config and make sure there’s no errors

nginx -t

Now reload nginx

nginx -s reload

NGiNX should no be working and listening on :443 at

To install rustic it’s very easy. apt install rustic

Configure Rustic

We will export the required variables. This make it easier to run the restic commands. Make sure now to exit the shell while running the commands since the env variable need to be there for it to work


Now we will create the repo with the following

restic init

Now we will backup the server to the repo

restic --exclude={/dev,/media,/mnt,/proc,/run,/sys,/tmp,/var/tmp,/var/lib/mysql} backup /

This might take a while. Now your server will be backed up once completed. Also remember if you’re backing up a mysql server you’ll want to dump the mysql databases somewhere since this script doesn’t backup the /var/lib/mysql to make sure the DB doesn’t get corrupted.

If you’d like to prune (cleanup) old files the below is what I recommend

restic forget --prune --keep-daily 5 --keep-weekly 15 --keep-monthly 15

Now whenever you’d like to run a backup all you have to do it export the variables above and run the backup command.

If you’d like to view snapshots it’s as easy as the following

restic snapshots