├── .drone.yml ├── .gitattributes ├── .github ├── config │ └── labels.yml └── workflows │ ├── CI.yml │ ├── autoassign.yml │ └── labelsync.yml ├── .hadolint.yaml ├── .wakatime-project ├── CHANGELOG.md ├── LICENCE.txt ├── README.md ├── base-fullbuild ├── .env.template ├── Dockerfile ├── data │ └── borgmatic.d │ │ ├── after-backup.example │ │ ├── before-backup.example │ │ ├── config.full.yaml.example │ │ ├── config.yaml │ │ ├── config.yaml.example │ │ └── failed-backup.example ├── requirements.txt └── root │ └── etc │ └── s6-overlay │ └── s6-rc.d │ ├── init-config-end │ ├── dependencies.d │ │ ├── base │ │ └── init-custom-packages │ ├── type │ └── up │ ├── init-custom-packages │ ├── run │ ├── type │ └── up │ ├── svc-cron │ ├── dependencies.d │ │ └── init-config-end │ ├── finish │ ├── run │ └── type │ └── user │ └── contents.d │ ├── init-custom-packages │ └── svc-cron ├── docker-compose.restore.yml ├── docker-compose.yml └── renovate.json /.drone.yml: -------------------------------------------------------------------------------- 1 | --- 2 | 3 | kind: pipeline 4 | type: docker 5 | name: FullBuild 6 | 7 | platform: 8 | os: linux 9 | arch: amd64 10 | 11 | steps: 12 | - name: Lint Dockerfile 13 | image: hadolint/hadolint:latest-alpine 14 | pull: if-not-exists 15 | commands: 16 | - hadolint base-fullbuild/Dockerfile* 17 | 18 | - name: FullBuild 19 | image: thegeeklab/drone-docker-buildx 20 | privileged: true 21 | 22 | settings: 23 | repo: modem7/borgmatic-docker 24 | purge: true 25 | compress: true 26 | no_cache: false 27 | build_args: BUILDKIT_INLINE_CACHE=1 28 | cache_from: modem7/borgmatic-docker:latest 29 | dockerfile: base-fullbuild/Dockerfile 30 | context: base-fullbuild/ 31 | platforms: # if it doesn't work run docker run --privileged --rm tonistiigi/binfmt --install all 32 | - linux/amd64 33 | - linux/arm64 34 | username: 35 | from_secret: docker_username 36 | password: 37 | from_secret: docker_password 38 | tags: 39 | - latest 40 | - 2.0.6-1.4.1 41 | 42 | - name: pushrm-dockerhub 43 | image: chko/docker-pushrm 44 | environment: 45 | DOCKER_USER: 46 | from_secret: docker_username 47 | DOCKER_PASS: 48 | from_secret: docker_password 49 | PUSHRM_FILE: README.md 50 | PUSHRM_SHORT: Multiarch Borgmatic with docker-cli 51 | PUSHRM_TARGET: modem7/borgmatic-docker 52 | when: 53 | status: 54 | - success 55 | 56 | - name: slack 57 | image: themaz/drone-slack 58 | settings: 59 | webhook: 60 | from_secret: slack_hook 61 | when: 62 | status: [ success, failure ] 63 | 64 | trigger: 65 | event: 66 | - custom 67 | -------------------------------------------------------------------------------- /.gitattributes: -------------------------------------------------------------------------------- 1 | ## GITATTRIBUTES FOR WEB PROJECTS 2 | # 3 | # These settings are for any web project. 4 | # 5 | # Details per file setting: 6 | # text These files should be normalized (i.e. convert CRLF to LF). 7 | # binary These files are binary and should be left untouched. 8 | # 9 | # Note that binary is a macro for -text -diff. 10 | ###################################################################### 11 | 12 | # Auto detect 13 | ## Handle line endings automatically for files detected as 14 | ## text and leave all files detected as binary untouched. 15 | ## This will handle all files NOT defined below. 16 | * text eol=lf 17 | 18 | # Source code 19 | *.bash text eol=lf 20 | *.bat text eol=crlf 21 | *.cmd text eol=crlf 22 | *.coffee text 23 | *.cpp text diff=cpp 24 | *.cs text diff=csharp 25 | *.css text diff=css 26 | *.go text diff=golang 27 | *.h text diff=cpp 28 | *.htm text diff=html 29 | *.html text diff=html 30 | *.inc text 31 | *.ini text 32 | *.java text diff=java 33 | *.js text 34 | *.json text 35 | *.jsx text 36 | *.less text 37 | *.ls text 38 | *.map text -diff 39 | *.od text 40 | *.onlydata text 41 | *.php text diff=php 42 | *.pl text 43 | *.ps1 text eol=crlf 44 | *.py text diff=python 45 | *.rb text diff=ruby 46 | *.rs text diff=rust 47 | *.ruby text diff=ruby 48 | *.sass text 49 | *.scm text 50 | *.scss text diff=css 51 | *.sh text diff=bash 52 | *.sh text diff=bash 53 | *.sql text 54 | *.styl text 55 | *.tag text 56 | *.ts text 57 | *.tsx text 58 | *.whl binary 59 | *.xhtml text diff=html 60 | *.xml text 61 | .husky/* text eol=lf 62 | Gemfile text diff=ruby 63 | 64 | # Docker 65 | Dockerfile text 66 | 67 | # Documentation 68 | *.ipynb text 69 | *.markdown text diff=markdown 70 | *.md text diff=markdown 71 | *.mdwn text diff=markdown 72 | *.mdown text diff=markdown 73 | *.mkd text diff=markdown 74 | *.mkdn text diff=markdown 75 | *.mdtxt text 76 | *.mdtext text 77 | *.txt text 78 | *.wakatime-project text 79 | AUTHORS text 80 | CHANGELOG text 81 | CHANGES text 82 | CONTRIBUTING text 83 | COPYING text 84 | copyright text 85 | *COPYRIGHT* text 86 | INSTALL text 87 | license text 88 | LICENSE text 89 | NEWS text 90 | readme text 91 | *README* text 92 | TODO text 93 | 94 | # Templates 95 | *.dot text 96 | *.ejs text 97 | *.erb text 98 | *.haml text 99 | *.handlebars text 100 | *.hbs text 101 | *.hbt text 102 | *.jade text 103 | *.latte text 104 | *.mustache text 105 | *.njk text 106 | *.phtml text 107 | *.svelte text 108 | *.tmpl text 109 | *.tpl text 110 | *.twig text 111 | *.vue text 112 | 113 | # Lock files 114 | *.lock text eol=lf -diff 115 | package-lock.json text eol=lf -diff 116 | pnpm-lock.yaml text eol=lf -diff 117 | yarn.lock text eol=lf -diff 118 | 119 | # Configs 120 | *.cnf text 121 | *.conf text 122 | *.config text 123 | .editorconfig text 124 | .env text 125 | .gitattributes text 126 | .gitconfig text 127 | .htaccess text 128 | *.lock text -diff 129 | package.json text eol=lf 130 | .prettierrc text 131 | yarn.lock text -diff 132 | *.toml text 133 | *.yaml text 134 | *.yml text 135 | browserslist text 136 | Makefile text 137 | makefile text 138 | 139 | # Heroku 140 | Procfile text 141 | 142 | # Graphics 143 | *.ai binary diff=exif 144 | *.bmp binary diff=exif 145 | *.eps binary 146 | *.gif binary diff=exif 147 | *.gifv binary 148 | *.hqx binary 149 | *.icns binary 150 | *.ico binary 151 | *.jng binary 152 | *.jp2 binary 153 | *.jpeg binary diff=exif 154 | *.jpg binary diff=exif 155 | *.jpx binary 156 | *.jxr binary 157 | *.pdf binary 158 | *.png binary diff=exif 159 | *.psb binary 160 | *.psd binary 161 | *.psd binary diff=exif 162 | *.svg text 163 | *.svgz binary 164 | *.tif binary diff=exif 165 | *.tiff binary diff=exif 166 | *.wbmp binary 167 | *.webp binary 168 | 169 | # Audio 170 | *.kar binary diff=exif 171 | *.m4a binary diff=exif 172 | *.mid binary diff=exif 173 | *.midi binary diff=exif 174 | *.mp3 binary diff=exif 175 | *.ogg binary diff=exif 176 | *.ra binary diff=exif 177 | 178 | # Video 179 | *.3gpp binary diff=exif 180 | *.3gp binary diff=exif 181 | *.as binary diff=exif 182 | *.asf binary diff=exif 183 | *.asx binary diff=exif 184 | *.avi binary diff=exif 185 | *.fla binary diff=exif 186 | *.flv binary diff=exif 187 | *.m4v binary diff=exif 188 | *.mng binary diff=exif 189 | *.mov binary diff=exif 190 | *.mp4 binary diff=exif 191 | *.mpeg binary diff=exif 192 | *.mpg binary diff=exif 193 | *.ogv binary diff=exif 194 | *.swc binary diff=exif 195 | *.swf binary diff=exif 196 | *.webm binary diff=exif 197 | 198 | # Archives 199 | *.7z binary 200 | *.cab binary 201 | *.ear binary 202 | *.gz binary diff=exif 203 | *.jar binary 204 | *.rar binary diff=exif 205 | *.tar binary 206 | *.tgz binary 207 | *.war binary 208 | *.zip binary diff=exif 209 | 210 | # Fonts 211 | *.ttf binary 212 | *.eot binary 213 | *.otf binary 214 | *.woff binary 215 | *.woff2 binary 216 | 217 | # Executables 218 | *.exe binary 219 | *.pyc binary 220 | 221 | # RC files (like .babelrc or .eslintrc) 222 | *.*rc text 223 | 224 | # Ignore files (like .npmignore or .gitignore) 225 | *.*ignore text 226 | 227 | # Documents 228 | *.DOC binary diff=exif 229 | *.DOCX binary diff=docx 230 | *.DOT binary diff=exif 231 | *.PDF binary diff=exif 232 | *.RTF binary diff=exif 233 | *.XLSX binary diff=exif 234 | *.adoc text 235 | *.bibtex text diff=bibtex 236 | *.csv text 237 | *.doc binary diff=exif 238 | *.docx binary diff=docx 239 | *.dot binary diff=exif 240 | *.dotx binary diff=exif 241 | *.epub diff=astextplain 242 | *.mdx text diff=markdown 243 | *.odb binary diff=exif 244 | *.odf binary diff=exif 245 | *.odg binary diff=exif 246 | *.odi binary diff=exif 247 | *.odp binary diff=exif 248 | *.ods binary diff=exif 249 | *.odt binary diff=odt 250 | *.otc binary diff=exif 251 | *.otg binary diff=exif 252 | *.oti binary diff=exif 253 | *.otp binary diff=exif 254 | *.ots binary diff=exif 255 | *.ott binary diff=exif 256 | *.pdf binary diff=exif 257 | *.ppt binary diff=exif 258 | *.pptx binary diff=exif 259 | *.ps binary diff=exif 260 | *.rtf binary diff=exif 261 | *.tab text 262 | *.tex text diff=tex 263 | *.textile text 264 | *.tsv text 265 | *.xls binary diff=exif 266 | *.xlsx binary diff=exif 267 | *.xlt binary diff=exif 268 | *.xltm binary diff=exif 269 | 270 | # Scripts 271 | *.fish text eol=lf 272 | *.zsh text eol=lf 273 | 274 | # Serialisation 275 | *.tar binary 276 | *.tgz binary 277 | *.zip binary 278 | 279 | # Text files where line endings should be preserved 280 | *.patch -text -------------------------------------------------------------------------------- /.github/config/labels.yml: -------------------------------------------------------------------------------- 1 | - name: "bug" 2 | color: "d73a4a" 3 | description: "Something isn't working" 4 | - name: "dependencies" 5 | color: "C62109" 6 | description: "Pull requests that update a dependency file" 7 | - name: "documentation" 8 | color: "0075ca" 9 | description: "Improvements or additions to documentation" 10 | - name: "duplicate" 11 | color: "cfd3d7" 12 | description: "This issue or pull request already exists" 13 | - name: "enhancement" 14 | color: "a2eeef" 15 | description: "New feature or request" 16 | - name: "good first issue" 17 | color: "7057ff" 18 | description: "Good for newcomers" 19 | - name: "help wanted" 20 | color: "008672" 21 | description: "Extra attention is needed" 22 | - name: "invalid" 23 | color: "e4e669" 24 | description: "This doesn't seem right" 25 | - name: "question" 26 | color: "d876e3" 27 | description: "Further information is requested" 28 | - name: "wontfix" 29 | color: "#ffffff" 30 | description: "This will not be worked on" 31 | -------------------------------------------------------------------------------- /.github/workflows/CI.yml: -------------------------------------------------------------------------------- 1 | name: Docker build CI 2 | 3 | on: 4 | push: 5 | paths: 6 | - base-fullbuild/Dockerfile 7 | - base-fullbuild/requirements.txt 8 | pull_request: 9 | paths: 10 | - base-fullbuild/Dockerfile 11 | - base-fullbuild/requirements.txt 12 | workflow_dispatch: 13 | 14 | jobs: 15 | build: 16 | runs-on: ubuntu-latest 17 | name: Set up Docker 18 | steps: 19 | - name: Checkout code 20 | uses: actions/checkout@v4 21 | 22 | - name: Set up Docker Buildx 23 | uses: docker/setup-buildx-action@v3 24 | 25 | - name: Build 26 | uses: docker/build-push-action@v6 27 | with: 28 | context: base-fullbuild/ 29 | file: base-fullbuild/Dockerfile 30 | pull: false 31 | push: false 32 | -------------------------------------------------------------------------------- /.github/workflows/autoassign.yml: -------------------------------------------------------------------------------- 1 | name: Issue assignment 2 | 3 | on: 4 | issues: 5 | types: [opened] 6 | 7 | jobs: 8 | auto-assign: 9 | runs-on: ubuntu-latest 10 | steps: 11 | - name: 'Auto-assign issue' 12 | uses: pozil/auto-assign-issue@v1 13 | with: 14 | assignees: modem7 15 | -------------------------------------------------------------------------------- /.github/workflows/labelsync.yml: -------------------------------------------------------------------------------- 1 | name: Label Manager 2 | 3 | on: 4 | push: 5 | paths: 6 | - '.github/config/labels.yml' 7 | workflow_dispatch: 8 | 9 | jobs: 10 | build: 11 | runs-on: ubuntu-latest 12 | steps: 13 | - name: Checkout 14 | uses: actions/checkout@v4 15 | 16 | - name: Synchronize labels 17 | uses: julb/action-manage-label@v1 18 | with: 19 | from: .github/config/labels.yml 20 | skip_delete: false 21 | env: 22 | GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} -------------------------------------------------------------------------------- /.hadolint.yaml: -------------------------------------------------------------------------------- 1 | override: 2 | style: 3 | - DL3013 4 | - DL3018 5 | - DL3042 6 | - DL3006 -------------------------------------------------------------------------------- /.wakatime-project: -------------------------------------------------------------------------------- 1 | docker-borgmatic -------------------------------------------------------------------------------- /CHANGELOG.md: -------------------------------------------------------------------------------- 1 | 2 | # Change Log 3 | All notable changes to this project will be documented in this file. 4 | 5 | The format is based on [Keep a Changelog](http://keepachangelog.com/). 6 | 7 | ## 2021-05-25 8 | 9 | ### Changed 10 | 11 | - Updated Borgmatic from v1.6.0 to v1.6.1. Read the [change notes](https://github.com/borgmatic-collective/borgmatic/releases/tag/1.6.1) 12 | - Updated Dockerfile to chmod script on COPY rather than via a separate chmod step. 13 | - Updated dependencies. 14 | 15 | ## 2021-04-26 16 | 17 | ### Changed 18 | 19 | - Updated Borgmatic from v1.5.24 to v1.6.0. Read the [change notes](https://github.com/borgmatic-collective/borgmatic/releases/tag/1.6.0) 20 | 21 | ## 2021-04-05 22 | 23 | ### Changed 24 | 25 | - Updated alpine to 3.15.4 26 | 27 | ## 2021-03-29 28 | 29 | ### Changed 30 | 31 | - Updated alpine to 3.15.3 32 | 33 | ## 2021-03-14 34 | 35 | ### Changed 36 | 37 | - Updated to latest dependencies. 38 | - Updated Changelog 39 | 40 | ## [1.5.24-1.2.0] - 2021-11-22 41 | 42 | ### Changed 43 | 44 | - Updated Borg backup from v1.1.17 to v1.2.0. 45 | - Updated tags to better follow both versions of Borg and Borgmatic 46 | 47 | ## [1.5.23] - 2021-02-10 48 | 49 | ### Changed 50 | 51 | - Updated Borgmatic to 1.5.23 52 | 53 | ## [1.5.22] - 2021-01-05 54 | 55 | ### Changed 56 | 57 | - Updated to latest dependencies. 58 | 59 | ## [1.5.20] - 2021-10-11 60 | 61 | ### Changed 62 | 63 | - Updated to latest dependencies. 64 | 65 | ## [Liveinstall] - 2021-10-11 66 | 67 | ### Changed 68 | 69 | - Updated Dockerfile based on the latest version. 70 | 71 | ## [DockerCLI] - 2021-10-11 72 | 73 | ### Changed 74 | 75 | - Updated Dockerfile based on the latest version. 76 | 77 | ## [1.5.19] - 2021-10-11 78 | 79 | ### Changed 80 | 81 | - Updated to latest dependencies 82 | 83 | 84 | ## [Liveinstall] - 2021-09-10 85 | 86 | ### Added 87 | 88 | - Created Dockerfile based on the latest version. 89 | - `Docker-cli` is installed on startup by default with `LIVEINSTALL` env variable available if you wish to customise. 90 | - Added [wtfc](https://github.com/typekpb/wtfc) script to make sure there is an internet connection prior to running live install. 91 | 92 | ## [DockerCLI](https://hub.docker.com/layers/164828805/modem7/borgmatic-docker/dockercli/images/sha256-992eeb053c59ad5cc953a4e96c3d702d32bb903b419463a27df9002e8a7f58fd?context=repo) - 2021-09-10 93 | 94 | ### Added 95 | 96 | - Created Dockerfile based on the latest version. 97 | - Baked in `docker-cli` during the install 98 | 99 | ## [1.5.18](https://hub.docker.com/layers/164830365/modem7/borgmatic-docker/1.5.18/images/sha256-12ad2daab8a13192908d9b5f37d7a5c0df1e76c87598bbf330f27c0fc11f78c4?context=repo) - 2021-09-10 100 | 101 | ### Added 102 | 103 | - Updated readme 104 | - Updated [guide](https://www.modem7.com/books/docker-backup/page/backup-docker-using-borgmatic) 105 | - Updated to latest dependencies 106 | - Added additional builds for docker-cli both as liveinstall and baked in 107 | 108 | ### Changed 109 | 110 | - Pinned dependency versions 111 | - `pip` to `21.2.4` 112 | - `borgbackup` to `1.1.17` 113 | - `borgmatic` to `1.5.18` 114 | - `llfuse` to `1.4.1` 115 | 116 | - Added `LIVEINSTALL` env variable to [liveinstall](https://hub.docker.com/layers/164828783/modem7/borgmatic-docker/liveinstall/images/sha256-9d53d2f4f00b7cf1e468db4a1ec10ac3698e0e61a7c0e666d6ac7954fc7f3aa2?context=repo) tag to allow for custom installation options 117 | - If `LIVEINSTALL` is not declared in your compose file then `docker-cli` gets installed by default. 118 | 119 | - Added Changelog. 120 | 121 | ## [1.5.14](https://hub.docker.com/layers/164832068/modem7/borgmatic-docker/1.5.14/images/sha256-f80eaa0fd3a9e1b42d91fb4fb677d07a43bdcfbc87db43f5a614b2de47b50209?context=repo) - 2021-09-10 122 | 123 | ### Added 124 | - Cloned [B3vis/Borgmatic](https://hub.docker.com/r/b3vis/borgmatic) repo 125 | 126 | ### Changed 127 | 128 | - Updated readme 129 | - Created [guide](https://www.modem7.com/books/docker-backup/page/backup-docker-using-borgmatic) 130 | - Added dependabot 131 | - Added requirements.txt 132 | - Created drone multiarch pipeline 133 | - Added hadolint file 134 | - List what package versions are installed in STDOUT 135 | 136 | ### Fixed 137 | 138 | - Pinned dependency versions 139 | - `pip` to `20.2.4` 140 | - `borgbackup` to `1.1.16` 141 | - `borgmatic` to `1.5.14` 142 | - `llfuse` to `1.3.8` 143 | -------------------------------------------------------------------------------- /LICENCE.txt: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2021 Alex Lane 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # Borgmatic Container with S6 2 | [![Docker Pulls](https://img.shields.io/docker/pulls/modem7/borgmatic-docker)](https://hub.docker.com/r/modem7/borgmatic-docker) 3 | [![Docker Image Size (tag)](https://img.shields.io/docker/image-size/modem7/borgmatic-docker/latest)](https://hub.docker.com/r/modem7/borgmatic-docker) 4 | [![Build Status](https://drone.modem7.com/api/badges/modem7/docker-borgmatic/status.svg)](https://drone.modem7.com/modem7/docker-borgmatic) 5 | [![GitHub last commit](https://img.shields.io/github/last-commit/modem7/docker-borgmatic)](https://github.com/modem7/docker-borgmatic) 6 | [![User Guide](https://img.shields.io/badge/User_Guide-OmegaWiki-informational?style=flat&logo=bookstack)](https://www.modem7.com/books/docker-backup/page/backup-docker-using-borgmatic) 7 | 8 | [!["Buy Me A Coffee"](https://www.buymeacoffee.com/assets/img/custom_images/orange_img.png)](https://www.buymeacoffee.com/modem7) 9 | 10 | ### Description 11 | Multiarch fork of [borgmatic-collective/borgmatic](https://github.com/borgmatic-collective/docker-borgmatic) with latest software versions and leveraging S6 so you can run Docker commands. 12 | 13 | There are also tags with Docker-CLI installed. Useful for container stop/start scripts. 14 | 15 | ### Dockerhub 16 | 17 | [modem7/borgmatic-docker](https://hub.docker.com/repository/docker/modem7/borgmatic-docker) 18 | 19 | ### Github 20 | 21 | [modem7/borgmatic-docker](https://github.com/modem7/docker-borgmatic) 22 | 23 | ### Readme 24 | 25 | A little container based on [b3vis's](https://github.com/borgmatic-collective/docker-borgmatic) work to automate my [Borgbackups](https://github.com/borgbackup) using the excellent [Borgmatic](https://github.com/borgmatic-collective/borgmatic). 26 | 27 | It uses cron to run the backups at a time you can configure in `data/borgmatic.d/crontab.txt`. 28 | 29 | # Tags 30 | | Tag | Description | 31 | | :----: | --- | 32 | | Latest | Latest version of Borgmatic| 33 | | 1.8.xx-1.2.x | Specific versions of Borgmatic | 34 | 35 | # Environment Variables 36 | | Variable | Description | Possible Values | Default | 37 | | :----: | --- | --- | --- | 38 | | DOCKERCLI | Install DockerCLI and ComposeCLI | true | Empty | 39 | | EXTRA_PKGS | Install additional packages | rclone coreutils jq other_packages | Empty | 40 | | CRON | Cron times | cron time, false | 0 1 * * * | 41 | | CRON_COMMAND | Command cron will run | borgmatic --stats -v 0 2>&1 | borgmatic --stats -v 0 2>&1 | 42 | | EXTRA_CRON | Extra cron lines | 0 5 2 * * command1 | Empty | 43 | 44 | ## Customising the container 45 | Simply mount a volume located at /custom-cont-init.d and add any scripts you want. These scripts can contain logic for installing packages, copying over custom files to other locations, or installing plugins. 46 | 47 | For example: 48 | ```yaml 49 | services: 50 | borgmatic: 51 | volumes: 52 | - /home/foo/my-custom-files:/custom-cont-init.d:ro 53 | ``` 54 | 55 | ### Usage 56 | 57 | Please look at this [guide](https://www.modem7.com/books/docker-backup/page/backup-docker-using-borgmatic) to help you run this container. 58 | 59 | To set your backup timing and configuration, you will need to create 60 | [crontab.txt](https://github.com/modem7/docker-borgmatic/blob/master/base-fullbuild/data/borgmatic.d/crontab.txt) and your borgmatic 61 | [config.yaml](https://github.com/modem7/docker-borgmatic/blob/master/base-fullbuild/data/borgmatic.d/config.yaml) and mount these files into the `/etc/borgmatic.d/` 62 | directory. When the container starts it creates the crontab from `crontab.txt` and starts crond. By 63 | cloning this repo in `/opt/docker/`, you will have a working setup to get started. 64 | 65 | If using remote repositories mount your .ssh to /root/.ssh within the container. 66 | 67 | #### Starting and stopping containers from hooks 68 | 69 | In case you are using the container to backup docker volumes used by other containers, you might 70 | want to make sure that the data is consistent and doesn't change while the backup is running. The 71 | easiest way to ensure this is to stop the affected containers before the backup and restart them 72 | afterwards. You can use the appropriate [borgmatic 73 | hooks](https://torsion.org/borgmatic/docs/how-to/add-preparation-and-cleanup-steps-to-backups/) and 74 | [control the docker engine through the API](https://docs.docker.com/engine/api/) using the hosts 75 | docker socket. 76 | 77 | Please note that you might want to prefer the `*_everything` hooks to the `*_backup` hooks, as 78 | `after_backup` will not run if the backup fails for any reason (missing disk space, etc.) and 79 | therefore the containers stay stopped. 80 | 81 | First mount the docker socket from the host by adding `-v /var/run/docker.sock:/var/run/docker.sock` 82 | to your `run` command or in the volume list of your `docker-compose.yml`. 83 | 84 | Then use the following example to create the start/stop hooks in the `config.yml` for the containers 85 | that you want to control. 86 | 87 | ```yaml 88 | hooks: 89 | before_everything: 90 | - echo "Stopping containers..." 91 | - 'echo -ne "POST /v1.41/containers//stop HTTP/1.1\r\nHost: localhost\r\n\r\n" | nc local:/var/run/docker.sock 80 > /dev/null && echo "Stopped Container 1" || echo "Failed to stop Container 1"' 92 | - 'echo -ne "POST /v1.41/containers//stop HTTP/1.1\r\nHost: localhost\r\n\r\n" | nc local:/var/run/docker.sock 80 > /dev/null && echo "Stopped Container 2" || echo "Failed to stop Container 2"' 93 | - echo "Containers stopped." 94 | - echo "Starting a backup." 95 | 96 | after_everything: 97 | - echo "Finished a backup." 98 | - echo "Restarting containers..." 99 | - 'echo -ne "POST /v1.41/containers//start HTTP/1.1\r\nHost: localhost\r\n\r\n" | nc local:/var/run/docker.sock 80 > /dev/null && echo "Started Container 1" || echo "Failed to start Container 1"' 100 | - 'echo -ne "POST /v1.41/containers//start HTTP/1.1\r\nHost: localhost\r\n\r\n" | nc local:/var/run/docker.sock 80 > /dev/null && echo "Started Container 2" || echo "Failed to start Container 2"' 101 | - echo "Containers restarted." 102 | ``` 103 | 104 | ### Example run command 105 | ```console 106 | docker run \ 107 | --detach --name borgmatic \ 108 | -v /home:/mnt/source:ro \ 109 | -v /opt/docker/docker-borgmatic/data/repository:/mnt/borg-repository \ 110 | -v /opt/docker/docker-borgmatic/data/borgmatic.d:/etc/borgmatic.d/ \ 111 | -v /opt/docker/docker-borgmatic/data/.config/borg:/root/.config/borg \ 112 | -v /opt/docker/docker-borgmatic/data/.ssh:/root/.ssh \ 113 | -v /opt/docker/docker-borgmatic/data/.cache/borg:/root/.cache/borg \ 114 | -e TZ=Europe/London \ 115 | modem7/borgmatic-docker 116 | ``` 117 | While the parameters above are sufficient for regular backups, following additional privileges will 118 | be needed to mount an archive as FUSE filesystem: 119 | ```console 120 | --cap-add SYS_ADMIN \ 121 | --device /dev/fuse \ 122 | --security-opt label:disable \ 123 | --security-opt apparmor:unconfined 124 | ``` 125 | Depending on your security system, `--security-opt` parameters may not be necessary. `label:disable` 126 | is needed for *SELinux*, while `apparmor:unconfined` is needed for *AppArmor*. 127 | 128 | To init the repo with encryption, run: 129 | ```console 130 | docker exec borgmatic \ 131 | sh -c "borgmatic --init --encryption repokey-blake2" 132 | ``` 133 | 134 | ### Layout 135 | #### /mnt/source 136 | Your data you wish to backup. For *some* safety you may want to mount read-only. Borgmatic is 137 | running as root so all files can be backed up. 138 | #### /mnt/borg-repository 139 | Mount your borg backup repository here. 140 | #### /etc/borgmatic.d 141 | Where you need to create crontab.txt and your borgmatic config.yml 142 | - To generate an example borgmatic configuration, run: 143 | ```console 144 | docker exec borgmatic \ 145 | sh -c "cd && borgmatic config generate -d /etc/borgmatic.d/config.yaml" 146 | ``` 147 | - crontab.txt example: In this file set the time you wish for your backups to take place default is 148 | 1am every day. In here you can add any other tasks you want ran 149 | ``` 150 | 0 1 * * * PATH=$PATH:/usr/bin /usr/bin/borgmatic --stats -v 0 2>&1 151 | ``` 152 | #### /root/.config/borg 153 | Here the borg config and keys for keyfile encryption modes are stored. Make sure to backup your 154 | keyfiles! Also needed when encryption is set to none. 155 | #### /root/.ssh 156 | Mount either your own .ssh here or create a new one with ssh keys in for your remote repo locations. 157 | #### /root/.cache/borg 158 | A non-volatile place to store the borg chunk cache. 159 | 160 | ### Environment 161 | - Time zone, e.g. `TZ="Europe/Berlin"'`. 162 | - SSH parameters, e.g. `BORG_RSH="ssh -i /root/.ssh/id_ed25519 -p 50221"` 163 | - BORG_RSH="ssh -i /root/.ssh/id_ed25519 -p 50221" 164 | - Repository passphrase, e.g. `BORG_PASSPHRASE="DonNotMissToChangeYourPassphrase"` 165 | 166 | ### Docker Compose 167 | - Prepare your configuration 168 | 1. `cp .env.template .env` 169 | 2. Set your environment and adapt volumes as needed 170 | - To start the container for backup: `docker-compose up -d` 171 | - For backup restore: 172 | 1. Stop the backup container: `docker-compose down` 173 | 2. Run an interactive shell: `docker-compose -f docker-compose.yml -f docker-compose.restore.yml 174 | run borgmatic` 175 | 3. Fuse-mount the backup: `borg mount /mnt/borg-repository ` 176 | 4. Restore your files 177 | 5. Finally unmount and exit: `borg umount && exit`. 178 | - In case Borg fails to create/acquire a lock: `borg break-lock /mnt/repository` 179 | -------------------------------------------------------------------------------- /base-fullbuild/.env.template: -------------------------------------------------------------------------------- 1 | TZ=Europe/Berlin 2 | BORG_PASSPHRASE=ReplaceWithYourSecretPassPhrase 3 | VOLUME_SOURCE=/home 4 | VOLUME_TARGET=./data/repository 5 | VOLUME_ETC_BORGMATIC=./data/borgmatic.d 6 | VOLUME_DOT_BORGMATIC=./data/.borgmatic 7 | VOLUME_BORG_CONFIG=./data/.config/borg 8 | VOLUME_SSH=./data/.ssh 9 | VOLUME_BORG_CACHE=./data/.cache/borg 10 | -------------------------------------------------------------------------------- /base-fullbuild/Dockerfile: -------------------------------------------------------------------------------- 1 | # syntax = docker/dockerfile:latest 2 | 3 | FROM python:3.13.3-alpine3.21 AS base 4 | ARG TARGETARCH 5 | 6 | LABEL maintainer='modem7' 7 | 8 | FROM base AS base-amd64 9 | ENV S6_OVERLAY_ARCH=x86_64 10 | 11 | FROM base AS base-arm64 12 | ENV S6_OVERLAY_ARCH=aarch64 13 | 14 | FROM base-${TARGETARCH}${TARGETVARIANT} 15 | 16 | ARG S6_OVERLAY_VERSION=3.2.0.2 17 | 18 | # Add S6 Overlay 19 | ADD https://github.com/just-containers/s6-overlay/releases/download/v${S6_OVERLAY_VERSION}/s6-overlay-${S6_OVERLAY_ARCH}.tar.xz /tmp/s6-overlay.tar.xz 20 | ADD https://github.com/just-containers/s6-overlay/releases/download/v${S6_OVERLAY_VERSION}/s6-overlay-noarch.tar.xz /tmp 21 | 22 | # Add S6 optional symlinks 23 | ADD https://github.com/just-containers/s6-overlay/releases/download/v${S6_OVERLAY_VERSION}/s6-overlay-symlinks-noarch.tar.xz /tmp 24 | ADD https://github.com/just-containers/s6-overlay/releases/download/v${S6_OVERLAY_VERSION}/s6-overlay-symlinks-arch.tar.xz /tmp 25 | 26 | ENV LANG='en_US.UTF-8' \ 27 | LANGUAGE='en_US.UTF-8' \ 28 | TERM='xterm' \ 29 | S6_LOGGING="1" \ 30 | S6_VERBOSITY="0" \ 31 | S6_CMD_WAIT_FOR_SERVICES_MAXTIME="0" \ 32 | TZ="Europe/London" 33 | 34 | RUN <?@[\\]^_`{|}~" 82 | 83 | # Type of compression to use when creating archives. See 84 | # https://borgbackup.readthedocs.org/en/stable/usage.html#borg-create for details. 85 | # Defaults to no compression. 86 | compression: lz4 87 | 88 | # Remote network upload rate limit in kiBytes/second. 89 | remote_rate_limit: 100 90 | 91 | # Command to use instead of just "ssh". This can be used to specify ssh options. 92 | ssh_command: ssh -i /path/to/private/key 93 | 94 | # Umask to be used for borg create. 95 | umask: 0077 96 | 97 | # Maximum seconds to wait for acquiring a repository/cache lock. 98 | lock_wait: 5 99 | 100 | # Name of the archive. Borg placeholders can be used. See the output of 101 | # "borg help placeholders" for details. Default is 102 | # "{hostname}-{now:%Y-%m-%dT%H:%M:%S.%f}". If you specify this option, you must 103 | # also specify a prefix in the retention section to avoid accidental pruning of 104 | # archives with a different archive name format. 105 | archive_name_format: '{hostname}-documents-{now}' 106 | 107 | # Retention policy for how many backups to keep in each category. See 108 | # https://borgbackup.readthedocs.org/en/stable/usage.html#borg-prune for details. 109 | # At least one of the "keep" options is required for pruning to work. 110 | retention: 111 | # Keep all archives within this time interval. 112 | keep_within: 3H 113 | 114 | # Number of minutely archives to keep. 115 | keep_minutely: 60 116 | 117 | # Number of hourly archives to keep. 118 | keep_hourly: 24 119 | 120 | # Number of daily archives to keep. 121 | keep_daily: 7 122 | 123 | # Number of weekly archives to keep. 124 | keep_weekly: 4 125 | 126 | # Number of monthly archives to keep. 127 | keep_monthly: 6 128 | 129 | # Number of yearly archives to keep. 130 | keep_yearly: 1 131 | 132 | # When pruning, only consider archive names starting with this prefix. 133 | # Borg placeholders can be used. See the output of "borg help placeholders" for 134 | # details. Default is "{hostname}-". 135 | prefix: sourcehostname 136 | 137 | # Consistency checks to run after backups. See 138 | # https://borgbackup.readthedocs.org/en/stable/usage.html#borg-check and 139 | # https://borgbackup.readthedocs.org/en/stable/usage.html#borg-extract for details. 140 | consistency: 141 | # List of one or more consistency checks to run: "repository", "archives", and/or 142 | # "extract". Defaults to "repository" and "archives". Set to "disabled" to disable 143 | # all consistency checks. "repository" checks the consistency of the repository, 144 | # "archive" checks all of the archives, and "extract" does an extraction dry-run 145 | # of just the most recent archive. 146 | checks: 147 | - repository 148 | - archives 149 | 150 | # Restrict the number of checked archives to the last n. Applies only to the "archives" check. 151 | check_last: 3 152 | 153 | # Shell commands or scripts to execute before and after a backup or if an error has occurred. 154 | # IMPORTANT: All provided commands and scripts are executed with user permissions of borgmatic. 155 | # Do not forget to set secure permissions on this file as well as on any script listed (chmod 0700) to 156 | # prevent potential shell injection or privilege escalation. 157 | hooks: 158 | # List of one or more shell commands or scripts to execute before creating a backup. 159 | before_backup: 160 | - echo "`date` - Starting a backup job." 161 | 162 | # List of one or more shell commands or scripts to execute after creating a backup. 163 | after_backup: 164 | - echo "`date` - Backup created." 165 | 166 | # List of one or more shell commands or scripts to execute in case an exception has occurred. 167 | on_error: 168 | - echo "`date` - Error while creating a backup." 169 | -------------------------------------------------------------------------------- /base-fullbuild/data/borgmatic.d/config.yaml: -------------------------------------------------------------------------------- 1 | location: 2 | source_directories: 3 | - /mnt/source 4 | repositories: 5 | - /mnt/borg-repository 6 | one_file_system: true 7 | 8 | storage: 9 | # Passphase is set in varibable $BORG_PASSPHRASE 10 | # encryption_passphrase: "DonNotMissToChangeYourPassphrase" 11 | compression: lz4 12 | archive_name_format: 'backup-{now}' 13 | 14 | retention: 15 | keep_hourly: 2 16 | keep_daily: 7 17 | keep_weekly: 4 18 | keep_monthly: 12 19 | keep_yearly: 10 20 | prefix: 'backup-' 21 | 22 | consistency: 23 | checks: 24 | - repository 25 | - archives 26 | check_last: 3 27 | prefix: 'backup-' 28 | 29 | hooks: 30 | before_backup: 31 | - echo "Starting a backup job." 32 | after_backup: 33 | - echo "Backup created." 34 | on_error: 35 | - echo "Error while creating a backup." 36 | -------------------------------------------------------------------------------- /base-fullbuild/data/borgmatic.d/config.yaml.example: -------------------------------------------------------------------------------- 1 | --- 2 | # see https://torsion.org/borgmatic/ for more info on this file 3 | location: 4 | source_directories: 5 | - /backup.tar.gz 6 | files_cache: ctime,size,inode 7 | remote_path: borg1 8 | repositories: 9 | - user@borg.example.com:myborgrepo 10 | exclude_caches: true 11 | 12 | storage: 13 | encryption_passcommand: cat /borgmatic/passphrase 14 | compression: auto,lz4 15 | umask: 0077 16 | lock_wait: 5 17 | archive_name_format: 'myservice-{now}' 18 | 19 | retention: 20 | keep_within: 3H 21 | keep_hourly: 24 22 | keep_daily: 7 23 | keep_weekly: 4 24 | keep_monthly: 6 25 | keep_yearly: 1 26 | prefix: 'myservice-' 27 | 28 | consistency: 29 | checks: 30 | - repository 31 | - archives 32 | check_last: 3 33 | 34 | hooks: 35 | before_backup: 36 | - /borgmatic/before-backup 37 | after_backup: 38 | - /borgmatic/after-backup 39 | on_error: 40 | - /borgmatic/failed-backup 41 | -------------------------------------------------------------------------------- /base-fullbuild/data/borgmatic.d/failed-backup.example: -------------------------------------------------------------------------------- 1 | # shellcheck shell=sh 2 | #!/usr/bin/with-contenv sh 3 | 4 | timestamp() { 5 | date -I'seconds' # ISO-8601 format 6 | } 7 | 8 | # things to when the backup has failed 9 | notify_admin() { 10 | echo 'the backup has failed' 11 | } 12 | 13 | echo "$(timestamp) - Backup failed" 14 | notify_admin 15 | -------------------------------------------------------------------------------- /base-fullbuild/requirements.txt: -------------------------------------------------------------------------------- 1 | --extra-index-url https://dl.cloudsmith.io/public/modem7/wheels/python/simple/ 2 | 3 | borgbackup==1.4.1 4 | borgmatic[apprise]==2.0.6 5 | llfuse==1.5.1 -------------------------------------------------------------------------------- /base-fullbuild/root/etc/s6-overlay/s6-rc.d/init-config-end/dependencies.d/base: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/modem7/docker-borgmatic/76bfa3f3bef10c4bc8ed8148a2097ee1f2d67926/base-fullbuild/root/etc/s6-overlay/s6-rc.d/init-config-end/dependencies.d/base -------------------------------------------------------------------------------- /base-fullbuild/root/etc/s6-overlay/s6-rc.d/init-config-end/dependencies.d/init-custom-packages: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/modem7/docker-borgmatic/76bfa3f3bef10c4bc8ed8148a2097ee1f2d67926/base-fullbuild/root/etc/s6-overlay/s6-rc.d/init-config-end/dependencies.d/init-custom-packages -------------------------------------------------------------------------------- /base-fullbuild/root/etc/s6-overlay/s6-rc.d/init-config-end/type: -------------------------------------------------------------------------------- 1 | oneshot 2 | -------------------------------------------------------------------------------- /base-fullbuild/root/etc/s6-overlay/s6-rc.d/init-config-end/up: -------------------------------------------------------------------------------- 1 | # This file doesn't do anything, it's just the end of the downstream image init process 2 | -------------------------------------------------------------------------------- /base-fullbuild/root/etc/s6-overlay/s6-rc.d/init-custom-packages/run: -------------------------------------------------------------------------------- 1 | #!/command/with-contenv bash 2 | 3 | # Install DockerCLI if true 4 | if [ "${DOCKERCLI}" == "true" ]; then 5 | echo "[custom-init] Installing Docker CLI and Docker Compose..." 6 | apk add -U --quiet docker-cli docker-cli-compose 7 | else 8 | echo "[custom-init] Docker CLI variable not set, skipping..." 9 | fi 10 | 11 | # Install additional packages 12 | if [ -v EXTRA_PKGS ]; then 13 | echo "[custom-init] Installing extra packages: $EXTRA_PKGS" 14 | apk add -U --quiet $EXTRA_PKGS 15 | else 16 | echo "[custom-init] No custom packages found, skipping..." 17 | fi 18 | -------------------------------------------------------------------------------- /base-fullbuild/root/etc/s6-overlay/s6-rc.d/init-custom-packages/type: -------------------------------------------------------------------------------- 1 | oneshot 2 | -------------------------------------------------------------------------------- /base-fullbuild/root/etc/s6-overlay/s6-rc.d/init-custom-packages/up: -------------------------------------------------------------------------------- 1 | /etc/s6-overlay/s6-rc.d/init-custom-packages/run 2 | -------------------------------------------------------------------------------- /base-fullbuild/root/etc/s6-overlay/s6-rc.d/svc-cron/dependencies.d/init-config-end: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/modem7/docker-borgmatic/76bfa3f3bef10c4bc8ed8148a2097ee1f2d67926/base-fullbuild/root/etc/s6-overlay/s6-rc.d/svc-cron/dependencies.d/init-config-end -------------------------------------------------------------------------------- /base-fullbuild/root/etc/s6-overlay/s6-rc.d/svc-cron/finish: -------------------------------------------------------------------------------- 1 | #!/command/with-contenv bash 2 | 3 | if test "$1" -eq 256 ; then 4 | e=$((128 + $2)) 5 | else 6 | e="$1" 7 | fi 8 | 9 | echo "Received exit code $e." 10 | echo "$e" > /run/s6-linux-init-container-results/exitcode 11 | -------------------------------------------------------------------------------- /base-fullbuild/root/etc/s6-overlay/s6-rc.d/svc-cron/run: -------------------------------------------------------------------------------- 1 | #!/command/with-contenv bash 2 | 3 | # Version variables 4 | borgver=$(borg --version) 5 | borgmaticver=$(borgmatic --version) 6 | apprisever=$(apprise --version | grep -Eo '[0-9]+\.[0-9]+\.[0-9]+') 7 | pythonver=$(python3 --version | grep -Eo '[0-9]+\.[0-9]+\.[0-9]+') 8 | 9 | if [ "${DOCKERCLI}" == "true" ]; then 10 | dockerver=$(docker --version | grep -Eo '[0-9]+\.[0-9]+\.[0-9]+') 11 | composever=$(docker compose version | grep -Eo '[0-9]+\.[0-9]+\.[0-9]+') 12 | else 13 | dockerver="not installed" 14 | composever="not installed" 15 | fi 16 | 17 | # Software versions 18 | echo "-----------------------------------" 19 | echo "Software Versions: 20 | ----------------------------------- 21 | apprise $apprisever 22 | $borgver 23 | borgmatic $borgmaticver 24 | dockercli $dockerver 25 | composecli $composever 26 | python $pythonver 27 | ----------------------------------- 28 | Time Zone: $TZ 29 | -----------------------------------" 30 | if [ -v EXTRA_PKGS ] 31 | then 32 | echo "Additional packages installed:" 33 | echo "-----------------------------------" 34 | echo $EXTRA_PKGS | tr -s " " "\n" 35 | echo "-----------------------------------" 36 | fi 37 | 38 | # Enable initial debug logging based on the DEBUG_SECRETS environment variable. 39 | # Logs the initial values of BORG_PASSPHRASE and BORG_PASSPHRASE_FILE. 40 | if [ "${DEBUG_SECRETS}" = "true" ] || [ "${DEBUG_SECRETS}" = "1" ]; then 41 | echo "Before: BORG_PASSPHRASE: ${BORG_PASSPHRASE}" 42 | echo "Before: BORG_PASSPHRASE_FILE: ${BORG_PASSPHRASE_FILE}" 43 | echo "Before: YOUR_PASSPHRASE: ${YOUR_PASSPHRASE}" 44 | echo "Before: YOUR_PASSPHRASE_FILE: ${YOUR_PASSPHRASE_FILE}" 45 | fi 46 | 47 | # Loop through all environment variables that start with 'BORG'. 48 | for var_name in $(set | grep -E '^BORG|^YOUR' | awk -F= '{print $1}'); do 49 | # Retrieve the current value of each environment variable. 50 | var_value=$(eval echo \$$var_name) 51 | 52 | # Check if the variable's name ends with '_FILE'. 53 | if [[ "$var_name" =~ _FILE$ ]]; then 54 | # Strip the '_FILE' suffix to obtain the corresponding variable name. 55 | original_var_name=${var_name%_FILE} 56 | 57 | # Retrieve the value of the original environment variable, if it exists. 58 | original_var_value=$(eval echo \$$original_var_name) 59 | 60 | # Ensure the *_FILE variable is valid, and the referenced file exists and is not empty. 61 | if [ -n "$var_value" ] && [ -s "$var_value" ]; then 62 | # Notify user if original variable is being overwritten. 63 | if [ -n "$original_var_value" ]; then 64 | echo "Note: $original_var_name was already set but is being overwritten by $var_name" 65 | fi 66 | 67 | # Update the original variable with the content of the file. 68 | export "$original_var_name"=$(cat "$var_value") 69 | echo "Setting $original_var_name from the content of $var_value" 70 | 71 | # Unset the *_FILE environment variable. 72 | unset "$var_name" 73 | echo "Unsetting $var_name" 74 | else 75 | # Issue an error if the *_FILE variable is not properly set, or the file does not exist or is empty. 76 | echo "Error: File $var_value does not exist or is empty." 77 | fi 78 | fi 79 | done 80 | 81 | # Enable final debug logging based on the DEBUG_SECRETS environment variable. 82 | # Logs the final values of BORG_PASSPHRASE and BORG_PASSPHRASE_FILE. 83 | if [ "${DEBUG_SECRETS}" = "true" ] || [ "${DEBUG_SECRETS}" = "1" ]; then 84 | echo "Before: BORG_PASSPHRASE: ${BORG_PASSPHRASE}" 85 | echo "Before: BORG_PASSPHRASE_FILE: ${BORG_PASSPHRASE_FILE}" 86 | echo "Before: YOUR_PASSPHRASE: ${YOUR_PASSPHRASE}" 87 | echo "Before: YOUR_PASSPHRASE_FILE: ${YOUR_PASSPHRASE_FILE}" 88 | fi 89 | 90 | # Disable cron if it's set to disabled. 91 | if [[ "$CRON" = "false" ]]; then 92 | echo "Disabling cron, removing configuration" 93 | # crontab -r # quite destructive 94 | # echo -n > /etc/crontabs/root # Empty config, doesn't look as nice with "crontab -l" 95 | echo "# Cron disabled" > /etc/crontabs/root 96 | echo "Cron is now disabled" 97 | # Apply default or custom cron if $CRON is unset or set (not null): 98 | elif [[ -v CRON ]]; then 99 | CRON="${CRON:-"0 1 * * *"}" 100 | CRON_COMMAND="${CRON_COMMAND:-"borgmatic --stats -v 0 2>&1"}" 101 | echo "$CRON $CRON_COMMAND" > /etc/crontabs/root 102 | echo "Applying custom cron" 103 | # If nothing is set, revert to default behaviour 104 | else 105 | echo "Applying crontab.txt" 106 | crontab /etc/borgmatic.d/crontab.txt 107 | fi 108 | 109 | # Apply extra cron if it's set 110 | if [ -v EXTRA_CRON ] 111 | then 112 | echo "$EXTRA_CRON" >> /etc/crontabs/root 113 | fi 114 | 115 | # Current crontab var 116 | crontab=$(crontab -l) 117 | 118 | # Output cron settings to console 119 | echo -e "Cron job set as: \n$crontab\n" 120 | 121 | # Start Cron 122 | exec /usr/sbin/crond -f -L /dev/stdout 123 | -------------------------------------------------------------------------------- /base-fullbuild/root/etc/s6-overlay/s6-rc.d/svc-cron/type: -------------------------------------------------------------------------------- 1 | longrun 2 | -------------------------------------------------------------------------------- /base-fullbuild/root/etc/s6-overlay/s6-rc.d/user/contents.d/init-custom-packages: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/modem7/docker-borgmatic/76bfa3f3bef10c4bc8ed8148a2097ee1f2d67926/base-fullbuild/root/etc/s6-overlay/s6-rc.d/user/contents.d/init-custom-packages -------------------------------------------------------------------------------- /base-fullbuild/root/etc/s6-overlay/s6-rc.d/user/contents.d/svc-cron: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/modem7/docker-borgmatic/76bfa3f3bef10c4bc8ed8148a2097ee1f2d67926/base-fullbuild/root/etc/s6-overlay/s6-rc.d/user/contents.d/svc-cron -------------------------------------------------------------------------------- /docker-compose.restore.yml: -------------------------------------------------------------------------------- 1 | version: "2.4" 2 | 3 | services: 4 | 5 | borgmaticrestore: 6 | container_name: Borg-restore 7 | volumes: 8 | - ${VOLUME_TARGET}:/mnt/borg-repository # backup source 9 | - ${VOLUME_RESTORE}:/RestoreMount # restore target 10 | - ${VOLUME_ETC_BORGMATIC}:/etc/borgmatic.d/ # borgmatic config file(s) + crontab.txt 11 | - ${VOLUME_BORG_CONFIG}:/root/.config/borg # config and keyfiles 12 | - ${VOLUME_SSH}:/root/.ssh # ssh key for remote repositories 13 | - ${VOLUME_BORG_CACHE}:/root/.cache/borg # checksums used for deduplication 14 | cap_add: 15 | - SYS_ADMIN 16 | security_opt: 17 | - apparmor:unconfined 18 | - label:disable 19 | environment: 20 | - TZ=$TZ 21 | devices: 22 | - /dev/fuse:/dev/fuse 23 | command: /bin/sh 24 | image: modem7/borgmatic-docker -------------------------------------------------------------------------------- /docker-compose.yml: -------------------------------------------------------------------------------- 1 | version: '2.4' 2 | services: 3 | borgmatic: 4 | image: modem7/borgmatic-docker 5 | container_name: Borgmatic 6 | volumes: 7 | - ${VOLUME_SOURCE}:/mnt/source:ro # backup source 8 | - ${VOLUME_TARGET}:/mnt/borg-repository # backup target 9 | - ${VOLUME_ETC_BORGMATIC}:/etc/borgmatic.d/ # borgmatic config file(s) + crontab.txt 10 | - ${VOLUME_BORG_CONFIG}:/root/.config/borg # config and keyfiles 11 | - ${VOLUME_SSH}:/root/.ssh # ssh key for remote repositories 12 | - ${VOLUME_BORG_CACHE}:/root/.cache/borg # checksums used for deduplication 13 | environment: 14 | - TZ=${TZ} 15 | - BORG_PASSPHRASE=${BORG_PASSPHRASE} 16 | -------------------------------------------------------------------------------- /renovate.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "https://docs.renovatebot.com/renovate-schema.json", 3 | "extends": [ 4 | "config:recommended" 5 | ], 6 | "assignees": [ 7 | "modem7" 8 | ], 9 | "labels": [ 10 | "dependencies" 11 | ], 12 | "timezone": "Europe/London" 13 | } 14 | --------------------------------------------------------------------------------