Oracle中如何解决ORA-01555错误

技术Oracle中如何解决ORA-01555错误这篇文章给大家分享的是有关Oracle中如何解决ORA-01555错误的内容。小编觉得挺实用的,因此分享给大家做个参考,一起跟随小编过来看看吧。11.6 ORA-01555

本文是关于如何解决Oracle中的ORA-01555错误。我觉得边肖很实用,就和大家分享一下作为参考。让我们跟着边肖看一看。

11.6 ORA-01555:快照太旧。

ORA-01555错误是什么?

ORA-01555是Oracle数据库运行中常见的错误。以下是甲骨文对ORA-01555错误的经典描述:

ORA-01555:快照太旧(回滚段太小)

原因:读取器一致读取所需的回滚记录有

被其他作者覆盖

简单地说,为确保一致性而读取的回滚段的数据会被其他写入进程覆盖。以下是一个典型的例子:

时间1:会话1开始查询A表。

时间2:会话2修改表a的记录X

时间点Session 1的查询语句查询记录X时,发现记录X被SCN号修改,修改时间(时间点2)晚于时间点1。这样,Oracle会在UNDO中记录X修改前的数据(简称之前镜像),以便一致读取。

时间4:会话2修改表A的记录Y并提交它。这样,该事务的槽数据可以被Oracle覆盖。

5: 00,会话2修改表A的记录Z并提交它。此时,由于UNDO表空间空间不足,记录Y修改前的数据被Oracle覆盖。

时间Session 1的查询语句查询记录Y时,发现记录Y被SCN号修改,修改时间(时间6)晚于时间1。因此,Oracle将通过保存在UNDO中记录的修改前的数据(称为图像前)来执行一致读取。然而,此时,记录Y的修改之前的数据已经在时间点5被覆盖。因此,系统将报告ORA-01555错误!

ORA-01555错误的原因和解决方法比较复杂,关于Oracle中错误处理的文章很多。本书一方面主要关注9i后的自动UNDO管理技术,另一方面只关注普通表的ORA-01555错误处理,没有关注LOB等特殊对象的ORA-01555错误处理。

如何获取ORA-01555错误的信息?

首先,分别从应用程序会话窗口和alert.log获取相关信息。

例如,应用程序会话窗口显示一条错误消息:

ORA-01555:快照太旧:名为“_SYSSMU1$”的回滚段编号9太小

根据警报日志:

ORA-01555由下面的SQL语句引起(查询持续时间=9999秒,SCN 33600x 000.008 a7 c2d)

其次,查询持续时间由alert.log决定.在上面的例子中,是9999秒。

第三,根据应用程序会话信息确定撤消段名称。示例:_ SYSSMU1 $

最后,确定UNDO表空间的UNDO _ retention值。

SQL显示参数撤销_保留

ORA-01555错误如何解决?

如果查询持续时间撤销保留

此时,Oracle无法保证在提交的事务到期时,即在UNDO_RETENTION时间之后,数据能够被一致地读取。

在这种情况下,最有效的解决方案是优化查询语句,减少语句的QUERY DURATION时间。如果无法优化,则只能通过引用QUERY DURATION时间值来扩展UNDO_RETENTION值,以确保Oracle可以将UNDO信息保存更长时间。

扩展UNDO_RETENTION值意味着需要更多的UNDO表空间,下面也将介绍UNDO表空间的计算方法。

如果查询持续时间=撤销保留

在这种情况下,通常UNDO表空间已满。如何进一步确定UNDO表空间是否已满?执行以下脚本:

将页面大小设置为25

设置线条大小120

选择inst_id,

to_char(begin_t

ime,’MM/DD/YYYY HH24:MI’) begin_time,
UNXPSTEALCNT “# Unexpired|Stolen”,
EXPSTEALCNT “# Expired|Reused”,
SSOLDERRCNT “ORA-1555|Error”,
NOSPACEERRCNT “Out-Of-space|Error”,
MAXQUERYLEN “Max Query|Length”
from gv$undostat
where begin_time between
to_date(‘<start time of the ORA-1555 query>’,’MM/DD/YYYY HH24:MI:SS’)
and
to_date(‘<time when ORA-1555 occured>’,’MM/DD/YYYY HH24:MI:SS’)
order by inst_id, begin_time;

其中:

  • UNXPSTEALCNT字段表示提交的Transaction Slots没有超出UNDO_RETENTION时间,也就是处于unexpired状态,但由于UNDO表空间满了,而被 Oracle覆盖了的次数。

  • <start time of the ORA-1555 query>时间可通过ORA-1555发生时间减去QUERY DURATION而得到。例如:

Tue May 26 16:16:57 2009
ORA-01555 caused by SQL statement below (SQL ID: 54yn3n36w24ft, Query Duration=922 sec, SCN: 0x0007.8a55f4e3)

922秒为15分22秒。这样 ORA-1555开始发生的时间为 May 26 16:01:35 2009(16:01:35 = 16:16:57 – 15:22)。

如何计算UNDO表空间大小?

UNDO表空间的计算公式如下:

UndoSpace = UR * (UPS * DBS)

其中:

  • UR = UNDO_RETENTION参数,单位为秒。

  • UPS = 每秒产生的UNDO数据块数量。

  • DBS = DB_BLOCK_SIZE参数。

上述UNDO_RETENTION、DB_BLOCK_SIZE可通过初始化参数文件获取,而UPS则可以通过查询v$undostat视图而获得。Oracle建议查询业务高峰时段产生的UNDO数据块数量。为此,执行如下查询:

SELECT undoblks / ((end_time – begin_time) * 86400) “Peak Undo Block Generation”

FROM v$undostat

WHERE undoblks = (SELECT MAX(undoblks) FROM v$undostat);

最终,计算高峰时段所需UNDO表空间大小的语句如下:

SELECT (UR * (UPS * DBS)) AS “Bytes”

FROM (SELECT value AS UR FROM v$parameter WHERE name = ‘undo_retention’),

(SELECT undoblks / ((end_time – begin_time) * 86400) AS UPS

FROM v$undostat

WHERE undoblks = (SELECT MAX(undoblks) FROM v$undostat)),

(SELECT block_size AS DBS

FROM dba_tablespaces

WHERE tablespace_name =

(SELECT UPPER(value)

FROM v$parameter

WHERE name = ‘undo_tablespace’));

11.7 ORA-30036: UNDO表空间无法扩展

什么叫ORA-30036错误?

ORA-30036也是Oracle数据库运行过程中常见的一个错误。以下就是Oracle关于ORA-30036错误的经典描述:

Error: ORA-30036 (ORA-30036)

Text: unable to extend segment by %s in undo tablespace ‘%s’

—————————————————————————

Cause: the specified undo tablespace has no more space available.

Action: Add more space to the undo tablespace before retrying the operation. An alternative is to wait until active transactions to commit.

该错误表示就是UNDO表空间不够了,简单解决办法就是对UNDO表空间进行扩容。但如同Oracle其它空间不够的类似错误一样,扩容并非唯一解决办法。

UNDO表空间分配算法

欲深入了解ORA-30036错误原因和解决办法,其实应从深入了解UNDO表空间分配算法开始。以下就是该算法主要思路:

  1. 如果当前的UNDO extent还有空间,则从中分配新的数据块。

  2. 否则,假设下一个extent过期(expired)了,则跳到(wrap)下一个extent,并且返回其第一个数据块。

  3. 假设下一个extent为非过期(unexpired)的,则尝试从UNDO表空间分配新的空间。假设 UNDO表空间足够,则分配新的extent给Undo segment,并且返回新extent的第一个数据块。

  4. 如果UNDO表空间不够了,则从offline状态的Undo Segment中去偷取过期(expired)的extent,分配给Undo segment,并且返回该extent的第一个数据块。

  5. 如果offline状态的Undo Segment中没有过期(expired)的extent,则从Online状态的Undo Segment中偷取过期(expired)的extent,分配给Undo segment,并且返回该extent的第一个数据块。

  6. 如果Undo表空间的数据文件是可扩展的,则扩展Undo表空间的数据文件,并且从中分配新的extent给Undo segment,以及返回该extent的第一个数据块。

  7. 降低Undo保存期限参数(undo_retention)10%,并从释放的空间中偷取extent。

  8. 从offline状态的Undo Segment中偷取非过期(unexpired)的extent。

  9. 重复使用现有Undo Segment中非过期(unexpired)的extent。如果所有extent都处于忙碌状态,即都包含了未提交的信息,则跳到第10步。否则,跳到(wrap)下一个extent。

  10. 从online状态的Undo Segment中偷取非过期(unexpired)的extent。

  11. 如果上述所有尝试都失败了,则Oracle报错:ORA-30036!

诊断和解决办法
  1. 首先,查询UNDO表空间的空间使用状况:

select sum(bytes) from dba_free_space where tablespace_name=’UNDOTBS1′;

select sum(bytes) from dba_data_files where tablespace_name=’UNDOTBS1′;

  1. 确定UNDO表空间的数据文件是否为可扩展的:

select autoextensible from dba_data_files where tablespace_name=’UNDOTBS1′;

  1. 按状态统计Undo Extents:

SELECT DISTINCT STATUS, SUM(BYTES), COUNT(*) FROM DBA_UNDO_EXTENTS GROUP BY STATUS;

如果没有过期(expired)而只有非过期(unexpired)的Undo Extent,以及Active Extents,则Undo表空间的确太小,需要对Undo表空间大小进行重新规划并扩容。关于Undo表空间大小的计算方法,请见本章前述内容。在10g中还可以通过OEM中的Undo Advisor特性来进行Undo表空间的规划。

假设Undo表空间不够,则Oracle会尝试偷取非过期(unexpired)的Undo Extent,此时可能会导致ORA-1555错误。如果也没有非过期(unexpired)的Undo Extent,则的确需要对Undo表空间进行扩容。

10g中可以为Undo表空间指定Guaranteed Undo Retention特性。例如:

create undo tablespace undotbs1 datafile ‘undotbs1.dbf’size 1000M autoextend on

retention guarantee;

这样,Oracle就不会重复使用非过期(unexpired)的Undo Extent。因此,此时只能对Undo表空间扩容了。

关于Bug 5442919

如果有过期(expired)的Undo Extent,意味着这些extent是可以被重用的。但系统却报出ORA-30036,则很有可能是撞上Oracle Bug 5442919了。以下就是满足该Bug的所有条件:

  1. undo_management=auto。

  2. Undo表空间包含的数据文件均不能自动扩展。

  3. DML操作失败并报ORA-30036错误,同时被写入log日志文件。而且alert.log中重复显示”Failure to extend rollback segment <us#>”,其中<us#>为相同值。

  4. 实例运行时间达到1小时以上。

  5. 系统存在大量offline的Undo Segment,例如1000个以上。

select count(*) from dba_rollback_segs where status=’OFFLINE’;

  1. Undo表空间满了。

  2. 存在大量过期(expired)或者非过期(unexpired)的Undo Extent。

select sum(bytes) “UNEXPIRED BYTES” from dba_undo_extents where tablespace_name=’UNDOTBS1’and status=’UNEXPIRED’;

select sum(bytes) “EXPIRED BYTES” from dba_undo_extents where tablespace_name=’UNDOTBS1’and status=’EXPIRED’;

该Bug在10.2.0.4以及11g中就已经修复了。在之前的版本,例如9i和10.2.0.1/2/3中,在某些平台可以向Oracle服务部门申请补丁回退(Backport),但这些版本早已经过了Oracle产品服务期,估计已经很难得到Oracle服务部门支持了。

感谢各位的阅读!关于“Oracle中如何解决ORA-01555错误”这篇文章就分享到这里了,希望

内容来源网络,如有侵权,联系删除,本文地址:https://www.230890.com/zhan/107939.html

(0)

相关推荐

  • 问所从来的所,《桃花源记》究竟讲了什么

    技术问所从来的所,《桃花源记》究竟讲了什么《桃花源记》——理想和现实的对白问所从来的所! 《桃花源记》是田园诗人陶渊明写的一篇散文诗般的短文,短文给我们描绘了一个乱世中的天堂——桃花源。这是一个质朴自然化的净土:她宁静和

    生活 2021年10月28日
  • Web中二次注入攻击原理的示例分析

    技术Web中二次注入攻击原理的示例分析这篇文章主要介绍Web中二次注入攻击原理的示例分析,文中介绍的非常详细,具有一定的参考价值,感兴趣的小伙伴们一定要看完!二次注入攻击二次注入攻击的测试地址:http://127.0.

    攻略 2021年11月7日
  • 如何修改图片大小尺寸,如何修改照片的尺寸和大小

    技术如何修改图片大小尺寸,如何修改照片的尺寸和大小使用美图秀秀可以做到如何修改图片大小尺寸。1、打开“美图秀秀”,点击“打开图片”,这里选择一个后缀为”jpg”图片文件。2、打开图片后,在屏幕的右下角点击”EXIF“,可

    生活 2021年10月20日
  • HashMap和HashTable的区别以及常见面试题是什么

    技术HashMap和HashTable的区别以及常见面试题是什么本篇文章为大家展示了HashMap和HashTable的区别以及常见面试题是什么,内容简明扼要并且容易理解,绝对能使你眼前一亮,通过这篇文章的详细介绍希望你

    攻略 2021年12月8日
  • 12月22号

    技术12月22号 12月22号在Ashx里面经常是有
    public void ProcessRequest(HttpContext context){context.Response.ContentTy

    礼包 2021年12月23日
  • 生信pheatmap绘制热图(pheatmap作图前数据)

    技术Pheatmap怎样绘制热图Pheatmap怎样绘制热图,相信很多没有经验的人对此束手无策,为此本文总结了问题出现的原因和解决方法,通过这篇文章希望你能解决这个问题。随机生成,10个基因,每个基因4个处理,每个处理3

    攻略 2021年12月20日