Intro to Python Packaging
http://slid.es/edwardliaw/python-packaging
Edward Liaw
2013-12-05
What we'll talk about today
How to install packages
How to set up a development environment
How to make your own packages
The Toolkit
Pip
Package manager that fetches from pypi.python.org
Virtualenv
Create isolated environments of installed packages
Setuptools
Packaging tool that makes installation/distribution easy
Pip
Install it
# Pip is automatically installed in new virtualenvs by the way
# Install setuptools first
curl -O https://bitbucket.org/pypa/setuptools/raw/bootstrap/ez_setup.py
python ez_setup.py
# Install pip via setuptools' easy_install script
easy_install pip
Install something?!
pip install ipython
Virtualenv
Install it
pip install virtualenv
# Or manually
curl -O https://pypi.python.org/packages/source/v/virtualenv/virtualenv-1.10.1.tar.gz
tar xzf virtualenv-1.10.1.tar.gz
cd virtualenv-1.10.1
python setup.py install
Create a new environment
virtualenv ~/.local/python27
# Handy defs for your .bash config
export VIRTUAL_ENV_DISABLE_PROMPT=1
function act-py2() { source ~/.local/python27/bin/activate; }
act-py2
deactivate
Managing venvs with virtualenvwrapper
# Install in base python (not in a virtualenv)
pip install virtualenvwrapper
# For your .bash config
export WORKON_HOME="~/.venvs"
[[ -f "/usr/local/bin/virtualenvwrapper.sh" ]] && source "/usr/local/bin/virtualenvwrapper.sh"
mkdir -p $WORKON_HOME
mkvirtualenv python27
workon python27
deactivate
Benefits
Keeps your venvs in one placeScripts to create, switch, delete, query installed packages, etc.
Auto-venv switching with autoenv
Small time-saver for developing on many projects (with many venvs)
Overrides cd
Not for me...
Let's make a package!
Read the docs
http://pythonhosted.org/setuptools/setuptools.html
Code
Getting started
setup.py
Where is your code is located?
Package dependencies?
Installation procedures?
Metadata for uploading to PyPI?
Simple setup.py
from setuptools import setup, find_packages
setup(
name = "demo_project",
version = "0.1",
packages = find_packages(),
)
Install as development package (symlink)
python setup.py develop
Hard install (copy)
python setup.py install
Readme
from setuptools import setup, find_packages
def readme():
with open("README.md") as f:
return f.read()
setup(
name = "demo_project",
version = "0.1",
packages = find_packages(),
long_description = readme(),
)
Metadata for PyPI
from setuptools import setup, find_packages
def readme():
with open("README.md") as f:
return f.read()
setup(
name = "demo_project",
version = "0.1",
packages = find_packages(),
# Metadata
author = "Me",
author_email = "me@gmail.com",
description = "A demonstration of setuptools' packaging system",
license = "None",
keywords = "example",
url = "https://github.com/edliaw/demo_project",
long_description = readme(),
# etc....
)
Directory structure
demo_project/
README.md
setup.py
demo_project/
__init__.py
hello.py
Modules
demo_project/
README.md
setup.py
demo_project/
__init__.py
hello.py
math/
__init__.py
fibonacci.py
Tests
demo_project/
README.md
setup.py
demo_project/
__init__.py
hello.py
math/
__init__.py
fibonacci.py
tests/
__init__.py
test_fibonacci.py
tests/
__init__.py
test_all.py
Scripts
demo_project/
README.md
setup.py
demo_project/
__init__.py
hello.py
math/
__init__.py
fibonacci.py
tests/
__init__.py
test_fibonacci.py
tests/
__init__.py
test_all.py
scripts/
fibonacci
setup.py++
from setuptools import setup, find_packages
setup(
name = "demo_project",
version = "0.1",
packages = find_packages(),
)
Exclusion rules
from setuptools import setup, find_packages
setup(
name = "demo_project",
version = "0.1",
packages = find_packages(exclude=["*.tests", "tests.*", "*.tests.*", "tests"]),
)
Tests
from setuptools import setup, find_packages
setup(
name = "demo_project",
version = "0.1",
packages = find_packages(exclude=["*.tests", "tests.*", "*.tests.*", "tests"]),
test_suite = "demo_project.tests.test_all",
)
Scripts
from setuptools import setup, find_packages
setup(
name = "demo_project",
version = "0.1",
packages = find_packages(exclude=["*.tests", "tests.*", "*.tests.*", "tests"]),
test_suite = "demo_project.tests.test_all",
scripts = ["scripts/fibonacci"],
)
Dependencies
from setuptools import setup, find_packages
setup(
name = "demo_project",
version = "0.1",
packages = find_packages(exclude=["*.tests", "tests.*", "*.tests.*", "tests"]),
test_suite = "demo_project.tests.test_all",
scripts = ["scripts/fibonacci"],
install_requires = [""],
)
Scripts #2
setup(
...
scripts = ["scripts/fibonacci"],
)
Another way of specifying scripts is as entry points to functions:
setup(
...
entry_points = {
'console_scripts' : [
'fibonacci = math.fibonacci.main',
],
'gui_scripts' : [
],
}
)
Python Packaging
By Edward Liaw
Python Packaging
Packaging using pip, setuptools, and virtualenv!
- 1,461