selfhostblocks/modules/contracts/databasebackup/docs/default.md
Pierre Penninckx 431dd058c5
Backup contracts for files and databases (#344)
This PR continues the work started in
https://github.com/ibizaman/selfhostblocks/pull/314

I had to create my own PR since I couldn't add commits on the fork.

---------

Co-authored-by: sivertism <10866270+sivertism@users.noreply.github.com>
2024-11-12 20:40:52 +00:00

2.9 KiB

Database Backup Contract

This NixOS contract represents a backup job that will backup everything in one database on a regular schedule.

It is a contract between a service that has database dumps to be backed up and a service that backs up databases dumps.

Contract Reference

These are all the options that are expected to exist for this contract to be respected.

id-prefix: contracts-databasebackup-options-
list-id: selfhostblocks-options
source: @OPTIONS_JSON@

Usage

A database that can be backed up will provide a databasebackup option. Such a service is a requester providing a request for a module provider of this contract.

What this option defines is, from the user perspective - that is you - an implementation detail but it will at least define how to create a database dump, the user to backup with and how to restore from a database dump.

Here is an example module defining such a databasebackup option:

{
  options = {
    myservice.databasebackup = mkOption {
      type = contracts.databasebackup.request;
      default = {
        user = "myservice";
        backupCmd = ''
          ${pkgs.postgresql}/bin/pg_dumpall | ${pkgs.gzip}/bin/gzip --rsyncable
        '';
        restoreCmd = ''
          ${pkgs.gzip}/bin/gunzip | ${pkgs.postgresql}/bin/psql postgres
        '';
      };
    };
  };
};

Now, on the other side we have a service that uses this backup option and actually backs up files. This service is a provider of this contract and will provide a result option.

Let's assume such a module is available under the databasebackupservice option and that one can create multiple backup instances under databasebackupservice.instances. Then, to actually backup the myservice service, one would write:

databasebackupservice.instances.myservice = {
  request = myservice.databasebackup;
  
  settings = {
    enable = true;

    repository = {
      path = "/srv/backup/myservice";
    };

    # ... Other options specific to backupservice like scheduling.
  };
};

It is advised to backup files to different location, to improve redundancy. Thanks to using contracts, this can be made easily either with the same databasebackupservice:

databasebackupservice.instances.myservice_2 = {
  request = myservice.backup;
  
  settings = {
    enable = true;
  
    repository = {
      path = "<remote path>";
    };
  };
};

Or with another module databasebackupservice_2!

Providers of the Database Backup Contract

Requester Blocks and Services