From 030305fc22b16851935de4dc52f912c550bdbd09 Mon Sep 17 00:00:00 2001 From: Trygve Laugstøl Date: Wed, 15 May 2019 13:58:42 +0200 Subject: o New borg. --- ansible/borg/borg.yml | 43 +++++++++++++++ ansible/borg/files/borg/birgitte/ssh-key | 25 +++++++++ ansible/borg/files/borg/birgitte/ssh-key.pub | 10 ++++ ansible/borg/files/borg/conflatorio/ssh-key | 26 +++++++++ ansible/borg/files/borg/conflatorio/ssh-key.pub | 10 ++++ .../group_vars/borg-malabaricus/borg-secrets.yml | 18 +++++++ ansible/borg/host_vars/conflatorio/borg.yml | 0 ansible/inventory | 13 +++++ ansible/roles/borg-client/defaults/main.yml | 2 + ansible/roles/borg-client/handlers/main.yml | 3 ++ ansible/roles/borg-client/tasks/main.yml | 59 ++++++++++++++++++++ ansible/roles/borg-client/templates/bin/tergum | 24 +++++++++ .../roles/borg-client/templates/bin/tergum-post | 18 +++++++ ansible/roles/borg-job/defaults/main.yml | 6 +++ ansible/roles/borg-job/handlers/main.yml | 8 +++ ansible/roles/borg-job/tasks/main.yml | 60 +++++++++++++++++++++ ansible/roles/borg-target/defaults/main.yml | 6 +++ ansible/roles/borg-target/tasks/borg-init.yml | 47 ++++++++++++++++ ansible/roles/borg-target/tasks/main.yml | 62 ++++++++++++++++++++++ 19 files changed, 440 insertions(+) create mode 100644 ansible/borg/borg.yml create mode 100644 ansible/borg/files/borg/birgitte/ssh-key create mode 100644 ansible/borg/files/borg/birgitte/ssh-key.pub create mode 100644 ansible/borg/files/borg/conflatorio/ssh-key create mode 100644 ansible/borg/files/borg/conflatorio/ssh-key.pub create mode 100644 ansible/borg/group_vars/borg-malabaricus/borg-secrets.yml create mode 100644 ansible/borg/host_vars/conflatorio/borg.yml create mode 100644 ansible/roles/borg-client/defaults/main.yml create mode 100644 ansible/roles/borg-client/handlers/main.yml create mode 100644 ansible/roles/borg-client/tasks/main.yml create mode 100644 ansible/roles/borg-client/templates/bin/tergum create mode 100644 ansible/roles/borg-client/templates/bin/tergum-post create mode 100644 ansible/roles/borg-job/defaults/main.yml create mode 100644 ansible/roles/borg-job/handlers/main.yml create mode 100644 ansible/roles/borg-job/tasks/main.yml create mode 100644 ansible/roles/borg-target/defaults/main.yml create mode 100644 ansible/roles/borg-target/tasks/borg-init.yml create mode 100644 ansible/roles/borg-target/tasks/main.yml (limited to 'ansible') diff --git a/ansible/borg/borg.yml b/ansible/borg/borg.yml new file mode 100644 index 0000000..b93780d --- /dev/null +++ b/ansible/borg/borg.yml @@ -0,0 +1,43 @@ +- hosts: + - malabaricus + roles: + - role: borg-target + tags: borg-target + become: yes + vars: + borg_target__clients: + conflatorio: + state: present + repos: + home: + db: + birgitte: + state: present + repos: + home: + +- hosts: + - conflatorio + roles: + - role: borg-client + tags: borg-client + become: yes + +- hosts: + - conflatorio + roles: + - role: borg-job + tags: borg-job + become: yes + vars: + borg_job__target: malabaricus.trygvis.io + borg_job__username: borg + borg_job__name: home + borg_job__on_calendar: daily + borg_job__settings: + patterns: | + P sh + R / + + /home + - /home/*/ownCloud + - /home/*/Nextcloud diff --git a/ansible/borg/files/borg/birgitte/ssh-key b/ansible/borg/files/borg/birgitte/ssh-key new file mode 100644 index 0000000..7c66e05 --- /dev/null +++ b/ansible/borg/files/borg/birgitte/ssh-key @@ -0,0 +1,25 @@ +$ANSIBLE_VAULT;1.1;AES256 +39616435363335396263373838383264356339303335303936313032613836326236383430626538 +3738363238363662643937353238306230663365366463390a333561333938323737326434346439 +34643736356564376162363633363462353534636137343665333365386439373261333734343430 +6362643433633263620a323831366231333738386638663037363164383962626135383566643237 +32363563333033646533306164663838356134383837653339616232373962376432373063633930 +35346432663838383462613537346137383837313765366463303034343562646532626364303364 +37303431653935626531316334646135623836383035343435393435373436326430646133633465 +62386134343535656437376664666230366463633432633130366365366531633937633538306431 +39636463313330623631316664626139393563303565393635623031353432303531653434633939 +61386538323664303230356464313233353338303630666532323630613134616335636365643137 +39306463323631636335663465356565353765646161653562663535353537316534363935653731 +62663561336566646234616665336463303932373162666238303431346231656630306231616432 +36666330393661313533666531373761383161336161323161663235643737626263373337393261 +30306130343531323935316131656330653231643336633735373336316663663836323039636630 +32303463633339356264306535303161613862376333346330373262613236383136303433653731 +34366636613435643263653834336636386530343838373635393331646634366634303839626161 +62373033616432303864363433343632383034643663353532313966666135376234326236383633 +66613762633135313938303364333738313639373165333063323636656161666535663865333463 +61333835376435313038303963306339363138636532613434336335646335383265306338383939 +64626638333663313333393236346263333265343463306137343364323437303931303264643662 +64316361383632366363646533633733343530666265346166323862316363643832656364313130 +63356265393736363538643262646261626337366162666338623163306533393231646433393663 +34636164636166393637643836343938386533653861303066663939333731643162313463346462 +61613563653139623432 diff --git a/ansible/borg/files/borg/birgitte/ssh-key.pub b/ansible/borg/files/borg/birgitte/ssh-key.pub new file mode 100644 index 0000000..c9778a2 --- /dev/null +++ b/ansible/borg/files/borg/birgitte/ssh-key.pub @@ -0,0 +1,10 @@ +$ANSIBLE_VAULT;1.1;AES256 +63376165646335383661373131643362393262303437376536313736316638616432346637343437 +3639623438363630306233623665326530323166653433640a353865613139303762363361653130 +32343835336138376133326231303031303133346338333262656436303466353932396563376564 +3739363739393263390a323763656165653965616637353266383538313865613866653437373065 +66363836376334366132626662366364303634333866333562353737396361656132653433386261 +36376335353232333832303938343535633735653338383562633864313936396135306166613466 +36643661646162373639633638313538383865333630646635383637636634373361623134316531 +32653163613161376662336366316237613835666138353730663466336330643639643430323739 +3338 diff --git a/ansible/borg/files/borg/conflatorio/ssh-key b/ansible/borg/files/borg/conflatorio/ssh-key new file mode 100644 index 0000000..008a1fa --- /dev/null +++ b/ansible/borg/files/borg/conflatorio/ssh-key @@ -0,0 +1,26 @@ +$ANSIBLE_VAULT;1.1;AES256 +34653933323431646362366231376636623532613535663532613664323830666133636334303937 +6437636464343732613531316232363939313131373130340a643631333439613466376261386431 +64346635343965323730643161343865623962653266343534303339303062333962383166633936 +3966333232373235640a353630323437336230316533363931336231306438333836643565623335 +66643834323539323936383764613838366532646538633239613961353531326334316439396339 +64393461383764336537333132303463613566633265396363323437636231643764323965626434 +64666562373365303230363937303466343538626165386235396534383136383634663232643465 +34326133653364353236366530643166316531656362326136373764323964633738613562343133 +64313038353663356366396337613466386461313135333862303466393630376531323864373437 +35323664396664643465626162353964353933323765656336343266623562336663303838616464 +33366637643039646363376437356164623936653832646231636364386131616663626262373436 +36316536646238306266653635333339623138356531343332623431363164363662363530626330 +64333131373937663039323863633563313038636338313461303538396634623732393561653064 +38653331313031613736306539643738336666663639313835623562363333333566376531356563 +37393631613233303866313361393863653663663330386530636365383336623366346663373731 +33356461396461626138643638656566653936373030633931643430363063363738306162353236 +63666437623631373939353937356639376133383931356438663365356433313039316633393166 +61343332326132623130343264353562363633343663353637373361383239623863373062363738 +33356438393364653833613635636564396332333235633636383231613233623431363338313633 +39386430366565326435396632316362666363663535356635623961363333396330343262303933 +30373134393536633337373434356633623663613531333861386438366335313430623235643634 +36306230383231373762373665326335323538346334653566343462306533623838353362653536 +64643638383035363739386439383861356661666339663662353535396564656331396237306135 +66363962393031396230363135313961386564393662373335376132333836333133636330363433 +3862 diff --git a/ansible/borg/files/borg/conflatorio/ssh-key.pub b/ansible/borg/files/borg/conflatorio/ssh-key.pub new file mode 100644 index 0000000..379ea4d --- /dev/null +++ b/ansible/borg/files/borg/conflatorio/ssh-key.pub @@ -0,0 +1,10 @@ +$ANSIBLE_VAULT;1.1;AES256 +62363039393235656365663736303332313265306434313639326139626564386361363061343463 +6432636435353563306162373066613830363831313230360a343164616530316138643765643934 +63306361386534646465393130313334306666646464353263316633326638343563333634653834 +6536633337383534390a373032396663656638646137656565323539363461373239623665363564 +35633636353839363533636666386263303335653538373266343465356537373430653363373265 +63336433626334393265363836633538353863363233343566666230663134313235653563346334 +66613135643435663837666464326463323865386535383462663430613438393333363532616363 +39333531396638303838396664313864383962363865353830623235373366363732616638366339 +32613037373530386461656565623264306137373561646531373737616138303133 diff --git a/ansible/borg/group_vars/borg-malabaricus/borg-secrets.yml b/ansible/borg/group_vars/borg-malabaricus/borg-secrets.yml new file mode 100644 index 0000000..9336f3b --- /dev/null +++ b/ansible/borg/group_vars/borg-malabaricus/borg-secrets.yml @@ -0,0 +1,18 @@ +$ANSIBLE_VAULT;1.1;AES256 +63386637353831373333643735383234383361643332373038363632393935653238623036623234 +3063383063323436396337356531313933626537353438360a353735666338336638343432306631 +38343963623261663933653735326264613964303138336630306431393864376465393362633963 +3264653032316333660a653932383264366633343361333934383961383461366637396138393530 +39646563386535656264636630323932303531653733343736653234663437666262656564363531 +64396138646364323039643762623835366363346264353538363431393063396666376534313832 +62356566306639333661663532363663646262353861396638323964373466656331336434656538 +30636262643335363763393139306262346339393563343737306639363962613836336633656439 +39393466373836386462303037663830383931383862663563343238643866303437346530323361 +31343139313366326634663335353235643832383064616161356565333432646130333131646337 +65356263313035396330343932363334333031623133363632623634303766383564353337333262 +32303739653738616632303664656334356666333830333931386635363437373237363138343836 +33393339303933306537356330353439623231656535663861633833323566626666336138323032 +37656665643861636363343131623838396338653034363833396538346364656235353431653339 +66643430306531383265346339623339666232363261653463333865386536393738353231376361 +30633765386237373763323837656165363431396136636662373430623937326366303834373064 +6132 diff --git a/ansible/borg/host_vars/conflatorio/borg.yml b/ansible/borg/host_vars/conflatorio/borg.yml new file mode 100644 index 0000000..e69de29 diff --git a/ansible/inventory b/ansible/inventory index 81f00bf..1f50459 100644 --- a/ansible/inventory +++ b/ansible/inventory @@ -119,6 +119,19 @@ all: ansible_connection: lxc_ssh ansible_ssh_extra_args: sz-test +# Borg + borg-malabaricus: + hosts: +# birgitte: + conflatorio: +# arius: +# vars: +# borg_client__server: malabaricus.trygvis.io + + borg_clients: + children: + borg_nas: + wireguard_wg-net1: hosts: akili: diff --git a/ansible/roles/borg-client/defaults/main.yml b/ansible/roles/borg-client/defaults/main.yml new file mode 100644 index 0000000..ff82ed3 --- /dev/null +++ b/ansible/roles/borg-client/defaults/main.yml @@ -0,0 +1,2 @@ +borg_client__ssh_key: "borg/{{ ansible_hostname }}/ssh-key" + diff --git a/ansible/roles/borg-client/handlers/main.yml b/ansible/roles/borg-client/handlers/main.yml new file mode 100644 index 0000000..970492f --- /dev/null +++ b/ansible/roles/borg-client/handlers/main.yml @@ -0,0 +1,3 @@ +- name: systemctl daemon-reload + systemd: + daemon_reload: true diff --git a/ansible/roles/borg-client/tasks/main.yml b/ansible/roles/borg-client/tasks/main.yml new file mode 100644 index 0000000..d5767cd --- /dev/null +++ b/ansible/roles/borg-client/tasks/main.yml @@ -0,0 +1,59 @@ +- tags: packages + apt: + name: + - borgbackup + install_recommends: no + +- name: "mkdir /etc/tergum" + file: + path: "/etc/tergum" + state: directory + mode: u=rwx,go= + owner: root + group: root + +- copy: + dest: /etc/tergum/ssh-key + src: "{{ borg_client__ssh_key }}" + mode: u=rwx,go= + owner: root + group: root + +- name: "/etc/systemd/system/tergum@.service" + copy: + dest: "/etc/systemd/system/tergum@.service" + content: | + [Unit] + Description=Borg backup + + [Service] + Type=oneshot + WorkingDirectory=/ + ExecStart=-/usr/bin/tergum %i + #ExecStartPost=-/usr/bin/tergum-post foo@example.org + SuccessExitStatus=0 1 + EnvironmentFile=/etc/tergum/jobs/%i/env + notify: + - systemctl daemon-reload + +- name: "/etc/systemd/system/tergum@.timer" + copy: + dest: "/etc/systemd/system/tergum@.timer" + content: | + [Unit] + Description=Borg + + [Install] + WantedBy=timers.target + notify: + - systemctl daemon-reload + +- template: + dest: "/usr/bin/{{ item }}" + src: "bin/{{ item }}" + mode: u=rwx,go=rx + owner: root + group: root + with_items: + - tergum + - tergum-post diff --git a/ansible/roles/borg-client/templates/bin/tergum b/ansible/roles/borg-client/templates/bin/tergum new file mode 100644 index 0000000..eaab95c --- /dev/null +++ b/ansible/roles/borg-client/templates/bin/tergum @@ -0,0 +1,24 @@ +#!/bin/bash + +set -euo pipefail + +cd / + +instance=$1; shift + +echo BORG_RSH="$BORG_RSH" +echo BORG_REPO="$BORG_REPO" + +echo "Doing backup for instance $instance" + +cmd=() +cmd+=(borg create) +cmd+=("--stats") +cmd+=("--exclude-from=/etc/tergum/jobs/$instance/excludes") +cmd+=("--patterns-from=/etc/tergum/jobs/$instance/patterns") +cmd+=("::{hostname}-{now:%Y-%m-%dT%H:%M:%S}") + +set -x +time "${cmd[@]}" + +borg info --last 1 diff --git a/ansible/roles/borg-client/templates/bin/tergum-post b/ansible/roles/borg-client/templates/bin/tergum-post new file mode 100644 index 0000000..647bf5b --- /dev/null +++ b/ansible/roles/borg-client/templates/bin/tergum-post @@ -0,0 +1,18 @@ +#!/bin/bash + +set -euo pipefail + +cd / + +instance=$1; shift + +/usr/sbin/sendmail -t < +Subject: Backup @ $HOSTNAME +Content-Transfer-Encoding: 8bit +Content-Type: text/plain; charset=UTF-8 + +$(systemctl status --full 2>&1) +$(journalctl --since today --unit tergum@$instance 2>&1) +ERRMAIL diff --git a/ansible/roles/borg-job/defaults/main.yml b/ansible/roles/borg-job/defaults/main.yml new file mode 100644 index 0000000..b5f3cbc --- /dev/null +++ b/ansible/roles/borg-job/defaults/main.yml @@ -0,0 +1,6 @@ +borg_job__on_calendar: daily +borg_job__default_excludes: + - /proc + - /dev + - /sys + - /run diff --git a/ansible/roles/borg-job/handlers/main.yml b/ansible/roles/borg-job/handlers/main.yml new file mode 100644 index 0000000..76e08ab --- /dev/null +++ b/ansible/roles/borg-job/handlers/main.yml @@ -0,0 +1,8 @@ +- name: systemctl daemon-reload + systemd: + daemon_reload: true + +- name: "service start tergum@{{ borg_job__name }}.timer" + service: + name: "tergum@{{ borg_job__name }}.timer" + state: restarted diff --git a/ansible/roles/borg-job/tasks/main.yml b/ansible/roles/borg-job/tasks/main.yml new file mode 100644 index 0000000..10076d6 --- /dev/null +++ b/ansible/roles/borg-job/tasks/main.yml @@ -0,0 +1,60 @@ +- name: Install packages + tags: packages + apt: + name: + - borgbackup + install_recommends: no + +- name: "mkdir /etc/tergum/jobs/{{ borg_job__name }}" + file: + path: "/etc/tergum/jobs/{{ borg_job__name }}" + state: directory + +- name: "/etc/tergum/jobs/{{ borg_job__name }}/env" + copy: + dest: "/etc/tergum/jobs/{{ borg_job__name }}/env" + content: | + BORG_REPO={{ borg_job__username }}@{{ borg_job__target }}:{{ ansible_hostname }}/{{ borg_job__name }} + BORG_RSH=ssh -i /etc/tergum/ssh-key + BORG_PASSPHRASE={{ borg__passphrases[ansible_hostname][borg_job__name] }} + +# BORG_KEYS_DIR +# BORG_SECURITY_DIR +# BORG_CACHE_DIR + +- name: "/etc/tergum/jobs/{{ borg_job__name }}/patterns" + copy: + dest: "/etc/tergum/jobs/{{ borg_job__name }}/patterns" + content: "{{ borg_job__settings.patterns }}" + +- name: "/etc/tergum/jobs/{{ borg_job__name }}/excludes" + vars: + excludes: "{{ borg_job__settings.excludes if borg_job__settings.excludes is defined else [] }}" + copy: + dest: "/etc/tergum/jobs/{{ borg_job__name }}/excludes" + content: | + {% for item in excludes %} + {{ item }} + {% endfor %} + {% for item in borg_job__default_excludes %} + {{ item }} + {% endfor %} + +- file: + path: "/etc/systemd/system/tergum@{{ borg_job__name }}.timer.d" + state: directory + +- copy: + dest: "/etc/systemd/system/tergum@{{ borg_job__name }}.timer.d/override.conf" + content: | + [Timer] + OnCalendar={{ borg_job__settings.on_calendar if borg_job__settings.on_calendar is defined else borg_job__on_calendar }} + notify: + - systemctl daemon-reload + +- meta: flush_handlers + +- systemd: + name: "tergum@{{ borg_job__name }}.timer" + enabled: yes + state: started diff --git a/ansible/roles/borg-target/defaults/main.yml b/ansible/roles/borg-target/defaults/main.yml new file mode 100644 index 0000000..734434a --- /dev/null +++ b/ansible/roles/borg-target/defaults/main.yml @@ -0,0 +1,6 @@ +borg_target__user: borg +borg_target__group: borg +borg_target__shell: /bin/bash +borg_target__home: /opt/borg + +borg_target__repos: diff --git a/ansible/roles/borg-target/tasks/borg-init.yml b/ansible/roles/borg-target/tasks/borg-init.yml new file mode 100644 index 0000000..21b86d6 --- /dev/null +++ b/ansible/roles/borg-target/tasks/borg-init.yml @@ -0,0 +1,47 @@ +- with_items: "{{ client.value.repos }}" + assert: + that: + - "item in borg_target__passphrases[client.key]" + fail_msg: "{{ item }} is missing from borg-secrets.yml" + success_msg: "" + +- set_fact: + ssh_key: "{{ client.value.ssh_key_path if client.value.ssh_key_path is defined else ('files/borg/' + client.key + '/ssh-key') }}" +- debug: var=ssh_key + +- with_items: "{{ client.value.repos }}" + name: mkdir client dir + file: + path: "{{ path | dirname }}" + state: directory + owner: "{{ borg_target__user }}" + group: "{{ borg_target__group }}" + vars: + path: "{{ borg_target__home }}/repos/{{ client.key }}/{{ item }}" + +- with_items: "{{ client.value.repos }}" + name: borg init + become_user: "{{ borg_target__user }}" + command: "borg init --encryption repokey {{ path }}" + args: + creates: "{{ path }}" + environment: + BORG_PASSPHRASE: "{{ borg_target__passphrases[client.key][item] }}" + vars: + path: "{{ borg_target__home }}/repos/{{ client.key }}/{{ item }}" + +- local_action: + module: stat + path: "{{ ssh_key }}" + register: ssh_key_stat + +- local_action: + module: file + path: "{{ (playbook_dir + '/' + ssh_key) | dirname }}" + state: directory + become: no + +- name: Generating SSH key + local_action: command ssh-keygen -t ed25519 -N "" -f "{{ ssh_key }}" -C "borg@{{ client.key }}" + when: not ssh_key_stat.stat.exists + become: no diff --git a/ansible/roles/borg-target/tasks/main.yml b/ansible/roles/borg-target/tasks/main.yml new file mode 100644 index 0000000..c3b8693 --- /dev/null +++ b/ansible/roles/borg-target/tasks/main.yml @@ -0,0 +1,62 @@ +- name: Install packages + tags: packages + apt: + name: + - borgbackup + install_recommends: no + +- name: Create unix group + become: yes + group: + name: "{{ borg_target__group }}" + system: yes + +- name: Create unix user + become: yes + user: + name: "{{ borg_target__user }}" + group: "{{ borg_target__group }}" + shell: "{{ borg_target__shell }}" + home: "{{ borg_target__home }}" + system: yes + +- name: mkdir repos + file: + path: "{{ borg_target__home }}/repos" + state: directory + mode: u=rwx,go= + owner: "{{ borg_target__user }}" + group: "{{ borg_target__group }}" + +- with_dict: "{{ borg_target__clients }}" + file: + path: "{{ borg_target__home }}/repos/{{ item.key }}" + state: directory + +- include_tasks: borg-init.yml + with_dict: "{{ borg_target__clients }}" + loop_control: + loop_var: client + +- file: + path: "{{ borg_target__home }}/.ssh" + state: directory + mode: u=rx,go= + owner: "{{ borg_target__user }}" + group: "{{ borg_target__group }}" + +- name: authorized_keys + tags: xxx + copy: + dest: "{{ borg_target__home }}/.ssh/authorized_keys" + content: | + tilde={{ '~borg' | expanduser }} + {% for client, config in borg_target__clients.items() %} + {% set state=config.state | default('present') %} + # Client: {{ client }}, state={{state}} + {% if state == 'present' %} + {% set key=lookup('file', 'borg/' + client + '/ssh-key.pub') %} + command="cd {{ borg_target__home }}/repos && borg serve --append-only{% for r in config.repos %} --restrict-to-repository {{ client }}/{{ r }}{% endfor %}",no-port-forwarding,no-X11-forwarding,no-pty,no-agent-forwarding,no-user-rc {{ key }} + {% endif %} + {% endfor %} +# " -- cgit v1.2.3