What is the correct way to share package version with setup.py and the package?

distutils, python, setuptools

Solution

Set the version in `setup.py` only, and read your own version with `pkg_resources`, effectively querying the `setuptools` metadata:

file: `setup.py`

setup(
    name='foobar',
    version='1.0.0',
    # other attributes
)

file: `__init__.py`

from pkg_resources import get_distribution

__version__ = get_distribution('foobar').version

To make this work in all cases, where you could end up running this without having installed it, test for `DistributionNotFound` and the distribution location:

from pkg_resources import get_distribution, DistributionNotFound
import os.path

try:
    _dist = get_distribution('foobar')
    # Normalize case for Windows systems
    dist_loc = os.path.normcase(_dist.location)
    here = os.path.normcase(__file__)
    if not here.startswith(os.path.join(dist_loc, 'foobar')):
        # not installed, but there is another version that *is*
        raise DistributionNotFound
except DistributionNotFound:
    __version__ = 'Please install this project with setup.py'
else:
    __version__ = _dist.version

Problem

With `distutils`, `setuptools`, etc. a package version is specified in `setup.py`: ``` # file: setup.py ... setup( name='foobar', version='1.0.0', # other attributes ) ``` I would like to be able to access the same version number from within the package: ``` >>> import foobar >>> foobar.__version__ '1.0.0' ``` I could add `__version__ = '1.0.0'` to my package's __init__.py, but I would also like to include additional imports in my package to create a simplified interface to the package: ``` # file: __init__.py from foobar import foo from foobar.bar import Bar __version__ = '1.0.0' ``` and ``` # file: setup.py from foobar import __version__ ... setup( name='foobar', version=__version__, # other attributes ) ``` However, these additional imports can cause the installation of `foobar` to fail if they import other packages that are not yet installed. What is the correct way to share package version with setup.py and the package?

Original source

Related problems