ORA-01591错误故障处理

摘要:

在访问某些表的特定行时报ORA-01591错误

select

* from BF_INCOME_EXPENSES_T

where

account_id = 36816153

and

user_id = 39964213

and

city_code = '185'

ORA-01591:锁定已被有问题的分配事务处理72.0.1608712挂起

SQL>

select count(*) from UNITELE.BI_MQSYNC_SOURCE_CONTROL_T1;

ORA-01591:锁定已被有问题的分配事务处理72.0.1608712挂起

由于该表是业务关键表,部分前台业务受到影响。

关键词:ORA-01591

DBA_2PC_PENDING分布式事务

1.故障分析

首先,在遇到ORA错误时,我们不可能知道每个ORA错误都是什么意思,所以通过oracle的联机文档查错误的cause和action可以让我们初步了解该错误。

01591, 00000,

"lock held by in-doubt distributed transaction %s"

//

*Cause:Trying to access resource that

is locked by a dead two-phase commit

//transaction that is in prepared

state.

//

*Action: DBA should query the pending_trans$ and related tables, and

attempt

//to repair network connection(s) to

coordinator and commit point.

//If timely repair is not possible, DBA

should contact DBA at commit

//point if known or end user for

correct outcome, or use heuristic

//default if given to issue a heuristic

commit or abort command to

//finalize the local portion of the

distributed transaction.

Oracle对ORA-01591错误的描述是"lock held by in-doubt

distributed transaction %s,由分布式事务持有锁造成的。通过错误的cause可以看到’Trying to access resource that is

locked by a dead two-phase commit transaction that is in prepared

state’该错误是由访问一个处于prepared状态的二阶段事务所持有锁的资源造成的。

下面简单介绍一下分布式事务。

分布式事务,简单来说,是指一个事务在本地和远程执行,本地需要等待确认远程的事务结束后,进行下一步本地的操作。如通过dblink

update远程数据库的一行记录,如果在执行过程中网络异常,或者其他事件导致本地数据库无法得知远程数据库的执行情况,此时就会发生in doublt的报错。此时需要dba介入,且需要分多种情况进行处理。

分布式事务的,会经历3个阶段:

1.PREPARE

PHASE:

1.1决定哪个数据库为commit point site。(注,参数文件中commit_point_strength值高的那个数据库为commit point

site)

1.2全局协调者(Global Coordinator)要求所有的点(除commit point

site外)做好commit或者rollback的准备。此时,对分布式事务的表加锁。

1.3所有分布式事务的节点将它的scn告知全局协调者。

1.4全局协调者取各个点的最大的scn作为分布式事务的scn。

至此,所有的点都完成了准备工作,我们开始进入COMMIT PHASE阶段,此时除commit point

site点外所有点的事务均为in doubt状态,直到COMMIT PHASE阶段结束。

2.COMMIT

PHASE:2.1 Global Coordinator将最大scn传到commit point site,要求其commit。2.2 commit point尝试commit或者rollback。分布式事务锁释放。2.3 commit point通知Global

Coordinator已经commit。2.4

Global Coordinator通知分布式事务的所有点进行commit。

3.FORGET

PHASE:3.1参与的点通知commit point

site他们已经完成commit,commit point

site就能忘记(forget)这个事务。3.2

commit point site在远程数据库上清除分布式事务信息。3.3 commit point

site通知Global Coordinator可以清除本地的分布式事务信息。3.4 Global Coordinator清除分布式事务信息。

有关分布式事务的详细信息请参阅oracle联机文档.

当前的分布式事务处于Two-Phase

Commit机制中的prepared阶段,这个阶段事务已经在表上加锁了,现在我们要访问这些表,但事务没有结束,一直持有锁,导致访问资源失败报ORA-01591。(在这里需要指出:分布式事务所持有的锁之所以堵塞读操作,是因为oralce不知道该显示哪个版本的数据)如果结束这个事务,那相应的锁也会释放,这样就能解决这个问题。我们知道要结束一个事务有两种办法:commit和rollback。现在我们尝试结束这个事务:

commit force

'72.0.1608712';

ORA-02058: no

prepared transaction found with ID 72.0.1608712

报错并没有发现prepared状态的事务,由于该事务是分布式事务,我们首先想到的是dba_2pc_pending这个试图

SQL> select

* from dba_2pc_pending;

no

rows selected

该试图并没有查到信息,所以我们无法用commit force结束这个分布式事务,那么现在我们查看是否存在该事务,通过实际报错,我们可以清晰的看到事务号为72.0.1608712,该事务在72号回滚段的0号事务槽上并且序列号是1608712,这时查询一个基表x$ktuxe,看看72号回滚段上是否有该事务。

SQL> SELECT

KTUXEUSN, KTUXESLT, KTUXESQN, /* Transaction ID */

2KTUXESTA

Status,

3KTUXECFL

Flags

4FROM x$ktuxe

5WHERE ktuxesta!='INACTIVE'

6AND ktuxeusn=

72;

KTUXEUSNKTUXESLTKTUXESQN STATUSFLAGS

----------

---------- ---------- ----------------

------------------------

7201608712 PREPAREDSCO|COL|REV|DEAD

通过x$ktuxe这个基表,我们看到确实存在这个事务,而且是prepared状态。

此时,我们基本清楚了这个问题的原因:当一个分布式事务死掉时,由于该事务没有正常结束,导致事务持有的锁一直没有释放,所以在访问这个事务涉及的资源时,申请不到锁资源,所以报ORA-01591。由于是分布式事务,当在dba_2pc_pending中查询不到事务信息时,我们是无法通过commit或者rollback结束该事务。

所以,我们目前的任务是模拟出这个分布式事务。由于dba_2pc_pending试图是依赖于pending_trans$这个表,同时事务是与session关联在一起的,所以我们需要手工往pending_trans$和pending_sessions$两个表中插入数据。

2.故障处理

SQL> alter

system disable distributed recovery;

系统已更改。

SQL> insert

into pending_trans$ (

2LOCAL_TRAN_ID,

3GLOBAL_TRAN_FMT,

4GLOBAL_ORACLE_ID,

5STATE,

6 STATUS,

7SESSION_VECTOR,

8RECO_VECTOR,

9TYPE#,

10FAIL_TIME,

11RECO_TIME)

12values( '72.0.1608712',

13306206,

14'XXXXXXX.12345.1.2.3',

15'prepared','P',

16hextoraw( '00000001' ),

17hextoraw( '00000000' ),

180, sysdate, sysdate );

已创建1行。

SQL> insert

into pending_sessions$

2values('72.0.1608712',

31, hextoraw('05004F003A1500000104'),

4'C', 0, 30258592, '',

5146

6);

已创建1行。

SQL>

commit;

提交完成。

SQL> alter

system enable distributed recovery;

系统已更改。

此时,查询dba_2pc_pending发现已有该事务,并且状态是我们模拟出的prepared状态

SQL> select

* from dba_2pc_pending;

LOCAL_TRAN_IDGLOBAL_TRAN_ID STATEMIX A TRAN_COMMENTFAIL_TIMEFORCE_TIME RETRY_TIME OS_USER

OS_TERMINAL HOSTDB_USER

COMMIT#

----------------

72.0.1608712XXXXXXX.12345.1.2.3preparedno12-11月-0812-11月-08

此时我们结束这个事务

SQL> COMMIT

FORCE '72.0.1608712';

提交完成。

再次查询dba_2pc_pending,发现事务是forced

commit状态,该事务已经结束。

SQL> select

* from dba_2pc_pending;

LOCAL_TRAN_IDGLOBAL_TRAN_ID STATEMIX A TRAN_COMMENTFAIL_TIMEFORCE_TIME RETRY_TIME OS_USER

OS_TERMINALHOSTDB_USER COMMIT#

----------------

72.0.1608712XXXXXXX.12345.1.2.3 forced commitno12-11月-08 12-11月-08 12-11月-08

通过x$kutxe查询事务信息,发现事务释放了回滚段,事务已经结束。

SQL> SELECT

KTUXEUSN, KTUXESLT, KTUXESQN, /* Transaction ID */

2KTUXESTA

Status,

3KTUXECFL

Flags

4FROM x$ktuxe

5WHERE ktuxesta!='INACTIVE'

6AND ktuxeusn=

72;

未选定行

此时,我们需要清除dba_2pc_pending中分布式事务的残余信息

SQL> alter

session set "_smu_debug_mode"=4;――在session级别设置回滚段处于手工管理模式,如果不设置这个参数,在回滚段自动管理模式下,清除事务信息会报错

会话已更改。

SQL>

execute DBMS_TRANSACTION.PURGE_LOST_DB_ENTRY('72.0.1608712');――用dbms包清除事务信息

PL/SQL过程已成功完成。

SQL> select

* from dba_2pc_pending;

未选定行

测试访问业务表

SQL> select

count(*) from UNITELE.BI_MQSYNC_SOURCE_CONTROL_T1;

COUNT(*)

----------

367

问题解决。

其实,我在另外一个客户处也碰到过类似问题,当时也是报ORA-01591,但是在dba_2pc_pending中可以查到prepared状态的事务,此时只需要commit

force结束这个事务,并清除事务信息就可以了。对于上面的案例,我怀疑开发商直接清除了分布式事务信息,但是事务并没有结束,导致锁资源得不到释放报ORA-01591。

总结:ORA-01591错误一般是由于分布式事务造成的,造成分布式事务失败的原因主要是库之间的网络突然中断,造成两个库中的事务信息不一致,所以会有残余的分布式事务信息。此时,要针对不同的事务状态做不同的处理。同时在遇到棘手的问题时,可以查询metalink,该案例参考metalink文档:NOTE:[@more@]

c 取oracle 错误代码,转载ORA-01591错误故障处理相关推荐

  1. Oracle 错误代码(ORA)对照表

    ORA-00001: 违反唯一约束条件 (.) 错误说明:当在唯一索引所对应的列上键入重复值时,会触发此异常. ORA-00017: 请求会话以设置跟踪事件 ORA-00018: 超出最大会话数 OR ...

  2. PLSQL连接Oracle数据库时报ORA 12154错误的解决方法

    pl/sql连接Oracle时遇到的问题: 解决办法:安装后将Oracle安装目录下的文件夹network(包括其中的子文件,其中主要是tnsnames.ora) 在pl/sql菜单–"工具 ...

  3. 【问题集锦】Oracle错误代码以及解决方案

    ORACLE错误代码目录 写在前边 ORA-17001=内部错误 ORA-17002=Io 异常 ORA-17003=无效的列索引 ORA-17004=无效的列类型 ORA-17005=不支持的列类型 ...

  4. Oracle 错误代码详解及解决方式--ORA

    ORA-00001: 违反唯一约束条件 (.) 错误说明:当在唯一索引所对应的列上键入重复值时,会触发此异常. ORA-00017: 请求会话以设置跟踪事件 ORA-00018: 超出最大会话数 OR ...

  5. ORACLE错误代码对照表

    ORA-00001: 违反唯一约束条件 (.) ORA-00017: 请求会话以设置跟踪事件 ORA-00018: 超出最大会话数 ORA-00019: 超出最大会话许可数 ORA-00020: 超出 ...

  6. oracle错误代码大全(超详细)

    本篇文章是对oracle错误代码进行了详细的总结与分析,需要的朋友参考下 ORA-00001: 违反唯一约束条件 (.) 错误说明:当在唯一索引所对应的列上键入重复值时,会触发此异常. ORA-000 ...

  7. Oracle错误代码大全

    ORA-00001: 违反唯一约束条件 (.) ORA-00017: 请求会话以设置跟踪事件 ORA-00018: 超出最大会话数 ORA-00019: 超出最大会话许可数 ORA-00020: 超出 ...

  8. Oracle 错误代码详解

    Oracle 错误代码详解及解决方式–ORA ORA-00001: 违反唯一约束条件 (.) 错误说明:当在唯一索引所对应的列上键入重复值时,会触发此异常. ORA-00017: 请求会话以设置跟踪事 ...

  9. oracle错误代码

    oracle错误代码 ORA-00001: 违反唯一约束条件 (.) 错误说明:当在唯一索引所对应的列上键入重复值时,会触发此异常. ORA-00017: 请求会话以设置跟踪事件 ORA-00018: ...

最新文章

  1. AndroidManifest.xml文件详解(activity)(三)四种工作模式
  2. 【转】关于HTTP中文翻译的讨论
  3. 自由自在休闲食品带给小资的冰淇淋生活
  4. Productivity Power Tools,对于Visual Studio 2017的15个扩展
  5. ssl1312ZP2502-[HAOI2006]旅行【图论,并查集】
  6. *【ZOJ - 3703】Happy Programming Contest(带优先级的01背包)
  7. MongoDB 计划从“Data Sprawl”中逃脱
  8. Java面向对象16种原则
  9. 数独终盘生成器(调试成果)
  10. 修改windows软件图标
  11. NFT 作品集推荐|Lululand《爱是永恒》
  12. 使用ssh工具登录亚马逊云服务器
  13. ECCV 2022 Oral | 无需微调即可泛化!RegAD:少样本异常检测新框架
  14. 【kafka】kafka 消费数据的时候 报错 (Re-) join group
  15. Java 中多态的概念以及前提条件
  16. RK方案OTG口 OTG与HOST切换
  17. STM32 OLED显示屏--SPI通信知识汇总
  18. 数字化的终局:赛博朋克?社会主义?
  19. 电子词典中鼠标取词的原理
  20. 天子呼来不上船,自称臣是酒中仙——我的嗜酒情节

热门文章

  1. java map 实例_java中map集合嵌套形式简单示例
  2. 玩转springboot2.x之自定义项目内自动配置
  3. 使用spring 配置数据源,并用数据源得到连接,操作sql
  4. Maven私服(一)
  5. html怎么隐藏y方向内容,如何隐藏scroll-Y纵向滚动条,并不影响内容滚动的方法...
  6. 基于JAVA+Servlet+JSP+MYSQL的企业员工投票系统
  7. 基于JAVA+SpringMVC+Mybatis+MYSQL的高校教学质量评价管理系统
  8. 5月7日MySQL 学习
  9. c++读取ini的Section节名
  10. GX works2 中的块的创建与使用方法