diff options
-rw-r--r-- | doc/build/changelog/changelog_08.rst | 9 | ||||
-rw-r--r-- | doc/build/changelog/changelog_09.rst | 9 | ||||
-rw-r--r-- | lib/sqlalchemy/orm/util.py | 1 | ||||
-rw-r--r-- | lib/sqlalchemy/util/_collections.py | 15 |
4 files changed, 29 insertions, 5 deletions
diff --git a/doc/build/changelog/changelog_08.rst b/doc/build/changelog/changelog_08.rst index 9d7b4b975..3e61ac570 100644 --- a/doc/build/changelog/changelog_08.rst +++ b/doc/build/changelog/changelog_08.rst @@ -7,6 +7,15 @@ :version: 0.8.3 .. change:: + :tags: bug, orm + :tickets: 2794 + + Fixed a potential issue in an ordered sequence implementation used + by the ORM to iterate mapper hierarchies; under the Jython interpreter + this implementation wasn't ordered, even though cPython and Pypy + maintained ordering. + + .. change:: :tags: bug, sql :tickets: 2801 diff --git a/doc/build/changelog/changelog_09.rst b/doc/build/changelog/changelog_09.rst index cc9954120..3c38367f2 100644 --- a/doc/build/changelog/changelog_09.rst +++ b/doc/build/changelog/changelog_09.rst @@ -7,6 +7,15 @@ :version: 0.9.0 .. change:: + :tags: bug, orm + :tickets: 2794 + + Fixed a potential issue in an ordered sequence implementation used + by the ORM to iterate mapper hierarchies; under the Jython interpreter + this implementation wasn't ordered, even though cPython and Pypy + maintained ordering. Also in 0.8.3. + + .. change:: :tags: bug, sql :tickets: 2801 diff --git a/lib/sqlalchemy/orm/util.py b/lib/sqlalchemy/orm/util.py index d88164e7d..973707249 100644 --- a/lib/sqlalchemy/orm/util.py +++ b/lib/sqlalchemy/orm/util.py @@ -911,3 +911,4 @@ def randomize_unitofwork(): from sqlalchemy.testing.util import RandomSet topological.set = unitofwork.set = session.set = mapper.set = \ dependency.set = RandomSet + diff --git a/lib/sqlalchemy/util/_collections.py b/lib/sqlalchemy/util/_collections.py index c3b44abae..b2e5c6250 100644 --- a/lib/sqlalchemy/util/_collections.py +++ b/lib/sqlalchemy/util/_collections.py @@ -650,18 +650,23 @@ class IdentitySet(object): class WeakSequence(object): def __init__(self, elements): - self._storage = weakref.WeakValueDictionary( - (idx, element) for idx, element in enumerate(elements) - ) + self._storage = [ + weakref.ref(element) for element in elements + ] + + def _remove(self, ref): + self._storage.remove(ref) def __iter__(self): - return iter(self._storage.values()) + return (obj for obj in (ref() for ref in self._storage) if obj is not None) def __getitem__(self, index): try: - return self._storage[index] + obj = self._storage[index] except KeyError: raise IndexError("Index %s out of range" % index) + else: + return obj() class OrderedIdentitySet(IdentitySet): |