mysqldump a un tar.gz

88

Por lo general, después de volcar una base de datos MySQL con el mysqldumpcomando, inmediatamente tar / gzip el archivo resultante. Estoy buscando una manera de hacer esto en un comando:

Entonces de esto:

mysqldump dbname -u root -p > dbname.sql
tar czvf dbname.sql.tgz dbname.sql
rm dbname.sql

A algo como esto:

mysqldump dbname -u root -p > some wizardry > dbname.sql.tgz

O incluso mejor (ya que generalmente estoy scp'ing el archivo de volcado a otro servidor):

mysqldump dbname -u root -p > send dbname.sql.tgz to user@host

Estoy ejecutando bash en Debian.

pygorex1
fuente

Respuestas:

102
mysqldump --opt <database> | gzip -c | ssh user@wherever 'cat > /tmp/yourfile.sql.gz'

No puede usar alquitrán en una tubería como esta, y no lo necesita de todos modos, ya que solo está generando un solo archivo. tar solo es útil si tiene varios archivos.

James
fuente
66
Tiene razón sobre no necesitar alquitrán, pero podría usarlo en la tubería si lo necesitara, conmysqldump | tar cf - | gzip -c | ssh ... 'cat > file.tgz'
Darren Chamberlain el
¿Eso realmente funciona? Estoy bastante seguro de que tar necesita una lista de nombres de archivo para trabajar.
James
2
Actualicé esto para trabajar localmente (no en un servidor ssh remoto) oh, y uso un nombre dinámico basado en la fecha, ¡gracias al póster original y al respondedor! mysqldump --opt <database> | gzip -c | cat > $(date +%Y-%m-%d-%H.%M.%S).sql.gz
electblake
44
@electblake: no necesitas usar 'cat' si es local. Justgzip -c > $(date +%Y-%m-%d-%H.%M.%S).sql.gz
James
Solo por diversión, podría usar en netcatlugar de tuberías para ssh. Debería ahorrar un poco en la sobrecarga de cifrado de ssh, si se transfiere a través de una red segura (o si no le importa la seguridad). Hoy en día también podría considerar usar en xzlugar de gzip.
James
45

Si está ejecutando esto localmente, simplemente use el siguiente comando para hacer una copia de seguridad de su base de datos y comprimirla usando gzip:

mysqldump -u userName -p (passwordPrompt) yourDatabaseName | gzip -c > output.gz 

(Editar: clave fija -c)

Dax
fuente
2
Sí, esta es la solución más simple. Yo también lo uso
Roman Snitko
2
Probablemente debería ser gzip -c, ¿verdad?
pilsetnieks
bien ... pero ¿cómo redirecciono stderr en este comando? Si agrego 2> / dev / null ya no funciona. Y 2> / dev / null antes de la tubería tampoco funciona.
Nelson Teixeira
mysqldump -u userName -p (passwordPrompt) yourDatabaseName 2> / var / log / dump-errors | gzip -v> output.gz
undefine
estoy usando como mysqldump -u root -p databasename --rutinas | gzip -v> myfile.sql.gz ... obtengo un archivo .gz parcial que no puedo descargar
Sushivam
18

Use una tubería con nombre.

mkfifo mysql_pipe
gzip -9 -c < mysql_pipe > name_of_dump.gz &
mysqldump database > mysql_pipe 
rm mysql_pipe

Lo uso todo el tiempo, es increíble.

http://en.wikipedia.org/wiki/Named_pipe

Jon Haddad
fuente
66
James hace lo mismo en 1 línea.
Jon Haddad
15
.. pero vale la pena aprender sobre las tuberías con nombre :-)
Tomasz Zieliński
mkfifo mysql_pipe; gzip -9 -c < mysql_pipe > name_of_dump.gz &; mysqldump database > mysql_pipe; rm mysql_pipeAhí, una línea. Por supuesto, mantendría el tubo alrededor y lo usaría siempre.
d34dh0r53
15

Escribí un script rápido para aspirar una base de datos remota de mysql. Utiliza compresión mysql, compresión gzip y ssh. Aspiró una base de datos multi GB a una velocidad increíble.

    ssh -C user@host "mysqldump --opt --compress database <table> | gzip -9 -c" > outputfile.sql.gz

Un beneficio adicional es que no requiere espacio libre en el servidor de la base de datos de origen, por lo que puede usarlo para hacer una copia de seguridad de una base de datos en un servidor con cero espacio libre en el disco antes de realizar una poda de sus datos.

Espero que ayude a alguien.

Tony Dillon
fuente
He creado un script de shell simple: #! / Bin / bash if [-z "$ 1"]; luego repita "Uso: $ {0} [host] [usuario] [base de datos] [archivo de salida]" exit else HOST = $ 1 fi if [-z "$ 2"]; luego repita "Uso: $ {0} $ {1} [usuario] [base de datos] [archivo de salida]" salir de otro modo USUARIO = $ 2 fi si [-z "$ 3"]; luego repita "Uso: $ {0} $ {1} $ {2} [base de datos] [archivo de salida]" salir de otro modo DB = $ 3 fi si [-z "$ 4"]; luego OUTFILE = "$ {DB} .sql.gz" else OUTFILE = $ 4 fi COMMAND = "ssh -C $ {USER} @ $ {HOST} \" mysqldump --opt $ {DB} | gzip -9 -c \ "> $ {OUTFILE}" ssh -C $ {USER} @ $ {HOST} "mysqldump --opt $ {DB} | gzip -9 -c"> $ {OUTFILE}
Tony Dillon
Dos de esas compresiones son inútiles: la opción de mysqldump comprime los datos en el proceso del servidor e inmediatamente se descomprime nuevamente (si mysqldump se ejecuta en el servidor DB). La opción -C para ssh activa la compresión gzip que desperdiciará más ciclos de CPU porque los datos ya están comprimidos en ese punto.
MattW.
5

Uso pvy tasa de monitor!

mysqldump prod_db -h dbslave | pv | gzip -c > prod_2012_08_20.dump.tgz

O, si conoce el tamaño (3GB), obtenga una estimación precisa:

mysqldump prod_db -h dbslave | pv -s 3g | gzip -c > prod_2012_08_20.dump.tgz
Nueva Alejandría
fuente
4

Prueba esto:

mysqldump --all-databases --password=dbpassword | gzip -c | ssh user@servername "cat >/tmp/filename_of_your_choice.gz"

Por favor, no es que no sea bueno en estas cosas, solo combiné 2 opciones en la web en una sola.

Es muy posible que sea mejor de alguna otra manera, pero esta es una frase que funciona para mí.

Sin embargo, requiere ssh.keysser instalado y aceptado si desea utilizarlo en scripts crontabo similares.

Charlie Candergart
fuente
1
Bienvenido a ServerFault. Me parece perfectamente razonable.
pollitos
2

Puedes hacer como:

mysqldump --add-drop-table -h dbhost -u dbuser -p dbname (tablename tablename ... ) | gzip -c > wp.sql.gz

p.ej

mysqldump --add-drop-table -h localhost -u root -p wordpress | gzip -c > wp.sql.gz

Min He
fuente
1

He estado trabajando en este script bash a continuación que intenta reunir todos los buenos consejos que he visto cuando se trata de volcar / restaurar con mysql. Está dirigido a operaciones remotas.

Solo reconfigura los vars y pruébalo. :)

Las características son:

  • puede pasar una lista de tablas para volcar (volcado selectivo)
  • se le pueden solicitar contraseñas (MySQL / SSH) o configurarlas en variables
  • la transmisión de red está comprimida
  • puede optar por guardar el volcado comprimido en el servidor remoto
  • puede volver a importar el volcado al servidor remoto sobre la marcha (sin archivos temporales en el servidor local / remoto)
  • tienes retroalimentación visual de lo que está sucediendo (gracias a echo y pv)
  • puedes configurar las variables mysql antes y después del proceso de volcado

Lo que necesita mejorar:

  • necesita pasar una lista de tablas (no puede volcar todas las tablas)
  • La contraseña de MySQL es la misma para el origen y el destino
  • necesita OTORGAR PRIVILEGIOS manualmente (parece que MySQL no permite hacerlo de forma remota)
  • necesitas tener instalado sshpass
  • algunas tablas comprimidas enormes de innodb son lentas para volcar (puede ser culpa de mysqldump)

Comparto este script aquí esperando que la comunidad pueda mejorarlo. (Se ve mejor con nano u otro editor que colorea el código)

--------------------------------- corta aquí --------------- -------------------

#!/bin/bash
#set -x

#REQUIRED VARS
SOURCE_USER=root   #MySQL user
SOURCE_HOST=localhost
SOURCE_PASSWORD=yourmysqlpass  #optional
SOURCE_DBNAME=yourdbname
TARGET_HOST=192.168.1.2
TARGET_DBNAME=yourdbname
TARGET_SSHUSER=root
TARGET_SSHPASSWORD=yoursshpass  #optional
TABLES='table1 table2 table3 table4'
TARGET_DIR="/data/dumpfiles"
EXEC_ACTION_TEXT[0]='Reimport TABLES directly into remote MySQL database'
EXEC_ACTION_TEXT[1]='Backup gzipped data to TARGED_DIR on remote TARGET_HOST'
EXEC_ACTION=0

#print config
echo "---------------------------------"
echo " SOURCE_USER:    $SOURCE_USER (MySQL)"
if [ "SOURCE_PASSWORD" != "" ]; then
echo " SOURCE_PASSWORD:<present>        "; else
echo " SOURCE_PASSWORD:<to be asked>    "
fi
echo " SOURCE_HOST:    $SOURCE_HOST     "
echo " SOURCE_DBNAME:  $SOURCE_DBNAME   "
echo " TARGET_HOST:    $TARGET_HOST     "
echo " TARGET_DBNAME:  $TARGET_DBNAME   "
echo " TARGET_SSHUSER: $TARGET_SSHUSER  "
if [ "TARGET_SSHPASSWORD" != "" ]; then
echo " TARGET_SSHPASS: <present>     "; else
echo " TARGET_SSHPASS: <to be asked>    "
fi
echo " TABLES:         $TABLES          "
echo " EXEC_ACTION:    $EXEC_ACTION - ${EXEC_ACTION_TEXT[$EXEC_ACTION]}"
echo " TARGET_DIR:     $TARGET_DIR (only for action 1)"
echo "---------------------------------"
echo "PRESS <ENTER> to continue...";  read;  echo

#read the mysql password from command-line (SOURCE and TARGET uses the same password)
if [ "$SOURCE_PASSWORD" == "" ]; then
     echo -n "Type $SOURCE_USER password for MySQL servers: "; read -s SOURCE_PASSWORD; echo
fi
echo "Creating database $TARGET_DBNAME on $TARGET_HOST if not exists ... "
mysql \
--user=$SOURCE_USER \
--password=$SOURCE_PASSWORD \
--host=$TARGET_HOST \
--execute "create database if not exists $TARGET_DBNAME;"

echo '--------------------------------------------------------------------------------------'
echo "**** ATTENTION ****: execute this command on mysql server at  $TARGET_HOST :"
echo "GRANT ALL PRIVILEGES ON $TARGET_DBNAME.* TO '$SOURCE_USER'@'%' IDENTIFIED BY 'yourpass';"
echo '--------------------------------------------------------------------------------------'
echo "PRESS <ENTER> to continue...";  read;  echo

#read the password from command-line
if [ "$TARGET_SSHPASSWORD" == "" ]; then
     echo -n "Type the password for remote SSH Server (TARGET) ['$TARGET_SSHUSER'@'$TARGET_HOST']: "; read -s TARGET_SSHPASSWORD; echo
fi

for thistable in $TABLES
do
     case "$EXEC_ACTION" in
         0)
         thisaction="gunzip | mysql --user=$SOURCE_USER --password=$SOURCE_PASSWORD -D $TARGET_DBNAME"
         endmessage='remote reimporting has finished'
         ;;
         1)
         thisaction="cat > $TARGET_DIR/`date +%Y.%m.%d`-"$thistable".gz"
         endmessage="$thisaction has finished"
         ;;
         *)   echo "EXEC_ACTION=$EXEC_ACTION not supported" && exit 1
     esac

     echo "---------------------------------------------------------------------"
     echo "-- table $thistable"
     echo "---------------------------------------------------------------------"
     (
       echo -n "-- setting variables... " > /dev/stderr  #talk to user via stderr
       echo "SET AUTOCOMMIT=0; SET UNIQUE_CHECKS=0; SET FOREIGN_KEY_CHECKS=0;"
       echo -n "starting mysqldump... " > /dev/stderr
       mysqldump --opt --user=$SOURCE_USER --password=$SOURCE_PASSWORD --host=$SOURCE_HOST $SOURCE_DBNAME $thistable
       echo -n "done mysqldump, reseting variables... " > /dev/stderr
       echo "SET FOREIGN_KEY_CHECKS=1; SET UNIQUE_CHECKS=1; SET AUTOCOMMIT=1;"
       echo -n "commiting... " > /dev/stderr
       echo "COMMIT;"
       echo "done!" > /dev/stderr
     ) | \
     gzip -c -2 | \
     pv | \
     sshpass -p $TARGET_SSHPASSWORD ssh $TARGET_SSHUSER'@'$TARGET_HOST $thisaction
     echo $endmessage ' with exit status '$?
done
Fernando Fabreti
fuente
0

También puede almacenar su contraseña en un archivo de configuración y usar esta opción --defaults-extra-file:

mysqldump --defaults-extra-file=mysqldump.cnf DataBaseName | gzip -c > DBOutputName.sql.gz

El archivo de configuración puede verse así:

[mysqldump]
host = localhost
user = username
password = "password"
linstar
fuente