事务和一致性

oracle的redo和undo机制保证了数据库的ACID特性,以及高性能和可恢复特性。

redo的数据是记录着数据块变更的顺序的正向数据流,

  1. commit时,保证redo同步持久化,保证高性能。
  2. 恢复的时候,顺序的应用日志。

redo的机制相对比较简单。

undo记录着数据块的前映像。

  1. 保证事务的特性,数据只有在commit后才可见。
  2. 提供读一致性,保证读写互不阻塞。

一方面,在undo segment header中transaction table中记录着事务,并在undo的record中维护着link list,实现事务的回滚。

另一方面,在数据块中intereted transaction list中保存着本事务对数据块的前映像的最新UBA,并在undo recored中
维护着link list,用于构建数据块的一致性读。

在正常的业务处理中,rollback属于比较少的情况,所以,oracle也特别优化了机制,commit的时间会非常的快,而rollback
因为要根据linked list顺序应用undo record,要比commit慢的多。

undo的机制相对比较复杂,这里就从两个不同的立足点去讨论

  1. 事务
  2. 表或者索引的数据块

1,事务

undo segment header包括了一般的数据块的通用结构,还包括了特殊的结构,
比如transaction table, extent retention table。
在8k大小的数据块中,每个undo segment header中的transaction table是有限的。比如下面的片段:

TRN TBL::

index state cflags wrap# uel scn dba parent-xid nub stmt_num cmt
------------------------------------------------------------------------------------------------
0x00 9 0x00 0x00f9 0x0011 0x0000.000e3357 0x008002be 0x0000.000.00000000 0x00000001 0x00000000 1326654543
0x01 9 0x00 0x00f9 0x0000 0x0000.000e3297 0x008002be 0x0000.000.00000000 0x00000001 0x00000000 1326654005
0x02 9 0x00 0x00f9 0x0006 0x0000.000e2fe0 0x008002bd 0x0000.000.00000000 0x00000001 0x00000000 1326652743
0x03 9 0x00 0x00f9 0x0008 0x0000.000e3153 0x008002be 0x0000.000.00000000 0x00000001 0x00000000 1326653343
0x04 9 0x00 0x00f9 0x002d 0x0000.000e30f3 0x008002bd 0x0000.000.00000000 0x00000001 0x00000000 1326653343
0x05 9 0x00 0x00f9 0x000c 0x0000.000e312a 0x008002be 0x0000.000.00000000 0x00000001 0x00000000 1326653343
.......

当事务为inactive状态,并且slot被重用的情况下,wrap#会向上递增。

这里有一点要注意:在oracle内容,持久化到文件的变更,db的restart都不会重置,而对于内存中的记录,比如动态性能视图,会被清除重置。

下面记录下事务的开始和结束进行的action:

1,begin transaction
2,写undo数据块变更的redo日志到redo buffer
3,变更undo数据块,包括,选择undo segment,transaction table entry,递增wrap#,更新state为10,即active。
4,commit 事务
5,写undo变更的redo
6,更新state为9,写入当前的scn到scn column中
7,同步等待lgwr写入完成

这里仅仅记录了在事务中,undo变化的过程。

注:在commit的时候,产生的所谓“redo commit record”,其实是undo segment header数据块变更的redo record。

在对事务的标示时,使用的是transaction id,这里唯一标识了一个事务,例如:0x0009.002.00002013
其包括:undo segment, entry,wrap#三部分。

所以,以事务为单位,在transaction table中可以看到以下信息:

1,事务(transaction id)的物理地址
2,事务的状态
3,事务提交的scn号
4,事务的最新的undo记录的地址
5,事务的undo记录量

查询这些信息不需要dump块,这里有一个视图x$ktuxe,但这个视图会扫描所有的undo segment header块。

select
indx,
ktuxesta,
ktuxecfl,
ktuxesqn wrap#,
ktuxescnw scnW,
ktuxescnb scnB,
ktuxerdbf dba_file,
ktuxerdbb dba_block,
ktuxesiz nub
from
x$ktuxe
where
ktuxeusn = 9
and ktuxeslt <= 5

注意:在oracle的官方文档中有一句“transactions don’t share undo blocks”,这里的意思是,这个事务own这个undo块,但如果这个事务是inactive的时候,

如果还有空闲空间,可是会被其它事务所使用。当undo要被清除的时候,oracle开辟一个块大小的buffer,然后format,而并非是从文件中读取块的内容。

2,表或者索引的数据块

下面看一下构建一致性块的过程
主要存在以下两种情况:

1,当事务未commit状态的时候,使用undo信息构建一致性块内容。
2,当块中事务commit的scn比当前query的scn大,使用undo 信息构建一致性内容。

这其中存在延迟块清除的情况:即当commit的时候,为了加快commit的时间,当事务更新的块较多的时候,仅仅更新了undo segment header中的transaction table中记录的事务的状态,当后面query到这个块的时候,进行块清除,即更改itl中事务的状态。

所以构建的主要过程:

1,在buffer中克隆这个块,下面的步骤都将应用在这个块上。
2,对这个块上所以commit的事务,进行块清除。
3,回滚没有提交的事务,应用undo record。
4,当commit的事务的scn大于query的scn时,就应用undo record。
5,重复第四步。

3,commit scn

fast commit:当事务commit的时候,仅仅修改transaction table的undo segment header这一个块,而跟修改的数据块的数量没有关系,修改这个块的redo vector就是所谓的commit record。
在oracle的演化过程中,oralce改变了fast commit,session memory中保存着(最多10% buffer cache)更改的块的list,当commit的时候,就会访问这些块,进行块清除。主要包括:

1,清理lock bytes
2,设置fsc/scn为commit的scn
3,设置commit的flag为C----
这个过程称为commit cleanout。

注:在这个过程中,仅仅更改transaction table slot中产生了redo日志,oracle优化了commit cleanout的过程。
其中,块的revisit并没有计入logical read,redo日志。

总结:

即:在事务的整个过程中,有两个重要的结构
1,itl
itl记录着事务的id,即txid,undo记录的地址UBA和commit scn,如果commit scn不可用,那么可以根据txid来确定undo segment header中的transaction table
slot中的信息,确定事务的状态,如果要构建一致性块,就根据UBA的地址找到undo record的链,回滚一致性的块内容。

2,transaction table
slot中记录着transaction的状态,最后更新的块的undo地址和commit scn,slot是有限的,当被重用的时候,会递增wrap#,wrap#数值是组成txid的一部分。
当事务回滚的时候,根据UBA地址,然后再undo record中有pointer指向想一个UBA,以此来回滚整个事务。
当slot被重用的时候,前一个事务的commit scn,uba地址会记录在下一个新事物的第一个undo record中,这样,就可以构建一致性的transaction table。

当事务根据UBA的链表查找的时候,发现当前undo record的seq#数值与当前不对,就会报出“ORA-01555”错误,说明undo块已经被重用。

Oracle core05_事务和一致性的更多相关文章

  1. 数据库事务隔离级ORACLE数据库事务隔离级别介绍

    本文系转载,原文地址:http://singo107.iteye.com/blog/1175084 数据库事务的隔离级别有4个,由低到高依次为Read uncommitted.Read committ ...

  2. Oracle之事务

    一,oracle的事务: 是指对数据操作的一系列动作的统称.即:事务的任务便是使数据库从一种状态变换成为另一种状态,这不同于文件系统,它是数据库所特用的. 事务有四大特性(ACID): 1,原子性(a ...

  3. 浅述Oracle分布式事务概念

    着系统的复杂性不断增加,我们所面对的分布式系统渐渐增加.分布式文件系统.分布式消息队列系统等等层出不穷,在一些行业特别是互联网行业应用广泛.分布式数据库也是目前使用比较常用的分布式系统之一. 简单来说 ...

  4. oracle如何保证读一致性 第二弹

    Oracle之数据库一致性读的原理 在Oracle数据库中,undo主要有三大作用:提供一致性读(Consistent Read).回滚事务(Rollback Transaction)以及实例恢复(I ...

  5. Oracle - 数据更新 - 事务

    /* 事务 事务是为了控制数据异步访问所使用的一种技术 就类似于java中的锁机制 synchronized,只不过功能更加强大 事务不能进行嵌套,当我们开启一个事务的之后作的每一次dml语句都属于这 ...

  6. oracle之事务和锁

    Oracle的事务和锁(PPT-I-283-293) 10.1 什么是事务 必须具备以下四个属性,简称ACID 属性:原子性(Atomicity):  事务是一个完整的操作.事务的各步操作是不可分的( ...

  7. 【Shashlik.EventBus】.NET 事件总线,分布式事务最终一致性

    [Shashlik.EventBus].NET 事件总线,分布式事务最终一致性 简介 github https://github.com/dotnet-shashlik/shashlik.eventb ...

  8. Oracle一个事务中的Insert和Update执行顺序

    今天碰到了一个奇怪的问题,是关于Oracle一个事务中的Insert和Update语句的执行顺序的问题. 首先详细说明下整个过程: 有三张表:A,B,C,Java代码中有一段代码是先在表A中插入一条数 ...

  9. [转]了解oracle自治事务

    http://blog.csdn.net/indexman/article/details/7799862 1.什么是Oracle自治事务 在官方文档中,是这样的定义的“Autonomous tran ...

随机推荐

  1. EF的TransactionScope

    TransactionScope是一个分布式事务的语句块,被包含起来的语句一起被提交,当出现异常,一起回滚,这都是托管的 当Web没有开启MSDTC服务时候会出现:

  2. c++ 学习之const专题之const成员函数

    一些成员函数改变对象,一些成员函数不改变对象. 例如: int Point::GetY() { return yVal; } 这个函数被调用时,不改变Point对象,而下面的函数改变Point对象: ...

  3. ITextSharp用来生成 PDF 的一个组件

    iTextSharp 是用来生成  PDF 的一个组件,在 1998 年夏天的时候,Bruno Lowagie ,iText 的创作者,参与了学校的一个项目,当时使用 HTML 来生成报告,但是,使用 ...

  4. mysql分区功能详细介绍,以及实例

    一,什么是数据库分区 前段时间写过一篇关于mysql分表的 的文章,下面来说一下什么是数据库分区,以mysql为例.mysql数据库中的数据是以文件的形势存在磁盘上的,默认放在/mysql/data下 ...

  5. swift-08-使用键值对儿统计字符在字符串中出现的次数

    // //  main.swift //  12- // //  Created by wanghy on 15/8/9. //  Copyright (c) 2015年 wanghy. All ri ...

  6. WordLight: highlights all occurrences of a selected text for VS2008

    https://visualstudiogallery.msdn.microsoft.com/ad686131-47d4-4c13-ada2-5b1a9019fb6f About This is a ...

  7. Spring Mvc 笔记二之异常和文件上传

    spring mvc的异常与文件上传 1.异常: spring注解版的异常有局部异常和全局异常                1.局部异常对单个controller有效;(在controller类写一 ...

  8. 常用数据与VARIANT之间的转换---从网上整理

    //头文件 1 #pragma once class VariantConvert { public: VariantConvert(void); ~VariantConvert(void); pub ...

  9. 日期字符串转换为NSDate

    // 纯数字日期 NSString *str1 = "; // 日期字符串 NSString *str2 = @"2015/05/12 10:22:01"; // 带时区 ...

  10. linux 文件操作编程

    Linux中所有的设备和文件的操作都使用文件描述符来进行. 文件描述符是一个非负的整数,它是一个索引值,指向内核中每个进程打开的记录表. 当打开一个文件或者创建一个新文件时,内核就向进程返回一个文件描 ...