Ticket #9206: extra_v3.diff

File extra_v3.diff, 3.8 KB (added by Richard Davies <richard.davies@…>, 15 years ago)

New draft again of extra piece

  • docs/topics/db/transactions.txt

     
    166166
    167167.. _information on MySQL transactions: http://dev.mysql.com/doc/refman/5.0/en/sql-syntax-transactions.html
    168168
    169 Transactions and savepoints in PostgreSQL 8
    170 ===========================================
     169Database exceptions within PostgreSQL transactions
     170==================================================
    171171
    172 When a call to a PostgreSQL 8 cursor raises an exception, all subsequent SQL
    173 in the same transaction fails with the error "current transaction is aborted,
    174 queries ignored until end of transaction block". Whilst simple use of save()
    175 is unlikely to raise an exception in PostgreSQL, there are many more advanced
    176 usage patterns which might: for example, saving objects with unique fields,
    177 saving using the force_insert/force_update flag, or invoking custom SQL.
     172When a call to a PostgreSQL cursor raises an exception (typically
     173``IntegrityError``), all subsequent SQL in the same transaction fails with
     174the error "current transaction is aborted, queries ignored until end of
     175transaction block".  Whilst simple use of save() is unlikely to raise an
     176exception in PostgreSQL, there are many more advanced usage patterns which
     177might: for example, saving objects with unique fields, saving using the
     178force_insert/force_update flag, or invoking custom SQL.  Example::
    178179
    179 In any of these cases, you can wrap the command which may throw
    180 IntegrityError inside savepoints, which will then allow subsequent commands
    181 to proceed. Example::
    182 
     180    a.save() # succeeds
    183181    try:
    184       sid = transaction.savepoint()
    185       x.save()
    186       transaction.savepoint_commit(sid)
    187     except IntegrityError:
    188       transaction.savepoint_rollback(sid)
    189       raise
     182      b.save() # throws exception due to unique field
     183    except:
     184      pass
     185    c.save() # fails as current transaction is aborted
    190186
    191 Savepoints are not implemented in PostgreSQL 7. If you experience an
    192 IntegrityError when using PostgreSQL 7, you will need to rollback to the
    193 start of the transaction.
     187There are three possible solutions to this issue:
     188
     189    * With any version of PostgreSQL, you can rollback to the start of the
     190      transaction if you experience an exception. Example::
     191
     192          a.save() # succeeds, but may be undone by rollback
     193          try:
     194            b.save() # throws exception due to unique field
     195          except:
     196            transaction.rollback()
     197          c.save() # succeeds
     198
     199      Note that under the ``commit_on_success`` or ``commit_manually``
     200      decorators the rollback will also undo ``a.save()``.
     201
     202    * With PostgreSQL 8 or later, you can wrap just the command which may
     203      raise an exception inside savepoints, isolating the rollback. Example::
     204
     205          a.save() # succeeds, and never undone by savepoint rollback
     206          try:
     207            sid = transaction.savepoint()
     208            b.save() # throws exception due to unique field
     209            transaction.savepoint_commit(sid)
     210          except:
     211            transaction.savepoint_rollback(sid)
     212          c.save() # succeeds
     213
     214    * With PostgreSQL 8.2 or later, there is an advanced option to run
     215      PostgreSQL with :ref:`database-level autocommit <ref-databases>`.
     216      With this option there is no constantly open transaction, so
     217      savepoints are not required to continue after catching an exception.
     218      Please see the documentation for that feature, which behaves
     219      differently from the standard ``autocommit`` decorator. Example::
     220
     221         a.save() # succeeds
     222         try:
     223           b.save() # throws exception due to unique field
     224         except:
     225           pass
     226         c.save() # succeeds
Back to Top