데이터베이스 트랜잭션의 기초 지식

봄이 유연하고 편리한 트랜잭션 관리 기능을 제공하지만,하지만 이러한 기능 자체가 작동 데이터베이스의 기본 트랜잭션 메커니즘을 기반으로합니다. Spring의 트랜잭션 관리 및 구성에 대한 자세한 내용은 데이터베이스 트랜잭션 학습의 기본으로 필요하다.


데이터베이스 트랜잭션 무엇 1.
"번영, 양측에 대한 손실." "이 문장은 트랜잭션, 단계별로 할 수있는 복잡한 많은 것들을 반영하기 위해 생각하지만, 그들은 중 하나을 적용하려면 전체, 또는 전체 실패로, 전체를 구성한다.이 데이터베이스에 반영 사고의 종류, 즉, 여러 SQL 문 또는 모두 성공하거나 모두 실패 수행합니다.

데이터베이스 트랜잭션이 엄격이 네 가지 속성을 만족해야하며, 정의 : 원 자성 (원자), 일관성 (일관성), 절연 (절연)과 지속성 (Durabiliy을), ACID라고도합니다. 다음은 각 기능에 대한 설명입니다.

1)의 원자 : 데이터베이스 조작 복수 구성된 트랜잭션의 모든 작업을 수행하는 경우에만 불가분 원자 단위 및 전체 트랜잭션 제출되어 나타낸다. 모든 데이터베이스 작업은 데이터베이스가 초기 상태로 복귀 될 수 있도록 수행 된 모든 작업은 철회되어야하며, 트랜잭션을 실패했습니다.

2) 일관성 다음 데이터베이스의 상태와 비즈니스 규칙이 동일한하는 성공적인 트랜잭션 작업 후, 데이터가 파괴되지 않습니다. 이러한 B 1백위안을 설명하기 계정 A로부터 전송 돈으로 관계없이 작업의 성공의 총 예금은 A와 B 계정이 변경되지 차지한다.

3) 분리 : 데이터의 동시 동작이 트랜잭션이 다른 각각의 데이터 공간을 가지며, 그것들은 다른 작동을 방해하지 않는다. 오히려, 요구 사항은 완전 무 간섭하지 않습니다. 데이터베이스 트랜잭션 격리 수준의 다양한 제공, 다른 분리 레벨은 데이터의 일관성이 더 크면 클수록, 간섭의 정도에 격리 수준을 해당하지만, 약한 동시성.

4) 내구성 : 트랜잭션이 성공적으로 커밋되면, 모든 작업에서 트랜잭션 데이터를 데이터베이스에 유지해야합니다. 트랜잭션이 데이터베이스는 즉시 충돌, 데이터베이스를 다시 시작 최선을 다하고 있습니다 후에도, 그 데이터가 어떤 메커니즘을 통해 복구 할 수 있는지 확인해야합니다.

이러한 거래 특성에서 데이터 "일관성"궁극적 인 목표이며, 다른 기능, 요구 사항 또는 수단을이 목표를 달성하기위한 조치입니다.

데이터베이스 관리 시스템은 일반적으로 재실행 로그 자성, 일관성과 내구성을 보장하기 위해 사용. 모든 움직임의 데이터베이스 변경, 데이터베이스 오류가 트랜잭션에서 작업의 구현의 출구 부분 이후에 발생한 중공업 실행 로그 기록, 당신은 데이터베이스가 심하게 실행 로그에서 수행 한 실행 취소 할 수 있습니다. 또한, 거래 할 수있는 데이터베이스 다시 시작할 때 영구 데이터가 로그를 기반으로하지 않은에서 데이터베이스 충돌, 해당 작업을 재 - 수행 할 경우에도 제시되었다.

그리고 트랜잭션을 보장하기 위해 데이터베이스 잠금 격리 메커니즘을 사용하여 객체 잠금 장치 유사한 스레드 동기화, 데이터베이스 관리 시스템을 사용하여 자바 프로그램. 여러 트랜잭션이 같은 데이터를 조작하려고 할 때 이전 트랜잭션이 완료된 후, 후속 트랜잭션이 데이터를 조작 할 수있는 기회를 가질 때까지, 트랜잭션 데이터는 잠금이 유지되고 작동합니다. 오라클 데이터베이스는 또한 장치의 데이터 버전을 사용, 데이터에 영향을주지 않고 데이터에 대한 변경의 버전을 저장 각 변화에 대한 롤백 데이터를 읽습니다.


2. 데이터 동시성 문제

데이터베이스는 여러 액세스 클라이언트를 가질 수있다, 이러한 클라이언트는 데이터베이스에 대한 동시 액세스를 사용할 수 있습니다.

필요한 검역 조치, 동시성 모든 종류의 문제로 이어질 데이터의 무결성을 훼손 촬영하지 않을 경우 데이터베이스에 동일한 데이터를 여러 사정에 의해 동시에 액세스 할 수 있습니다. 이러한 문제는 문제를 읽어 데이터의 세 가지 유형 (더티 읽기, 비 반복 읽기 및 팬텀 읽기) 및 2 급 데이터 업데이트 문제 (첫 번째 유형 및 업데이트 손실의 두 번째 유형의 업데이트를 잃었)를 포함, 다섯 개 가지 범주에 기인 할 수있다. 예는 다음 문제를 일으키는 현장을 설명합니다.

1) 더티 판독 (더티 판독)
는 데이터 B를 변경하는 트랜잭션이 커밋되지 않은 트랜잭션을 판독하고,이 데이터에 기초하여 작동된다. 당신이 B 트랜잭션이 일어날 경우, 트랜잭션 읽은 데이터는 단순히 인식되지 않는, 롤백됩니다. 동시 트랜잭션 및 뷰 창구 거래의 전송 더러운 장면을 읽을 때 발생합니다.

이 시나리오에서는, B 희망을 인출 $ 500 나중에 움직임을 철회하면서 동일한 계좌 이체 $ 100는 A, 트랜잭션은 읽기 때문에 데이터 B 트랜잭션이 헛된 계정 500 위안 손실의 결과, 제출하지 않은 . Oracle 데이터베이스에서, 더러운 읽기의 경우가 발생하지 않습니다.

2) 비 - 반복적으로 판독 (판독 반복 할 수없는)

트랜잭션 판독 비 반복 읽기가 범한 데이터 트랜잭션을 변경할 B를 의미한다. 철수는 트랜잭션 동안, B 100 위안 계정 전송이 있다고 가정 계정이의 균형이 불일치가 발생 읽습니다.

동일한 트랜잭션에서, 시간 T4 및 T7 시간 계정 예금 잔고 점은 일관성이 읽을 수 있습니다.

3) 환상 읽기 (점선)은 읽기

트랜잭션은 B에 의해 제출 된 새로운 트랜잭션 데이터를 읽고, 다음 팬텀은 문제가 나타납니다 업무를 읽습니다. 팬텀은 일반적으로 판독 된 통계 데이터 트랜잭션의 계산에서 일어난다. 예를 들어, 동일한 트랜잭션의 예금 계좌 통계에 두 번 금융 시스템의 총량, 통계적 공정 두 번, 단지 저축 계정을 추가 한 것으로 가정하고 두 번 다음 전체 통계 $ 100 입금 금액이 일치하지 않을 수 있습니다.

새로운 데이터는 단지 쿼리의 문제를 충족하는 경우, 새로운 데이터가 일치하지 통계 이가지 경우의 결과로, 거래의 시야를 입력합니다.

후자는 읽기 트랜잭션이 데이터 변경 (변경 또는 삭제)에 제출되었습니다에 의미있는 동안, 전자는 거래에 제출되었습니다 다른 새로운 데이터를 읽고 의미, 팬텀 읽기 및 비 반복 읽기는 두 개념을 혼동하기 쉽습니다. 어느 경우를 방지하기 위해 대책을하는 것은 다릅니다, 데이터는 데이터 작업 변경을 방지하기 위해 행 수준 잠금의 작동에 추가됩니다 읽은 데이터의 변경을 방지하기 위해, 새로운 데이터를 읽는 방지, 그것은 종종 필요 표 (방식의 여러 버전을 사용하여 Oracle 데이터) 새로운 데이터를 방지하기 위해 전체 테이블을 잠급니다 백열하나를 잠글 추가.

4) 제 1 카테고리 업데이트 누락

트랜잭션 철회 업데이트 데이터 B의 트랜잭션이 제출 커버하고있다합니다. 이 오류는 매우 심각한 문제, 그것은 다음과 같은 계정 인출 전송에서 볼 수있는 원인이 될 수 있습니다.

취소시 트랜잭션은 "실수로"B의 거래 금액은 계정에 전멸 전송 된 것입니다.

5) 제 2 카테고리 업데이트 누락

B 트랜잭션을 포함하는 트랜잭션 데이터는 조작을하는 B 회사의 손실의 결과로, 최선을 다하고있다.

체크 전송 트랜잭션이 예금의 인출을 업데이트했다 트랜잭션을 포함하기 때문에 위의 예에서, 은행은 마침내 $ 100 손실로 이어집니다. 제 1 이송 트랜잭션이 커밋 경우 반대로, 사용자 계정 100 위안 잃게됩니다.

 

3. 데이터베이스 잠금 장치

데이터 동시성은 많은 문제를 일으킬 수 있고, 어떤 경우에는 몇 가지 문제는 허용되지만 다른 경우에는 치명적일 수있다. 구현 세부 사항에 다른 데이터베이스의 차이가 있지만, 데이터베이스 잠금 장치는 동시 액세스하여 문제를 해결하기 위해,하지만 원리는 기본적으로 동일합니다.

按锁定的对象的不同,一般可以分为表锁定和行锁定。前者对整张表进行锁定,而后者对表中的特定行进行锁定。从并发事务锁定的关系上看,可以分为共享锁定和独占锁定。共享锁定会防止独占锁定,但允许其他的共享锁定。而独占锁定既防止其他的独占锁定,也防止其他的共享锁定。为了更改数据,数据库必须在进行更改的行上施加行独占锁定,INSERT、UPDATE、DELETE 和 SELECT FOR UPDATE 语句都会隐式采用必要的行锁定。下面介绍一下Oracle数据库常用的5种锁定。

1)行共享锁定:一般通过 SELECT FOR UPDATE 语句隐式获得行共享锁定,在Oracle中用户也可以通过 LOCK TABLE ROW SHARE MODE 语句显式获得行共享锁定。行共享锁定并不防止对数据行进行更改操作,但是可以防止其他会话获取独占性数据表锁定。允许进行多个并发的行共享和行独占锁定,还允许进行数据表的共享或者采用共享行独占锁定。

2)行独占锁定:通过一条 INSERT、UPDATE 或 DELETE 语句隐式获取,或者通过一条 LOCK TABLE IN ROW  EXCLUSIVE MODE语句显式获取。这种锁定可以防止其他会话获取一个共享锁定、共享行独占锁定或独占锁定。

3)表共享锁定:通过 LOCK TABLE IN SHARE MODE 语句显式获得。这种锁定可以防止其他会话获取行独占锁定(INSERT、UPDATE 或 DELETE),或者防止其他表共享行独占锁定或表独占锁定,但它允许在表中拥有多个行共享和表共享锁定。该锁定可以让会话具有对表事务级一致性访问,因为其他会话在用户提交或者回滚该事务并释放对该表的锁定之前不能更改这张被锁定的表。

4)表共享行独占锁定:通过 LOCK TABLE IN SHARE ROW EXCLUSIVE MODE 语句显式获得。这种锁定可以防止其他会话获取一个表共享、行独占或者表独占锁定,但允许其他行共享锁定。这种锁定类似于表共享锁定,只是一次只能对一张表放置一个表共享行独占锁定。如果A会话拥有该锁定,则B会话可以执行 SELECT FOR UPDATE操作;但如果B会话试图更新选择的行,则需要等待。

5)表独占锁定:通过 LOCK TABLE IN EXCLUSIVE MODE 语句显式获得。这种锁定可以防止其他会话对该表的任何其他锁定。

 

4.事务隔离级别

尽管数据库为用户提供了锁的DML操作方式,但直接使用锁管理是非常麻烦的,因此数据库为用户提供了自动锁机制。只要用户指定会话的事务隔离级别,数据库就会分析事务中的SQL语句,然后自动为事务操作的数据资源添加适合的锁。此外,数据库还会维护这些锁,当一个资源上的锁数目太多时,自动进行锁升级以提高系统的运行性能,而这一过程对用户来说完全是透明的。

ANSI/ISO SQL 92 标准定义了4个等级的事务隔离级别,在相同的数据环境下,使用相同的输入,执行相同的工作,根据不同的隔离级别,可能导致不同的结果。不同的事务隔离级别能够解决的数据并发问题的能力是不同的,如下表所示:

事务的隔离级别和数据库并发性是对立的。一般来说,使用 READ UNCOMMITED 隔离级别的数据库拥有最高的并发性和吞吐量,而使用 SERIALIZABLE 隔离级别的数据库并发性最低。

SQL 92 定义 READ UNCOMMITED 主要是为了提供非阻塞读的能力。Oracle 虽然也支持  READ  UNCOMMITED,但它不支持脏读;因为 Oracle 使用多版本机制彻底解决了在非阻塞读时读到脏数据的问题并保证读的一致性,所以,Oracle 的 READ COMMITTED 隔离级别就已经满足了 SQL 92 标准的 REPEATABLE READ 隔离级别。

SQL 92 推荐使用 REPEATABLE READ 以保证数据的读一致性,不过用户可以根据应用的需要选择适合的隔离等级。

 

5.JDBC对事务的支持

并不是所有的数据库都支持事务,即使支持事务的数据库也并非支持所有的事务隔离级别。用户可以通过 Connection#getMetaData() 方法获取 DatabaseMetaData 对象,并通过该对象的 supportsTransactions()、supportsTransactionIsoationLevel(int level) 方法查看底层数据库的事务支持情况。

Connection 默认情况下是自动提交的,即每条执行的 SQL 语句都对应一个事务。为了将多条SQL语句当成一个事务执行,必须先通过 Connection#setAutoCommit(false) 阻止 Connection 自动提交,并通过 Connection#setTransactionIsolation() 设置事务的隔离级别。Connection 中定义了对应 SQL 92 标准4个事务隔离级别的常量。通过 Connection#commit() 提交事务,通过 Connection#rollback() 回滚事务。下面是典型的 JDBC事务数据操作的代码,如下图所示。

在 JDBC 2.0 中,事务最终只能有两个操作:提交和回滚。但是,有些应用可能需要对事务进行更多的控制,而不是简单地提交或回滚。JDBC 3.0(Java1.4及以后的版本)引入了一个全新的保存点特性,Savepoint 接口允许用户将事务分割为多个阶段,用户可以指定回滚到事务的特定保存点,而并非像 JDBC 2.0 一样只能回滚到开始事务的点,如下图所示。

下面的代码使用了保存点功能,在发生特定问题时,回滚到指定的保存点,而非回滚整个事务,如下图所示。

并非所有数据库都支持保存点功能,用户可以通过 DatabaseMetaData#supportsSavepoints() 方法查看是否支持。

추천

출처www.cnblogs.com/jwen1994/p/11291827.html