具有不同IsolationLevel的内部TransactionScope,如何实现? [英] Inner TransactionScope with different IsolationLevel, how can it be achieved?

查看:147
本文介绍了具有不同IsolationLevel的内部TransactionScope,如何实现?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

TransactionScope 的当前实现缺少更改嵌套作用域中的IsolationLevels的能力。

The current implementation of TransactionScope lacks the ability to change IsolationLevels in nested scopes.

MSDN 状态:使用嵌套的TransactionScope对象时,如果所有嵌套的作用域想要加入环境事务,则必须将它们配置为使用完全相同的隔离级别。如果嵌套的TransactionScope对象尝试加入环境事务,但它指定了不同的隔离级别,则会抛出 ArgumentException

MSDN states: When using nested TransactionScope objects, all nested scopes must be configured to use exactly the same isolation level if they want to join the ambient transaction. If a nested TransactionScope object tries to join the ambient transaction yet it specifies a different isolation level, an ArgumentException is thrown.

但是SQL Server允许我们可以随时更改隔离级别,为什么TransactionScope不允许?我不明白。

However SQL Server allows us to change Isolation Levels at any times we please, why doesn't the TransactionScope allow? I don't get it.

BCL中是否有任何有关嵌套SQL事务及其隔离级别的标准禁止这种行为。我有什么选择?我当然不能仅仅为了可以使用它们而设计类库并与它们一起提升隔离级别。

Are there any standards in the BCL about nested SQL Transactions and their isolation levels that prohibits this behavior. What are my options? I certainly cannot design class libraries and promote Isolation Levels along with them just for the sake that they can be used.

如果方法 A()需要快照级别,并调用要 Read Committed 级别的方法B()。方法 A()在我开发的LibraryA中,方法 B()在虚拟公司开发的LibraryB中。 A()如何在不获取 ArgumentException 的情况下调用 B()

If method A() wants a Snapshot level and calls method B() which wants Read Committed level. Method A() is in LibraryA which is developed by me, method B() is in LibraryB which is developed by a fictitious company. How can A() call B() without getting ArgumentException?

推荐答案

与任何特定产品相比,这更多是理论问题。基本上,交易的原始概念具有所有ACID属性:原子,一致,隔离和持久。

This is more a question of theory than of any particular product. Basically, the original notion of a transaction is something that has all the ACID properties: Atomic, Consistent, Isolated, and Durable.

http://databases.about.com/od/specificproducts/a/acid.htm

现在,请考虑隔离级别的含义:本质上,出于性能或其他原因,我们可以选择放弃数据库对ACIDity的部分或全部保证。隔离性和原子性密切相关,就像彼此之间的双重性。

Now, consider what is meant by "isolation level": essentially, for performance or other reasons, we may choose to forego some or all of the guarantees that the database makes concerning ACIDity. Isolation and atomicity are intimately related, like a dual of each other. Break one, and the other suffers.

将事务分解成在特定的SQL语句中可单独表达的部分是很常见的,但是为了保证您的帮助,您需要将它们包装在交易中,并且至少要有足够的隔离度,以使整个涂片正常工作。

It's common to break a transaction into the parts that are individually expressible in particular SQL statements, but for your guarantees to help at all, you need to wrap them up in a transaction with at least enough isolation for the whole shmear to work properly.

现在,如果交易的某些部分需要更大程度的隔离,那么整个事务也会执行,否则可能会在敏感部分中断。相反,如果某个部分的隔离度较低,那么很可能是该部分的正常功能需要的隔离度较低。 (不要问我何时提供一个很好的例子。)

Now, if some fraction of your transaction requires a greater degree of isolation, then the whole transaction does also, or else it could break during the sensitive part. Conversely, if some part is given a lower level of isolation, then it could well be that the proper function of that part requires less isolation. (Don't ask me to come up with a good example of when this could be true.)

无论如何,数据库服务器无法告知实际需求是兼容的,因此完全放弃了这个问题。

Anyway, the database server has no way of telling if the actual requirements are compatible, so it gives up on the problem altogether.

真正应该发生的事情是人们开发所需的交易。我意识到这并不总是那么容易,但是鉴于您的业务数据模式仅由您自己决定,将随机SQL组件插入在一起并不容易。

What's really supposed to happen is that people develop the transactions they need. I realize this isn't always easy, but in light of the fact that your business data schema is yours alone, it's not supposed to be easy to plug random SQL components together.

在处理集中式数据库(例如SQL Server)的情况下,最佳实践是设计整个事务,然后当您注意到设计之间的共性时,可以在编写冗长的代码之前将其排除在外。

In the case of dealing with centralized databases (like SQL Server) the best practice is to design entire transactions, and then as you notice commonality among the designs, you can factor it out possibly before you write hairy code.

如果您确实需要在不同数据存储库(或类似存储库)之间进行协调,则需要使用分布式事务管理器。这是一个单独的产品,比数据库服务器更难解决。但这对于诸如ATM之类的东西是必不可少的,这些东西要么给你钱要么不给你,要么打到你的银行账户要么不给你,而这两个必须匹配。

If you really need to coordinate among different data repositories (or similar) then a distributed transaction manager is called for. It's a separate product, and even more difficult to get right than a database server. But that's necessary for things like ATMs which either give you money or don't, and which either hit your bank account or don't, and those two have to match.

祝你好运!

这篇关于具有不同IsolationLevel的内部TransactionScope,如何实现?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆