About nesting of database transactions

Source: Internet
Author: User
Tags commit getdate rollback

first, the basic concept

The SQL Server database engine ignores the commit of the internal transaction. The internal transaction is committed or rolled back according to the action taken at the end of the most external transaction. If an external transaction is committed, the internal nested transaction is also committed. If the external transaction is rolled back, all internal transactions are also rolled back, regardless of whether the internal transaction was committed separately.

The procedure for executing a nested transaction should be: As the transaction executes, the number of nested layers is incremented by one and then gradually decremented to the first layer. Whether the entire transaction is committed depends on the last layer running commit (commit) or rollback (rollback).

1. Each invocation of COMMIT TRANSACTION is applied to the last executed BEGIN TRANSACTION. If the BEGIN TRANSACTION statement is nested, then the COMMIT statement applies only to the last nested transaction, which is the most internal transaction. Even if the commit TRANSACTION transaction_name statement inside the nested transaction references the transaction name of the external transaction, the commit is applied only to the most internal transaction.

2. The transaction_name parameter of the ROLLBACK TRANSACTION statement refers to a set of internal transactions that name nested transactions is illegal, and transaction_name can only reference the transaction name of the most external transaction. If you execute an ROLLBACK TRANSACTION transaction_name statement that uses an external transaction name at any level of a set of nested transactions, all nested transactions are rolled back. If you execute an ROLLBACK TRANSACTION statement with no transaction_name parameter at any level of a set of nested transactions, all nested transactions are rolled back, including the most external transactions. (This paragraph means that only the first layer of the nested layer is allowed to use rollback rollback)

3, @ @TRANCOUNT function records the nesting level of the current transaction. Each BEGIN TRANSACTION statement increases the @ @TRANCOUNT by 1. Each COMMIT transaction statement causes the @ @TRANCOUNT minus 1.

A, a rollback TRANSACTION statement without a transaction name will roll back all nested transactions and reduce the @ @TRANCOUNT to 0.

B, ROLLBACK TRANSACTION, which uses a set of transaction names for the most external transactions in a nested transaction, rolls back all nested transactions and reduces the @ @TRANCOUNT to 0.

C, you can use the SELECT @ @TRANCOUNT to determine if the @ @TRANCOUNT is equal to 1 or greater than 1 when it is not possible to determine whether it is already in the transaction. If @ @TRANCOUNT equals 0, it indicates that it is not in a transaction.

Note: The above content is excerpted from--http://msdn.microsoft.com/zh-cn/library/ms189336.aspx

Second, the example illustrates:

1. Create a table to experiment with inserting data

CREATE TABLE Trantesttable (

T datetime

)

2. No transaction is used and the program runs with errors. However, the first statement inserts a record, and the second one does not insert a record.

Alter PROC TRANTEST2 (@errorTag int output)

As

BEGIN

INSERT into trantesttable values (GETDATE ())

INSERT into trantesttable values (' ... ')

END

3, see the following code, there are two layers of transaction nested use, TranTest1 nested call TranTest2, according to "one" in 1, 2 can draw the following code. Call TranTest1 is running normally and no records are inserted.

Alter PROC TranTest1 (@errorTag int output)

As

BEGIN

Set @errorTag = 0

Begin Transaction

DECLARE @errorTag2 int

EXEC TranTest2 @errorTag2 output–– call TranTest2 stored procedure

If @errorTag2 <0

BEGIN

Set @errorTag =-1

ROLLBACK TRANSACTION

RETURN

END

IF @ @TRANCOUNT > 0

COMMIT TRANSACTION

END

-----------TranTest2 Code------------

Alter PROC TRANTEST2 (@errorTag int output)

As

BEGIN

Set @errorTag = 0

Begin Transaction

INSERT into trantesttable values (GETDATE ())

INSERT into trantesttable values (' ... ')

If @ @error <> 0

BEGIN

Set @errorTag =-1

COMMIT TRANSACTION

RETURN

END

IF @ @TRANCOUNT > 0

COMMIT TRANSACTION

END

4, but TranTest2 is a separate stored procedure, may also be used directly to the use of the (outer layer does not nest transaction), TranTest2 is TranTest1 called and directly called the difference between the transaction nesting level is different. is called directly (there is no nested call), at this point in the TRANTEST2 is the first layer of transactions, encountered an exception should run ROLLBACK TRANSACTION the whole transaction rollback; called by TranTest1 (there is a nested call), The level of TranTest2 (@ @TRANCOUNT value) is 2, at which point the exception should run commit TRANSACTION, reduce the number of nesting layers by 1, and leave the transaction to the previous level, and finally the commit depends on whether the first layer is committed or rolled back;

To make TranTest2 stored procedures universal, you can decide whether to call commit or rollback based on the number of nested layers. If it is greater than 1, it indicates that there is a transaction package on it, and the transaction should be handed over to the previous layer. If it is 1, the entire transaction needs to be rolled back because there is no other place to roll back the transaction.

Alter PROC TRANTEST2 (@errorTag int output)

As

BEGIN

Set @errorTag = 0

Begin Transaction

INSERT into trantesttable values (GETDATE ())

INSERT into trantesttable values (' ... ')

If @ @error <> 0

BEGIN

Set @errorTag =-1

IF @ @TRANCOUNT > 1

COMMIT TRANSACTION

ELSE

ROLLBACK TRANSACTION

RETURN

END

IF @ @TRANCOUNT > 0

COMMIT TRANSACTION

END

5, finally will TranTest1 like TranTest2 change to have universality, because TranTest1 also do not know who will be called.

Alter PROC TranTest1 (@errorTag int output)

As

BEGIN

Set @errorTag = 0

Begin Transaction

DECLARE @errorTag2 int

EXEC TranTest2 @errorTag2 output

If @errorTag2 <0

BEGIN

Set @errorTag =-1

IF @ @TRANCOUNT > 1

COMMIT TRANSACTION

ELSE

ROLLBACK TRANSACTION

RETURN

END

IF @ @TRANCOUNT > 0

COMMIT TRANSACTION

END

Iii. Summary and finishing

 

To start a transaction in a stored procedure:

Following a principle, when a transaction is started, the value of @ @TRANCOUNT and the value of @ @TRANCOUNT at the end of the transaction are equal. Whether to commit or rollback in a transaction in the previous layer is determined by the rollback commit flag returned by the inner layer.

1, at the end of the normal completion of the transaction. At normal end of transaction, @ @TRANCOUNT minus 1.

IF @ @TRANCOUNT > 0

COMMIT TRANSACTION

A, if the outer layer does not have a nested transaction, then @ @TRANCOUNT = 1 Normal commit;

B, if the outer layer nested transactions, then @ @TRANCOUNT >1, run commit so that @ @TRANCOUNT-1, and return the correct system to run normal information, the real commit of the transaction to the outer transaction.

2. Exit the transaction midway through the transaction, and return the error flag (rollback flag).

IF @ @TRANCOUNT > 1

COMMIT TRANSACTION

ELSE

ROLLBACK TRANSACTION

RETURN

A, if the outer layer nested transactions, then satisfy if @ @TRANCOUNT > 1 conditions, Run commit so that @ @TRANCOUNT-1, and return an error message, the real rollback to the top-level transaction (by the upper layer according to this error message to determine the rollback).

B, if the outer layer does not have nested transactions, then @ @TRANCOUNT = 1, satisfy else, directly rollback;

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.