Django事务:在覆盖save()方法的内部原子地管理两个不同的事务

时间:2015-06-08 15:48:21

标签: python django transactions

在Django 1.4中,我有一个如下代码:

from django.db import models
from django.db import transaction

class MyModel(models.Model):
    # model definition

    @transaction.commit_manually
    def save(self, *args, **kwargs):
        try:
            super(MyModel, self).save(*args, **kwargs)
            do_other_things()
        except:
            transaction.rollback()
            raise
        else:
            transaction.commit()
            obj2 = MySecondModel(mymodel = self, foo = "bar")
            obj2.save()


class MySecondModel(models.Model):
    myModelId = models.ForeignKey(MyModel)
    # other fields defining this model

正如您所看到的,在创建MyModel类的对象之后,我还必须创建另一个MySecondModel类的对象,该对象具有对第一个的引用。

在上面的代码中,如果在obj2.save()期间出现问题,则无法回滚第一个事务。

如何将这两个事务处理为唯一的原子事务?

1 个答案:

答案 0 :(得分:0)

正如Gocht在该问题的评论中所建议的那样,Django 1.4中的解决方案正在使用@transaction.commit_on_success()。代码可能是这样的:

from django.db import models
from django.db import transaction

class MyModel(models.Model):
    # model definition

    @transaction.commit_on_success()
    def save(self, *args, **kwargs):
        try:
            super(MyModel, self).save(*args, **kwargs)
            do_other_things()
            obj2 = MySecondModel(mymodel = self, foo = "bar")
            obj2.save()
        except:
            print 'exception'
            raise
        else:
            print 'job done'



class MySecondModel(models.Model):
    myModelId = models.ForeignKey(MyModel)
    # other fields defining this model