Releasing python software basically means you make a zipfile of couple of grouped-together python files. And of course this has to have a name, version, etc. The standard way of doing this in python is with setuptools.
If you use a couple of python files in several projects, you probably do not want to copy them around time and again. Fix a bug in one and the fix should end up in the others, too. It is handier to just use an installed package in each of your projects instead of coping around by hand.
So if you have an existing monolithic project, see if you can extract some useful functionality out of it so you can re-use it in another project. Once you get the hang of it it can give you loads of productivity! The cheaper and easier it is to re-use existing software, the quicker you can get things done. “Cheaper” does mean an initial price in setting up things and understanding the mechanisms. I’d personally say packaging often pays for itself real quick.
Packaging is a no-brainer if you want others to use your software. Or if you
have to distribute it to a customer. Non-packaged software is a maintenance
nightmare waiting to happen. It needs manual steps to “install”. You cannot
reliably override an older installation if all you do is putting
files in a directory. Old files will stay put. People will forget to
copy all files, leaving an old one in place (good luck debugging that one when
the customer phones you). People will copy files into the wrong directory.
Just package up your software properly and you can sleep more soundly at night.
The end result you want is:
import sample sample.utils.init_something('hurray') bla_bla = sample.database.BlaBla() bla_bla.calculate()
So: a couple of python files (
database.py in this case)
grouped together under one name so you can import them from somewhere else
import sample or
from sample import utils).
Take the python files you want to group together and put them in a directory with a good name:
__init__.pyin the directory to tell python that the directory contents are importable (see explanation). The
__init__.pycan be empty, but I normally put a
# packagecomment in it as empty files can give problems (like not showing up in “svn diff” sometimes).
You’ve probably seen instructions like:
python setup.py installon the extracted mypackage-1.0.tgz to install it”.
easy_install mypackageto install it”.
easy_install http://example.org/dist/mypackage-1.0.tgzto install it”.
These commands install the “mypackage” package neatly into your python’s
so-called “site-packages” directory. Dig around in your python installation,
you’ll find a
site-packages directory in there somewhere. Start up the
python prompt and you can do an
setup.py file is what makes all of this work. A
setuptools (or its replacement
distribute) to actually install
the software. This means placing a
setup.py in a directory and putting
your directory of grouped code in a subdirectory. An example:
setup.py tells a few things like name, version, dependencies:
from setuptools import setup setup(name='sample', version='1.0', description="My sample package", long_description="", author='Reinout', email@example.com', license='GPL', packages=['sample'], zip_safe=False, install_requires=['dependency1', 'dependency2'], )
I’ve left out quite a number of possible fields here. That’s one of the
setup.py rightfully mentioned by Jacob Kaplan-Moss: you basically
have to cargo-cult your config
files from other projects.
What this example config file tells setuptools, however, is:
site-packages/sample-1.0/.... And if you release it on pypi, the python package index, it will become http://pypi.python.org/pypi/sample.
packages=['sample']line tells that, inside the current directory,
sample/is an actual package (so: grouping of python files) that belongs in this “sample” package.
zip_safe=Falseis just there to make sure python unzips the package while installing it. So instead of one file (a zipped .egg) in your python site-package directory, you will get a directory with the unzipped contents of your package: waaaaay handier. (Corrected 2010-02-23 after tip from Maurits).
Plone, you’ll pull in virtually the whole world.
You of course want to install your software. Some ways to do this:
python setup.py installinstalls it in your system python.
python setup.py develop, which also installs it in your system python, but keeps track of changes. It is essentially a link to the directory you’re developing in. So changes in your code show up right away in the installed version. Only exception: if you’ve changed the
setup.py, you have to re-run
python setup.py develop.
python setup.py sdist, which creates a “source distribution”. Place the resulting
dist/sample-1.0.tar.gz(for example) somewhere on-line and tell others to do
python setup.py sdist register uploadwill upload the .tar.gz to the python package index, ready for all to install with a simple
My name is Reinout van Rees and I work a lot with Python (programming language) and Django (website framework). I live in The Netherlands and I'm happily married to Annie van Rees-Kooiman.
Most of my website content is in my weblog. You can keep up to date by subscribing to the automatic feeds (for instance with Google reader):