Commit 106a8dca authored by Tres Seaver's avatar Tres Seaver

Merge pull request #8 from NextThought/jython

In WeakSet, use the `valuerefs` method from Python 2.5 instead of accessing the internal `data` implementation detail.
parents bf6e186c b42a65c5
...@@ -4,6 +4,9 @@ Changes ...@@ -4,6 +4,9 @@ Changes
1.4.4 (unreleased) 1.4.4 (unreleased)
------------------ ------------------
- Use the standard ``valuerefs()`` method rather than relying on
implementation details of ``WeakValueDictionary`` in ``WeakSet``.
- Add support for PyPy3. - Add support for PyPy3.
- Require 100% branch coverage (in addition to 100% statement coverage). - Require 100% branch coverage (in addition to 100% statement coverage).
......
[tox] [tox]
# Jython 2.7rc2+ does work, but unfortunately has an issue running
# with Tox 1.9.2 (see https://github.com/pypa/virtualenv/pull/746)
envlist = envlist =
# Jython support pending 2.7 support, due 2012-07-15 or so. See:
# http://fwierzbicki.blogspot.com/2012/03/adconion-to-fund-jython-27.html
# py26,py27,py32,pypy,jython,coverage
py26,py27,pypy,py32,py33,py34,pypy3,coverage,docs py26,py27,pypy,py32,py33,py34,pypy3,coverage,docs
[testenv] [testenv]
...@@ -10,10 +9,6 @@ commands = ...@@ -10,10 +9,6 @@ commands =
python setup.py test -q python setup.py test -q
deps = transaction deps = transaction
[testenv:jython]
commands =
jython setup.py test -q
[testenv:coverage] [testenv:coverage]
basepython = basepython =
python2.6 python2.6
......
...@@ -2,6 +2,7 @@ import sys ...@@ -2,6 +2,7 @@ import sys
import types import types
PY3 = sys.version_info[0] == 3 PY3 = sys.version_info[0] == 3
JYTHON = sys.platform.startswith('java')
if PY3: # pragma: no cover if PY3: # pragma: no cover
string_types = str, string_types = str,
...@@ -87,4 +88,3 @@ if PY3: ...@@ -87,4 +88,3 @@ if PY3:
else: else:
def func_name(func): #pragma NO COVER def func_name(func): #pragma NO COVER
return func.func_name return func.func_name
...@@ -12,7 +12,7 @@ ...@@ -12,7 +12,7 @@
# #
############################################################################## ##############################################################################
import unittest import unittest
from transaction._compat import JYTHON
class WeakSetTests(unittest.TestCase): class WeakSetTests(unittest.TestCase):
def test_contains(self): def test_contains(self):
...@@ -35,6 +35,8 @@ class WeakSetTests(unittest.TestCase): ...@@ -35,6 +35,8 @@ class WeakSetTests(unittest.TestCase):
self.assertEqual(len(w), 2) self.assertEqual(len(w), 2)
del d1 del d1
gc.collect() gc.collect()
if not JYTHON:
# The Jython GC is non deterministic
self.assertEqual(len(w), 1) self.assertEqual(len(w), 1)
def test_remove(self): def test_remove(self):
......
...@@ -13,6 +13,7 @@ ...@@ -13,6 +13,7 @@
############################################################################ ############################################################################
import weakref import weakref
from ._compat import PY3
# A simple implementation of weak sets, supplying just enough of Python's # A simple implementation of weak sets, supplying just enough of Python's
# sets.Set interface for our needs. # sets.Set interface for our needs.
...@@ -62,7 +63,6 @@ class WeakSet(object): ...@@ -62,7 +63,6 @@ class WeakSet(object):
# underlying dict may change size during iteration, due to gc or # underlying dict may change size during iteration, due to gc or
# activity from other threads). as_weakef_list() is safe. # activity from other threads). as_weakef_list() is safe.
# #
# Something like this should really be a method of Python's weak dicts.
# If we invoke self.data.values() instead, we get back a list of live # If we invoke self.data.values() instead, we get back a list of live
# objects instead of weakrefs. If gc occurs while this list is alive, # objects instead of weakrefs. If gc occurs while this list is alive,
# all the objects move to an older generation (because they're strongly # all the objects move to an older generation (because they're strongly
...@@ -75,9 +75,12 @@ class WeakSet(object): ...@@ -75,9 +75,12 @@ class WeakSet(object):
# elements are actually trash. By returning a list of weakrefs instead, # elements are actually trash. By returning a list of weakrefs instead,
# we avoid that, although the decision to use weakrefs is now very # we avoid that, although the decision to use weakrefs is now very
# visible to our clients. # visible to our clients.
def as_weakref_list(self): if PY3: #pragma: no cover (coverage tests run under 2.7)
# We're cheating by breaking into the internals of Python's # Python 3: be sure to freeze the iterator, to avoid RuntimeError:
# WeakValueDictionary here (accessing its .data attribute).
# Python 3: be sure to freeze the list, to avoid RuntimeError:
# dictionary changed size during iteration. # dictionary changed size during iteration.
return list(self.data.data.values()) def as_weakref_list(self):
return list(self.data.valuerefs())
else:
# On Python2 we already get a list, no need to copy
def as_weakref_list(self):
return self.data.valuerefs()
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment