Còpies de seguretat de Postgres I
Contingut |
Fent la còpia de seguretat: pg_dump dbname > outfile
http://www.postgresql.org/docs/8.3/interactive/backup-dump.html
Amb pg_dump generarem un fitxer de text amb les comandes SQL de manera que, un cop importades altre cop al servidor, recrearà la base de dades i la deixarà en el mateix estat que quan vam fer el dump.
pg_dump és una aplicació client del PostgreSQL, i a efectes pràctics, per no tenir problemes de permisos, millor executar-lo com a superusuari:
$ pg_dump -h localhost -p 5432 -U postgres abanq > abanq.dmp
o bé, per tal que no ens demani password (que és el que necessito per poder fer còpies de seguretat):
$ PGUSER=postgres $ PGPASSWORD=postgres $ PGHOST=localhost $ PGPORT=5432 $ export PGUSER PGPASSWORD PGHOST PGPORT $ pg_dump abanq > abanq.dmp
$ joe abanq.dmp -- -- PostgreSQL database dump -- SET client_encoding = 'UTF8'; SET standard_conforming_strings = off; SET check_function_bodies = false; SET client_min_messages = warning; SET escape_string_warning = off; SET search_path = public, pg_catalog; SET default_tablespace = ''; SET default_with_oids = false; -- -- Name: agentes; Type: TABLE; Schema: public; Owner: postgres; Tablespace: -- CREATE TABLE agentes ( codpostal character varying(10), codagente character varying(10) NOT NULL, ...
com veiem, aquesta exportació s'ha realitzat en mode text pla, amb totes les comandes SQL visibles i comprensibles.
La Comanda pg_dmp té diferents opcions (man pg_dmp), les més destacades són:
- -a: data only
- -c: clean, fa un drop dels objectes abans de tornar-los a crear.
- -C: create, crea la base de dades
- -d, -D : fa inserts en comptes de COPY, i això fa que la restauració sigui molt més lenta, però és útil per a fer exportacions a altres bases de dades. Amb -D es posen els noms dels camps de forma explícita.
- -f fitxer. És el fitxer de sortida que contindrà la còpia de seguretat.
- -F format: és el format de sortida, que pot ser:
- p: text pla
- c: custom. És el format més flexible, és un format comprimit, i va bé per utilitzar després el pg_restore en la restauració.
- t: tar, comprimit
- -i: ignorar la versió
- -O: no owner. No escriu les comandes per fer que els objectes conservin el propietari.
- -s: schema only. Només exporta la definició dels objectes, no les dades.
- -t table: s'especifica quines taules vols exportar
- -v: verbose
- -x: no-privileges. No s'exporten les comandes GRANT, REVOKE originals
Per exemple, també podem fer:
$ PGUSER=postgres $ PGPASSWORD=postgres $ PGHOST=localhost $ PGPORT=5432 $ export PGUSER PGPASSWORD PGHOST PGPORT $ pg_dump abanq -f abanq2.dmp -i -x -O
Si vull exportar a un fitxer comprimit, i que després pugui importar mitjançant pg_restore:
$ pg_dump abanq -f abanq3.dmp -i -x -O -Fc
Si ara visualitzo el fitxer abanq3.dmp, veuré que hi ha caràcters comprimits, sobretot en la part de les dades.
Si volem comprimir el fitxer de sortida:
$ pg_dump dbname | gzip > filename.gz (per fer la còpia) $ gunzip -c filename.gz | psql dbname (per fer la restauració, veure més avall com utilitzem psql)
pg_dumpall
pg_dump només fa la còpia d'una base de dades, i no copia informació de rols i espais de taula. Per fer una còpia total del clúster de base de dades, s'utilitza pg_dumpall:
$ pg_dumpall > outfile (còpia) $ psql -f infile postgres (restauració)
PGUSER=postgres PGPASSWORD=postgres PGHOST=localhost PGPORT=5432 export PGUSER PGPASSWORD PGHOST PGPORT
Restaurar la còpia de seguretat
Per restaurar hi ha vàries possibilitats: psql, pg_restore (que utilitzarem quan utilitzem el format custom: -Fc)
Restauració amb psql
els fitxers de text creats amb pg_dump es restauren amb psql:
$ psql dbname < infile $ psql abanq < abanq.dmp
Dóna un missatge de què els objectes ja existeixen. Una possibilitat és dir en el pg_dump que es tornin a crear els objectes (-c). En aquest cas no es pot utilitzar -C per tornar a crear la base de dades.
Una seqüència que funciona sense errors i sense missatges d'error és:
$ pg_dump abanq -f abanq4.dmp -c $ psql abanq < abanq4.dmp
Nota: si fem l'exportació amb l'opció -Fc, hem de restaurar amb pg_restore.
Restauració amb pg_restore
$ man pg_restore
És la restauració que farem quan utilitzem l'opció -Fc (o qualsevol format que no sigui text pla), que és un format que comprimeix. És el format que utiltizaré per a fer les meves còpies de seguretat automàtiques.
pg_restore permet ser selectiu amb allò que es restaura.
$ pg_dump -Fc dbname > filename $ pg_restore -d dbname filename
Per exemple, una seqüència que funciona és:
$ pg_dump -Fc -f abanq6.dmp abanq $ # eliminem les dues files de la taula provincias $ psql -h localhost -p 5432 -U postgres abanq abanq# delete from provincias; abanq# \q $ pg_restore -a -d abanq abanq6.dmp $ psql -h localhost -p 5432 -U postgres abanq abanq# select from provincias; (comprovem que la informació hi és) abanq# \q
Per llistar tot allò que conté un fitxer de restauració:
$ pg_restore -l -d abanq abanq6.dmp
Una seqüència que funciona, eliminant la base de dades i tornant-la a crear és:
$ pg_dump -C -Fc -f abanq8.dmp abanq $ dropdb abanq http://www.postgresql.org/docs/8.3/interactive/backup-dump.html $ createdb -T template0 abanq $ pg_restore -d abanq abanq8.dmp
scripts: automatitzar les còpies de seguretat
pg_dmp_automatic.sh
Aquest script és una simplificació del script pg_dmp.sh, que utilitza la utilitat pg_dump del postgres per fer còpies de seguretat.
Ús: ./pg_dmp_automatic.sh <base_dades>, on <base_dades> és la base de dades de la que vull fer un backup.
#!/bin/bash ############################## #Script by Joan Q, a partir de pg_dmp.sh ############################## PGUSER=postgres PGPASSWORD=postgres PGHOST=localhost PGPORT=5432 export PGUSER PGPASSWORD PGHOST PGPORT tdate=`date +%d%m%y` if ! [ -d $HOME/pg_backup_$1 ] then #if folder pg_backup_'databsename' does not exist in the current users home dierectory then create a new folder mkdir $HOME/pg_backup_$1 fi pg_dump $1 -f $HOME/pg_backup_$1/$1_$tdate -i -x -Fc #reset PGUSER and PGPASSWORD PGUSER="" PGPASSWORD="" PGHOST="" PGPORT="" export PGUSER PGPASSWORD PGHOST PGPORT #End
- Exporto les variables d'entorn del postgres
- fico la data en la variable tdate amb el format date111008
- el primer paràmetre és la base de dades que vull copiar. Comprova si existeix el directori $HOME/pg_backup_$1, (per ex, /home/joan/pg_backup_postgres), i si no existeix el crea
- pg_dump $1 -f $HOME/pg_backup_$1/$1_$tdate -i -x -Fc
- fa la còpia de seguretat pròpiament dita.
- especifico la base de dades que vull copiar, el fitxer que es crearà (-f), que serà del tipus postgres_101108, ignore-version (-i), no-privileges (-x), format custom (-Fc, custom: Output a custom archive suitable for input into pg_restore. This is the most flexible format in that it allows reordering of loading data as well as object definitions. This format is also compressed by default.)
pg_dmp.sh
#!/bin/bash ############################## #Script by Anas V ############################## #Substitute your postgresql root username in the below given line PGUSER=postgres #Substitute your postgresql root password in the below given line PGPASSWORD=postgres export PGUSER PGPASSWORD PGHOST=localhost PGPORT=5432 export PGHOST PGPORT tdate=`date +%d-%b-%Y` if [ $# -lt 1 ] # Check if there is at least one argument [i.e the database whose dump is to be taken] #First argument is mandatory - Databse name #Second argument is optional - Destination path to save dump then echo "Bad Arguments" echo "-----------------------------------" echo "USAGE : pg_dmp.sh <databasename> [outputfile]" echo "-----------------------------------" exit 1 else #if one or more arguments were provided if [ $# -ge 2 ] #if arguments provided is greater than or equal to 2 then #Comment out the below given file exist check and it's associated messages # if you want to run the pg_dmpsh script to run silently. i.e from a cron or at job # without any user interaction. Then the output dump file will be rewritten if a file # already exists. if [ -f $2 ] # if destination file ie argument 2 is already existing then #Show confirmation message to confirm whether replace file with new one or exit dialog --title "Confirm File Replace" --backtitle "pg_dmp.sh" --yesno "\nFile already exist, Do you want to replace it with '$2' file" 7 90 sel=$? case $sel in #if Yes then take dump and replace the existing file with new dump 0) pg_dump $1 -f $2 -i -x -O -R;; #if No then exit 1) exit 1 ;; #if escape then exit 255) exit 1;; esac else #if destination file does not exist then create and save the dump in destination path pg_dump $1 -f $2 -i -x -O -R fi else if [ $# -eq 1 ] #if arguments provided is equal to 1 then if [ -d $HOME/pg_backup_$1 ] #if folder name pg_backup_'databsename' exist in the current users home directory then if [ -f $HOME/pg_backup_$1/$1_$tdate ] #if destination file name exist in pg_backup_'databasename' folder in current users home dierectory then #Show confirmation message for replacing the file with new dump dialog --title "Confirm File Replace" --backtitle "pg_dump.sh"\ --yesno "\nFile already exist, Do you want to replace it with '$HOME/pg_backup_$1/$1_$tdate' file" 7 90 sel=$? case $sel in #if Yes then replace the file with new dump file 0) pg_dump $1 -f $HOME/pg_backup_$1/$1_$tdate -i -x -O -R;; #if No then exit 1) exit 1 ;; #if escape thenexit 255) exit 1;; esac else #if destination file does not exist then create and save the dump pg_dump $1 -f $HOME/pg_backup_$1/$1_$tdate -i -x -O -R fi else #if folder pg_backup_'databsename' does not exist in the current users home dierectory then #Create a new folder mkdir $HOME/pg_backup_$1 #then create dump and save it pg_dump $1 -f $HOME/pg_backup_$1/$1_$tdate -i -x -O -R #if databse to take does not exist then Delete the folder created if [ $? -ne 0 ] then rmdir $HOME/pg_backup_$1 fi fi fi fi if [ $# -gt 2 ] #if arguments passed where greater than 2 then show message then echo "Extra Arguments ignored" fi fi #reset PGUSER and PGPASSWORD PGUSER="" PGPASSWORD="" export PGUSER PGPASSWORD PGHOST="" PGPORT="" export PGHOST PGPORT #End
En aquest script, més complet, tenim la possibilitat de ficar un segon argument, que és el nom que donarem a la còpia. En el cas de què existeixi la còpia hi ha la possibilitat de reemplaçar-la o conservar-la. Es fa de forma interactiva mitjançant un dialog.
Si no funciona la comanda dialog, s'ha d'instal.lar el paquet:
$ sudo apt-get install dialog $ man dialog $ dialog --msgbox 'hola món!' 0 0
Cron: Còpies periòdiques. Fitxer crontab
el fitxer crontab queda de la següent manera, on la última línia diu que s'executi cada minut el script pg_dmp_automatic.sh, que fa una còpia de la base de dades <postgres>, valor que passo com a paràmetre.
# /etc/crontab: system-wide crontab # Unlike any other crontab you don't have to run the `crontab' # command to install the new version when you edit this file # and files in /etc/cron.d. These files also have username fields, # that none of the other crontabs do. SHELL=/bin/sh PATH=/usr/local/sbin:/usr/local/bin:/sbin:/bin:/usr/sbin:/usr/bin # m h dom mon dow user command 17 * * * * root cd / && run-parts --report /etc/cron.hourly 25 6 * * * root test -x /usr/sbin/anacron || ( cd / && run-parts --report /etc/cron.daily ) 47 6 * * 7 root test -x /usr/sbin/anacron || ( cd / && run-parts --report /etc/cron.weekly ) 52 6 1 * * root test -x /usr/sbin/anacron || ( cd / && run-parts --report /etc/cron.monthly ) */1 * * * * joan /home/joan/llegir.sh */1 * * * * joan /home/joan/pg_dmp_automatic.sh postgres #
creat per Joan Quintana Compte, novembre 2008