Created
February 13, 2016 15:32
-
-
Save andrew-azarov/a903fc4f2f63239ee39e to your computer and use it in GitHub Desktop.
Simple smart backup script focused on files, mysql, pgsql and ftp upload (files are from FreeBSD edition, can be redefined in the beginning)
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/bin/sh | |
# Global settings | |
gz_b="/usr/bin/pigz" # Gzip | |
awk_b="/usr/bin/awk" # Awk | |
echo_b="/bin/echo" # Echo | |
tar_b="/usr/bin/tar" # Tar | |
xargs_b="/usr/bin/xargs" # Xargs | |
cat_b="/bin/cat" # Cat | |
find_b="/usr/bin/find" # Find | |
grep_b="/usr/bin/grep" # Grep | |
cut_b="/usr/bin/cut" # Cut | |
sed_b="/usr/bin/sed" # Sed | |
rm_b="/bin/rm" # Rm | |
mkdir_b="/bin/mkdir" # Mkdir | |
mktemp_b="/usr/bin/mktemp" # Mktemp | |
basename_b="/usr/bin/basename" # Basename | |
date_b="/bin/date" # Date | |
cc_b="/usr/bin/cc" # CC, needed for pgsql backup with password | |
strip_b="/usr/bin/strip" # strip, the same for pgsql backup with password | |
tr_b="/usr/bin/tr" # Tr | |
ftp_b="/usr/bin/ftp" # FTP | |
my_dir=`pwd` | |
# FTP Upload settings | |
upload_do="NO" | |
upload_login="" | |
upload_password="" | |
upload_host="" | |
upload_p="${ftp_b} -Viu " | |
upload_pm="${upload_p} ftp://${upload_login}:${upload_password}@${upload_host}:21/mysql/" # Mysql dir | |
upload_pf="${upload_p} ftp://${upload_login}:${upload_password}@${upload_host}:21/files/" # File dir | |
upload_pb="${upload_p} ftp://${upload_login}:${upload_password}@${upload_host}:21/mysql/" # Binlog mysql dir | |
upload_pp="${upload_p} ftp://${upload_login}:${upload_password}@${upload_host}:21/pgsql/" # Pgsql dir | |
upload_mysql="YES" | |
upload_pgsql="NO" | |
upload_files="YES" | |
# File Setting | |
file_do="YES" # Do backup? | |
file_backup_d="/backup/" # Where to backup? | |
file_purge_time="72h" # Time backups reside | |
file_dir_to_b=`ls / | grep -v backup | sed -e 's/^/\//g'` # List of files and directories to backup | |
# Mysql Setting | |
mysql_do="NO" # Do backup? | |
mysql_u="" # Username | |
mysql_p="" # Password | |
mysql_purge_time="72h" # Time backups reside | |
mysql_backup_bin_logs=0 # Do we backup the binary logs? | |
mysql_bin_d="/usr/local/bin" # Binary directory of mysql | |
mysql_bin_log_d="/var/db/mysql" # Binary log directory | |
mysql_backup_d="/home/backup/mysql" # Where to backup? | |
mysql_b="${mysql_bin_d}/mysql -u${mysql_u} -p${mysql_p}" # Mysql main usage command | |
mysql_dump_b="${mysql_bin_d}/mysqldump -u${mysql_u} -p${mysql_p} -f" # Mysql dump usage | |
mysql_admin_b="${mysql_bin_d}/mysqladmin -u${mysql_u} -p${mysql_p}" # Mysql admin usage | |
# Pgsql Setting | |
pgsql_do="NO" # Do backup? | |
pgsql_u="" # Username | |
pgsql_p="" | |
pgsql_purge_time="72h" # Time backups reside | |
pgsql_bin_d="/usr/local/bin" # Binary directory of mysql | |
pgsql_backup_d="/home/backup/pgsql" # Where to backup? | |
pgsql_b="${pgsql_bin_d}/psql -U ${pgsql_u}" # Pgsql main usage command | |
pgsql_dump_b="${pgsql_bin_d}/pg_dump -U ${pgsql_u}" # Pgsql dump usage | |
pgsql_vac_b="${pgsql_bin_d}/vacuumdb -z -U ${pgsql_u}" # Pgsql vacuum usages | |
${echo_b} Starting backup \( `${date_b}` \) | |
file_backup() | |
{ | |
${echo_b} File backup started \( `${date_b}` \) | |
if [ ! -d "${file_backup_d}" ] | |
then | |
${echo_b} "Making backup dir ${file_backup_d}" | |
${mkdir_b} ${file_backup_d} | |
fi | |
${echo_b} "Preparing files and directories for backup" | |
for dbs in ${file_dir_to_b} | |
do | |
${echo_b} -n "Compressing ${dbs}." | |
dbs2=`${echo_b} ${dbs} | ${tr_b} / - ` | |
${echo_b} -n "." | |
nname=`${date_b} "+%Y-%m-%d-%H-%M"` | |
${tar_b} czf ${file_backup_d}/${nname}${dbs2}.tar.gz ${dbs} 1>/dev/null 2>&1 | |
if [ "${upload_do}" = "YES" ] | |
then | |
${echo_b} -n ". Uploading file..." | |
cd ${file_backup_d} | |
${upload_pf} ${nname}${dbs2}.tar.gz | |
cd ${my_dir} | |
else | |
${echo_b} -n "." | |
fi | |
${echo_b} " Done!" | |
done | |
${echo_b} -n "Purging old backups..." | |
${find_b} ${file_backup_d} -type f -ctime +${file_purge_time} -depth 1 -delete | |
${echo_b} " Done!" | |
${echo_b} File backup complete \( `${date_b}` \) | |
} | |
pgsql_backup() | |
{ | |
${echo_b} Pgsql Database backup started \( `${date_b}` \) | |
if [ ! -d "${pgsql_backup_d}" ] | |
then | |
${echo_b} "Making backup dir ${pgsql_backup_d}" | |
${mkdir_b} ${pgsql_backup_d} | |
fi | |
${echo_b} "Preparing databases for backup" | |
for dbs in `${echo_b} "${pgsql_p}" | ${pgsql_b} -l | ${sed_b} -n '4,/\eof/p' | ${grep_b} -v rows\) | ${cut_b} -f 1 -d '|' -s | ${awk_b} '{print $1}'` | |
do | |
${echo_b} -n "Vacuuming db ${dbs}..." | |
${echo_b} "${pgsql_p}" | ${pgsql_vac_b} -z ${dbs} > /dev/null 2>&1 | |
${echo_b} " Done!" | |
${echo_b} -n "Backing up db ${dbs}.." | |
nname=`${date_b} "+%Y-%m-%d-%H-%M"` | |
${echo_b} "${pgsql_p}" | ${pgsql_dump_b} ${dbs} | ${gz_b} > ${pgsql_backup_d}/${nname}-${dbs}.sql.gz | |
if [ "${upload_do}" = "YES" ] | |
then | |
${echo_b} -n ". Uploading file..." | |
cd ${pgsql_backup_d} | |
${upload_pp} ${nname}-${dbs}.sql.gz | |
cd ${my_dir} | |
else | |
${echo_b} -n "." | |
fi | |
${echo_b} " Done!" | |
done | |
${echo_b} -n "Purging old backups..." | |
${find_b} ${pgsql_backup_d} -type f -ctime +${pgsql_purge_time} -depth 1 -delete | |
${echo_b} " Done!" | |
${echo_b} Pgsql Database backup complete \( `${date_b}` \) | |
} | |
mysql_backup() | |
{ | |
${echo_b} Mysql Database backup started \( `${date_b}` \) | |
if [ ! -d "${mysql_backup_d}" ] | |
then | |
${echo_b} "Making backup dir ${mysql_backup_d}" | |
${mkdir_b} ${mysql_backup_d} | |
fi | |
${echo_b} "Preparing to backup non-InnoDB tables" | |
for dbs in `${mysql_b} -r --batch -N -e "show databases;"` | |
do | |
if [ "${dbs}" != 'information_schema' ] | |
then | |
innodbs=`${mysql_b} -r --batch -N ${dbs} -e "show table status;" | ${awk_b} -v dbs="${dbs}" '{ if ($2 == "InnoDB") {print "--ignore-table="dbs"."$1}}' | ${xargs_b} ${echo_b}` | |
${echo_b} -n "Backing up db ${dbs}.." | |
nname=`${date_b} "+%Y-%m-%d-%H-%M"` | |
${mysql_dump_b} --hex-blob ${innodbs} ${dbs} | ${gz_b} > ${mysql_backup_d}/${nname}-${dbs}-non-innodb-tables.sql.gz | |
if [ "${upload_do}" = "YES" ] | |
then | |
${echo_b} -n ". Uploading file..." | |
cd ${mysql_backup_d} | |
${upload_pm} ${nname}-${dbs}-non-innodb-tables.sql.gz | |
cd ${my_dir} | |
else | |
${echo_b} -n "." | |
fi | |
${echo_b} " Done!" | |
fi | |
done | |
${echo_b} "Preparing to backup InnoDB tables" | |
for dbs in `${mysql_b} -r --batch -N -e "show databases;"` | |
do | |
for innodbs in `${mysql_b} -r --batch -N ${dbs} -e "show table status;" | ${awk_b} '{ if ($2 == "InnoDB") {print $1}}'` | |
do | |
${echo_b} -n "Backing up db ${dbs}, table: ${innodbs}.." | |
nname=`${date_b} "+%Y-%m-%d-%H-%M"` | |
${mysql_dump_b} -q --single-transaction --hex-blob ${dbs} ${innodbs} | ${gz_b} > ${mysql_backup_d}/${nname}-${dbs}.${innodbs}-innodb-table.sql.gz | |
if [ "${upload_do}" = "YES" ] | |
then | |
${echo_b} -n ". Uploading file..." | |
cd ${mysql_backup_d} | |
${upload_pm} ${nname}-${dbs}.${innodbs}-innodb-table.sql.gz | |
cd ${my_dir} | |
else | |
${echo_b} -n "." | |
fi | |
${echo_b} " Done!" | |
done | |
done | |
if [ `${mysql_b} -r --batch -N -e 'show binary logs;' 2>&1 | ${grep_b} -c "ERROR 1381"` -ne 1 -a ${mysql_backup_bin_logs} -eq 1 ] | |
then | |
${echo_b} "Preparing binary log backup" | |
${mysql_admin_b} flush-logs | |
s=`${mysql_b} -r --batch -N mysql -e "show binary logs;" | ${awk_b} '$2>0 {i++};END{print i}'` | |
d=`${mysql_b} -r --batch -N mysql -e "show binary logs;" | ${awk_b} '$2>0 {print $1}' | tail -1` | |
r=0 | |
for k in `${mysql_b} -r --batch -N mysql -e "show binary logs;" | ${awk_b} '$2>0 {print $1}` | |
do | |
if [ "${k}" != "${d}" -a "${r}" -le "${s}" -a ${s} -gt 0 ] | |
then | |
${echo_b} -n "Backing up binary log ${k}.." | |
nname=`${date_b} "+%Y-%m-%d-%H-%M"` | |
${cat_b} ${mysql_bin_log_d}/${k} | ${gz_b} > ${mysql_backup_d}/${nname}_binlog_${k}.gz | |
${rm_b} -f ${mysql_bin_log_d}/${k} | |
r=`expr ${r} + 1` | |
if [ "${upload_do}" = "YES" ] | |
then | |
${echo_b} -n ". Uploading file..." | |
cd ${mysql_bin_log_d} | |
${upload_pmb} ${nname}_binlog_${k}.gz | |
cd ${my_dir} | |
else | |
${echo_b} -n "." | |
fi | |
${echo_b} " Done!" | |
fi | |
done | |
fi | |
${echo_b} -n "Purging old backups..." | |
${find_b} ${mysql_backup_d} -type f -ctime +${mysql_purge_time} -depth 1 -delete | |
${echo_b} " Done!" | |
${echo_b} Mysql Database backup complete \( `${date_b}` \) | |
} | |
notty() | |
{ | |
if [ $1 -eq 1 ] | |
then | |
temp=`${basename_b} $0` | |
TMPFILE=`${mktemp_b} ${temp}.XXXXX.c` || exit 1 | |
${cat_b} <<ENDFILE>> ${TMPFILE} | |
/* | |
* Copyright (c) 2008 The DragonFly Project. All rights reserved. | |
* | |
* This code is derived from software contributed to The DragonFly Project | |
* by Matthew Dillon <[email protected]> | |
* | |
* Redistribution and use in source and binary forms, with or without | |
* modification, are permitted provided that the following conditions | |
* are met: | |
* | |
* 1. Redistributions of source code must retain the above copyright | |
* notice, this list of conditions and the following disclaimer. | |
* 2. Redistributions in binary fo${rm_b} must reproduce the above copyright | |
* notice, this list of conditions and the following disclaimer in | |
* the documentation and/or other materials provided with the | |
* distribution. | |
* 3. Neither the name of The DragonFly Project nor the names of its | |
* contributors may be used to endorse or promote products derived | |
* from this software without specific, prior written permission. | |
* | |
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS | |
* ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT | |
* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS | |
* FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE | |
* COPYRIGHT HOLDERS OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, | |
* INCIDENTAL, SPECIAL, EXEMPLARY OR CONSEQUENTIAL DAMAGES (INCLUDING, | |
* BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | |
* LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED | |
* AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, | |
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT | |
* OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF | |
* SUCH DAMAGE. | |
* | |
* $DragonFly: src/bin/notty/notty.c,v 1.2 2008/06/24 21:13:26 thomas Exp $ | |
*/ | |
/* | |
* NOTTY.C - program to disconnect a program from the tty and close | |
* stdin, stdout, and stderr (-012 to specify which descriptors | |
* to leave open). | |
* | |
* NOTTY [-012] <command> | |
*/ | |
#include <sys/types.h> | |
#include <sys/ioctl.h> | |
#include <sys/time.h> | |
#include <sys/wait.h> | |
#include <stdio.h> | |
#include <stdlib.h> | |
#include <string.h> | |
#include <stdarg.h> | |
#include <fcntl.h> | |
#include <signal.h> | |
#include <unistd.h> | |
static void usage(void); | |
int | |
main(int ac, char **av) | |
{ | |
const char *opts = ""; | |
int ttyfd; | |
int fd; | |
if (ac == 1) | |
usage(); | |
if (av[1]) { | |
if (av[1][0] == '-') { | |
opts = av[1]; | |
++av; | |
} | |
} | |
ttyfd = open("/dev/null", O_RDWR); | |
if (strchr(opts, '0') == NULL && ttyfd != 0) | |
dup2(ttyfd, 0); | |
if (strchr(opts, '1') == NULL && ttyfd != 1) | |
dup2(ttyfd, 1); | |
if (strchr(opts, '2') == NULL && ttyfd != 2) | |
dup2(ttyfd, 2); | |
if (ttyfd > 2) | |
close(ttyfd); | |
fd = open("/dev/tty", O_RDWR); | |
if (fd >= 0) { | |
ioctl(fd, TIOCNOTTY, 0); | |
close(fd); | |
} | |
if (fork() == 0) { | |
setsid(); | |
exit(execvp(av[1], av + 1)); | |
} | |
exit(0); | |
} | |
static void | |
usage(void) | |
{ | |
fprintf(stderr, "notty [-012] command args ...\n"); | |
exit(1); | |
} | |
ENDFILE | |
${cc_b} -o ./notty.bin ${TMPFILE} | |
${strip_b} ./notty.bin | |
${rm_b} -f ${TMPFILE} | |
notty="./notty.bin" | |
pgsql_b="${notty} -01 ${pgsql_b}" | |
pgsql_dump_b="${notty} -01 ${pgsql_dump_b}" | |
pgsql_vac_b="${notty} -01 ${pgsql_vac_b}" | |
else | |
${rm_b} -f ${notty} | |
${echo_b} "Cleaned up..." | |
fi | |
} | |
if [ "${mysql_do}" = "YES" ] | |
then | |
mysql_backup | |
fi | |
if [ "${file_do}" = "YES" ] | |
then | |
file_backup | |
fi | |
if [ "${pgsql_do}" = "YES" ] | |
then | |
if [ '$pgsql_p' != '' ] | |
then | |
notty 1 | |
fi | |
pgsql_backup | |
if [ '$pgsql_p' != '' ] | |
then | |
notty 0 | |
fi | |
fi |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
MIT Licensed