1 问题描述
数据库在正常运行,误操作,直接rm 掉了数据文件。(注意:这种方法数据不能重启)
[root@zw ~]# cat /etc/redhat-release
Red Hat Enterprise Linux Server release 5.5 (Tikanga)
Oracle 11.2.0.3 单实例。
[oracle@zw ~]$ sqlplus / as sysdba
SQL*Plus: Release 11.2.0.3.0 Production on Wed Jan 7 20:02:10 2015
Copyright (c) 1982, 2011, Oracle. All rights reserved.
Connected to:
Oracle Database 11g Enterprise Edition Release 11.2.0.3.0 - 64bit Production
With the Partitioning, OLAP, Data Mining and Real Application Testing options
SQL>
这个问题也要分2种情况,一种是归档模式,一种是非归档模式,归档模式处理就容易很多了。
2 创建测试数据
SQL> create tablespace test1 datafile '/oradata/ogg02/test1.dbf' size 100m;
Tablespace created.
SQL> create tablespace test1 datafile '/oradata/ogg02/test1.dbf' size 100m;
Tablespace created.
SQL> create user ztt identified by ztt default tablespace test1;
User created.
SQL> grant connect,resource,dba to ztt;
Grant succeeded.
SQL> conn ztt/ztt;
Connected.
SQL> create table t1 as select * from all_users;
Table created.
SQL> create table t2 as select * from all_users;
Table created.
SQL> create table t3 as select * from all_users;
Table created.
3 归档模式处理
3.1 模拟故障
SQL> archive log list;
Database log mode Archive Mode
Automatic archival Enabled
Archive destination /oradata/arch
Oldest online log sequence 6
Next log sequence to archive 8
Current log sequence 8
在操作系统上直接删除数据文件:
[oracle@dg1 u01]$ rm -rf /oradata/ogg02/test1.dbf
此时数据库还是正常运行,我们查询我们之前创建的几张表:
SQL> select count(1) from t1;
select count(1) from t1
*
ERROR at line 1:
ORA-01116: error in opening database file 7
ORA-01110: data file 7: '/oradata/ogg02/test1.dbf'
ORA-27041: unable to open file
Linux-x86_64 Error: 2: No such file or directory
Additional information: 3
至少从目前看,一切都是正常。 这里正常也是因为我们的操作系统是Linux,当数据文件从操作系统级别被rm掉,但之前打开该文件的进程仍然持有相应的文件句柄,所以指向的文件仍然可以读写,并且该文件的文件描述符可以从/proc目录中获得,也可以利用这个句柄恢复文件。如果在这个时候,重启了数据库或者操作系统,那么句柄就会消失,也就只能通过扫描磁盘进行文件恢复。
3.2 恢复
dbwr进程会打开所有数据文件的句柄,在proc目录中可以查到这些数据文件的信息,目录名是进程PID,fd表示文件描述符。
检查dbwr的进程PID:
[oracle@dg1 trace]$ ps -ef|grep dbw0
[root@zw ogg02]# ps -ef|grep dbw0
oracle 21884 1 0 19:05 ? 00:00:00 ora_dbw0_ogg02
[oracle@dg1 trace]$ cd /proc/21884/fd
[oracle@dg1 fd]$ ls -l
这里的 265 就是我们删掉的数据文件。
//直接cp该句柄文件名回原位置:
[oracle@dg1 fd]$ cp 265 /oradata/ogg02/test1.dbf
[oracle@dg1 fd]$
因为数据库一直是open的,那么SCN也会不断的变化,我们cp出来的数据文件和数据库当前的信息不一致,所以我们需要进行recover:
SQL> alter database datafile'/oradata/ogg02/test1.dbf' offline;
Database altered.
SQL> recover datafile'/oradata/ogg02/test1.dbf'
ORA-00283: recovery session canceled due to errors
ORA-01110: data file 7: '/oradata/ogg02/test1.dbf'
ORA-01157: cannot identify/lock data file 7 - see DBWR trace file
ORA-01110: data file 7: '/oradata/ogg02/test1.dbf'
这里报错,是因为 cp的时候用root用户,导致test1.dbf 是root用户组的
1.查看这个数据文件有没有权限
-rw-r----- 1 root root
一看原来是root 的用户组
[root@zw ogg02]# chown oracle:dba test1.dbf
-rw-r----- 1 oracle dba 104865792 Jan 7 20:41 test1.dbf
现在权限改过来了
SQL> recover datafile 7;
Media recovery complete.
现在恢复成功!!
SQL> alter database datafile'/oradata/ogg02/test1.dbf' online;
Database altered.
恢复正常。
//重启数据库:
SQL> shutdown immediate
Database closed.
Database dismounted.
ORACLE instance shut down.
SQL> startup
ORACLE instance started.
Total System Global Area 814227456 bytes
Fixed Size 2232760 bytes
Variable Size 490737224 bytes
Database Buffers 318767104 bytes
Redo Buffers 2490368 bytes
Database mounted.
Database opened.
SQL>
注意:①.数据库是归档模式
②.数据库或者操作系统没有重启。
在非归档模式下,如果删除了数据文件,并且又触发了CKPT,那么CKPT 会直接把整个实例中断掉,也就是说,如果是比较繁忙的数据库,如果误删除数据文件,实例可能会中断,一旦实例中断,那么用用上面的通过句柄恢复就没有可能性了。