我有一个观点函数结束。但是Django似乎在抱怨它没有。有任何想法吗?事务管理块未决的COMMIT/ROLLBACK
Django Version: 1.3
Exception Type: TransactionManagementError
Exception Value: Transaction managed block ended with pending COMMIT/ROLLBACK
编辑:没有其他异常正在抛出来改变代码路径。
我有一个观点函数结束。但是Django似乎在抱怨它没有。有任何想法吗?事务管理块未决的COMMIT/ROLLBACK
Django Version: 1.3
Exception Type: TransactionManagementError
Exception Value: Transaction managed block ended with pending COMMIT/ROLLBACK
编辑:没有其他异常正在抛出来改变代码路径。
在得到类似的问题并浪费了几个小时后,我想出了如何调试这种情况。
由于某种原因,@ transaction.commit_manually装饰器会使发生在函数中的异常无效。
暂时从您的函数中删除装饰器,您现在将看到异常,修复它并将装饰器放回!
我遇到了同样的问题,并尝试过各种方法。这是对我有用的东西,但我不确定这是否是正确的做法。将您的退货声明更改为:
with transaction.commit_on_success():
return render(request, "template.html", {
'status': status,
})
Django Pros,这是正确的做法吗?
当代码中发生未处理的异常时,总会发生这种情况。在我的情况下,出于某种原因,这个例外情况并没有引发给调试器,这对我造成了困惑。
这是我怀疑的。但是,如果有例外,我无法看到它,我已经尝试过了!最后,我决定用不同的方式解决交易问题,而用我的新方法,我没有看到我期望看到的例外。 – Joe 2011-04-15 15:35:58
我有同样的问题。我发现的唯一解决方案是使用try/finally子句来确保渲染后发生提交。
@transaction.commit_manually
def xyz(request):
committed = False
try:
if ABC:
success = something()
if success:
status = "success"
transaction.commit()
committed = True
else:
status = "dataerrors"
transaction.rollback()
committed = True
else:
status = "uploadproblem"
transaction.rollback()
committed = True
return render(request, "template.html", {
'status': status,
})
finally:
if not committed:
transaction.rollback() # or .commit() depending on your error-handling logic
没有意义,但它对我有用。
这对我有效。另外,我发现如果我想作为正常流程的一部分进行回滚(而不是例外),那么我必须创建一个异常(x = 1/0)来确保最终以回滚结束。也许是因为我的整个功能都处于试验阶段。 – user984003 2012-10-22 12:57:34
这是一个很好的解决方案,但是可以使用'transaction.is_dirty()'来代替使用'commited'变量。如果可以的话,请检查django事务中间件,它们完全相同。 – Hassek 2014-01-30 00:33:10
我有类似的问题,也许这个代码工作正常,为您提供:
@transaction.commit_on_success
def xyz(request):
if ABC:
success = something()
if success:
status = "success"
else:
status = "dataerrors"
transaction.rollback()
else:
status = "uploadproblem"
transaction.rollback()
return render(request, "template.html", {
'status': status,
})
我有同样的问题,得知即使你正确手动关闭交易中的异常的情况下,如果再写入在手动事务范围内再次使用orm,似乎以某种方式重新打开事务并导致事务异常。
with transaction.commit_manually():
try:
<exciting stuff>
transaction.commit()
except Exception, e:
transaction.rollback()
o.error='failed' <== caused transaction exception
您可能会看到此问题的另一个原因是系统中有多个db。
我是能够克服这种错误与
@transaction.commit_manually(using='my_other_db')
def foo():
try:
<db query>
transaction.commit(using='my_other_db')
except:
transaction.rollback(using='my_other_db')
把你的代码中的try/except块。在拦网除外只是做了transaction.rollback并记录异常对象。
@transaction.commit_manually
def xyz(xyz):
try:
some_logic
transaction.commit()
except Exception,e:
transaction.rollback()
print str(e)
您确定这是与被接受的答案提出的要点兼容吗? – Joe 2015-02-27 17:20:06
正如其他人所说,装饰功能中发生的异常“丢失”,因为它们是由TransactionManagementError
例外覆盖。
我建议扩展transaction.commit_manually
修饰符。我的装饰器transaction_commit_manually
内部使用transaction.commit_manually
修饰器;如果在装饰函数中发生异常,我的装饰器捕获异常,执行transaction.rollback()
并再次引发异常。因此事务被正确地清除,并且原始异常不会丢失。
def _create_decorator_transaction_commit_manually(using=None):
def deco(f):
def g(*args, **kwargs):
try:
out = f(*args, **kwargs)
except Exception as e:
if using is not None:
transaction.rollback(using=using)
else:
transaction.rollback()
raise e
return out
if using is not None:
return transaction.commit_manually(using=using)(g)
return transaction.commit_manually(g)
return deco
def transaction_commit_manually(*args, **kwargs):
"""
Improved transaction.commit_manually that does not hide exceptions.
If an exception occurs, rollback work and raise exception again
"""
# If 'using' keyword is provided, return a decorator
if 'using' in kwargs:
return _create_decorator_transaction_commit_manually(using=kwargs['using'])
# If 'using' keyword is not provided, act as a decorator:
# first argument is function to be decorated; return modified function
f = args[0]
deco = _create_decorator_transaction_commit_manually()
return deco(f)
“ABC”是否定义在其他地方? – 2011-04-13 11:32:25
你在使用postgres吗?这些可能是相关的:[这里](http://groups.google.com/group/django-users/browse_thread/thread/9b85e45d8fc015d2)和[这里](https://groups.google.com/group/django- cms/browse_thread/thread/3f8b1c10faa773f3/dddbc3b93b658e80?#dddbc3b93b658e80) – DTing 2011-04-13 12:08:03
是的,ABC定义为抱歉。在热情的来源清洁! – Joe 2011-04-13 12:57:17