7

I have a setup.py that needs to support both Python 2 and 3.

The code currently works and is installable in Python 2.x

If I add the use_2to3 = True clause to my setup.py, then the module can be installed in Python 3, however, doing a:

python setup.py test

Causes a failure as one of the tests uses the StringIO class, and the import line goofs in Python 3 (it's currently from StringIO import StringIO, where in Python3 it should be from io import StringIO

I thought though that once you add the use_2to3 keyword all tests (including unittests) were processed by 2to3 before being tested.

What am I missing? In case it helps, the bulk of my setup.py looks like:

from setuptools import setup

setup(
    name='myproject',
    version='1.0',
    description='My Cool project',
    classifiers = [
        'Programming Language :: Python',
        'Programming Language :: Python :: 3',
    ],

    py_modules=['mymodule'],
    test_suite='test_mymodule',
    zip_safe=False,
    use_2to3 = True,
)

Edit: the reason I feel as though 2to3 isn't getting run on a python setup.py test is that it blows up & the bottom of the stacktrace reads:

File "/home/aparkin/temp/mymodule/test_mymodule.py", line 18, in <module>
    from StringIO import StringIO

But if I ran 2to3 on test_mymodule.py, then that import line should've been reworked to:

from io import StringIO

And (at worst) the tests should just individually fail.

Adam Parkin
  • 17,891
  • 17
  • 66
  • 87

1 Answers1

1

In order for distribute to pick your module up and run in through 2to3, it must be listed in py_modules. So change that to:

py_modules=['mymodule', 'test_mymodule'],

Unfortunately this has a side-effect of installing test_mymodule when you install the project, which you probably did not want. For cases like this I will generally convert the project into a package with a mymodule.tests sub-package. This way the tests can be "installable" without adding additional clutter.

Iguananaut
  • 21,810
  • 5
  • 50
  • 63
  • 1
    What do you mean by mymodule.tests sub-package? – Cameron White Dec 19 '13 at 02:16
  • I mean make a package called "mymodule" and under it create a directory called "tests" and put all your test modules under that, remembering to include an `__init__.py`as well so that tests is a subpackage of mymodule (hence mymodule.tests) – Iguananaut Dec 19 '13 at 03:34