【IT168 技术文档】SQL Server 2005在实现高可用性和灾难恢复方面给我们提供了很多种选择。比技术本身更重要的是拿出适当的程序,这是因为我们要管理不同的灾难恢复方案。我们应该如何拿出程序来管理多种多样的灾难恢复场景呢?
专家解答
这一系列文章将探讨不同的灾难恢复场景和涉及你的恢复计划的程序。考虑到你的SQL Server 2005数据库中的灾难恢复选项,你应该包含尽可能多的技术,因为如果灾难发生时你将会有很多种选择来解决这个问题。尽管拥有这些技术被证实是很重要的,但是它也是一个伴随着使整个程序更加有效的过程。在这篇文章里,让我们来看看一个简单的场景,那就是在发生数据库备份的5个小时后,一个用户不小心删除了一张表。从一个数据库备份中恢复意味着失去5小时的数据。而对于大多数的公司来说,比起失去数据,他们更愿意选择失去时间。并且,如果这是一个非常大的数据库,那么将花很长一段时间来恢复和使它联机。在将数据损失控制到最小的前提下,我们将考虑这种情况来建立一个程序方法,以此来尽快地恢复数据库。我们将使用Northwind数据库来显示这个过程。记住在进行以下步骤之前先把Northwind中的数据库恢复模式改成FULL。
(1) 确保你有一个好的备份
针对上面的场景,我们假设你有一个每天早上6:00运行的备份,并且没有一个定期创建的数据库快照。你的数据库被配置成使用一个单一的MDF和LDF文件,这个文件对灾难恢复不太适用。让我们在Northwind数据库中创建一个全数据库备份,它将是数据库恢复的起始点。以下是代码:
GO
BACKUP DATABASE Northwind
TO DISK = N'D:\DBBackup\NorthwindBackup.bak'
WITH NAME = N'Full Database Backup', DESCRIPTION = 'Starting point for recovery',
INIT, STATS = 10
GO
从Northwind数据库模式中,你很难删除Products, Orders和Customers表,这是因为有其他表比如Order Details表的外码约束限制。但我敢打赌你可以轻易地删除Order Details表。接下来,我们来模拟在大约上午11:00时删除这张表的灾难情景。
DROP TABLE [Order Details]
(2) 包含发生的问题
由于这个数据库只有一个单一的MDF和LDF文件,我们不可能做很多操作。我们所能做的就是通过把它设置成有限制的用户模式来使数据库脱机。
GO
ALTER DATABASE Northwind
SET RESTRICTED_USER
WITH ROLLBACK IMMEDIATE
GO
这将很有效地使数据库脱机,停止所有活动的连接。这是分秒必争的时刻,我们需要采取行动。当进行到下面的步骤时,请牢记你的RPO和RTO。
(3) 备份事务日志
一个好的数据库管理员应该知道当灾难来临时,首先要做的是备份事务日志 – 假设你的数据库被设置成全数据库备份。这是为了确保在上次备份之后你还保存所有活动的事务。在我们的场景中,由于上次的备份 – 全备份,在这个例子中 – 发生于早上6:00。
TO DISK = N'D:\DBBackup\NorthwindBackupLog.trn'
WITH NAME = N'Transaction Log Backup'
, DESCRIPTION = 'Getting everything to current point in time.',
STATS = 10
GO
(4)还原数据库到一个已知的良好时间点
现在,任何用户意外地删除一张表或者在数据库上造成一些破坏后都不会立即告诉你。有时候,你可能需要自己深入挖掘它,但是这需要花很多时间。由于我们想让数据库尽快地联机,所以我们假设一个众所周知的良好时间点,并且让发掘在稍后的时间里进行。在下面的脚本中,我将选择在我的STOPAT参数中将早上 10:42设置成已知的良好时间点,一次达到展示的目的。
FROM DISK = N'D:\DBBackup\NorthwindBackup.bak'
WITH NORECOVERY, RESTRICTED_USER
GO
RESTORE LOG Northwind
FROM DISK = N'D:\DBBackup\NorthwindBackupLog.trn'
WITH RESTRICTED_USER,
STOPAT = '2008-09-23 10:42:44.00', RECOVERY
-- use a "known good" point in time
GO
虽然我们已经把数据库恢复到一个已知的良好时间点,但是我们并没有知道我们实际上到底失去了多少数据。我们需要找出在执行DROP TABLE语句之前执行最后的一个INSERT语句的准确时间,这样我们才能恢复尽可能多的数据。但是由于我们需要尽可能快地使数据库联机,所以我们不想在数据库上直接做这些。这正证明了接下来的步骤是有价值的。
你可以通过执行一个针对它的查询来验证删除的表是否已经恢复。
FROM Northwind.dbo.[Order Details]
GO
(5)创建一个恢复点的快照
我们将创建一个还原数据库的数据库快照,以此来做进一步的处理。这个数据库快照将是把数据恢复到执行DROP TABLE语句之前的准确时间的参考。
GO
CREATE DATABASE Northwind_RestorePointSnapshot
ON
( NAME = N'Northwind',
FILENAME = N'D:\DBBackup\NorthwindData_RestorePontSnapshot.snap')
AS SNAPSHOT OF [Northwind]
GO
依靠这个表模式,我们可以选择让它保持原状,或者像我们对Order Details 表所做的那样,或者多做一些操作。如果这张表有一个现有IDENTITY栏,我们需要在IDENTITY栏的最大值和需要恢复的行的假设数量之间创建一个间隙。这当然取决于在服务器上发生的事务数目。要确定IDENTITY栏的最大值,你可以执行如下显示的DBCC CHECKIDENT命令: