修复发生“由于数据移动,未能继续以 NOLOCK 方式扫描”错误的数据库

SQL SERVER 2005以上的版本,使用以下方式:
USE MASTER
GO
--单用户模式
ALTER DATABASE work_yf SET SINGLE_USER
GO

--允许丢失数据修复
DBCC CHECKDB (work_yf, REPAIR_ALLOW_DATA_LOSS)
GO
--多用户模式
ALTER DATABASE work_yf SET MULTI_USER

SQL SERVER 2000,使用以下方式:

第一步:通过以下代码查询,是哪些表中出错了

DECLARE @table_name sysname

DECLARE ROY_table CURSOR FOR

SELECT name FROM sysobjects where xtype  in ('u','s')

OPEN ROY_table

FETCH NEXT FROM ROY_table INTO @table_name

WHILE @@FETCH_STATUS = 0

BEGIN

DBCC CheckTable (@table_name)

PRINT '--------------数据表'+@table_name + '的检查整理完成------------------'

FETCH NEXT FROM ROY_table INTO @table_name

END

CLOSE ROY_table

DEALLOCATE ROY_table

执行上述命名之后,会在“消息”窗口中显示如下信息:(以下信息中只有出错信息,其他正常信息已经去除)

服务器: 消息 8929,级别 16,状态 1,行 10

对象 ID 2: 在文本 ID 177078272 中发现错误,该文本的所有者是由 RID = (1:135:19) id = 661577395 and indid = 3 标识的数据记录。

服务器: 消息 8961,级别 16,状态 1,行 10

表错误: 对象 ID 2。text、ntext 或 image 节点(位于页 (1:66),槽 2,文本 ID 177078272)与该节点位于页 (1:284),
槽 6 处的引用不匹配。

'sysindexes' 的 DBCC 结果。

对象 'sysindexes' 有 304 行,这些行位于 14 页中。

CHECKTABLE 发现了 0 个分配错误和 2 个一致性错误(在表 'sysindexes' 中,该表的对象 ID 为 2)。

通过上面的提示信息,找到出错的索引或统计信息

--------------数据表sysindexes的检查整理完成------------------

服务器: 消息 8936,级别 16,状态 1,行 10

表错误: 对象 ID 709577566,索引 ID 1。B 树链的链接不匹配。(1:2203)->next = (1:176),但 (1:176)->Prev = (1:2045)。

服务器: 消息 8977,级别 16,状态 1,行 10

表错误: 对象 ID 709577566,索引 ID 1。未遇到页 (1:2203) 的父节点。

'PDE_LIST_ORG' 的 DBCC 结果。

对象 'PDE_LIST_ORG' 有 216 行,这些行位于 11 页中。

CHECKTABLE 发现了 0 个分配错误和 2 个一致性错误(在表 'PDE_LIST_ORG' 中,该表的对象 ID 为 709577566)。

repair_rebuild 是最低的修复级别(对于由 DBCC CHECKTABLE (work_yf.dbo.PDE_LIST_ORG ) 发现的错误而言)。

--------------数据表PDE_LIST_ORG的检查整理完成------------------

服务器: 消息 8978,级别 16,状态 1,行 10

表错误: 对象 ID 725577623,索引 ID 1。页 (1:3891) 缺少上一页 (1:3892) 对它的引用。可能是因为链的链接有问题。

服务器: 消息 8976,级别 16,状态 1,行 10

表错误: 对象 ID 725577623,索引 ID 1。在扫描操作中未发现页 (1:3892),而其父代 (1:2198) 和上一页 (1:3889) 指向了该页。
请检查先前的错误。

'PDE_LIST_ORG_HISTROY' 的 DBCC 结果。

对象 'PDE_LIST_ORG_HISTROY' 有 16755 行,这些行位于 489 页中。

CHECKTABLE 发现了 0 个分配错误和 2 个一致性错误(在表 'PDE_LIST_ORG_HISTROY' 中,该表的对象 ID 为 725577623)。

repair_rebuild 是最低的修复级别(对于由 DBCC CHECKTABLE (work_yf.dbo.PDE_LIST_ORG_HISTROY ) 发现的错误而言)。

--------------数据表PDE_LIST_ORG_HISTROY的检查整理完成------------------
第二步,进行分析,除了上面的斜体字部分,需要注意,其他都很清楚,就是两张业务表发生了错误。

而斜体字部分是指一张系统表sysindexes,需要进一步查询是哪些索引出错了。
使用以下语句检查是哪些索引出现了问题,原来是_WA_Sys_STATUS_276EDEB3出错是问题。
SELECT *  FROM SYSINDEXES WHERE  id = 661577395 and indid = 3

select * from sysobjects where id = 661577395
第三步,进行修得操作。具体操作方法如下:


--方法如下:

--1. 先停掉数据库服务器,把出问题的数据库(例如:work_yf)的.mdf与.ldf文件备份到备份目录中。

--2.我们使用默认方式建立一个供恢复使用的数据库(如work_yf)。可以在SQL   Server   Enterprise   Manager里面建立。  

--3.停掉数据库服务器。  

--4.将刚才生成的数据库的日志文件work_yf_log.ldf删除,用要修复的数据库mdf文件覆盖刚才生成的数据库数据文件work_yf_data.mdf。  

--5.启动数据库服务器。此时会看到数据库work_yf的状态为“置疑”。这时候不能对此数据库进行任何操作。  

--6.执行以下代码
use   master
go

exec sp_configure   'allow updates',1
go

reconfigure   with   override
go 
--7.设置work_yf为紧急修复模式  
update sysdatabases set status=-32768 where dbid=DB_ID('work_yf')  
go
 此时可以在SQL   Server   Enterprise   Manager里面看到该数据库处于“只读\置疑\脱机\紧急模式”可以看到数据库里面的表,
但是仅仅有系统表  

--8.下面执行恢复操作,重建数据库日志文件  
dbcc rebuild_log('work_yf','D:\Program Files\Microsoft SQL Server\MSSQL\Data\work_yf_log.ldf')
go
执行过程中,如果遇到下列提示信息:  
服务器:   消息   5030,级别   16,状态   1,行   1  
未能排它地锁定数据库以执行该操作。  
DBCC   执行完毕。如果   DBCC   输出了错误信息,请与系统管理员联系。  

 说明您的其他程序正在使用该数据库,如果刚才使用SQL  Server  Enterprise  Manager打开了work_yf库的系统表, 那么退出SQL   Server   Enterprise   Manager就可以了。  

正确执行完成的提示应该类似于:

警告:   数据库   'work_yf'   的日志已重建。已失去事务的一致性。应运行DBCC CHECKDB以验证物理一致性。
   将必须重置数据库选项,并且可能需要删除多余的日志文件。  

DBCC   执行完毕。如果   DBCC   输出了错误信息,请与系统管理员联系。  
此时打开在SQL   Server   Enterprise   Manager里面会看到数据库的状态为“只供DBO使用”。此时可以访问数据库里面的用户表了。  

--9 设置为单用户状态
exec sp_dboption 'work_yf','dbo use only','false'
GO

exec sp_dboption 'work_yf', 'single user', 'true'
go

reconfigure   with   override  
--10 修复表,具体要修复哪些表,请在执行DBCC CheckTable (表名) ,自行检查。我在这里使用了"重建索引并修复(REPAIR_REBUILD)"的选项。
一共有三个选项:

--1) 快速修复          REPAIR_FAST

--2) 重建索引并修复     REPAIR_REBUILD

--3) 允许丢失数据修复    REPAIR_ALLOW_DATA_LOSS
use work_yf
GO

DBCC CheckTable (PDE_LIST_ORG_HISTROY,REPAIR_REBUILD)
GO

DBCC CheckTable (PDE_LIST_ORG,REPAIR_REBUILD)
GO

DBCC CheckTable (PDE_HEAD,REPAIR_REBUILD)
GO

 刚才我在检查的时候,发现一个_WA_Sys_STATUS_276EDEB3也出错了,这是SQL SERVER自动建立的统计信息, 所以需要进行删除,然后在进行修复。

DROP STATISTICS PDE_HEAD._WA_Sys_STATUS_276EDEB3
GO

DBCC CheckTable (SYSINDEXES,REPAIR_REBUILD)
GO

--11.验证数据库一致性(可省略)  
 use   master
 go

DBCC CheckDB (work_yf) 
go

 一般执行结果如下:

CHECKDB   发现了   0   个分配错误和   0   个一致性错误(在数据库   'work_yf'   中)。 

DBCC   执行完毕。如果   DBCC   输出了错误信息,请与系统管理员联系。

--12.设置数据库为正常状态  
exec sp_dboption 'work_yf', 'single user', 'false'
go

exec sp_dboption 'work_yf','dbo use only','false'
go
如果没有出错,那么恭喜,现在就可以正常的使用恢复后的数据库啦。  

--13.最后一步,我们要将步骤E中设置的“允许对系统目录直接修改”一项恢复。因为平时直接操作系统表是一件比较危险的事情。
exec sp_configure   'allow updates',0
go

reconfigure   with   override
go 

 PS:这文章仅供参考,实际操作中需谨慎。

有空我实操后补充相关内容。

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值