分享

SQL SERVER数据的差异备份如何还原?

 看见就非常 2014-07-14
由于全盘数据库备份耗时太大,
我现在想做一个定时的数据库差异备份。
但是,我不知道怎么恢复差异备份。

比如:
我最初第一次备份在12-15号,生成一个MyDB_bak.bak这个完整的备份。
2008-12-16我做一个差异备份生成MyDB_diff_bak_081216.bak。
2008-12-17我做一个差异备份生成MyDB_diff_bak_081217.bak。
2008-12-18我做一个差异备份生成MyDB_diff_bak_081218.bak。

现在,我怎么恢复一个完整的到2008-12-18的数据库呢?
不懂这个差异备份是怎么回事?

是不是我的MyDB_diff_bak_081216.bak是与MyDB_diff_bak_081217.bak的数据库差异备份?
回复次数:19
liangCK
关注
liangCK
liangCK
等级:Blank
2
更多勋章
#1 得分:0 回复于: 2008-12-19 09:45:28
还原 完整备份..再还原12-18号的差异备份即可..
liangCK
关注
liangCK
liangCK
等级:Blank
2
更多勋章
#2 得分:0 回复于: 2008-12-19 09:46:29
SQL code?
1
2
RESTORE DATABASE dbname FROM DISK='c:\MyDB_bak.bak' WITH NORECOVERY
RESTORE DATABASE dbname FROM DISK='c:\MyDB_diff_bak_081218.bak' WITH RECOVERY
dawugui
关注
dawugui
dawugui
等级:Blank
3
更多勋章
#3 得分:0 回复于: 2008-12-19 09:47:31
差异备份和还原(转)


作者:8LY8Apollo   (阿波罗) 

  差异备份只创建数据库中自上一次数据库备份之后修改过的所有页的复本。差异日志主要用于使用频繁的系统,一旦这类系统中的数据库发生故障,必须尽快使其重新联机。差异备份比完整数据库备份小,因此对正在运行的系统影响较小。   
    
  例如,某个站点在星期天晚上执行完整数据库备份。在白天每隔   4   小时制作一个事务日志备份集,并用当天的备份重写头一天的备份。每晚则进行差异备份。如果数据库的某个数据磁盘在星期四上午   9:12   出现故障,则该站点可以:     
    
  备份当前事务日志。   
    
    
  还原从星期天晚上开始的数据库备份。   
    
    
  还原从星期三晚上开始的差异备份,将数据库前滚到这一时刻。   
    
    
  还原从早上   4   点到   8   点的事务日志备份,以将数据库前滚到早上   8   点。   
    
    
  还原故障之后的日志备份。这将使数据库前滚到故障发生的那一刻。     
    
  如何创建差异数据库备份(企业管理器)   
  创建差异数据库备份     
    
  展开服务器组,然后展开服务器。   
    
    
  展开"数据库"文件夹,右击数据库,指向"所有任务"子菜单,再单击"备份数据库"命令。   
    
    
  在"名称"框内,输入备份集名称。在"描述"框中输入备份集的描述(可选)。   
    
    
  在"备份"框下选择"数据库   —   差异"。   
    
    
  在"目的"下,单击"磁带"或"磁盘",然后指定备份目的地。     
  如果没有出现目的地,单击"添加"以添加现有的备份设备或创建新的备份设备。   
    
  在"重写"下执行下列操作之一:     
  单击"追加到媒体",将备份追加到备份设备上任何现有的备份中。   
    
    
  单击"重写现有媒体",将重写备份设备中任何现有的备份。     
  选择"调度"复选框调度备份操作以后执行或定期执行。(可选)   
    
    
  单击"选项"选项卡,然后执行下列一项或多项操作:(可选)     
  选择"完成后验证备份"复选框,在备份时验证备份。   
    
    
  选择"备份后弹出磁带"复选框,在备份操作完成后弹出磁带。该选项只适用于磁带设备。   
    
    
  选择"检查媒体集名称和备份集到期时间"复选框,检查备份媒体以防意外重写。在"媒体集名称"框中,输入将用于备份操作的媒体的名称。如果仅指定备份集到期时间,则将其保留为空。     
  如果是第一次使用备份媒体,或者要更改现有的媒体标签,则在"媒体集标签"框下选择"初始化并标识媒体"复选框,然后输入媒体集名称和媒体集描述。只有在重写媒体时才能对其进行初始化和标识设置。     
  如何还原差异数据库备份(企业管理器)   
    
    
  说明     如果要还原差异数据库备份,而在   msdb   数据库中存储的备份历史记录中没有列出此差异数据库备份的任何备份集信息,例如在另一台服务器上创建的差异数据库备份,请参阅如何从备份设备还原备份。   
    
    
  还原差异数据库备份     
    
  展开服务器组,然后展开服务器。   
    
    
  展开"数据库"文件夹,右击数据库,指向"所有任务"子菜单,然后单击"还原数据库"命令。   
    
    
  在"还原为数据库"框中,如果要还原的数据库名称与显示的默认数据库名称不同,请在其中进行输入或选择。   
    
    
  单击"数据库"。   
    
    
  在"要还原的第一个备份"列表中,选择要还原的备份集。   
    
    
  在"还原"列表中,单击要还原的差异备份。   
    
    
  单击"选项"选项卡,然后执行下列操作之一:(可选)     
  单击"使数据库可以继续运行,但无法还原其它事务日志",如果没有其它要应用的事务日志备份。   
    
    
  单击"使数据库不再运行,但能还原其它事务日志",如果要应用其它事务日志备份。
wufeng4552
关注
wufeng4552 版主
水族杰纶
等级:Blank
2
2
更多勋章
#4 得分:0 回复于: 2008-12-19 09:48:17
SQL code?
1
2
3
restore headeronly from bak2              --从差异备份中恢复
restore database d2 from bak2 with file=1,norecovery    
restore database d2 from bak2 with file=5,recovery
liangCK
关注
liangCK
liangCK
等级:Blank
2
更多勋章
#5 得分:0 回复于: 2008-12-19 09:48:44
差异备份是备份自最近一次完整备份后所做的更改的备份..所以你只需要还原最近的一次差异备份即可.
dawugui
关注
dawugui
dawugui
等级:Blank
3
更多勋章
#6 得分:0 回复于: 2008-12-19 09:49:05
日志备份和差异备份还原中的常见问题示例

--创建测试
CREATE DATABASE db
GO

--正常备份
BACKUP DATABASE db TO DISK='c:\1.bak' WITH FORMAT
BACKUP LOG db TO DISK='c:\2.bak' WITH FORMAT
BACKUP LOG db TO DISK='c:\3.bak' WITH FORMAT
BACKUP DATABASE db TO DISK='c:\4.bak' WITH FORMAT
BACKUP DATABASE db TO DISK='c:\5.bak' WITH FORMAT,DIFFERENTIAL
BACKUP LOG db TO DISK='c:\6.bak' WITH FORMAT
GO

--下面是用于日志备份和差异备份还原中易犯的错误

--1. 恢复时使用错误的日志顺序
IF DB_ID('db') IS NOT NULL DROP DATABASE db
RESTORE DATABASE db FROM DISK='c:\1.bak' WITH NORECOVERY
RESTORE LOG db FROM DISK='c:\3.bak'
/*--收到信息
服务器: 消息 4305,级别 16,状态 1,行 5
此备份集中的日志开始于 LSN 6000000002800001,该 LSN 太晚,无法应用到数据库。包含 LSN 6000000002500001 的较早的日志备份可以还原。
--*/
GO

--2. 恢复时,将日志备份应用于错误的完全备份
IF DB_ID('db') IS NOT NULL DROP DATABASE db
RESTORE DATABASE db FROM DISK='c:\4.bak' WITH NORECOVERY
RESTORE LOG db FROM DISK='c:\2.bak'
/*--收到错误信息
服务器: 消息 4326,级别 16,状态 1,行 5
此备份集中的日志终止于 LSN 6000000002800001,该 LSN 太早,无法应用到数据库。包含 LSN 6000000003000001 的较新的日志备份可以还原。
--*/
GO

--3. 将日志备份用于RESTORE DATABASE
IF DB_ID('db') IS NOT NULL DROP DATABASE db
RESTORE DATABASE db FROM DISK='c:\2.bak' WITH NORECOVERY
/*--收到错误信息
服务器: 消息 3135,级别 16,状态 2,行 4
文件 'c:\2.bak' 中的备份集是由 BACKUP LOG 创建的,无法用于此还原操作。
--*/
GO

--4. 将差异备份用于RESTORE LOG
IF DB_ID('db') IS NOT NULL IF DB_ID('db') IS NOT NULL DROP DATABASE db
RESTORE DATABASE db FROM DISK='c:\4.bak' WITH NORECOVERY
RESTORE LOG db FROM DISK='c:\5.bak'
/*--收到错误信息
服务器: 消息 3135,级别 16,状态 2,行 3
文件 'c:\5.bak' 中的备份集是由 BACKUP DATABASE WITH DIFFERENTIAL 创建的,无法用于此还原操作。
--*/
GO

--5. 将差异备份用于RESTORE LOG
IF DB_ID('db') IS NOT NULL IF DB_ID('db') IS NOT NULL DROP DATABASE db
RESTORE DATABASE db FROM DISK='c:\4.bak' WITH NORECOVERY
RESTORE LOG db FROM DISK='c:\5.bak'
/*--收到错误信息
服务器: 消息 3135,级别 16,状态 2,行 3
文件 'c:\5.bak' 中的备份集是由 BACKUP DATABASE WITH DIFFERENTIAL 创建的,无法用于此还原操作。
--*/
GO

--6. 将差异备份用于错误的完全备份中
IF DB_ID('db') IS NOT NULL IF DB_ID('db') IS NOT NULL DROP DATABASE db
RESTORE DATABASE db FROM DISK='c:\1.bak' WITH NORECOVERY
RESTORE DATABASE db FROM DISK='c:\5.bak'
/*--收到错误信息
服务器: 消息 3136,级别 16,状态 1,行 3
无法将设备 'c:\5.bak' 上的备份应用于数据库 'db'。
--*/
GO

--7. 直接使用日志备份或者差异备份还原
IF DB_ID('db') IS NOT NULL IF DB_ID('db') IS NOT NULL DROP DATABASE db
RESTORE DATABASE db FROM DISK='c:\5.bak'
RESTORE LOG db FROM DISK='c:\2.bak'
/*--收到错误信息
服务器: 消息 913,级别 16,状态 8,行 3
未能找到 ID 为 65535 的数据库。可能该数据库尚未激活,也可能正在转换过程中。
--*/
GO

--8. 还原完全备份时,未使用NORECOVERY,导致不能正确还原日志备份或者差异备份
IF DB_ID('db') IS NOT NULL IF DB_ID('db') IS NOT NULL DROP DATABASE db
RESTORE DATABASE db FROM DISK='c:\1.bak'
RESTORE LOG db FROM DISK='c:\2.bak'
/*--收到错误信息
服务器: 消息 4306,级别 16,状态 1,行 4
先前的还原操作未指定 WITH NORECOVERY 或 WITH STANDBY。请在除最后步骤之外的所有其他步骤中指定 WITH NORECOVERY 或 WITH STANDBY 后,重新启动该还原序列。
--*/
GO

--删除测试
IF DB_ID('db') IS NOT NULL DROP DATABASE db
bluefangxiao
关注
bluefangxiao
bluefangxiao
等级:Blank
#7 得分:0 回复于: 2008-12-19 09:54:42
SQL code?
1
2
RESTORE DATABASE dbname FROM DISK='c:\MyDB_bak.bak' WITH NORECOVERY
RESTORE DATABASE dbname FROM DISK='c:\MyDB_diff_bak_081218.bak' WITH RECOVERY
NewCenturyNewPage
关注
NewCenturyNewPage
NewCenturyNewPage
等级:Blank
#8 得分:0 回复于: 2008-12-19 09:56:06
引用 5 楼 liangCK 的回复:
差异备份是备份自最近一次完整备份后所做的更改的备份..所以你只需要还原最近的一次差异备份即可.

我如果要恢复2008-12-17的数据库,是不是只有结合:
MyDB_bak.bak和MyDB_diff_bak_081217.bak才行?
怎么才能确定file = n?
这个n呢?
liangCK
关注
liangCK
liangCK
等级:Blank
2
更多勋章
#9 得分:0 回复于: 2008-12-19 09:59:11
引用 8 楼 NewCenturyNewPage 的回复:
引用 5 楼 liangCK 的回复:
差异备份是备份自最近一次完整备份后所做的更改的备份..所以你只需要还原最近的一次差异备份即可. 
 

我如果要恢复2008-12-17的数据库,是不是只有结合: 
MyDB_bak.bak和MyDB_diff_bak_081217.bak才行? 
怎么才能确定file = n? 
这个n呢?

是的..

要确定file=n
那你可以在联机丛书中查
SQL code?
1
RESTORE FILELISTONLY
NewCenturyNewPage
关注
NewCenturyNewPage
NewCenturyNewPage
等级:Blank
#10 得分:0 回复于: 2008-12-19 10:16:49
谢谢楼上的各位星星们!

还有一个问题:


2008-12-16我做一个差异备份生成MyDB_diff_bak_081216.bak。 
2008-12-17我做一个差异备份生成MyDB_diff_bak_081217.bak。 
2008-12-18我做一个差异备份生成MyDB_diff_bak_081218.bak。

MyDB_diff_bak_081217.bak是不是和MyDB_diff_bak_081216.bak的差异?
这样结合MyDB_bak.bak 和 MyDB_diff_bak_081217.bak 好像恢复不了完整的17号的数据库哦?
因为MyDB_diff_bak_081216.bak的变化被忽略了。
liangCK
关注
liangCK
liangCK
等级:Blank
2
更多勋章
#11 得分:0 回复于: 2008-12-19 10:20:31
看我5楼的.
---------------------
MyDB_diff_bak_081217.bak是不是和MyDB_diff_bak_081216.bak的差异? 
--------------------
不是.每个差异备份都是对最近一次完整备份的差异..

所以你要还原到12-17号.还原完整备份后.再还原12-17的差异备份..其中12-16号的所做的操作不会被忽略..因为都记录到12-17号的差异备份那了.
liangCK
关注
liangCK
liangCK
等级:Blank
2
更多勋章
#12 得分:0 回复于: 2008-12-19 10:29:15
SQL code?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
--创建测试数据库
CREATE DATABASE Test
GO
--将测试数据库的恢复模式设置为FULL
ALTER DATABASE Test 
    SET RECOVERY FULL
GO
USE Test
GO
CREATE TABLE tb(id int,col varchar(20))
--完整备份数据库
BACKUP DATABASE Test TO DISK='G:\Test.bak' WITH FORMAT
--对tb表插入第一条记录
INSERT INTO tb(id,col) VALUES(1,'第一次差异备份')
--第一次差异备份
BACKUP DATABASE Test TO DISK='G:\Test_One_Dif.bak' WITH FORMAT,DIFFERENTIAL
--对tb表插入第二条记录
INSERT INTO tb(id,col) VALUES(2,'第二次差异备份')
--第二次差异备份
BACKUP DATABASE Test TO DISK='G:\Test_Two_Dif.bak' WITH FORMAT,DIFFERENTIAL
--OK.现在直接还原.完整备份+第二次差异备份.看看第二条记录在不在.
GO
USE tempdb
--完整备份还原
RESTORE DATABASE Test FROM DISK='G:\Test.bak' WITH REPLACE,NORECOVERY
--第二次差异备份还原
RESTORE DATABASE Test FROM DISK='G:\Test_Two_Dif.bak' WITH RECOVERY
GO
USE Test
GO
SELECT FROM tb
GO
USE tempdb
GO
--删除测试数据库
DROP DATABASE Test
liangCK
关注
liangCK
liangCK
等级:Blank
2
更多勋章
#13 得分:0 回复于: 2008-12-19 10:30:02
你可以根据我的测试自己试试...
guanghui_10
关注
guanghui_10
guanghui_10
等级:Blank
#14 得分:0 回复于: 2008-12-19 10:34:57
还真没这样做过。学习了。。。。
NewCenturyNewPage
关注
NewCenturyNewPage
NewCenturyNewPage
等级:Blank
#15 得分:0 回复于: 2008-12-19 11:16:49
小梁写的测试很好!谢谢!
NewCenturyNewPage
关注
NewCenturyNewPage
NewCenturyNewPage
等级:Blank
#16 得分:0 回复于: 2008-12-19 11:35:46
还有一个疑问:
因为差异备份是建立在上次完整备份的基础上。

假设我第一次建立了一个基准的完整数据库备份test.bak,
然后我用SQL 语句在这个基准上进行了若干次修改,产生了若干个差异备份:
test_diff_00.bak;test_diff_01.bak; test_diff_02.bak

后来我又在SQL SERVER 2005的Management Studio里面使用用界面操作的方式对数据库test做了一个完整的备份,
生成一个新的完整数据库备份test_newbak.bak
往表tb插入了1条新记录。
然后我又用SQL SERVER的你上面的备份语句对test进行了1次差异备份,
生成: test_diff_03.bak

这样我如果用test.bak 结合 test_diff_03.bak 是不是就恢复不了最新的数据库了??
这种情况如何办呢???

定时器并不能阻止用户通过界面的方式对数据库test做完整的备份啊?
liangCK
关注
liangCK
liangCK
等级:Blank
2
更多勋章
#17 得分:0 回复于: 2008-12-19 11:42:42
引用 16 楼 NewCenturyNewPage 的回复:
还有一个疑问: 
因为差异备份是建立在上次完整备份的基础上。 

假设我第一次建立了一个基准的完整数据库备份test.bak, 
然后我用SQL 语句在这个基准上进行了若干次修改,产生了若干个差异备份: 
test_diff_00.bak;test_diff_01.bak; test_diff_02.bak 

后来我又在SQL SERVER 2005的Management Studio里面使用用界面操作的方式对数据库test做了一个完整的备份, 
生成一个新的完整数据库备份test_newbak.bak 
往表…

用老的完整备份+新的差异备份当然不可以..

你直接使用最新的完整备份+最新的差异备份就可以了.
NewCenturyNewPage
关注
NewCenturyNewPage
NewCenturyNewPage
等级:Blank
#18 得分:0 回复于: 2008-12-19 11:46:45
小梁:
我问这个问题的原因是想我每天对数据库做一个自动备份。
最初建立一个基准数据库备份,
然后开始一个作业,每天只做差异备份。

需要恢复的时候,用最初的基准数据库备份+具体哪一天的差异备份就可以了。

但是,如果有人在某一天又对数据库做了一个完整备份的话,
我用这个差异备份恢复就必然失败了啊。

不知道数据库每天自动备份的标准做法该怎么做呢??
liangCK
关注
liangCK
liangCK
等级:Blank
2
更多勋章
#19 得分:0 回复于: 2008-12-19 12:22:08
授予一个专用的账户对这个数据库进行备份..其它用户就不给予备份该数据库的权限..

    本站是提供个人知识管理的网络存储空间,所有内容均由用户发布,不代表本站观点。请注意甄别内容中的联系方式、诱导购买等信息,谨防诈骗。如发现有害或侵权内容,请点击一键举报。
    转藏 分享 献花(0

    0条评论

    发表

    请遵守用户 评论公约

    类似文章 更多