:version: 0.9.7
:released:
+ .. change::
+ :tags: bug, orm
+ :tickets: 3108
+ :versions: 1.0.0
+
+ Fixed bug where items that were persisted, deleted, or had a
+ primary key change within a savepoint block would not
+ participate in being restored to their former state (not in
+ session, in session, previous PK) after the outer transaction
+ were rolled back.
+
.. change::
:tags: bug, orm
:tickets: 3106
for s in self._deleted:
s.session_id = None
self._deleted.clear()
-
+ elif self.nested:
+ self._parent._new.update(self._new)
+ self._parent._deleted.update(self._deleted)
+ self._parent._key_switches.update(self._key_switches)
def _connection_for_bind(self, bind):
self._assert_active()
assert session.query(User).get([1, PUBLISHED]) is a_published
assert session.query(User).get([1, EDITABLE]) is a_editable
+ @testing.requires.savepoints
+ def test_reverse_savepoint(self):
+ user, User = self.tables.user, self.classes.User
+
+ PUBLISHED, EDITABLE, ARCHIVED = 1, 2, 3
+
+ mapper(User, user)
+
+ session = sa.orm.sessionmaker()()
+
+ a_published = User(1, PUBLISHED, 'a')
+ session.add(a_published)
+ session.commit()
+
+ a_editable = User(1, EDITABLE, 'a')
+
+ session.add(a_editable)
+ session.commit()
+
+ # testing #3108
+ session.begin_nested()
+
+ a_published.status = ARCHIVED
+ a_editable.status = PUBLISHED
+
+ session.commit()
+
+ session.rollback()
+ eq_(a_published.status, PUBLISHED)
+ eq_(a_editable.status, EDITABLE)
class SelfReferentialTest(fixtures.MappedTest):
# mssql, mysql don't allow
raise
+ @testing.requires.savepoints
+ def test_nested_accounting_new_items_removed(self):
+ User, users = self.classes.User, self.tables.users
+
+ mapper(User, users)
+
+ session = create_session(bind=testing.db)
+ session.begin()
+ session.begin_nested()
+ u1 = User(name='u1')
+ session.add(u1)
+ session.commit()
+ assert u1 in session
+ session.rollback()
+ assert u1 not in session
+
+ @testing.requires.savepoints
+ def test_nested_accounting_deleted_items_restored(self):
+ User, users = self.classes.User, self.tables.users
+
+ mapper(User, users)
+
+ session = create_session(bind=testing.db)
+ session.begin()
+ u1 = User(name='u1')
+ session.add(u1)
+ session.commit()
+
+ session.begin()
+ u1 = session.query(User).first()
+
+ session.begin_nested()
+ session.delete(u1)
+ session.commit()
+ assert u1 not in session
+ session.rollback()
+ assert u1 in session
@testing.requires.savepoints
def test_heavy_nesting(self):