Ecosyste.ms: Awesome

An open API service indexing awesome lists of open source software.

Awesome Lists | Featured Topics | Projects

https://github.com/daniel-lerch/juggler

Docker based server management system
https://github.com/daniel-lerch/juggler

Last synced: about 2 months ago
JSON representation

Docker based server management system

Awesome Lists containing this project

README

        

# Juggler

## Install
1. Clone Juggler
`git clone https://github.com/daniel-lerch/juggler.git /opt/juggler`
2. Configure environment variables
`sudo cp /opt/juggler/res/juggler.sh /etc/profile.d/`
3. Copy Systemd unit files
`sudo cp /opt/juggler/res/juggler.timer /opt/juggler/res/juggler.service /etc/systemd/system/`
4. Enable Systemd timer
`sudo systemctl enable --now juggler.timer`

## Fundamentals
Juggler simpfies management of Docker Compose services by using common patterns and providing tools.
Applications are split into groups which reside in `/opt/`.
Within its group, each application is located in its own subfolder with a `docker-compose.yml` or `juggler.sh` file.

Juggler can manage manage backups for arbitrary applications but we will focus on Docker Compose here.
To use an existing Compose file with Juggler, no changes are required.
Just run `app up` and Juggler will take care of Docker Compose settings and provide you a simple backup mechanism.
With a `juggler.sh` file you can add custom commands as functions with a `cmd_` prefix.
Any variables you set will be available in the Compose file with the `${BASH_VARIABLE_NAME}` syntax.

Technically, Juggler scans a Compose file for variable names and adds them from Bash to a generated `.env` file.

## Bash architecture
Juggler consists out of four main components:
1. `bin/app` the bootstrapper executable
2. `lib/core.sh` the core module
3. `lib/compose.sh` the Docker Compose module
4. `lib/backup.sh` the Borg Backup module

Major challenges with Bash for a complex framework like Juggler
- Parse variables from `docker-compose.yml` files. Solution: Implemented in an external Python script.
- Juggler cannot iterate through multiple apps because of dangling variables. Solution: Start an own Juggler process for each app.
- Creating a good help overview requires lots of additional functions. Solution: Only show compose commands and backup module.
- For multiple apps it is hard to determine whether a command is available. Solution: Only allow certain command for batch execution.

## Variables and functions

### Core module
Exposed variables:
- `PROJECT_DIR` e.g. _/opt/global/nginx_
- `PROJECT_DIR_UID` e.g. _root_
- `PROJECT_DIR_GID` e.g. _root_
- `PROJECT_NAME` e.g. _nginx_
- `PROJECT_GROUP` e.g. _global_
- `PROJECT_TITLE` e.g. _global/nginx_
- `PROJECT_FULLNAME` e.g. _global-nginx_

Optional variables:
- `JUGGLER_CONFIG_FILE`
- `JUGGLER_PROJECT_PATH` defaults to _~/apps_

### Docker Compose module
Exposed variables:
- `COMPOSE_PROJECT_NAME` alias for _PROJECT\_FULLNAME_
- `COMPOSE_FILE` e.g. _/opt/global/nginx/docker-compose.yml_
- `APP_CONTAINER_NAME` e.g. _global-nginx-app_

Optional variables (for `execdb` command):
- `MYSQL_DATABASE`
- `MYSQL_USER`
- `MYSQL_PASSWORD`

Other optional variables:
- `DOCKER_CONTEXT`

Exposed functions:
- `invoke_compose()` Invokes _docker-compose_ with all required options

Optional callbacks:
- `update_images()` (optional callback) Builds custom images and pull images

### Borg Backup module
Exposed variables (change to customize behavior):
- `BACKUP_DIRS` e.g. _/opt/global/nginx_
- `BACKUP_EXCLUDE` e.g. _/opt/global/nginx/log /opt/global/nginx/.env_
- `BACKUP_PRUNE` e.g. _--keep-within=7d --keep-weekly=4 --keep-monthly=12_
- `BACKUP_CRONJOB` e.g. _0_ (disabled) or _1_ (enabled)

Optional variables (for automatic MySQL dumps to `/var/opt/backup`):
- `MYSQL_DATABASE`
- `MYSQL_ROOT_PASSWORD`

Optional callbacks:
- `prepare_backup()` Exports data before Borg backup starts

## Example
Nextcloud (located in `/opt/church/nextcloud`)

- `juggler.sh` Custom functions and environment variables
```bash
APP_IMAGE=nextcloud:latest

DB_IMAGE=mariadb:latest
DB_CONTAINER_NAME=$COMPOSE_PROJECT_NAME-db

MYSQL_ROOT_PASSWORD=root
MYSQL_DATABASE=nextcloud
MYSQL_USER=nextcloud
MYSQL_PASSWORD=password

function cmd_execw() {
invoke_composer exec -u www-data app bash
}
```
- `.env` Environment file generated by Juggler
- `docker-compose.yml` Compose file template using variables
```yaml
version: '2.1'

services:
app:
image: ${APP_IMAGE}
container_name: ${APP_CONTAINER_NAME}
environment:
- MYSQL_DATABASE
- MYSQL_USER
- MYSQL_PASSWORD
- MYSQL_HOST=db
db:
image: ${DB_IMAGE}
container_name: ${DB_CONTAINER_NAME}
environment:
- MYSQL_ROOT_PASSWORD
- MYSQL_DATABASE
- MYSQL_USER
- MYSQL_PASSWORD
```
- _$JUGGLER\_CONFIG\_FILE_ Global Juggler config file
```bash
ENABLE_PROJECT_GROUPS=1
# Change this variable to set custom default backup target
BACKUP_TARGET_DEFAULT="/var/opt/backup"
BACKUP_TARGET_DEFAULT_ENCRYPTION="none"
BACKUP_TARGET_DEFAULT_PASSPHRASE=""
# Add additional targets that can be selected manually
BACKUP_TARGET_REMOTE="[email protected]:/var/opt/backup"
BACKUP_TARGET_REMOTE_ENCRYPTION="repokey"
BACKUP_TARGET_REMOTE_PASSPHRASE="password"
```