PostgreSQL: Jak utworzyć pełną kopię schematu bazy danych w tej samej bazie danych?

26

Jak mogę skopiować mój publicschemat do tej samej bazy danych z pełną strukturą tabeli, danymi, funkcjami, fk, pk itp.
Moja wersja Postgresa to 8.4
PS Muszę skopiować schemat NIE bazy danych

Sigra
źródło
Masz więcej schematów, czy tylko public?
a_horse_w_no_name
Mam schematy publiczne i demo. I muszę skopiować wersję demo, aby utworzyć konto demo ...
Byłoby to przydatne, aby móc to zrobić.
Kuberchaun

Odpowiedzi:

19

Nie ma prostego sposobu, aby to zrobić w samym pg_dump / pg_restore. Możesz spróbować wykonać następujące czynności, jeśli możesz tymczasowo usunąć bazę danych.

  1. Zrób zrzut swojego publicznego schematu za pomocą pg_dump
  2. uruchom „ALTER SCHEMA public RENAME TO public_copy”
  3. Przywróć zrzut swojego schematu publicznego z kroku 1 za pomocą pg_restore
użytkownik1113185
źródło
jak mogę uzyskać dostęp do pg_dump i pg_restore przez PHP?
To zależy od tego, gdzie prowadzisz bazę danych. Możesz uzyskać dostęp do pg_dump i pg_restore z powłoki na serwerze. Jeśli nie masz dostępu do powłoki, możesz spróbować użyć PHP_ shell_exec , w przeciwnym razie będziesz musiał spojrzeć na alternatywną metodę tworzenia kopii zapasowych, być może przy użyciu narzędzia GUI PostgreSQL
1
+1 To jak dotąd najmądrzejsze rozwiązanie. Polecenie powłoki będzie wyglądać mniej więcej tak ( więcej w instrukcji ) pg_dump -n my_schema -f '/path/to/file.pgsql' my_db. Najłatwiejszy jako superuser ( postgres) z peerautoryzacją bez pw w pg_haba.conf. Przywrócić po zmianie nazwy oryginalnego schematu: psql my_db -f '/path/to/file.pgsql'. Jeśli masz zwykły zrzut SQL, nie potrzebujesz pg_restore.
Erwin Brandstetter,
Jest prosty sposób, zobacz moją odpowiedź. pg_dump obsługuje przełącznik -n do wybierania schematu. Następnie po prostu edytuj nazwę schematu na zrzucie i załaduj ponownie.
Scott Marlowe,
2
Po prostu zmiana nazwy schematu nie spowoduje aktualizacji referencji w funkcjach: gist.github.com/pschultz/5387172 . Zamiana nazwy to zrzut jest o wiele bardziej niezawodny, jeśli uzyskasz prawidłowe wyszukiwanie i zamienisz.
Peter
9
pg_dump -n schema_name > dump.sql
vi dump.sql # edit the schema name
psql: psql -f dump.sql

Jeśli utkniesz z php, użyj jednego z tylnych tików

`/usr/bin/pg_dump-n myschema mydb -U username > /tmp/dump.sql`

lub polecenie exec (). Do zmiany możesz użyć sed w ten sam sposób.

Oto 6 dodatkowych znaków

Scott Marlowe
źródło
1
bezpieczniej jest zmienić nazwę schematu i załadować z powrotem kopię oryginalnego schematu, szczególnie gdy nazwa schematu może pojawiać się jako treść (np public.).
artm
7

Za pomocą pgAdmin możesz wykonać następujące czynności. Jest dość ręczny, ale może być wszystkim, czego potrzebujesz. Podejście oparte na skryptach byłoby znacznie bardziej pożądane. Nie jestem pewien, jak dobrze to zadziała, jeśli nie masz dostępu administratora i jeśli Twoja baza danych jest duża, ale powinna dobrze działać na bazie danych programowania, którą masz tylko na komputerze lokalnym.

  1. Kliknij prawym przyciskiem myszy nazwę schematu, którą chcesz skopiować, a następnie kliknij polecenie Kopia zapasowa. (Możesz przejść głębiej i wybrać kopię zapasową struktury zamiast obu).

  2. Nadaj nazwę plikowi kopii zapasowej, a także wybierz format. (Zwykle używam Tar.)

  3. Kliknij Kopia zapasowa.

  4. Kliknij prawym przyciskiem myszy schemat, z którego utworzono kopię zapasową, kliknij właściwości i tymczasowo zmień jego nazwę na inną. (np. nazwa tymczasowa )

  5. Kliknij katalog główny schematu i kliknij go prawym przyciskiem myszy w przeglądarce obiektów, a następnie kliknij Utwórz nowy schemat i nadaj schematowi nazwę publiczną . Będzie to schemat, na który kopiujesz z kopii zapasowej.

  6. Kliknij prawym przyciskiem myszy nowy schemat publiczny z kroku 5. i kliknij przywróć. Przywróć z pliku kopii zapasowej w kroku 3.

  7. Zmień nazwę nowego schematu na publiczny na inną nazwę (np. Newschema ).

  8. Zmień nazwę tymczasowej zmiany schematu z kroku 4 z powrotem na pierwotną nazwę.

Kuberchaun
źródło
Nowy schemat utworzony w kroku 5 musi mieć taką samą nazwę jak schemat, którego kopię zapasową utworzono, w przeciwnym razie pgAdmin niczego nie przywróci.
Cao Minh Tu
5

Możesz użyć

CREATE DATABASE new_db TEMPLATE = old_db;

Następnie upuść wszystkie schematy, których nie potrzebujesz:

DROP SCHEMA public CASCADE;
DROP SCHEMA other CASCADE;

Jedyną wadą jest to, że wszystkie połączenia ze old_db muszą zostać określone przed utworzeniem kopii (więc proces uruchamiający CREATE DATABASEinstrukcję musi łączyć się np. Z szablonem 1)

Jeśli nie jest to opcja, jedynym sposobem na to jest pg_dump / pg_restore.

koń bez imienia
źródło
1
Zanim zadałem to pytanie, użyłem podobnej metody klonowania bazy danych. Ale spędza dużo czasu i myślę, że klonowanie tylko schematu jest znacznie szybsze ...
@sigra: metoda klonowania a_horse jest najszybszą dostępną dla baz danych, ponieważ rzeczywiste pliki można po prostu skopiować, co pozwala zaoszczędzić sporo kosztów. Wątpię, aby zrzut i ponowne załadowanie schematu przebiegały szybciej, chyba że schemat jest tylko małą częścią całej bazy danych. Tak więc +1 za tę odpowiedź, nawet jeśli nie odpowiada na zadane pytanie.
Erwin Brandstetter
Klonowanie jednego schematu wymaga dużo pracy. zrzucanie schematu, zmiana jego nazwy na zrzucie i przeładowywanie jest znacznie szybsze.
Scott Marlowe,
@ScottMarlowe: zależy od tego, który jest największy schemat. Jeśli największy jest jednym z upuszczonych, to tak, zgadzam się.
a_horse_w_no_name
2

rozwijając odpowiedź user1113185 , oto pełny przepływ pracy przy użyciu psql / pg_dump.

Poniżej eksportuje wszystkie obiekty old_schemai importuje je do nowego new_schemaschematu, as user, w dbnamebazie danych:

psql -U user -d dbname -c 'ALTER SCHEMA old_schema RENAME TO new_schema'
pg_dump -U user -n new_schema -f new_schema.sql dbname
psql -U user -d dbname -c 'ALTER SCHEMA new_schema RENAME TO old_schema'
psql -U user -d dbname -c 'CREATE SCHEMA new_schema'
psql -U user -q -d dbname -f new_schema.sql
rm new_schema.sql
dwelle
źródło