代码改变世界

Oracle 18c&19c physical dg切换总结

2024-07-15 23:23  潇湘隐者  阅读(180)  评论(0编辑  收藏  举报

这篇文章总结Oracle 18c/19c Physical Standby DG的主备切换的操作流程,主要参考官方文档18c & 19c Physical Standby Switchover Best Practices using SQL*Plus (Doc ID 2485237.1)[1]. 由于参考官方的最佳实践,所以有些步骤/过程略显繁琐。其实正常情况下,这里面的很多步骤都可以略过。但是不妨我们从更严谨的态度和细节方面了解更多的技术细节。

前提条件(Prerequisites)检查

DG的设置/配置验证

  • Primary & Standby 应使用相同版本的RDBMS
  • 检查/验证主备库的告警日志,并确保没有错误或告警
$ grep "ORA-" alert_<ORACLE_SID>.log 
$ tail -600 alert_<ORACLE_SID>.log  | grep "ORA-"
  • 在主库和备用数据库运行下面SQL检查验证没有坏块
select * from v$database_block_corruption; 
select * from v$nonlogged_block;

注意:没有记录表示正常,如果有相关记录返回,则表示数据库存在坏块。

  • 确保主库和备库的配置正常/正确,并且重做日志传输(redo transport)和重做日志应用(redo apply)中没有错误
  • 验证物理备用数据库是否正常运行,检查DG的主备库情况

获取主备库的信息以及保护模式(主备库执行)

set linesize 720
col name for a10
col open_mode for a20
col database_role for a16
col switchover_status for a12 heading "SWITCHOVER |STATUS"
col force_logging for a8
col dataguard_broker for a8 heading "DATAGUARD|BROKER"
col guard_status for a8
select name
      ,open_mode
      ,database_role
      ,protection_mode
      ,protection_level
      ,switchover_status 
      ,force_logging
      ,dataguard_broker
      ,guard_status
from v$database;

检查主库下SWITCHOVER_STATUS字段,如果值为"SESSION ACTIVE"或者"TO STANDBY", 则主数据库角色可以切换为备库角色。关于SWITCHOVER_STATUS字段的各个取值如下所示:

SWITCHOVER_STATUS取值 意义
NOT ALLOWED 在主数据库上,此状态表示没有有效且已启用的备用数据库。如果配有DG关系,则表示当前数据库不允许进行Switchover操作。这可能是因为多种原因,如数据库状态不正确、主备库之间存在延迟或不一致、存在活跃的会话等。具体原因需要结合数据库状态和日志信息等来判断。在备用数据库上,此状态表示尚未从主数据库收到切换请求
SESSIONS ACTIVE 表示当前数据库有活跃的会话或事务,这些会话或事务需要被断开或提交后,才能进行Switchover操作。 数据库具有活动会话。在物理备用数据库上,必须指定 WITH SESSION SHUTDOWN 这样的SQL子句才能在此状态下执行角色转换。在逻辑备用数据库上,可以在此状态下执行角色转换,但在提交所有当前事务之前,角色转换不会完成。
SWITCHOVER PENDING 在物理备用数据库上,此状态表示已从主数据库收到切换请求并正在处理。在此瞬态状态下,物理备用数据库无法切换到主要角色。
SWITCHOVER LATENT 在物理备用数据库上,此状态表示切换请求处于挂起状态,但原始主数据库已切换回主要角色。
TO PRIMARY 表示当前数据库可以切换为主数据库(Primary Database)。这通常是在执行Switchover操作后,原备用数据库(Standby Database)切换为主数据库(Primary Database)时显示的状态。
TO STANDBY 表示当前数据库可以切换为备用数据库(Standby Database)。这通常意味着数据库处于可以安全地进行Switchover操作的状态,且没有活跃的会话或事务阻止切换。
TO LOGICAL STANDBY 数据库已从逻辑备用数据库接收到数据字典,并准备切换到逻辑备用角色。
RECOVERY NEEDED 在物理备用数据库上,此状态指示必须先应用额外的重做,然后数据库才能切换到主要角色
PREPARING SWITCHOVER 在主数据库上,此状态表示正在从逻辑备用数据库接收数据字典,以准备切换到逻辑备用角色。在逻辑备用数据库上,此状态表示数据字典已发送到主数据库和其他备用数据库。
PREPARING DICTIONARY 在逻辑备用数据库上,此状态表示正在将数据字典发送到主数据库和其他备用数据库,以准备切换到主要角色。
FAILED DESTINATION 在主数据库上,此状态表示一个或多个备用目标处于错误状态。这个值可能不是SWITCHOVER_STATUS的直接状态值,但在执行Switchover过程中,如果遇到配置错误或网络问题导致目标数据库无法接收归档日志,可能会间接导致Switchover失败,并显示为类似“Failed Destination”的错误信息。这种情况需要DBA检查相关配置和网络连接。
RESOLVABLE GAP 在主数据库上,此状态表示一个或多个备用数据库具有redo gap,可以通过从主数据库或另一个备用数据库获取丢失的重做来自动解决该差距。 在某些情况下,如归档日志传输过程中出现短暂的中断导致日志间隙(Gap),但这些间隙可以通过后续操作解决时,可能会显示为“Resolvable Gap”状态。这通常不是SWITCHOVER_STATUS的直接输出,而是描述问题性质的一种方式。
UNRESOLVABLE GAP 在主数据库上,此状态表示一个或多个备用数据库具有redo缺失(redo gap),无法通过从主数据库或另一个备用数据库获取丢失的redo日志来自动解决该缺口
LOG SWITCH GAP 在主数据库上,此状态表示由于最近的日志切换,一个或多个备用数据库缺失了redo log。

检查主库重做日志传输和应用状态

主库(Primary)

COL DEST_NAME FOR A20
COL DESTINATION FOR A25
COL ERROR FOR A15
COL ALTERNATE FOR A20
SET LINES 1000
SELECT DEST_NAME,DESTINATION,ERROR
      ,ALTERNATE,TYPE,STATUS
      ,VALID_TYPE,VALID_ROLE 
FROM V$ARCHIVE_DEST 
WHERE STATUS <>'INACTIVE';

重点关注ERROR字段的输出信息,如果重做日志传输和应用有问题,就会有相关错误信息提示。

检查主库最后生成的归档日志文件

主库(Primary)

SELECT   THREAD#, MAX(SEQUENCE#) "Last Primary Seq Generated"  
FROM     GV$ARCHIVED_LOG VAL, GV$DATABASE VDB
WHERE    VAL.RESETLOGS_CHANGE# = VDB.RESETLOGS_CHANGE#
GROUP BY THREAD# ORDER BY 1;

备库(Standby)检查验证最后收到主库的归档日志

--Using the below query, check the last received archivelog from primary database 
--(RAC database result will be displayed for each thread).
SELECT   THREAD#, MAX(SEQUENCE#) "Last Standby Seq Received"  
FROM     GV$ARCHIVED_LOG VAL, GV$DATABASE VDB
WHERE    VAL.RESETLOGS_CHANGE# = VDB.RESETLOGS_CHANGE#
GROUP BY THREAD# ORDER BY 1;

备库(standby)检查最后应用的归档日志序列

--Check last archive log sequence applied at standby.
SELECT    THREAD#, MAX(SEQUENCE#) "Last Standby Seq Applied"
FROM     GV$ARCHIVED_LOG VAL, GV$DATABASE VDB
WHERE    VAL.RESETLOGS_CHANGE# = VDB.RESETLOGS_CHANGE#
AND      VAL.APPLIED IN ('YES','IN-MEMORY')
GROUP BY THREAD# ORDER BY 1; 

验证初始化参数

--主库(primary)&备库(standby)检查

--检查验证参数

show parameter log_archive_config;
show parameter fal_server;
show parameter fal_client;
show parameter db_unique_name;
show parameter log_archive_dest_;
show parameter compatible;
show parameter db_file_name_convert;
show parameter log_file_name_convert;
show parameter pdb_file_name_convert;



set linesize 720 pagesize 60
col name for a30
col value for a120
SELECT 
    NAME,
    VALUE 
FROM 
    V$PARAMETER 
WHERE 
    NAME IN (
        'db_unique_name',
        'log_archive_config',
        'log_archive_dest_1',
        'log_archive_dest_2',
        'log_archive_dest_state_1',
        'log_archive_dest_state_2',
        'remote_login_passwordfile',
        'log_archive_format',
        'standby_file_management',
        'compatible',
        'fal_server',
        'db_file_name_convert',
        'log_file_name_convert'
        )
order by name;       

注意事项:要确保兼容参数compatible和noncdb_compatible在主备上一致。

切换前工作(Pre-Switchover)

Ensure Prerequisites are completely verified. Along with Prerequisites, Follow the below guidance to have successful switchover. These steps should be executed before real planned outage starts and ensure no issues.

检查MRP进程状态

备库(standby)

select * from gv$dataguard_process;

停止/启动MRP进程,特殊情况下执行,此处不用执行。

ALTER DATABASE RECOVER MANAGED STANDBY DATABASE CANCEL;
ALTER DATABASE RECOVER MANAGED STANDBY DATABASE  DISCONNECT;

检查数据文件和Tempfiles

这个步骤不是必须的,如果你确认DG最近没有相关数据文件和临时表空间的相关文件调整,可以直接跳过这一步。

--Check the datafiles & Tempfiles status

SELECT NAME FROM V$DATAFILE WHERE STATUS='OFFLINE';
--ALTER DATABASE DATAFILE 'datafile-name' ONLINE;

检查temp表空间的文件

set linesize 680
set pagesize 40
col filename for a80
col tablespace for a16
select tf.name filename
      , bytes
      , ts.name tablespace    
from v$tempfile tf, v$tablespace ts where tf.ts#=ts.ts#;

检查redo log和standby redo log的信息

执行下面SQL检查redo log和standby redo log的信息(主库和备库)

set lines 680
col member for a50
select a.thread#,a.group#,a.bytes,a.blocksize,b.type,a.status,b.member 
from v$log a,v$logfile b 
where a.group#=b.group#
order by a.group#;
set lines 680
col member for a50
select s.thread#,s.group#,s.status,s.bytes,l.type,l.member 
from v$logfile l,v$standby_log s where s.group#=l.group#
order by s.thread#,s.group#;

--检查REDO LOG或归档日志应用延迟。(主库执行)

SELECT STATUS, GAP_STATUS FROM V$ARCHIVE_DEST_STATUS WHERE DEST_ID = 2;

DEST_ID的值可以根据实际情况调整。STATUS字段应该为VALID,GAP_STATUS字段应该为"NO GAP"

检查监控告警日志

主库(Primary)和备库(Standby)

$ tail -600 alert_<ORACLE_SID>.ora | grep ORA 
$ tail -60f alert_<ORACLE_SID>.ora

关于检查的具体内容,官方文档描述为

1) From primary database alert logfile:
    * Check for issue reported for redo transport
    * Ensure there is no password file issue
    * Ensure there are no TNS or connection issue

2) From Standby database alert logfile:
    * There are no error related to Managed recovery
    * Recovery is moving forward by applying the archive log / redo log
    * There are no TNS or connection issue
    * There are no I/O issue or corruption issue
    select * from v$database_block_corruption;  -- it should return no rows
    select * from v$nonlogged_block; -- it should return no rows

DG切换(Switchover)

验证切换(Verify the switchover)

ADG切换验证:(主库执行):

ALTER DATABASE SWITCHOVER TO gspro VERIFY;

上面命令成功执行的话,则会返回"Database altered.",才可以执行下面命令,否则需要检查分析原因。

上面命令执行成功,主库告警日志中会出现下面信息:

2024-07-10T09:11:45.281610+08:00
ALTER DATABASE SWITCHOVER TO gspro VERIFY
2024-07-10T09:11:45.530174+08:00
SWITCHOVER VERIFY: Send VERIFY request to switchover target GSPRO
SWITCHOVER VERIFY COMPLETE: READY FOR SWITCHOVER
Completed: ALTER DATABASE SWITCHOVER TO gspro VERIFY

备库的告警日志中也会出现下面日志

2024-07-10T09:11:45.598106+08:00
SWITCHOVER VERIFY BEGIN
SWITCHOVER VERIFY COMPLETE

如果执行报错,也会在告警日志中看到详细的错误信息。

切换(Switchover)步骤

--Step 1: (主库执行)

ALTER DATABASE SWITCHOVER TO gspro;

--Step 2: 旧备库上/新的主库(new primary)执行

ALTER DATABASE OPEN;

--Step 3: 新的备库/旧主库上执行(current/new standby )

--If standby is Oracle Active data guard physical standby:
STARTUP;
--If standby is NOT Oracle Active data guard physical standby:
STARTUP MOUNT;

--注意:退出之前的sqlplus命令窗口,重新登陆执行命令,否则可能会遇到一些错误。如下例子所示:

SQL> STARTUP;
ORA-32004: obsolete or deprecated parameter(s) specified for RDBMS instance
ORA-49100: Failed to process event statement [10235 trace name context forever,level 2: 7445 trace name heapdump level 2: 10027 trace name context forever,level 1: 10949 trace name context forever,level 1] 
ORA-00972: identifier is too long

将PDB启动到OPEN状态

SHOW PDBS;
ALTER PLUGGABLE DATABASE ALL OPEN;

--Step 4:新的备库开始redo apply

ALTER DATABASE RECOVER MANAGED STANDBY DATABASE DISCONNECT FROM SESSION;

--Step 5: 检查确认Switchover是否正常

--主库

alter system archive log current;
set linesize 720;
select dest_id,error,status from v$archive_dest where dest_id=<your remote log_archive_dest_<n>>;  --一般为2
select max(sequence#),thread# from v$log_history group by thread#;
select max(sequence#)  from v$archived_log where applied='YES' and dest_id=2;

--备库(standby)

select max(sequence#),thread# from v$archived_log group by thread#;
select name,role,instance,thread#,sequence#,action from gv$dataguard_process;

--备库执行SQL,检查同步状态

set linesize 720;
col name for a24;
col source_db_unique_name for a16;
col value for a16;
col unit for a20;
col time_computed for a19;
col datum_time for a19;
select source_db_unique_name
     , name
     , value
     , unit
     , time_computed 
     , datum_time
from v$dataguard_stats;

SQL> set linesize 720;
SQL> col name for a24;
SQL> col source_db_unique_name for a16;
SQL> col value for a16;
SQL> col unit for a20;
SQL> col time_computed for a19;
SQL> col datum_time for a19;
SQL> select source_db_unique_name
  2       , name
  3       , value
  4       , unit
  5       , time_computed 
  6       , datum_time
  7  from v$dataguard_stats;

SOURCE_DB_UNIQUE NAME                     VALUE            UNIT                 TIME_COMPUTED       DATUM_TIME
---------------- ------------------------ ---------------- -------------------- ------------------- -------------------
gspro            transport lag            +00 00:00:00     day(2) to second(0)  07/10/2024 09:44:36 07/10/2024 09:44:35
                                                           interval

gspro            apply lag                +00 00:00:00     day(2) to second(0)  07/10/2024 09:44:36 07/10/2024 09:44:35
                                                           interval

gspro            apply finish time        +00 00:00:00.000 day(2) to second(3)  07/10/2024 09:44:36
                                                           interval

                 estimated startup time   16               second               07/10/2024 09:44:36

SQL>
参考资料
[1]

1: https://support.oracle.com/epmos/faces/DocumentDisplay?_afrLoop=246469404737555&id=2485237.1&_afrWindowMode=0&_adf.ctrl-state=18aegmiut3_4