数据库备份
-- 1.1 --------------------------------------------------
--
避免数据丢失
/*
避免数据丢失是
DBA
的最关键的任务之一。
导致数据丢失的原因有:
意外或恶意的使用
DELETE
、
UPDATE
语句,如没有使用
WHERE
字句
具有破坏性的病毒
硬件损坏
自然灾害,如火灾,地震等
盗窃
如果用户拥有适当的备份策略,就能够以最低的生产时间代价恢复数据,并大大降低永久性数据丢失的机会。
对待备份如同对待保险策略一样,用户需要问自己:‘我愿意支付多少?我可以接受多大的损失?’。
越少的数据丢失,越短的恢复时间意味着备份的成本会很高。
用户不能完全避免数据丢失,在规划备份策略的时候,需要考虑:
可以接受的停机时间
可以接受的数据损失量
定期备份:
若系统处于
OLTP
环境中,需要经常备份数据库
若数据更改较少,则不需经常备份数据库
可以使用
SQL Server Agent
,使得备份工作自动化
进行数据库备份的时候不会影响用户继续使用数据库,但会损失一些性能。
作为
DBA
,我们的目标是:
最小化数据丢失
以最低的生产时间代价还原数据
*/
-- 1.2 --------------------------------------------------
--
数据库还原模型
/*
可以为
SQL Server
中的每个数据库选择三种恢复模型中的一种,以确定如何备份数据以及能承受何种程度的数据丢失。
下面是可以选择的三种恢复模型:
简单还原模型
使用简单还原模型可以将数据库恢复到上次备份的即时点。不过,无法将数据库还原到故障点或特定的即时点。
可以将数据库恢复到最新的全备份或是差异备份。
这种还原模型对日志所需的存储空间最小。
不能使用日志备份。
大容量日志记录还原模型
可以使用全备份、差异备份和日志备份。
对某些大规模或大容量复制操作,如
create index,
大批量数据导入,提供最佳性能和最少的日志使用空间,
因为对以上操作记录的是操作后的结果,所以产生的日志更小,因此也就不支持时间点还原。
完全还原模型
可以使用全备份、差异备份和日志备份。
日志记录了对数据库进行的全部更改,除了故障期间发生的事务之外,能够还原全部数据。
可以将数据库还原到即时点。
产生的日志文件较大,有一定的性能代价。
更改数据库还原模型
ALTER DATABASE database_name SET RECOVERY FULL|SIMPLE|BULK_LOGGED
*/
-- 1.3 --------------------------------------------------
--
备份数据库的时机
/*
--
备份系统数据库
系统数据库存储
SQL Server
和全部数据库的重要数据。因此,应当有规律地备份系统数据库,特别是在修改它们之后。
修改
master
数据库之后
master
数据库包含了
SQL Server
中全部数据库的相关信息。
当执行某些语句的时候,
SQL Server
会修改
master
数据库中:
使用
create|alter|drop database
来创建,修改,删除数据库时
使用
sp_addlinkedserver
来增添加链接服务器
使用
sp_addmessage
来添加错误消息
修改
msdb
、
model
数据库之后
--
备份用户数据库
创建数据库之后
如果没有全备份就无法恢复日志备份,所以要在创建数据库后执行全备份作为备份的基线
创建索引之后
不是必须的,但是可以在恢复过程中节省时间
清理事务日志之后
当使用
backup log with truncate_only
或
backup log with no_log
语句清理事务日志之后,
日志中不再包含数据库活动记录,不能用来恢复数据库,因此要马上备份数据库
--
备份过程中受到限制的活动
创建或修改数据库
执行自动增长操作
创建索引
执行无日志操作
收缩数据库
*/
-- 1.4 --------------------------------------------------
--
执行数据库备份
/*
--
备份到设备
如果希望重复利用所创建的备份文件,或者使得数据库备份任务自动化,可以考虑创建备份设备。
使用
sp_addumpdevice
,可以在磁带或磁盘中创建备份设备,或者将数据定向到命名管道。
sp_addumpdevice
@devtype = 'device_type', --
备份设备的类型,可以是
DISK|TAPE|PIPE
@logicalname = 'logical_name', --
备份设备的逻辑名称,该逻辑名称用于
BACKUP
和
RESTORE
语句中
@physicalname = 'physical_name' --
备份设备的物理名称。必须遵照操作系统文件名称的规则或者网络设备的通用命名规则,并且必须包括完整的路径
--
利用
BACKUP
语句执行备份
BACKUP DATABASE database_name TO backup_device|backup_file
*/
1.
在硬盘中创建备份设备
myDevice
,从企业管理器中查看:管理
->
备份
sp_addumpdevice 'disk','myDevice','d:\myDevice.bak'
2.
将数据库
Test
备份至设备
myDevice
,查看结果
backup database Test to myDevice
--
备份到文件
/*
不准备重复利用备份文件,或测试自动化备份的操作时,可以考虑创建临时备份文件。
需要使用
BACKUP DATABASE
语句来创建备份文件。
*/
1.
使用
BACKUP DATABASE
语句,把数据库
Test
备份至磁盘文件
'd:\test.bak'
backup database Test to disk='d:\test.bak'
2.
从查询分析器中查看备份文件中的信息
restore headeronly from disk='d:\test.bak'
3.
再次向磁盘文件
'd:\test.bak'
中写入数据库
Test
的备份,查看结果
4.
可以指定
WITH INIT
选项来重写备份文件,查看结果
backup database Test to disk='d:\test.bak' with init
--
备份设备和备份文件的区别
/*
可以在没有创建数据库备份的时候,先创建备份设备,以备后用;而创建备份文件的时候,必须同时写入数据库备份。
备份设备中的信息可以从企业管理器或查询分析器中读取,而备份文件中的信息只能通过查询分析器来读取。
*/
-- 1.5 --------------------------------------------------
--
备份到多个备份文件
/*
SQL Server
能并行地向多个备份文件进行写操作,以此减少备份和恢复的时间。
BACKUP DATABASE database_name TO device_1,device_2 WITH MEDIANAME = media_name
*/
sp_addumpdevice 'disk','Device_1','d:\Device_1.bak'
Go
sp_addumpdevice 'disk','Device_2','d:\Device_2.bak'
Go
sp_addumpdevice 'disk','Device_3','d:\Device_3.bak'
Go
backup database Test To device_1,device_2,device_3 with medianame = 'MediaSet_Test_123'
restore labelonly from device_1
restore labelonly from device_2
restore labelonly from device_3
/*
当使用多个文件来存储备份的时候,需要考虑以下情况:
单个备份媒体中的所有设备必须是同种类型的媒体(磁盘或磁带)
可以组合使用备份设备和备份文件
如果将某个文件定义为备份集成员,那么备份时必须一起使用这些文件
除非用户重新格式化备份集中的文件,否则不能将单个备份集成员应用于备份操作中
如果重新格式化了备份集的某个成员,那么备份集其他成员所包含的数据就是无效的,不能再被使用
*/
backup database msdb to device_1
backup database msdb to device_1 with format,init restore headeronly from device_1
restore labelonly from device_1
-- 1.6 --------------------------------------------------
--
数据库备份类型
/*
全备份
备份数据库中所有的数据页,可以直接用来进行恢复操作。
系统出现故障时,全备份可以作为还原基线,是其它两种备份的基础。
BACKUP DATABASE database_name TO device
差异备份
备份数据库中,自最近一次全备份以来,数据库中的更改部分。
只有在执行全备份的基础之上,才可以执行差异备份。
备份集更小,节省备份和还原的时间。
BACKUP DATABASE database_name TO device WITH DIFFERENTIAL
日志备份
日志备份用来记录最近一次备份之后,到当前日志备份的全部数据库更改。
需要完全数据库备份。
在使用简单还原模型的时候,不能进行日志备份。
BACKUP LOG database_name TO device
使用
NO_TRUNCATE
选项
数据库出现损坏或丢失的现象,用户应当利用
NO_TRUNCATE
选项备份事务日志
即时在无法访问数据库的情况下,也可以保存完整事务日志(自最近的
BACKUP LOG
语句以来发生的每件事情)
允许数据恢复到系统出现故障的那一时刻
恢复数据库过程的最后,可以应用
NO_TRUNCATE
选项所创建的事务日志来恢复数据库
BACKUP LOG database_name TO device WITH NO_TRUNCATE
数据文件或文件组备份
备份数据库中的某个数据文件或文件组
需要完全数据库备份
使用的时候需要配合日志备份,使得还原后的某个数据文件与其他数据文件保持一致
针对
VLDB
BACKUP DATABASE database_name FILE = file_name TO device
清理事务日志
在事务日志满的时候,数据库就无法做任何改动,因此需要清理事务日志
清理事务日志之后,应当立即备份数据库
BACKUP LOG database_name WITH TRUNCATE_ONLY | NO_LOG
*/
--
练习
-------------------------------------------------
-- 1
--
答案
-------------------------------------------------
-- 1
-- 2072_06 **********************************************
--
数据库恢复
-- 1.7 --------------------------------------------------
--
恢复前的准备工作
/*
为了确认是否正在恢复想要的数据和对象,以及备份中是否包含有效信息,应当验证备份。
RESTORE HEADERONLY FROM device|file --
获得备份文件的头部信息
RESTORE FILELISTONLY FROM device|file --
获得备份中原始数据文件和日志文件的相关信息
RESTORE LABELONLY FROM device|file --
获得备份媒体的有关信息
RESTORE VERIFYONLY FROM device|file --
验证备份集是否完整以及是否可读
*/
-- 1.8 --------------------------------------------------
--
从不同备份策略中恢复数据库
--
全备份
/*
每天下午
18:00
执行全备份
适用于:
数据库较小,备份所需的时间是合理的
开发数据库,非生产环将中数据库
两次全备份间发生故障时,丢失的数据量是可以接受的
只需恢复最近的一次全备份
F F | F
|
SUN 18:00 MON 18:00 | TUE 18:00
|
Fail 13:00
*/
1. backup database Test to device -- SUN 18:00
2. backup database Test to device -- MON 18:00
3. system failure occurred -- TUE 13:00
4. restore database Test from device with file = 2 --
恢复
MON 18:00
的全备份
--
差异备份
/*
周日下午
18:00
执行全备份
其余每天下午
18:00
执行差异备份
适用于:
数据库较大,全备份执行时间过长,差异备份所需时间是合理的
首先恢复最近的全备份,然后恢复全备份以来的最近一次差异备份
F D D | D
|
SUN 18:00 MON 18:00 TUE 18:00 | WED 18:00
|
Fail 13:00
*/
1. backup database Test to device -- SUN 18:00
2. backup database Test to device with differential -- MON 18:00
3. backup database Test to device with differential -- TUE 18:00
4. system failure occurred -- WED 13:00
5. restore database Test from device with file = 1,norecovery --
恢复
SUN 18:00
的全备份
--
指定
norecovery
选项,使得本次恢复后,数据库不可用,等待下一个备份的恢复
--
默认
recovery
,说明恢复已结束,允许访问数据库
6. restore database Test from device with file = 3,recovery --
恢复
TUE 18:00
的差异备份
--
日志备份
/*
每天早上
0:00
执行全备份,之后每三小时执行日志备份
适用于:
数据库较大,全备份执行时间较长,日至备份所需时间是合理的
发生故障时,首先尝试备份故障前最近一次日志备份以来的未备份的日志(可能成功也可能失败)
恢复时,首先恢复最近一次的全备份,然后依次逐个恢复日志备份
F L L | L
|
MON 00:00 MON 03:00 MON 06:00 | MON 09:00
|
Fail 08:00
*/
1. backup database Test to device -- MON 00:00
2. backup log Test to device -- MON 03:00
3. backup log Test to device -- MON 06:00
4. system failure occurred -- MON 08:00
5. backup log Test to device with no_truncate -- MON 08:00
6. restore database Test from device with file = 1,norecovery --
恢复
MON 00:00
的全备份
7. restore log Test from device with file = 2,norecovery --
恢复
MON 03:00
的日志备份
8. restore log Test from device with file = 3,norecovery --
恢复
MON 06:00
的日志备份
9. restore log Test from device with file = 4,recovery --
恢复
MON 08:00
的日志备份
--
数据文件备份
/*
数据库包含
3
个数据文件
每周的周日凌晨
00:00
进行数据库全备份,其他六天轮流备份
3
个数据文件,每天的中午
12:00
和下午
18:00
进行日志备份
适用于:
VLDB
超大的数据库,全备份执行时间长的不可接受
与事务日志备份结合,可以节省时间,需要轮流备份数据文件
发生故障时,首先尝试备份故障前最近一次日志备份以来的未备份的日志(可能成功也可能失败)
恢复时,仅恢复损坏的那个数据文件的最近的备份,再依次恢复之后的日志备份
F L L DF_1 L L DF_2 L L DF_3 | L
|
SUN 00:00 SUN 12:00 SUN 18:00 MON 00:00 MON 12:00 MON 18:00 TUE 00:00 TUE 12:00 TUE 18:00 WED 00:00 | WED 12:00
|
DF_2 Fail 08:00
*/
use master
Go
drop database Test
Go
create database Test
on
primary
(
name = DF_1,
filename = 'd:\Test_DF_1.mdf',
size = 1,
maxsize = 10,
filegrowth = 5
),
(
name = DF_2,
filename = 'd:\Test_DF_2.ndf',
size = 1,
maxsize = 10,
filegrowth = 5
),
(
name = DF_3,
filename = 'd:\Test_DF_3.ndf',
size = 1,
maxsize = 10,
filegrowth = 5
)
log on
(
name = 'Test_Log',
filename = 'd:\Test_Log.ldf',
size = 1,
maxsize = 10,
filegrowth = 5
)
Go
1. backup database Test to device -- SUN 00:00
2. backup log Test to device -- SUM 12:00
3. backup log Test to device -- SUM 18:00
4. backup database Test file = 'DF_1' to device -- MON 00:00
5. backup log Test to device -- MON 12:00
6. backup log Test to device -- MON 18:00
7. backup database Test file = 'DF_2' to device -- TUE 00:00
8. backup log Test to device -- TUE 12:00
9. backup log Test to device -- TUE 18:00
10. backup database Test file = 'DF_3' to device -- WED 00:00
12. system failure occurred -- WED 08:00
13. backup log Test to device with no_truncate -- WED 08:00
14. restore database Test file = 'DF_2' from device with file = 7,norecovery --
恢复
TUE 00:00
的
DF_2
数据文件备份
15. restore log Test from device with file = 8,norecovery --
恢复
TUE 12:00
的日志备份
16. restore log Test from device with file = 9,norecovery --
恢复
TUE 18:00
的日志备份
17. restore log Test from device with file = 11,recovery --
恢复
WED 08:00
的日志备份