AskOverflow.Dev

AskOverflow.Dev Logo AskOverflow.Dev Logo

AskOverflow.Dev Navigation

  • 主页
  • 系统&网络
  • Ubuntu
  • Unix
  • DBA
  • Computer
  • Coding
  • LangChain

Mobile menu

Close
  • 主页
  • 系统&网络
    • 最新
    • 热门
    • 标签
  • Ubuntu
    • 最新
    • 热门
    • 标签
  • Unix
    • 最新
    • 标签
  • DBA
    • 最新
    • 标签
  • Computer
    • 最新
    • 标签
  • Coding
    • 最新
    • 标签
主页 / dba / 问题 / 186045
Accepted
guettli
guettli
Asked: 2017-09-16 02:54:47 +0800 CST2017-09-16 02:54:47 +0800 CST 2017-09-16 02:54:47 +0800 CST

如何防止更改我的 PostgreSQL 数据库?

  • 772

我的步骤:

  1. pg_dumpall在服务器上运行决赛prod-server-old
  2. 永远关闭prod-server-old。
  3. 将输出复制到不同的服务器 ( prod-server-new)
  4. 在那里恢复数据库。
  5. 所有流量都到prod-server-new现在

如何避免在pg_dumpall(step1 和 step2 之间)对数据库进行修改,使这段时间的修改不会丢失?

在我的情况下,有一小段停机时间是 100% 可以的。

“集群”中有几个数据库(顺便说一句,我不喜欢“集群”这个词。我想大多数人认为“集群”是一组多台计算机,但在这种情况下它意味着一个 Postgres 服务器,它拥有几个数据库)。

我的问题被标记为可能与“使 Postgres 数据库暂时只读(用于执行卷快照)”重复。我不认为它是重复的,因为在我的情况下是不同的,因为我不要求临时只读状态。

postgresql migration
  • 4 4 个回答
  • 3944 Views

4 个回答

  • Voted
  1. anto418
    2017-09-16T04:31:05+08:002017-09-16T04:31:05+08:00

    有两种方法可以做到这一点:

    • 如果您不介意停机时间(简单方法):

    撤销对该组的connect特权public。这将阻止除超级用户之外的所有人进行连接。然后重新启动服务器或终止所有连接,然后使用超级用户帐户继续备份。

    REVOKE CONNECT TO DATABASE (database) FROM public
    
    • 如果您确实介意停机时间:

    将您的数据库置于只读模式:

    ALTER DATABASE (database) SET default_transaction_read_only = true;
    

    继续pg_dumpall。无需重新启动,也无需停机。

    当然,您必须在要“锁定”的每个数据库上重复此操作。如果您有大量数据库,您可以将整个集群设为只读:default_transaction_read_only = on;在您的 postgresql.conf 中设置,然后重新加载 postgres 服务。

    请注意,我没有测试任何这些命令,风险自负。

    • 4
  2. Best Answer
    guettli
    2017-09-16T03:37:00+08:002017-09-16T03:37:00+08:00

    一种解决方法:

    更改 PostgreSQL 的端口prod-server-old。这样,客户端不太可能在pg_dumpall --port=OTHER_PORT.

    • 3
  3. SEarle1986
    2017-09-16T03:15:08+08:002017-09-16T03:15:08+08:00

    我是 SQL Server 管理员(不是 Postgres),所以我不能 100% 确定,但如果停机时间不是问题,您可以:

    • 杀死所有连接
    • 防止远程登录
    • 登录数据库服务器并以超级用户身份登录数据库
    • 做 pg_dumpall
    • 重新启用远程登录

    ?

    • 2
  4. Abelisto
    2017-09-17T04:43:32+08:002017-09-17T04:43:32+08:00

    使用触发器:

    create function __fn_db_readonly() returns event_trigger language plpgsql as $$
    begin
      raise exception '%', 'Database is in read-only mode';
    end $$;
    
    create function _fn_db_readonly() returns trigger language plpgsql as $$
    begin
      raise exception '%', TG_ARGV[0];
    end $$;
    
    create function set_db_readonly(amessage text) returns void language plpgsql as $$
    declare
      t record;
      tbl_name text;
      stm text;
    begin
      if coalesce(amessage, '') = '' then
        -- Database
        drop event trigger __tg_ro_database1;
        drop event trigger __tg_ro_database2;
        drop event trigger __tg_ro_database3;
        -- Data
        for t in (select * from pg_tables where not schemaname in ('pg_catalog', 'information_schema')) loop
          tbl_name := format('%I.%I', t.schemaname, t.tablename);
          stm := 'drop trigger if exists _tg_ro on ' || tbl_name;
          execute stm;
        end loop;
      else
        -- Data
        for t in (select * from pg_tables where not schemaname in ('pg_catalog', 'information_schema')) loop
          tbl_name := format('%I.%I', t.schemaname, t.tablename);
          stm := format('create trigger _tg_ro before insert or update or delete on %s execute procedure _fn_db_readonly(%L)', tbl_name, amessage);
          execute stm;
        end loop;
        -- Database
        create event trigger __tg_ro_database1 on ddl_command_start execute procedure __fn_db_readonly();
        create event trigger __tg_ro_database2 on table_rewrite execute procedure __fn_db_readonly();
        create event trigger __tg_ro_database3 on sql_drop execute procedure __fn_db_readonly();
      end if;
      return;
    end $$;
    

    然后使数据库只读:

    select set_db_readonly('Database is in read-only mode due to maintance.');
    

    并使其再次可编辑:

    select set_db_readonly('');
    
    • 0

相关问题

  • 我可以在使用数据库后激活 PITR 吗?

  • 运行时间偏移延迟复制的最佳实践

  • 存储过程可以防止 SQL 注入吗?

  • PostgreSQL 中 UniProt 的生物序列

  • PostgreSQL 9.0 Replication 和 Slony-I 有什么区别?

Sidebar

Stats

  • 问题 205573
  • 回答 270741
  • 最佳答案 135370
  • 用户 68524
  • 热门
  • 回答
  • Marko Smith

    连接到 PostgreSQL 服务器:致命:主机没有 pg_hba.conf 条目

    • 12 个回答
  • Marko Smith

    如何让sqlplus的输出出现在一行中?

    • 3 个回答
  • Marko Smith

    选择具有最大日期或最晚日期的日期

    • 3 个回答
  • Marko Smith

    如何列出 PostgreSQL 中的所有模式?

    • 4 个回答
  • Marko Smith

    列出指定表的所有列

    • 5 个回答
  • Marko Smith

    如何在不修改我自己的 tnsnames.ora 的情况下使用 sqlplus 连接到位于另一台主机上的 Oracle 数据库

    • 4 个回答
  • Marko Smith

    你如何mysqldump特定的表?

    • 4 个回答
  • Marko Smith

    使用 psql 列出数据库权限

    • 10 个回答
  • Marko Smith

    如何从 PostgreSQL 中的选择查询中将值插入表中?

    • 4 个回答
  • Marko Smith

    如何使用 psql 列出所有数据库和表?

    • 7 个回答
  • Martin Hope
    Jin 连接到 PostgreSQL 服务器:致命:主机没有 pg_hba.conf 条目 2014-12-02 02:54:58 +0800 CST
  • Martin Hope
    Stéphane 如何列出 PostgreSQL 中的所有模式? 2013-04-16 11:19:16 +0800 CST
  • Martin Hope
    Mike Walsh 为什么事务日志不断增长或空间不足? 2012-12-05 18:11:22 +0800 CST
  • Martin Hope
    Stephane Rolland 列出指定表的所有列 2012-08-14 04:44:44 +0800 CST
  • Martin Hope
    haxney MySQL 能否合理地对数十亿行执行查询? 2012-07-03 11:36:13 +0800 CST
  • Martin Hope
    qazwsx 如何监控大型 .sql 文件的导入进度? 2012-05-03 08:54:41 +0800 CST
  • Martin Hope
    markdorison 你如何mysqldump特定的表? 2011-12-17 12:39:37 +0800 CST
  • Martin Hope
    Jonas 如何使用 psql 对 SQL 查询进行计时? 2011-06-04 02:22:54 +0800 CST
  • Martin Hope
    Jonas 如何从 PostgreSQL 中的选择查询中将值插入表中? 2011-05-28 00:33:05 +0800 CST
  • Martin Hope
    Jonas 如何使用 psql 列出所有数据库和表? 2011-02-18 00:45:49 +0800 CST

热门标签

sql-server mysql postgresql sql-server-2014 sql-server-2016 oracle sql-server-2008 database-design query-performance sql-server-2017

Explore

  • 主页
  • 问题
    • 最新
    • 热门
  • 标签
  • 帮助

Footer

AskOverflow.Dev

关于我们

  • 关于我们
  • 联系我们

Legal Stuff

  • Privacy Policy

Language

  • Pt
  • Server
  • Unix

© 2023 AskOverflow.DEV All Rights Reserve