Oracle - 关于恢复数据库的一点理解

    Oracle的备份与恢复一直是很吸引我的一个地方。一直搞不明白到底是怎么个标准来恢复,怎么来备份。今天就来稍微就这其中的一点名词和过程来写写:

    都知道,在创建Oracle的时候,初始默认都会建立三个redo log的文件组。可能大家对这三个log文件组的作用可能不太理解,我自己的理解是这三个log文件组就类似于一个循环,一个组写满了,Oracle就切换到另外的一个组里面去,然后就这么来来去去。大家可能又会问到,那么如果这三个组都满了,怎么办?这个我也不太清楚,据我跟一个DBA的探讨,应该Oracle就不会忘Redo log文件里记录了。但是Oracle也可以通过设置备份策略来避免这种情况的发生。

    通常Oracle在提交一个事务,或者是做一个操作的时候,首先将数据读到内存中来,然后做修改。修改完成后,一般的步骤会是先想Redo log文件里写入修改的记录,然后等待一段时间,由Oracle统一将一批修改写入磁盘。

    那么怎么来查看当前是哪个一个redo log文件组被使用呢:

  1. SQL> select * from v$logfile; 
  2.  
  3.     GROUP# STATUS  TYPE    MEMBER               IS_ 
  4. ---------- ------- ------- -------------------- --- 
  5.          3 STALE   ONLINE  D:\ORACLE\DATA\GJSID NO 
  6.                            \REDO03.LOG 
  7.  
  8.          2         ONLINE  D:\ORACLE\DATA\GJSID NO 
  9.                            \REDO02.LOG 
  10.  
  11.          1         ONLINE  D:\ORACLE\DATA\GJSID NO 
  12.                            \REDO01.LOG 

 

  1. SQL> select * from v$log; 
  2.  
  3.     GROUP#    THREAD#  SEQUENCE#      BYTES    MEMBERS ARC STATUS 
  4. ---------- ---------- ---------- ---------- ---------- --- ---------------- 
  5. FIRST_CHANGE# FIRST_TIME 
  6. ------------- -------------- 
  7.          1          1         11   52428800          1 NO  CURRENT 
  8.        814175 06-3月 -11 
  9.  
  10.          2          1          9   52428800          1 YES INACTIVE 
  11.        791711 05-3月 -11 
  12.  
  13.          3          1         10   52428800          1 NO  INACTIVE 
  14.        791923 05-3月 -11 

可以看到现在系统中总共是有三组redo log文件组,而且当前被激活是是第一个redo log文件组。

    接下来可能会涉及到一个概念,SCN - system change number。这个数字是Oracle在内部用来记录变化的唯一的一个标示,事务的提交,各种修改的发生,都会修改到这个SCN。也就是可以这样讲到SCN是Oracle的内部逻辑时钟。那么怎么样子才可以查看到当前的SCN呢:

  1. SQL> select dbms_flashback.get_system_change_number from dual; 
  2.  
  3. GET_SYSTEM_CHANGE_NUMBER 
  4. ------------------------ 
  5.                   815255 

通过这样的一条语句就可以看到current SCN是多少,你也可以反复的查看,你就会发现SCN经常在变。

通过上述的语句检查出来的SCN是系统最新的SCN,上面也讲到了,Oracle会统一地将一批数据写入磁盘,可能就会有这样的情况,数据修改在Redo log文件中,还没有及时地反映到磁盘中去,数据库就发生了Crush,这样就意味数据的完整性没有保证,那么Oracle是怎么做到恢复的呢。

这个时候,一个检查点的概念就出来了,checkpoint scn。检查点就相当于Oracle每隔多长时间做了一次写入磁盘的批处理动作一样。

看到了吧,如果在T1时刻Oracle做了一次check,然后在T2时刻数据库崩溃,那么Oracle就只需要做T1 - T2时刻的redo log的恢复就Ok。

那么我是如何知道Oracle是在哪个时刻做了一个check呢:

  1. SQL> select file#,checkpoint_change#,to_char(checkpoint_time,'yyyy-mm-dd hh24:mm:ss'from v$datafile; 
  2.  
  3.      FILE# CHECKPOINT_CHANGE# TO_CHAR(CHECKPOINT_ 
  4. ---------- ------------------ ------------------- 
  5.          1             814915 2011-03-06 16:03:55 
  6.          2             814915 2011-03-06 16:03:55 
  7.          3             814915 2011-03-06 16:03:55 
  8.          4             814915 2011-03-06 16:03:55 

看到了吧,这个时候,在SCN是814915的时候,Oracle做了一次check。

  1. SQL> select dbms_flashback.get_system_change_number from dual; 
  2.  
  3. GET_SYSTEM_CHANGE_NUMBER 
  4. ------------------------ 
  5.                   816436 

而当前最新的Oracle SCN是816436,所以说如果当前Oracle崩溃了,系统需要从814915恢复到816436.

其实我还是有一点不太明白,Oracle难道是只有发生check的时候,才将数据写向磁盘么,还是一直都在写。如果是前者的话,那么这么长间隔的数据修改,只能从redo log里查询么?如果是后者的话,如果数据已经写到了磁盘,Oracle在恢复的时候,会不会造成数据的重复写的情况呢?

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章