Mike Bayer avatar Mike Bayer committed 2fd686f

- [feature] Added "no_autoflush" context
manager to Session, used with with:
will temporarily disable autoflush.

Comments (0)

Files changed (5)

 0.7.6
 =====
 - orm
+  - [feature] Added "no_autoflush" context
+    manager to Session, used with with:
+    will temporarily disable autoflush.
+
   - [bug] Fixed bug whereby MappedCollection
     would not get the appropriate collection
     instrumentation if it were only used

lib/sqlalchemy/orm/session.py

 
         return self._query_cls(entities, self, **kwargs)
 
+    @property
+    @util.contextmanager
+    def no_autoflush(self):
+        """Return a context manager that disables autoflush.
+        
+        e.g.::
+        
+            with session.no_autoflush:
+                
+                some_object = SomeClass()
+                session.add(some_object)
+                # won't autoflush
+                some_object.related_thing = session.query(SomeRelated).first()
+        
+        Operations that proceed within the ``with:`` block
+        will not be subject to flushes occurring upon query
+        access.  This is useful when initializing a series
+        of objects which involve existing database queries,
+        where the uncompleted object should not yet be flushed.
+        
+        New in 0.7.6.
+
+        """
+        autoflush = self.autoflush
+        self.autoflush = False
+        yield self
+        self.autoflush = autoflush
+
     def _autoflush(self):
         if self.autoflush and not self._flushing:
             self.flush()

lib/sqlalchemy/util/__init__.py

 from compat import callable, cmp, reduce, defaultdict, py25_dict, \
     threading, py3k_warning, jython, pypy, win32, set_types, buffer, pickle, \
     update_wrapper, partial, md5_hex, decode_slice, dottedgetter,\
-    parse_qsl, any
+    parse_qsl, any, contextmanager
 
 from _collections import NamedTuple, ImmutableContainer, immutabledict, \
     Properties, OrderedProperties, ImmutableProperties, OrderedDict, \

lib/sqlalchemy/util/compat.py

 # end Py2K
 
 try:
+    from contextlib import contextmanager
+except ImportError:
+    def contextmanager(fn):
+        return fn
+
+try:
     from functools import update_wrapper
 except ImportError:
     def update_wrapper(wrapper, wrapped,

test/orm/test_session.py

         eq_(bind.connect().execute("select count(1) from users").scalar(), 1)
         sess.close()
 
+    @testing.requires.python26
+    def test_with_no_autoflush(self):
+        User, users = self.classes.User, self.tables.users
+
+        mapper(User, users)
+        sess = Session()
+
+        u = User()
+        u.name = 'ed'
+        sess.add(u)
+        def go(obj):
+            assert u not in sess.query(User).all()
+        testing.run_as_contextmanager(sess.no_autoflush, go)
+        assert u in sess.new
+        assert u in sess.query(User).all()
+        assert u not in sess.new
+
     def test_make_transient(self):
         users, User = self.tables.users, self.classes.User
 
Tip: Filter by directory path e.g. /media app.js to search for public/media/app.js.
Tip: Use camelCasing e.g. ProjME to search for ProjectModifiedEvent.java.
Tip: Filter by extension type e.g. /repo .js to search for all .js files in the /repo directory.
Tip: Separate your search with spaces e.g. /ssh pom.xml to search for src/ssh/pom.xml.
Tip: Use ↑ and ↓ arrow keys to navigate and return to view the file.
Tip: You can also navigate files with Ctrl+j (next) and Ctrl+k (previous) and view the file with Ctrl+o.
Tip: You can also navigate files with Alt+j (next) and Alt+k (previous) and view the file with Alt+o.