OS-X: fix package generation

The old scheme depended upon the bespoke pseudo-virtualenv scheme that
we cooked up long ago (it copied the entire source tree, bin/tahoe and
support/ and all, into the mac .pkg archive). When we moved to real
virtualenvs, that broke.

This new scheme only installs a populated virtualenv into the archive.
It replaces the entry-point bin/tahoe with a script that behaves a lot
like the old bespoke script: it inserts a relative site-packages/ into
sys.path before importing allmydata.scripts.runner and calling run().

This still depends upon the end-users $PATH having a python that is
compatible with the binary modules we've compiled here, and there are
three potentially-differing Pythons to worry about (homebrew, python.org
installers, and Apple's native /usr/bin/python). We'll have to see if
they tend to differ in ways that cause problems (I think the maintainers
generally try to avoid that). If that's an issue, the next level up is
to use bbfreeze or py2app or something in that category, to ship an
entire python, and not just a bundle of libraries.
This commit is contained in:
Brian Warner 2016-03-16 12:31:21 -07:00
parent 082bc3de6f
commit b5b2036d37

View File

@ -1,22 +1,52 @@
#!/bin/sh
APPNAME=$1
VERSION=`sh -c "cat src/allmydata/_version.py | grep verstr | head -n 1 | cut -d' ' -f 3" | sed "s/'//g"`
PWD=`pwd`
TARGET="/Applications/tahoe.app"
# The editing of allmydata-tahoe.egg-link and easy-install.pth files
# (*in-place*) ensures that we reference the source at the correct path,
# removing the hard-coded local source tree directory names.
#
find support -name $APPNAME.egg-link -execdir sh -c "echo >> {}; echo /Applications/tahoe.app/src >> {}" \;
find support -name easy-install.pth -execdir sed -i.bak 's|^.*/src$|../../../../src|' '{}' \;
virtualenv osx-venv
osx-venv/bin/pip install .
# The virtualenv contains all the dependencies we need, but the bin/python
# itself is not useful, nor is having it as the shbang line in the generated
# bin/tahoe executable. Replace bin/tahoe with a form that explicitly sets
# sys.path to the target directory (/Applications/tahoe.app). This isn't as
# isolated as a proper virtualenv would be (the system site-packages
# directory will still appear later in sys.path), but I think it ought to
# work.
rm osx-venv/bin/*
cat >osx-venv/bin/tahoe <<EOF
#!/usr/bin/env python
import sys, os.path
up = os.path.dirname
bintahoe = os.path.abspath(__file__)
appdir = up(up(bintahoe))
sitedir = os.path.join(appdir, "lib", "python2.7", "site-packages")
# usually "/Applications/tahoe.app/lib/python2.7/site-packages"
sys.path.insert(0, sitedir)
from allmydata.scripts.runner import run
run()
EOF
chmod +x osx-venv/bin/tahoe
# The venv has a .pth file which allows "import zope.interface" to work even
# though "zope" isn't really a package (it has no __init__.py). The venv's
# python has this site-packages/ on sys.path early enough to process the .pth
# file, and running tahoe with PYTHONPATH=...site-packages would also process
# it, but a simple sys.path.insert doesn't. This is the simplest hack I could
# find to fix it.
touch osx-venv/lib/python2.7/site-packages/zope/__init__.py
cp -r $PWD/misc/build_helpers/osx/Contents osx-venv/Contents
# create component pkg
pkgbuild --root "$PWD" \
pkgbuild --root osx-venv \
--identifier com.leastauthority.tahoe \
--version "$VERSION" \
--ownership recommended \
--install-location /Applications/tahoe.app \
--install-location $TARGET \
--scripts "$PWD/misc/build_helpers/osx/scripts" \
tahoe-lafs.pkg