生产上还在使用GOLDENGATE HANDLECOLLISIONS

【背景】

经常有朋友遇到ogg数据不一致或者遇到ogg replicate进程abend,比如1403错误之类,然后排除原因,大部分出现问题都是配置问题(少数情况下是bug),会造成业务统计数据不准或者涉及金额更麻烦(大库就比较麻烦,尤其报表库,主库数据都删除,报表数据不准了,最后pk吧),ogg虽然入门相对简单,使用这些参数之前,一定了解作用以及什么场景下适合使用。另外hanlecollisions与allownoopdates配合使用时候,allownoopdates作用失效.

【以下操作容易数据不一致】

临时方案---跳过事务skip transaction或者alter replicat xx,begin now

长期方案---使用handlecollisions参数来保证ogg不会abend(有时候还会出现abend),这个使用比较多,经常在生产环境遇到这个参数。

初始化存在问题---使用expdp scn初始化(数据库活跃事务,参考上一篇expdp)

【handlecollisions作用】

hanlecollisions意思: handle是处理,collisions是冲突,组合在一起就是处理冲突.

数据同步冲突:更新删除无记录(丢失),插入主键冲突(重复插入)

使用场景:从源端初始化数据到目标端,数据库有实时操作影响初始化同步的表,例如extract捕获更新,然后删除记录,初始化完成后,目标端无此记录,ogg replicat会应该更新,删除---这个时候就出现冲突,使用handlecollisions来处理,等待目标断追平后应移除这个参数.

【handlecollisions如何处理冲突的危害】

有主键表非主键列进行更新或删除时找不到记录--1403错误--丢弃此操作--会造成数据不一致.

有主键表主键列进行更新时找不到记录--1403错误--此记录转换插入(等价于insertmissingupdates)--也可能会造成数据不一致或者无法插入非空记录abend.此时extract必须使用nocompressupdates或者fetchoptions fetchpkupdatecols来捕获完整记录(默认情况下数据库日志只记录主键值+修改列当前值,导致其他没有修改列无法获取,会造成更新转换插入后只有部分列有值)

有主键表插入重复记录---违反唯一约束--插入变成更新操作且stats统计不算更新,只算插入.

无主键表(所有列作为key,不存在非主键和主键更新)进行更新或删除时找不到记录--1403错误--丢弃此操作,不存在转换问题--会造成数据不一致.

无主键表(所有列作为key,不存在非主键和主键更新)插入重复记录---只能插入重复记录,无招。

【handlecollisions也会导致allownoopudates失效】

allownoopupdates是什么意思:

allow-noop-updates:由allow加上noop以及updates三部分组成,大概意思就是允许没有操作的更新;

allownoopudates应用场景[这个官方解释的]

对于源端存在的列,目标端没有列或者使用colsexcept排除列,进行更新这个列,此时目标端这个列,那么应该不进行更新就是noop操作--对于不管使用allownoopdates还是noallownoopdates配置,效果都一样.

对于更新列的值与之前值保持一致(set name='xiaoxu' where name='xiaoxu'),此时extract应该不会捕获这个值----这个说法是不严谨,这个只是针对主键值更新才说对,对于非主键列更新不适应。这个也属于noop

以下官方说法是片面,甚至存在错误,当非主键更新时候,extract会捕获更新列值,只有主键更新时候才说这样,trailfile中记录pkupdate也变成FiledComp.

对于不管使用allownoopdates还是noallownoopdates配置,效果都一样.

对于没有主键或者唯一索引的表,所有列作为key,此时如果更新任何列值与之前列值保持一致的话,那么就适应allownoopdates,如果使用noallownoopdates参数没有添加allownoopudates这个参数,会提示如下错误:

2018-10-14 15:28:52

ERROR OGG-01168 Encountered an update for target table TARGET.SOURCE, which has no unique key defined. KEYCOLS can be used to define a key. Use ALLOWNOOPUPDATES to process the update without applying it to the target database. Use APPLYNOOPUPDATES to force the update to be applied using all columns in both the SET and WHERE clause.

【handlecollisions与allownoopudates案例】

注释:handlecollisions与allownoopudates等价于applynoopupdates

没有hanlecollisions参数时allownoopupdates可以正常工作:

--源端更新

update source.source set address='shanghai' where id=1;

--目标端没有执行任何SQL,但是stats里面显示有一条

Opened trail file ./dirdat/tt000014 at 2018-10-14 20:26:05

Wildcard MAP resolved (entry SOURCE.*):

MAP "SOURCE"."SOURCE",TARGET TARGET."SOURCE";

Using following columns in default map by name:

ID, NAME, AGE, SEX, ADDRESS

Using the following key columns for target table TARGET.SOURCE: ID.

此处没有SQL

Sending STATS request to REPLICAT REPTT ...

Start of Statistics at 2018-10-14 20:14:27.

Replicating from SOURCE.SOURCE to TARGET.SOURCE:

*** Total statistics since 2018-10-14 20:14:26 ***

Total inserts 0.00

Total updates 1.00

Total deletes 0.00

Total discards 0.00

Total operations 1.0

hanlecollisions与allownoopupdates一起使用时候:

--源端更新

update source.source set address='shanghai' where id=1;

--目标端有执行SQL,但是stats里面显示有一条

***********************************************************************

** Run Time Messages **

***********************************************************************

Opened trail file ./dirdat/tt000014 at 2018-10-14 20:26:05

Wildcard MAP resolved (entry SOURCE.*):

MAP "SOURCE"."SOURCE",TARGET TARGET."SOURCE";

Using following columns in default map by name:

ID, NAME, AGE, SEX, ADDRESS

Using the following key columns for target table TARGET.SOURCE: ID.

UPDATE "TARGET"."SOURCE" SET "ID" = '1' WHERE "ID"='1'

Statement length: 54

(S)top display, (K)eep displaying (default):

Sending STATS request to REPLICAT REPTT ...

Start of Statistics at 2018-10-14 20:34:34.

Replicating from SOURCE.SOURCE to TARGET.SOURCE:

*** Total statistics since 2018-10-14 20:26:13 ***

Total inserts 0.00

Total updates 1.00

Total deletes 0.00

Total discards 0.00

Total operations 1.00

【总结】

至此handlecollisions除了初始化外,生产数据库还继续使用handlecollisions吗?虽然配置这个参数基本上可以一劳永逸的,活的潇潇洒洒,天天睡大觉,有一天分析数据部门找你麻烦,哈哈。

allownoopupdates基本上跟官方说的一样,但是好多场景下allownoopupdates与noallownoopupdates功能一致,且对于非主键列更新列值没有变化,这个是不适用,只使用主键列更新,ogg怎么知道主键列更新没有改变了?只要是trailfile里面pkupdate变成filedcomp,由主键更新变成普通列更新来判断.

  • 发表于:
  • 原文链接https://kuaibao.qq.com/s/20181014G1IIJ000?refer=cp_1026
  • 腾讯「腾讯云开发者社区」是腾讯内容开放平台帐号(企鹅号)传播渠道之一,根据《腾讯内容开放平台服务协议》转载发布内容。
  • 如有侵权,请联系 cloudcommunity@tencent.com 删除。

扫码关注腾讯云开发者

领取腾讯云代金券