Quelle est la bonne façon de copier la base de données entière (sa structure et ses données) dans une nouvelle base de données dans pgAdmin?
Postgres permet d'utiliser n'importe quelle base de données existante sur le serveur comme modèle lors de la création d'une nouvelle base de données. Je ne sais pas si pgAdmin vous donne l'option dans la boîte de dialogue de création de base de données, mais vous devriez pouvoir exécuter les opérations suivantes dans une fenêtre de requête si ce n'est pas le cas:
CREATE DATABASE newdb WITH TEMPLATE originaldb OWNER dbuser;
Cependant, vous pouvez obtenir:
ERROR: source database "originaldb" is being accessed by other users
Pour résoudre ce problème, vous pouvez utiliser cette requête.
SELECT pg_terminate_backend(pg_stat_activity.pid) FROM pg_stat_activity
WHERE pg_stat_activity.datname = 'originaldb' AND pid <> pg_backend_pid();
Une version en ligne de commande de Réponse de Bell :
createdb -O ownername -T originaldb newdb
Cela devrait être exécuté sous les privilèges du maître de la base de données, généralement postgres.
Pour cloner une base de données existante avec postgres, vous pouvez le faire.
/* KILL ALL EXISTING CONNECTION FROM ORIGINAL DB (sourcedb)*/
SELECT pg_terminate_backend(pg_stat_activity.pid) FROM pg_stat_activity
WHERE pg_stat_activity.datname = 'SOURCE_DB' AND pid <> pg_backend_pid();
/* CLONE DATABASE TO NEW ONE(TARGET_DB) */
CREATE DATABASE TARGET_DB WITH TEMPLATE SOURCE_DB OWNER USER_DB;
Il va tuer toute la connexion à la base de données en évitant l'erreur
ERROR: source database "SOURCE_DB" is being accessed by other users
Dans l'environnement de production, où la base de données d'origine est sous trafic, j'utilise simplement:
pg_dump production-db | psql test-db
Je ne connais pas pgAdmin, mais pgdump
vous donne une image de la base de données en SQL Il vous suffit de créer une base de données du même nom et de
psql mydatabase < my dump
pour restaurer toutes les tables et leurs données et tous les privilèges d'accès.
Tout d’abord, Sudo
en tant qu’utilisateur de la base de données:
Sudo su postgres
Aller à la ligne de commande PostgreSQL:
psql
Créez la nouvelle base de données, donnez les droits et quittez:
CREATE DATABASE new_database_name;
GRANT ALL PRIVILEGES ON DATABASE new_database_name TO my_user;
\d
Copiez la structure et les données de l'ancienne base de données sur la nouvelle:
pg_dump old_database_name | psql new_database_name
J'ai reconstitué cette approche avec les exemples ci-dessus. Je travaille sur un serveur "sous charge" et j'ai eu l'erreur lorsque j'ai tenté l'approche de @zbyszek. Je recherchais également une solution "en ligne de commande uniquement".
createdb: database creation failed: ERROR: source database "exampledb" is being accessed by other users
.
Voici ce qui a fonctionné pour moi ( Les commandes précédées de Nohup
pour déplacer la sortie dans un fichier et se protéger d'un serveur déconnecté ):
Nohup pg_dump exampledb > example-01.sql
createdb -O postgres exampledbclone_01
</ p>mon utilisateur est "postgres" </ li>
- </ ol>
Nohup psql exampledbclone_01 < example-01.sql
Dans pgAdmin, vous pouvez créer une sauvegarde à partir de votre base de données d'origine, puis simplement créer une nouvelle base de données et la restaurer à partir de la sauvegarde créée:
Quelle est la bonne façon de copier la base de données entière (sa structure et ses données) dans une nouvelle base de données dans pgAdmin?
Réponse:
CREATE DATABASE newdb WITH TEMPLATE originaldb;
Essayé et testé.
PostgreSQL 9.1.2:
$ CREATEDB new_db_name -T orig_db_name -O db_user;
Pour ceux qui sont toujours intéressés, j'ai créé un script bash qui fait (plus ou moins) ce que l'auteur voulait. Je devais faire une copie quotidienne de la base de données métier sur un système de production, ce script semble faire l'affaire. N'oubliez pas de changer le nom de la base de données/l'utilisateur/les valeurs de pw.
#!/bin/bash
if [ 1 -ne $# ]
then
echo "Usage `basename $0` {tar.gz database file}"
exit 65;
fi
if [ -f "$1" ]
then
EXTRACTED=`tar -xzvf $1`
echo "using database archive: $EXTRACTED";
else
echo "file $1 does not exist"
exit 1
fi
PGUSER=dbuser
PGPASSWORD=dbpw
export PGUSER PGPASSWORD
datestr=`date +%Y%m%d`
dbname="dbcpy_$datestr"
createdbcmd="CREATE DATABASE $dbname WITH OWNER = postgres ENCODING = 'UTF8' TABLESPACE = pg_default LC_COLLATE = 'en_US.UTF-8' LC_CTYPE = 'en_US.UTF-8' CONNECTION LIMIT = -1;"
dropdbcmp="DROP DATABASE $dbname"
echo "creating database $dbname"
psql -c "$createdbcmd"
rc=$?
if [[ $rc != 0 ]] ; then
rm -rf "$EXTRACTED"
echo "error occured while creating database $dbname ($rc)"
exit $rc
fi
echo "loading data into database"
psql $dbname < $EXTRACTED > /dev/null
rc=$?
rm -rf "$EXTRACTED"
if [[ $rc != 0 ]] ; then
psql -c "$dropdbcmd"
echo "error occured while loading data to database $dbname ($rc)"
exit $rc
fi
echo "finished OK"
Pour créer un vidage de base de données
cd /var/lib/pgsql/
pg_dump database_name> database_name.out
Pour resoter la sauvegarde de la base de données
psql -d template1
CREATE DATABASE database_name WITH ENCODING 'UTF8' LC_CTYPE 'en_US.UTF-8' LC_COLLATE 'en_US.UTF- 8' TEMPLATE template0;
CREATE USER role_name WITH PASSWORD 'password';
ALTER DATABASE database_name OWNER TO role_name;
ALTER USER role_name CREATEDB;
GRANT ALL PRIVILEGES ON DATABASE database_name to role_name;
CTR+D(logout from pgsql console)
cd /var/lib/pgsql/
psql -d database_name -f database_name.out
À partir de documentation , l'utilisation de createdb
ou CREATE DATABASE
avec des modèles n'est pas encouragée:
Bien qu'il soit possible de copier une base de données autre que template1 par en spécifiant son nom en tant que modèle, il ne s’agit pas (encore) de Fonction "COPY DATABASE" à usage général. La principale limitation est qu'aucune autre session ne peut être connectée à la base de données de modèles avec il est copié. CREATE DATABASE échouera si toute autre connexion existe quand il commence; sinon, nouvelles connexions au modèle base de données sont verrouillées jusqu'à la fin de CREATE DATABASE.
pg_dump
ou pg_dumpall
est un bon moyen de copier la base de données ET TOUTES LES DONNÉES. Si vous utilisez une interface graphique telle que pgAdmin, ces commandes sont appelées en arrière-plan lorsque vous exécutez une commande de sauvegarde. La copie dans une nouvelle base de données se fait en deux phases: Sauvegarde et restauration
pg_dumpall
enregistre toutes les bases de données sur le cluster PostgreSQL. L'inconvénient de cette approche est que vous vous retrouvez avec un fichier texte potentiellement très volumineux contenant du code SQL requis pour créer la base de données et renseigner les données. L'avantage de cette approche est que vous obtenez gratuitement tous les rôles (autorisations) du cluster. Pour vider toutes les bases de données, faites-le à partir du compte superutilisateur.
pg_dumpall > db.out
et pour restaurer
psql -f db.out postgres
pg_dump
a des options de compression qui vous donnent des fichiers beaucoup plus petits. J'ai une base de données de production que je sauvegarde deux fois par jour avec un travail cron utilisant
pg_dump --create --format=custom --compress=5 ==file=db.dump mydatabase
où compress
est le niveau de compression (0 à 9) et create
indique à pg_dump d'ajouter des commandes pour créer la base de données. Restaurez (ou déplacez vers un nouveau cluster) en utilisant
pg_restore -d newdb db.dump
où newdb est le nom de la base de données que vous souhaitez utiliser.
PostgreSQL utilise ROLES pour gérer les autorisations. Ceux-ci ne sont pas copiés par pg_dump
. De plus, nous n'avons pas traité les paramètres de postgresql.conf et pg_hba.conf (si vous déplacez la base de données sur un autre serveur). Vous devrez déterminer vous-même les paramètres de configuration. Mais il y a un truc que je viens de découvrir pour la sauvegarde des rôles. Les rôles sont gérés au niveau du cluster et vous pouvez demander à pg_dumpall
de ne sauvegarder que les rôles à l'aide du commutateur de ligne de commande --roles-only
.
Si la base de données a des connexions ouvertes, ce script peut vous aider. J'utilise ceci pour créer chaque nuit une base de données de test à partir d'une sauvegarde de la base de données de production en direct. Cela suppose que vous ayez un fichier de sauvegarde .SQL de la base de production (je le fais dans Webmin).
#!/bin/sh
dbname="desired_db_name_of_test_enviroment"
username="user_name"
fname="/path to /ExistingBackupFileOfLive.sql"
dropdbcmp="DROP DATABASE $dbname"
createdbcmd="CREATE DATABASE $dbname WITH OWNER = $username "
export PGPASSWORD=MyPassword
echo "**********"
echo "** Dropping $dbname"
psql -d postgres -h localhost -U "$username" -c "$dropdbcmp"
echo "**********"
echo "** Creating database $dbname"
psql -d postgres -h localhost -U "$username" -c "$createdbcmd"
echo "**********"
echo "** Loading data into database"
psql -d postgres -h localhost -U "$username" -d "$dbname" -a -f "$fname"
À l’aide de pgAdmin, déconnectez la base de données que vous souhaitez utiliser comme modèle. Ensuite, vous le sélectionnez comme modèle pour créer la nouvelle base de données, cela évite d’obtenir l’erreur déjà utilisée.
Si vous voulez copier le schéma entier, vous pouvez créer un pg_dump avec la commande suivante:
pg_dump -h database.Host.com -d database_name -n schema_name -U database_user --password
Et lorsque vous souhaitez importer ce dump, vous pouvez utiliser:
psql "Host=database.Host.com user=database_user password=database_password dbname=database_name options=--search_path=schema_name" -f sql_dump_to_import.sql
Plus d'informations sur les chaînes de connexion: https://www.postgresql.org/docs/current/libpq-connect.html#LIBPQ-CONNSTRING
Ou alors simplement en le combinant dans une doublure:
pg_dump -h database.Host.com -d postgres -n schema_name -U database_user --password | psql "Host=database.Host.com user=database_user password=database_password dbname=database_name options=--search_path=schema_name”
Déconnectez la base de données "modèle" que vous souhaitez utiliser comme modèle.
Exécuter 2 requêtes comme ci-dessous
SELECT pg_terminate_backend(pg_stat_activity.pid)
FROM pg_stat_activity
WHERE pg_stat_activity.datname = 'TemplateDB' AND pid <> pg_backend_pid();
(L'instruction SQL ci-dessus mettra fin à toutes les sessions actives avec TemplateDB. Vous pourrez ensuite la sélectionner en tant que modèle pour créer la nouvelle base de données TargetDB. Cela évite d'obtenir l'erreur déjà utilisée.)
CREATE DATABASE 'TargetDB'
WITH TEMPLATE='TemplateDB'
CONNECTION LIMIT=-1;