데이터베이스 연구실.log

Flashback Database

Flashback Database와 보장 복원 지점의 조건, 읽기 전용 검증 및 RESETLOGS로 DB 열기

UNIFIED_AUDIT_TRAILTO TIMESTAMPFLASHBACK PLUGGABLE DATABASEPDB_RESTORE_POINTORA-65025FLASHBACK DATABASEFLASHBACK ONGUARANTEED RESTORE POINTV$FLASHBACK_DATABASE_LOGOPEN READ ONLYRESETLOGSORA-38729

#핵심 요약

Flashback Database는 플래시백 로그로 데이터 블록의 과거 버전을 가져와 데이터베이스 전체를 과거 시점으로 되감음
백업을 복원하지 않음

미리 플래시백 로그를 켜 두었거나(ALTER DATABASE FLASHBACK ON), 보장 복원 지점을 만들어 두어야 함

미디어 장애 복구용이 아님
데이터 파일이 손상되거나 삭제된 경우, 컨트롤 파일을 복원하거나 다시 만든 시점 이전으로 가는 경우에는 쓸 수 없음

되감은 뒤 OPEN READ ONLY로 내용을 확인하고, 만족하면 OPEN RESETLOGS로 엶
끝나면 새 전체 백업을 받음

#개념과 동작 원리

쓸 수 없는 경우:

  1. 현재 데이터 파일이 손상되거나 없어진 경우
    Flashback Database는 Oracle이 데이터 파일에 한 변경만 되돌림
  2. 데이터 파일 삭제, 데이터 파일 축소, 데이터베이스 이름 변경을 되돌리려는 경우
  3. 컨트롤 파일을 복원하거나 다시 만든 시점 이전으로 가려는 경우
    그때 쌓인 플래시백 로그 정보가 모두 버려짐
  4. 호환성(COMPATIBLE) 변경을 되돌리려는 경우

대상 SCN이 플래시백 창 밖이면 ORA-38729로 실패하고 데이터베이스는 바뀌지 않음
FRA 공간 부족으로 플래시백 로그가 지워졌으면 도달하지 못할 수 있음

되감기가 끝나면 데이터베이스는 MOUNT 상태로 남음

RESETLOGS로 열면 대상 SCN 이후의 변경은 버려짐
대신 손상된 객체만 Data Pump로 내보낸 뒤 RECOVER DATABASE로 현재 시점까지 다시 감을 수도 있음

너무 멀리 되감았으면 RECOVER DATABASE UNTIL SCN으로 앞으로 감고, 아예 취소하려면 UNTIL 없는 RECOVER DATABASE로 완전 복구함

CDB 전체나 개별 PDB에 할 수 있지만 루트만 따로 할 수는 없음

#필수 명령어 또는 SQL

#사전 설정과 복원 지점

SQL*Plus (SYSDBA)조회만 함
SELECT flashback_on FROM v$database;
SQL*Plus (SYSDBA)인스턴스 또는 서비스 중단이 필요함
SHUTDOWN IMMEDIATE
STARTUP MOUNT
ALTER DATABASE FLASHBACK ON;
SQL*Plus (SYSDBA)객체 또는 설정을 변경함
CREATE RESTORE POINT before_drop GUARANTEE FLASHBACK DATABASE;

결과 해석:

실습에서는 중요한 작업 전에 보장 복원 지점을 만들어 두라고 적었음
실습에서는 이 명령을 RMAN 단계로 표시했음

SQL*Plus (SYSDBA)조회만 함
SELECT oldest_flashback_scn, oldest_flashback_time FROM v$flashback_database_log;
SELECT current_scn FROM v$database;
SELECT name, scn, time, database_incarnation#, guarantee_flashback_database
  FROM v$restore_point WHERE guarantee_flashback_database = 'YES';

결과 해석:

위 조회는 되감을 수 있는 가장 이른 시점과 보장 복원 지점을 확인하는 공식 문서 예시임

#실수 시각 찾기

SQL*Plus (SYSDBA)조회만 함
SELECT first_load_time, last_active_time, parsing_schema_name, sql_text
  FROM v$sql
 WHERE UPPER(sql_text) LIKE 'DROP USER%'
 ORDER BY last_active_time DESC;

결과 해석:

실습에서는 패턴을 'DROP USER$'로 적어 와일드카드가 없었음
공유 풀에서 이미 밀려났으면 찾을 수 없음

SQL*Plus (SYSDBA)현재 세션 설정만 변경함
SET SERVEROUTPUT ON
DECLARE
  v_cnt NUMBER;
BEGIN
  FOR i IN 1..180 LOOP
    EXECUTE IMMEDIATE
      'SELECT COUNT(*) FROM dba_users AS OF TIMESTAMP SYSDATE - ' || i ||
      '/1440 WHERE username = ''<USERNAME>'''
      INTO v_cnt;
    IF v_cnt > 0 THEN
      DBMS_OUTPUT.PUT_LINE(i || ' 분 전에는 존재 → 그 직후에 DROP');
      EXIT;
    END IF;
  END LOOP;
END;
/

결과 해석:

실습 기록: "8 분 전에는 존재"가 나왔음
1분 단위로 거슬러 올라가며 Flashback Query로 사용자가 있었는지 확인하는 방식임
바꿀 입력값: <USERNAME>

#되감기와 확인, 열기

SQL*Plus (SYSDBA)인스턴스 또는 서비스 중단이 필요함
SHUTDOWN IMMEDIATE
STARTUP MOUNT
SQL*Plus (SYSDBA, MOUNT)객체 또는 설정을 변경함
FLASHBACK DATABASE TO TIMESTAMP TO_TIMESTAMP('<YYYY/MM/DD:HH24:MI:SS>', 'RRRR/MM/DD:HH24:MI:SS');
ALTER DATABASE OPEN READ ONLY;
SELECT COUNT(*) FROM dba_users WHERE username = '<USERNAME>';
SQL*Plus (SYSDBA)인스턴스 또는 서비스 중단이 필요함
SHUTDOWN IMMEDIATE
STARTUP MOUNT
ALTER DATABASE OPEN RESETLOGS;
SQL*Plus (SYSDBA)데이터 또는 파일을 삭제함, 되돌릴 수 없음
DROP RESTORE POINT before_drop;
RMAN객체 또는 설정을 변경함
BACKUP DATABASE;

결과 해석:

공식 문서의 RMAN 형식은 FLASHBACK DATABASE TO SCN <SCN>, FLASHBACK DATABASE TO RESTORE POINT <이름>임
보장 복원 지점은 쓰지 않으면 지움
지우지 않으면 FRA에 플래시백 로그가 계속 쌓이는 것으로 보이나 설명은 기재 없음

#RAC에서 PDB 하나만 되감기

잘못된 배포 뒤 CDB와 다른 PDB는 계속 열어 둔 채 한 PDB만 배포 직전으로 되돌리는 실습
PDB PITR은 백업 데이터 파일을 복원한 뒤 리두를 적용하지만, PDB Flashback은 FRA의 flashback 로그로 현재 파일을 과거로 되돌려 큰 파일을 다시 복원하는 시간을 줄일 수 있음

SQL*Plus (1번 노드, CDB$ROOT SYSDBA)조회만 함
SHOW PARAMETER db_recovery_file_dest
SELECT log_mode, flashback_on FROM v$database;
SELECT property_value FROM database_properties WHERE property_name = 'LOCAL_UNDO_ENABLED';
SQL*Plus (1번 노드, CDB$ROOT SYSDBA)데이터 또는 파일을 삭제함, 되돌릴 수 없음
CREATE RESTORE POINT rp_pdb1 FOR PLUGGABLE DATABASE <PDB_NAME> GUARANTEE FLASHBACK DATABASE;
SELECT con_id, name, guarantee_flashback_database, pdb_restore_point FROM v$restore_point;

-- (실수 재현 뒤)
ALTER PLUGGABLE DATABASE <PDB_NAME> CLOSE IMMEDIATE INSTANCES = ALL;
SELECT inst_id, name, open_mode FROM gv$pdbs WHERE name = '<PDB_NAME>';

FLASHBACK PLUGGABLE DATABASE <PDB_NAME> TO RESTORE POINT rp_pdb1;
ALTER PLUGGABLE DATABASE <PDB_NAME> OPEN RESETLOGS;
ALTER PLUGGABLE DATABASE <PDB_NAME> OPEN INSTANCES = ('<INSTANCE2>');

DROP RESTORE POINT rp_pdb1 FOR PLUGGABLE DATABASE <PDB_NAME>;

결과 해석:

전제: CDB ARCHIVELOG, FRA 설정(실습은 +FRA), FLASHBACK_ON = YES(NO면 루트에서 ALTER DATABASE FLASHBACK ON), 로컬 UNDO TRUE

실습 기록: 복원 지점은 CON_ID 3, GUARANTEE_FLASHBACK_DATABASE = YES, PDB_RESTORE_POINT = YES인 PDB 전용으로 만들어졌고, 2번 노드에서 t_bk 1,000건을 TRUNCATE한 뒤 1번 노드에서 되감자 2번 노드에서 다시 1,000건이 보였음
공유 데이터 파일이라 실수를 한 노드와 되감는 노드가 달라도 됨

PDB가 한 노드라도 열려 있으면 ORA-65025로 거부되므로 CLOSE ... INSTANCES = ALL로 모든 노드에서 MOUNTED로 만든 뒤 되감음
CLOSE 때 그 PDB 세션은 끊겨 다시 접속해야 함

OPEN RESETLOGS 뒤 PDB의 새 incarnation은 V$PDB_INCARNATION에서 봄

보장 복원 지점은 쓴 뒤 남겨 두면 flashback 로그가 FRA에 계속 쌓여 아카이브 로그와 백업 공간을 압박하므로 확인 뒤 지움

#복원 지점 없이 시각으로 PDB 되감기 (RAC 2번 노드만 사용)

수업 확인문제: 2번 노드에서 운영 계정을 DROP USER ... CASCADE로 지워 주문 테이블까지 사라졌고 미리 만든 복원 지점은 없음
1번 노드는 다른 업무 중이라 2번 노드에서만 작업함

SQL*Plus (2번 노드, PDB 안 → CDB$ROOT SYSDBA)현재 세션 설정만 변경함
SELECT event_timestamp, dbusername, action_name, object_name
  FROM unified_audit_trail
 WHERE action_name = 'DROP USER'
 ORDER BY event_timestamp;

ALTER SESSION SET CONTAINER = CDB$ROOT;
ALTER SESSION SET nls_date_format = 'YYYY-MM-DD HH24:MI:SS';
SELECT oldest_flashback_time, retention_target FROM v$flashback_database_log;
SELECT inst_id, name, open_mode FROM gv$pdbs WHERE name = '<PDB_NAME>';
SQL*Plus (2번 노드, CDB$ROOT SYSDBA)데이터 또는 파일을 삭제함, 되돌릴 수 없음
ALTER PLUGGABLE DATABASE <PDB_NAME> CLOSE IMMEDIATE INSTANCES = ALL;
FLASHBACK PLUGGABLE DATABASE <PDB_NAME>
  TO TIMESTAMP TO_TIMESTAMP('<사고 직전 시각>', 'YYYY-MM-DD HH24:MI:SS');
ALTER PLUGGABLE DATABASE <PDB_NAME> OPEN RESETLOGS;
ALTER PLUGGABLE DATABASE <PDB_NAME> OPEN INSTANCES = ALL;
SELECT inst_id, name, open_mode FROM gv$pdbs WHERE name = '<PDB_NAME>';

결과 해석:

DROP USER ... CASCADE로 지운 객체는 휴지통에 들어가지 않아 FLASHBACK TABLE ... TO BEFORE DROP으로 살릴 수 없음

사고 시각은 UNIFIED_AUDIT_TRAIL에서 찾고, 기본 감사 정책(ORA_SECURECONFIG)이 꺼져 결과가 없으면 미리 기록해 둔 시각을 씀
되감을 시각은 V$FLASHBACK_DATABASE_LOG.OLDEST_FLASHBACK_TIME보다 뒤여야 함

시각과 SCN의 대응에는 몇 초 오차가 있어 사고 시각보다 조금 앞으로 잡아야 DROP이 다시 포함되지 않음
TO SCN으로도 되감을 수 있음

보장 복원 지점과 달리 시각 기준 되감기는 db_flashback_retention_target 안에서 flashback 로그가 남아 있어야만 되며, 범위를 벗어나면 백업 기반 PDB PITR로 감

되감은 시각 이후 그 PDB의 정상 변경도 함께 사라지므로 작업 전에 손실 범위를 먼저 합의함

실행 결과는 확인 불가
예상값: 두 노드 모두 READ WRITE, 계정 복구, 주문 1,000건이 DROP 직전 상태

#사용 조건과 주의사항

RESETLOGS로 열면 되감은 시점 이후의 모든 변경을 잃음
한 테이블만 되돌리면 되는 경우 Flashback 조회와 테이블 복구를 먼저 검토함

SEO_HKabsumveritas@gmail.comBuilt with Claude Code & Codex

마지막 갱신 개인 학습 기록이며 운영 환경 적용 전 공식 문서 확인 필요

두 글자 이상 입력, 위아래 화살표로 이동하고 Enter로 열기