Изменить OWNER для всех таблиц одновременно в PostgreSQL - PullRequest
378 голосов
/ 28 августа 2009

Как изменить владельца всех таблиц в базе данных PostgreSQL?

Я пытался ALTER TABLE * OWNER TO new_owner, но он не поддерживает синтаксис звездочки.

Ответы [ 20 ]

4 голосов
/ 05 февраля 2019

Мне пришлось сменить владельца таблиц, представлений и последовательностей, и я обнаружил, что отличное решение, опубликованное @rjk, работает нормально, несмотря на одну деталь: Если имена объектов имеют смешанный регистр (например, «TableName»), произойдет сбой с ошибкой «not found».
Чтобы обойти это, оберните имена объектов знаком "" "следующим образом:

Таблица

SELECT 'ALTER TABLE \"'|| schemaname || '.' || tablename ||'\" OWNER TO my_new_owner;'
FROM pg_tables WHERE NOT schemaname IN ('pg_catalog', 'information_schema')
ORDER BY schemaname, tablename;

Последовательность

SELECT 'ALTER SEQUENCE \"'|| sequence_schema || '.' || sequence_name ||'\" OWNER TO my_new_owner;'
FROM information_schema.sequences WHERE NOT sequence_schema IN ('pg_catalog', 'information_schema')
ORDER BY sequence_schema, sequence_name;

1010 * Просмотры * SELECT 'ALTER VIEW \"'|| table_schema || '.' || table_name ||'\" OWNER TO my_new_owner;' FROM information_schema.views WHERE NOT table_schema IN ('pg_catalog', 'information_schema') ORDER BY table_schema, table_name;

3 голосов
/ 09 июня 2016

На основе ответа от elysch приведено решение для нескольких схем:

DO $$
DECLARE 
  r record;
  i int;
  v_schema text[] := '{public,schema1,schema2,schema3}';
  v_new_owner varchar := 'my_new_owner';
BEGIN
    FOR r IN 
        select 'ALTER TABLE "' || table_schema || '"."' || table_name || '" OWNER TO ' || v_new_owner || ';' as a from information_schema.tables where table_schema = ANY (v_schema)
        union all
        select 'ALTER TABLE "' || sequence_schema || '"."' || sequence_name || '" OWNER TO ' || v_new_owner || ';' as a from information_schema.sequences where sequence_schema = ANY (v_schema)
        union all
        select 'ALTER TABLE "' || table_schema || '"."' || table_name || '" OWNER TO ' || v_new_owner || ';' as a from information_schema.views where table_schema = ANY (v_schema)
        union all
        select 'ALTER FUNCTION "'||nsp.nspname||'"."'||p.proname||'"('||pg_get_function_identity_arguments(p.oid)||') OWNER TO ' || v_new_owner || ';' as a from pg_proc p join pg_namespace nsp ON p.pronamespace = nsp.oid where nsp.nspname = ANY (v_schema)
        union all
        select 'ALTER DATABASE "' || current_database() || '" OWNER TO ' || v_new_owner 
    LOOP
        EXECUTE r.a;
    END LOOP;
    FOR i IN array_lower(v_schema,1) .. array_upper(v_schema,1)
    LOOP
        EXECUTE 'ALTER SCHEMA "' || v_schema[i] || '" OWNER TO ' || v_new_owner ;
    END LOOP;
END
$$;
2 голосов
/ 15 июня 2012

Ответ @Alex Soto является правильным, и суть, загруженная @Yoav Aner, также работает при условии, что в именах таблиц / представлений нет специальных символов (которые разрешены в postgres).

Вам нужно заставить их работать, и я добавил для этого суть: https://gist.github.com/2911117

1 голос
/ 06 сентября 2017

То же, что и подход @ AlexSoto для функций:

IFS=$'\n'  
for fnc in `psql -qAt -c "SELECT  '\"' || p.proname||'\"' || '(' || pg_catalog.pg_get_function_identity_arguments(p.oid) || ')' FROM pg_catalog.pg_namespace n JOIN pg_catalog.pg_proc p ON p.pronamespace = n.oid WHERE n.nspname = 'public';" YOUR_DB` ; do  psql -c "alter function $fnc owner to NEW_OWNER" YOUR_DB; done
1 голос
/ 05 декабря 2010
pg_dump as insert statements 
pg_dump -d -O database filename
-d ( data as inserts ) -O ( capital O is no owner )

Затем перенаправьте файл резервной копии обратно в PostgreSQL, используя:

psql -d database -U username -h hostname < filename

Поскольку не указан владелец, все созданные таблица, схема и т. Д. Создаются под указанным пользователем для входа.

Я прочитал, что это может быть хорошим подходом и для миграции между версиями PostgreSQL.

1 голос
/ 09 февраля 2012

Начиная с PostgreSQL 9.0, у вас есть возможность GRANT [priv name] ON ALL [object type] IN SCHEMA, где [priv name] является типичным SELECT, INSERT, UPDATE, DELETE, etc, а [object type] может быть одним из:

  • TABLES
  • SEQUENCES
  • FUNCTIONS

Документы PostgreSQL по GRANT и REVOKE более подробно касаются этого. В некоторых ситуациях все еще требуется использовать приемы с системными каталогами (pg_catalog.pg_*), но это не так часто. Я часто делаю следующее:

  1. BEGIN транзакция для изменения привилегий
  2. Изменить владельца DATABASES на «роль администратора базы данных»
  3. Изменить владельца SCHEMAS на "роль администратора базы данных"
  4. REVOKE ALL привилегий на всех TABLES, SEQUENCES и FUNCTIONS от всех ролей
  5. GRANT SELECT, INSERT, UPDATE, DELETE на соответствующих / соответствующих таблицах для соответствующих ролей
  6. COMMIT транзакция DCL.
1 голос
/ 08 декабря 2014

У меня сработал следующий более простой сценарий оболочки.

#!/bin/bash
for i in  `psql -U $1  -qt -c  "select tablename from pg_tables where schemaname='$2'"`
do
psql -U $1 -c  "alter table $2.$i set schema $3"
done

Где ввод $ 1 - имя пользователя (база данных) $ 2 = существующая схема $ 3 = в новую схему.

1 голос
/ 15 августа 2014

Я создал удобный скрипт для этого; pg_change_db_owner.sh . Этот скрипт меняет владельца всех таблиц, представлений, последовательностей и функций в схеме базы данных, а также владельца самой схемы.

Обратите внимание, что если вы хотите просто изменить владельца всех объектов в конкретной базе данных, принадлежащий определенной роли базы данных, тогда вы можете просто использовать команду REASSIGN OWNED.

1 голос
/ 08 октября 2012

Принятое решение не заботится о владении функциями. Следующее решение заботится обо всем (при просмотре я заметил, что оно похоже на @magiconair выше)

echo "Database: ${DB_NAME}"
echo "Schema: ${SCHEMA}"
echo "User: ${NEW_OWNER}"

pg_dump -s -c -U postgres ${DB_NAME} | egrep "${SCHEMA}\..*OWNER TO"| sed -e "s/OWNER TO.*;$/OWNER TO ${NEW_OWNER};/" | psql -U postgres -d ${DB_NAME}
# do following as last step to allow recovery
psql -U postgres -d postgres -c "ALTER DATABASE ${DB_NAME} OWNER TO ${NEW_OWNER};"
0 голосов
/ 15 апреля 2016

Докер: Изменить владельца всех таблиц + последовательности

export user="your_new_owner"
export dbname="your_db_name"

cat <<EOF | docker run -i --rm --link postgres:postgres postgres sh -c "psql -h \$POSTGRES_PORT_5432_TCP_ADDR -p \$POSTGRES_PORT_5432_TCP_PORT -U postgres -d $dbname" | grep ALTER | docker run -i --rm --link postgres:postgres postgres sh -c "psql -h \$POSTGRES_PORT_5432_TCP_ADDR -p \$POSTGRES_PORT_5432_TCP_PORT -U postgres -d $dbname"
SELECT 'ALTER TABLE '||schemaname||'.'||tablename||' OWNER TO $user;' FROM pg_tables WHERE schemaname = 'public';
SELECT 'ALTER SEQUENCE '||relname||' OWNER TO $user;' FROM pg_class WHERE relkind = 'S';
EOF
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...