为了防止数据丢失,生产数据库一般要求配置为归档模式。运行中生成的归档日志保存着所有redo记录,当发生故障时可以应用备份文件和归档日志将数据库恢复到故障前。所以非常重要,那么我们怎么知道目录中的归档日志不曾被误删除呢?
伴随着国产化大潮,很多ORACLE DBA转过来学习达梦数据库。我们先回忆一下ORACLE中是怎么实现这个功能的。ORACLE中每个归档日志有一个sequence,号码连续递增。文件名由sequence组成。用ls命令对归档目录进行排序,检查文件名字号码是否连续。
还有一个更简单的方法,使用rman命令:
crosscheck archivelog all;
list expired archivelog all;
上面命令输出被删除的归档日志列表。
达梦8中归档日志没有sequence编号,所以方法1用不了。而且归档日志文件信息并没有像ORACLE那样存储在控制文件中,方法2也无效。
测试前先把一个归档文件挪走,然后在disql中输入如下脚本:
select arch_seq,next_seq,path,close_time from v$arch_file a
where not exists ( select * from v$arch_file b
where a.arch_seq=b.next_seq+1)
输出如下
![](https://img-blog.csdnimg.cn/img_convert/5a652e8df19c807180a766bd0c87fa78.jpeg)
2023-01-12 16:09:56关闭的归档文件(归档文件起始包序号 12416)之前的归档缺失。缺失几个文件,无法得知。下面检索所有归档:
![](https://img-blog.csdnimg.cn/img_convert/fd7881687bb6abd96936b291b0420df1.jpeg)
我们只知道现在它下面是12106号,无法判断中间丢了几个文件。因为ARCH_SEQ是日志包的序号,不是标识归档的唯一号码。每一个归档文件是由无数日志包组成。
把挪走的文件再拷贝回来,然后再检索本文中的sql
![](https://img-blog.csdnimg.cn/img_convert/32d0524119e828b56f4ac3ea171b4664.jpeg)
可以看到只有绿线标注的这一行了。只有一行代表是最老的一个归档文件。请注意黄先部分。12416下面是12381,之前是12106。12381文件被挪回后归档连续了。
达梦8中归档日志和后续可能的备份文件都是交付给文件系统,而不是ORACLE那样由控制文件管理。为了更清晰地说明,我们把12381文件重命名
![](https://img-blog.csdnimg.cn/img_convert/8b03685b0a2038e68ade6ccef981e255.png)
再执行上面两个sql
![](https://img-blog.csdnimg.cn/img_convert/e123c708c4043c7d06fb960b26d7eac3.png)
可以看出,12381文件已经恢复,只是名字变了。
前面讲了如何判断是否归档日志有缺失。下面这个sql是引申而来,查询最近一次备份以来归档是否有缺失。空行代表不缺失,如果查出一行,代表这行归档日志下面的文件有缺失:
select path,create_time from v$arch_file a
where not exists ( select * from v$arch_file b
where a.arch_seq=b.next_seq+1)
and arch_lsn >=(select max(begin_lsn) from v$backupset)
;
我们把12381文件再挪走后查询:
![](https://img-blog.csdnimg.cn/img_convert/5b0538ee00d44cf3dcd6b35e97dab69f.png)
可见有归档缺失
做一次新备份(绿线)
![](https://img-blog.csdnimg.cn/img_convert/ce3b425d9512197e1a8558b7cfaac111.png)
可见无归档缺失(黄色)
再次拓展一下,下面语句查看没有备份的归档日志
#方法1
select * from v$arch_file
where not exists (select * from v$backupset_arch
where path=file_name);
#方法2
select * from v$arch_file
where not exists (select * from v$backupset_arch
where begin_lsn=arch_lsn and end_lsn=clsn);
#方法3
select * from v$arch_file
where not exists (select * from v$backupset_arch
where begin_seqno=arch_seq and end_seqno=next_seq);