4.9 设置数据库选项
我们可以设置很多的数据库选项或属性来控制某个数据库的特定行为。某些选项必须设置为ON或OFF,另一些选项必需从一组可选值中取值,其他的选项只需指定它们的名字即可启用。默认情况下,所有取值为ON或OFF的选项的初始值为OFF,除非model数据库中该选项是设置为ON的。在model数据库中的一个选项取值发生变化后创建的所有数据库在该选项上将会和model数据库取相同的值。我们可以通过SQL Server Management Studio很容易地修改一些选项的值。我们可以直接使用ALTER DATABASE命令来设置所有属性的值(也可以使用sp_dboption系统存储过程来设置一些选项,不过这个存储过程只是为了向后兼容而提供的,并且已经计划从将来版本的SQL Server中移除该存储过程)。
通过查看sys.databases目录视图我们会发现所有已经设置的选项值。该过程还能返回其他一些有用的信息,例如数据库ID、创建日期和数据库所有者的安全ID(Security ID,SID)。下面的查询从sys.databases中返回一些最重要列,这些列中的信息是针对一个新安装的SQL Server默认实例上存在的四个数据库的。
SELECT name, database_id, suser_sname(owner_sid) as owner , |
该查询的输出如下:
|
name |
data |
owner |
create_date |
user_ |
state_desc |
|
------ |
------- |
----- |
----------------------- |
----------- |
---------- |
|
master |
1 |
sa |
2003-04-08 09:13:36.390 |
MULTI_USER |
ONLINE |
|
tempdb |
2 |
sa |
2006-05-27 12:02:35.327 |
MULTI_USER |
ONLINE |
|
model |
3 |
sa |
2003-04-08 09:13:36.390 |
MULTI_USER |
ONLINE |
|
msdb |
4 |
sa |
2005-10-14 01:54:05.240 |
MULTI_USER |
ONLINE |
sys.databases视图实际上同时包含了user_access和state信息的数值和名字。从sys.databases选择所有的列将会使我们看到user_access_desc的值MULTI_USER有一个对应的user_access值为 0,并且state_desc的值ONLINE有一个对应的state值为0。联机丛书中有一个关于sys.databases视图中各列的数值和名称关系的完整列表。上面这些仅仅是显示在sys.databases视图中的众多数据库选项中两个。数据库选项的完整列表可以分为七大类:状态选项、游标选项、自动选项、参数化选项、SQL选项、数据库恢复选项和外部访问选项。还有一些是针对SQL Server使用的一些特殊技术的选项,包括数据库镜像、Service Broker活动和快照隔离。一些选项(特别是SQL选项)有着对应的SET选项可以为某个特别的连接而打开或关闭。
需要注意的是ODBC和OLE DB驱动程序在默认情况下会打开很多这种SET选项,所以应用程序会表现得好像相应的数据库选项已经被设置了一样。
下面是这些选项的一个列表,按照类别列出。在单行中列出的各个选项和用垂直条(|)分开的各个值是互相排斥的。
状态选项
|
游标选项
CURSOR_CLOSE_ON_COMMIT { ON | OFF } |
自动选项
|
参数化选项
|
数据库恢复选项
|
外部访问选项
DB_CHAINING { ON | OFF } |
数据库镜像选项
|
快照隔离选项
|
状态选项
状态选项控制着谁能够使用数据库和进行哪些操作。可用性有三个方面:用户访问状态决定了哪些用户能够使用该数据库;状态信息决定了一个数据库是否对所有的用户可用;可更新能力状态决定了在一个数据库上能够进行哪些操作。我们可以通过使用ALTER DATABASE命令启用数据库中的一些选项来控制上面的各个方面。
这些状态选项都不使用关键词ON和OFF来控制状态值。
单用户|限制用户|多用户
这三个选项描述了一个数据库的用户访问属性。这些选项是相互排斥的;选择一个选项的同时不能选择其他选项。要对数据库设置一个这种选项,只需使用选项的名称。例如,可以使用下面的代码将AdventureWorks数据库设置为单用户(single-user)模式:
ALTER DATABASE AdventureWorks SET SINGLE_USER;
一个在单用户(SINGLE_USER)模式下的数据库一次只能有一个连接。在限制用户(RESTRICTED_USER)模式下的数据库只能接受被认为是“合格”用户的连接——这些用户属于dbcreator或sysadmin服务器角色,或者是那个数据库的db_owner角色的成员。数据库在默认时处于多用户模式(MULTIPLE_USER),这意味着所有具有一个数据库中有效用户名的用户都可以连接该数据库。如果我们试图将数据的状态改变到一个与当前情况不相容的状态——例如,在有多个连接存在的情况下试图将数据库设置为单用户模式,这时SQL Server的行为由我们所指定的“结束”(TERMINATION)选项决定。稍后我们会对该“结束”选项进行讨论。
为了确定一个数据库中设置了哪一个用户访问值,我们可以检查sys.databases目录视图,如下所示:
SELECT USER_ACCESS_DESC FROM sys.databases |
该查询将会返回这些值之一:MULTI_USER、SINGLE_USER或RESTRICTED_USER。
离线|在线|紧急
我们可以使用这三个选项来描述一个数据库的状态。这些选项是互相排斥的。一个数据库默认是ONLINE的。与用户访问选项一样,当我们使用ALTER DATABASE来将数据库设置为这些模式之一时,不需要为其指定一个ON或者OFF值——我们只需要使用该选项的名字即可。当一个数据库被设置为离线(OFFLINE)时,它会被正常地关闭并被标记为离线,数据的所有快照也都会被自动删除。当一个数据库在离线状态时它是不能被修改的。当一个数据库中有任何连接时,它是不能被设置为离线的。在这种情况下SQL Server是等待其他连接终止还是产生一条错误信息取决于指定的结束(TERMINATION)选项。
下面的示例代码显示了如何将一个数据库的状态值设置为OFFLINE和如何确定一个数据库的状态:
ALTER DATABASE AdventureWorks SET OFFLINE; |
一个数据库能够显式地设置为紧急(EMERGENCY)模式,并且在讨论一些不能设置的数据库状态值之后将会解释为什么我们可能希望那样做。
如前面的查询所示,我们可以通过检查sys.databases视图的state_desc列来确定一个数据库的当前状态。此列可以返回除OFFLINE、ONLINE和EMERGENRCY以外的状态值,但是那些值不能通过ALTER DATABASE命令直接进行设置。一个数据库处于从备份还原的过程中时会具有还原中(RESTORING)状态值。在SQL Server重新启动期间数据库会具有恢复中(RECOVERING)状态值。还原进程一次只能在一个数据库上进行,并且一个数据库会保持恢复中(RECOVERING)状态值直到SQL Server完成该数据库的还原。如果由于某种原因,恢复进程无法完成(很有可能是由于数据库的一个或多个日志文件不可用或不可读),SQL Server会给该数据库一个恢复中断(RECOVERY_PENDING)的状态值。如果SQL Server在回滚恢复过程中用完了日志或数据空间,或者如果SQL Server在启动过程的某个部分用完了锁或内存,数据库也会被置为恢复中断(RECOVERY_PENDING)模式。我们会在第5章中对回滚恢复和启动恢复的不同进行更多讨论。
如果所有需要的资源包括日志文件都可获得,但是在恢复期间探测到了故障,数据库可能会被设置为置疑(SUSPECT)状态。这时我们可以通过查看sys.databases视图的state_desc列来确定数据库的状态值。当一个数据库处于置疑(SUSPECT)状态时它是完全不可用的,并且即使我们运行sp_helpdb,也无法看到该数据库。然而,我们可以查看一个置疑数据库的数据库属性(DATABASEPROPERTY)的值,并从sys.databases视图来查看其状态值。在很多情况下,可以通过将一个置疑的数据库设置到紧急(EMERGERCY)模式来使得该数据库能够进行只读操作。如果确实丢失了一个数据库的一个或多个日志文件,紧急模式允许我们在将数据复制到一个新的位置之后访问数据。当我们将一个数据库从恢复中断(RECOVERY_PENDING)模式转换到紧急模式时,SQL Server关闭该数据库,然后使用一个允许它跳过恢复过程的特殊的标志位重新启动该数据库。跳过恢复过程意味着会出现一些在逻辑上或物理上不一致的数据——丢失索引行、损坏的页面链接或不正确的元数据指针。我们虽然承认数据也许是不一致的,但是不管怎样还是希望在访问数据库的情况下,可以通过专门将数据库设置到紧急模式来读取数据。
紧急模式修复
我们可以在紧急模式下运行DBCC CHECKDB命令,并且当指定REPAIR_ALLOW_ DATA_LOSS选项时,SQL Server能够在数据库上进行一些专门的修复,这有可能使通常无法恢复的数据库变得在物理上一致,并且能够重新上线。这些修复应该作为我们最后的手段,在无法从备份中还原数据库时才考虑使用。
当数据库被设置为紧急模式时,该数据库被内部地设置为只读(READ_ONLY),日志被禁用了,并且对该数据库的访问也仅限于sysadmin角色的成员。然而,我们从sys.databases系统表中看到的数据库的属性不会反映这些限制。
当数据库处于紧急模式并且运行带REPAIR_ALLOW_DATALOSS从句的DBCC CHECKDB时,会进行下面的操作:
为了增加数据恢复的概率,DBCC CHECKDB会使用由于I/O或校验和(checksum)错误已经被标为无法访问的页面,就好像这些错误还没有发生一样。
DBCC CHECKDB会尝试使用常规的基于日志的恢复技术来恢复数据库。
如果数据库恢复没有成功,会重建事务日志。重建事务日志也许会导致事务一致性被破坏。
如果DBCC CHECKDB命令成功了,那么这个数据库会处于物理上一致的状态,并且这个数据库的状态会被设置为ONLINE。然而,该数据库也许含有一个或更多事务的或逻辑的不连续处。这时我们可以考虑运行DBCC CHECKCONSTRAINTS来找出所有的业务逻辑方面的错误,并且马上备份该数据库。
如果DBCC CHECKDB命令失败了,那么该数据库就无法修复了。
在某些情况下,紧急模式是不可能的,特别是当与空间分配有关的一些元数据(数据库启动时需要这些数据时)丢失或损坏的时候。
我们可以尝试将一个紧急模式下的数据库设置为在线(ONLINE)模式(例如,当丢失的文件已经重新可用时),SQL Server将会试图在该数据库上运行恢复。如果到在线(ONLINE)模式的转变无法完成,那么数据库或者停留在恢复中断(RECOVERY_ PENDING)状态,或者停留在置疑(SUSPECT)状态,就像我们首次启动SQL Server实例并尝试恢复数据库时一样。再次强调一下,我们可以通过将处于恢复中断(RECOVERY_PENDING)状态的数据库切换到紧急模式来使得数据能够被读取。
在一台测试服务器上测试一个数据库的紧急状态值相对容易。我们可以使用三个单词的命令CREATE DATABASE TESTDB来创建一个简单的数据库,然后停止SQL Server实例并重新命名(或删除)日志文件。当我们重新启动该实例时,检查该新数据库的状态:
SELECT name, database_id, user_access_desc, state_desc |
state_desc列应该会显示RECOVERY_PENDING,这时我们可以将它切换到紧急(EMERGENCY)模式:
ALTER DATABASE testdb SET EMERGENCY;
虽然这时并没有事务日志,但是数据库将允许读取数据。无论我们使用何种方式来尝试更新数据,都会收到下面的错误:
|
如果将数据库的状态切换回在线(ONLINE),我们会收到一个指出无法进行恢复的错误,并且数据库将被重新设置为恢复中断(RECOVERY_PENDING)模式。前面提到过,在紧急模式下运行带repair选项的DBCC CHECKDB命令能够使可以修复的数据库重新上线。
只读 | 读写
这些选项描述了一个数据库的可更新性。这些选项是互斥的。一个数据库在默认情况下是读写的(READ_WRITE)。与用户访问选项一样,当使用ALTER DATABASE命令将一个数据库设置为这些模式之一时,我们不用指定ON或OFF值,只需使用该选项的名字即可。当该数据库处于读写模式时,任何有着合适权限的用户都能够执行数据修改操作。在只读模式,不能执行插入(INSERT)、更新(UPDATE)和删除(DELETE)操作。另外,因为当一个数据库处于只读模式时不能进行任何修改操作,所以数据库重新启动时不会在该数据库上运行自动恢复,并且所有的SELECT操作中都不需要获得任何锁。在只读模式下收缩数据库是不可能的。
当存在任何到一个数据库的连接时,该数据库是不可能设置为只读模式的。SQL Server是等待其他连接结束还是产生一条错误信息,取决于指定的结束(TERMINATION)选项。
下面的代码显示了如果将一个数据库的可更新性设置为只读(READ_ONLY)及如何确定一个数据库的可更新性:
ALTER DATABASE AdventureWorks SET READ_ONLY; |
当数据库启用了只读选项,is_read_only列将会返回1;否则对一个读写的数据库,它会返回0。
结束(Termination)选项
刚刚提到过当一个数据库正在使用或正在被不合格的用户使用时,有几个状态选项无法设置。这时我们可以在ALTER DATABASE命令中使用一个结束(termination)选项指定SQL Server如何来处理这种情况。我们可以指定SQL Server等待情况发生变化,或者产生一条错误信息,或者结束不合格用户的连接。
结束(termination)选项决定了SQL Server在以下情况中的行为:
当我们尝试切换一个数据库到单用户(SINGLE_USER)模式,但该数据库有多于一个的当前连接时。
当我们尝试切换一个数据库到限制用户(RESTRICTED_USER)模式,但该数据库当前有不合格的用户连接时。
当我们尝试切换数据库到离线(OFFLINE)状态,但是尚有当前连接时。
当我们尝试切换数据库到只读(READ_ONLY)状态,但是尚有当前连接时。
SQL Server在这些情形下的默认行为是无限期等待。下面的TERMINATION选项会改变这种行为:
ROLLBACK AFTER integer [SECONDS] 这个选项会使SQL Server先等待指定的秒数,然后中断不合格的连接。不完整的事务会被回滚。当切换到单用户(SINGLE_USER)模式时,除了发出ALTER DATABASE语句的连接,所有的连接都被当作不合格的连接。当切换到限制用户(RESTRICT_USER)模式时,不合格的连接不仅包括那些非db_owner固定数据库角色成员的连接,还包括那些非dbcreator且非sysadmin固定服务器角色成员的连接。
ROLLBACK IMMEDIATE 这个选项马上就中断不合格的连接。所有尚未完成的事务都会被回滚。要注意的是也许连接被马上中断,回滚却需要一些时间来完成。事务所有的工作都必须被撤销,所以对某些特定的操作,例如一个对数百万行数据进行更新的批处理操作,或者对一个大型索引的重建操作,我们可能需要等待很久。这里的不合格连接与前面所描述的不合格连接相同。
NO_WAIT 该选项会使得SQL Server在尝试改变数据库状态之前检查连接,并且当某些连接存在时该选项会导致ALTER DATABASE语句失败。如果数据库被设置为SINGLE_USER模式,当存在任何其他连接时ALTER DATABASE语句都会失败。如果是切换到限制用户模式,当存在任何不合格用户的连接时ALTER DATABASE语句都会失败。
下面的命令将AdventureWorks数据库的用户访问选项切换到单用户(SINGLE_USER)模式,并且当存在任何其他到AdventureWorks数据库的连接时都会产生一条错误信息:
ALTER DATABASE AdventureWorks SET SINGLE_VSER WITH NO_WAIT;
游标(CURSOR)选项
游标选项控制着服务器端游标的行为,服务器端游标的定义使用下面的用来定义和操纵游标的T-SQL命令:DECLARE、OPEN、FETCH、CLOSE和DEALLOCATE。T-SQL游标在《Microsoft SQL Server 2005技术内幕:T-SQL程序设计》一书中有详细讨论。
CURSOR_CLOSE_ON_COMMIT{ON|OFF} 如果该选项设置为ON,那么当一个事务被提交或被回滚时所有打开的游标都会被关闭(遵守SQL-92标准)。如果OFF(默认值)被指定,那么在事务提交后游标仍然保持开放。回滚一个事务会关闭除了被定义为INSENSITIVE或STATIC之外的所有游标。
CURSOR_DEFAULT {LOCAL|GLOBAL} 当这个选项被设置为LOCAL且游标在创建时没有被指定为GLOBAL时,任何游标的作用域都是创建它的本地批处理、存储过程或触发器。游标名称只在它的作用域内才有效。游标可以被批处理、存储过程或触发器,或者一个存储过程的输出参数中的本地游标变量所引用。当这个选项被设置为GLOBAL且游标在创建时没有被指定为LOCAL时,游标的作用域就是整个连接。游标的名称能够被任何使用该连接执行的存储过程或批处理所引用。
自动(AUTO)选项
自动选项会影响SQL Server可能自动采取的行动。所有这些选项都是布尔(Boolean)选项,其取值或者是ON,或者是OFF。
AUTO_CLOSE 如果这个选项设置为ON时,那么当一个数据库的最后一个用户退出时,该数据库会被正常关闭,并因此释放所有的资源。所有的文件句柄都会被关闭,所有在内存中的结构都会被删除以便该数据库不再使用任何内存。当一个用户尝试重新使用该数据库时,它会重新打开该数据库。如果一个数据库被正常地关闭,那么直到有一个用户在SQL Server下次重新启动后尝试使用该数据库时,该数据库才会被初始化(重新打开)。AUTO_CLOSE选项对SQL Server的个人数据库来讲是十分方便的,因为它允许我们像管理普通的文件一样管理数据库文件。我们可以移动它们,通过复制来制作备份,甚至可以通过电子邮件将它们发送给其他用户。然而这个选项不能应用于需要重复地向SQL Server建立和中断连接的应用程序所访问的数据库。每个连接之间的关闭和重新打开数据库操作所带来的开销会对系统的性能有着明显的不利影响。
AUTO_SHRINK 当这个选项被启用时,一个数据库的所有文件都会成为周期性收缩的对象。数据文件和日志文件都能够被SQL Server自动地收缩。释放日志文件空间以便它们能够被收缩的唯一方法是备份日志文件并将恢复模式设定为SIMPLE。日志文件收缩发生在日志被备份或截断时。
AUTO_CREATE_STATISTICS 当这个选项被设置为ON(默认值)时,SQL Server查询优化器会在被一个查询的WHERE子句引用的列上创建索引。增加索引能够改善查询的性能是因为SQL Server查询优化器能够更好地判断如何估价一个查询。
AUTO_UPDATE_STATISTICS 当这个选项被设置为ON时(默认值),如果表中数据发生了改变,那么当前统计信息(statistics)就会被更新。SQL Server有一个针对发生在表上修改的计数器,可以用它来确定什么时候统计信息会过期。当这个选项是OFF时,当前索引不会被自动更新(可以手动来更新它们)。我们会在第7章对统计信息进行更多的讨论。
前面的两个统计信息选项与AUTO_UPDATE_STATISTICS_ASYNC 和参数化选项DATE_CORRELATION_OPTIMIZATION及PARAMETERIZATION(所有这些选项都是SQL Server 2005新引入的),我们将会在《Microsoft SQL Server 2005技术内幕:查询优化与调校》中对它们进行更为详细的讨论。
SQL 选项
SQL 选项控制着不同的SQL语句是如何被解释的。这些选项都是布尔选项。对SQL Server来讲这些选项的默认值都是OFF,但是很多工具,例如SQL Server Management Studio和许多编程接口,ODBC都会启用某些会话级别的选项,这些选项会覆盖数据库选项,这使得看起来ON行为好像是默认的行为一样。
ANSI_NULL_DEFAULT 当这个选项被设置为ON时,各列都会符合ANSI SQL-92标准的列的空值规则。也就是说,如果没有明确指定一张表中的一列允许为NULL值,NULL值是允许的。当这个选项被设置为OFF时,在没有指定空值约束的情况下新创建的列不允许是NULL值。
ANSI_NULLS 当这个选项被设置为ON时,任何和NULL值的比较结果都是未知(UNKNOWN)的,正如ANSI-92标准所指定的那样。如果这个选项被设置为OFF,当两个参加比较的值都是NULL值时非Unicode值与NULL比较的结果会是TRUE。
ANSI_PADDING 当这个选项被设置为ON时,互相比较的字符串在比较发生以前被设置为相同的长度。当这个选项是OFF时,不会发生填充。
ANSI_WARNNINGS 当这个选项被设置为ON时,在出现一些条件例如被0除或算术溢出时将有错误或警告发出。
ARITHABORT 当该选项被设置为ON时,查询在执行期间出现被0除或者算术溢出错误,该查询会被终止。当这个选项为OFF时,该查询会返回NULL值作为操作的结果。
CONCAT_NULL_YIELDS_NULL 当这个选项被设置为ON时,如果连接两个字符串时一个字符串为NULL值,那么连接的结果是一个NULL值。当这个选项被设置为OFF值,为了进行连接一个NULL字符串会被视作空白(0长度)字符串。
NUMERIC_ROUNDABORT 当这个选项被设置为ON时,如果一个表达式会导致精度降低就会产生一个错误。当该选项为OFF时,结果是简单圆整的。ARITHABORT的设置决定了错误的级别。如果ARITHABORT是OFF,只会产生一个警告并且表达式会返回一个NULL值。如果ARITHABORT是ON,则会产生一个错误,并且没有结果返回。
QUOTED_IDENTIFIER 当这个选项被设置为ON时,标志符例如表名和列名能够用双引号进行分隔,并且字符必须使用单引号进行分隔。所有使用双引号分隔的字符串会被解释为对象标志符。当QUOTED_IDENTIFIER是ON时,被引用的标志符不需要服从T-SQL的标志符规则。它们可以是保留关键字,并且能够包括通常在T-SQL标志符中不允许出现的字符,例如空格和破折号。我们不能使用双引号来分隔字符串表达式,而必须使用单引号来做这种分隔。如果一个单引号是字符串的一部分,可以用两个单引号(’’)来表示它。当保留的关键字被用作数据库中的对象名称时,必须将该选项设置为ON。当它是OFF时,标志符不能在引号中并且必须遵守所有的T-SQL标志符规则。
RECURSIVE_TRIGGERS 当这个选项被设置为ON时,触发器能够被直接或间接地递归触发。当间接递归发生时,一个触发器被触发并执行了一个引起另一张表上的一个触发器被触发的操作,因此,在引起对原来的表的一个更新操作后,该更新操作又重新触发了原来的触发器。例如,一个应用程序更新了表T1,这触发了一个触发器Trig1。触发器Trig1更新了表T2,这引起了触发器Trig2被触发。Trig2反过来又更新了表T1,这又重新触发了触发器Trig1。直接递归发生时,一个触发器被触发并执行了一个引起了同一个触发器被再次触发的操作。例如,一个应用程序更新了表T3,这触发了触发器Trig3。Trig3又更新了表T3,这又导致触发器Trig3被触发。当该选项为OFF时(默认情况),触发器不能够被递归地触发。
数据库恢复选项
数据库恢复(RECOVERY)选项(FULL、BULK_LOGGED或SIMPLE)决定了能够在一个SQL Server数据库上进行多少恢复。它还控制着日志记录多少信息和有多少日志可以备份。我们会在第5章中对该选项进行更多讨论。
当一个数据库被恢复时还有另外两个选项能够应用到完成的工作。在SQL Server 2005中能够设置TORN_PAGE_DETECTION选项为ON或OFF,但是该选项在将来的版本中将不复存在。推荐的替代方法是设置PAGE_VERITY选项的值为TORN_PAGE_DETECTION或CHECKSUM(TORN_PAGE_DETECTION这里应该被看作一个值,而不是一个选项的名称)。
PAGE_VERITY选项能够发现由于磁盘I/O路径错误而损坏的数据库页面,这可能会引起数据库损坏问题。I/O错误本身一般是由于在一个页面被写入磁盘时发生了电源故障或磁盘故障所引起的。
CHECKSUM 当PAGE_VERIFY选项被设置为CHECKSUM时,SQL Server根据每个页面的内容计算出一个校验和,并在页面被写入磁盘时将该值保存在页面头部。当从磁盘读出该页面时,会重新计算出一个校验和并与保存在页面头部的值相比较。如果这两个值并不匹配,错误信息824(表示校验和错误)会被报告出来。
TORN_PAGE_DETECTION 当PAGE_VERIFY选项被设置为TORN_PAGE_ DETECTION时,无论何时只要有页面被写入磁盘,一个数据库页面(8KB)的每512字节的扇区就会有一个比特位被反转。它允许SQL Server探测由于电源故障或其他系统故障造成的不完整的I/O操作。如果以后SQL Server从磁盘读取数据时发现一个比特位的状态不正确,那意味着该页面没有被正确地写入磁盘(探测到了一个损坏的页面)。虽然SQL Server数据库页面大小为8KB,但是磁盘I/O操作使用的是512字节的扇区。因此,每个数据库页面要写入16个扇区。如果系统在操作系统向磁盘写入第一个512字节的扇区和完成8KB的I/O操作之间停机(例如由于电源故障),就可能会出现一个损坏的页面。当从磁盘读取该页面时,存储在页面头部的损坏的比特位会被与实际的页面扇区信息相比较。不匹配的值表明了那个页面只有一部分被写入了磁盘。在这种情况下,错误信息824(表明页面损坏错误)会被报告。如果页面确实没有被完整写入,典型情况下损坏的页面会被数据库恢复过程检测到。不过,其他的I/O路径错误随时会导致一个损坏的页面产生。
NONE(没有页面校验选项) 指定该值后,当一个页面被写入时,CHECKSUM 和TORN_PAGE_DETCTION 值都不会产生,并且当页面被读取时也不会校验这些值。
校验和与损坏页面错误都产生错误信息824,该错误信息会被写入SQL Server错误日志和Windows 事件日志。当读取任意一个页面时,如果产生了824错误,SQL Server都会在msdb数据库的系统表suspect_pages中插入一行(联机丛书在“理解和管理suspect_pages表”一节有关于该表的更多信息)。
SQL Server将会对任何校验和、损坏页和其他I/O错误进行四次重试操作。如果在这些尝试中有一次是成功的,那么就会向错误日志中写入一条记录,并且触发该读取操作的命令将会继续执行。如果所有的尝试都是失败的,那么该命令将会失败并给出824错误信息。
我们可以通过还原数据,或者当错误仅限于索引页面时重建索引来“修复”这个错误。如果我们遭遇一个校验和错误,可以运行DBCC CHECKDB来确定受到影响的数据页类型和数据页。我们还应该确定错误的根本原因并尽快解决它以防止额外的或正在发生的错误。发现问题的根本原因需要调查硬件、固件驱动程序、BIOS、过滤器驱动程序(例如反病毒软件)和其他I/O路径组件。
在SQL Server 2005中,默认值是CHECKSUM。在SQL Server 2000中,TORN_PAGE_DETECTION是默认值,CHECKSUM不可用。如果我们从SQL Server 2000升级一个数据库,那么PAGE_VERIFY的值将会为NONE或TORN_PAGE_DETECTION。如果它是TORN_PAGE_DETECTION,我们应该考虑将它更改为CHECKSUM。虽然TORN_PAGE_DETECTION使用的资源较少,与CHECKSUM相比它提供的保护也较少。
其他数据库选项
在其他四个数据库选项类别中,我们仅会详细讨论其中一类——外部访问选项。快照隔离选项将会在第8章中加以讨论。Service Broker选项会在《Microsoft SQL Server 2005技术内幕:T-SQL程序设计》中讨论。数据库镜像选项也超出了本书讨论的范围。数据库镜像是一种新的SQL Server 2005技术,它为高可用性提供了更多的选项,并且SQL Server 2005 SP1对此技术提供了全面的支持(微软在SQL Server 2005最初的RTM版本中并没有提供对数据库镜像的全面支持,但是在那个版本中可以通过启用跟踪标记1400作为启动参数来启用镜像功能)。我们可能想了解的所有细节,包括内部的和外部的,都可以在白皮书《SQL Server 2005中的数据库镜像》(作者是Ron Talmage)和微软TechNet文章《数据库镜像最优实践和性能考虑》(作者是Sanjay Mishra)中找到,这两者都被包含在本书的关联内容里。
| 回书目 上一节 下一节 |