【问题标题】:Django DB transactions and deadlocksDjango DB事务和死锁
【发布时间】:2012-06-28 03:12:41
【问题描述】:

在使用 Gunicorn 和多个进程/工作人员运行 Django 时,我的一些手动 MySQL 数据库事务遇到了死锁问题。

DatabaseError(1205, 'Lock wait timeout exceeded; try restarting transaction')

我的设置使用了多个数据库,并且我的函数需要传递给数据库才能在调用时使用。出于这个原因,我不能使用标准Django transaction decorators,因为数据库需要硬编码为参数。我检查了装饰器代码以了解事务是如何管理的,我的函数如下所示:

from django.db import connections

def process(self, db, data):

    # Takeover transaction management
    connections[db].enter_transaction_management(True)
    connections[db].managed(True)

    # Process
    try:
        # do things with my_objects...
        for obj in my_objects:
            obj.save(using=db)
        connections[db].commit()
    except Exception as e:
        connections[db].rollback()
    finally:
        connections[db].leave_transaction_management()

谁能发现这里可能出了什么问题?

【问题讨论】:

    标签: python mysql django mysql-python django-orm


    【解决方案1】:

    请注意,您可能希望使用更清晰的with 样式语法。以下内容应该与您上面的代码相同,但更复杂。

    from django.db import transaction
    from __future__ import with_statement
    
    def process(self, db, data):
    
        with transaction.commit_on_success(using=db):
            # do things with my_objects...
            for obj in my_objects:
                obj.save(using=db)
    

    或使用装饰器

    from django.db import transaction
    
    @transaction.commit_on_success(using=db)
    def process(self, db, data):    
    
        # do things with my_objects...
        for obj in my_objects:
            obj.save(using=db)
    

    但这并不能解决您的死锁问题..

    您可能会成功降低事务隔离级别。这在 mysql 上默认为REPEATABLE READ,这对于大多数用途来说太严格了。 (oracle 默认为READ COMMITTED')

    您可以通过将其添加到您的 settings.py 来实现此目的

    MYSQL_DATABASE_OPTIONS = {'init_command': 'SET storage_engine=INNODB; SET 
                     SESSION TRANSACTION ISOLATION LEVEL READ COMMITTED;'}
    
    DATABASES = {
      'default': {  # repeat for each db
           'ENGINE':  ... etc
           ...
           ...
           'OPTIONS': MYSQL_DATABASE_OPTIONS
          }
      }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2014-04-26
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多