views:

453

answers:

2

I'm trying to use Django transactions on MySQL with the commit_on_success decorator. According to the documentation, "If the function raises an exception, though, Django will roll back the transaction." However, this doesn't seem to work for me:

>>> @transaction.commit_on_success
... def fails():
...     Site.objects.create(name="New Site", ip_address="127.0.0.1")
...     raise ValueError("oh noes!")
... 
>>> Site.objects.count()   
2
>>> fails()
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "/usr/local/lib/python2.6/site-packages/django/db/transaction.py", line 240, in _commit_on_success
    res = func(*args, **kw)
  File "<stdin>", line 4, in fails
ValueError: oh noes!
>>> Site.objects.count()
3
>>>

I'm pretty sure that MySQL supports transactions; do I need to use a different table type or something?

+1  A: 

Apparently MySQL doesn't support transactions with MyISAM tables, which is the default type of tables. InnoDB tables do support transactions, so I'll recreate the tables and then see whether the transactions work then.

Eli Courtwright
Defaulting to table storage that doesn't support transactions is enough to convince me never to go near MySQL. That's like a car with airbags that you have to turn on yourself. Frankly, it's so absurd that I'd be afraid of what other broken defaults they have lying in wait.
Glenn Maynard
+1  A: 

From http://docs.djangoproject.com/en/dev/ref/databases/:

"The default engine is MyISAM [1]. The main drawback of MyISAM is that it doesn't currently support transactions or foreign keys. On the plus side, it's currently the only engine that supports full-text indexing and searching.

"The InnoDB engine is fully transactional and supports foreign key references."

Fred Larson
Would someone like to explain their downvote?
Fred Larson
This says nothing that wasn't said already by the OP below.
Glenn Maynard