Как я могу отбросить все таблицы в PostgreSQL, работая из командной строки?
Я не хочу отбрасывать саму базу данных, только все таблицы и все данные в них.
public
, вы теряете все установленные расширения.
Как я могу отбросить все таблицы в PostgreSQL, работая из командной строки?
Я не хочу отбрасывать саму базу данных, только все таблицы и все данные в них.
public
, вы теряете все установленные расширения.
Ответы:
Если все ваши таблицы находятся в одной схеме, этот подход может работать (код ниже предполагает, что имя вашей схемы public
)
DROP SCHEMA public CASCADE;
CREATE SCHEMA public;
Если вы используете PostgreSQL 9.3 или более поздней версии, вам также может потребоваться восстановить права по умолчанию.
GRANT ALL ON SCHEMA public TO postgres;
GRANT ALL ON SCHEMA public TO public;
pg_
), поскольку они находятся в другой схеме pg_catalog
.
GRANT ALL ON SCHEMA public TO public;
после создания.
GRANT ALL
после создания?
Вы можете написать запрос для генерации сценария SQL следующим образом:
select 'drop table "' || tablename || '" cascade;' from pg_tables;
Или:
select 'drop table if exists "' || tablename || '" cascade;' from pg_tables;
В случае, если некоторые таблицы автоматически отбрасываются из-за каскадной опции в предыдущем предложении.
Кроме того, как указано в комментариях, вы можете отфильтровать таблицы, которые вы хотите удалить по имени схемы:
select 'drop table if exists "' || tablename || '" cascade;'
from pg_tables
where schemaname = 'public'; -- or any other schema
А затем запустите его.
Славная КОПИЯ + ПАСТА также будет работать.
drop schema public cascade;
, но у вас почти всегда есть права на удаление таблиц.
Наиболее приемлемый ответ на момент написания статьи (январь 2014 г.):
drop schema public cascade;
create schema public;
Это работает, однако если ваше намерение состоит в том, чтобы восстановить общедоступную схему в ее первоначальное состояние, это не полностью решит задачу. В pgAdmin III для PostgreSQL 9.3.1, если вы нажмете на «публичную» схему, созданную таким образом, и посмотрите на «панель SQL», вы увидите следующее:
-- Schema: public
-- DROP SCHEMA public;
CREATE SCHEMA public
AUTHORIZATION postgres;
Однако, напротив, новая база данных будет иметь следующее:
-- Schema: public
-- DROP SCHEMA public;
CREATE SCHEMA public
AUTHORIZATION postgres;
GRANT ALL ON SCHEMA public TO postgres;
GRANT ALL ON SCHEMA public TO public;
COMMENT ON SCHEMA public
IS 'standard public schema';
Для меня я использую веб-фреймворк Python, который создает таблицы базы данных (web2py), используя ранее вызванные проблемы:
<class 'psycopg2.ProgrammingError'> no schema has been selected to create in
На мой взгляд, полностью правильный ответ:
DROP SCHEMA public CASCADE;
CREATE SCHEMA public;
GRANT ALL ON SCHEMA public TO postgres;
GRANT ALL ON SCHEMA public TO public;
COMMENT ON SCHEMA public IS 'standard public schema';
Также обратите внимание, что для выдачи этих команд в pgAdmin III, я использовал инструмент Query (значок лупы «Выполнение запросов SQL»), или вы можете использовать Plugins-> PSQL Console
Запись
Если у вас установлены какие-либо расширения, они будут отброшены при удалении схемы, поэтому вы должны записать, что вам нужно установить, а затем выполнить инструкции по мере необходимости. Например
CREATE EXTENSION postgis;
drop
тогда create
) использовалось для работы с PostgreSQL 9.1. После обновления до 9.3 необходимы два дополнительных grant
.
Вы можете удалить все таблицы с
DO $$ DECLARE
r RECORD;
BEGIN
-- if the schema you operate on is not "current", you will want to
-- replace current_schema() in query with 'schematodeletetablesfrom'
-- *and* update the generate 'DROP...' accordingly.
FOR r IN (SELECT tablename FROM pg_tables WHERE schemaname = current_schema()) LOOP
EXECUTE 'DROP TABLE IF EXISTS ' || quote_ident(r.tablename) || ' CASCADE';
END LOOP;
END $$;
ИМО это лучше, чем drop schema public
, потому что вам не нужно воссоздавать schema
и восстанавливать все гранты.
Дополнительный бонус в том, что для этого не требуется внешний язык сценариев или копирование-вставка сгенерированного SQL обратно в интерпретатор
drop schema
хитрость, поскольку пользователь не был владельцем схемы, только таблиц. Этот работал, хотя :)
EXECUTE 'DROP TABLE IF EXISTS ' || quote_ident(r.tablename) || ' CASCADE';
следующим образом: EXECUTE format('DROP TABLE IF EXISTS %I CASCADE', quote_ident(r.tablename));
Если все, что вы хотите удалить, принадлежит одному и тому же пользователю, то вы можете использовать:
drop owned by the_user;
Это отбросит все, что принадлежит пользователю.
Это включает в себя материализованные представления, представления, последовательности, триггеры, схемы, функции, типы, агрегаты, операторы, домены и т. Д. (Так, действительно: все ), которым the_user
принадлежит (= создан).
Вы должны заменить the_user
действительное имя пользователя, в настоящее время нет возможности отбросить все для «текущего пользователя». В следующей версии 9.5 будет опция drop owned by current_user
.
Более подробная информация в руководстве: http://www.postgresql.org/docs/current/static/sql-drop-owned.html
public
схема принадлежат postgres
, но все остальное принадлежит определенному пользователю, поэтому удаление всего принадлежащего этому пользователю очищает базу данных, за исключением схемы.
В соответствии с Пабло выше, чтобы просто отказаться от конкретной схемы, в отношении случая:
select 'drop table "' || tablename || '" cascade;'
from pg_tables where schemaname = 'public';
where schemaname='public'
часть значима?
drop schema public cascade;
должен сделать свое дело.
CREATE SCHEMA public;
. Также см. Stackoverflow.com/a/14286370 для получения дополнительной информации
Вслед за Пабло и LenW, вот одна строка, которая делает все это и подготовку, и затем выполнение:
psql -U $PGUSER $PGDB -t -c "select 'drop table \"' || tablename || '\" cascade;' from pg_tables where schemaname = 'public'" | psql -U $PGUSER $PGDB
NB: либо установите, либо замените, $PGUSER
и $PGDB
значения, которые вы хотите
Если у вас есть PL / PGSQL процедурный язык установлен вы можете использовать следующую команду, чтобы удалить все без оболочки / Perl внешнего скрипта.
DROP FUNCTION IF EXISTS remove_all();
CREATE FUNCTION remove_all() RETURNS void AS $$
DECLARE
rec RECORD;
cmd text;
BEGIN
cmd := '';
FOR rec IN SELECT
'DROP SEQUENCE ' || quote_ident(n.nspname) || '.'
|| quote_ident(c.relname) || ' CASCADE;' AS name
FROM
pg_catalog.pg_class AS c
LEFT JOIN
pg_catalog.pg_namespace AS n
ON
n.oid = c.relnamespace
WHERE
relkind = 'S' AND
n.nspname NOT IN ('pg_catalog', 'pg_toast') AND
pg_catalog.pg_table_is_visible(c.oid)
LOOP
cmd := cmd || rec.name;
END LOOP;
FOR rec IN SELECT
'DROP TABLE ' || quote_ident(n.nspname) || '.'
|| quote_ident(c.relname) || ' CASCADE;' AS name
FROM
pg_catalog.pg_class AS c
LEFT JOIN
pg_catalog.pg_namespace AS n
ON
n.oid = c.relnamespace WHERE relkind = 'r' AND
n.nspname NOT IN ('pg_catalog', 'pg_toast') AND
pg_catalog.pg_table_is_visible(c.oid)
LOOP
cmd := cmd || rec.name;
END LOOP;
FOR rec IN SELECT
'DROP FUNCTION ' || quote_ident(ns.nspname) || '.'
|| quote_ident(proname) || '(' || oidvectortypes(proargtypes)
|| ');' AS name
FROM
pg_proc
INNER JOIN
pg_namespace ns
ON
(pg_proc.pronamespace = ns.oid)
WHERE
ns.nspname =
'public'
ORDER BY
proname
LOOP
cmd := cmd || rec.name;
END LOOP;
EXECUTE cmd;
RETURN;
END;
$$ LANGUAGE plpgsql;
SELECT remove_all();
Вместо того, чтобы вводить это в приглашении "psql", я бы посоветовал вам скопировать его в файл и затем передать этот файл в качестве ввода в psql, используя опции "--file" или "-f":
psql -f clean_all_pg.sql
Кредит, где кредит должен: я написал функцию, но думаю, что запросы (или, по крайней мере, первый) пришли от кого-то из одного из списков рассылки pgsql несколько лет назад. Не помню точно, когда или какой.
Если вы все равно хотите уничтожить все таблицы, вы можете обойтись без таких тонких вещей, как CASCADE, поместив все таблицы в один оператор. Это также ускоряет выполнение.
SELECT 'TRUNCATE TABLE ' || string_agg('"' || tablename || '"', ', ') || ';'
FROM pg_tables WHERE schemaname = 'public';
Выполнение этого напрямую:
DO $$
DECLARE tablenames text;
BEGIN
tablenames := string_agg('"' || tablename || '"', ', ')
FROM pg_tables WHERE schemaname = 'public';
EXECUTE 'TRUNCATE TABLE ' || tablenames;
END; $$
Заменить TRUNCATE
с , DROP
как это применимо.
public
схемой, не забудьте включить имя схемы в выражение: string_agg(quote_ident(schemaname) || '.' || quote_ident(tablename), ', ')
вместо простой передачи имен таблиц.
Используйте этот скрипт в pgAdmin:
DO $$
DECLARE
brow record;
BEGIN
FOR brow IN (select 'drop table "' || tablename || '" cascade;' as table_name from pg_tables where schemaname = 'public') LOOP
EXECUTE brow.table_name;
END LOOP;
END; $$
На всякий случай ... Простой скрипт на Python, который очищает базу данных Postgresql
import psycopg2
import sys
# Drop all tables from a given database
try:
conn = psycopg2.connect("dbname='akcja_miasto' user='postgres' password='postgres'")
conn.set_isolation_level(0)
except:
print "Unable to connect to the database."
cur = conn.cursor()
try:
cur.execute("SELECT table_schema,table_name FROM information_schema.tables WHERE table_schema = 'public' ORDER BY table_schema,table_name")
rows = cur.fetchall()
for row in rows:
print "dropping table: ", row[1]
cur.execute("drop table " + row[1] + " cascade")
cur.close()
conn.close()
except:
print "Error: ", sys.exc_info()[1]
Удостоверьтесь, что после копирования это отступ правильно, так как Python полагается на него.
Вы можете использовать функцию string_agg, чтобы создать разделенный запятыми список, идеально подходящий для DROP TABLE. Из скрипта bash:
#!/bin/bash
TABLES=`psql $PGDB -t --command "SELECT string_agg(table_name, ',') FROM information_schema.tables WHERE table_schema='public'"`
echo Dropping tables:${TABLES}
psql $PGDB --command "DROP TABLE IF EXISTS ${TABLES} CASCADE"
Это действительно интересный вопрос, и вы решите его несколькими способами. Я надеюсь, что это будет полезно для вас.
- Путем удаления и воссоздания текущей схемы
Здесь, в общем, у нас есть public
схема по умолчанию. Итак, я использую это как пример.
DROP SCHEMA `public` CASCADE;
CREATE SCHEMA `public`;
GRANT ALL ON SCHEMA public TO postgres;
GRANT ALL ON SCHEMA public TO public;
Если вы используете PostgreSQL 9.3 или более поздней версии, вам также может потребоваться восстановить права по умолчанию.
Плюсы:
Это очистит всю схему и заново создаст ее как новую.
Минусы:
Вы потеряете другие объекты тоже , как Functions
, Views
, Materialized views
и т.д.
- Используя выборку всех имен
pg_tables
таблиц из таблицы.
PostgreSQL хранит все таблицы в своей таблице записей с именем pg_table
.
SELECT
'DROP TABLE IF EXISTS "' || tablename || '" CASCADE;'
from
pg_tables WHERE schemaname = 'public';
Как видите, с помощью подзапроса мы можем удалить все таблицы из схемы.
Плюсы:
Когда другие объекты данных Важны, и вы просто хотите удалить только таблицы из схемы, этот подход действительно будет вам полезен.
Если вы хотите удалить данные (не удалить таблицу):
-- Truncate tables and restart sequnces
SELECT 'TRUNCATE TABLE "' || table_schema || '"."' || table_name || '" RESTART IDENTITY CASCADE;'
FROM information_schema.tables
WHERE table_catalog = '<database>' AND table_schema = '<schema>';
Или, если вы хотите удалить таблицу, вы можете использовать этот sql:
-- For tables
SELECT 'DROP TABLE "' || table_schema || '"."' || table_name || '" CASCADE;'
FROM information_schema.tables
WHERE table_catalog = '<database>' AND table_schema = '<schema>';
-- For sequences
SELECT 'DROP SEQUENCE d_a_seq "' || sequence_schema || '"."' || sequence_name || '";'
FROM information_schema.sequences
WHERE sequence_catalog = '<database>' AND sequence_schema = '<schema>';
Примечание: мой ответ - действительно удалить таблицы и другие объекты базы данных; для удаления всех данных в таблицах, т. е. усечения всех таблиц , Endre Both предоставил аналогично хорошо выполненный оператор (непосредственное выполнение) месяцем позже.
Для тех случаев , когда вы можете не только DROP SCHEMA public CASCADE;
, DROP OWNED BY current_user;
или что - то, вот автономный SQL скрипт я написал, что сделка безопасным (т.е. вы можете поместить его между BEGIN;
и или ROLLBACK;
к просто проверить это или COMMIT;
на самом деле делать дело) и очищает «все» объекты базы данных… ну, все те, которые используются в базе данных, которую использует наше приложение, или я мог бы разумно добавить, что:
CHECK
, UNIQUE
)VIEW
s (нормальный или материализованный)public
внутренние или DB-внутренние), которыми владеем «мы»: сценарий полезен, когда выполняется как «не суперпользователь базы данных»; суперпользователь может отбросить все схемы (хотя действительно важные из них явно исключены)Не исключены (некоторые преднамеренные; некоторые только потому, что у меня нет примера в нашей БД):
public
схемы (например , для расширения предоставленного материала в них)Это действительно полезно в тех случаях, когда дамп, который вы хотите восстановить, имеет другую версию схемы базы данных (например, с Debian dbconfig-common
, Flyway или Liquibase / DB-Manul), чем база данных, в которую вы хотите восстановить ее.
У меня также есть версия, которая удаляет «все, кроме двух таблиц и того, что им принадлежит» (последовательность, проверенная вручную, извините, я знаю, скучно), если кто-то заинтересован; разница маленькая. Свяжитесь со мной или проверьте этот репо, если интересно.
-- Copyright © 2019, 2020
-- mirabilos <t.glaser@tarent.de>
--
-- Provided that these terms and disclaimer and all copyright notices
-- are retained or reproduced in an accompanying document, permission
-- is granted to deal in this work without restriction, including un‐
-- limited rights to use, publicly perform, distribute, sell, modify,
-- merge, give away, or sublicence.
--
-- This work is provided “AS IS” and WITHOUT WARRANTY of any kind, to
-- the utmost extent permitted by applicable law, neither express nor
-- implied; without malicious intent or gross negligence. In no event
-- may a licensor, author or contributor be held liable for indirect,
-- direct, other damage, loss, or other issues arising in any way out
-- of dealing in the work, even if advised of the possibility of such
-- damage or existence of a defect, except proven that it results out
-- of said person’s immediate fault when using the work as intended.
-- -
-- Drop everything from the PostgreSQL database.
DO $$
DECLARE
q TEXT;
r RECORD;
BEGIN
-- triggers
FOR r IN (SELECT pns.nspname, pc.relname, pt.tgname
FROM pg_catalog.pg_trigger pt, pg_catalog.pg_class pc, pg_catalog.pg_namespace pns
WHERE pns.oid=pc.relnamespace AND pc.oid=pt.tgrelid
AND pns.nspname NOT IN ('information_schema', 'pg_catalog', 'pg_toast')
AND pt.tgisinternal=false
) LOOP
EXECUTE format('DROP TRIGGER %I ON %I.%I;',
r.tgname, r.nspname, r.relname);
END LOOP;
-- constraints #1: foreign key
FOR r IN (SELECT pns.nspname, pc.relname, pcon.conname
FROM pg_catalog.pg_constraint pcon, pg_catalog.pg_class pc, pg_catalog.pg_namespace pns
WHERE pns.oid=pc.relnamespace AND pc.oid=pcon.conrelid
AND pns.nspname NOT IN ('information_schema', 'pg_catalog', 'pg_toast')
AND pcon.contype='f'
) LOOP
EXECUTE format('ALTER TABLE ONLY %I.%I DROP CONSTRAINT %I;',
r.nspname, r.relname, r.conname);
END LOOP;
-- constraints #2: the rest
FOR r IN (SELECT pns.nspname, pc.relname, pcon.conname
FROM pg_catalog.pg_constraint pcon, pg_catalog.pg_class pc, pg_catalog.pg_namespace pns
WHERE pns.oid=pc.relnamespace AND pc.oid=pcon.conrelid
AND pns.nspname NOT IN ('information_schema', 'pg_catalog', 'pg_toast')
AND pcon.contype<>'f'
) LOOP
EXECUTE format('ALTER TABLE ONLY %I.%I DROP CONSTRAINT %I;',
r.nspname, r.relname, r.conname);
END LOOP;
-- indicēs
FOR r IN (SELECT pns.nspname, pc.relname
FROM pg_catalog.pg_class pc, pg_catalog.pg_namespace pns
WHERE pns.oid=pc.relnamespace
AND pns.nspname NOT IN ('information_schema', 'pg_catalog', 'pg_toast')
AND pc.relkind='i'
) LOOP
EXECUTE format('DROP INDEX %I.%I;',
r.nspname, r.relname);
END LOOP;
-- normal and materialised views
FOR r IN (SELECT pns.nspname, pc.relname
FROM pg_catalog.pg_class pc, pg_catalog.pg_namespace pns
WHERE pns.oid=pc.relnamespace
AND pns.nspname NOT IN ('information_schema', 'pg_catalog', 'pg_toast')
AND pc.relkind IN ('v', 'm')
) LOOP
EXECUTE format('DROP VIEW %I.%I;',
r.nspname, r.relname);
END LOOP;
-- tables
FOR r IN (SELECT pns.nspname, pc.relname
FROM pg_catalog.pg_class pc, pg_catalog.pg_namespace pns
WHERE pns.oid=pc.relnamespace
AND pns.nspname NOT IN ('information_schema', 'pg_catalog', 'pg_toast')
AND pc.relkind='r'
) LOOP
EXECUTE format('DROP TABLE %I.%I;',
r.nspname, r.relname);
END LOOP;
-- sequences
FOR r IN (SELECT pns.nspname, pc.relname
FROM pg_catalog.pg_class pc, pg_catalog.pg_namespace pns
WHERE pns.oid=pc.relnamespace
AND pns.nspname NOT IN ('information_schema', 'pg_catalog', 'pg_toast')
AND pc.relkind='S'
) LOOP
EXECUTE format('DROP SEQUENCE %I.%I;',
r.nspname, r.relname);
END LOOP;
-- extensions (only if necessary; keep them normally)
FOR r IN (SELECT pns.nspname, pe.extname
FROM pg_catalog.pg_extension pe, pg_catalog.pg_namespace pns
WHERE pns.oid=pe.extnamespace
AND pns.nspname NOT IN ('information_schema', 'pg_catalog', 'pg_toast')
) LOOP
EXECUTE format('DROP EXTENSION %I;', r.extname);
END LOOP;
-- aggregate functions first (because they depend on other functions)
FOR r IN (SELECT pns.nspname, pp.proname, pp.oid
FROM pg_catalog.pg_proc pp, pg_catalog.pg_namespace pns, pg_catalog.pg_aggregate pagg
WHERE pns.oid=pp.pronamespace
AND pns.nspname NOT IN ('information_schema', 'pg_catalog', 'pg_toast')
AND pagg.aggfnoid=pp.oid
) LOOP
EXECUTE format('DROP AGGREGATE %I.%I(%s);',
r.nspname, r.proname,
pg_get_function_identity_arguments(r.oid));
END LOOP;
-- routines (functions, aggregate functions, procedures, window functions)
IF EXISTS (SELECT * FROM pg_catalog.pg_attribute
WHERE attrelid='pg_catalog.pg_proc'::regclass
AND attname='prokind' -- PostgreSQL 11+
) THEN
q := 'CASE pp.prokind
WHEN ''p'' THEN ''PROCEDURE''
WHEN ''a'' THEN ''AGGREGATE''
ELSE ''FUNCTION''
END';
ELSIF EXISTS (SELECT * FROM pg_catalog.pg_attribute
WHERE attrelid='pg_catalog.pg_proc'::regclass
AND attname='proisagg' -- PostgreSQL ≤10
) THEN
q := 'CASE pp.proisagg
WHEN true THEN ''AGGREGATE''
ELSE ''FUNCTION''
END';
ELSE
q := '''FUNCTION''';
END IF;
FOR r IN EXECUTE 'SELECT pns.nspname, pp.proname, pp.oid, ' || q || ' AS pt
FROM pg_catalog.pg_proc pp, pg_catalog.pg_namespace pns
WHERE pns.oid=pp.pronamespace
AND pns.nspname NOT IN (''information_schema'', ''pg_catalog'', ''pg_toast'')
' LOOP
EXECUTE format('DROP %s %I.%I(%s);', r.pt,
r.nspname, r.proname,
pg_get_function_identity_arguments(r.oid));
END LOOP;
-- nōn-default schemata we own; assume to be run by a not-superuser
FOR r IN (SELECT pns.nspname
FROM pg_catalog.pg_namespace pns, pg_catalog.pg_roles pr
WHERE pr.oid=pns.nspowner
AND pns.nspname NOT IN ('information_schema', 'pg_catalog', 'pg_toast', 'public')
AND pr.rolname=current_user
) LOOP
EXECUTE format('DROP SCHEMA %I;', r.nspname);
END LOOP;
-- voilà
RAISE NOTICE 'Database cleared!';
END; $$;
Протестировано, за исключением более поздних дополнений ( extensions
предоставленных Clément Prévost ), на PostgreSQL 9.6 ( jessie-backports
). Удаление агрегатов проверено на 9.6 и 12.2, процедура удаления также проверена на 12.2. Исправления и дальнейшие улучшения приветствуются!
DROP FUNCTION
не выполняется для процедуры и наоборот. Я изменил раздел функций так: AND pp.prokind ='f' -- Function
илиAND pp.prokind ='p' -- Procedure
proisagg
) на ≤ 10.x и агрегатов и процедур ( prokind
) на ≥ 11 (проверено динамически) и протестировал оба - спасибо за подсказку.
Вам нужно отбросить таблицы и последовательности, вот что сработало для меня
psql -qAtX -c "select 'DROP TABLE IF EXISTS ' || quote_ident(table_schema) || '.' || quote_ident(table_name) || ' CASCADE;' FROM information_schema.tables where table_type = 'BASE TABLE' and not table_schema ~ '^(information_schema|pg_.*)$'" | psql -qAtX
psql -qAtX -c "select 'DROP SEQUENCE IF EXISTS ' || quote_ident(relname) || ' CASCADE;' from pg_statio_user_sequences;" | psql -qAtX
Перед выполнением команды вам может понадобиться SUDO / су на postgres
пользователя или (экспорт соединения деталей PGHOST
, PGPORT
, PGUSER
и PGPASSWORD
) , а затемexport PGDATABASE=yourdatabase
Задача Rake для Rails для уничтожения всех таблиц в текущей базе данных
namespace :db do
# rake db:drop_all_tables
task drop_all_tables: :environment do
query = <<-QUERY
SELECT
table_name
FROM
information_schema.tables
WHERE
table_type = 'BASE TABLE'
AND
table_schema NOT IN ('pg_catalog', 'information_schema');
QUERY
connection = ActiveRecord::Base.connection
results = connection.execute query
tables = results.map do |line|
table_name = line['table_name']
end.join ", "
connection.execute "DROP TABLE IF EXISTS #{ tables } CASCADE;"
end
end
rake db:create
я запускаю его. Вы можете сделать Steve наконечник и удалить код table_name =
и изменения ", "
для ","
и #{ tables }
Ф.О.#{tables}
Следующие шаги могут быть полезны (для пользователей Linux):
Сначала введите в postgres
командной строке следующую команду:
sudo -u postgres psql
Введите базу данных этой командой (мое имя базы данных:) maoss
:
\c maoss
Теперь введите команду для удаления всех таблиц:
DROP SCHEMA public CASCADE;
CREATE SCHEMA public;
GRANT ALL ON SCHEMA public TO postgres;
GRANT ALL ON SCHEMA public TO public;
Я улучшил метод bash от jamie, позаботившись о представлениях, потому что он учитывает только тип таблицы «базовая таблица», который используется по умолчанию.
следующий код Bash сначала удаляет представления, а затем все остальные
#!/usr/bin/env bash
PGDB="yourDB"
# By exporting user & pass your dont need to interactively type them on execution
export PGUSER="PGusername"
export PGPASSWORD="PGpassword"
VIEWS=`psql -d $PGDB -t --command "SELECT string_agg(table_name, ',') FROM information_schema.tables WHERE table_schema='public' AND table_type='VIEW'"`
BASETBLS=`psql -d $PGDB -t --command "SELECT string_agg(table_name, ',') FROM information_schema.tables WHERE table_schema='public' AND table_type='BASE TABLE'"`
echo Dropping views:${VIEWS}
psql $PGDB --command "DROP VIEW IF EXISTS ${VIEWS} CASCADE"
echo Dropping tables:${BASETBLS}
psql $PGDB --command "DROP TABLE IF EXISTS ${BASETBLS} CASCADE"
psql -d $PGDB -t --command "SELECT string_agg(sequence_name, ',') FROM information_schema.sequences WHERE sequence_schema='public' AND sequence_catalog='$PGDB'"
ну, так как мне нравится работать из командной строки ...
psql -U <user> -d <mydb> -c '\dt' | cut -d ' ' -f 4 | sed -e "s/^/drop table if exists /" | sed -e "s/$/;/"
-c '\dt'
вызовет команду списка таблиц.
List of relations
Schema | Name | Type | Owner
--------+-------------------+-------+----------
public | _d_psidxddlparm | table | djuser
public | _d_psindexdefn | table | djuser
cut -d ' ' -f 4
Теперь передайте его вывод, чтобы получить 4-е поле (при использовании пробела в качестве разделителя), которое является таблицей.
sed
затем используется для добавления префикса a drop table
и суффикса к ;
разделителю команд.
| egrep '_d_'
- Добавьте еще grep
немного, и вы можете быть более разборчивы в том, какие таблицы вы бросаете.
drop table if exists _d_psidxddlparm;
drop table if exists _d_psindexdefn;
Примечание: как написано, это сгенерирует фиктивные строки для \dt
вывода команд заголовков столбцов и итоговых строк в конце. Я избегаю этого путаницей, но вы можете использовать head
и tail
.
Самый простой способ - удалить общедоступную схему, как предлагали другие в предыдущих ответах. Тем не менее, это НЕ хороший способ. Вы никогда не знаете, что было сделано с публичной схемой, которая с тех пор была забыта и не была задокументирована. Вы также не знаете, будет ли это работать в будущем. В V9 это было бы нормально, но в V10 все ваши пользователи потеряли бы доступ к схеме, и им необходимо было бы снова предоставить доступ, иначе ваше приложение сломается. Я не проверял V11, но дело в том, что вы никогда не знаете, что сломается при переходе с компьютера на компьютер, с сайта на сайт или с версии на версию. Этого также нельзя сделать, если вы являетесь пользователем, который имеет доступ к базе данных, но не к схеме.
Если вам нужно сделать это программно, то другие ответы выше покрывают это, но одна вещь, которую ответы выше не учитывают, - это заставить Postgres выполнить эту работу за вас. Если вы используете pg_dump с опцией -c, как показано ниже:
sudo su postgres -c "pg_dump -U postgres WhateverDB -c -f "/home/Anyone/DBBackupWhateverDB-ServerUnscheduled.sql""
Это создаст скрипт восстановления БД с инструкциями sql, который удалит все таблицы.
Если единственная цель при задании вопроса состояла в том, чтобы удалить таблицы перед восстановлением, то ваше восстановление сделает всю работу за вас.
Однако, если вам это нужно для чего-то другого, вы можете просто скопировать операторы drop из сценария sql.