VSS 测试编写器工具
测试编写器是一个实用工具,可用于测试 VSS 请求程序应用程序。 此编写器可配置为执行 VSS 编写器可执行的几乎所有操作。 此外,测试编写器会执行广泛的检查,以确保请求者已正确处理这些编写器操作。
编写器的每个实例都使用 XML 配置文件进行初始化,该文件准确描述了编写器将报告的组件,以及编写器的行为方式。 编写器可配置为报告各种类型的方案,包括使用增量接口和差异接口的更复杂方案。 编写器将在过程中的各个点执行检查,以确保请求者的行为正确。 完成还原后,编写器将检查所有必需的文件是否已还原,而不会损坏。 还可以将编写器配置为执行其他操作,例如使特定事件失败。
备注
该工具包含在适用于 Windows Vista 及更高版本的 Microsoft Windows 软件开发工具包 (SDK) 中。 您可以从 https://msdn.microsoft.com/windowsvista 下载 Windows SDK。
在 Windows SDK 安装中,可以在 %Program Files(x86)%\Windows Kits\8.1\bin\x64
(适用于 64 位 Windows)和 %Program Files(x86)%\Windows Kits\8.1\bin\x86
中找到 VssSampleProvider 工具。
若要启动测试编写器,请在命令提示符处键入以下内容:
vswriter.exe config-file
其中,config-file 是指定此编写器行为的配置文件的路径。
若要停止测试编写器,请按 Ctrl+C。
可以同时运行测试编写器的多个实例。 但是,编写器的每个实例将报告相同的编写器类 ID(虽然是不同的编写器实例 ID),因此逻辑路径和组件名称必须跨所有同时运行的编写器实例保持唯一。
为了确保编写器能够正确检查请求者是否遵守了排除文件规范,应在尝试还原之前从原始卷中删除备份的所有文件。 建议存储每个编写器方案的模板,以便可以轻松重新创建方案。
以下示例配置文件 vswriter_config.xml 在 x86 平台上可在 %ProgramFiles%\Microsoft SDKs\Windows\v7.0\bin\vsstools
中找到,在 x64 平台上可在 %ProgramFiles%\Microsoft SDKs\Windows\v7.0\bin\x64\vsstools
中找到。
<TestWriter usage="USER_DATA">
<RestoreMethod method="RESTORE_IF_CAN_BE_REPLACED"
writerRestore="always"
rebootRequired="no" />
<ExcludeFile path="c:\writerData\notTheseFiles"
filespec="excludeThisFile.txt"
recursive="no"/>
<Component componentType="filegroup"
componentName="TestFiles">
<ComponentFile path="c:\writerData\myFilesHere"
filespec="*"
recursive="no" />
</Component>
</TestWriter>
此配置文件中的根元素名为 TestWriter。 所有其他元素都排列在 TestWriter 元素下。
与 TestWriter 关联的属性之一是使用属性。 此属性指定通过 IVssExamineWriterMetadata::GetIdentity 报告的使用类型。 此属性的可能值之一是 USER_DATA。
根元素的第一个子元素必须始终是 RestoreMethod 元素。 此元素指定以下内容:
- 还原方法(在本例中为 RESTORE_IF_CAN_BE_REPLACED)
- 编写器是否需要还原事件(在这种情况下为始终)
- 在还原编写器后是否需要重新启动(在这种情况下为否)
此元素可以选择指定备用位置映射。 (在这种情况下,未指定备用位置。)
第二个子元素是 ExcludeFile 元素。 此元素会导致编写器从备份中排除一个文件或一组文件。
第三个子元素是 Component 元素。 此元素使编写器将组件添加到其元数据中。 Component 元素包含用于描述组件的属性以及用于描述组件内容的子元素,如下所示:
- componentType 用于指示这是文件组还是数据库
- 组件逻辑路径的 logicalPath
- componentName 表示组件名称
- selectable 表示可选择的备份状态
Component 元素还有一个名为 ComponentFile 的子元素,用于向此组件添加文件规范。 (一个 Component 元素可以有任意数量的 ComponentFile 元素,可以为每个组件指定这些元素。)此 ComponentFile 元素具有以下属性:
- path="c:\writerData\myFilesHere"
- filespec="*"
- recursive="no"
尽管测试编写器验证了请求者的行为,但它不验证配置文件是否始终保持编写器的文档语义。 行为良好的编写器不应执行许多操作(如在多个组件中报告同一文件),并且由 XML 配置文件的作者来维护这些语义。
TestWriter 根元素包含确定编写器的各种行为的属性。 可以更改的一些行为如下:
属性 | 说明 |
---|---|
verbosity |
编写器在接收事件并处理事件时将状态打印到控制台。 显示的详细程度级别由详细属性指定。 有三个详细级别可供选择:
|
deleteFiles |
若要执行额外验证,请将此属性设置为“是”,以便编写器在创建卷影副本后立即删除其所有文件。 然后,请求者必须从卷影副本中复制文件,因为它们已不再存在于原始卷上。 注意:对于 spit 编写器,文件会在 spit 之后但在创建卷影副本之前从原始位置删除。 创建卷影副本后,文件将从 Spit 目录中删除。 |
deletePartialFiles |
若要删除部分文件,请将此属性设置为“yes”。 |
deleteDifferencedFiles |
若要删除不同的文件,请将此属性设置为“yes”。 |
checkIncludes |
将此属性设置为“yes”,使编写器检查是否已将已备份的每个文件还原到适当的位置,并且该文件尚未损坏。 部分文件和差异文件也得到正确处理。 |
checkExcludes |
将此属性设置为“是”,使编写器检查是否未还原与排除列表中的文件规范匹配的文件。 为了使其正常运行,必须在还原之前清空还原目录。 |
备用位置映射指定在还原方法为 VSS_WRE_RESTORE_TO_ALTERNATE_LOCATION 或组件正常还原失败时要还原到的位置。 编写器可以使用 IVssExamineWriterMetadata::GetAlternateLocationMapping 方法向请求者报告其备用位置映射。 通过将 AlternateLocationMapping 子元素添加到 RestoreMethod 元素,可以将备用位置映射添加到测试编写器配置文件。
以下 RestoreMethod 元素包含 AlternateLocationMapping 子元素。
<RestoreMethod method="RESTORE_IF_CAN_REPLACE"
writerRestore="always"
rebootRequired="no">
<AlternateLocationMapping path="c:\files"
filespec="*.txt"
recursive="no"
alternatePath="c:\altfiles"/>
</RestoreMethod>
此示例指定请求者应首先尝试将匹配 c:\files\*.txt 的所有文件还原到 c:\files 目录。 如果无法替换其中一个文件,则请求者应改为将所有文件还原到 c:\altfiles 目录。 请求者应使用 IVssBackupComponents::AddAlternativeLocationMapping 方法保存此备用位置映射。 如果测试编写器配置为检查文件是否已还原,它还将检查请求者是否已调用 AddAlternativeLocationMapping。
每个编写器都可以指定文件规范列表,这些规范指定要从备份中排除的请求者的文件。 通过将 ExcludeFile 子元素添加到 TestWriter 根元素,可将这些文件规范添加到测试编写器配置文件。
下面是 ExcludeFile 子元素的示例,该子元素排除 C:\files 目录中与 C:\temp*.* 匹配的所有文件。
<ExcludeFile path="c:\files"
filespec="temp*.*"
recursive="no"/>
许多写入器充当“spit 写入器”。spit 编写器基于原始文件集创建中间文件或“spit 文件”,并在备份时将 spit 文件放在备用位置。 编写器使用 IVssWMFiledesc::GetAlternateLocation 方法通知请求者,请求者应从备用位置备份这些文件。 但是,这些文件仍应还原到原始文件的活动位置。 可以将测试编写器配置为充当特定文件规范的 spit 编写器。
以下 ComponentFile 元素包含 alternatePath 属性:
<ComponentFile path="c:\files"
filespec="*.txt"
recursive="no"
alternatePath="c:\files\spit" />
此示例将测试编写器配置为在创建卷影副本之前立即将所有与 c:\files\*.txt 匹配的文件复制到 c:\files\spit 目录。 请求者必须备份 c:\files\spit 目录中的文件。 如果测试编写器配置为删除文件,则会在创建卷影副本之前删除原始文件,因此它们不会显示在卷影副本卷上的 c:\files 目录中。 在这种情况下, c:\files\spit 中的文件会在创建卷影副本后被删除,因此必须从卷影副本卷上的 c:\files\spit 目录中备份这些文件。
编写器可以指定本地组件与另一编写器中存在的组件之间的依赖关系。 这些依赖项使用 IVssWMComponent::GetDependency 向请求者报告。 可以通过向 Component 元素添加一个或多个依赖项子元素来配置测试编写器来报告这些依赖项。
以下 Component 元素包含 Dependency 子元素:
<Component componentType="filegroup"
logicalPath=""
componentName="WriterComponent"
selectable="yes">
<Dependency writerId="<GUID of target writer>"
logicalPath="ComponentPath"
componentName="Writer2Component" />
</Component>
依赖项被指定为 Dependency 元素的属性。 writerId 是包含依赖项目标的编写器的类 ID,logicalPath 是该编写器中组件的逻辑路径,componentName 是组件的名称。 在这种情况下,如果请求者正在备份当前编写器中的“WriterComponent”,则它还应在目标编写器中备份组件“ComponentPath\Writer2Component”。
备注
测试编写器不会执行检查,以确保依赖关系得到遵守。
可以将测试编写器配置为使编写器接收的任何正常事件失败。 这些事件如下所示:
事件 | 说明 |
---|---|
Identify |
作为对 IVssBackupComponents::GatherWriterMetadata 调用的响应接收。 此处失败将导致编写器不被报告。 |
PrepareForBackup |
作为对调用 IVssBackupComponents::P repareForBackup 请求者的响应接收。 |
PrepareForSnapsot |
当请求者调用 IVssBackupComponents::D oSnapshotSet 时收到,但在创建卷影副本之前。 |
锁定 |
在 PrepareForSnapshot 之后立即收到,但仍在创建卷影副本之前。 |
解冻 |
在卷影复制创建完成后收到。 |
PostSnapshot |
在解冻完成后收到,但在 IVssBackupComponents::DoSnapshotSet 完成之前收到。 |
中止 |
如果在冻结和解冻之间花费了太多时间,或者请求者调用了 IVssBackupComponents::AbortBackup,则会收到该消息。 |
BackupComplete |
请求者退出时收到。 此处的故障永远不会被报告。 |
PreRestore |
当请求者调用 IVssBackupComponents::PreRestore 时收到。 |
PostRestore |
当请求者调用 IVssBackupComponents::PostRestore 时收到。 |
这些故障通过将一个或多个 FailEvent 子元素添加到 TestWriter 根元素来配置。 可以设置两类故障:可重试和不可重试。 可重试错误是指在重试整个备份过程时可能会消失的错误,而不可重试的错误不太可能消失。 事件的故障类型根据可重试属性选择。
下面是基本不可重试错误的示例:
<FailEvent writerEvent="Freeze"
retryable="no" />
本示例将导致编写器在冻结事件期间失败。 IVssBackupComponents::GatherWriterStatus 将报告编写器失败报告为 VSS_E_WRITERERROR_NONRETRYABLE。
下面是基本可重试错误的一个示例:
<FailEvent writerEvent="Freeze"
retryable="yes"
numFailures="2"/>
此示例将导致编写器在前两次收到冻结事件时失败。 前两次之后,编写器始终都会成功。 通过 GatherWriterStatus 报告的编写器失败将是随机可重试的错误代码。
编写器通过请求者的调用 IVssExamineWriterMetadata::GetBackupSchema 传达支持的备份类型。 TestWriter 根元素包含每种备份类型的属性,以表示支持。 这些属性是 supportsCopy、supportsDifferential、supportsIncremental 和 supportsLog。 若要表示对特定备份类型的支持,请将相应的属性设置为“yes”。
如果请求者将备份类型设置为编写器不支持的备份类型,则编写器将在 PrepareForBackup 期间记下此事实,但在其他情况下仍可正常工作。
IVssWMFiledesc::GetBackupTypeMask 方法会向请求者返回位掩码,表明应如何备份文件。 这将指示在特定类型的备份期间是否需要文件,以及特定类型的备份期间是否需要卷影副本。 此位掩码中的备份类型在文档请求者在备份复杂存储中的作用中有详细说明。
在测试编写器中,通过设置每个 ComponentFile 元素中的属性来指定此位掩码的元素。 fullBackupRequired、diffBackupRequired、incBackupRequired 和 logBackupRequired 属性指定何时需要备份文件。 fullSnapshotRequired、diffSnapshotRequired、incSnapshotRequired 和 logSnapshotRequired 属性指定何时必须从卷的卷影副本备份文件(从不从原始卷备份)。 所有这些值的默认值为“是”,表示文件必须始终备份,并且必须从卷的卷影副本进行备份。
在处理 DoSnapshotSet 期间,编写器有机会向每个组件添加部分文件。 这些部分文件使用 IVssComponent::GetPartialFile 报告。 可以通过在 Component 元素中指定 PartialFile 子元素来配置测试编写器以添加部分文件。
下面是包含两个 PartialFile 子元素的 Component 元素示例:
<Component componentType="filegroup"
logicalPath=""
componentName="WriterComponent"
selectable="yes">
<ComponentFile path="c:\files"
filespec="*.txt"
recursive="no"/>
<PartialFile path="c:\files"
filespec="partial.txt"
ranges="0:5,100:20" />
<PartialFile path="c:\files2"
filespec="partial.txt"
ranges="0:5,100:20" />
</Component>
只有与现有 ComponentFile 部分匹配的部分文件(如示例中的第一个部分文件)或与现有 ComponentFile 位于同一卷上的新部分文件(如第二个部分文件)才应以这种方式指定。 对于此组件,请求者必须完全备份与 c:\files\*.txt 匹配的所有文件,partial.txt除外。 然后,请求者必须为文件 c:\files\partial.txt 和 c:\files2\partial.txt 备份指定的范围(其中范围是偏移量后跟长度)。
如果编写器配置为检查文件还原,则还原时只会检查部分文件的备份范围。 对文件其他部分的修改将不会被察觉。 如果设置了 TestWriter 根元素的 deletePartialFiles 属性,则会在创建卷影副本后立即从原始卷中删除部分文件。
在处理 DoSnapshotSet 期间,编写器可以将差异文件添加到每个组件。 这些差异文件使用 IVssComponent::GetDifferencedFile 报告。 可以通过在 Component 元素中指定 DifferencedFile 子元素,将测试编写器配置为添加差异文件。
下面是包含两个 DifferencedFile 子元素的 Component 元素示例:
<Component componentType="filegroup"
logicalPath=""
componentName="WriterComponent"
selectable="yes">
<ComponentFile path="c:\files"
filespec="*.txt"
recursive="no"/>
<DifferencedFile path="c:\files"
filespec="*.txt"
year="2007"
month="1"
day="22"
hour="12"
minute="44"
second="17" />
<DifferencedFile path="c:\files2"
filespec="*.txt"
year="2007"
month="1"
day="22"
hour="12"
minute="44"
second="17" />
</Component>
与部分文件不同,差异文件不应部分匹配 ComponentFile 规范。 DifferencedFile 元素中的文件规范应完全匹配 ComponentFile(如示例中的第一个差异文件),或者它根本不应该匹配它,而是位于 ComponentFile 中引用的卷上(如第二个差异文件)。 日期和时间值应相对于本地时区,但在向请求者报告之前,这些值将转换为 GMT。 在此示例中,仅自 2003/1/22:12:44:17 起修改的 c:\files\*.txt 或 c:\files2\*.txt 会被备份。
如果测试编写器配置为检查文件还原,则只会检查修改的文件进行还原。 如果设置了 TestWriter 根元素的 deleteDifferencedFiles 属性,则会在创建卷影副本后立即从原始卷中删除差异文件。
某些编写器允许请求者通知他们已选择新位置以将某些文件还原到其中。 编写器指示它支持此模式,作为 IVssExamineWriterMetadata::GetBackupSchema 返回的位掩码的一部分。 默认情况下,测试编写器始终支持新目标。 可以通过将 TestWriter 根元素中的 supportsNewTarget 属性设置为“no”来禁用此支持。
如果编写器支持新目标,则请求者可以通过调用 IVssBackupComponents::AddNewTarget 通知编写者新目标。 然后,编写器将检查新的目标位置以验证还原,而不是原始位置。
测试编写器支持此处未介绍的更多配置选项。 测试编写器的所有配置功能的完整架构在 swriter.xml %ProgramFiles%\Microsoft SDKs\Windows\v7.0\bin\x64\vsstools
(64 位 Windows)和 %ProgramFiles%\Microsoft SDKs\Windows\v7.0\bin\vsstools
(32 位 Windows)中指定。 此文件包含一个 XML 架构,该架构完整描述了构成配置文件的所有元素和属性。 此文件中的每个元素和每个属性都带有注释,说明了相应元素或属性的用途。