Oracle数据库备份与恢复
文章目录
一、使用RMAN工具
1、创建恢复目录
1、创建表空间
[root@oracle ~]# mkdir -p /u01/app/oracle/oradata/rmandb
[root@oracle ~]# chown -R oracle /u01/app/oracle/oradata/rmandb/
[root@oracle ~]# su - oracle
Last login: Wed Jul 31 18:45:40 CST 2019 on pts/0
[oracle@oracle ~]$ sqlplus / as sysdba
SQL> startup
SQL> create tablespace rmants datafile '/u01/app/oracle/oradata/rmandb/rmants.dbf' size 20M;
表空间已创建。
2、在恢复目录数据库中创建RMAN用户并授权
SQL> create user c##rman identified by rman
2 default tablespace rmants
3 temporary tablespace temp
4 quota unlimited on rmants;
用户已创建。
SQL> grant connect,resource to c##rman;
授权成功。
SQL> grant recovery_catalog_owner to c##rman;
授权成功。
SQL> exit
从 Oracle Database 12c Enterprise Edition Release 12.2.0.1.0 - 64bit Production 断开
3、在恢复目录数据库中创建恢复目录
[oracle@oracle ~]$ rman catalog c##rman/rman
RMAN> create catalog tablespace rmants;
恢复目录已创建
RMAN> exit
恢复管理器完成。
2、注册目标数据库到恢复目录
[oracle@oracle ~]$ rman target sys/orcle;
RMAN> connect catalog c##rman/rman
连接到恢复目录数据库
RMAN> register database;
注册在恢复目录中的数据库
正在启动恢复目录的全部重新同步
完成全部重新同步
RMAN> exit
恢复管理器完成。
3、备份与恢复
1、在归档方式下备份与恢复
将数据库设置为归档模式,数据库实例要处于启动状态,数据库已经加载或打开状态
[oracle@oracle ~]$ sqlplus c##rman/rman
SQL> select count(*) from rc_database;
COUNT(*)
----------
1
SQL> conn sys/oracle as sysdba;
已连接。
SQL> shutdown immediate;
SQL> startup mount;
SQL> alter database archivelog; //备份文件包括数据文件、控制文件、重做日志文件和参数文件
数据库已更改。
SQL> alter database open; //backup database plus archivelog delete input:如果还要包含归档日志文件,则要加上plus archivelog关键字.delete input的意思是在备份完成后,删除archivelog文件
数据库已更改。
修改快闪恢复区的参数
SQL> set line 120
SQL> show parameter db_recovery_file_dest;
NAME TYPE VALUE
------------------------------------ --------------- ------------------------------
db_recovery_file_dest string
db_recovery_file_dest_size big integer 0
SQL> alter system set db_recovery_file_dest_size=2g;
系统已更改。
创建一个表空间和表
SQL> create tablespace tab1
2 datafile '/u01/app/oracle/oradata/rmandb/tab1.dbf' size 10m;
表空间已创建。
创建表tab1
SQL> create table tab1 (id int);
表已创建。
向表tab1中添加记录
SQL> insert into tab1 values(1);
已创建 1 行。
SQL> commit;
提交完成。
SQL> exit
使用数据库用户sys登录RMAN
[oracle@oracle ~]$ rman target sys/oracle
RMAN> backup database;
RMAN> select systimestamp from dual; //数据库正常时查看时间点
SYSTIMESTAMP
-------------------------------------
20-5月 -20 03.12.31.337814 下午 +0
RMAN> exit
恢复管理器完成。
删除tab1表
[oracle@oracle ~]$ sqlplus sys/oracle as sysdba
SQL> drop table tab1;
表已删除。
SQL> commit;
提交完成。
恢复表
SQL> shutdown immediate;
SQL> startup mount
SQL> exit;
[oracle@oracle ~]$ rman target sys/oracle
RMAN> restore database; //恢复数据文件
RMAN> recover database until time "to_date('2020-05-20 15:12:31','yyyy-mm-dd hh24:mi:ss')"; //执行不完全恢复,时间为正常时查询的时间点
从位于 20-5月 -20 的 recover 开始
使用通道 ORA_DISK_1
正在开始介质的恢复
介质恢复完成, 用时: 00:00:00
在 20-5月 -20 完成了 recover
RMAN> alter database open resetlogs; //不完全恢复一定要使用resetlogs选项
已处理语句
RMAN> select * from tab1;
ID
----------
1
RMAN> exit
恢复管理器完成。
2、恢复表空间
[oracle@oracle ~]$ sqlplus / as sysdba
SQL> create tablespace tab2
2 Datafile '/u01/app/oracle/oradata/rmandb/tab2.dbf' size 10m;
表空间已创建。
SQL> quit
[oracle@oracle ~]$ rman target sys/oracle
RMAN> backup tablespace tab2; //表空间备份
RMAN> quit
恢复管理器完成。
[oracle@oracle ~]$ mv /u01/app/oracle/oradata/rmandb/tab2.dbf /u01/app/oracle/oradata/rmandb/tab2.dbf.bak
[oracle@oracle ~]$ rman target sys/oracle11g
RMAN> run{ //在RUN命令中备份表空间
2> sql 'alter tablespace tab2 offline immediate';
3> restore tablespace tab2;
4> recover tablespace tab2;
5> sql 'alter tablespace tab2 online';
6> }
RMAN> exit
恢复管理器完成。
[oracle@oracle ~]$ ls /u01/app/oracle/oradata/rmandb/
rmants.dbf tab1.dbf tab2.dbf tab2.dbf.bak
3、数据文件备份与恢复
[oracle@oracle ~]$ sqlplus / as sysdba
SQL> col file_name for a50;
SQL> col file_id for 99999;
SQL> set line 100
SQL> col TABLESPACE_NAME for a10;
SQL> select file_id,file_name,tablespace_name from dba_data_files;
FILE_ID FILE_NAME TABLESPACE_NAME
------- -------------------------------------------------- ------------------------------
1 /u01/app/oracle/oradata/orcl/system01.dbf SYSTEM
3 /u01/app/oracle/oradata/orcl/sysaux01.dbf SYSAUX
4 /u01/app/oracle/oradata/orcl/undotbs01.dbf UNDOTBS1
7 /u01/app/oracle/oradata/orcl/users01.dbf USERS
13 /u01/app/oracle/oradata/rmandb/rmants.dbf RMANTS
14 /u01/app/oracle/oradata/rmandb/tab1.dbf TAB1
15 /u01/app/oracle/oradata/rmandb/tab2.dbf TAB2
已选择 7 行。
SQL> quit
[oracle@oracle ~]$ rman target sys/oracle
RMAN> backup datafile 15; //进行备份。15为查询需要备份的表所对应的FILE_ID
RMAN> quit
恢复管理器完成。
[oracle@oracle ~]$ mv /u01/app/oracle/oradata/rmandb/tab2.dbf /u01/app/oracle/oradata/rmandb/tab2.dbf.bak1
[oracle@oracle ~]$ rman target sys/oracle
RMAN> run{
2> allocate channel dev1 type disk;
3> sql 'alter tablespace tab2 offline immediate';
4> restore datafile 15;
5> recover datafile 15;
6> sql 'alter tablespace tab2 online';
7> release channel dev1;
8> }
RMAN> quit
恢复管理器完成。
[oracle@oracle ~]$ ls /u01/app/oracle/oradata/rmandb/
rmants.dbf tab1.dbf tab2.dbf tab2.dbf.bak tab2.dbf.bak1
二、使用数据泵技术实现逻辑备份
1、创建—个操作目录
[root@oracle ~]# su - oracle
Last login: Wed Jul 31 18:45:40 CST 2019 on pts/0
[oracle@oracle ~]$ sqlplus / as sysdba
SQL> startup
SQL> exit
[oracle@oracle ~]$ exit
登出
[root@oracle ~]# mkdir /u01/app/backup
[root@oracle ~]# chown -R oracle /u01/app/backup/
[root@oracle ~]# su - oracle
Last login: Fri May 22 14:28:06 CST 2020 on pts/0
[oracle@oracle ~]$ sqlplus / as sysdba
SQL> create directory dump_dir as '/u01/app/backup'; //如果提示已存在,请忽略
目录已创建。
2、授予用户操作dump_dir目录的权限
SQL> grant read,write on directory dump_dir to c##scott;
授权成功。
3、创建测试用户user1并授权
SQL> create user c##user1 identified by 123456;
用户已创建。
SQL> grant connect,resource to c##user1;
授权成功。
SQL> grant read,write on directory dump_dir to c##user1;
授权成功。
SQL> grant unlimited tablespace to c##user1;
授权成功。
SQL> exit
4、导出c##scott用户的emp和dept表
[oracle@oracle ~]$ expdp c##scott/123456 directory=dump_dir dumpfile=scotttab.dmp tables=emp,dept
5、导入scott用户表(模拟损坏)
[oracle@oracle ~]$ sqlplus c##scott/123456
SQL> select table_name from user_all_tables;
TABLE_NAME
--------------------------------------------------------------------------------
DEPT
EMP
BONUS
SALGRADE
SQL> drop table emp;
表已删除。
SQL> exit
[oracle@oracle ~]$ impdp c##scott/123456 directory=dump_dir dumpfile=scotttab.dmp tables=emp
[oracle@oracle ~]$ sqlplus c##scott/123456
SQL> select table_name from user_all_tables;
TABLE_NAME
--------------------------------------------------------------------------------
DEPT
BONUS
SALGRADE
EMP
SQL> exit
6、将导出的c##scott用户的dept和emp表导入给c##user1
[oracle@oracle ~]$ impdp system/oracle directory=dump_dir dumpfile=scotttab.dmp tables=c##scott.dept,c##scott.emp remap_schema=c##scott:c##user1
[oracle@oracle ~]$ sqlplus c##user1/123456
SQL> select table_name from user_all_tables;
TABLE_NAME
--------------------------------------------------------------------------------
DEPT
EMP
SQL> exit
7、导出与导入scott用户模式
[oracle@oracle ~]$ expdp c##scott/123456 directory=dump_dir dumpfile=scottschema.dmp schemas=c##scott //导出c##scott.emp表
[oracle@oracle ~]$ sqlplus c##scott/123456 //用scott用户连接数据库,删除emp表
SQL> drop table emp;
表已删除。
SQL> select * from emp; //emp已不存在
select * from emp
*
第 1 行出现错误:
ORA-00942: 表或视图不存在
SQL> exit
[oracle@oracle ~]$ impdp c##scott/123456 directory=dump_dir dumpfile=scottschema.dmp schemas=c##scott //导入scott.emp表
[oracle@oracle ~]$ sqlplus c##scott/123456 //用scott用户连接数据库
SQL> col ENAME for a10
SQL> col JOB for a10
SQL> set line 120
SQL> select * from emp;
EMPNO ENAME JOB MGR HIREDATE SAL COMM DEPTNO
---------- ---------- ---------- ---------- ------------ ---------- ---------- ----------
7369 SMITH CLERK 7902 17-12月-80 800 20
7499 ALLEN SALESMAN 7698 20-2月 -81 1600 300 30
7521 WARD SALESMAN 7698 22-2月 -81 1250 500 30
7566 JONES MANAGER 7839 02-4月 -81 2975 20
7654 MARTIN SALESMAN 7698 28-9月 -81 1250 1400 30
7698 BLAKE MANAGER 7839 01-5月 -81 2850 30
7782 CLARK MANAGER 7839 09-6月 -81 2450 10
7788 SCOTT ANALYST 7566 19-4月 -87 3000 20
7839 KING PRESIDENT 17-11月-81 5000 10
7844 TURNER SALESMAN 7698 08-9月 -81 1500 0 30
7876 ADAMS CLERK 7788 23-5月 -87 1100 20
EMPNO ENAME JOB MGR HIREDATE SAL COMM DEPTNO
---------- ---------- ---------- ---------- ------------ ---------- ---------- ----------
7900 JAMES CLERK 7698 03-12月-81 950 30
7902 FORD ANALYST 7566 03-12月-81 3000 20
7934 MILLER CLERK 7782 23-1月 -82 1300 10
已选择 14 行。
SQL> exit
8、导入与导出表空间
[oracle@oracle ~]$ sqlplus system/oracle
SQL> create tablespace user01
2 datafile '/u01/app/oracle/oradata/user01.dbf' size 10m;
表空间已创建。
SQL> create table t1(id int) tablespace user01;
表已创建。
SQL> insert into t1 values(1);
已创建 1 行。
SQL> commit;
提交完成。
SQL> exit
从 Oracle Database 12c Enterprise Edition Release 12.2.0.1.0 - 64bit Production 断开
[oracle@oracle ~]$ expdp system/oracle directory=dump_dir dumpfile=tablespaceusers.dmp tablespaces=user01
[oracle@oracle ~]$ sqlplus system/oracle
SQL> drop table t1;
表已删除。
SQL> exit
从 Oracle Database 12c Enterprise Edition Release 12.2.0.1.0 - 64bit Production 断开
[oracle@oracle ~]$ impdp system/oracle directory=dump_dir dumpfile=tablespaceusers.dmp tablespaces=user01
[oracle@oracle ~]$ sqlplus system/oracle
SQL> select * from t1;
ID
----------
1
SQL> exit
9、导入与导出数据库
[oracle@oracle ~]$ expdp system/oracle directory=dump_dir dumpfile=full.dmp full=y
[oracle@oracle ~]$ impdp system/oracle directory=dump_dir dumpfile=full.dmp full=y
三、闪回技术
1、设置闪回数据库
1、启用归档模式
[oracle@oracle ~]$ sqlplus / as sysdba
SQL> shutdown immediate;
SQL> startup mount;
SQL> alter database archivelog;
数据库已更改。
SQL> exit
[oracle@oracle ~]$ exit
2、建立闪回区
[root@oracle ~]# mkdir -p /u01/app/oracle/flash_recovery_area
[root@oracle ~]# chown -R oracle /u01/app/oracle/flash_recovery_area
[root@oracle ~]# su - oracle
Last login: Fri May 22 14:30:51 CST 2020 on pts/0
[oracle@oracle ~]$ sqlplus / as sysdba
SQL> alter system set db_recovery_file_dest_size=3g scope=both;
系统已更改。
SQL> alter system set db_recovery_file_dest='/u01/app/oracle/flash_recovery_area' scope=both;
系统已更改。
3、设置闪回数据库的数据保留周期
SQL> alter system set db_flashback_retention_target=1440; //周期为一天,以min为单位
系统已更改。
4、启用闪回日志
SQL> alter database flashback on;
数据库已更改。
SQL> alter database open;
数据库已更改。
SQL> show parameter db_recovery_file; //查询是否成功启用闪回恢复区
NAME TYPE
------------------------------------ ---------------------------------
VALUE
------------------------------
db_recovery_file_dest string
/u01/app/oracle/flash_recovery
_area
db_recovery_file_dest_size big integer
3G
SQL> col TYPE for a15
SQL> col VALUE for a30
SQL> show parameter db_recovery_file;
NAME TYPE VALUE
------------------------------------ --------------- ------------------------------
db_recovery_file_dest string /u01/app/oracle/flash_recovery
_area
db_recovery_file_dest_size big integer 3G
SQL> col VALUE for a50
SQL> show parameter db_recovery_file;
NAME TYPE VALUE
------------------------------------ --------------- ------------------------------
db_recovery_file_dest string /u01/app/oracle/flash_recovery
_area
db_recovery_file_dest_size big integer 3G
SQL> select flashback_on from v$database; //查询是否成功启用闪回数据库
FLASHBACK_ON
------------------------------------------------------
YES
2、使用scn闪回数据库
1、查询数据库系统当前的scn
SQL> select current_scn from v$database;
CURRENT_SCN
-----------
1789789
2、改变数据库的当前状态,模拟创建表test1,并插入1条数据
SQL> create table test1(id number,name char(20));
表已创建。
SQL> insert into test1 values(1,'data');
已创建 1 行。
SQL> commit;
提交完成。
3、进行闪回数据库恢复,将数据库恢复到创建表之前的状态
SQL> select OLDEST_FLASHBACK_SCN from v$FLASHBACK_DATABASE_LOG;
OLDEST_FLASHBACK_SCN
--------------------
1787872
SQL> shutdown immediate
SQL> startup mount;
SQL> flashback database to scn 1787872; //1787872为查询到的SCN
闪回完成。
4、使用resetlogs选项打开数据库
SQL> alter database open resetlogs;
数据库已更改。
5、验证数据库的状态
SQL> select * from test1;
select * from test1
*
第 1 行出现错误:
ORA-00942: 表或视图不存在
6、按照指定时间闪回数据库
SQL> alter session set nls_date_format='yyyy-mm-dd hh24:mi:ss'; //设置显示日期格式
会话已更改。
SQL> select sysdate from dual; //查看系统时间
SYSDATE
-------------------
2020-05-22 15:17:53
SQL> set time on;
15:17:58 SQL> create table test2(id number,name char(20)); //模拟创建表test2
表已创建。
15:18:09 SQL> insert into test2 values(1,'data'); //插入1条记录
已创建 1 行。
15:18:15 SQL> commit;
提交完成。
15:18:33 SQL> shutdown immediate;
15:19:11 SQL> startup mount;
15:19:19 SQL> flashback database to timestamp to_timestamp('2020-05-22 15:17:53','yyyy-mm-dd hh24:mi:ss'); //日期为前面查看到的系统时间
闪回完成。
15:19:44 SQL> alter database open resetlogs;
数据库已更改。
15:19:55 SQL> select * from test2;
select * from test2
*
第 1 行出现错误:
ORA-00942: 表或视图不存在
说明:闪回数据库操作的限制
1、数据文件损坏或丢失等介质故障不能使用闪回数据库进行恢复。闪回数据库只能基于当前正常运行的数据文件。
2、闪回数据库功能启动后,如果发生数据库控制文件重建或利用备份恢复控制文件,则不能使用闪回数据库。
3、不能使用闪回数据库进行数据文件收缩操作。
4、不能使用闪回数据库将数据库恢复到闪回日志中可获得最早的SCN之前的SCNM,因为闪回日志文件在一定条件下被删除,而不是始终保存在闪回恢复区中。
3、闪回表
注意:SYS用户或以AS SYSDBA身份登录的用户不能执行闪回表操作
1、授予scott用户select any dictionary的权限
15:20:46 SQL> conn / as sysdba
已连接。
15:20:51 SQL> grant select any dictionary to c##scott; //授予权限
授权成功。
15:20:56 SQL> set time on
15:21:02 SQL> conn c##scott/123456;
已连接。
15:21:07 SQL> select current_scn from v$database; //查询SCN
CURRENT_SCN
-----------
1790449
15:21:14 SQL> update test3 set name='liu' where id=1;
已更新 1 行。
15:21:20 SQL> commit;
提交完成。
15:21:25 SQL> select * from test3;
ID NAME
---------- ------------------------------------------------------------
1 liu
2 zhao
3 wang
15:21:29 SQL> delete from test3 where id=3;
已删除 1 行。
15:21:35 SQL> commit;
提交完成。
15:21:47 SQL> select * from test3;
ID NAME
---------- ------------------------------------------------------------
1 liu
2 zhao
2、启动表的row movement特性
15:21:55 SQL> alter table test3 enable row movement;
表已更改。
15:22:03 SQL> flashback table test3 to timestamp to_timestamp('2020-05-22 15:21:35','yyyy-mm-dd hh24:mi:ss'); //时间为之前提交的时间
闪回完成。
15:22:46 SQL> select * from test3; //闪回到了删除前的表
ID NAME
---------- ------------------------------------------------------------
1 liu
2 zhao
3 wang
15:22:52 SQL> flashback table test3 to scn 1790449; //闪回到了表格第一次commit的数据
闪回完成。
4、闪回删除
注意:不支持SYS用户,SYSTEM表空间下的对象也不能从回收站里拿到。故使用SYS或者SYSTEM用户登录时,查询为空
1、启动回收站,在默认情况下回收站已经启动
15:23:14 SQL> conn / as sysdba;
已连接。
15:23:24 SQL> show parameter recyclebin;
NAME TYPE VALUE
------------------------------------ --------------- ------------------------------
recyclebin string on
15:23:29 SQL> alter system set recyclebin=on deferred;
系统已更改。
2、切换用户查看回收站
15:23:34 SQL> conn c##scott/123456;
已连接。
15:23:40 SQL> create table test4(id number,name char(20));
表已创建。
15:23:46 SQL> insert into test4 values(3,'wang');
已创建 1 行。
15:23:51 SQL> commit;
提交完成。
15:23:56 SQL> drop table test4;
表已删除。
15:25:10 SQL> col ORIGINAL_NAME for a20
15:25:39 SQL> col OBJECT_NAME for a40
15:25:56 SQL> select object_name,original_name,type from user_recyclebin; //查看回收站
OBJECT_NAME ORIGINAL_NAME TYPE
---------------------------------------- -------------------- ---------------
BIN$pjfmyORcD6HgUwEBqMCc3A==$0 PK_EMP INDEX
BIN$pjfmyORdD6HgUwEBqMCc3A==$0 EMP TABLE
BIN$pjfxCnKKEAXgUwEBqMCwSA==$0 PK_EMP INDEX
BIN$pjfxCnKLEAXgUwEBqMCwSA==$0 EMP TABLE
BIN$pjiDXz1kFwLgUwEBqMDJ1g==$0 TEST4 TABLE
15:25:58 SQL> flashback table test4 to before drop rename to new_test4; //闪回表并重命名为new_test4
闪回完成。
15:26:10 SQL> select * from new_test4;
ID NAME
---------- ------------------------------------------------------------
3 wang
15:26:21 SQL> purge recyclebin; //清空回收站,慎用
回收站已清空。
5、闪回查询
15:26:27 SQL> conn c##scott/123456;
已连接。
15:26:33 SQL> alter session set nls_date_format='yyyy-mm-dd hh24:mi:ss';
会话已更改。
15:26:38 SQL> set time on;
15:26:45 SQL> select empno,sal from emp where empno=7844;
EMPNO SAL
---------- ----------
7844 1500
15:26:51 SQL> update emp set sal=2000 where empno=7844;
已更新 1 行。
15:26:58 SQL> commit;
提交完成。
15:27:06 SQL> update emp set sal=2500 where empno=7844;
已更新 1 行。
15:27:12 SQL> update emp set sal=3000 where empno=7844;
已更新 1 行。
15:27:17 SQL> commit;
提交完成。
15:27:21 SQL> select empno,sal from scott.emp as of timestamp sysdate-1/24 where empno=7844; //查询7844员工前一个小时的工资值
select empno,sal from scott.emp as of timestamp sysdate-1/24 where empno=7844
*
第 1 行出现错误:
ORA-00942: 表或视图不存在
15:28:50 SQL> select sal from emp as of timestamp to_timestamp('2020-05-22 15:27:17','yyyy-mm-dd hh24:mi:ss') where empno=7844; //查询第二次commit之前的数据
SAL
----------
2000