sysrestic

command module
v0.1.0 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Jul 11, 2017 License: AGPL-3.0 Imports: 10 Imported by: 0

README

= sysrestic: encapsulate restic & your laptop
:toc:
:LVMencryption: https://wiki.archlinux.org/index.php/Dm-crypt/Encrypting_an_entire_system
:slocRefBin: https://github.com/jzacsh/bin/blob
:homeScript: {slocRefBin}/b73710888c23d/share/resticw.sh
:systemScript: {slocRefBin}/b73710888c23d/share/borgw_system.sh
:golangforkat: 4031a8c162765b
:olddocefforts: https://github.com/jzacsh/sysrestic/tree/{golangforkat}#overview-usage-how-to
:resticurl: https://restic.github.io
:whatisrepo: https://restic.readthedocs.io/en/stable/#quick-start
:excludes: https://restic.readthedocs.io/en/stable/manual.html?highlight=exclude
:resticusage: https://restic.github.io/#quickstart
:cistatus: https://travis-ci.org/jzacsh/sysrestic
:jzacshegexclude: https://github.com/jzacsh/dotfiles/blob/94d0f80eabe/.config/sysrestic.exclude
:systemdmanlimit: https://www.freedesktop.org/software/systemd/man/systemd.exec.html#LimitCPU=

Facilitates system-wide backup for an encrypted drive on a personal computer,
using {resticurl}[`restic`].

image:{cistatus}.svg?branch=master["Build Status", link="{cistatus}"]

== Motivation

This project provides two things for my personal use footnoteref:[usecase, I
assume `/` is {LVMencryption}[encrypted somehow] and I just want local-only
backups for my sanity but not for production robustness]:

1. Debian *package*: a `.deb` for me to `dpkg -i` and forget about
2. `sysrestic` *exclude-files* logic: a local binary to aggregate some ASCII
    {excludes}[excludes] files for me, in a semi-predictable way

== Installing & Updating

Everything below assumes you:

a. know what the `restic` {resticurl}[backup program] is; go check it out!
b. are on Debian...ish
c. have a `restic` {whatisrepo}[repo] somewhere on local disk +
  _(or plan to `restic init` one soon...)_


.clean slate; skip if no git repo
----
$ git clone github.com/jzacsh/sysrestic && cd sysrestic/
$ git archive --output /tmp/sysrestic.tgz master --prefix sysrestic/
$ cd /tmp/ && tar -xf sysrestic.tgz && cd sysrestic
----

.build
----
$ make deb
go build ./...
go build -o sysrestic
sudo --remove-timestamp
mkdir -p sysrestic_0.1/usr/lib/sysrestic/bin
mkdir -p sysrestic_0.1/usr/lib/sysrestic/systemd
mkdir -p sysrestic_0.1/etc/
mkdir -p sysrestic_0.1/DEBIAN
mkdir -p sysrestic_0.1/usr/lib/systemd/system/
mkdir -p sysrestic_0.1/etc/systemd/system/sysrestic.service.d
cp sysrestic sysrestic_0.1/usr/lib/sysrestic/bin/
cp debian/system.exclude sysrestic_0.1/usr/lib/sysrestic/default.exclude
cp debian/system.exclude sysrestic_0.1/etc/sysrestic.exclude
cp debian/systemd.conf   sysrestic_0.1/etc/systemd/system/sysrestic.service.d/systemd.conf
cp debian/systemd.conf   sysrestic_0.1/usr/lib/sysrestic/systemd/example.conf
cp debian/sysrestic.service sysrestic_0.1/usr/lib/sysrestic/systemd/sysrestic.service
cp debian/sysrestic.timer   sysrestic_0.1/usr/lib/sysrestic/systemd/sysrestic.timer
cd sysrestic_0.1/usr/lib/systemd/system/ && ln -s /usr/lib/sysrestic/systemd/sysrestic.service
cd sysrestic_0.1/usr/lib/systemd/system/ && ln -s /usr/lib/sysrestic/systemd/sysrestic.timer
echo /etc/sysrestic.exclude >> sysrestic_0.1/DEBIAN/conffiles
echo /etc/systemd/system/sysrestic.service.d/systemd.conf >> sysrestic_0.1/DEBIAN/conffiles
chmod 600 sysrestic_0.1/etc/systemd/system/sysrestic.service.d/systemd.conf
cp debian/control sysrestic_0.1/DEBIAN/
sed --in-place "s/VERSION_HERE/0.1/g" sysrestic_0.1/DEBIAN/control
sudo chown -R root:root sysrestic_0.1
[sudo] password for jzacsh:
sudo fakeroot dpkg-deb --build sysrestic_0.1
dpkg-deb: building package 'sysrestic' in 'sysrestic_0.1.deb'.
success; now consider `sudo` removing sysrestic_0.1
----

.install
----
$ sudo rm sysrestic_0.1/ -rf # <1>
$ sudo dpkg -i sysrestic_0.1.deb # <2>
----
<1> don't forget to cleanup my `root` mess
<2> *this* is the actual install

.if you're curious
----
$ find /usr/lib/sysrestic/ \
       /etc/sysrestic* \
       /usr/lib/systemd/system/sysrestic* \
       /etc/systemd/system/sysrestic* -exec file {} +;

/usr/lib/systemd/system/sysrestic.timer:              symbolic link to /usr/lib/sysrestic/systemd/sysrestic.timer
/usr/lib/systemd/system/sysrestic.service:            symbolic link to /usr/lib/sysrestic/systemd/sysrestic.service
/usr/lib/sysrestic/:                                  directory
/usr/lib/sysrestic/systemd:                           directory
/usr/lib/sysrestic/systemd/sysrestic.timer:           ASCII text
/usr/lib/sysrestic/systemd/sysrestic.service:         ASCII text
/usr/lib/sysrestic/systemd/example.conf:              ASCII text
/usr/lib/sysrestic/default.exclude:                   ASCII text
/usr/lib/sysrestic/bin:                               directory
/usr/lib/sysrestic/bin/sysrestic:                     ELF 64-bit LSB executable, x86-64, version 1 (SYSV), dynamically linked, interpreter /lib64/ld-linux-x86-64.so.2, not stripped
/etc/systemd/system/sysrestic.timer:                  symbolic link to /usr/lib/sysrestic/systemd/sysrestic.timer
/etc/systemd/system/sysrestic.service:                symbolic link to /usr/lib/sysrestic/systemd/sysrestic.service
/etc/systemd/system/sysrestic.service.d:              directory
/etc/systemd/system/sysrestic.service.d/systemd.conf: regular file, no read permission
/etc/sysrestic.exclude:                               ASCII text
----

[[systemwideconf]]
.configure: set `$SYSRESTIC_REPO` & `$RESTIC_PASSWORD`
----
$ $EDITOR /etc/systemd/system/sysrestic.service.d/systemd.conf
$ $EDITOR /etc/sysrestic.exclude # <1>
----
<1> optional

.systemd: tell your machine
----
$ systemctl daemon-reload
$ systemctl enable sysrestic.{timer,service} # <1>
$ systemctl start sysrestic.timer
$ systemctl status sysrestic.{timer,service}
----
<1> here & below are vanilla commands; part of regular usage

== Usage

=== One-Time Configurations

The idea of this repo is backups run without you're being involved. Aside from
<<systemwideconf, system-wide configuration>> already mentioned, you'll want to
make your own exclude file in `$HOME/.config/sysrestic.exclude` or
`$HOME/.sysrestic.exclude`. {jzacshegexclude}[Eg]:

----
back/local
.android/
.cinnamon/
.cache/
.config/google-chrome/
.mozilla/firefox/
.gnome/apps/
.gradle/
.npm/
.thumbnails/
.tor-browser*/
.opam/
.local/share/lxc/*/rootfs
tmp/
usr/local/vm/
usr/local/bin/
----

That's it. Combining all exclude files, across all `$HOME` dirs on your system,
together with your system exclude file _(`/etc/sysrestic.exclude`)_  is really
<<sysrestichelp, all that `sysrestic` does>>, aside from finally calling
`restic` on your behalf.

=== Restic & Systemd

Other than such period configuration changes, Systemd is now your interface for
this repository's impact on your machine. Of course the usual applies
{resticusage}[as an end-user of restic], eg, poke at your backups:
`sudo restic -r /srv/sysrestic/restic mount /tmp/sysbackups`

.modify frequency of backups
----
$ $EDITOR /etc/systemd/system/sysrestic.timer
----

.check latest status
----
$ systemctl status sysrestic.{timer,service}
● sysrestic.timer - Periodically backup via sysrestic
   Loaded: loaded (/usr/lib/sysrestic/systemd/sysrestic.timer; enabled; vendor preset: enabled)
   Active: active (waiting) since Tue 2017-07-11 14:16:48 EDT; 45min ago

Jul 11 14:16:48 mylaptop systemd[1]: Started Periodically backup via sysrestic.

● sysrestic.service - System-wide backups to a restic repo with excludes for everyone
   Loaded: loaded (/usr/lib/sysrestic/systemd/sysrestic.service; linked; vendor preset: enabled)
  Drop-In: /etc/systemd/system/sysrestic.service.d
           └─systemd.conf
   Active: active (running) since Tue 2017-07-11 14:45:54 EDT; 15min ago
     Docs: https://github.com/jzacsh/sysrestic
 Main PID: 32072 (sysrestic)
    Tasks: 38
   Memory: 3.5G
      CPU: 16min 27.190s
   CGroup: /system.slice/sysrestic.service
           ├─32072 /usr/lib/sysrestic/bin/sysrestic /srv/sysrestic/restic /etc/sysrestic.exclude
           └─32084 restic backup --repo /srv/sysrestic/restic --exclude-file /tmp/sysrestic-unified-excludes_122220733 /

Jul 11 14:45:54 mylaptop systemd[1]: Started System-wide backups to a restic repo with excludes for everyone.
Jul 11 14:45:54 mylaptop bash[32072]: 25 excludes from 1 of 1 users written to /tmp/sysrestic-unified-excludes_122220733
Jul 11 14:45:55 mylaptop bash[32072]: scan [/]
Jul 11 14:46:23 mylaptop bash[32072]: [0:28] 103269 directories, 566652 files, 22.123 GiB
Jul 11 14:46:23 mylaptop bash[32072]: scanned 103269 directories, 566652 files in 0:28
----

.watch logs
----
$ journalctl --pager-end --follow sysrestic.service
Jul 11 14:45:54 mylaptop systemd[1]: Started System-wide backups to a restic repo with excludes for everyone.
-- Subject: Unit sysrestic.service has finished start-up
-- Defined-By: systemd
-- Support: http://lists.freedesktop.org/mailman/listinfo/systemd-devel
--
-- Unit sysrestic.service has finished starting up.
--
-- The start-up result is done.
Jul 11 14:45:54 mylaptop bash[32072]: 25 excludes from 1 of 1 users written to /tmp/sysrestic-unified-excludes_122220733
Jul 11 14:45:55 mylaptop bash[32072]: scan [/]
Jul 11 14:46:23 mylaptop bash[32072]: [0:28] 103269 directories, 566652 files, 22.123 GiB
Jul 11 14:46:23 mylaptop bash[32072]: scanned 103269 directories, 566652 files in 0:28
Jul 11 15:17:51 mylaptop bash[32072]: can not obtain extended attribute system.posix_acl_access for /sys:
Jul 11 15:17:51 mylaptop bash[32072]: can not obtain extended attribute system.posix_acl_default for /sys:
Jul 11 15:29:42 mylaptop bash[32072]: [43:18] 100.00%  0B/s  43.439 GiB / 22.123 GiB  674476 / 669921 items  0 errors  ETA 0:00
Jul 11 15:29:42 mylaptop bash[32072]: duration: 43:18, 8.72MiB/s
Jul 11 15:29:42 mylaptop bash[32072]: snapshot db8f7eff saved
Jul 11 15:29:42 mylaptop bash[32072]: Restic exited OK. Cleaning up... done.
----

NOTE: duration of the above backup, in my `journalctl` output, was during a
*first* backup _(ie: longer than usual)_.

.control backups
----
$ systemctl stop sysrestic.service
$ systemctl restart sysrestic.service
----

.determine next backups
----
$ systemctl list-timers sysrestic.timer
NEXT                         LEFT          LAST                         PASSED    UNIT            ACTIVATES
Tue 2017-07-11 16:15:54 EDT  1h 15min left Tue 2017-07-11 14:16:48 EDT  43min ago sysrestic.timer sysrestic.service

1 timers listed.
Pass --all to see loaded but inactive timers, too.
----

.stop upcoming backups
----
$ systemctl stop sysrestic.timer
----

.update if you've moved your `restic` repo
----
$ $EDITOR /etc/systemd/system/sysrestic.service.d/systemd.conf # <1>
----
<1> specifically, change the `$SYSRESTIC_REPO` value

.tweak resources restic gets
----
$ printf '%s\n' 'CPUQuota=20%' LimitNICE=8 \
             >> /etc/systemd/system/sysrestic.service # <1>
$ systemctl daemon-reload
----
<1> read more about your options {systemdmanlimit}[in the systemd manual]

== Contributing

Despite remarks above, that this serves a highly personal use to my own laptop,
I'd be *happy* to patch or accept patches to make this useful for you too! If
you want a quick overview on *what* is installed, this README {olddocefforts}[as
of `{golangforkat}` walked through] exactly what I ultimately tried to encode
into the debian package.

=== `sysrestic` command

Most of this repo deals with the small `sysrestic` tool. Debian packaging is
only addressed by `./debian/` and its contents, and the make target `deb` & co.

.build & test: `sysrestic`, `test`
----
$ make sysrestic test
go build ./...
go build -o sysrestic
go test ./...
ok  	github.com/jzacsh/sysrestic	0.008s
ok  	github.com/jzacsh/sysrestic/exclude	0.025s
ok  	github.com/jzacsh/sysrestic/file	0.021s
ok  	github.com/jzacsh/sysrestic/usr	0.016s
----

.make `all`: `clean`, `test`, `sysrestic`
----
$ make clean
rm -f -rf sysrestic sysrestic_*

# snipped ... same as above
----

Though I don't see any reason why one would find and call the `sysrestic` tool
themselves, here's what its help output would say:

[[sysrestichelp]]
----
$ sysrestic --help
sysrestic - an exclude-file joiner for system backups with restic

Synopsis:
  sysreestic [help] RESTIC_REPO EXCLUDE_FILE

Description:
  Execs to restic[1] to backup / to RESTIC_REPO path with an automatically
  built list for restic's --exclude-file option.

Outline:
  1. visits every $HOME on the system
  2. reads said $HOME's ~/.config/sysrestic.exclude or ~/.sysrestic.exclude
  3. creates a new exclude-file, unifying all $HOME's excludes w/EXCLUDE_FILE
  4. shells out to restic:
       restic backup \
          --repo RESTIC_REPO \
          --exclude-file /path/to/temporary/unified/exclude-list \
          /

Reading Exclude Files:
  For both system and users' exclude files, empty files are okay.

  All lines in a user's exclude file are read as relative to their home.
  Leading slashes are ignored. Not much care has been taken beyond this to
  prevent bad things (eg: users may be able to exclude important files that do
  not belong to them using hard-link walks, like "../../../").

[1]: https://restic.github.io
----

NOTE: until `{golangforkat}`, this project was originally a documentation effort
so I would understand what/how my backup script was installed when I'd
inevitably forget 6 months down the line. Now this is a locally-built debian
package that is hopefully just as self-documentation, thanks to tools like `dpkg
-S ...` and `dpkg-query`, `apt remove`, etc.

Documentation

The Go Gopher

There is no documentation for this package.

Directories

Path Synopsis

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL