Commit 44b7b85e authored by Jason Madden's avatar Jason Madden

In WeakSet, use the `valuerefs` method, added in Python 2.5 instead of...

In WeakSet, use the `valuerefs` method, added in Python 2.5 instead of accessing the internal `data` implementation detail.

This lets us support Jython.
parent bf6e186c
...@@ -11,6 +11,27 @@ python: ...@@ -11,6 +11,27 @@ python:
install: install:
- pip install . --use-mirrors - pip install . --use-mirrors
script: script:
- python setup.py test -q - $PYTHON_EXE setup.py test -q
notifications: notifications:
email: false email: false
env:
- JYTHON=true
- JYTHON=false
before_script: if [ "$JYTHON" == "true" ]; then export PYTHON_EXE=jython; jython -c "print ''"; else export PYTHON_EXE=python; fi
before_install:
- export JYTHON_URL='http://search.maven.org/remotecontent?filepath=org/python/jython-installer/2.7-rc2/jython-installer-2.7-rc2.jar'
- if [ "$JYTHON" == "true" ]; then wget $JYTHON_URL -O jython_installer.jar; java -jar jython_installer.jar -s -d $HOME/jython; export PATH=$HOME/jython:$PATH; fi
matrix:
exclude:
- python: 2.6
env: JYTHON=true
- python: 3.2
env: JYTHON=true
- python: 3.3
env: JYTHON=true
- python: 3.4
env: JYTHON=true
- python: pypy
env: JYTHON=true
- python: pypy3
env: JYTHON=true
...@@ -4,7 +4,7 @@ Changes ...@@ -4,7 +4,7 @@ Changes
1.4.4 (unreleased) 1.4.4 (unreleased)
------------------ ------------------
- Add support for PyPy3. - Add support for PyPy3 and Jython 2.7.
- Require 100% branch coverage (in addition to 100% statement coverage). - Require 100% branch coverage (in addition to 100% statement coverage).
......
...@@ -48,6 +48,7 @@ setup(name='transaction', ...@@ -48,6 +48,7 @@ setup(name='transaction',
"Programming Language :: Python :: 3.4", "Programming Language :: Python :: 3.4",
"Programming Language :: Python :: Implementation :: CPython", "Programming Language :: Python :: Implementation :: CPython",
"Programming Language :: Python :: Implementation :: PyPy", "Programming Language :: Python :: Implementation :: PyPy",
"Programming Language :: Python :: Implementation :: Jython",
"Framework :: ZODB", "Framework :: ZODB",
], ],
author="Zope Corporation", author="Zope Corporation",
......
[tox] [tox]
envlist = # Jython 2.7rc2 does work, but unfortunately has an issue running
# Jython support pending 2.7 support, due 2012-07-15 or so. See: # with Tox 1.9.2 (apparently its non-interactive console still prints
# http://fwierzbicki.blogspot.com/2012/03/adconion-to-fund-jython-27.html # interactive prompts ):
# py26,py27,py32,pypy,jython,coverage # $ tox -e jython
# ...
# ERROR: InvocationError: Failed to get version_info for jython: could not decode ">>> ... ... ... >>> {'version_info': (2, 7, 0, 'candidate', 2)}\n>>> "
envlist =
py26,py27,pypy,py32,py33,py34,pypy3,coverage,docs py26,py27,pypy,py32,py33,py34,pypy3,coverage,docs
[testenv] [testenv]
commands = commands =
python setup.py test -q python setup.py test -q
deps = transaction deps = transaction
[testenv:jython] [testenv:jython]
commands = commands =
jython setup.py test -q jython setup.py test -q
[testenv:coverage] [testenv:coverage]
basepython = basepython =
python2.6 python2.6
commands = commands =
nosetests --with-xunit --with-xcoverage nosetests --with-xunit --with-xcoverage
deps = deps =
nose nose
...@@ -27,7 +30,7 @@ deps = ...@@ -27,7 +30,7 @@ deps =
[testenv:docs] [testenv:docs]
basepython = basepython =
python2.6 python2.6
commands = commands =
sphinx-build -b html -d docs/_build/doctrees docs docs/_build/html sphinx-build -b html -d docs/_build/doctrees docs docs/_build/html
sphinx-build -b doctest -d docs/_build/doctrees docs docs/_build/doctest sphinx-build -b doctest -d docs/_build/doctrees docs docs/_build/doctest
deps = deps =
......
...@@ -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,
...@@ -79,12 +80,11 @@ if PY3: #pragma NO COVER ...@@ -79,12 +80,11 @@ if PY3: #pragma NO COVER
from threading import _get_ident as get_thread_ident from threading import _get_ident as get_thread_ident
else: else:
from thread import get_ident as get_thread_ident from thread import get_ident as get_thread_ident
if PY3: if PY3:
def func_name(func): #pragma NO COVER def func_name(func): #pragma NO COVER
return func.__name__ return func.__name__
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,7 +35,9 @@ class WeakSetTests(unittest.TestCase): ...@@ -35,7 +35,9 @@ class WeakSetTests(unittest.TestCase):
self.assertEqual(len(w), 2) self.assertEqual(len(w), 2)
del d1 del d1
gc.collect() gc.collect()
self.assertEqual(len(w), 1) if not JYTHON:
# The Jython GC is non deterministic
self.assertEqual(len(w), 1)
def test_remove(self): def test_remove(self):
from transaction.weakset import WeakSet from transaction.weakset import WeakSet
...@@ -100,17 +102,17 @@ class WeakSetTests(unittest.TestCase): ...@@ -100,17 +102,17 @@ class WeakSetTests(unittest.TestCase):
gc.collect() gc.collect()
return result return result
w.as_weakref_list = _as_weakref_list w.as_weakref_list = _as_weakref_list
def poker(x): def poker(x):
x.poked = 1 x.poked = 1
w.map(poker) w.map(poker)
for thing in dummy, dummy2: for thing in dummy, dummy2:
self.assertEqual(thing.poked, 1) self.assertEqual(thing.poked, 1)
class Dummy: class Dummy:
pass pass
def test_suite(): def test_suite():
return unittest.makeSuite(WeakSetTests) return unittest.makeSuite(WeakSetTests)
...@@ -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
...@@ -76,8 +76,8 @@ class WeakSet(object): ...@@ -76,8 +76,8 @@ class WeakSet(object):
# 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): def as_weakref_list(self):
# 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()) # On Python2 we already get a list, no need to copy
refs = self.data.valuerefs()
return list(refs) if PY3 else refs
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