引言
DDL 语句用于描述数据库、定义数据库的结构、创建数据库的对象以及创建表的子对象,在构建数据库方面起了重要作用。如果数据复制引擎不能支持 DDL 变化的复制,将会给数据的实时复制和决策带来巨大障碍。
作为一款举足轻重的数据变化实时复制产品,InfoSphere Change Data Capture 在支持数据库的 DDL 变化上已持续做出很多努力。虽然所有 InfoSphere CDC 复制引擎都可以复制 DML 更改,但只有 InfoSphere CDC for Oracle 和 InfoSphere CDC for DB2 for LUW 才支持复制 DDL 更改,从而使得更改这两种数据库的数据时管理更为简单且自动化。本文将详细讲述 CDC 为支持 DB2 DDL 复制而引入的不同于普通预订(direct mapping)的全新预订模式——基于规则集(rule set)的 Rule-based Mapping,并讲解如何在管理控制器 MC 中创建 Rule-based Mapping 并配置所必需的参数以达到 DDL 复制能力,同时探讨了复制 DDL 更改的先决条件和注意事项、目前受支持 DDL 操作及使用规则集等,帮助您对如何通过 CDC 来复制带有 DDL 的数据变化场景了然于胸。
DDL 复制能力的必要性
SQL 语句分为两类:数据定义语言 (DDL,Data Definition Language) 和数据操作语言 (DML,Data Manipulation Language)。DDL 语句用于描述数据库,定义它的结构,创建数据库中的各种对象——表、视图、索引、同义词、聚簇等,如:CREATE TABLE、VIEW、INDEX、SYN、CLUSTER,主要的命令有 CREATE、ALTER、DROP 等。DDL 主要是用在定义或改变表(TABLE)的结构、数据类型、表之间的连接和约束等初始化工作上,他们大多在建立表时使用。由此可见 DDL 在构建数据库方面起了重要作用。
如果数据复制引擎不能支持 DDL 复制,一旦在场景中出现了 DDL 变化,可能引起业务逻辑的不可控提交和数据不一致,将会给数据的实时更新和决策带来巨大障碍,而这个风险在任何客户级应用中都是不允许的。
以往旧版本的 CDC 不支持 DDL 复制,在实际的场景中,一旦遇到 DDL 变化,则预订(subscription)会停掉,不利于数据的实时同步。如果 CDC 在及时处理 DML 变化的同时能兼顾处理 DDL,就能迅速处理信息、降低停机时间、减少客户服务问题,并在分发信息时将效能影响降至最低。可见对 DDL 的复制能力对于保证数据的实时完整一致性有着重要的意义。
有了 DDL 复制功能之后,在表的结构发生更改的同时,数据更改会继续复制,不必再手动更新预订信息。例如,将根据 DDL 语句来添加新的表和列。不过 CDC 目前仅支持复制那些与表和表特性相关的 DDL 操作,而不会复制较为大型的数据库上下文。
评判 DDL 复制能力的术语
DDL Awareness:DDL 变化的感知能力。它将决定当 DDL 变化发生在某个待复制主体身上的时候,能否及时鉴别到这种 DDL 变化。
DDL Resiliency:发生 DDL 时对 DML 的复制能力。它将决定在复制 DDL 变化的同时如果发生 DML 变化,待复制主体会有哪些能力及限制。
DDL Replication:DDL 复制能力。它决定可以对待复制主体进行哪些包括创建和删除在内的结构变化上的复制。
CDC 如何实现对 DB2 DDL 的支持
作为一个复制解决方案,IBM InfoSphere CDC(Change Data Capture)用于捕获正在发生的数据库更改并根据 InfoSphere CDC Management Console GUI 应用程序中配置的表映射将这些更改传递到目标数据库、消息队列或 ETL 解决方案(例如 InfoSphere DataStage)。
CDC 适用于多种场景,如动态数据仓储、主控方数据管理、应用程序合并或迁移、运营 BI 以及启用 SOA 项目之类的关键信息管理活动。CDC 不仅能够以影响性较低的方式捕获数据更改并高速传递这些更改,还可帮助降低处理开销和网络流量,因为它仅发送已更改的数据。用户可以持续进行复制或者定期进行复制。另外,传输来自源服务器的数据时,可以在目标 CDC 环境中对这些数据进行重新映射或变换。
引入全新的 Rule Based Mapping
最初版本的 CDC 是不支持复制 DDL 的,遇到复制场景中发生 DDL 变化的时候,预订会自动停止,用户必须手动配置与 DDL 相关的变化,比如将很多新表添加到用户的应用里面,待一切就绪之后再次重新启动预订。当用户有很多表的时候,这种操作方法无疑是很麻烦的。手动的配置行为在无形之中加大了 CDC 的开销,在提高用户的产品满意度和人性化方面以及同其他款数据复制产品对比方面是很不利的。
从版本 6.5.1 开始,CDC 持续增加对 DDL 复制的支持。在较新版的 10.2.1 版本及之后,CDC 开始实现对 DB2 数据库表和索引的 DDL 变化的复制。
在对 DB2 DDL 变化复制支持方面,CDC 最大的特色是引入了不同于原有直接映射(direct mapping)的一种全新的映射模式:基于规则的映射(Rule-Based Mapping)。这种映射的最大特点是,映射由事先定义好的规则决定,符合规则的表将顺利从源端映射到目标端,接着根据规则来决定何时、针对哪些 DDL 变化进行复制。
用户可以利用自行设定的规则(rule)来规定哪些表准许被纳入 DDL 变化复制的范围内,还可以审计 DDL 操作,并可以主动停止对 DDL 变化的复制。此外,在更改或选择性忽视执行哪些 DDL 语句上,提供给了用户更多的弹性。允许用户对一个已经被 Rules Based Selection 选中的表进行刷新操作。用户还可以在整个数据库层面对外部同步机制协调工作,如数据库的备份和还原。
如果源表未被规则集(rule set)选中,则此表在此期间发生的任何 DDL 变化和 DML 变化,都不能得到复制。
基于规则的映射及其预订,既可以单独存在,也可以同静态映射(或叫直接映射)及其预订同时存在,还可以在复制的过程中临时加入到预订当中。但是预订不能同时包含基于规则的映射和静态映射,也即,每个预订只能包含一种类型的映射。不过,不妨碍同时存在两种类型的预订,且每个预订中也可以定义多个规则集。
CDC 复制 DDL 变化的先决条件
要想进行 DDL 复制,CDC 要求必须满足以下先决条件:
- 源和目标数据存储器都必须为 CDC for DB2 for LUW V10.2.1 或更高版本。
- 对于源和目标数据存储器,DB2 LUW 数据库必须为 V10.1 或更高版本。
- DB2 LUW 数据库的发行版本需要兼容。也就是说在源数据库上执行的 DDL 操作必须在目标数据库上也能执行成功。
- 创建源和目标 CDC for DB2 for LUW 实例期间指定的 DB2 LUW 用户必须相同。
- 源和目标数据存储器必须是不同的数据库。不能将同一数据库同时用作源和目标数据存储器,即不能使用 loopback。
- 必须针对将属于规则集的任何模式在模式级别对源数据库启用日志记录。确保 DFT_SCHEMAS_DCC 设置为 YES。(DB2 UPDATE DB CFG FOR dbzm01 using DFT_SCHEMAS_DCC YES)
- DB2 中的 LOG_DDL_STMTS 系统参数必须设置为 YES。(DB2 UPDATE DB CFG FOR dbzm01 using LOG_DDL_STMTS YES)
- 源和目标数据存储器的物理元素必须完全相同。
- 源和目标的数据库编码(代码页)必须完全相同。
- 在针对临时表复制 DDL 操作时,必须为复制同时选择临时表和历史记录表。将通过管理历史记录的源复制临时表。否则 CDC 不会自动复制未选的部分。
CDC 复制 DDL 变化的注意事项
在复制 DDL 变化之前,应考虑到:
- DDL 复制的目标表不能参与任何其他 CDC 表映射。即,不能制作从两个不同的源表到同一个目标表的镜像。
- 不支持将“冲突检测和解决”用于 DDL 复制。
- 不支持将“差分刷新”和“刷新行的子集”用于要为其复制 DDL 操作的表。
- 不支持派生列和派生表达式用于要为其复制 DDL 操作的表。
- 在复制时使用与源表相关联的键或唯一索引(如果存在)从数据库选择 LOB 列。因此,复制时仅发送源表中 LOB 列字段的当前映像。如果对于要复制 DDL 操作的预订存在等待时间,并且更改了列的列表(这些列生成用于搜索的键),那么目标列可能会一直包含空值,直到对该行进行下一次 DML 更改。如果存在等待时间,且行键发生更改,那么目标列可能包含空值或者不正确的值。
- 不支持将双向复制用于 DDL 复制。
- CDC 遇到诸如 UDT(用户定义的列)之类不能复制的特定对象类型时,该表将停用。应当确定不受支持的表是否对于复制解决方案必不可少。如果确定这并非必需,那么应修改规则集以排除表。如果确定该表必不可少,那么应删除并重新创建表,并更改其结构以便 DDL 复制支持。
受 CDC 支持的 DDL 操作
CDC for DB2 for LUW 仅复制与表相关的操作,此时包括表上的 从属对象(如约束和索引),但不复制与表无关的操作(如仅涉及到索引)。比如,一个带有指定约束的 CREATE TABLE 会被 CDC for DB2 for LUW 复制,但是一个 CREATE INDEX 语句却不会被 CDC 复制。
可以由 CDC for DB2 for LUW 复制的 DDL 更改的类型如表 1 所示。注意,仅当这些类型的任何 DDL 操作不依赖生成这些操作的数据库会话的任何特定特性时,CDC 才将成功复制这些操作。其他情况需要用户出口(User Exit)。
表 1. 受支持的 DDL 操作
CDC 不支持其 DDL 复制与表相关对象的示例包括:
- 视图(Views)
- 同义词(Synonyms)
- 触发器(Triggers)
- 具体化查询表(Materialized query tables)
- 包含用户定义的类型的表(Tables containing user-defined types)
CDC 不支持其 DDL 复制与数据库相关对象的示例包括:
- 函数(Functions)
- 存储过程(Store Procedures)
- 程序包(Packages)
- Java 类(Java classes)
- 数据库链接(Database links)
- 角色(Roles)
- 目录(Directories)
- 维(Dimensions)
- 库(Libraries)
- 概要文件(Profiles)
- 用户(Users)
- 序列(Sequences)
- 表空间(Tablespaces)
- 模式(Schemas)
CDC 不支持以下 DDL 操作:
- 重命名(Rename)
- 移动(Move)
Rules Based Mapping 配置示例
截止到 Version 11.3.3 版本为止,CDC for DB2 支持的 DDL 类型包括:添加源表,删除源表,在源表中添加一列或多列,更改源表中列的属性。其余 DDL 类型复制的支持将会在后续版本中陆续推出。
Rules Based Mapping(以下简记为RBM)利用的选择方法叫做Rules-based Selection (RBS)。这是一种基于规则来筛选待复制主体的方法。比如,一个规则可以设定为“只选择某个 schema,如 moira 名下的表参与复制”。这时 schema 不为 moira 的表将不参与复制。
注意,在开始复制预订中满足 rule set 的所有表时,将先删除掉目标表(如果存在)然后再创建新目标表。这称为结构性刷新。然后,会执行常规数据刷新。在刷新完成之后,将开始镜像 DML 和 DDL 变化。
可见定义规则集的行为只在源端发生。
为预订定义规则集
在表映射(Table Mapping)视图为每个映射定义所需的规则集。与静态映射的预订类似,CDC 支持用户对 RBM 进行复制、提升、导出和导入。如果是静态映射与基于规则映射组合的预订,同样支持上述操作。
在规则集中通过确切名称或格式(pattern)来选择表。可以选择个别表精确匹配,以在复制中包括或排除该表,也可以定义模式 schema 以包括或排除与条件相匹配的表。基于确切名称的规则集好理解。那么,基于 pattern 的规则集简单示例如下:
- 要包含的表:A*, B*
- 要排除的表:*C
那么返回的结果将是所选格式中名称以字母 A 或 B 开头、名称不以字母 C 结尾的所有表都将在复制的作用域内。注意,可以定义多个规则集,但是规则集并无优先顺序。定义规则集时,下列问题值得考虑:
- 用户所创建的各种规则中所设置的条件不应该互相矛盾。
- 不仅应考虑目前存在且将与规则相匹配的表,还应考虑规则集将来要与之匹配的表。
- 还应该考虑为复制到相同目标数据库的其他预订定义的规则,并验证是否没有重叠。已经用于 DDL 复制目标端的表不能再用于其它映射中。
- 规则集创建模式区分大小写。
- MC 中表的所有 DDL 复制操作都是基于表名而非基于源标识。
当 Mirror 尚未启动的时候,只能创建或修改规则集。可以通过设置“刷新顺序”并将位于复制作用域内的表移到组中可以安排表的刷新顺序。那么 Mirroring 开始的时候将按照选择的顺序来执行刷新顺序。
可以为包括在规则集中的表设置捕获点。如果将表标记为“镜像”/“活动”,那么 CDC 将假定在标记捕获点时,目标表与源表处于同步状态,因此不需要执行刷新。
在启动复制之前,可以通过预览将要位于复制作用域内的表来查看规则的求值结果。MC 将显示当前满足规则集条件的表的列表。也就是说,进行预览时数据库中的实际情况;如果对数据库进行了更改,那么可能会导致实际启动复制时作用域内的表的列表与预览时作用域内的表的列表不同。
请注意,已定义规则集的预订具有下列局限性:
- 不能在基于规则的映射中手动停止表。
- 静态表映射优先于该表的基于规则的映射。在 DDL 复制中将排除静态映射中的表。
- DDL 复制不适用于使用静态映射的表。
- 只有基于规则的映射才支持复制具有时间间隔分区的表,而静态映射不支持此操作。
配置 Rules Based Mapping 示例如图 1 所示。首先左边红框和右边红框都可添加新的规则集:
图 1. 添加新的规则集
在规则集名称框中,输入规则的名称,注意预订内的每个规则集名称都必须唯一,如图 2 所示。
图 2. 定义规则集名称
选择完使用的 schema 之后(页面略),如果选择手动添加某些表包含在规则集中,那么执行如下图 3 所示。
图 3. 通过确切名称添加表
如果选择在表名内使用格式(Pattern)以选择要将哪些表包含在规则集中,那么执行如下图 4 所示。
图 4. 通过格式添加表
上图中,各条名词解释如下:
- Match all table 指定覆盖所有已定义的模式,并考虑对所有的表进行复制;
- Matches the pattern 指定将名称与模式匹配的表包括在规则集中;
- Starts with the pattern 指定将名称开头与模式匹配的表包括在规则集中;
- Contains the pattern 指定将名称的任何部分中包含模式的表包括在规则集中;
- Ends with the pattern 指定将名称结尾与模式匹配的表包括在规则集中。
注意,可以选择仅复制 DDL、不复制 DML。同理,定义欲排除在外的表也可以通过确切名称或格式(pattern)来选择,如图 5 所示。
图 5. 通过确切名称或者格式确定排除在外的表
当想删除某个 rule set 时,直接右键“Delete”即可。前面已知可以定义多个规则集,但规则集并无优先顺序,也无依赖关系。删除某个规则集的时候,不会影响尚存的其他有效规则集。
修改规则集
在复制启动的时候,CDC 会根据规则集选出将要被复制的表。如果想修改原有的规则集,先把复制停掉再修改。
处于正在编辑状态的规则集名称旁边将出现一个星星标记,保存即消失。无效的规则集无法保存且必须予以更正才能继续。也可单击“还原按钮”回退更改以返回上次保存的规则集。
用户可以在启动复制之前预览位于复制作用域内的表。MC 将显示当前满足规则集条件的表的列表。如果对数据库进行了更改,那么可能会导致实际启动复制时作用域内的表的列表与预览时作用域内的表的列表不同。
对规则集进行更改之后,如果重新启动复制,将导致对预订中当前与规则集条件相匹配但在上次对预订进行镜像时不匹配的所有表执行刷新。该刷新将是结构性刷新,这表示将删除并重新创建目标表。预订中继续与已修改的规则集相匹配的表将开始镜像。如果已对与规则集条件相匹配的表标记了“表捕获点”,那么将遵守该捕获点。将不刷新该表,并且复制将在所设置的点处开始。不再满足规则集条件的表将从复制中予以排除,但不会将其从目标中删除。
复制规则集
规则集和预订都可以进行复制。二者的区别在于,复制预订包含了复制规则集。当仅需要复制预订中规则集的某个子集时,使用复制规则集。
所有来自同一个源数据存储器的预订都必须具有唯一的名称,并且所有前往同一个目标数据存储器的预订都必须具有唯一的源标识。源标识通过将预订名称截断为 8 个字符自动生成。如果尝试创建具有重复源标识的预订,那么将发生错误,并且不会创建该预订。
注意,当源数据存储器与目标数据存储器相同时,无法提升具有基于规则的表映射的预订。
导出规则集
使用 CDC 的导出和导入功能,可以把预订的配置信息输入到 XML 文件中。其中包含已在预订中设置的详细信息,并且可以在本地计算机上或其他位置中保存这些文件。导出预订中所选规则集的操作为:右键,选择“导出...”,为 XML 文件输入名称,然后单击保存即可。
提升规则集
用户可以通过提升规则集将该预订从开发环境提升到生产环境中,有以下两种应用方式:
- 将预订提升到新环境 - 在此场景中,可把所选规则集提升到新环境中的预订。例如,可能具有不适用于开发或测试目的的项目,或者可以将预订提升到其中一个环境中。
- 将更改提升到现有预订 - 在此场景中,可对已提升到另一个环境中的预订内的规则集进行更改。例如,该预订可能已存在于为测试预订而保留的项目中,但可能已对该预订的规则集进行了一些小幅更改。要确保测试环境中的预订包含所作的更改,需要将这些更改提升到测试环境。
注意,将更改提升到现有预订时,CDC 会在源表与目标表之间保持同步,不需要在新环境中设置日志位置。但是,如果所做的更改导致源表与目标表之间不再同步(例如,更新源表的定义),那么 CDC 不会保留日志位置,必须再次主动同步原始环境与新环境中的源表和目标表。
更改基于规则的预订中表的刷新顺序
只有当预订未处于运行状态时,才能更改表的刷新顺序。确定要移至组中的每个表都将分配到一个序号,CDC 会使用该序号按照数字顺序来刷新每个表映射。未添加到组中的任何剩余表映射将由 CDC 按照任意顺序在最后进行刷新。
注意,刷新顺序的设置是操作性设置。当刷新完成后,将删除基于规则的预订的刷新顺序信息。
如果在已指定刷新顺序的基于规则的表上标记了表捕获点,那么已标记的表将从刷新顺序中除去并返回到未分组表列表中。注意,要先确保已结束所有针对此预订的活动复制。如果设置具有引用完整性约束的表时,需要先确保在启动复制之前目标表为空。设置好之后,会先刷新分组表(按照指定这些表的顺序)。所有其他表都是在分组表之后刷新的。
CDC 对 DB2 DDL 复制的审计
如果用户开启了 CDC 的一个参数:mirror_audit_ddl_statements,那么所有从源端接收来的 DDL 变化还会被写入目标数据库内的一个审计表(audit table),如图 6 所示。
图 6. 修改 CDC 系统参数以支持 DDL 复制审计
CDC 对不予支持 DB2 DDL 的复制处理
前面提到 CDC for DB2 目前只支持四种 DDL 变化的复制。那么对于众多其他暂时未予支持的 DDL 变化,CDC 将如何处理呢?建议按如下顺序进行操作:
- 用户暂停更新表
- 停止复制并确保已更新至最新
- 在源表上执行 DDL 变化(如有需要包括目标表)
- 更新源端的表定义,将表重新添加至源端
- 更新目标端的表定义,重新分配表至目标端
- 查看映射状态正常
- 确保表复制状态是 active(Mark table capture point for mirroring)
- 用户可以恢复此期间的 DML 变化
- 开始制作镜像
结束语
数据复制引擎不支持 DDL 复制可能引起业务逻辑的不可控提交和数据不一致,给数据的实时更新和决策带来巨大障碍,而这个风险在任何应用中都是不允许的。对于 DB2 数据库,CDC 目前可以在及时处理 DML 变化的同时兼顾处理 DDL,有利于迅速处理信息、降低停机时间、减少客户等待问题,并在分发信息时将效能影响降至最低,在保证数据的实时完整一致性方面有着重要的意义和极其实用的价值。
本文作者:
赵 萌, 软件工程师, IBM
郭 玮, 软件工程师, IBM
刘 艳, 软件工程师, IBM
声明: 此文观点不代表本站立场;转载须要保留原文链接;版权疑问请联系我们。