# MySQL Automatic Backup A sidecar container for backing up MySQL databases. Every night at 23:50, internal cron runs `mysqldump` to dump all databases on the target server to a SQL file. ## Changing when the job runs [mysqlCron](mysqlCron) defines when the job will be run. To change this, simply modify the values. Use the chart below as reference. By default, the job is confirued to run at 23:50 every night. > [!IMPORTANT] > The crontab file (mysqlCron) must always contain an empty line at the end of the file. ``` sh 50 23 * * * backup.sh >> /var/log/cron.log 2>&1 - - - - - | | | | | | | | | ----- Day of week (0 - 7) (Sunday=0 or 7) | | | ------- Month (1 - 12) | | --------- Day of month (1 - 31) | ----------- Hour (0 - 23) ------------- Minute (0 - 59) ``` # Usage Simply start a container using this image. The service needs to have network access to the target server on a network that can log into the target with a root password. ## Install It's recommended to set up this container by adding it to the target service's docker compose. ### Examples #### Simple Setup ``` yaml version: "3" services: db: image: mysql:latest container_name: nasdb restart: always env_file: stack.env volumes: - "db:/var/lib/mysql" networks: - nastest backup: image: gitea.jv.com/audrey/mysql-backup-agent:test env_file: stack.env environment: MYSQL_HOST: nasdb BACKUP_NAME: nastest APPEND_DATE: true networks: - nastest volumes: - "backup:/backup" volumes: db: driver: local backup: driver: local networks: nastest: external: false ``` #### Backup to NAS For increased data security, it's recommended to store database backups on the NAS where they can take advantage of increased storage, automatic snapshots, & further backups. The below example is identical to the one above, except `APPEND_DATE` has been set to `false` & the volume definition for `backup` has been modified. > [!IMPORTANT] > If you intend to keep regular snapshots of this backup on the file server, you should set APPEND_DATE to false ``` yaml version: "3" services: db: image: mysql:latest container_name: nasdb restart: always env_file: stack.env volumes: - "db:/var/lib/mysql" networks: - nastest backup: image: gitea.jv.com/audrey/mysql-backup-agent:test env_file: stack.env environment: MYSQL_HOST: nasdb BACKUP_NAME: nastest APPEND_DATE: false networks: - nastest volumes: - "backup:/backup" volumes: db: driver: local backup: driver: local driver_opts: #config to connect to an NFS share is defined using these options type: nfs o: addr=172.16.1.2,rw #If a direct link is available, use that device: :/mnt/tank/Docker/Volumes/Intranet #this will usually be the path to the folder shared by NFS, relative to the file server. networks: nastest: external: false ``` ## Config Some basic config options are available through environment variables. ### Required Vars | Variable | Description | Example | | :--- | :--- | :--- | | MYSQL_HOST | The IP/identifier of the target server. Typically, the container name or ID | `MYSQL_HOST=websitedb` | | MYSQL_ROOT_PASSWORD | The root password of the target server. Used for authentication | `MYSQL_ROOT_PASSWORD=someval` | #### Optional Vars |Variable|Description|Example| | :--- | :--- | :---| |APPEND_DATE|`Default: false` If set, appends the yyyy-mm-dd of the backup to the end of the file name. Leaving this unset will cause existing backups to be overwritten.| `APPEND_DATE=true`| |BACKUP_NAME|`Default: Value of MYSQL_HOST`If set, the name of the file will be set to this value. Example: setting this to 'epicdb' will cause files to save as 'epicdb.sql'|`BACKUP_NAME='pubweb-backup'`| ## Recovery Recovering from a MySQL dump is a very manual process. There's no one method to do it. Generally, all you need to do is download the latest dump from the NAS/backup target & import it into the MySQL database. For simple services, it may be sufficient to delete the faulty MySQL data & rebuild it from the dump. To do so, delete the existing volume for MySQL then simply bind the directory containing the backed-up SQL dump file to the MySQL container's entrypoint dir. Review the below Compose.yaml for an example: ``` yaml version: "3" services: db: image: mysql:latest container_name: pubwebdb restart: always volumes: - "db:/var/lib/mysql" - "backup:/docker-entrypoint-initdb.d:r" volumes: db: driver: local backup: driver: local driver_opts: #config to connect to an NFS share is defined using these options type: nfs o: addr=172.16.1.2,rw #If a direct link is available, use that device: :/mnt/tank/Docker/Volumes/Pubweb #this will usually be the path to the folder shared by NFS, relative to the file server. ``` When MySQL starts, it should detect an empty database (if this doesn't happen, make sure you deleted the persistent volume that was mapped to /var/lib/mysql.) This will trigger it to check /docker-entrypoint-initdb.d for any .sql files it can execute to populate itself. Once the prepopulation has been completed, you can comment out the volume binding. If `APPEND_DATE` is set to true, you'll need to make sure this directory contains only the SQL dump you want to restore. Move all others somewhere safe.