feat: Create role

This commit is contained in:
pulsar89.5 2023-03-07 00:13:54 +01:00 committed by pulsar89.5
parent 9864366433
commit b993d55f55
13 changed files with 466 additions and 3 deletions

View File

@ -1,3 +1,3 @@
# role_modele
# role_borgmatic
Modèle
Deploy and configure borgmatic.

57
defaults/main.yml Normal file
View File

@ -0,0 +1,57 @@
---
# defaults file for borgmatic
# Define path to store borgmatic configuration and ssh keys
borgmatic_conf_path: /etc/borgmatic.d
# Configure bormatic
borgmatic_checks:
- name: repository
frequency: 4 weeks
- name: extract
frequency: 2 weeks
borgmatic_healthchecks: ""
borgmatic_exclude_patterns: []
borgmatic_repositories: []
# Exemple:
# - label: default
# path: ssh://user@backupserver/./sourcehostname.borg
borgmatic_source_directories: []
borgmatic_retention:
daily: 7
monthly: 0
weekly: 4
borgmatic_name: "{{ inventory_hostname }}_{now}"
borgmatic_compression: lz4
borgmatic_passphrase: ""
borgmatic_actions: {}
borgmatic_mariadb_enabled: false
borgmatic_postgresql_enabled: false
borgmatic_restore_first: true
# targets
## BorgServer configuration
borgmatic_server: {}
# Example:
# host: borg.service.gaia.ykn.fr
# repo_path: /srv/borg
# user: borg
# group: borg
## BorgWarehouse configuration
borgmatic_borgwarehouse_url: ""
borgmatic_borgwarehouse_key: ""
borgmatic_borgwarehouse_alias: "{{ inventory_hostname }}"
borgmatic_borgwarehouse_sshPublicKey: ""
borgmatic_borgwarehouse_storageSize: 100
borgmatic_borgwarehouse_comment: ""
borgmatic_borgwarehouse_alert: 90000 # one day
borgmatic_borgwarehouse_lanCommand: true
borgmatic_borgwarehouse_appendOnlyMode: false

28
handlers/main.yml Normal file
View File

@ -0,0 +1,28 @@
---
# handlers file for borgmatic
- name: Initialize repository
ansible.builtin.command:
argv:
- "{{ which_borgmatic.stdout }}"
- init
- --encryption
- repokey
when: repo_infos | length == 0
become: true
loop: "{{ borgmatic_repositories }}"
- name: Restore repository
ansible.builtin.command:
argv:
- "{{ which_borgmatic.stdout }}"
- extract
- --archive
- latest
- --destination
- /
when:
- repo_infos | length > 0
- borgmatic_restore_first
become: true
loop: "{{ borgmatic_repositories }}"

View File

@ -1,7 +1,7 @@
galaxy_info:
namespace: ykn
author: pulsar89.5
description: Rôle modèle
description: Deploy and configure borgmatic
license: GPL-3.0-or-later

109
tasks/configuration.yml Normal file
View File

@ -0,0 +1,109 @@
---
# tasks file for borgmatic
#
- name: Get path to borgmatic
ansible.builtin.command:
cmd: which borgmatic
become: true
register: which_borgmatic
- name: Create configuration example
ansible.builtin.command:
argv:
- "{{ which_borgmatic.stdout }}"
- config
- generate
- --destination
- "{{ borgmatic_conf_path }}/config.yaml"
creates: "{{ borgmatic_conf_path }}/config.yaml"
become: true
- name: Create keys pair
community.crypto.openssh_keypair:
path: "{{ borgmatic_conf_path }}/id_ed25519"
comment: borgmatic@{{ inventory_hostname }}
type: ed25519
become: true
- name: Get public key content
ansible.builtin.slurp:
src: "{{ borgmatic_conf_path }}/id_ed25519.pub"
become: true
register: id_ed25519
- name: Import task to manage borgwarehouse repository
ansible.builtin.import_tasks:
file: configuration_borgwarehouse.yml
when: borgmatic_borgwarehouse_url | length > 0
- name: Import task to manage borgserver repository
ansible.builtin.import_tasks:
file: configuration_borgserver.yml
when: borgmatic_server | length > 0
- name: Deploy ssh configuration
ansible.builtin.blockinfile:
path: /root/.ssh/config
owner: root
group: root
mode: u=rw,g=r,o=
create: true
marker: "# {mark} ANSIBLE MANAGED BLOCK for role_borgmatic"
block: |
{% for repository in borgmatic_repositories %}
Host {{ repository.path | ansible.builtin.urlsplit('hostname') }}
Compression yes
Protocol 2
PreferredAuthentications=publickey
StrictHostKeyChecking no
UserKnownHostsFile /dev/null
IdentityFile {{ borgmatic_conf_path }}/id_ed25519
IdentitiesOnly yes
{% endfor %}
become: true
- name: Deploy borgmatic configuration
ansible.builtin.template:
src: config.yaml.j2
dest: "{{ borgmatic_conf_path }}/config.yaml"
owner: root
group: root
mode: u=rw,g=,o=
validate: borgmatic config validate --config %s
become: true
notify:
- Initialize repository
- Restore repository
- name: Deploy borgmatic.service
ansible.builtin.template:
src: borgmatic.service.j2
dest: /etc/systemd/system/borgmatic.service
owner: root
group: root
mode: u=rw,g=r,o=r
become: true
- name: Ensure borgmatic.service is disabled
ansible.builtin.systemd:
enabled: false
state: stopped
name: borgmatic.service
become: true
- name: Deploy borgmatic.timer
ansible.builtin.template:
src: borgmatic.timer.j2
dest: /etc/systemd/system/borgmatic.timer
owner: root
group: root
mode: u=rw,g=r,o=r
become: true
- name: Enable and start borgmatic.service
ansible.builtin.systemd:
daemon_reload: true
enabled: true
state: started
name: borgmatic.timer
become: true

View File

@ -0,0 +1,20 @@
---
- name: Create repository on borg server
ansible.builtin.file:
path: "{{ borgmatic_server.repo_path }}/{{ inventory_hostname }}"
state: directory
owner: "{{ borgmatic_server.user }}"
group: "{{ borgmatic_server.group }}"
mode: u=rwX,g=rX,o=
become: true
delegate_to: "{{ borgmatic_server.host }}"
- name: Deploy public key on borg server
ansible.posix.authorized_key:
user: "{{ borgmatic_server.user }}"
state: present
key: "{{ key['content'] | b64decode }}"
key_options: 'command="cd {{ borgmatic_server.repo_path }}/{{ inventory_hostname }};borg serve --restrict-to-path {{ borgmatic_server.repo_path }}/{{ inventory_hostname }}",restrict'
become: true
delegate_to: "{{ borgmatic_server.host }}"

View File

@ -0,0 +1,38 @@
---
- name: Get list of repositories
ansible.builtin.uri:
url: "{{ borgmatic_borgwarehouse_url }}/api/repo"
method: GET
headers:
Authorization: "Bearer {{ borgmatic_borgwarehouse_key }}"
Content-Type: "application/json"
body_format: json
return_content: true
register: repo_list
- name: Get repository informations
ansible.builtin.set_fact:
repo_infos: "{{ repo_list.json.repoList | selectattr('alias', 'equalto', inventory_hostname) }}"
- name: Create repository
ansible.builtin.uri:
url: "{{ borgmatic_borgwarehouse_url }}/api/repo/add"
method: POST
headers:
Authorization: "Bearer {{ borgmatic_borgwarehouse_key }}"
Content-Type: "application/json"
body_format: json
body: "{{ borgwarehouse_body }}"
when: repo_infos | length == 0
- name: Update repository
ansible.builtin.uri:
url: "{{ borgmatic_borgwarehouse_url }}/api/repo/id/{{ repo_infos[0].id }}/edit"
method: PATCH
headers:
Authorization: "Bearer {{ borgmatic_borgwarehouse_key }}"
Content-Type: "application/json"
body_format: json
body: "{{ borgwarehouse_body }}"
when: repo_infos | length > 0

39
tasks/installation.yml Normal file
View File

@ -0,0 +1,39 @@
---
# tasks file for borgmatic
- name: Install prerequisites
ansible.builtin.apt:
name:
- pipx
- build-essential
- libacl1-dev
- libacl1
- libb2-dev
- liblz4-dev
- libssl-dev
- libxxhash-dev
- libzstd-dev
- pkg-config
- python3
- python3-dev
- python3-pkgconfig
become: true
- name: Install packages
community.general.pipx:
state: latest
name: "{{ item }}"
install_deps: true
include_injected: true
become: true
environment:
PIPX_HOME: /opt/pipx
PIPX_BIN_DIR: /usr/local/bin
loop:
- borgbackup
- borgmatic
- name: Ensure binary installed by pipx are in the path # noqa: no-changed-when
ansible.builtin.command:
cmd: pipx ensurepath
become: true

10
tasks/main.yml Normal file
View File

@ -0,0 +1,10 @@
---
# tasks file for borgmatic
- name: Importer les tâches d'installation
ansible.builtin.include_tasks:
file: installation.yml
- name: Importer les tâches de configuration
ansible.builtin.import_tasks:
file: configuration.yml

View File

@ -0,0 +1,66 @@
# {{ ansible_managed }}
[Unit]
Description=borgmatic backup
Wants=network-online.target
After=network-online.target
# Prevent borgmatic from running unless the machine is plugged into power. Remove this line if you
# want to allow borgmatic to run anytime.
ConditionACPower=true
[Service]
Type=oneshot
# Security settings for systemd running as root, optional but recommended to improve security. You
# can disable individual settings if they cause problems for your use case. For more details, see
# the systemd manual: https://www.freedesktop.org/software/systemd/man/systemd.exec.html
LockPersonality=true
# Certain borgmatic features like Healthchecks integration need MemoryDenyWriteExecute to be off.
# But you can try setting it to "yes" for improved security if you don't use those features.
MemoryDenyWriteExecute=no
NoNewPrivileges=yes
PrivateDevices=yes
PrivateTmp=yes
ProtectClock=yes
ProtectControlGroups=yes
ProtectHostname=yes
ProtectKernelLogs=yes
ProtectKernelModules=yes
ProtectKernelTunables=yes
RestrictAddressFamilies=AF_UNIX AF_INET AF_INET6 AF_NETLINK
RestrictNamespaces=yes
RestrictRealtime=yes
RestrictSUIDSGID=yes
SystemCallArchitectures=native
SystemCallFilter=@system-service
SystemCallErrorNumber=EPERM
# To restrict write access further, change "ProtectSystem" to "strict" and uncomment
# "ReadWritePaths", "ReadOnlyPaths", "ProtectHome", and "BindPaths". Then add any local repository
# paths to the list of "ReadWritePaths" and local backup source paths to "ReadOnlyPaths". This
# leaves most of the filesystem read-only to borgmatic.
ProtectSystem=full
# ReadWritePaths=-/mnt/my_backup_drive
# ReadOnlyPaths=-/var/lib/my_backup_source
# This will mount a tmpfs on top of /root and pass through needed paths
# ProtectHome=tmpfs
# BindPaths=-/root/.cache/borg -/root/.config/borg -/root/.borgmatic
# May interfere with running external programs within borgmatic hooks.
CapabilityBoundingSet=CAP_DAC_READ_SEARCH CAP_NET_RAW
# Lower CPU and I/O priority.
Nice=19
CPUSchedulingPolicy=batch
IOSchedulingClass=best-effort
IOSchedulingPriority=7
IOWeight=100
Restart=no
# Prevent rate limiting of borgmatic log events. If you are using an older version of systemd that
# doesn't support this (pre-240 or so), you may have to remove this option.
LogRateLimitIntervalSec=0
# Delay start to prevent backups running during boot. Note that systemd-inhibit requires dbus and
# dbus-user-session to be installed.
ExecStartPre=sleep 1m
ExecStart=systemd-inhibit --who="borgmatic" --what="sleep:shutdown" --why="Prevent interrupting scheduled backup" {{ which_borgmatic.stdout }} --verbosity -1 --syslog-verbosity 1

View File

@ -0,0 +1,12 @@
# {{ ansible_managed }}
[Unit]
Description=Run borgmatic backup
[Timer]
OnCalendar=daily
Persistent=true
RandomizedDelaySec=3h
[Install]
WantedBy=timers.target

71
templates/config.yaml.j2 Normal file
View File

@ -0,0 +1,71 @@
---
# {{ ansible_managed }}
repositories:
{% for repository in borgmatic_repositories %}
- label: {{ repository.label }}
path: {{ repository.path }}
{% endfor %}
{% if borgmatic_exclude_patterns | length > 0 %}
exclude_patterns:
{% for pattern in borgmatic_exclude_patterns %}
- {{ pattern }}
{% endfor %}
{% endif %}
{% if borgmatic_source_directories | length > 0%}
source_directories:
{% for directory in borgmatic_source_directories %}
- {{ directory }}
{% endfor %}
{% endif %}
archive_name_format: {{ borgmatic_name }}
compression: {{ borgmatic_compression }}
encryption_passphrase: {{ borgmatic_passphrase }}
checks:
{% for check in borgmatic_checks %}
- name: {{ check.name }}
frequency: {{ check.frequency }}
{% endfor %}
healthchecks:
ping_url: {{ borgmatic_healthchecks }}
send_logs: false
# states:
# - finish
# - fail
{% if borgmatic_retention | length > 0 %}
{% for param, value in borgmatic_retention.items() %}
keep_{{ param }}: {{ value }}
{% endfor %}
{% endif %}
{% if borgmatic_actions | length > 0 %}
{% for param, values in borgmatic_actions.items() %}
{{ param }}:
{% for value in values %}
- {{ value }}
{% endfor %}
{% endfor %}
{% endif %}
{% if borgmatic_mariadb_enabled %}
mariadb_databases:
- name: all
format: sql
add_drop_database: true
{% endif %}
{% if borgmatic_postgresql_enabled %}
postgresql_databases:
- name: all
username: postgres
format: plain
pg_dump_command: sudo -u postgres pg_dump
pg_restore_command: sudo -u postgres pg_restore
psql_command: sudo -u postgres psql
{% endif %}

13
vars/main.yml Normal file
View File

@ -0,0 +1,13 @@
---
# vars file for borgmatic
borgwarehouse_body: >
{
"alert": {{ borgmatic_borgwarehouse_alert }},
"alias": "{{ borgmatic_borgwarehouse_alias }}",
"appendOnlyMode": {{ borgmatic_borgwarehouse_appendOnlyMode }},
"comment": "{{ borgmatic_borgwarehouse_comment }}",
"lanCommand": {{ borgmatic_borgwarehouse_lanCommand }},
"sshPublicKey": "{{ id_ed25519['content'] | b64decode | trim }}",
"storageSize": {{ borgmatic_borgwarehouse_storageSize | int }},
}