Automatyzując zadania tworzenia kopii zapasowej, warto pamiętać o takich narzędziach jak CRON i języku skryptowym BASH. Przykład dla Ubuntu 20.
Oczywiście ważne jest zabezpieczenie kopii bazy danych, nie trzeba wielkiej wyobraźni aby uświadomić sobie zagrożenia utraty i dostępu do takiej kopii.
O ile w CRON może to wyglądać np tak:
# crontab -e
15 3 * * * /home/wiks/cron_mysql_arch.sh&
lub w osobnym skrypcie dla /etc/cron.d/wiks (z podaniem użytkownika wykonującego skrypt):
# vi /etc/cron.d/wiks
15 3 * * * wiks /home/wiks/cron_mysql_arch.sh&
Czyli raz dziennie, w okolicy 3 nad razem wykonaj skrypt jako użytkownik wiks .
W BASHu zaś (niech to będzie plik o nazwie: cron_mysql_arch.sh ) umieszczam definicje i polecenia do wykonania kopii, spakowania jej i …
#!/bin/bash
DB_BACKUP_PATH='/home/wiks/db_backups'
TODAY=`date +"%Y%m%d"`
MYSQL_HOST='localhost'
MYSQL_PORT='3306'
MYSQL_USER='cron_dbarch'
MYSQL_PASSWORD='????????????'
MYSQL_DB_NAME='baza_danych'
DB_BACKUP_PATH_TODAY=${DB_BACKUP_PATH}/${TODAY}
mkdir -p ${DB_BACKUP_PATH_TODAY}
mysqldump --no-tablespaces --single-transaction -h ${MYSQL_HOST} \
-P ${MYSQL_PORT} \
-u ${MYSQL_USER} \
-p${MYSQL_PASSWORD} \
${MYSQL_DB_NAME} | gzip > ${DB_BACKUP_PATH_TODAY}/${MYSQL_DB_NAME}_${TODAY}.sql.gz
Warto zabezpieczyć ten plik, ograniczając możliwość podejrzenia: chmod 700 oraz umżliwiając bycie wykonywalnym: chmod +x
chmod 700 cron_mysql_arch.sh
chmod +x cron_mysql_arch.sh
Skrypt loguje się do bazy danych MySQL jako użytkownik cron_dbarch (też warto starannie dobrać uprawnienia -nie zbyt duże), i pobiera bazę danych, kompresując ją za pomocą gzip. wcześniej utworzył sobie katalog o nazwie zależnej od aktualnej daty, do tego zaś katalogu tworzy spakowany plik bazy danych, o nazwie będącej połączeniem nazwy tej bazy z datą.
Utworzony folder dla jednego dnia, można wykorzystać również jako pojemnik np. na kopie logów (gdyby uznano, że warto je mieć również zarchiwizowane dla potencjalnych prób wyjaśniania niewyjaśnionego…). Korzystając z pomysłu poniższego, czyli archiwizowania codziennego logów np Django, warto zadbać o ich codzienną rotację [ 'logging.handlers.TimedRotatingFileHandler’, 'when’: 'D’ ].
# logi apache:
echo 'kopia logów Apache2 (2)'
mkdir -p ${DB_BACKUP_PATH_TODAY}/var_log/apache2
cp /var/log/apache2/web_access.log ${DB_BACKUP_PATH_TODAY}/var_log/apache2/
cp /var/log/apache2/web_error.log ${DB_BACKUP_PATH_TODAY}/var_log/apache2/
# albo:
# logi django:
echo 'kopia logów Django (2)'
mkdir -p ${DB_BACKUP_PATH_TODAY}/django_logs
cp /home/wiks/Django/logs/debug.log ${DB_BACKUP_PATH_TODAY}/django_logs/
Gdy mam już paczkę, którą chciałbym odesłać na półkę, zapewniając, że będę mógł odzyskać jej zawartość, ale nikt poza mną nie będzie w stanie tego zrobić (nawet jak pozna miejsce półki)… spakuję paczkę do jednego pliku i zaszyfruję. Oczywiście usuwając folder i niezaszyfrowaną paczkę:
echo 'pakuję wszystko razem'
tar -zcvf ${DB_BACKUP_PATH_TODAY}.tar ${DB_BACKUP_PATH_TODAY}
echo 'usuwam folder po spakowaniu i skopiowaniu'
rm -rf ${DB_BACKUP_PATH_TODAY}
echo 'encryption...'
gpg --batch --yes -e -r qr@qrgo.pl ${DB_BACKUP_PATH_TODAY}.tar
echo 'usuwam spakowany po zakodowaniu'
rm -rf ${DB_BACKUP_PATH_TODAY}.tar
Pakowanie, usuwanie folderu – jasne, teraz kilka słów o kodowaniu.
gpg używa tutaj klucza publicznego skojarzonego z adresem email qr@qrgo.pl
Taki klucz mógłby być wytworzony na komputerze, który tworzy tą kopię zapasową, wtedy komputer miałby również klucz prywatny i byłby w stanie nie tylko szyfrować, ale również niezaprzeczalnie podpisać zaszyfrowany plik.
Tak się jednak nie stało, klucze zostały utworzone w innym miejscu, tutaj jedynie zaimportowałem klucz publiczny.
wiks@qrgo:/home/wiks/Django$ gpg --import pub_key.asc
gpg: key 7A619650AE5B0EE0: public key "QRgo.pl team <qr@qrgo.pl>" imported
gpg: Total number processed: 1
gpg: imported: 1
wiks@qrgo:/home/wiks/Django$ gpg -e -r qr@qrgo.pl plik.test
gpg: 7A619650AE5B0EE0: There is no assurance this key belongs to the named user
sub cv25519/7A619650AE5B0EE0 2020-12-23 QRgo.pl team <qr@qrgo.pl>
Primary key fingerprint: 7630 9D31 B660 D1E4 A4A4 8EF5 E038 254A 1AE7 8E43
Subkey fingerprint: 44B8 945F E9E2 4441 EC79 35E3 7A61 9650 AE5B 0EE0
you may answer the next question with yes.
Use this key anyway? (y/N) y
Zaimportowanie klucza sprawiło, że jest on dla gpg niewiarygodny, dlatego przy każdej próbie użycia go do szyfrowania, otrzymamy pytanie 'czy na pewno chcę go użyć?’. -cała automatyzacja prysnęła jak bańka mydlana…
Należy na komputerze na którym zaimportowano dany klucz publiczny, wyedytować go gpg –edit-key <email> i zmienić zaufanie na absolutne – wybierając jak w poniższym przykładzie '5′ :
gpg --edit-key qr@qrgo.pl
[...]
gpg> trust
sec ed25519/E038254A1AE78E43
utworzono: 2020-12-23 wygasa: 2025-12-22 użycie: SC
zaufanie: absolutne poprawność: absolutne
ssb cv25519/7A619650AE5B0EE0
utworzono: 2020-12-23 wygasa: 2025-12-22 użycie: E
[ absolutne ] (1). QRgo.pl team <qr@qrgo.pl>
Zastanów się jak bardzo ufasz temu użytkownikowi w kwestii sprawdzania
tożsamości innych użytkowników (czy sprawdzi on odciski kluczy pobrane
z różnych źródeł, dokumenty potwierdzające tożsamość, itd.).
1 = nie wiem albo nie powiem
2 = NIE ufam
3 = mam ograniczone zaufanie
4 = mam pełne zaufanie
5 = ufam absolutnie
m = powrót do głównego menu
Decyzja?
Należy pamiętać, że importujemy klucz jako ten użytkownik, który będzie reprezentowany przez CRON wykonujący archiwizację i szyfrowanie. I jako ten użytkownik edytować klucz i ustawić zaufanie do niego jako pełne.
Plik wynikowy będzie miał zatem rozszerzenie *.tar.gpg i będzie dość bezpieczny, nawet jeśli ktoś pozna miejsce półki i go skopiuje, nie będzie w stanie nic zrobić bez klucza prywatnego.