SQLServer恢复表级数据详解,sqlserver详解
最近几天,公司的技术维护人员频繁让我恢复数据库,因为他们总是少了where条件,导致update、delete出现了无法恢复的后果,加上那些库都是几十G。恢复起来少说也要十几分钟。为此,找了一些资料和工作总结,给出一下几个方法,用于快速恢复表,而不是库,但是切记,防范总比亡羊补牢好。
在生产环境或者开发环境,往往都有某些非常重要的表。这些表存放了核心数据。当这些表出现数据损坏时,需要尽快还原。但是,正式环境的数据库往往都是非 常大的,统计数据表明,1T的数据库还原时间接近24小时,所以因为一个表而还原一个库,不单空间,甚至时间上都是一个很大的挑战。本文介绍如何恢复单 表,而不需要恢复整个库。
现在假设一个表:TEST_TABLE。我们需要尽快恢复这个表,并且把恢复过程中对其他表和用户的影响降到最低。
SQLServer(特别是2008以后),具有很多备份及恢复功能:完整、部分、文件、差异和事务备份。而恢复模式的选择严重影响备份策略和备份类型。
下面是几个可供参考的方案,但是记住,各有好坏,应该按照实际需要选择:
方案1:恢复到一个不同的数据库:
对于小数据库来说不失为一种好的办法,用备份还原一个新的库,并把新库中的表数据同步回去。你可以做完整恢复,或者时间点恢复。但是对于大数据库,是非常耗时和耗费磁盘空间的。这个方法仅仅用于还原数据,在还原数据(就是同步数据)的时候,你要考虑触发器、外键等因素。
方案2:使用STOPAT来还原日志:
你可能想恢复最近的数据库备份,并回滚到某个时间点,即发生意外前的某个时刻。此时可以使用STOPAT子句,但是前提是必须为完整或大容量日志恢复模式。下面是例子:
RESTORE DATABASE 需要恢复的数据库 FROM 数据库备份 WITH FILE=3, NORECOVERY ; RESTORE LOG需要恢复的数据库 FROM数据库备份 WITH FILE=4, NORECOVERY, STOPAT = 'Oct 22, 2012 02:00 AM' ; RESTORE DATABASE 需要恢复的数据库 WITH RECOVERY ;
注意:这种方法的主要缺点是会覆盖掉从stopat指定时间点之后所修改的所有数据。所以要衡量好得失。
方案3:数据库快照:
创建数据库快照。当发生意外时,可以从快照中直接获取原来的数据。但是必须是在发生意外之前创建的快照。这在核心表不经常更新,特别是有规律更新时很有用。但是当表经常、不定期被更新,或者很多用户在访问时,这种方法就不可取了。当需要使用这种方法时,记得在每次更新前先创建快照。
方案4:使用视图:
你可以创建一个新的数据库,并把TEST_TABLE移动到这个库里面。当你需要恢复的时候,你只需要恢复这个非常小的数据库即可。访问源数据库的数据时,最简单的方法就是创建一个视图,选择TEST_TABLE表中所有列的所有数据。但是注意这个方法需要在创建视图前,重命名或者删除源数据库的表:
USE 需要恢复的数据库 ; GO CREATE VIEW TEST_TABLE AS SELECT * FROM 备份数据库.架构名.TEST_TABLE ; GO
使用这种方法,可以对视图使用SELECT /INSERT/UPDATE/DELETE语句,就像直接操作实体表似得。当TEST_TABLE更改时,要使用SP_REFRESHVIEW存储过程来更新元数据。
方案5:创建同义词(Synonym):
和方案4类似,把表移到另外一个数据库,然后对源数据库的这个表创建一个同义词:
USE 需要恢复的数据库 ; GO CREATE SYNONYM TEST_TABLE FOR 新数据库.架构名.TEST_TABLE ; GO
方案6:使用BCP保存数据:
你可以创建一个作业,使用BCP定期导出数据。但是这种方法的缺点和方案1类似,需要找到哪天的文件并导进去,同时要考虑触发器和外键问题。
各种方法的对比:这个方法的有点就是你不需要担心元数据更新所带来的结构变更不及时。但是这个方法的问题就是不能在DDL语句中引用同义词,或者不能在链接服务器中找到。
方法 优点 缺点
还原数据库 快且容易 适用于小库,且要注意触发器和外键等
还原日志 能指定时间点 所有时间点后的新数据会被覆盖
数据库快照 当表不是经常更新时很有用 当表并行更新时,快照容易出现问题
视图 把表的数据于库分开,没有数据丢失 元数据需要周期性更新,并要定期维护新数据库
同义词 把表的数据于库分开,没有数据丢失 在链接服务器上不能用,并要定期维护新数据库
BCP 拥有表的专用备份 需要额外的空间、还会出现触发器、外键等问题
总结:
良好的编程习惯和良好的备份机制才是解决问题的根本,以上的措施都仅仅是一个亡羊补牢的办法。可能有人说SQLServer 新版本不是有部分还原吗?我们来看看联机丛书的说明:
可以看到,其他这种方法很难还原一个表,但是当库小的时候,倒可以试试。
SQL Server数据库为何不可以恢复单表数据
比如,你备份了AdventureWorks数据库,现的你只恢复里面Vendor表数据。不幸的是,SQL Server本身并不支持这样还原,你需要从第三方提供的工具中来执行这样的任务。提供这种功能的程序都是一些SQL Server第三方备份工具。它们可以让你从备份文件中抽取或是读取单个表数据。但是这里有一点要注意是,假如你选择恢复一个完整数据库,那么你选择要恢复的数据有可能与你获取的数据不同。原因就是因为当你执行完整数据库备份时,备份文件包括数据文件和事务日志文件。有一些已经提交的事务还没有写入数据文件,在这种情况下,事务仅仅存储在事务日志中,或者部份数据存储在数据文件。当你使用第三方程序恢复所选择的单表数据时,仅仅只能从备份文件中的数据库文件中获取数据,事务日志中的新数据将会被忽略。下图显示了在备份期间没有checkpoint的备份序列。在备份开始之前,如果事务还没有被写到数据文件中,那会怎么样呢?答案是不确定,因为当备份开始后,SQL Server会自动执行checkpoint操作。当checkpoint期间,脏数据页已经被写到磁盘上了。当我们从备份文件恢复单独一个表的数据时,我们能不能认为要恢复的数据就处于备份开始处呢?这取决于备份过程。如果在备份期间没有事务在运行,那就没问题。如果这期间有事务在运行而且checkpoint也没有被触发,那也没问题。但是如果在备份期间有事务在执行,那我们恢复的数据也许就会包括备份起始时的数据,而且在备份期间数据被提交了的话,如果在备份期间发生了checkpoint而且数据也被写到了数据页,而这个数据页在checkpoint发生时没有被备份。(最后这句实在不知道怎么翻译才好,附上原文如下:If however there were transactions performed during the backup, the data we recover may include data at the beginning of the backup, and data that were committed during the backup IF checkpoints occurred during the backup AND the data was written to pages that were not yet backed up yet at the time the checkpoint occurred.)下图显示了带checkpoint的备份序列当你进行表级别的恢复之前,要先考虑一些事情。一个完整备份包括所有的数据,还有数据库所有直到备份结尾的改变。一个单独的数据文件无法映射出指定时刻数据库的状态。因此,表级别的恢复包括旧、脏数据。
sql server 2005中清除了表中数据怎恢复?
1.如果有备份 赶紧先使用日志备份备份下,然后依次还原 完整备份 差异备份(如果有) 日志备份
2.没有备份 试试使用LOG EXPLORER 还原
但是不保证能全部还原