yangtingkun
===========================================================
流捕获进程——流
===========================================================

流的捕获是流机制中的第一步,主要描述和捕获进程有关的概念。


捕获进程是Oracle的可选后台进程(CPnn),用来捕获联机重做日志文件中的数据库对象的DMLDDL操作。

逻辑改变记录(Logical Change RecordLCRsLCR就是通过指定的格式描述数据库对象的改变。捕获进程负责从联机重做日志中捕捉到对象的改变,并将其转化为LCR的格式。捕获进程捕捉两种类型的LCRrow LCRsDDL LCRs

Row LCRs:一条Row LCR描述一跳记录的修改或者描述一条记录的一个LOB列。每条Row LCR包含下列信息:源数据库名字、DML语句的类型、表的SCHEMA名字、表名、raw tag、当前事务的标识、SCN、变化记录的OLD VALUENEW VALUE

DDL LCRs:一条DDL LCR描述数据定义语言(DDL)的变化。每条DDL LCR包含下列信息:源数据库名字、DDL语句的类型、DDL目标对象的名字、DDL目标对象的类型、DDL语句的内容、登陆用户名称、执行DDLSCHEMA名字(如果DDL中没有明确指出SCHEMA名称的话)、基表所属用户名、基本名称、RAW TAG、当前事务的标识和SCN

捕获规则:捕获进程可以根据用户定义的规则进行捕获。每个规则说明捕获数据库中哪个对象的修改和捕获哪知类型的修改。表级规则在指定表上捕获捕获DMLDDL修改;方案规则在指定方案中捕获DMLDDL修改;全局规则捕获数据库中所有的DMLDDL。注意,捕获进程永远不会捕获SYSSYSTEM方案中的修改。

捕获支持的数据类型包括:CHARVARCHAR2NCHARNVARCHAR2NUMBERDATECLOBBLOBRAWTIMESTAMPTIMESTAMP WITH TIME ZONETIME STAMP WITH LOCAL TIME ZONEINTERVAL YEAR TO MONTHINTERVAL DAY TO SECOND

不支持的数据类型包括:NCLOBLONGLONG RAWBFILEROWIDUROWID,以及用户自定义对象,比如:嵌套表、数组等。

流捕获支持的DML操作有:INSERTUPDATEDELETEMERGE以及LOB的分段更新。不支持的DML包括:CALLEXPLAIN PLANLOCK TABLE。另外,对临时表、索引组织表和对象表的所有DML操作都是无法捕获的。

流捕获不支持的DDL操作包括:ALTER DATABASECREATE CONTROLFILECREATE DATABASECREATE PFILECREATE SPFILE

流捕获机制不支持下列语句:ALTER SYSTEMALTER SESSIONSET ROLE以及PL/SQL的调用。另外流机制也不支持使用DBMS_REDEFINITION包进行的在线重定义操作。

如果SQL语句指定了NOLOGGINGUNRECOVERABLE 语句,那么当前SQL语句影响的记录无法被流捕获。可以设置数据库级的FORCE LOGGING,强制所有操作都必须写重做日志,这时候表级和语句级指定的NOLOGGING语句将失效。

如果SQLLOADER程序的控制文件中指定了UNRECOVERABLE语句,则SQLLOADER导出的数据无法被流捕获。解决的方法是在源和目标数据库执行同样的数据装载操作,或者在使用SQLLOADER的时候避免UNRECOVERABLE语句。如果设置了数据库级的FORCE LOGGING参数,则UNRECOVERABLE语句失效。

SUPPLEMENTAL LOGGING:开启了SUPPLEMENTAL LOGGING后,在重做日志中记录UPDATE操作时会记录一些额外的列。SUPPLEMENTAL LOGGING包括数据库级和表级两种类型,而表级SUPPLEMENTAL LOGGING又可以选择UNCONDITIONALCONDITIONAL日志组。

UNCONDITIONAL日志组:只有表被更新就会记录指定列的前映像,也称为ALWAYS日志组。CONDITIONAL日志组:只有日志组中的列别更新时,才会记录所有指定列的前映像。

如果需要使用一个或多个应用进程,则必须满足下列条件:

源数据库中所有构成表的主键的列必须是UNCONDITIONAL日志组的成员或者设置DATABASE SUPPLEMENTAL LOGGING OF PRIMARY KEY

如果应用进程数大于1,则源数据库中所有构成复合唯一约束的列必须是CONDITIONAL日志组成员。

如果应用进程数大于1,则源数据库中所有构成复合外键约束的列必须是CONDITIONAL日志组成员。

源数据库中所有替代键列必须是UNCONDITIONAL日志组成员。

冲突解决方案中涉及的列的个数如果超过一个,则这些列都是必须是CONDITIONAL日志组成员。

DML句柄或错误句柄指明用于更新或分段更新LOBs的列必须是UNCONDITIONAL日志组成员。

RULE或基于RULE进行的转换所使用的列必须是UNCONDITIONAL日志组成员。

如果在目标数据库指定了行子集,则在目标数据库表中出现的列以及作为行子集的条件列都必须是UNCONDITIONAL日志组成员。

流的实例化:如果计划使用流的捕获来建立复制机制的话,那么目标数据库必须包含数据库对象的一个拷贝。如果这个拷贝不存在,在把变化数据复制到目标数据库前必须实例化这个对象。实例化的典型方法是利用exp/imp

在实例化之前需要对表进行准备,使得捕获进程知道从哪个SCN开始捕捉表的修改。通过调用这个准备过程,记录每个对象的最小SCN号,这个最小的SCN号会被用来进行对象的实例化。

当满足下列任意条件时,必须执行准备过程来同步流机制相关的数据字典信息:

捕获进程的规则组中填加一个或多个规则;(通过DBMS_RULE_ADM包填加的规则需要手工进行准备,通过DBMS_STREAMS_ADM包填加的规则会自动进行准备工作)

捕获进程的规则组中修改一个或多个规则;

传播进程的规则组中填加一个或多个规则;

传播进程的规则组中修改一个或多个规则;

流机制建立的数据字典在源数据库和目标数据库是异步的,当执行准备过程时,源数据库会讲流数据字典填加到重做日志中,当日志中的内容传播到目标数据库时,目标数据库会同步流的数据字典信息。

当使用EXP/IMP进行实例化时,表的SUPPLEMENTAL LOG GROUP仍然会保留。但是数据库级的SUPPLEMENTAL LOG则不会保留,即使执行的全库EXP/IMP

开始SCN、捕捉SCN和应用SCN

开始SCN:捕获进程开始捕捉变化的SCN号。默认情况下开始SCN对应着捕获进程建立的SCN。如果建立捕获进程之后之后没有直接启动而是在两天以后开始启动捕获,那么捕获进程会自动到归档日志中去寻找两天前的日志,找到建立捕获进程的SCN,然后开始捕捉。可以在建立的时候设置捕获进程的开始捕获SCN,也可以改变捕获进程的开始捕获SCN,但是必须保证开始捕获SCN必须大于第一个捕获进程在数据库中的建立SCN

捕获SCN:指捕获进程所捕获的最近修改的SCN

应用SCN:捕获进程的应用SCN指相关应用进程最后出队列的事件的SCN

捕获进程与RESTRICTED SESSION:当数据库使用STARTUP RESTRICT模式启动的时候,捕获进程不会启动,只有数据库关闭正常启动后,捕获进程才会启动。如果使用ALTER SYSTEM ENABLE RESTRICTED SESSION语句,则不会影响当前已经启动的捕获进程。如果停掉捕获进程,则捕获进程只能当DISABLE RESTRICTED SESSION的时候才能重新启动。

捕获进程与RAC环境:如果在RAC环境中配置了一个或多个捕获进程,则必须满足以下条件:

RAC环境中,捕获进程必须读取所有的实例的修改,因此必须读取归档重做日志。这要求归档重做日志必须对每个实例都是可以访问的;

DBMS_CAPTURE_ADM.START_CAPTURE过程的调用必须在拥有捕获进程队列的那个实例进行。对其他过程和函数的调用则可以在任意一个实例中进行;

SUPPLEMENTAL LOG的说明必须在每个实例上进行。如果实例关闭都重启,不需要再次说明,也不需要对新增实例进行说明;

初始化参数ARCHIVE_LAG_TARGET必须设置为大于0的值。

如果包含捕获进程队列的实例不可用,则队列的所有权自动转换到RAC的其他实例上。如果这种情况发生,需要连接到拥有队列的实例,执行START_CAPTURE过程来重新启动捕获进程。可以通过DBA_QUEUE_TABLES数据字断表来查询队列表拥有实例。

捕获进程结构:

捕获进程是ORACLE后台进程,进程的名称是cpnnnn是捕获进程编号,范围是0199。捕获进程使用LOGMINER机制从在线重做日志中捕获变化,流机制会自动配置LOGMINER。可以创建、修改、启动、停止和删除捕获进程,且可以建立捕获规则来控制捕获哪些改变。

捕获进程的成员:

当捕获进程并行参数设置大于等于3时,则捕获进程包括:

一个reader server:从联机重做日志中读取修改。

一定数量的preparer servers:将reader server发现的修改格式化为LCR。数量等于并行参数设置减2

一个builder server:将preparer servers创建的LCR按照SCN顺序合并,合并后将LCR加入到于捕获进程关联的序列中。

LOGMINER的设置:

由于捕获进程需要使用LOGMINER,且LOGMINER默认表空间为SYSTEM,应该使用DBMS_LOGMNR_D.SET_TABLESPACE过程为LOGMINER设置单独的表空间。

当一个数据库中运行多个捕获进程的时候,需要将初始化参数LOGMNR_MAX_PERSISTENT_SESSIONS的值大于等于捕获进程数。且需要适当增加SGA的大小。

捕获进程可以通过DBMS_STREAMS_ADM包和DBMS_CAPTURE_ADM建立。由于使用了很多默认设置,利用DBMS_STREAMS_ADM包建立捕获进程相对简单,使用DBMS_CAPTURE_ADM包可以进行更加灵活的设置。

如果使用DBMS_CAPTURE_ADM包的CREATE_CAPTURE过程来创建捕获进程,则需要手工调用准备过程PREPARE_TABLE(SCHEMA/GLOBAL)_INSTANTIATION,为捕获进行准备工作。

以下过程可以创建捕获进程:

DBMS_STREAMS_ADM.ADD_TABLE_RULESDBMS_STREAMS_ADM.ADD_SCHEMA_RULESDBMS_STREAM_AMD.ADD_GLOBAL_RULESDBMS_CAPTURE_ADM.CREATE_CAPTURE

注意:一旦建立了捕获进程就不要再修改数据库的DBIDDBNAME

创建数据字典副本:当数据库中第一次创建捕获进程的时候,流会建立数据字典的副本——流数据字典,用来进行捕获和传播。开始时,流数据字典和主数据字典在捕获进程创建时是一致的。

由于捕获进程从重做日志中捕获的动作要比系统中的实时修改要慢,而已,捕获进程可能被停止,因此为捕获进程创建单独的数据字典是必要的。因为捕获进程必须使用当时的数据字典来进行捕获,而这时的主数据字典可能已经发生了变化。

流数据字典在捕获进程捕获到DDL语句时进行更新。流数据字典根据DDL发生的时间进行更新,从而保证了流数据字典总可以正确的对应捕获进程所需的字典信息。

当捕获进程决定是否对表的DDL进行捕获,捕获进程会自动将修改信息添加到流数据字典。Oracle评估捕获规则,只要有一个规则评估为TRUEMAYBE,则流数据字典的修改被捕获进程捕获。

由于流数据字典的创建是在第一次建立捕获过程的时候,因此第一次创建捕获过程需要较多的时间,具体时间长短取决于数据库中对象的数量。

多个捕获进程使用同一个流数据字典。由于流数据字典是多版本的,每个捕获进程都和流数据字典是同步的。

归档模式和捕获进程:如果可能捕获进程就会读取联机重做日志,否则就读取归档重做日志。因此,数据库必须配置为归档模式。查询视图DBA_CAPTUREAPPLY_SCN列可以确定应用进程出队列的最近的SCN。当捕获进程落后了,捕获进程会进行从读联机重做日志到读归档重做日志的无缝转换,当捕获进程赶上以后,也会进行从读归档重做日志到读联机重做日志的无缝转换。

捕获进程参数:

常用的捕获进程参数包括:并行度parallelism和捕获进程启动停止的限制disable_on_limittime_limitmessage_limit

捕获进程规则的评估:

1、在重做日志中发现修改

2、重做日志中修改的预过滤。如果日志中的修改在转化为LCR后,会使得一个以上的规则评估为TRUE,则修改记录被保留,否则,修改记录被过滤。

3、将预过滤的修改转化为LCR

4、执行LCR过滤。这一步,LCR被分为两部分,一部分将被加入到队列中,另一部分将被丢弃。

5、丢弃那些不加入到队列的LCR

6、将剩余LCR添加到队列中。

捕获进程状态维持:

捕获进程在数据库关闭并重启后会维持关闭前的状态。

yangtingkun 发表于:2006.01.04 20:26 ::分类: ( 读书笔记 ) ::阅读:(61944次) :: 评论 (8)
re: 流捕获进程——流 [回复]

我最近在看流复制的有关文章,觉得你写的很好。
只是我在自己这边一直都没有配置成功。
你能帮帮我吗?

阿华 评论于: 2008.04.29 16:35
re: 流捕获进程——流 [回复]

我的邮箱:jinyehouse@sina.com

阿华 评论于: 2008.04.29 16:36
re: 流捕获进程——流 [回复]

建议楼上的参考Oracle的官方文档进行配置

如果真的有问题,可以在论坛里面将问题详细描述出来。

yangtingkun 评论于: 2008.05.04 14:34
re: 流捕获进程——流 [回复]

配置成功了。数据也可以正常的复制过去了。
只是我们这边的表中有一种特殊的字段类型,oracle不支持,错误如下:
ORA-26744: STREAMS capture process "CAPTURE_CQ" does not support "LANDINFO"."TGEOC_DJ_PARCEL_5H" because of the following reason: ORA-26783: Column data type not supported
有没有好的方法解决特殊字段类型的问题呢?

阿华 评论于: 2008.05.16 10:12
re: 流捕获进程——流 [回复]

11069633 我的qq号码
能加我吗?有问题向请教你!

阿华 评论于: 2008.05.16 10:24
re: 流捕获进程——流 [回复]

没有办法,流还有很多不支持的数据类型。

检查一下最新的Oracle版本,看看是否已经支持,如果支持,那么可以考虑升级数据库,如果也不支持,那么就没有其他的办法了。

除非你可以考虑用其他支持的数据类型来替代这个数据类型。

btw:已经很长时间不使用qq了,如果是针对我BLOG的问题,就在这里提出吧,如果是其他的问题,可以到ITPUB论坛中发贴提问。

yangtingkun 评论于: 2008.05.20 11:09
re: 流捕获进程——流 [回复]

我最近又碰到一个问题。
我的源库是带分区的 比如 有2个分区 A B
现在希望把分区 A 的数据传播到 数据库1
希望把分区 B 的数据传播到 数据库2
实现上面的功能,修改流的规则可以达到吗?
如果可以,请简单说一下该怎么设置这种类型的规则!
不胜感谢!!!

阿华 评论于: 2008.05.23 11:16
re: 流捕获进程——流 [回复]

通过分区列上设置过滤条件应该是可以实现的。

yangtingkun 评论于: 2008.05.27 15:48

发表评论
标题

在此添加评论
表情符号: smile laughing tongue angry crying sad wassat wink

称呼

邮箱地址(可选)

个人主页(可选)

 authimage


切换风格
新闻聚合
博客日历
文章归档...
最新发表...
最新评论...
最多阅读文章...
最多评论文章...
博客统计...
Blog信息
网站链接...